Explain preconditions whenever UNSAFE_BUFFER_USAGE.

Prototype what a requirement that all UNSAFE_BUFFER_USAGE be
accompanied by a `/ PRECONDITIONS` comment would look like. Such
a requirement (as opposed to writing `// SAFETY`, say) allows
better documentation.

Bug: 415821827
Change-Id: I2456ab7fbdc9b272df834d883ab72257cc9a33d8
Reviewed-on: https://pdfium-review.googlesource.com/c/pdfium/+/131610
Reviewed-by: Lei Zhang <thestig@chromium.org>
Commit-Queue: Tom Sepez <tsepez@chromium.org>
diff --git a/core/fxcodec/gif/lzw_decompressor.h b/core/fxcodec/gif/lzw_decompressor.h
index 50fe0f7..1d572d0 100644
--- a/core/fxcodec/gif/lzw_decompressor.h
+++ b/core/fxcodec/gif/lzw_decompressor.h
@@ -42,6 +42,8 @@
   void SetSource(pdfium::span<const uint8_t> src_buf) {
     avail_input_ = src_buf;
   }
+
+  // PRECONDITIONS: `dest_buf` must point to memory of `*dest_size` bytes.
   UNSAFE_BUFFER_USAGE Status Decode(uint8_t* dest_buf, uint32_t* dest_size);
 
   // Used by unittests, should not be called in production code.
diff --git a/core/fxcodec/jbig2/JBig2_Image.h b/core/fxcodec/jbig2/JBig2_Image.h
index a56960c..55d7e3e 100644
--- a/core/fxcodec/jbig2/JBig2_Image.h
+++ b/core/fxcodec/jbig2/JBig2_Image.h
@@ -48,8 +48,9 @@
   int GetPixel(int32_t x, int32_t y) const;
   void SetPixel(int32_t x, int32_t y, int v);
 
-  // SAFETY: propogated to caller via UNSAFE_BUFFER_USAGE.
+  // PRECONDITIONS: `y` must refer to a line within the image.
   UNSAFE_BUFFER_USAGE uint8_t* GetLineUnsafe(int32_t y) const {
+    // SAFETY: propogated to caller via UNSAFE_BUFFER_USAGE.
     return UNSAFE_BUFFERS(data() + y * stride_);
   }
 
diff --git a/core/fxcrt/bytestring.h b/core/fxcrt/bytestring.h
index 3beb998..92aaf8b 100644
--- a/core/fxcrt/bytestring.h
+++ b/core/fxcrt/bytestring.h
@@ -36,6 +36,7 @@
 
   ~ByteString() = default;
 
+  // PRECONDITIONS: `pStr` must point to `len` valid bytes.
   UNSAFE_BUFFER_USAGE ByteString(const char* pStr, size_t len);
   UNSAFE_BUFFER_USAGE ByteString(const uint8_t* pStr, size_t len);
 
diff --git a/core/fxcrt/fixed_size_data_vector.h b/core/fxcrt/fixed_size_data_vector.h
index fd01fae..e72e88d 100644
--- a/core/fxcrt/fixed_size_data_vector.h
+++ b/core/fxcrt/fixed_size_data_vector.h
@@ -131,6 +131,7 @@
   pdfium::span<const T> last(size_t count) const { return span().last(count); }
 
  private:
+  // PRECONDITIONS: `ptr` must point to `size` consecutive T elements.
   UNSAFE_BUFFER_USAGE FixedSizeDataVector(T* ptr, size_t size)
       : data_(ptr), size_(size) {}
 
diff --git a/core/fxcrt/fx_extension.h b/core/fxcrt/fx_extension.h
index af2c932..8f5b54e 100644
--- a/core/fxcrt/fx_extension.h
+++ b/core/fxcrt/fx_extension.h
@@ -29,6 +29,7 @@
 
 float FXSYS_wcstof(WideStringView pwsStr, size_t* pUsedLen);
 
+// PRECONDITIONS: `dstStr` and `srcStr` must point to `count` valid wchars.
 UNSAFE_BUFFER_USAGE wchar_t* FXSYS_wcsncpy(wchar_t* dstStr,
                                            const wchar_t* srcStr,
                                            size_t count);
diff --git a/core/fxcrt/widestring.h b/core/fxcrt/widestring.h
index 7dc81c4..a5f203e 100644
--- a/core/fxcrt/widestring.h
+++ b/core/fxcrt/widestring.h
@@ -40,6 +40,7 @@
 
   ~WideString() = default;
 
+  // PRECONDITIONS: `pStr` must point to `len` valid wchars.
   UNSAFE_BUFFER_USAGE WideString(const wchar_t* pStr, size_t len);
 
   // Make a one-character string from one wide char.
diff --git a/core/fxcrt/zip.h b/core/fxcrt/zip.h
index 738030f..8a44a16 100644
--- a/core/fxcrt/zip.h
+++ b/core/fxcrt/zip.h
@@ -49,6 +49,7 @@
       return lhs.first == rhs.first;
     }
 
+    // PRECONDITIONS: Iter must not have reached end().
     UNSAFE_BUFFER_USAGE Iter& operator++() {
       // SAFETY: required from caller, enforced by UNSAFE_BUFFER_USAGE.
       UNSAFE_BUFFERS(++first);
@@ -85,6 +86,7 @@
       return lhs.first == rhs.first;
     }
 
+    // PRECONDITIONS: Iter must not have reached end().
     UNSAFE_BUFFER_USAGE Iter& operator++() {
       // SAFETY: required from caller, enforced by UNSAFE_BUFFER_USAGE.
       UNSAFE_BUFFERS(++first);
diff --git a/core/fxge/dib/fx_dib.h b/core/fxge/dib/fx_dib.h
index 6ca3062..ed6cbfd 100644
--- a/core/fxge/dib/fx_dib.h
+++ b/core/fxge/dib/fx_dib.h
@@ -211,32 +211,36 @@
   ((uint8_t)(argb >> 16) | ((uint8_t)(argb >> 8)) << 8 | \
    ((uint8_t)(argb)) << 16 | ((uint8_t)(argb >> 24) << 24))
 
-// SAFETY: Caller must ensure 4 valid bytes at `p`.
+// PRECONDITIONS: Caller must ensure 4 valid bytes at `p`.
 UNSAFE_BUFFER_USAGE inline FX_ARGB FXARGB_GetDIB(const uint8_t* p) {
+  // SAFETY: required from caller, enforced by UNSAFE_BUFFER_USAGE.
   return ArgbEncode(UNSAFE_BUFFERS(p[3]), UNSAFE_BUFFERS(p[2]),
                     UNSAFE_BUFFERS(p[1]), UNSAFE_BUFFERS(p[0]));
 }
 
-// SAFETY: Caller must ensure 4 valid bytes at `p`.
+// PRECONDITIONS: Caller must ensure 4 valid bytes at `p`.
 UNSAFE_BUFFER_USAGE inline void FXARGB_SetDIB(uint8_t* p, uint32_t argb) {
+  // SAFETY: required from caller, enforced by UNSAFE_BUFFER_USAGE.
   UNSAFE_BUFFERS(p[0]) = FXARGB_B(argb);
   UNSAFE_BUFFERS(p[1]) = FXARGB_G(argb);
   UNSAFE_BUFFERS(p[2]) = FXARGB_R(argb);
   UNSAFE_BUFFERS(p[3]) = FXARGB_A(argb);
 }
 
-// SAFETY: Caller must ensure 4 valid bytes at `p`.
+// PRECONDITIONS: Caller must ensure 4 valid bytes at `p`.
 UNSAFE_BUFFER_USAGE inline void FXARGB_SetRGBOrderDIB(uint8_t* p,
                                                       uint32_t argb) {
+  // SAFETY: required from caller, enforced by UNSAFE_BUFFER_USAGE.
   UNSAFE_BUFFERS(p[0]) = FXARGB_R(argb);
   UNSAFE_BUFFERS(p[1]) = FXARGB_G(argb);
   UNSAFE_BUFFERS(p[2]) = FXARGB_B(argb);
   UNSAFE_BUFFERS(p[3]) = FXARGB_A(argb);
 }
 
-// SAFETY: Caller must ensure 3 valid bytes at `dest` and `src`.
+// PRECONDITIONS: Caller must ensure 3 valid bytes at `dest` and `src`.
 UNSAFE_BUFFER_USAGE inline void ReverseCopy3Bytes(uint8_t* dest,
                                                   const uint8_t* src) {
+  // SAFETY: required from caller, enforced by UNSAFE_BUFFER_USAGE.
   UNSAFE_BUFFERS(dest[2] = src[0]);
   UNSAFE_BUFFERS(dest[1] = src[1]);
   UNSAFE_BUFFERS(dest[0] = src[2]);
diff --git a/fpdfsdk/cpdfsdk_helpers.h b/fpdfsdk/cpdfsdk_helpers.h
index 90cdc96..6231757 100644
--- a/fpdfsdk/cpdfsdk_helpers.h
+++ b/fpdfsdk/cpdfsdk_helpers.h
@@ -274,15 +274,18 @@
 
 CPDFSDK_InteractiveForm* FormHandleToInteractiveForm(FPDF_FORMHANDLE hHandle);
 
+// PRECONDITIONS: `wide_string` must be terminated by a NUL FPDF_WCHAR.
 UNSAFE_BUFFER_USAGE ByteString
 ByteStringFromFPDFWideString(FPDF_WIDESTRING wide_string);
 
+// PRECONDITIONS: `wide_string` must be terminated by a NUL FPDF_WCHAR.
 UNSAFE_BUFFER_USAGE WideString
 WideStringFromFPDFWideString(FPDF_WIDESTRING wide_string);
 
 // Public APIs are not consistent w.r.t. the type used to represent buffer
 // length, while internal code generally expects size_t. Use StrictNumeric here
 // to make sure the length types fit in a size_t.
+// PRECONDITIONS: `buffer` must point to `buflen` valid bytes.
 UNSAFE_BUFFER_USAGE pdfium::span<char> SpanFromFPDFApiArgs(
     void* buffer,
     pdfium::StrictNumeric<size_t> buflen);
diff --git a/fpdfsdk/fpdf_structtree.cpp b/fpdfsdk/fpdf_structtree.cpp
index ab37c6a..5ca81f1 100644
--- a/fpdfsdk/fpdf_structtree.cpp
+++ b/fpdfsdk/fpdf_structtree.cpp
@@ -20,6 +20,7 @@
 
 namespace {
 
+// PRECONDITIONS: `buffer` must point to `buflen` valid bytes.
 UNSAFE_BUFFER_USAGE unsigned long WideStringToBuffer(const WideString& str,
                                                      void* buffer,
                                                      unsigned long buflen) {