Fix bug where the gain map is not detected if iprp appears before iref.
Change-Id: I851c3adb9c6a760ea1693b2ee914d651a0fc7441
diff --git a/avifinfo.c b/avifinfo.c
index 77b8b03..62abf28 100644
--- a/avifinfo.c
+++ b/avifinfo.c
@@ -175,6 +175,7 @@
uint8_t data_was_skipped; // True if some loops/indices were skipped.
uint8_t tone_mapped_item_id; // Id of the "tmap" box, > 0 if present.
uint8_t iinf_parsed; // True if the "iinf" (item info) box was parsed.
+ uint8_t iref_parsed; // True if the "iref" (item reference) box was parsed.
uint8_t num_tiles;
AvifInfoInternalTile tiles[AVIFINFO_MAX_TILES];
@@ -267,7 +268,8 @@
}
// If the gain map has not been found but we haven't read all the relevant
// metadata, we might still find one later and cannot stop now.
- if (!f->primary_item_features.has_gainmap && !f->iinf_parsed) {
+ if (!f->primary_item_features.has_gainmap &&
+ (!f->iinf_parsed || (f->tone_mapped_item_id && !f->iref_parsed))) {
return kNotFound;
}
@@ -605,6 +607,8 @@
uint32_t num_remaining_bytes,
uint32_t* num_parsed_boxes,
AvifInfoInternalFeatures* features) {
+ features->iref_parsed = 1;
+
do {
AvifInfoInternalBox box;
AVIFINFO_CHECK_FOUND(AvifInfoInternalParseBox(
diff --git a/tests/avifinfo_test.cc b/tests/avifinfo_test.cc
index e115299..a9f4b5e 100644
--- a/tests/avifinfo_test.cc
+++ b/tests/avifinfo_test.cc
@@ -128,37 +128,43 @@
}
TEST(AvifInfoGetTest, WithGainmapTmap) {
- const Data input = LoadFile("avifinfo_test_12x34_gainmap_tmap.avif");
- ASSERT_FALSE(input.empty());
+ for (const char* file_name :
+ {"avifinfo_test_12x34_gainmap_tmap.avif",
+ "avifinfo_test_12x34_gainmap_tmap_iref_after_iprp.avif"}) {
+ SCOPED_TRACE(file_name);
+ const Data input = LoadFile(file_name);
+ ASSERT_FALSE(input.empty());
- ASSERT_EQ(AvifInfoIdentify(input.data(), input.size()), kAvifInfoOk);
- AvifInfoFeatures f;
- ASSERT_EQ(AvifInfoGetFeatures(input.data(), input.size(), &f), kAvifInfoOk);
- ExpectEqual(f, {.width = 12u,
- .height = 34u,
- .bit_depth = 10u,
- .num_channels = 4u,
- .has_gainmap = 1u,
- .gainmap_item_id = 4u,
- .primary_item_id_location = 96u,
- .primary_item_id_bytes = 2u});
+ ASSERT_EQ(AvifInfoIdentify(input.data(), input.size()), kAvifInfoOk);
+ AvifInfoFeatures f;
+ ASSERT_EQ(AvifInfoGetFeatures(input.data(), input.size(), &f), kAvifInfoOk);
+ ExpectEqual(f, {.width = 12u,
+ .height = 34u,
+ .bit_depth = 10u,
+ .num_channels = 4u,
+ .has_gainmap = 1u,
+ .gainmap_item_id = 4u,
+ .primary_item_id_location = 96u,
+ .primary_item_id_bytes = 2u});
- Data gainmap = input;
- ASSERT_TRUE(SetPrimaryItemIdToGainmapId(gainmap));
- ASSERT_EQ(AvifInfoIdentify(gainmap.data(), gainmap.size()), kAvifInfoOk);
- AvifInfoFeatures gainmap_f;
- ASSERT_EQ(AvifInfoGetFeatures(gainmap.data(), gainmap.size(), &gainmap_f),
- kAvifInfoOk);
- // Note that num_channels says 4 even though the alpha plane is associated to
- // the main image and not the gain map, but libavifinfo does not check this.
- ExpectEqual(gainmap_f, {.width = 6u,
- .height = 17u,
- .bit_depth = 8u,
- .num_channels = 4u,
- .has_gainmap = 1u,
- .gainmap_item_id = 4u,
- .primary_item_id_location = 96u,
- .primary_item_id_bytes = 2u});
+ Data gainmap = input;
+ ASSERT_TRUE(SetPrimaryItemIdToGainmapId(gainmap));
+ ASSERT_EQ(AvifInfoIdentify(gainmap.data(), gainmap.size()), kAvifInfoOk);
+ AvifInfoFeatures gainmap_f;
+ ASSERT_EQ(AvifInfoGetFeatures(gainmap.data(), gainmap.size(), &gainmap_f),
+ kAvifInfoOk);
+ // Note that num_channels says 4 even though the alpha plane is associated
+ // to the main image and not the gain map, but libavifinfo does not check
+ // this.
+ ExpectEqual(gainmap_f, {.width = 6u,
+ .height = 17u,
+ .bit_depth = 8u,
+ .num_channels = 4u,
+ .has_gainmap = 1u,
+ .gainmap_item_id = 4u,
+ .primary_item_id_location = 96u,
+ .primary_item_id_bytes = 2u});
+ }
}
TEST(AvifInfoGetTest, NoPixi10b) {
diff --git a/tests/avifinfo_test_12x34_gainmap_tmap_iref_after_iprp.avif b/tests/avifinfo_test_12x34_gainmap_tmap_iref_after_iprp.avif
new file mode 100644
index 0000000..c363b12
--- /dev/null
+++ b/tests/avifinfo_test_12x34_gainmap_tmap_iref_after_iprp.avif
Binary files differ