Remove #defines from fx_bmp.h.

Move them into cfx_bmpdecompressor.cpp and replace them with:
- constexpr values
- enum class DecodeStatus
- CalculatePitch32()

Change-Id: I40fe37f1616f9e9d7e49c6bd5489e4bf0a326d33
Reviewed-on: https://pdfium-review.googlesource.com/c/pdfium/+/56012
Commit-Queue: Lei Zhang <thestig@chromium.org>
Reviewed-by: Tom Sepez <tsepez@chromium.org>
diff --git a/core/fxcodec/bmp/cfx_bmpdecompressor.cpp b/core/fxcodec/bmp/cfx_bmpdecompressor.cpp
index 2bff458..6966a78 100644
--- a/core/fxcodec/bmp/cfx_bmpdecompressor.cpp
+++ b/core/fxcodec/bmp/cfx_bmpdecompressor.cpp
@@ -12,6 +12,7 @@
 
 #include "core/fxcodec/bmp/cfx_bmpcontext.h"
 #include "core/fxcodec/codec/cfx_codec_memory.h"
+#include "core/fxcodec/fx_codec.h"
 #include "core/fxcrt/fx_safe_types.h"
 #include "core/fxcrt/fx_system.h"
 #include "third_party/base/logging.h"
@@ -19,6 +20,9 @@
 
 namespace {
 
+#define BMP_PAL_ENCODE(a, r, g, b) \
+  (((uint32_t)(a) << 24) | ((r) << 16) | ((g) << 8) | (b))
+
 constexpr size_t kBmpCoreHeaderSize = 12;
 constexpr size_t kBmpInfoHeaderSize = 40;
 
@@ -27,6 +31,17 @@
 static_assert(sizeof(BmpInfoHeader) == kBmpInfoHeaderSize,
               "BmpInfoHeader has wrong size");
 
+constexpr uint16_t kBmpSignature = 0x4D42;
+constexpr int32_t kBmpPalOld = 1;
+constexpr uint8_t kRleMarker = 0;
+constexpr uint8_t kRleEol = 0;
+constexpr uint8_t kRleEoi = 1;
+constexpr uint8_t kRleDelta = 2;
+constexpr uint32_t kBmpRgb = 0L;
+constexpr uint32_t kBmpRle8 = 1L;
+constexpr uint32_t kBmpRle4 = 2L;
+constexpr uint32_t kBmpBitfields = 3L;
+
 uint8_t HalfRoundUp(uint8_t value) {
   uint16_t value16 = value;
   return static_cast<uint8_t>((value16 + 1) / 2);
@@ -53,7 +68,7 @@
 }
 
 int32_t CFX_BmpDecompressor::ReadHeader() {
-  if (decode_status_ == BMP_D_STATUS_HEADER) {
+  if (decode_status_ == DecodeStatus::kHeader) {
     BmpFileHeader bmp_header;
     if (!ReadData(reinterpret_cast<uint8_t*>(&bmp_header),
                   sizeof(BmpFileHeader))) {
@@ -66,7 +81,7 @@
         FXDWORD_GET_LSBFIRST(reinterpret_cast<uint8_t*>(&bmp_header.bfOffBits));
     data_size_ =
         FXDWORD_GET_LSBFIRST(reinterpret_cast<uint8_t*>(&bmp_header.bfSize));
-    if (bmp_header.bfType != BMP_SIGNATURE) {
+    if (bmp_header.bfType != kBmpSignature) {
       Error();
       NOTREACHED();
     }
@@ -94,7 +109,7 @@
             reinterpret_cast<uint8_t*>(&bmp_core_header.bcHeight));
         bit_counts_ = FXWORD_GET_LSBFIRST(
             reinterpret_cast<uint8_t*>(&bmp_core_header.bcBitCount));
-        compress_flag_ = BMP_RGB;
+        compress_flag_ = kBmpRgb;
         img_tb_flag_ = false;
         break;
       }
@@ -162,7 +177,7 @@
         dpi_y_ = FXDWORD_GET_LSBFIRST(
             reinterpret_cast<uint8_t*>(&bmp_info_header.biYPelsPerMeter));
         SetHeight(signed_height);
-        if (compress_flag_ != BMP_RGB || bi_planes != 1 || color_used_ != 0) {
+        if (compress_flag_ != kBmpRgb || bi_planes != 1 || color_used_ != 0) {
           Error();
           NOTREACHED();
         }
@@ -170,7 +185,7 @@
       }
     }
 
-    if (width_ > BMP_MAX_WIDTH || compress_flag_ > BMP_BITFIELDS) {
+    if (compress_flag_ > kBmpBitfields) {
       Error();
       NOTREACHED();
     }
@@ -194,17 +209,33 @@
         NOTREACHED();
         break;
     }
-    src_row_bytes_ = BMP_WIDTHBYTES(width_, bit_counts_);
+    FX_SAFE_UINT32 stride = CalculatePitch32(bit_counts_, width_);
+    if (!stride.IsValid()) {
+      Error();
+      NOTREACHED();
+    }
+
+    src_row_bytes_ = stride.ValueOrDie();
     switch (bit_counts_) {
       case 1:
       case 4:
       case 8:
-        out_row_bytes_ = BMP_WIDTHBYTES(width_, 8);
+        stride = CalculatePitch32(8, width_);
+        if (!stride.IsValid()) {
+          Error();
+          NOTREACHED();
+        }
+        out_row_bytes_ = stride.ValueOrDie();
         components_ = 1;
         break;
       case 16:
       case 24:
-        out_row_bytes_ = BMP_WIDTHBYTES(width_, 24);
+        stride = CalculatePitch32(24, width_);
+        if (!stride.IsValid()) {
+          Error();
+          NOTREACHED();
+        }
+        out_row_bytes_ = stride.ValueOrDie();
         components_ = 3;
         break;
       case 32:
@@ -220,12 +251,12 @@
     }
 
     out_row_buffer_.resize(out_row_bytes_);
-    SaveDecodingStatus(BMP_D_STATUS_PAL);
+    SaveDecodingStatus(DecodeStatus::kPal);
   }
-  if (decode_status_ != BMP_D_STATUS_PAL)
+  if (decode_status_ != DecodeStatus::kPal)
     return 1;
 
-  if (compress_flag_ == BMP_BITFIELDS) {
+  if (compress_flag_ == kBmpBitfields) {
     if (bit_counts_ != 16 && bit_counts_ != 32) {
       Error();
       NOTREACHED();
@@ -244,7 +275,7 @@
       NOTREACHED();
     }
     header_offset_ = std::max(header_offset_, 26 + img_ifh_size_);
-    SaveDecodingStatus(BMP_D_STATUS_DATA_PRE);
+    SaveDecodingStatus(DecodeStatus::kDataPre);
     return 1;
   }
 
@@ -267,7 +298,7 @@
 
     palette_.resize(pal_num_);
     int32_t src_pal_index = 0;
-    if (pal_type_ == BMP_PAL_OLD) {
+    if (pal_type_ == kBmpPalOld) {
       while (src_pal_index < pal_num_) {
         palette_[src_pal_index++] = BMP_PAL_ENCODE(
             0x00, src_pal_data[2], src_pal_data[1], src_pal_data[0]);
@@ -283,16 +314,16 @@
   }
   header_offset_ = std::max(
       header_offset_, 14 + img_ifh_size_ + pal_num_ * (pal_type_ ? 3 : 4));
-  SaveDecodingStatus(BMP_D_STATUS_DATA_PRE);
+  SaveDecodingStatus(DecodeStatus::kDataPre);
   return 1;
 }
 
 bool CFX_BmpDecompressor::ValidateFlag() const {
   switch (compress_flag_) {
-    case BMP_RGB:
-    case BMP_BITFIELDS:
-    case BMP_RLE8:
-    case BMP_RLE4:
+    case kBmpRgb:
+    case kBmpBitfields:
+    case kBmpRle8:
+    case kBmpRle4:
       return true;
     default:
       return false;
@@ -300,29 +331,29 @@
 }
 
 int32_t CFX_BmpDecompressor::DecodeImage() {
-  if (decode_status_ == BMP_D_STATUS_DATA_PRE) {
+  if (decode_status_ == DecodeStatus::kDataPre) {
     input_buffer_->Seek(0);
     if (!GetDataPosition(header_offset_)) {
-      decode_status_ = BMP_D_STATUS_TAIL;
+      decode_status_ = DecodeStatus::kTail;
       Error();
       NOTREACHED();
     }
 
     row_num_ = 0;
-    SaveDecodingStatus(BMP_D_STATUS_DATA);
+    SaveDecodingStatus(DecodeStatus::kData);
   }
-  if (decode_status_ != BMP_D_STATUS_DATA || !ValidateFlag()) {
+  if (decode_status_ != DecodeStatus::kData || !ValidateFlag()) {
     Error();
     NOTREACHED();
   }
 
   switch (compress_flag_) {
-    case BMP_RGB:
-    case BMP_BITFIELDS:
+    case kBmpRgb:
+    case kBmpBitfields:
       return DecodeRGB();
-    case BMP_RLE8:
+    case kBmpRle8:
       return DecodeRLE8();
-    case BMP_RLE4:
+    case kBmpRle4:
       return DecodeRLE4();
     default:
       return 0;
@@ -345,7 +376,7 @@
     if (!ReadData(dest_buf.data(), src_row_bytes_))
       return 2;
 
-    SaveDecodingStatus(BMP_D_STATUS_DATA);
+    SaveDecodingStatus(DecodeStatus::kData);
     switch (bit_counts_) {
       case 1: {
         for (uint32_t col = 0; col < width_; ++col)
@@ -408,7 +439,7 @@
     ReadScanline(img_tb_flag_ ? row_num_++ : (height_ - 1 - row_num_++),
                  out_row_buffer_);
   }
-  SaveDecodingStatus(BMP_D_STATUS_TAIL);
+  SaveDecodingStatus(DecodeStatus::kTail);
   return 1;
 }
 
@@ -420,14 +451,14 @@
       return 2;
 
     switch (first_part) {
-      case RLE_MARKER: {
+      case kRleMarker: {
         if (!ReadData(&first_part, sizeof(first_part)))
           return 2;
 
         switch (first_part) {
-          case RLE_EOL: {
+          case kRleEol: {
             if (row_num_ >= height_) {
-              SaveDecodingStatus(BMP_D_STATUS_TAIL);
+              SaveDecodingStatus(DecodeStatus::kTail);
               Error();
               NOTREACHED();
             }
@@ -436,19 +467,19 @@
                          out_row_buffer_);
             col_num_ = 0;
             std::fill(out_row_buffer_.begin(), out_row_buffer_.end(), 0);
-            SaveDecodingStatus(BMP_D_STATUS_DATA);
+            SaveDecodingStatus(DecodeStatus::kData);
             continue;
           }
-          case RLE_EOI: {
+          case kRleEoi: {
             if (row_num_ < height_) {
               ReadScanline(
                   img_tb_flag_ ? row_num_++ : (height_ - 1 - row_num_++),
                   out_row_buffer_);
             }
-            SaveDecodingStatus(BMP_D_STATUS_TAIL);
+            SaveDecodingStatus(DecodeStatus::kTail);
             return 1;
           }
-          case RLE_DELTA: {
+          case kRleDelta: {
             uint8_t delta[2];
             if (!ReadData(delta, sizeof(delta)))
               return 2;
@@ -524,14 +555,14 @@
       return 2;
 
     switch (first_part) {
-      case RLE_MARKER: {
+      case kRleMarker: {
         if (!ReadData(&first_part, sizeof(first_part))) {
           return 2;
         }
         switch (first_part) {
-          case RLE_EOL: {
+          case kRleEol: {
             if (row_num_ >= height_) {
-              SaveDecodingStatus(BMP_D_STATUS_TAIL);
+              SaveDecodingStatus(DecodeStatus::kTail);
               Error();
               NOTREACHED();
             }
@@ -540,19 +571,19 @@
                          out_row_buffer_);
             col_num_ = 0;
             std::fill(out_row_buffer_.begin(), out_row_buffer_.end(), 0);
-            SaveDecodingStatus(BMP_D_STATUS_DATA);
+            SaveDecodingStatus(DecodeStatus::kData);
             continue;
           }
-          case RLE_EOI: {
+          case kRleEoi: {
             if (row_num_ < height_) {
               ReadScanline(
                   img_tb_flag_ ? row_num_++ : (height_ - 1 - row_num_++),
                   out_row_buffer_);
             }
-            SaveDecodingStatus(BMP_D_STATUS_TAIL);
+            SaveDecodingStatus(DecodeStatus::kTail);
             return 1;
           }
-          case RLE_DELTA: {
+          case kRleDelta: {
             uint8_t delta[2];
             if (!ReadData(delta, sizeof(delta)))
               return 2;
@@ -645,7 +676,7 @@
   return input_buffer_ && input_buffer_->ReadBlock(destination, size) == size;
 }
 
-void CFX_BmpDecompressor::SaveDecodingStatus(int32_t status) {
+void CFX_BmpDecompressor::SaveDecodingStatus(DecodeStatus status) {
   decode_status_ = status;
 }
 
diff --git a/core/fxcodec/bmp/cfx_bmpdecompressor.h b/core/fxcodec/bmp/cfx_bmpdecompressor.h
index 574a831..1f88c73 100644
--- a/core/fxcodec/bmp/cfx_bmpdecompressor.h
+++ b/core/fxcodec/bmp/cfx_bmpdecompressor.h
@@ -40,13 +40,21 @@
   int32_t dpi_y() const { return dpi_y_; }
 
  private:
+  enum class DecodeStatus : uint8_t {
+    kHeader,
+    kPal,
+    kDataPre,
+    kData,
+    kTail,
+  };
+
   bool GetDataPosition(uint32_t cur_pos);
   void ReadScanline(uint32_t row_num, const std::vector<uint8_t>& row_buf);
   int32_t DecodeRGB();
   int32_t DecodeRLE8();
   int32_t DecodeRLE4();
   bool ReadData(uint8_t* destination, uint32_t size);
-  void SaveDecodingStatus(int32_t status);
+  void SaveDecodingStatus(DecodeStatus status);
   bool ValidateColorIndex(uint8_t val);
   bool ValidateFlag() const;
   void SetHeight(int32_t signed_height);
@@ -76,7 +84,7 @@
   uint32_t mask_red_ = 0;
   uint32_t mask_green_ = 0;
   uint32_t mask_blue_ = 0;
-  int32_t decode_status_ = BMP_D_STATUS_HEADER;
+  DecodeStatus decode_status_ = DecodeStatus::kHeader;
   RetainPtr<CFX_CodecMemory> input_buffer_;
 };
 
diff --git a/core/fxcodec/bmp/fx_bmp.h b/core/fxcodec/bmp/fx_bmp.h
index 82a695a..79c61bb 100644
--- a/core/fxcodec/bmp/fx_bmp.h
+++ b/core/fxcodec/bmp/fx_bmp.h
@@ -9,26 +9,6 @@
 
 #include <stdint.h>
 
-#define BMP_WIDTHBYTES(width, bitCount) ((width * bitCount) + 31) / 32 * 4
-#define BMP_PAL_ENCODE(a, r, g, b) \
-  (((uint32_t)(a) << 24) | ((r) << 16) | ((g) << 8) | (b))
-#define BMP_D_STATUS_HEADER 0x01
-#define BMP_D_STATUS_PAL 0x02
-#define BMP_D_STATUS_DATA_PRE 0x03
-#define BMP_D_STATUS_DATA 0x04
-#define BMP_D_STATUS_TAIL 0x00
-#define BMP_SIGNATURE 0x4D42
-#define BMP_PAL_OLD 1
-#define RLE_MARKER 0
-#define RLE_EOL 0
-#define RLE_EOI 1
-#define RLE_DELTA 2
-#define BMP_RGB 0L
-#define BMP_RLE8 1L
-#define BMP_RLE4 2L
-#define BMP_BITFIELDS 3L
-// Limit width to (MAXINT32 - 31) / 32
-#define BMP_MAX_WIDTH 67108863
 #pragma pack(1)
 struct BmpFileHeader {
   uint16_t bfType;
@@ -61,4 +41,8 @@
 };
 #pragma pack()
 
+static_assert(sizeof(BmpFileHeader) == 14, "BmpFileHeader has wrong size");
+static_assert(sizeof(BmpCoreHeader) == 12, "BmpCoreHeader has wrong size");
+static_assert(sizeof(BmpInfoHeader) == 40, "BmpInfoHeader has wrong size");
+
 #endif  // CORE_FXCODEC_BMP_FX_BMP_H_