factorize WebPMuxValidate
move count extraction, count and feature flag validation to
ValidateChunk.
Change-Id: I4bd81bbc8a5a48e1263d11992ab3f285c45417b8
diff --git a/src/mux/muxinternal.c b/src/mux/muxinternal.c
index 9502bed..2926dec 100644
--- a/src/mux/muxinternal.c
+++ b/src/mux/muxinternal.c
@@ -453,6 +453,27 @@
return (feature != 0) != (num_items > 0);
}
+#define NO_FLAG 0
+
+// Test basic constraints:
+// retrieval, maximum number of chunks by id (use -1 to skip)
+// and feature incompatibility (use NO_FLAG to skip).
+// On success returns WEBP_MUX_OK and stores the chunk count in *num.
+static WebPMuxError ValidateChunk(const WebPMux* const mux, TAG_ID id,
+ FeatureFlags feature, FeatureFlags vp8x_flags,
+ int max, int* num) {
+ const WebPMuxError err =
+ WebPMuxNumNamedElements(mux, kChunks[id].chunkName, num);
+ assert(id == kChunks[id].chunkId);
+
+ if (err != WEBP_MUX_OK) return err;
+ if (max > -1 && *num > max) return WEBP_MUX_INVALID_ARGUMENT;
+ if (feature != NO_FLAG && IsNotCompatible(vp8x_flags & feature, *num)) {
+ return WEBP_MUX_INVALID_ARGUMENT;
+ }
+ return WEBP_MUX_OK;
+}
+
WebPMuxError WebPMuxValidate(const WebPMux* const mux) {
int num_iccp;
int num_meta;
@@ -480,68 +501,45 @@
if (err != WEBP_MUX_OK) return err;
// At most one color profile chunk.
- err = WebPMuxNumNamedElements(mux, kChunks[ICCP_ID].chunkName, &num_iccp);
+ err = ValidateChunk(mux, ICCP_ID, ICCP_FLAG, flags, 1, &num_iccp);
if (err != WEBP_MUX_OK) return err;
- if (num_iccp > 1) return WEBP_MUX_INVALID_ARGUMENT;
-
- // ICCP_FLAG and color profile chunk is consistent.
- if (IsNotCompatible(flags & ICCP_FLAG, num_iccp)) {
- return WEBP_MUX_INVALID_ARGUMENT;
- }
// At most one XMP metadata.
- err = WebPMuxNumNamedElements(mux, kChunks[META_ID].chunkName, &num_meta);
+ err = ValidateChunk(mux, META_ID, META_FLAG, flags, 1, &num_meta);
if (err != WEBP_MUX_OK) return err;
- if (num_meta > 1) return WEBP_MUX_INVALID_ARGUMENT;
-
- // META_FLAG and XMP metadata chunk is consistent.
- if (IsNotCompatible(flags & META_FLAG, num_meta)) {
- return WEBP_MUX_INVALID_ARGUMENT;
- }
-
- // At most one loop chunk.
- err = WebPMuxNumNamedElements(mux, kChunks[LOOP_ID].chunkName,
- &num_loop_chunks);
- if (err != WEBP_MUX_OK) return err;
- if (num_loop_chunks > 1) return WEBP_MUX_INVALID_ARGUMENT;
// Animation: ANIMATION_FLAG, loop chunk and frame chunk(s) are consistent.
- err = WebPMuxNumNamedElements(mux, kChunks[FRAME_ID].chunkName, &num_frames);
+ // At most one loop chunk.
+ err = ValidateChunk(mux, LOOP_ID, NO_FLAG, flags, 1, &num_loop_chunks);
if (err != WEBP_MUX_OK) return err;
- if ((flags & ANIMATION_FLAG) &&
- (num_loop_chunks == 0 || num_frames == 0)) {
- return WEBP_MUX_INVALID_ARGUMENT;
- } else if (!(flags & ANIMATION_FLAG) &&
- (num_loop_chunks == 1 || num_frames > 0)) {
- return WEBP_MUX_INVALID_ARGUMENT;
+ err = ValidateChunk(mux, FRAME_ID, NO_FLAG, flags, -1, &num_frames);
+ if (err != WEBP_MUX_OK) return err;
+
+ {
+ const int has_animation = !!(flags & ANIMATION_FLAG);
+ if (has_animation && (num_loop_chunks == 0 || num_frames == 0)) {
+ return WEBP_MUX_INVALID_ARGUMENT;
+ }
+ if (!has_animation && (num_loop_chunks == 1 || num_frames > 0)) {
+ return WEBP_MUX_INVALID_ARGUMENT;
+ }
}
// Tiling: TILE_FLAG and tile chunk(s) are consistent.
- err = WebPMuxNumNamedElements(mux, kChunks[TILE_ID].chunkName, &num_tiles);
+ err = ValidateChunk(mux, TILE_ID, TILE_FLAG, flags, -1, &num_tiles);
if (err != WEBP_MUX_OK) return err;
- if (IsNotCompatible(flags & TILE_FLAG, num_tiles)) {
- return WEBP_MUX_INVALID_ARGUMENT;
- }
// Verify either VP8X chunk is present OR there is only one elem in
// mux->images_.
- err = WebPMuxNumNamedElements(mux, kChunks[VP8X_ID].chunkName, &num_vp8x);
+ err = ValidateChunk(mux, VP8X_ID, NO_FLAG, flags, 1, &num_vp8x);
if (err != WEBP_MUX_OK) return err;
- err = WebPMuxNumNamedElements(mux, kChunks[IMAGE_ID].chunkName, &num_images);
+ err = ValidateChunk(mux, IMAGE_ID, NO_FLAG, flags, -1, &num_images);
if (err != WEBP_MUX_OK) return err;
-
- if (num_vp8x > 1) {
- return WEBP_MUX_INVALID_ARGUMENT;
- } else if (num_vp8x == 0 && num_images != 1) {
- return WEBP_MUX_INVALID_ARGUMENT;
- }
+ if (num_vp8x == 0 && num_images != 1) return WEBP_MUX_INVALID_ARGUMENT;
// ALPHA_FLAG & alpha chunk(s) are consistent.
- err = WebPMuxNumNamedElements(mux, kChunks[ALPHA_ID].chunkName, &num_alpha);
+ err = ValidateChunk(mux, ALPHA_ID, ALPHA_FLAG, flags, -1, &num_alpha);
if (err != WEBP_MUX_OK) return err;
- if (IsNotCompatible(flags & ALPHA_FLAG, num_alpha)) {
- return WEBP_MUX_INVALID_ARGUMENT;
- }
// num_images & num_alpha_chunks are consistent.
if (num_alpha > 0 && num_alpha != num_images) {
@@ -553,6 +551,8 @@
return WEBP_MUX_OK;
}
+#undef NO_FLAG
+
//------------------------------------------------------------------------------
#if defined(__cplusplus) || defined(c_plusplus)