Commit 2468231c63 for aom

commit 2468231c631b71a34900ab388049311ae7e82219
Author: James Zern <jzern@google.com>
Date:   Fri Mar 6 11:07:28 2026 -0800

    encode_api_test: add test coverage for issue 487259772

    This covers a fix made in
      c2daa0f13c Use enc_row_mt->allocated_tile_cols/rows correctly
    that involved resolution / tile configurations related to row-mt. In
    some situations this would cause the tile data size to fall out of sync
    with the `row_mt_sync` allocation causing a memset on a NULL value.

    Note there is still an additional crash with row-mt disabled. A test is
    added, but disabled in this commit.

    Bug: 487259772
    Change-Id: I58cf96e729a64c3cf1ca0e93d77fb636cbc271a9

diff --git a/test/encode_api_test.cc b/test/encode_api_test.cc
index 4999493b98..cc53d9291f 100644
--- a/test/encode_api_test.cc
+++ b/test/encode_api_test.cc
@@ -11,6 +11,7 @@

 #include <cassert>
 #include <climits>
+#include <cmath>
 #include <cstdint>
 #include <cstdlib>
 #include <cstring>
@@ -494,6 +495,8 @@ class AV1Encoder {
                  aom_rc_mode end_usage, unsigned int usage);
   void Encode(bool key_frame);

+  aom_codec_ctx_t *GetCodecCtx() { return &enc_; }
+
  private:
   // Flushes the encoder. Should be called after all the Encode() calls.
   void Flush();
@@ -532,6 +535,32 @@ void AV1Encoder::Configure(unsigned int threads, unsigned int width,
     cfg_.rc_max_quantizer = 58;
     ASSERT_EQ(aom_codec_enc_init(&enc_, iface, &cfg_, 0), AOM_CODEC_OK);
     ASSERT_EQ(aom_codec_control(&enc_, AOME_SET_CPUUSED, speed_), AOM_CODEC_OK);
+
+    const int log2_threads =
+        (cfg_.g_threads == 0) ? 0 : static_cast<int>(std::log2(cfg_.g_threads));
+    int tile_columns_log2 = 0;
+    int tile_rows_log2 = 0;
+    switch (log2_threads) {
+      case 4:
+        tile_columns_log2 = 2;
+        tile_rows_log2 = 2;
+        break;
+      case 3:
+        tile_columns_log2 = 2;
+        tile_rows_log2 = 1;
+        break;
+      case 2:
+        tile_columns_log2 = 1;
+        tile_rows_log2 = 1;
+        break;
+      default: tile_columns_log2 = log2_threads;
+    }
+    ASSERT_EQ(
+        aom_codec_control(&enc_, AV1E_SET_TILE_COLUMNS, tile_columns_log2),
+        AOM_CODEC_OK);
+    ASSERT_EQ(aom_codec_control(&enc_, AV1E_SET_TILE_ROWS, tile_rows_log2),
+              AOM_CODEC_OK);
+
     initialized_ = true;
     return;
   }
@@ -981,6 +1010,60 @@ TEST(EncodeAPI, Buganizer392929025) {
   ASSERT_EQ(aom_codec_destroy(&enc), AOM_CODEC_OK);
 }

+void ReproBuganizer487259772(const bool row_mt, int initial_threads = 2) {
+  AV1Encoder encoder(7);
+
+  encoder.Configure(initial_threads, 800, 600, AOM_VBR, AOM_USAGE_REALTIME);
+  // This is not exposed by the WebCodecs interface. It's set to 1 in Chrome's
+  // implementation.
+  ASSERT_EQ(aom_codec_control(encoder.GetCodecCtx(), AV1E_SET_ROW_MT, row_mt),
+            AOM_CODEC_OK);
+  encoder.Encode(false);
+  encoder.Encode(false);
+  encoder.Encode(false);
+
+  encoder.Configure(1, 352, 288, AOM_VBR, AOM_USAGE_REALTIME);
+  encoder.Encode(false);
+  encoder.Encode(false);
+  encoder.Encode(false);
+  encoder.Encode(false);
+
+  encoder.Configure(1, 48, 480, AOM_VBR, AOM_USAGE_REALTIME);
+  encoder.Encode(false);
+  encoder.Encode(true);
+  encoder.Encode(false);
+
+  encoder.Configure(1, 8, 8, AOM_VBR, AOM_USAGE_REALTIME);
+  encoder.Encode(false);
+  encoder.Encode(false);
+
+  encoder.Configure(1, 24, 24, AOM_VBR, AOM_USAGE_REALTIME);
+  encoder.Encode(false);
+  encoder.Encode(false);
+
+  encoder.Configure(1, 97, 53, AOM_VBR, AOM_USAGE_REALTIME);
+  encoder.Encode(false);
+  encoder.Encode(false);
+
+  encoder.Configure(1, 32, 320, AOM_VBR, AOM_USAGE_REALTIME);
+  encoder.Encode(false);
+  encoder.Encode(false);
+}
+
+TEST(EncodeAPI, Buganizer487259772NoThreads) {
+  ReproBuganizer487259772(/*row_mt=*/false, /*initial_threads=*/1);
+}
+
+// TODO: bug 487259772 - Enable this test after assertion/crash (NULL mbmi) in
+// av1_loopfilter is fixed.
+TEST(EncodeAPI, DISABLED_Buganizer487259772NoRowMT) {
+  ReproBuganizer487259772(/*row_mt=*/false);
+}
+
+TEST(EncodeAPI, Buganizer487259772RowMT) {
+  ReproBuganizer487259772(/*row_mt=*/true);
+}
+
 class EncodeAPIParameterized
     : public testing::TestWithParam<std::tuple<
           /*usage=*/unsigned int, /*speed=*/int, /*aq_mode=*/unsigned int>> {};