Split avifRawData and avifStream into read-only (const) and read/write versions, updated code accordingly
diff --git a/CHANGELOG.md b/CHANGELOG.md index 06309d7..80ed04d 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md
@@ -5,6 +5,8 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html). ## [Unreleased] +### Changed +- Split avifRawData and avifStream into read-only (const) and read/write versions, updated code accordingly ## [0.3.8] - 2019-09-04 ### Changed
diff --git a/README.md b/README.md index d0a5061..2ae29af 100644 --- a/README.md +++ b/README.md
@@ -16,7 +16,7 @@ #include "avif/avif.h" // point raw.data and raw.size to the contents of an .avif(s) - avifRawData raw; + avifROData raw; raw.data = ...; raw.size = ...; @@ -72,7 +72,7 @@ #include "avif/avif.h" // point raw.data and raw.size to the contents of an .avif(s) - avifRawData raw; + avifROData raw; raw.data = ...; raw.size = ...; @@ -176,7 +176,7 @@ size_t iccSize = ...; // Length of raw ICC profile data avifImageSetProfileICC(image, icc, iccSize); - avifRawData output = AVIF_RAW_DATA_EMPTY; + avifRWData output = AVIF_DATA_EMPTY; avifEncoder * encoder = avifEncoderCreate(); encoder->maxThreads = ...; // Choose max encoder threads, 1 to disable multithreading encoder->minQuantizer = AVIF_QUANTIZER_LOSSLESS; @@ -189,7 +189,7 @@ } else { printf("ERROR: Failed to encode: %s\n", avifResultToString(encodeResult)); } - avifRawDataFree(&output); + avifRWDataFree(&output); avifEncoderDestroy(encoder); ```
diff --git a/apps/avifdec.c b/apps/avifdec.c index d527f76..24007af 100644 --- a/apps/avifdec.c +++ b/apps/avifdec.c
@@ -67,12 +67,12 @@ return 1; } - avifRawData raw = AVIF_RAW_DATA_EMPTY; - avifRawDataRealloc(&raw, inputFileSize); + avifRWData raw = AVIF_DATA_EMPTY; + avifRWDataRealloc(&raw, inputFileSize); if (fread(raw.data, 1, inputFileSize, inputFile) != inputFileSize) { fprintf(stderr, "Failed to read %zu bytes: %s\n", inputFileSize, inputFilename); fclose(inputFile); - avifRawDataFree(&raw); + avifRWDataFree(&raw); return 1; } @@ -81,7 +81,7 @@ avifImage * avif = avifImageCreateEmpty(); avifDecoder * decoder = avifDecoderCreate(); - avifResult decodeResult = avifDecoderRead(decoder, avif, &raw); + avifResult decodeResult = avifDecoderRead(decoder, avif, (avifROData *)&raw); if (decodeResult == AVIF_RESULT_OK) { printf("Image decoded: %s\n", inputFilename); printf("Image details:\n"); @@ -90,7 +90,7 @@ } else { printf("ERROR: Failed to decode image: %s\n", avifResultToString(decodeResult)); } - avifRawDataFree(&raw); + avifRWDataFree(&raw); avifDecoderDestroy(decoder); avifImageDestroy(avif); return 0;
diff --git a/apps/avifenc.c b/apps/avifenc.c index 7daf929..a854c1e 100644 --- a/apps/avifenc.c +++ b/apps/avifenc.c
@@ -162,7 +162,7 @@ int returnCode = 0; avifImage * avif = avifImageCreateEmpty(); - avifRawData raw = AVIF_RAW_DATA_EMPTY; + avifRWData raw = AVIF_DATA_EMPTY; if (!y4mRead(avif, inputFilename)) { avifImageDestroy(avif); @@ -211,6 +211,6 @@ avifEncoderDestroy(encoder); } avifImageDestroy(avif); - avifRawDataFree(&raw); + avifRWDataFree(&raw); return returnCode; }
diff --git a/apps/shared/y4m.c b/apps/shared/y4m.c index 203ea6b..e722ccf 100644 --- a/apps/shared/y4m.c +++ b/apps/shared/y4m.c
@@ -117,12 +117,12 @@ return AVIF_FALSE; } - avifRawData raw = AVIF_RAW_DATA_EMPTY; - avifRawDataRealloc(&raw, inputFileSize); + avifRWData raw = AVIF_DATA_EMPTY; + avifRWDataRealloc(&raw, inputFileSize); if (fread(raw.data, 1, inputFileSize, inputFile) != inputFileSize) { fprintf(stderr, "Failed to read %zu bytes: %s\n", inputFileSize, inputFilename); fclose(inputFile); - avifRawDataFree(&raw); + avifRWDataFree(&raw); return AVIF_FALSE; } @@ -136,7 +136,7 @@ if (memcmp(p, "YUV4MPEG2 ", 10) != 0) { fprintf(stderr, "Not a y4m file: %s\n", inputFilename); - avifRawDataFree(&raw); + avifRWDataFree(&raw); return AVIF_FALSE; } ADVANCE(10); // skip past header @@ -252,7 +252,7 @@ result = AVIF_TRUE; cleanup: - avifRawDataFree(&raw); + avifRWDataFree(&raw); return result; }
diff --git a/examples/avif_example1.c b/examples/avif_example1.c index bc30e62..10e9951 100644 --- a/examples/avif_example1.c +++ b/examples/avif_example1.c
@@ -34,7 +34,7 @@ // uint32_t fakeICCSize = (uint32_t)strlen(fakeICC); // apgImageSetICC(image, fakeICC, fakeICCSize); - avifRawData raw = AVIF_RAW_DATA_EMPTY; + avifRWData raw = AVIF_DATA_EMPTY; avifEncoder * encoder = avifEncoderCreate(); encoder->maxThreads = 1; encoder->minQuantizer = AVIF_QUANTIZER_BEST_QUALITY; @@ -57,7 +57,7 @@ // Decode it avifImage * decoded = avifImageCreateEmpty(); avifDecoder * decoder = avifDecoderCreate(); - avifResult decodeResult = avifDecoderRead(decoder, decoded, &raw); + avifResult decodeResult = avifDecoderRead(decoder, decoded, (avifROData *)&raw); avifDecoderDestroy(decoder); if (decodeResult == AVIF_RESULT_OK) { @@ -88,14 +88,14 @@ fseek(f, 0, SEEK_END); uint32_t size = ftell(f); fseek(f, 0, SEEK_SET); - avifRawData raw = AVIF_RAW_DATA_EMPTY; - avifRawDataRealloc(&raw, size); + avifRWData raw = AVIF_DATA_EMPTY; + avifRWDataRealloc(&raw, size); fread(raw.data, 1, size, f); fclose(f); avifImage * decoded = avifImageCreate(); avifResult decodeResult = avifImageRead(decoded, &raw); - avifRawDataFree(&raw); + avifRWDataFree(&raw); #endif /* if 1 */ return 0; }
diff --git a/include/avif/avif.h b/include/avif/avif.h index 1fb6818..fbb380b 100644 --- a/include/avif/avif.h +++ b/include/avif/avif.h
@@ -90,27 +90,30 @@ const char * avifResultToString(avifResult result); // --------------------------------------------------------------------------- -// avifRawData: Generic raw memory storage +// avifROData/avifRWData: Generic raw memory storage -// Note: you can use this struct directly (without the functions) if you're -// passing data into avif*() functions, but you should use avifRawDataFree() -// if any avif*() function populates one of these. +typedef struct avifROData +{ + const uint8_t * data; + size_t size; +} avifROData; -typedef struct avifRawData +// Note: Use avifRWDataFree() if any avif*() function populates one of these. + +typedef struct avifRWData { uint8_t * data; size_t size; -} avifRawData; +} avifRWData; // clang-format off -// Initialize avifRawData on the stack with this -#define AVIF_RAW_DATA_EMPTY { NULL, 0 } +// Initialize avifROData/avifRWData on the stack with this +#define AVIF_DATA_EMPTY { NULL, 0 } // clang-format on -void avifRawDataRealloc(avifRawData * raw, size_t newSize); -void avifRawDataSet(avifRawData * raw, const uint8_t * data, size_t len); -void avifRawDataConcat(avifRawData * dst, avifRawData ** srcs, int srcsCount); -void avifRawDataFree(avifRawData * raw); +void avifRWDataRealloc(avifRWData * raw, size_t newSize); +void avifRWDataSet(avifRWData * raw, const uint8_t * data, size_t len); +void avifRWDataFree(avifRWData * raw); // --------------------------------------------------------------------------- // avifPixelFormat @@ -290,7 +293,7 @@ // Profile information avifProfileFormat profileFormat; - avifRawData icc; + avifRWData icc; avifNclxColorProfile nclx; } avifImage; @@ -300,7 +303,7 @@ void avifImageDestroy(avifImage * image); void avifImageSetProfileNone(avifImage * image); -void avifImageSetProfileICC(avifImage * image, uint8_t * icc, size_t iccSize); +void avifImageSetProfileICC(avifImage * image, const uint8_t * icc, size_t iccSize); void avifImageSetProfileNCLX(avifImage * image, avifNclxColorProfile * nclx); void avifImageAllocatePlanes(avifImage * image, uint32_t planes); // Ignores any pre-existing planes @@ -378,7 +381,7 @@ void avifDecoderDestroy(avifDecoder * decoder); // Simple interface to decode a single image, independent of the decoder afterwards (decoder may be deestroyed). -avifResult avifDecoderRead(avifDecoder * decoder, avifImage * image, avifRawData * input); +avifResult avifDecoderRead(avifDecoder * decoder, avifImage * image, avifROData * input); // Multi-function alternative to avifDecoderRead() for image sequences and gaining direct access // to the decoder's YUV buffers (for performance's sake). Data passed into avifDecoderParse() is NOT @@ -394,12 +397,12 @@ // You can use avifDecoderReset() any time after a successful call to avifDecoderParse() // to reset the internal decoder back to before the first frame. avifResult avifDecoderSetSource(avifDecoder * decoder, avifDecoderSource source); -avifResult avifDecoderParse(avifDecoder * decoder, avifRawData * input); +avifResult avifDecoderParse(avifDecoder * decoder, avifROData * input); avifResult avifDecoderNextImage(avifDecoder * decoder); avifResult avifDecoderReset(avifDecoder * decoder); // avifEncoder notes: -// * if avifEncoderWrite() returns AVIF_RESULT_OK, output must be freed with avifRawDataFree() +// * if avifEncoderWrite() returns AVIF_RESULT_OK, output must be freed with avifRWDataFree() // * if (maxThreads < 2), multithreading is disabled // * quality range: [AVIF_BEST_QUALITY - AVIF_WORST_QUALITY] // * To enable tiling, set tileRowsLog2 > 0 and/or tileColsLog2 > 0. @@ -418,7 +421,7 @@ } avifEncoder; avifEncoder * avifEncoderCreate(void); -avifResult avifEncoderWrite(avifEncoder * encoder, avifImage * image, avifRawData * output); +avifResult avifEncoderWrite(avifEncoder * encoder, avifImage * image, avifRWData * output); void avifEncoderDestroy(avifEncoder * encoder); // Helpers @@ -426,7 +429,7 @@ // Returns AVIF_TRUE if input begins with a valid FileTypeBox (ftyp) that supports // either the brand 'avif' or 'avis' (or both), without performing any allocations. -avifBool avifPeekCompatibleFileType(avifRawData * input); +avifBool avifPeekCompatibleFileType(avifROData * input); #ifdef __cplusplus } // extern "C"
diff --git a/include/avif/internal.h b/include/avif/internal.h index ae1ecaf..0de7181 100644 --- a/include/avif/internal.h +++ b/include/avif/internal.h
@@ -57,7 +57,8 @@ void avifArrayPush(void * arrayStruct, void * element); void avifArrayDestroy(void * arrayStruct); -AVIF_ARRAY_DECLARE(avifRawDataArray, avifRawData, raw); +AVIF_ARRAY_DECLARE(avifRODataArray, avifROData, raw); +AVIF_ARRAY_DECLARE(avifRWDataArray, avifRWData, raw); // Used internally by avifDecoderNextImage() when there is limited range alpha void avifImageCopyDecoderAlpha(avifImage * image); @@ -73,7 +74,7 @@ typedef struct avifCodecDecodeInput { - avifRawDataArray samples; + avifRODataArray samples; avifBool alpha; // if true, this is decoding an alpha plane } avifCodecDecodeInput; @@ -123,7 +124,7 @@ typedef avifBool (*avifCodecAlphaLimitedRangeFunc)(struct avifCodec * codec); typedef avifBool (*avifCodecGetNextImageFunc)(struct avifCodec * codec, avifImage * image); // avifCodecEncodeImageFunc: if either OBU* is null, skip its encode. alpha should always be lossless -typedef avifBool (*avifCodecEncodeImageFunc)(struct avifCodec * codec, avifImage * image, avifEncoder * encoder, avifRawData * obu, avifBool alpha); +typedef avifBool (*avifCodecEncodeImageFunc)(struct avifCodec * codec, avifImage * image, avifEncoder * encoder, avifRWData * obu, avifBool alpha); typedef void (*avifCodecGetConfigurationBoxFunc)(struct avifCodec * codec, avifCodecConfigurationBox * outConfig); typedef void (*avifCodecDestroyInternalFunc)(struct avifCodec * codec); @@ -149,48 +150,56 @@ typedef size_t avifBoxMarker; -typedef struct avifStream -{ - avifRawData * raw; - size_t offset; -} avifStream; - typedef struct avifBoxHeader { size_t size; uint8_t type[4]; } avifBoxHeader; -uint8_t * avifStreamCurrent(avifStream * stream); +typedef struct avifROStream +{ + avifROData * raw; + size_t offset; +} avifROStream; -void avifStreamStart(avifStream * stream, avifRawData * raw); +const uint8_t * avifROStreamCurrent(avifROStream * stream); +void avifROStreamStart(avifROStream * stream, avifROData * raw); +size_t avifROStreamOffset(avifROStream * stream); +void avifROStreamSetOffset(avifROStream * stream, size_t offset); -// Read -avifBool avifStreamHasBytesLeft(avifStream * stream, size_t byteCount); -size_t avifStreamRemainingBytes(avifStream * stream); -size_t avifStreamOffset(avifStream * stream); -void avifStreamSetOffset(avifStream * stream, size_t offset); -avifBool avifStreamSkip(avifStream * stream, size_t byteCount); -avifBool avifStreamRead(avifStream * stream, uint8_t * data, size_t size); -avifBool avifStreamReadU16(avifStream * stream, uint16_t * v); -avifBool avifStreamReadU32(avifStream * stream, uint32_t * v); -avifBool avifStreamReadUX8(avifStream * stream, uint64_t * v, uint64_t factor); // Reads a factor*8 sized uint, saves in v -avifBool avifStreamReadU64(avifStream * stream, uint64_t * v); -avifBool avifStreamReadString(avifStream * stream, char * output, size_t outputSize); -avifBool avifStreamReadBoxHeader(avifStream * stream, avifBoxHeader * header); -avifBool avifStreamReadVersionAndFlags(avifStream * stream, uint8_t * version, uint8_t * flags); // flags is an optional uint8_t[3] -avifBool avifStreamReadAndEnforceVersion(avifStream * stream, uint8_t enforcedVersion); // currently discards flags +avifBool avifROStreamHasBytesLeft(avifROStream * stream, size_t byteCount); +size_t avifROStreamRemainingBytes(avifROStream * stream); +avifBool avifROStreamSkip(avifROStream * stream, size_t byteCount); +avifBool avifROStreamRead(avifROStream * stream, uint8_t * data, size_t size); +avifBool avifROStreamReadU16(avifROStream * stream, uint16_t * v); +avifBool avifROStreamReadU32(avifROStream * stream, uint32_t * v); +avifBool avifROStreamReadUX8(avifROStream * stream, uint64_t * v, uint64_t factor); // Reads a factor*8 sized uint, saves in v +avifBool avifROStreamReadU64(avifROStream * stream, uint64_t * v); +avifBool avifROStreamReadString(avifROStream * stream, char * output, size_t outputSize); +avifBool avifROStreamReadBoxHeader(avifROStream * stream, avifBoxHeader * header); +avifBool avifROStreamReadVersionAndFlags(avifROStream * stream, uint8_t * version, uint8_t * flags); // flags is an optional uint8_t[3] +avifBool avifROStreamReadAndEnforceVersion(avifROStream * stream, uint8_t enforcedVersion); // currently discards flags -// Write -void avifStreamFinishWrite(avifStream * stream); -void avifStreamWrite(avifStream * stream, const uint8_t * data, size_t size); -void avifStreamWriteChars(avifStream * stream, const char * chars, size_t size); -avifBoxMarker avifStreamWriteBox(avifStream * stream, const char * type, int version /* -1 for "not a FullBox" */, size_t contentSize); -void avifStreamFinishBox(avifStream * stream, avifBoxMarker marker); -void avifStreamWriteU8(avifStream * stream, uint8_t v); -void avifStreamWriteU16(avifStream * stream, uint16_t v); -void avifStreamWriteU32(avifStream * stream, uint32_t v); -void avifStreamWriteZeros(avifStream * stream, size_t byteCount); +typedef struct avifRWStream +{ + avifRWData * raw; + size_t offset; +} avifRWStream; + +uint8_t * avifRWStreamCurrent(avifRWStream * stream); +void avifRWStreamStart(avifRWStream * stream, avifRWData * raw); +size_t avifRWStreamOffset(avifRWStream * stream); +void avifRWStreamSetOffset(avifRWStream * stream, size_t offset); + +void avifRWStreamFinishWrite(avifRWStream * stream); +void avifRWStreamWrite(avifRWStream * stream, const uint8_t * data, size_t size); +void avifRWStreamWriteChars(avifRWStream * stream, const char * chars, size_t size); +avifBoxMarker avifRWStreamWriteBox(avifRWStream * stream, const char * type, int version /* -1 for "not a FullBox" */, size_t contentSize); +void avifRWStreamFinishBox(avifRWStream * stream, avifBoxMarker marker); +void avifRWStreamWriteU8(avifRWStream * stream, uint8_t v); +void avifRWStreamWriteU16(avifRWStream * stream, uint16_t v); +void avifRWStreamWriteU32(avifRWStream * stream, uint32_t v); +void avifRWStreamWriteZeros(avifRWStream * stream, size_t byteCount); #ifdef __cplusplus } // extern "C"
diff --git a/src/avif.c b/src/avif.c index 4006d35..bd9e8db 100644 --- a/src/avif.c +++ b/src/avif.c
@@ -188,22 +188,22 @@ void avifImageDestroy(avifImage * image) { avifImageFreePlanes(image, AVIF_PLANES_ALL); - avifRawDataFree(&image->icc); + avifRWDataFree(&image->icc); avifFree(image); } void avifImageSetProfileNone(avifImage * image) { image->profileFormat = AVIF_PROFILE_FORMAT_NONE; - avifRawDataFree(&image->icc); + avifRWDataFree(&image->icc); } -void avifImageSetProfileICC(avifImage * image, uint8_t * icc, size_t iccSize) +void avifImageSetProfileICC(avifImage * image, const uint8_t * icc, size_t iccSize) { avifImageSetProfileNone(image); if (iccSize) { image->profileFormat = AVIF_PROFILE_FORMAT_ICC; - avifRawDataSet(&image->icc, icc, iccSize); + avifRWDataSet(&image->icc, icc, iccSize); } }
diff --git a/src/codec_aom.c b/src/codec_aom.c index 44967d5..fd4c9ea 100644 --- a/src/codec_aom.c +++ b/src/codec_aom.c
@@ -35,7 +35,7 @@ uint32_t inputSampleIndex; aom_image_t * image; - avifRawData encodedOBU; + avifRWData encodedOBU; avifCodecConfigurationBox config; }; @@ -44,7 +44,7 @@ if (codec->internal->decoderInitialized) { aom_codec_destroy(&codec->internal->decoder); } - avifRawDataFree(&codec->internal->encodedOBU); + avifRWDataFree(&codec->internal->encodedOBU); avifFree(codec->internal); } @@ -83,7 +83,7 @@ break; } else if (codec->internal->inputSampleIndex < codec->decodeInput->samples.count) { // Feed another sample - avifRawData * sample = &codec->decodeInput->samples.raw[codec->internal->inputSampleIndex]; + avifROData * sample = &codec->decodeInput->samples.raw[codec->internal->inputSampleIndex]; ++codec->internal->inputSampleIndex; codec->internal->iter = NULL; if (aom_codec_decode(&codec->internal->decoder, sample->data, sample->size, NULL)) { @@ -232,7 +232,7 @@ return fmt; } -static avifBool encodeOBU(avifImage * image, avifBool alphaOnly, avifEncoder * encoder, avifRawData * outputOBU, avifCodecConfigurationBox * outputConfig) +static avifBool encodeOBU(avifImage * image, avifBool alphaOnly, avifEncoder * encoder, avifRWData * outputOBU, avifCodecConfigurationBox * outputConfig) { avifBool success = AVIF_FALSE; aom_codec_iface_t * encoder_interface = aom_codec_av1_cx(); @@ -399,7 +399,7 @@ if (pkt == NULL) break; if (pkt->kind == AOM_CODEC_CX_FRAME_PKT) { - avifRawDataSet(outputOBU, pkt->data.frame.buf, pkt->data.frame.sz); + avifRWDataSet(outputOBU, pkt->data.frame.buf, pkt->data.frame.sz); success = AVIF_TRUE; break; } @@ -410,7 +410,7 @@ return success; } -static avifBool aomCodecEncodeImage(avifCodec * codec, avifImage * image, avifEncoder * encoder, avifRawData * obu, avifBool alpha) +static avifBool aomCodecEncodeImage(avifCodec * codec, avifImage * image, avifEncoder * encoder, avifRWData * obu, avifBool alpha) { if (!encodeOBU(image, alpha, encoder, obu, &codec->internal->config)) { return AVIF_FALSE;
diff --git a/src/codec_dav1d.c b/src/codec_dav1d.c index be2090f..4cc2da8 100644 --- a/src/codec_dav1d.c +++ b/src/codec_dav1d.c
@@ -38,7 +38,7 @@ dav1d_data_unref(&codec->internal->dav1dData); if (codec->internal->inputSampleIndex < codec->decodeInput->samples.count) { - avifRawData * sample = &codec->decodeInput->samples.raw[codec->internal->inputSampleIndex]; + avifROData * sample = &codec->decodeInput->samples.raw[codec->internal->inputSampleIndex]; ++codec->internal->inputSampleIndex; // OPTIMIZE: Carefully switch this to use dav1d_data_wrap or dav1d_data_wrap_user_data
diff --git a/src/colr.c b/src/colr.c index 082bc98..498623f 100644 --- a/src/colr.c +++ b/src/colr.c
@@ -262,19 +262,19 @@ return XYZ.xyz.y; } -static avifBool readXYZ(uint8_t * data, size_t size, float xyz[3]) +static avifBool readXYZ(const uint8_t * data, size_t size, float xyz[3]) { - avifRawData xyzData; + avifROData xyzData; xyzData.data = data; xyzData.size = size; - avifStream s; - avifStreamStart(&s, &xyzData); - CHECK(avifStreamSkip(&s, 8)); + avifROStream s; + avifROStreamStart(&s, &xyzData); + CHECK(avifROStreamSkip(&s, 8)); int32_t fixedXYZ[3]; - CHECK(avifStreamReadU32(&s, (uint32_t *)&fixedXYZ[0])); - CHECK(avifStreamReadU32(&s, (uint32_t *)&fixedXYZ[1])); - CHECK(avifStreamReadU32(&s, (uint32_t *)&fixedXYZ[2])); + CHECK(avifROStreamReadU32(&s, (uint32_t *)&fixedXYZ[0])); + CHECK(avifROStreamReadU32(&s, (uint32_t *)&fixedXYZ[1])); + CHECK(avifROStreamReadU32(&s, (uint32_t *)&fixedXYZ[2])); xyz[0] = fixedToFloat(fixedXYZ[0]); xyz[1] = fixedToFloat(fixedXYZ[1]); @@ -282,37 +282,41 @@ return AVIF_TRUE; } -static avifBool readMat3(uint8_t * data, size_t size, gbMat3 * m) +static avifBool readMat3(const uint8_t * data, size_t size, gbMat3 * m) { - avifRawData xyzData; + avifROData xyzData; xyzData.data = data; xyzData.size = size; - avifStream s; - avifStreamStart(&s, &xyzData); - CHECK(avifStreamSkip(&s, 8)); + avifROStream s; + avifROStreamStart(&s, &xyzData); + CHECK(avifROStreamSkip(&s, 8)); for (int i = 0; i < 9; ++i) { int32_t fixedXYZ; - CHECK(avifStreamReadU32(&s, (uint32_t *)&fixedXYZ)); + CHECK(avifROStreamReadU32(&s, (uint32_t *)&fixedXYZ)); m->e[i] = fixedToFloat(fixedXYZ); } return AVIF_TRUE; } -static avifBool calcYUVInfoFromICC(avifRawData * icc, float coeffs[3]) +static avifBool calcYUVInfoFromICC(const uint8_t * iccData, size_t iccSize, float coeffs[3]) { - avifStream s; + avifROData icc; + icc.data = iccData; + icc.size = iccSize; + + avifROStream s; + avifROStreamStart(&s, &icc); uint8_t iccMajorVersion; - avifStreamStart(&s, icc); - CHECK(avifStreamSkip(&s, 8)); // skip to version - CHECK(avifStreamRead(&s, &iccMajorVersion, 1)); + CHECK(avifROStreamSkip(&s, 8)); // skip to version + CHECK(avifROStreamRead(&s, &iccMajorVersion, 1)); - avifStreamStart(&s, icc); // start stream over - CHECK(avifStreamSkip(&s, 128)); // skip past the ICC header + avifROStreamStart(&s, &icc); // start stream over + CHECK(avifROStreamSkip(&s, 128)); // skip past the ICC header uint32_t tagCount; - CHECK(avifStreamReadU32(&s, &tagCount)); + CHECK(avifROStreamReadU32(&s, &tagCount)); avifBool rXYZPresent = AVIF_FALSE; avifBool gXYZPresent = AVIF_FALSE; @@ -330,26 +334,26 @@ uint8_t tagSignature[4]; uint32_t tagOffset; uint32_t tagSize; - CHECK(avifStreamRead(&s, tagSignature, 4)); - CHECK(avifStreamReadU32(&s, &tagOffset)); - CHECK(avifStreamReadU32(&s, &tagSize)); - if ((tagOffset + tagSize) > icc->size) { + CHECK(avifROStreamRead(&s, tagSignature, 4)); + CHECK(avifROStreamReadU32(&s, &tagOffset)); + CHECK(avifROStreamReadU32(&s, &tagSize)); + if ((tagOffset + tagSize) > icc.size) { return AVIF_FALSE; } if (!memcmp(tagSignature, "rXYZ", 4)) { - CHECK(readXYZ(icc->data + tagOffset, tagSize, &colorants.e[0])); + CHECK(readXYZ(icc.data + tagOffset, tagSize, &colorants.e[0])); rXYZPresent = AVIF_TRUE; } else if (!memcmp(tagSignature, "gXYZ", 4)) { - CHECK(readXYZ(icc->data + tagOffset, tagSize, &colorants.e[3])); + CHECK(readXYZ(icc.data + tagOffset, tagSize, &colorants.e[3])); gXYZPresent = AVIF_TRUE; } else if (!memcmp(tagSignature, "bXYZ", 4)) { - CHECK(readXYZ(icc->data + tagOffset, tagSize, &colorants.e[6])); + CHECK(readXYZ(icc.data + tagOffset, tagSize, &colorants.e[6])); bXYZPresent = AVIF_TRUE; } else if (!memcmp(tagSignature, "wtpt", 4)) { - CHECK(readXYZ(icc->data + tagOffset, tagSize, &wtpt.e[0])); + CHECK(readXYZ(icc.data + tagOffset, tagSize, &wtpt.e[0])); wtptPresent = AVIF_TRUE; } else if (!memcmp(tagSignature, "chad", 4)) { - CHECK(readMat3(icc->data + tagOffset, tagSize, &chad)); + CHECK(readMat3(icc.data + tagOffset, tagSize, &chad)); chadPresent = AVIF_TRUE; } } @@ -462,7 +466,7 @@ float coeffs[3]; if ((image->profileFormat == AVIF_PROFILE_FORMAT_ICC) && image->icc.data && image->icc.size) { - if (calcYUVInfoFromICC(&image->icc, coeffs)) { + if (calcYUVInfoFromICC(image->icc.data, image->icc.size, coeffs)) { kr = coeffs[0]; kg = coeffs[1]; kb = coeffs[2];
diff --git a/src/rawdata.c b/src/rawdata.c index 86e7476..afff617 100644 --- a/src/rawdata.c +++ b/src/rawdata.c
@@ -5,7 +5,7 @@ #include <string.h> -void avifRawDataRealloc(avifRawData * raw, size_t newSize) +void avifRWDataRealloc(avifRWData * raw, size_t newSize) { if (raw->size != newSize) { uint8_t * old = raw->data; @@ -20,37 +20,19 @@ } } -void avifRawDataSet(avifRawData * raw, const uint8_t * data, size_t len) +void avifRWDataSet(avifRWData * raw, const uint8_t * data, size_t len) { if (len) { - avifRawDataRealloc(raw, len); + avifRWDataRealloc(raw, len); memcpy(raw->data, data, len); } else { avifFree(raw); } } -void avifRawDataFree(avifRawData * raw) +void avifRWDataFree(avifRWData * raw) { avifFree(raw->data); raw->data = NULL; raw->size = 0; } - -void avifRawDataConcat(avifRawData * dst, avifRawData ** srcs, int srcsCount) -{ - size_t totalSize = 0; - for (int i = 0; i < srcsCount; ++i) { - totalSize += srcs[i]->size; - } - - avifRawDataRealloc(dst, totalSize); - - uint8_t * p = dst->data; - for (int i = 0; i < srcsCount; ++i) { - if (srcs[i]->size) { - memcpy(p, srcs[i]->data, srcs[i]->size); - p += srcs[i]->size; - } - } -}
diff --git a/src/read.c b/src/read.c index 7c16d86..06e87ea 100644 --- a/src/read.c +++ b/src/read.c
@@ -50,7 +50,7 @@ typedef struct avifColourInformationBox { avifProfileFormat format; - uint8_t * icc; + const uint8_t * icc; size_t iccSize; avifNclxColorProfile nclx; } avifColourInformationBox; @@ -177,7 +177,7 @@ { avifCodecDecodeInput * decodeInput = (avifCodecDecodeInput *)avifAlloc(sizeof(avifCodecDecodeInput)); memset(decodeInput, 0, sizeof(avifCodecDecodeInput)); - avifArrayCreate(&decodeInput->samples, sizeof(avifRawData), 1); + avifArrayCreate(&decodeInput->samples, sizeof(avifROData), 1); return decodeInput; } @@ -187,7 +187,7 @@ avifFree(decodeInput); } -static avifBool avifCodecDecodeInputGetSamples(avifCodecDecodeInput * decodeInput, avifSampleTable * sampleTable, avifRawData * rawInput) +static avifBool avifCodecDecodeInputGetSamples(avifCodecDecodeInput * decodeInput, avifSampleTable * sampleTable, avifROData * rawInput) { uint32_t sampleSizeIndex = 0; for (uint32_t chunkIndex = 0; chunkIndex < sampleTable->chunks.count; ++chunkIndex) { @@ -216,7 +216,7 @@ avifSampleTableSampleSize * sampleSize = &sampleTable->sampleSizes.sampleSize[sampleSizeIndex]; - avifRawData * rawSample = (avifRawData *)avifArrayPushPtr(&decodeInput->samples); + avifROData * rawSample = (avifROData *)avifArrayPushPtr(&decodeInput->samples); rawSample->data = rawInput->data + sampleOffset; rawSample->size = sampleSize->size; @@ -240,7 +240,7 @@ avifItemArray items; avifPropertyArray properties; avifTrackArray tracks; - avifRawData rawInput; + avifROData rawInput; avifCodecDecodeInput * colorInput; avifCodecDecodeInput * alphaInput; avifDecoderSource source; @@ -321,43 +321,43 @@ // BMFF Parsing #define BEGIN_STREAM(VARNAME, PTR, SIZE) \ - avifStream VARNAME; \ - avifRawData VARNAME##_rawData; \ - VARNAME##_rawData.data = PTR; \ - VARNAME##_rawData.size = SIZE; \ - avifStreamStart(&VARNAME, &VARNAME##_rawData) + avifROStream VARNAME; \ + avifROData VARNAME##_roData; \ + VARNAME##_roData.data = PTR; \ + VARNAME##_roData.size = SIZE; \ + avifROStreamStart(&VARNAME, &VARNAME##_roData) -static avifBool avifParseItemLocationBox(avifData * data, uint8_t * raw, size_t rawLen) +static avifBool avifParseItemLocationBox(avifData * data, const uint8_t * raw, size_t rawLen) { BEGIN_STREAM(s, raw, rawLen); - CHECK(avifStreamReadAndEnforceVersion(&s, 0)); + CHECK(avifROStreamReadAndEnforceVersion(&s, 0)); uint8_t offsetSizeAndLengthSize; - CHECK(avifStreamRead(&s, &offsetSizeAndLengthSize, 1)); + CHECK(avifROStreamRead(&s, &offsetSizeAndLengthSize, 1)); uint8_t offsetSize = (offsetSizeAndLengthSize >> 4) & 0xf; // unsigned int(4) offset_size; uint8_t lengthSize = (offsetSizeAndLengthSize >> 0) & 0xf; // unsigned int(4) length_size; uint8_t baseOffsetSizeAndReserved; - CHECK(avifStreamRead(&s, &baseOffsetSizeAndReserved, 1)); + CHECK(avifROStreamRead(&s, &baseOffsetSizeAndReserved, 1)); uint8_t baseOffsetSize = (baseOffsetSizeAndReserved >> 4) & 0xf; // unsigned int(4) base_offset_size; uint16_t itemCount; - CHECK(avifStreamReadU16(&s, &itemCount)); // unsigned int(16) item_count; + CHECK(avifROStreamReadU16(&s, &itemCount)); // unsigned int(16) item_count; for (int i = 0; i < itemCount; ++i) { - uint16_t itemID; // unsigned int(16) item_ID; - CHECK(avifStreamReadU16(&s, &itemID)); // - uint16_t dataReferenceIndex; // unsigned int(16) data_ref rence_index; - CHECK(avifStreamReadU16(&s, &dataReferenceIndex)); // - uint64_t baseOffset; // unsigned int(base_offset_size*8) base_offset; - CHECK(avifStreamReadUX8(&s, &baseOffset, baseOffsetSize)); // - uint16_t extentCount; // unsigned int(16) extent_count; - CHECK(avifStreamReadU16(&s, &extentCount)); // + uint16_t itemID; // unsigned int(16) item_ID; + CHECK(avifROStreamReadU16(&s, &itemID)); // + uint16_t dataReferenceIndex; // unsigned int(16) data_ref rence_index; + CHECK(avifROStreamReadU16(&s, &dataReferenceIndex)); // + uint64_t baseOffset; // unsigned int(base_offset_size*8) base_offset; + CHECK(avifROStreamReadUX8(&s, &baseOffset, baseOffsetSize)); // + uint16_t extentCount; // unsigned int(16) extent_count; + CHECK(avifROStreamReadU16(&s, &extentCount)); // if (extentCount == 1) { uint64_t extentOffset; // unsigned int(offset_size*8) extent_offset; - CHECK(avifStreamReadUX8(&s, &extentOffset, offsetSize)); + CHECK(avifROStreamReadUX8(&s, &extentOffset, offsetSize)); uint64_t extentLength; // unsigned int(offset_size*8) extent_length; - CHECK(avifStreamReadUX8(&s, &extentLength, lengthSize)); + CHECK(avifROStreamReadUX8(&s, &extentLength, lengthSize)); avifItem * item = avifDataFindItem(data, itemID); if (!item) { @@ -374,110 +374,110 @@ return AVIF_TRUE; } -static avifBool avifParseImageSpatialExtentsProperty(avifData * data, uint8_t * raw, size_t rawLen, int propertyIndex) +static avifBool avifParseImageSpatialExtentsProperty(avifData * data, const uint8_t * raw, size_t rawLen, int propertyIndex) { BEGIN_STREAM(s, raw, rawLen); - CHECK(avifStreamReadAndEnforceVersion(&s, 0)); + CHECK(avifROStreamReadAndEnforceVersion(&s, 0)); - CHECK(avifStreamReadU32(&s, &data->properties.prop[propertyIndex].ispe.width)); - CHECK(avifStreamReadU32(&s, &data->properties.prop[propertyIndex].ispe.height)); + CHECK(avifROStreamReadU32(&s, &data->properties.prop[propertyIndex].ispe.width)); + CHECK(avifROStreamReadU32(&s, &data->properties.prop[propertyIndex].ispe.height)); return AVIF_TRUE; } -static avifBool avifParseAuxiliaryTypeProperty(avifData * data, uint8_t * raw, size_t rawLen, int propertyIndex) +static avifBool avifParseAuxiliaryTypeProperty(avifData * data, const uint8_t * raw, size_t rawLen, int propertyIndex) { BEGIN_STREAM(s, raw, rawLen); - CHECK(avifStreamReadAndEnforceVersion(&s, 0)); + CHECK(avifROStreamReadAndEnforceVersion(&s, 0)); - CHECK(avifStreamReadString(&s, data->properties.prop[propertyIndex].auxC.auxType, AUXTYPE_SIZE)); + CHECK(avifROStreamReadString(&s, data->properties.prop[propertyIndex].auxC.auxType, AUXTYPE_SIZE)); return AVIF_TRUE; } -static avifBool avifParseColourInformationBox(avifData * data, uint8_t * raw, size_t rawLen, int propertyIndex) +static avifBool avifParseColourInformationBox(avifData * data, const uint8_t * raw, size_t rawLen, int propertyIndex) { BEGIN_STREAM(s, raw, rawLen); data->properties.prop[propertyIndex].colr.format = AVIF_PROFILE_FORMAT_NONE; uint8_t colourType[4]; // unsigned int(32) colour_type; - CHECK(avifStreamRead(&s, colourType, 4)); + CHECK(avifROStreamRead(&s, colourType, 4)); if (!memcmp(colourType, "rICC", 4) || !memcmp(colourType, "prof", 4)) { data->properties.prop[propertyIndex].colr.format = AVIF_PROFILE_FORMAT_ICC; - data->properties.prop[propertyIndex].colr.icc = avifStreamCurrent(&s); - data->properties.prop[propertyIndex].colr.iccSize = avifStreamRemainingBytes(&s); + data->properties.prop[propertyIndex].colr.icc = avifROStreamCurrent(&s); + data->properties.prop[propertyIndex].colr.iccSize = avifROStreamRemainingBytes(&s); } else if (!memcmp(colourType, "nclx", 4)) { // unsigned int(16) colour_primaries; - CHECK(avifStreamReadU16(&s, &data->properties.prop[propertyIndex].colr.nclx.colourPrimaries)); + CHECK(avifROStreamReadU16(&s, &data->properties.prop[propertyIndex].colr.nclx.colourPrimaries)); // unsigned int(16) transfer_characteristics; - CHECK(avifStreamReadU16(&s, &data->properties.prop[propertyIndex].colr.nclx.transferCharacteristics)); + CHECK(avifROStreamReadU16(&s, &data->properties.prop[propertyIndex].colr.nclx.transferCharacteristics)); // unsigned int(16) matrix_coefficients; - CHECK(avifStreamReadU16(&s, &data->properties.prop[propertyIndex].colr.nclx.matrixCoefficients)); + CHECK(avifROStreamReadU16(&s, &data->properties.prop[propertyIndex].colr.nclx.matrixCoefficients)); // unsigned int(1) full_range_flag; // unsigned int(7) reserved = 0; - CHECK(avifStreamRead(&s, &data->properties.prop[propertyIndex].colr.nclx.fullRangeFlag, 1)); + CHECK(avifROStreamRead(&s, &data->properties.prop[propertyIndex].colr.nclx.fullRangeFlag, 1)); data->properties.prop[propertyIndex].colr.nclx.fullRangeFlag |= 0x80; data->properties.prop[propertyIndex].colr.format = AVIF_PROFILE_FORMAT_NCLX; } return AVIF_TRUE; } -static avifBool avifParseItemPropertyContainerBox(avifData * data, uint8_t * raw, size_t rawLen) +static avifBool avifParseItemPropertyContainerBox(avifData * data, const uint8_t * raw, size_t rawLen) { BEGIN_STREAM(s, raw, rawLen); - while (avifStreamHasBytesLeft(&s, 1)) { + while (avifROStreamHasBytesLeft(&s, 1)) { avifBoxHeader header; - CHECK(avifStreamReadBoxHeader(&s, &header)); + CHECK(avifROStreamReadBoxHeader(&s, &header)); int propertyIndex = avifArrayPushIndex(&data->properties); memcpy(data->properties.prop[propertyIndex].type, header.type, 4); if (!memcmp(header.type, "ispe", 4)) { - CHECK(avifParseImageSpatialExtentsProperty(data, avifStreamCurrent(&s), header.size, propertyIndex)); + CHECK(avifParseImageSpatialExtentsProperty(data, avifROStreamCurrent(&s), header.size, propertyIndex)); } if (!memcmp(header.type, "auxC", 4)) { - CHECK(avifParseAuxiliaryTypeProperty(data, avifStreamCurrent(&s), header.size, propertyIndex)); + CHECK(avifParseAuxiliaryTypeProperty(data, avifROStreamCurrent(&s), header.size, propertyIndex)); } if (!memcmp(header.type, "colr", 4)) { - CHECK(avifParseColourInformationBox(data, avifStreamCurrent(&s), header.size, propertyIndex)); + CHECK(avifParseColourInformationBox(data, avifROStreamCurrent(&s), header.size, propertyIndex)); } - CHECK(avifStreamSkip(&s, header.size)); + CHECK(avifROStreamSkip(&s, header.size)); } return AVIF_TRUE; } -static avifBool avifParseItemPropertyAssociation(avifData * data, uint8_t * raw, size_t rawLen) +static avifBool avifParseItemPropertyAssociation(avifData * data, const uint8_t * raw, size_t rawLen) { BEGIN_STREAM(s, raw, rawLen); uint8_t version; uint8_t flags[3]; - CHECK(avifStreamReadVersionAndFlags(&s, &version, flags)); + CHECK(avifROStreamReadVersionAndFlags(&s, &version, flags)); avifBool propertyIndexIsU16 = (flags[2] & 0x1) ? AVIF_TRUE : AVIF_FALSE; // is flags[2] correct? uint32_t entryCount; - CHECK(avifStreamReadU32(&s, &entryCount)); + CHECK(avifROStreamReadU32(&s, &entryCount)); for (uint32_t entryIndex = 0; entryIndex < entryCount; ++entryIndex) { unsigned int itemID; if (version < 1) { uint16_t tmp; - CHECK(avifStreamReadU16(&s, &tmp)); + CHECK(avifROStreamReadU16(&s, &tmp)); itemID = tmp; } else { - CHECK(avifStreamReadU32(&s, &itemID)); + CHECK(avifROStreamReadU32(&s, &itemID)); } uint8_t associationCount; - CHECK(avifStreamRead(&s, &associationCount, 1)); + CHECK(avifROStreamRead(&s, &associationCount, 1)); for (uint8_t associationIndex = 0; associationIndex < associationCount; ++associationIndex) { // avifBool essential = AVIF_FALSE; // currently unused uint16_t propertyIndex = 0; if (propertyIndexIsU16) { - CHECK(avifStreamReadU16(&s, &propertyIndex)); + CHECK(avifROStreamReadU16(&s, &propertyIndex)); // essential = (propertyIndex & 0x8000) ? AVIF_TRUE : AVIF_FALSE; propertyIndex &= 0x7fff; } else { uint8_t tmp; - CHECK(avifStreamRead(&s, &tmp, 1)); + CHECK(avifROStreamRead(&s, &tmp, 1)); // essential = (tmp & 0x80) ? AVIF_TRUE : AVIF_FALSE; propertyIndex = tmp & 0x7f; } @@ -515,49 +515,49 @@ return AVIF_TRUE; } -static avifBool avifParseItemPropertiesBox(avifData * data, uint8_t * raw, size_t rawLen) +static avifBool avifParseItemPropertiesBox(avifData * data, const uint8_t * raw, size_t rawLen) { BEGIN_STREAM(s, raw, rawLen); avifBoxHeader ipcoHeader; - CHECK(avifStreamReadBoxHeader(&s, &ipcoHeader)); + CHECK(avifROStreamReadBoxHeader(&s, &ipcoHeader)); if (memcmp(ipcoHeader.type, "ipco", 4) != 0) { return AVIF_FALSE; } // Read all item properties inside of ItemPropertyContainerBox - CHECK(avifParseItemPropertyContainerBox(data, avifStreamCurrent(&s), ipcoHeader.size)); - CHECK(avifStreamSkip(&s, ipcoHeader.size)); + CHECK(avifParseItemPropertyContainerBox(data, avifROStreamCurrent(&s), ipcoHeader.size)); + CHECK(avifROStreamSkip(&s, ipcoHeader.size)); // Now read all ItemPropertyAssociation until the end of the box, and make associations - while (avifStreamHasBytesLeft(&s, 1)) { + while (avifROStreamHasBytesLeft(&s, 1)) { avifBoxHeader ipmaHeader; - CHECK(avifStreamReadBoxHeader(&s, &ipmaHeader)); + CHECK(avifROStreamReadBoxHeader(&s, &ipmaHeader)); if (!memcmp(ipmaHeader.type, "ipma", 4)) { - CHECK(avifParseItemPropertyAssociation(data, avifStreamCurrent(&s), ipmaHeader.size)); + CHECK(avifParseItemPropertyAssociation(data, avifROStreamCurrent(&s), ipmaHeader.size)); } else { // These must all be type ipma return AVIF_FALSE; } - CHECK(avifStreamSkip(&s, ipmaHeader.size)); + CHECK(avifROStreamSkip(&s, ipmaHeader.size)); } return AVIF_TRUE; } -static avifBool avifParseItemInfoEntry(avifData * data, uint8_t * raw, size_t rawLen) +static avifBool avifParseItemInfoEntry(avifData * data, const uint8_t * raw, size_t rawLen) { BEGIN_STREAM(s, raw, rawLen); - CHECK(avifStreamReadAndEnforceVersion(&s, 2)); // TODO: support version > 2? 2+ is required for item_type + CHECK(avifROStreamReadAndEnforceVersion(&s, 2)); // TODO: support version > 2? 2+ is required for item_type - uint16_t itemID; // unsigned int(16) item_ID; - CHECK(avifStreamReadU16(&s, &itemID)); // - uint16_t itemProtectionIndex; // unsigned int(16) item_protection_index; - CHECK(avifStreamReadU16(&s, &itemProtectionIndex)); // - uint8_t itemType[4]; // unsigned int(32) item_type; - CHECK(avifStreamRead(&s, itemType, 4)); // + uint16_t itemID; // unsigned int(16) item_ID; + CHECK(avifROStreamReadU16(&s, &itemID)); // + uint16_t itemProtectionIndex; // unsigned int(16) item_protection_index; + CHECK(avifROStreamReadU16(&s, &itemProtectionIndex)); // + uint8_t itemType[4]; // unsigned int(32) item_type; + CHECK(avifROStreamRead(&s, itemType, 4)); // avifItem * item = avifDataFindItem(data, itemID); if (!item) { @@ -568,74 +568,74 @@ return AVIF_TRUE; } -static avifBool avifParseItemInfoBox(avifData * data, uint8_t * raw, size_t rawLen) +static avifBool avifParseItemInfoBox(avifData * data, const uint8_t * raw, size_t rawLen) { BEGIN_STREAM(s, raw, rawLen); uint8_t version; - CHECK(avifStreamReadVersionAndFlags(&s, &version, NULL)); + CHECK(avifROStreamReadVersionAndFlags(&s, &version, NULL)); uint32_t entryCount; if (version == 0) { uint16_t tmp; - CHECK(avifStreamReadU16(&s, &tmp)); // unsigned int(16) entry_count; + CHECK(avifROStreamReadU16(&s, &tmp)); // unsigned int(16) entry_count; entryCount = tmp; } else if (version == 1) { - CHECK(avifStreamReadU32(&s, &entryCount)); // unsigned int(32) entry_count; + CHECK(avifROStreamReadU32(&s, &entryCount)); // unsigned int(32) entry_count; } else { return AVIF_FALSE; } for (uint32_t entryIndex = 0; entryIndex < entryCount; ++entryIndex) { avifBoxHeader infeHeader; - CHECK(avifStreamReadBoxHeader(&s, &infeHeader)); + CHECK(avifROStreamReadBoxHeader(&s, &infeHeader)); if (!memcmp(infeHeader.type, "infe", 4)) { - CHECK(avifParseItemInfoEntry(data, avifStreamCurrent(&s), infeHeader.size)); + CHECK(avifParseItemInfoEntry(data, avifROStreamCurrent(&s), infeHeader.size)); } else { // These must all be type ipma return AVIF_FALSE; } - CHECK(avifStreamSkip(&s, infeHeader.size)); + CHECK(avifROStreamSkip(&s, infeHeader.size)); } return AVIF_TRUE; } -static avifBool avifParseItemReferenceBox(avifData * data, uint8_t * raw, size_t rawLen) +static avifBool avifParseItemReferenceBox(avifData * data, const uint8_t * raw, size_t rawLen) { BEGIN_STREAM(s, raw, rawLen); uint8_t version; - CHECK(avifStreamReadVersionAndFlags(&s, &version, NULL)); + CHECK(avifROStreamReadVersionAndFlags(&s, &version, NULL)); - while (avifStreamHasBytesLeft(&s, 1)) { + while (avifROStreamHasBytesLeft(&s, 1)) { avifBoxHeader irefHeader; - CHECK(avifStreamReadBoxHeader(&s, &irefHeader)); + CHECK(avifROStreamReadBoxHeader(&s, &irefHeader)); uint32_t fromID = 0; if (version == 0) { uint16_t tmp; - CHECK(avifStreamReadU16(&s, &tmp)); // unsigned int(16) from_item_ID; + CHECK(avifROStreamReadU16(&s, &tmp)); // unsigned int(16) from_item_ID; fromID = tmp; } else if (version == 1) { - CHECK(avifStreamReadU32(&s, &fromID)); // unsigned int(32) from_item_ID; + CHECK(avifROStreamReadU32(&s, &fromID)); // unsigned int(32) from_item_ID; } else { // unsupported iref version, skip it break; } uint16_t referenceCount = 0; - CHECK(avifStreamReadU16(&s, &referenceCount)); // unsigned int(16) reference_count; + CHECK(avifROStreamReadU16(&s, &referenceCount)); // unsigned int(16) reference_count; for (uint16_t refIndex = 0; refIndex < referenceCount; ++refIndex) { uint32_t toID = 0; if (version == 0) { uint16_t tmp; - CHECK(avifStreamReadU16(&s, &tmp)); // unsigned int(16) to_item_ID; + CHECK(avifROStreamReadU16(&s, &tmp)); // unsigned int(16) to_item_ID; toID = tmp; } else if (version == 1) { - CHECK(avifStreamReadU32(&s, &toID)); // unsigned int(32) to_item_ID; + CHECK(avifROStreamReadU32(&s, &toID)); // unsigned int(32) to_item_ID; } else { // unsupported iref version, skip it break; @@ -661,50 +661,50 @@ return AVIF_TRUE; } -static avifBool avifParseMetaBox(avifData * data, uint8_t * raw, size_t rawLen) +static avifBool avifParseMetaBox(avifData * data, const uint8_t * raw, size_t rawLen) { BEGIN_STREAM(s, raw, rawLen); - CHECK(avifStreamReadAndEnforceVersion(&s, 0)); + CHECK(avifROStreamReadAndEnforceVersion(&s, 0)); - while (avifStreamHasBytesLeft(&s, 1)) { + while (avifROStreamHasBytesLeft(&s, 1)) { avifBoxHeader header; - CHECK(avifStreamReadBoxHeader(&s, &header)); + CHECK(avifROStreamReadBoxHeader(&s, &header)); if (!memcmp(header.type, "iloc", 4)) { - CHECK(avifParseItemLocationBox(data, avifStreamCurrent(&s), header.size)); + CHECK(avifParseItemLocationBox(data, avifROStreamCurrent(&s), header.size)); } else if (!memcmp(header.type, "iprp", 4)) { - CHECK(avifParseItemPropertiesBox(data, avifStreamCurrent(&s), header.size)); + CHECK(avifParseItemPropertiesBox(data, avifROStreamCurrent(&s), header.size)); } else if (!memcmp(header.type, "iinf", 4)) { - CHECK(avifParseItemInfoBox(data, avifStreamCurrent(&s), header.size)); + CHECK(avifParseItemInfoBox(data, avifROStreamCurrent(&s), header.size)); } else if (!memcmp(header.type, "iref", 4)) { - CHECK(avifParseItemReferenceBox(data, avifStreamCurrent(&s), header.size)); + CHECK(avifParseItemReferenceBox(data, avifROStreamCurrent(&s), header.size)); } - CHECK(avifStreamSkip(&s, header.size)); + CHECK(avifROStreamSkip(&s, header.size)); } return AVIF_TRUE; } -static avifBool avifParseTrackHeaderBox(avifData * data, avifTrack * track, uint8_t * raw, size_t rawLen) +static avifBool avifParseTrackHeaderBox(avifData * data, avifTrack * track, const uint8_t * raw, size_t rawLen) { BEGIN_STREAM(s, raw, rawLen); (void)data; uint8_t version; uint8_t flags[3]; - CHECK(avifStreamReadVersionAndFlags(&s, &version, flags)); + CHECK(avifROStreamReadVersionAndFlags(&s, &version, flags)); uint32_t ignored32, trackID; uint64_t ignored64; if (version == 1) { - CHECK(avifStreamReadU64(&s, &ignored64)); // unsigned int(64) creation_time; - CHECK(avifStreamReadU64(&s, &ignored64)); // unsigned int(64) modification_time; - CHECK(avifStreamReadU32(&s, &trackID)); // unsigned int(32) track_ID; + CHECK(avifROStreamReadU64(&s, &ignored64)); // unsigned int(64) creation_time; + CHECK(avifROStreamReadU64(&s, &ignored64)); // unsigned int(64) modification_time; + CHECK(avifROStreamReadU32(&s, &trackID)); // unsigned int(32) track_ID; } else if (version == 0) { - CHECK(avifStreamReadU32(&s, &ignored32)); // unsigned int(32) creation_time; - CHECK(avifStreamReadU32(&s, &ignored32)); // unsigned int(32) modification_time; - CHECK(avifStreamReadU32(&s, &trackID)); // unsigned int(32) track_ID; + CHECK(avifROStreamReadU32(&s, &ignored32)); // unsigned int(32) creation_time; + CHECK(avifROStreamReadU32(&s, &ignored32)); // unsigned int(32) modification_time; + CHECK(avifROStreamReadU32(&s, &trackID)); // unsigned int(32) track_ID; } else { // Unsupported version return AVIF_FALSE; @@ -716,28 +716,28 @@ return AVIF_TRUE; } -static avifBool avifParseMediaHeaderBox(avifData * data, avifTrack * track, uint8_t * raw, size_t rawLen) +static avifBool avifParseMediaHeaderBox(avifData * data, avifTrack * track, const uint8_t * raw, size_t rawLen) { BEGIN_STREAM(s, raw, rawLen); (void)data; uint8_t version; uint8_t flags[3]; - CHECK(avifStreamReadVersionAndFlags(&s, &version, flags)); + CHECK(avifROStreamReadVersionAndFlags(&s, &version, flags)); uint32_t ignored32, mediaTimescale, mediaDuration32; uint64_t ignored64, mediaDuration64; if (version == 1) { - CHECK(avifStreamReadU64(&s, &ignored64)); // unsigned int(64) creation_time; - CHECK(avifStreamReadU64(&s, &ignored64)); // unsigned int(64) modification_time; - CHECK(avifStreamReadU32(&s, &mediaTimescale)); // unsigned int(32) timescale; - CHECK(avifStreamReadU64(&s, &mediaDuration64)); // unsigned int(64) duration; + CHECK(avifROStreamReadU64(&s, &ignored64)); // unsigned int(64) creation_time; + CHECK(avifROStreamReadU64(&s, &ignored64)); // unsigned int(64) modification_time; + CHECK(avifROStreamReadU32(&s, &mediaTimescale)); // unsigned int(32) timescale; + CHECK(avifROStreamReadU64(&s, &mediaDuration64)); // unsigned int(64) duration; track->mediaDuration = mediaDuration64; } else if (version == 0) { - CHECK(avifStreamReadU32(&s, &ignored32)); // unsigned int(32) creation_time; - CHECK(avifStreamReadU32(&s, &ignored32)); // unsigned int(32) modification_time; - CHECK(avifStreamReadU32(&s, &mediaTimescale)); // unsigned int(32) timescale; - CHECK(avifStreamReadU32(&s, &mediaDuration32)); // unsigned int(32) duration; + CHECK(avifROStreamReadU32(&s, &ignored32)); // unsigned int(32) creation_time; + CHECK(avifROStreamReadU32(&s, &ignored32)); // unsigned int(32) modification_time; + CHECK(avifROStreamReadU32(&s, &mediaTimescale)); // unsigned int(32) timescale; + CHECK(avifROStreamReadU32(&s, &mediaDuration32)); // unsigned int(32) duration; track->mediaDuration = (uint64_t)mediaDuration32; } else { // Unsupported version @@ -748,22 +748,22 @@ return AVIF_TRUE; } -static avifBool avifParseChunkOffsetBox(avifData * data, avifSampleTable * sampleTable, avifBool largeOffsets, uint8_t * raw, size_t rawLen) +static avifBool avifParseChunkOffsetBox(avifData * data, avifSampleTable * sampleTable, avifBool largeOffsets, const uint8_t * raw, size_t rawLen) { BEGIN_STREAM(s, raw, rawLen); (void)data; - CHECK(avifStreamReadAndEnforceVersion(&s, 0)); + CHECK(avifROStreamReadAndEnforceVersion(&s, 0)); uint32_t entryCount; - CHECK(avifStreamReadU32(&s, &entryCount)); // unsigned int(32) entry_count; + CHECK(avifROStreamReadU32(&s, &entryCount)); // unsigned int(32) entry_count; for (uint32_t i = 0; i < entryCount; ++i) { uint64_t offset; if (largeOffsets) { - CHECK(avifStreamReadU64(&s, &offset)); // unsigned int(32) chunk_offset; + CHECK(avifROStreamReadU64(&s, &offset)); // unsigned int(32) chunk_offset; } else { uint32_t offset32; - CHECK(avifStreamReadU32(&s, &offset32)); // unsigned int(32) chunk_offset; + CHECK(avifROStreamReadU32(&s, &offset32)); // unsigned int(32) chunk_offset; offset = (uint64_t)offset32; } @@ -773,39 +773,39 @@ return AVIF_TRUE; } -static avifBool avifParseSampleToChunkBox(avifData * data, avifSampleTable * sampleTable, uint8_t * raw, size_t rawLen) +static avifBool avifParseSampleToChunkBox(avifData * data, avifSampleTable * sampleTable, const uint8_t * raw, size_t rawLen) { BEGIN_STREAM(s, raw, rawLen); (void)data; - CHECK(avifStreamReadAndEnforceVersion(&s, 0)); + CHECK(avifROStreamReadAndEnforceVersion(&s, 0)); uint32_t entryCount; - CHECK(avifStreamReadU32(&s, &entryCount)); // unsigned int(32) entry_count; + CHECK(avifROStreamReadU32(&s, &entryCount)); // unsigned int(32) entry_count; for (uint32_t i = 0; i < entryCount; ++i) { avifSampleTableSampleToChunk * sampleToChunk = (avifSampleTableSampleToChunk *)avifArrayPushPtr(&sampleTable->sampleToChunks); - CHECK(avifStreamReadU32(&s, &sampleToChunk->firstChunk)); // unsigned int(32) first_chunk; - CHECK(avifStreamReadU32(&s, &sampleToChunk->samplesPerChunk)); // unsigned int(32) samples_per_chunk; - CHECK(avifStreamReadU32(&s, &sampleToChunk->sampleDescriptionIndex)); // unsigned int(32) sample_description_index; + CHECK(avifROStreamReadU32(&s, &sampleToChunk->firstChunk)); // unsigned int(32) first_chunk; + CHECK(avifROStreamReadU32(&s, &sampleToChunk->samplesPerChunk)); // unsigned int(32) samples_per_chunk; + CHECK(avifROStreamReadU32(&s, &sampleToChunk->sampleDescriptionIndex)); // unsigned int(32) sample_description_index; } return AVIF_TRUE; } -static avifBool avifParseSampleSizeBox(avifData * data, avifSampleTable * sampleTable, uint8_t * raw, size_t rawLen) +static avifBool avifParseSampleSizeBox(avifData * data, avifSampleTable * sampleTable, const uint8_t * raw, size_t rawLen) { BEGIN_STREAM(s, raw, rawLen); (void)data; - CHECK(avifStreamReadAndEnforceVersion(&s, 0)); + CHECK(avifROStreamReadAndEnforceVersion(&s, 0)); uint32_t allSamplesSize, entryCount; - CHECK(avifStreamReadU32(&s, &allSamplesSize)); // unsigned int(32) sample_size; - CHECK(avifStreamReadU32(&s, &entryCount)); // unsigned int(32) entry_count; + CHECK(avifROStreamReadU32(&s, &allSamplesSize)); // unsigned int(32) sample_size; + CHECK(avifROStreamReadU32(&s, &entryCount)); // unsigned int(32) entry_count; for (uint32_t i = 0; i < entryCount; ++i) { avifSampleTableSampleSize * sampleSize = (avifSampleTableSampleSize *)avifArrayPushPtr(&sampleTable->sampleSizes); if (allSamplesSize == 0) { - CHECK(avifStreamReadU32(&s, &sampleSize->size)); // unsigned int(32) entry_size; + CHECK(avifROStreamReadU32(&s, &sampleSize->size)); // unsigned int(32) entry_size; } else { // This could be done more efficiently, memory-wise. sampleSize->size = allSamplesSize; @@ -814,25 +814,25 @@ return AVIF_TRUE; } -static avifBool avifParseTimeToSampleBox(avifData * data, avifSampleTable * sampleTable, uint8_t * raw, size_t rawLen) +static avifBool avifParseTimeToSampleBox(avifData * data, avifSampleTable * sampleTable, const uint8_t * raw, size_t rawLen) { BEGIN_STREAM(s, raw, rawLen); (void)data; - CHECK(avifStreamReadAndEnforceVersion(&s, 0)); + CHECK(avifROStreamReadAndEnforceVersion(&s, 0)); uint32_t entryCount; - CHECK(avifStreamReadU32(&s, &entryCount)); // unsigned int(32) entry_count; + CHECK(avifROStreamReadU32(&s, &entryCount)); // unsigned int(32) entry_count; for (uint32_t i = 0; i < entryCount; ++i) { avifSampleTableTimeToSample * timeToSample = (avifSampleTableTimeToSample *)avifArrayPushPtr(&sampleTable->timeToSamples); - CHECK(avifStreamReadU32(&s, &timeToSample->sampleCount)); // unsigned int(32) sample_count; - CHECK(avifStreamReadU32(&s, &timeToSample->sampleDelta)); // unsigned int(32) sample_delta; + CHECK(avifROStreamReadU32(&s, &timeToSample->sampleCount)); // unsigned int(32) sample_count; + CHECK(avifROStreamReadU32(&s, &timeToSample->sampleDelta)); // unsigned int(32) sample_delta; } return AVIF_TRUE; } -static avifBool avifParseSampleTableBox(avifData * data, avifTrack * track, uint8_t * raw, size_t rawLen) +static avifBool avifParseSampleTableBox(avifData * data, avifTrack * track, const uint8_t * raw, size_t rawLen) { if (track->sampleTable) { // A TrackBox may only have one SampleTable @@ -842,132 +842,132 @@ BEGIN_STREAM(s, raw, rawLen); - while (avifStreamHasBytesLeft(&s, 1)) { + while (avifROStreamHasBytesLeft(&s, 1)) { avifBoxHeader header; - CHECK(avifStreamReadBoxHeader(&s, &header)); + CHECK(avifROStreamReadBoxHeader(&s, &header)); if (!memcmp(header.type, "stco", 4)) { - CHECK(avifParseChunkOffsetBox(data, track->sampleTable, AVIF_FALSE, avifStreamCurrent(&s), header.size)); + CHECK(avifParseChunkOffsetBox(data, track->sampleTable, AVIF_FALSE, avifROStreamCurrent(&s), header.size)); } else if (!memcmp(header.type, "co64", 4)) { - CHECK(avifParseChunkOffsetBox(data, track->sampleTable, AVIF_TRUE, avifStreamCurrent(&s), header.size)); + CHECK(avifParseChunkOffsetBox(data, track->sampleTable, AVIF_TRUE, avifROStreamCurrent(&s), header.size)); } else if (!memcmp(header.type, "stsc", 4)) { - CHECK(avifParseSampleToChunkBox(data, track->sampleTable, avifStreamCurrent(&s), header.size)); + CHECK(avifParseSampleToChunkBox(data, track->sampleTable, avifROStreamCurrent(&s), header.size)); } else if (!memcmp(header.type, "stsz", 4)) { - CHECK(avifParseSampleSizeBox(data, track->sampleTable, avifStreamCurrent(&s), header.size)); + CHECK(avifParseSampleSizeBox(data, track->sampleTable, avifROStreamCurrent(&s), header.size)); } else if (!memcmp(header.type, "stts", 4)) { - CHECK(avifParseTimeToSampleBox(data, track->sampleTable, avifStreamCurrent(&s), header.size)); + CHECK(avifParseTimeToSampleBox(data, track->sampleTable, avifROStreamCurrent(&s), header.size)); } - CHECK(avifStreamSkip(&s, header.size)); + CHECK(avifROStreamSkip(&s, header.size)); } return AVIF_TRUE; } -static avifBool avifParseMediaInformationBox(avifData * data, avifTrack * track, uint8_t * raw, size_t rawLen) +static avifBool avifParseMediaInformationBox(avifData * data, avifTrack * track, const uint8_t * raw, size_t rawLen) { BEGIN_STREAM(s, raw, rawLen); - while (avifStreamHasBytesLeft(&s, 1)) { + while (avifROStreamHasBytesLeft(&s, 1)) { avifBoxHeader header; - CHECK(avifStreamReadBoxHeader(&s, &header)); + CHECK(avifROStreamReadBoxHeader(&s, &header)); if (!memcmp(header.type, "stbl", 4)) { - CHECK(avifParseSampleTableBox(data, track, avifStreamCurrent(&s), header.size)); + CHECK(avifParseSampleTableBox(data, track, avifROStreamCurrent(&s), header.size)); } - CHECK(avifStreamSkip(&s, header.size)); + CHECK(avifROStreamSkip(&s, header.size)); } return AVIF_TRUE; } -static avifBool avifParseMediaBox(avifData * data, avifTrack * track, uint8_t * raw, size_t rawLen) +static avifBool avifParseMediaBox(avifData * data, avifTrack * track, const uint8_t * raw, size_t rawLen) { BEGIN_STREAM(s, raw, rawLen); - while (avifStreamHasBytesLeft(&s, 1)) { + while (avifROStreamHasBytesLeft(&s, 1)) { avifBoxHeader header; - CHECK(avifStreamReadBoxHeader(&s, &header)); + CHECK(avifROStreamReadBoxHeader(&s, &header)); if (!memcmp(header.type, "mdhd", 4)) { - CHECK(avifParseMediaHeaderBox(data, track, avifStreamCurrent(&s), header.size)); + CHECK(avifParseMediaHeaderBox(data, track, avifROStreamCurrent(&s), header.size)); } else if (!memcmp(header.type, "minf", 4)) { - CHECK(avifParseMediaInformationBox(data, track, avifStreamCurrent(&s), header.size)); + CHECK(avifParseMediaInformationBox(data, track, avifROStreamCurrent(&s), header.size)); } - CHECK(avifStreamSkip(&s, header.size)); + CHECK(avifROStreamSkip(&s, header.size)); } return AVIF_TRUE; } -static avifBool avifTrackReferenceBox(avifData * data, avifTrack * track, uint8_t * raw, size_t rawLen) +static avifBool avifTrackReferenceBox(avifData * data, avifTrack * track, const uint8_t * raw, size_t rawLen) { BEGIN_STREAM(s, raw, rawLen); (void)data; - while (avifStreamHasBytesLeft(&s, 1)) { + while (avifROStreamHasBytesLeft(&s, 1)) { avifBoxHeader header; - CHECK(avifStreamReadBoxHeader(&s, &header)); + CHECK(avifROStreamReadBoxHeader(&s, &header)); if (!memcmp(header.type, "auxl", 4)) { uint32_t toID; - CHECK(avifStreamReadU32(&s, &toID)); // unsigned int(32) track_IDs[] - CHECK(avifStreamSkip(&s, header.size - sizeof(uint32_t))); // just take the first one + CHECK(avifROStreamReadU32(&s, &toID)); // unsigned int(32) track_IDs[] + CHECK(avifROStreamSkip(&s, header.size - sizeof(uint32_t))); // just take the first one track->auxForID = toID; } else { - CHECK(avifStreamSkip(&s, header.size)); + CHECK(avifROStreamSkip(&s, header.size)); } } return AVIF_TRUE; } -static avifBool avifParseTrackBox(avifData * data, uint8_t * raw, size_t rawLen) +static avifBool avifParseTrackBox(avifData * data, const uint8_t * raw, size_t rawLen) { BEGIN_STREAM(s, raw, rawLen); avifTrack * track = (avifTrack *)avifArrayPushPtr(&data->tracks); - while (avifStreamHasBytesLeft(&s, 1)) { + while (avifROStreamHasBytesLeft(&s, 1)) { avifBoxHeader header; - CHECK(avifStreamReadBoxHeader(&s, &header)); + CHECK(avifROStreamReadBoxHeader(&s, &header)); if (!memcmp(header.type, "tkhd", 4)) { - CHECK(avifParseTrackHeaderBox(data, track, avifStreamCurrent(&s), header.size)); + CHECK(avifParseTrackHeaderBox(data, track, avifROStreamCurrent(&s), header.size)); } else if (!memcmp(header.type, "mdia", 4)) { - CHECK(avifParseMediaBox(data, track, avifStreamCurrent(&s), header.size)); + CHECK(avifParseMediaBox(data, track, avifROStreamCurrent(&s), header.size)); } else if (!memcmp(header.type, "tref", 4)) { - CHECK(avifTrackReferenceBox(data, track, avifStreamCurrent(&s), header.size)); + CHECK(avifTrackReferenceBox(data, track, avifROStreamCurrent(&s), header.size)); } - CHECK(avifStreamSkip(&s, header.size)); + CHECK(avifROStreamSkip(&s, header.size)); } return AVIF_TRUE; } -static avifBool avifParseMoovBox(avifData * data, uint8_t * raw, size_t rawLen) +static avifBool avifParseMoovBox(avifData * data, const uint8_t * raw, size_t rawLen) { BEGIN_STREAM(s, raw, rawLen); - while (avifStreamHasBytesLeft(&s, 1)) { + while (avifROStreamHasBytesLeft(&s, 1)) { avifBoxHeader header; - CHECK(avifStreamReadBoxHeader(&s, &header)); + CHECK(avifROStreamReadBoxHeader(&s, &header)); if (!memcmp(header.type, "trak", 4)) { - CHECK(avifParseTrackBox(data, avifStreamCurrent(&s), header.size)); + CHECK(avifParseTrackBox(data, avifROStreamCurrent(&s), header.size)); } - CHECK(avifStreamSkip(&s, header.size)); + CHECK(avifROStreamSkip(&s, header.size)); } return AVIF_TRUE; } -static avifBool avifParseFileTypeBox(avifFileType * ftyp, uint8_t * raw, size_t rawLen) +static avifBool avifParseFileTypeBox(avifFileType * ftyp, const uint8_t * raw, size_t rawLen) { BEGIN_STREAM(s, raw, rawLen); - CHECK(avifStreamRead(&s, ftyp->majorBrand, 4)); - CHECK(avifStreamReadU32(&s, &ftyp->minorVersion)); + CHECK(avifROStreamRead(&s, ftyp->majorBrand, 4)); + CHECK(avifROStreamReadU32(&s, &ftyp->minorVersion)); - size_t compatibleBrandsBytes = avifStreamRemainingBytes(&s); + size_t compatibleBrandsBytes = avifROStreamRemainingBytes(&s); if ((compatibleBrandsBytes % 4) != 0) { return AVIF_FALSE; } @@ -975,29 +975,29 @@ // TODO: stop clamping and resize this compatibleBrandsBytes = (4 * MAX_COMPATIBLE_BRANDS); } - CHECK(avifStreamRead(&s, ftyp->compatibleBrands, compatibleBrandsBytes)); + CHECK(avifROStreamRead(&s, ftyp->compatibleBrands, compatibleBrandsBytes)); ftyp->compatibleBrandsCount = (int)compatibleBrandsBytes / 4; return AVIF_TRUE; } -static avifBool avifParse(avifData * data, uint8_t * raw, size_t rawLen) +static avifBool avifParse(avifData * data, const uint8_t * raw, size_t rawLen) { BEGIN_STREAM(s, raw, rawLen); - while (avifStreamHasBytesLeft(&s, 1)) { + while (avifROStreamHasBytesLeft(&s, 1)) { avifBoxHeader header; - CHECK(avifStreamReadBoxHeader(&s, &header)); + CHECK(avifROStreamReadBoxHeader(&s, &header)); if (!memcmp(header.type, "ftyp", 4)) { - CHECK(avifParseFileTypeBox(&data->ftyp, avifStreamCurrent(&s), header.size)); + CHECK(avifParseFileTypeBox(&data->ftyp, avifROStreamCurrent(&s), header.size)); } else if (!memcmp(header.type, "meta", 4)) { - CHECK(avifParseMetaBox(data, avifStreamCurrent(&s), header.size)); + CHECK(avifParseMetaBox(data, avifROStreamCurrent(&s), header.size)); } else if (!memcmp(header.type, "moov", 4)) { - CHECK(avifParseMoovBox(data, avifStreamCurrent(&s), header.size)); + CHECK(avifParseMoovBox(data, avifROStreamCurrent(&s), header.size)); } - CHECK(avifStreamSkip(&s, header.size)); + CHECK(avifROStreamSkip(&s, header.size)); } return AVIF_TRUE; } @@ -1026,19 +1026,19 @@ return avifCompatible; } -avifBool avifPeekCompatibleFileType(avifRawData * input) +avifBool avifPeekCompatibleFileType(avifROData * input) { BEGIN_STREAM(s, input->data, input->size); avifBoxHeader header; - CHECK(avifStreamReadBoxHeader(&s, &header)); + CHECK(avifROStreamReadBoxHeader(&s, &header)); if (memcmp(header.type, "ftyp", 4) != 0) { return AVIF_FALSE; } avifFileType ftyp; memset(&ftyp, 0, sizeof(avifFileType)); - avifBool parsed = avifParseFileTypeBox(&ftyp, avifStreamCurrent(&s), header.size); + avifBool parsed = avifParseFileTypeBox(&ftyp, avifROStreamCurrent(&s), header.size); if (!parsed) { return AVIF_FALSE; } @@ -1079,7 +1079,7 @@ return avifDecoderReset(decoder); } -avifResult avifDecoderParse(avifDecoder * decoder, avifRawData * rawInput) +avifResult avifDecoderParse(avifDecoder * decoder, avifROData * rawInput) { #if !defined(AVIF_CODEC_AOM) && !defined(AVIF_CODEC_DAV1D) // Just bail out early, we're not surviving this function without a decoder compiled in @@ -1095,7 +1095,7 @@ decoder->data = avifDataCreate(); // Shallow copy, on purpose - memcpy(&decoder->data->rawInput, rawInput, sizeof(avifRawData)); + memcpy(&decoder->data->rawInput, rawInput, sizeof(avifROData)); if (!avifParse(decoder->data, decoder->data->rawInput.data, decoder->data->rawInput.size)) { return AVIF_RESULT_BMFF_PARSE_FAILED; @@ -1256,8 +1256,8 @@ } else { // Create from items - avifRawData colorOBU = AVIF_RAW_DATA_EMPTY; - avifRawData alphaOBU = AVIF_RAW_DATA_EMPTY; + avifROData colorOBU = AVIF_DATA_EMPTY; + avifROData alphaOBU = AVIF_DATA_EMPTY; avifItem * colorOBUItem = NULL; // Find the colorOBU item @@ -1318,12 +1318,12 @@ } data->colorInput = avifCodecDecodeInputCreate(); - avifRawData * rawColorInput = (avifRawData *)avifArrayPushPtr(&data->colorInput->samples); - memcpy(rawColorInput, &colorOBU, sizeof(avifRawData)); + avifROData * rawColorInput = (avifROData *)avifArrayPushPtr(&data->colorInput->samples); + memcpy(rawColorInput, &colorOBU, sizeof(avifROData)); if (alphaOBU.size > 0) { data->alphaInput = avifCodecDecodeInputCreate(); - avifRawData * rawAlphaInput = (avifRawData *)avifArrayPushPtr(&data->alphaInput->samples); - memcpy(rawAlphaInput, &alphaOBU, sizeof(avifRawData)); + avifROData * rawAlphaInput = (avifROData *)avifArrayPushPtr(&data->alphaInput->samples); + memcpy(rawAlphaInput, &alphaOBU, sizeof(avifROData)); data->alphaInput->alpha = AVIF_TRUE; } @@ -1418,7 +1418,7 @@ return AVIF_RESULT_OK; } -avifResult avifDecoderRead(avifDecoder * decoder, avifImage * image, avifRawData * input) +avifResult avifDecoderRead(avifDecoder * decoder, avifImage * image, avifROData * input) { avifResult result = avifDecoderParse(decoder, input); if (result != AVIF_RESULT_OK) {
diff --git a/src/stream.c b/src/stream.c index 8eb7edc..ce76329 100644 --- a/src/stream.c +++ b/src/stream.c
@@ -5,36 +5,36 @@ #include <string.h> -uint8_t * avifStreamCurrent(avifStream * stream) +// --------------------------------------------------------------------------- +// avifROStream + +const uint8_t * avifROStreamCurrent(avifROStream * stream) { return stream->raw->data + stream->offset; } -void avifStreamStart(avifStream * stream, avifRawData * raw) +void avifROStreamStart(avifROStream * stream, avifROData * raw) { stream->raw = raw; stream->offset = 0; } -// --------------------------------------------------------------------------- -// Read - -avifBool avifStreamHasBytesLeft(avifStream * stream, size_t byteCount) +avifBool avifROStreamHasBytesLeft(avifROStream * stream, size_t byteCount) { return (stream->offset + byteCount) <= stream->raw->size; } -size_t avifStreamRemainingBytes(avifStream * stream) +size_t avifROStreamRemainingBytes(avifROStream * stream) { return stream->raw->size - stream->offset; } -size_t avifStreamOffset(avifStream * stream) +size_t avifROStreamOffset(avifROStream * stream) { return stream->offset; } -void avifStreamSetOffset(avifStream * stream, size_t offset) +void avifROStreamSetOffset(avifROStream * stream, size_t offset) { stream->offset = offset; if (stream->offset > stream->raw->size) { @@ -42,18 +42,18 @@ } } -avifBool avifStreamSkip(avifStream * stream, size_t byteCount) +avifBool avifROStreamSkip(avifROStream * stream, size_t byteCount) { - if (!avifStreamHasBytesLeft(stream, byteCount)) { + if (!avifROStreamHasBytesLeft(stream, byteCount)) { return AVIF_FALSE; } stream->offset += byteCount; return AVIF_TRUE; } -avifBool avifStreamRead(avifStream * stream, uint8_t * data, size_t size) +avifBool avifROStreamRead(avifROStream * stream, uint8_t * data, size_t size) { - if (!avifStreamHasBytesLeft(stream, size)) { + if (!avifROStreamHasBytesLeft(stream, size)) { return AVIF_FALSE; } @@ -62,26 +62,26 @@ return AVIF_TRUE; } -avifBool avifStreamReadUX8(avifStream * stream, uint64_t * v, uint64_t factor) +avifBool avifROStreamReadUX8(avifROStream * stream, uint64_t * v, uint64_t factor) { if (factor == 0) { // Don't read anything, just set to 0 *v = 0; } else if (factor == 1) { uint8_t tmp; - CHECK(avifStreamRead(stream, &tmp, 1)); + CHECK(avifROStreamRead(stream, &tmp, 1)); *v = tmp; } else if (factor == 2) { uint16_t tmp; - CHECK(avifStreamReadU16(stream, &tmp)); + CHECK(avifROStreamReadU16(stream, &tmp)); *v = tmp; } else if (factor == 4) { uint32_t tmp; - CHECK(avifStreamReadU32(stream, &tmp)); + CHECK(avifROStreamReadU32(stream, &tmp)); *v = tmp; } else if (factor == 8) { uint64_t tmp; - CHECK(avifStreamReadU64(stream, &tmp)); + CHECK(avifROStreamReadU64(stream, &tmp)); *v = tmp; } else { // Unsupported factor @@ -90,32 +90,32 @@ return AVIF_TRUE; } -avifBool avifStreamReadU16(avifStream * stream, uint16_t * v) +avifBool avifROStreamReadU16(avifROStream * stream, uint16_t * v) { - CHECK(avifStreamRead(stream, (uint8_t *)v, sizeof(uint16_t))); + CHECK(avifROStreamRead(stream, (uint8_t *)v, sizeof(uint16_t))); *v = avifNTOHS(*v); return AVIF_TRUE; } -avifBool avifStreamReadU32(avifStream * stream, uint32_t * v) +avifBool avifROStreamReadU32(avifROStream * stream, uint32_t * v) { - CHECK(avifStreamRead(stream, (uint8_t *)v, sizeof(uint32_t))); + CHECK(avifROStreamRead(stream, (uint8_t *)v, sizeof(uint32_t))); *v = avifNTOHL(*v); return AVIF_TRUE; } -avifBool avifStreamReadU64(avifStream * stream, uint64_t * v) +avifBool avifROStreamReadU64(avifROStream * stream, uint64_t * v) { - CHECK(avifStreamRead(stream, (uint8_t *)v, sizeof(uint64_t))); + CHECK(avifROStreamRead(stream, (uint8_t *)v, sizeof(uint64_t))); *v = avifNTOH64(*v); return AVIF_TRUE; } -avifBool avifStreamReadString(avifStream * stream, char * output, size_t outputSize) +avifBool avifROStreamReadString(avifROStream * stream, char * output, size_t outputSize) { // Check for the presence of a null terminator in the stream. - size_t remainingBytes = avifStreamRemainingBytes(stream); - uint8_t * p = avifStreamCurrent(stream); + size_t remainingBytes = avifROStreamRemainingBytes(stream); + const uint8_t * p = avifROStreamCurrent(stream); avifBool foundNullTerminator = AVIF_FALSE; for (size_t i = 0; i < remainingBytes; ++i) { if (p[i] == 0) { @@ -140,36 +140,36 @@ return AVIF_TRUE; } -avifBool avifStreamReadBoxHeader(avifStream * stream, avifBoxHeader * header) +avifBool avifROStreamReadBoxHeader(avifROStream * stream, avifBoxHeader * header) { size_t startOffset = stream->offset; uint32_t smallSize; - CHECK(avifStreamReadU32(stream, &smallSize)); - CHECK(avifStreamRead(stream, header->type, 4)); + CHECK(avifROStreamReadU32(stream, &smallSize)); + CHECK(avifROStreamRead(stream, header->type, 4)); uint64_t size = smallSize; if (size == 1) { - CHECK(avifStreamReadU64(stream, &size)); + CHECK(avifROStreamReadU64(stream, &size)); } if (!memcmp(header->type, "uuid", 4)) { - CHECK(avifStreamSkip(stream, 16)); + CHECK(avifROStreamSkip(stream, 16)); } header->size = (size_t)(size - (stream->offset - startOffset)); // Make the assumption here that this box's contents must fit in the remaining portion of the parent stream - if (header->size > avifStreamRemainingBytes(stream)) { + if (header->size > avifROStreamRemainingBytes(stream)) { return AVIF_FALSE; } return AVIF_TRUE; } -avifBool avifStreamReadVersionAndFlags(avifStream * stream, uint8_t * version, uint8_t * flags) +avifBool avifROStreamReadVersionAndFlags(avifROStream * stream, uint8_t * version, uint8_t * flags) { uint8_t versionAndFlags[4]; - CHECK(avifStreamRead(stream, versionAndFlags, 4)); + CHECK(avifROStreamRead(stream, versionAndFlags, 4)); if (version) { *version = versionAndFlags[0]; } @@ -179,18 +179,18 @@ return AVIF_TRUE; } -avifBool avifStreamReadAndEnforceVersion(avifStream * stream, uint8_t enforcedVersion) +avifBool avifROStreamReadAndEnforceVersion(avifROStream * stream, uint8_t enforcedVersion) { uint8_t version; - CHECK(avifStreamReadVersionAndFlags(stream, &version, NULL)); + CHECK(avifROStreamReadVersionAndFlags(stream, &version, NULL)); return (version == enforcedVersion) ? AVIF_TRUE : AVIF_FALSE; } // --------------------------------------------------------------------------- -// Write +// avifRWStream #define AVIF_STREAM_BUFFER_INCREMENT (1024 * 1024) -static void makeRoom(avifStream * stream, size_t size) +static void makeRoom(avifRWStream * stream, size_t size) { size_t neededSize = stream->offset + size; size_t newSize = stream->raw->size; @@ -198,22 +198,41 @@ newSize += AVIF_STREAM_BUFFER_INCREMENT; } if (stream->raw->size != newSize) { - avifRawDataRealloc(stream->raw, newSize); + avifRWDataRealloc(stream->raw, newSize); } } -void avifStreamFinishWrite(avifStream * stream) +void avifRWStreamStart(avifRWStream * stream, avifRWData * raw) +{ + stream->raw = raw; + stream->offset = 0; +} + +size_t avifRWStreamOffset(avifRWStream * stream) +{ + return stream->offset; +} + +void avifRWStreamSetOffset(avifRWStream * stream, size_t offset) +{ + stream->offset = offset; + if (stream->offset > stream->raw->size) { + stream->offset = stream->raw->size; + } +} + +void avifRWStreamFinishWrite(avifRWStream * stream) { if (stream->raw->size != stream->offset) { if (stream->offset) { stream->raw->size = stream->offset; } else { - avifRawDataFree(stream->raw); + avifRWDataFree(stream->raw); } } } -void avifStreamWrite(avifStream * stream, const uint8_t * data, size_t size) +void avifRWStreamWrite(avifRWStream * stream, const uint8_t * data, size_t size) { if (!size) { return; @@ -224,12 +243,12 @@ stream->offset += size; } -void avifStreamWriteChars(avifStream * stream, const char * chars, size_t size) +void avifRWStreamWriteChars(avifRWStream * stream, const char * chars, size_t size) { - avifStreamWrite(stream, (const uint8_t *)chars, size); + avifRWStreamWrite(stream, (const uint8_t *)chars, size); } -avifBoxMarker avifStreamWriteBox(avifStream * stream, const char * type, int version, size_t contentSize) +avifBoxMarker avifRWStreamWriteBox(avifRWStream * stream, const char * type, int version, size_t contentSize) { avifBoxMarker marker = stream->offset; size_t headerSize = sizeof(uint32_t) + 4 /* size of type */; @@ -250,13 +269,13 @@ return marker; } -void avifStreamFinishBox(avifStream * stream, avifBoxMarker marker) +void avifRWStreamFinishBox(avifRWStream * stream, avifBoxMarker marker) { uint32_t noSize = avifNTOHL((uint32_t)(stream->offset - marker)); memcpy(stream->raw->data + marker, &noSize, sizeof(uint32_t)); } -void avifStreamWriteU8(avifStream * stream, uint8_t v) +void avifRWStreamWriteU8(avifRWStream * stream, uint8_t v) { size_t size = sizeof(uint8_t); makeRoom(stream, size); @@ -264,7 +283,7 @@ stream->offset += size; } -void avifStreamWriteU16(avifStream * stream, uint16_t v) +void avifRWStreamWriteU16(avifRWStream * stream, uint16_t v) { size_t size = sizeof(uint16_t); v = avifHTONS(v); @@ -273,7 +292,7 @@ stream->offset += size; } -void avifStreamWriteU32(avifStream * stream, uint32_t v) +void avifRWStreamWriteU32(avifRWStream * stream, uint32_t v) { size_t size = sizeof(uint32_t); v = avifHTONL(v); @@ -282,7 +301,7 @@ stream->offset += size; } -void avifStreamWriteZeros(avifStream * stream, size_t byteCount) +void avifRWStreamWriteZeros(avifRWStream * stream, size_t byteCount) { makeRoom(stream, byteCount); uint8_t * p = stream->raw->data + stream->offset;
diff --git a/src/write.c b/src/write.c index 3967907..3fd41f0 100644 --- a/src/write.c +++ b/src/write.c
@@ -21,7 +21,7 @@ static const size_t alphaURNSize = sizeof(alphaURN); static avifBool avifImageIsOpaque(avifImage * image); -static void writeConfigBox(avifStream * s, avifCodecConfigurationBox * cfg); +static void writeConfigBox(avifRWStream * s, avifCodecConfigurationBox * cfg); avifEncoder * avifEncoderCreate(void) { @@ -47,15 +47,15 @@ #endif } -avifResult avifEncoderWrite(avifEncoder * encoder, avifImage * image, avifRawData * output) +avifResult avifEncoderWrite(avifEncoder * encoder, avifImage * image, avifRWData * output) { if ((image->depth != 8) && (image->depth != 10) && (image->depth != 12)) { return AVIF_RESULT_UNSUPPORTED_DEPTH; } avifResult result = AVIF_RESULT_UNKNOWN_ERROR; - avifRawData colorOBU = AVIF_RAW_DATA_EMPTY; - avifRawData alphaOBU = AVIF_RAW_DATA_EMPTY; + avifRWData colorOBU = AVIF_DATA_EMPTY; + avifRWData alphaOBU = AVIF_DATA_EMPTY; avifCodec * codec[AVIF_CODEC_PLANES_COUNT]; codec[AVIF_CODEC_PLANES_COLOR] = avifCodecCreateForEncode(); @@ -71,8 +71,8 @@ codec[AVIF_CODEC_PLANES_ALPHA] = avifCodecCreateForEncode(); } - avifStream s; - avifStreamStart(&s, output); + avifRWStream s; + avifRWStreamStart(&s, output); // ----------------------------------------------------------------------- // Reformat pixels, if need be @@ -100,7 +100,7 @@ // ----------------------------------------------------------------------- // Encode AV1 OBUs - // avifRawData * alphaOBUPtr = &alphaOBU; + // avifRWData * alphaOBUPtr = &alphaOBU; // if (avifImageIsOpaque(image)) { // alphaOBUPtr = NULL; // } @@ -122,41 +122,41 @@ // ----------------------------------------------------------------------- // Write ftyp - avifBoxMarker ftyp = avifStreamWriteBox(&s, "ftyp", -1, 0); - avifStreamWriteChars(&s, "avif", 4); // unsigned int(32) major_brand; - avifStreamWriteU32(&s, 0); // unsigned int(32) minor_version; - avifStreamWriteChars(&s, "avif", 4); // unsigned int(32) compatible_brands[]; - avifStreamWriteChars(&s, "mif1", 4); // ... compatible_brands[] - avifStreamWriteChars(&s, "miaf", 4); // ... compatible_brands[] + avifBoxMarker ftyp = avifRWStreamWriteBox(&s, "ftyp", -1, 0); + avifRWStreamWriteChars(&s, "avif", 4); // unsigned int(32) major_brand; + avifRWStreamWriteU32(&s, 0); // unsigned int(32) minor_version; + avifRWStreamWriteChars(&s, "avif", 4); // unsigned int(32) compatible_brands[]; + avifRWStreamWriteChars(&s, "mif1", 4); // ... compatible_brands[] + avifRWStreamWriteChars(&s, "miaf", 4); // ... compatible_brands[] if ((image->depth == 8) || (image->depth == 10)) { // if (image->yuvFormat == AVIF_PIXEL_FORMAT_YUV420) { // - avifStreamWriteChars(&s, "MA1B", 4); // ... compatible_brands[] + avifRWStreamWriteChars(&s, "MA1B", 4); // ... compatible_brands[] } else if (image->yuvFormat == AVIF_PIXEL_FORMAT_YUV444) { // - avifStreamWriteChars(&s, "MA1A", 4); // ... compatible_brands[] + avifRWStreamWriteChars(&s, "MA1A", 4); // ... compatible_brands[] } } - avifStreamFinishBox(&s, ftyp); + avifRWStreamFinishBox(&s, ftyp); // ----------------------------------------------------------------------- // Start meta - avifBoxMarker meta = avifStreamWriteBox(&s, "meta", 0, 0); + avifBoxMarker meta = avifRWStreamWriteBox(&s, "meta", 0, 0); // ----------------------------------------------------------------------- // Write hdlr - avifBoxMarker hdlr = avifStreamWriteBox(&s, "hdlr", 0, 0); - avifStreamWriteU32(&s, 0); // unsigned int(32) pre_defined = 0; - avifStreamWriteChars(&s, "pict", 4); // unsigned int(32) handler_type; - avifStreamWriteZeros(&s, 12); // const unsigned int(32)[3] reserved = 0; - avifStreamWriteChars(&s, "libavif", 8); // string name; (writing null terminator) - avifStreamFinishBox(&s, hdlr); + avifBoxMarker hdlr = avifRWStreamWriteBox(&s, "hdlr", 0, 0); + avifRWStreamWriteU32(&s, 0); // unsigned int(32) pre_defined = 0; + avifRWStreamWriteChars(&s, "pict", 4); // unsigned int(32) handler_type; + avifRWStreamWriteZeros(&s, 12); // const unsigned int(32)[3] reserved = 0; + avifRWStreamWriteChars(&s, "libavif", 8); // string name; (writing null terminator) + avifRWStreamFinishBox(&s, hdlr); // ----------------------------------------------------------------------- // Write pitm - avifStreamWriteBox(&s, "pitm", 0, sizeof(uint16_t)); - avifStreamWriteU16(&s, 1); // unsigned int(16) item_ID; + avifRWStreamWriteBox(&s, "pitm", 0, sizeof(uint16_t)); + avifRWStreamWriteU16(&s, 1); // unsigned int(16) item_ID; // ----------------------------------------------------------------------- // Write iloc @@ -165,74 +165,74 @@ size_t colorOBUOffsetOffset = 0; size_t alphaOBUOffsetOffset = 0; - avifBoxMarker iloc = avifStreamWriteBox(&s, "iloc", 0, 0); + avifBoxMarker iloc = avifRWStreamWriteBox(&s, "iloc", 0, 0); // iloc header uint8_t offsetSizeAndLengthSize = (4 << 4) + (4 << 0); // unsigned int(4) offset_size; // unsigned int(4) length_size; - avifStreamWrite(&s, &offsetSizeAndLengthSize, 1); // - avifStreamWriteZeros(&s, 1); // unsigned int(4) base_offset_size; + avifRWStreamWrite(&s, &offsetSizeAndLengthSize, 1); // + avifRWStreamWriteZeros(&s, 1); // unsigned int(4) base_offset_size; // unsigned int(4) reserved; - avifStreamWriteU16(&s, hasAlpha ? 2 : 1); // unsigned int(16) item_count; + avifRWStreamWriteU16(&s, hasAlpha ? 2 : 1); // unsigned int(16) item_count; // Item ID #1 (Color OBU) - avifStreamWriteU16(&s, 1); // unsigned int(16) item_ID; - avifStreamWriteU16(&s, 0); // unsigned int(16) data_reference_index; - avifStreamWriteU16(&s, 1); // unsigned int(16) extent_count; - colorOBUOffsetOffset = avifStreamOffset(&s); // - avifStreamWriteU32(&s, 0 /* set later */); // unsigned int(offset_size*8) extent_offset; - avifStreamWriteU32(&s, (uint32_t)colorOBU.size); // unsigned int(length_size*8) extent_length; + avifRWStreamWriteU16(&s, 1); // unsigned int(16) item_ID; + avifRWStreamWriteU16(&s, 0); // unsigned int(16) data_reference_index; + avifRWStreamWriteU16(&s, 1); // unsigned int(16) extent_count; + colorOBUOffsetOffset = avifRWStreamOffset(&s); // + avifRWStreamWriteU32(&s, 0 /* set later */); // unsigned int(offset_size*8) extent_offset; + avifRWStreamWriteU32(&s, (uint32_t)colorOBU.size); // unsigned int(length_size*8) extent_length; if (hasAlpha) { - avifStreamWriteU16(&s, 2); // unsigned int(16) item_ID; - avifStreamWriteU16(&s, 0); // unsigned int(16) data_reference_index; - avifStreamWriteU16(&s, 1); // unsigned int(16) extent_count; - alphaOBUOffsetOffset = avifStreamOffset(&s); // - avifStreamWriteU32(&s, 0 /* set later */); // unsigned int(offset_size*8) extent_offset; - avifStreamWriteU32(&s, (uint32_t)alphaOBU.size); // unsigned int(length_size*8) extent_length; + avifRWStreamWriteU16(&s, 2); // unsigned int(16) item_ID; + avifRWStreamWriteU16(&s, 0); // unsigned int(16) data_reference_index; + avifRWStreamWriteU16(&s, 1); // unsigned int(16) extent_count; + alphaOBUOffsetOffset = avifRWStreamOffset(&s); // + avifRWStreamWriteU32(&s, 0 /* set later */); // unsigned int(offset_size*8) extent_offset; + avifRWStreamWriteU32(&s, (uint32_t)alphaOBU.size); // unsigned int(length_size*8) extent_length; } - avifStreamFinishBox(&s, iloc); + avifRWStreamFinishBox(&s, iloc); // ----------------------------------------------------------------------- // Write iinf - avifBoxMarker iinf = avifStreamWriteBox(&s, "iinf", 0, 0); - avifStreamWriteU16(&s, hasAlpha ? 2 : 1); // unsigned int(16) entry_count; + avifBoxMarker iinf = avifRWStreamWriteBox(&s, "iinf", 0, 0); + avifRWStreamWriteU16(&s, hasAlpha ? 2 : 1); // unsigned int(16) entry_count; - avifBoxMarker infe0 = avifStreamWriteBox(&s, "infe", 2, 0); - avifStreamWriteU16(&s, 1); // unsigned int(16) item_ID; - avifStreamWriteU16(&s, 0); // unsigned int(16) item_protection_index; - avifStreamWriteChars(&s, "av01", 4); // unsigned int(32) item_type; - avifStreamWriteChars(&s, "Color", 6); // string item_name; (writing null terminator) - avifStreamFinishBox(&s, infe0); + avifBoxMarker infe0 = avifRWStreamWriteBox(&s, "infe", 2, 0); + avifRWStreamWriteU16(&s, 1); // unsigned int(16) item_ID; + avifRWStreamWriteU16(&s, 0); // unsigned int(16) item_protection_index; + avifRWStreamWriteChars(&s, "av01", 4); // unsigned int(32) item_type; + avifRWStreamWriteChars(&s, "Color", 6); // string item_name; (writing null terminator) + avifRWStreamFinishBox(&s, infe0); if (hasAlpha) { - avifBoxMarker infe1 = avifStreamWriteBox(&s, "infe", 2, 0); - avifStreamWriteU16(&s, 2); // unsigned int(16) item_ID; - avifStreamWriteU16(&s, 0); // unsigned int(16) item_protection_index; - avifStreamWriteChars(&s, "av01", 4); // unsigned int(32) item_type; - avifStreamWriteChars(&s, "Alpha", 6); // string item_name; (writing null terminator) - avifStreamFinishBox(&s, infe1); + avifBoxMarker infe1 = avifRWStreamWriteBox(&s, "infe", 2, 0); + avifRWStreamWriteU16(&s, 2); // unsigned int(16) item_ID; + avifRWStreamWriteU16(&s, 0); // unsigned int(16) item_protection_index; + avifRWStreamWriteChars(&s, "av01", 4); // unsigned int(32) item_type; + avifRWStreamWriteChars(&s, "Alpha", 6); // string item_name; (writing null terminator) + avifRWStreamFinishBox(&s, infe1); } - avifStreamFinishBox(&s, iinf); + avifRWStreamFinishBox(&s, iinf); // ----------------------------------------------------------------------- // Write iref (auxl) for alpha, if any if (hasAlpha) { - avifBoxMarker iref = avifStreamWriteBox(&s, "iref", 0, 0); - avifBoxMarker auxl = avifStreamWriteBox(&s, "auxl", -1, 0); - avifStreamWriteU16(&s, 2); // unsigned int(16) from_item_ID; - avifStreamWriteU16(&s, 1); // unsigned int(16) reference_count; - avifStreamWriteU16(&s, 1); // unsigned int(16) to_item_ID; - avifStreamFinishBox(&s, auxl); - avifStreamFinishBox(&s, iref); + avifBoxMarker iref = avifRWStreamWriteBox(&s, "iref", 0, 0); + avifBoxMarker auxl = avifRWStreamWriteBox(&s, "auxl", -1, 0); + avifRWStreamWriteU16(&s, 2); // unsigned int(16) from_item_ID; + avifRWStreamWriteU16(&s, 1); // unsigned int(16) reference_count; + avifRWStreamWriteU16(&s, 1); // unsigned int(16) to_item_ID; + avifRWStreamFinishBox(&s, auxl); + avifRWStreamFinishBox(&s, iref); } // ----------------------------------------------------------------------- // Write iprp->ipco->ispe - avifBoxMarker iprp = avifStreamWriteBox(&s, "iprp", -1, 0); + avifBoxMarker iprp = avifRWStreamWriteBox(&s, "iprp", -1, 0); { uint8_t ipcoIndex = 0; struct ipmaArray ipmaColor; @@ -240,42 +240,42 @@ struct ipmaArray ipmaAlpha; memset(&ipmaAlpha, 0, sizeof(ipmaAlpha)); - avifBoxMarker ipco = avifStreamWriteBox(&s, "ipco", -1, 0); + avifBoxMarker ipco = avifRWStreamWriteBox(&s, "ipco", -1, 0); { - avifBoxMarker ispe = avifStreamWriteBox(&s, "ispe", 0, 0); - avifStreamWriteU32(&s, image->width); // unsigned int(32) image_width; - avifStreamWriteU32(&s, image->height); // unsigned int(32) image_height; - avifStreamFinishBox(&s, ispe); + avifBoxMarker ispe = avifRWStreamWriteBox(&s, "ispe", 0, 0); + avifRWStreamWriteU32(&s, image->width); // unsigned int(32) image_width; + avifRWStreamWriteU32(&s, image->height); // unsigned int(32) image_height; + avifRWStreamFinishBox(&s, ispe); ++ipcoIndex; ipmaPush(&ipmaColor, ipcoIndex); // ipma is 1-indexed, doing this afterwards is correct ipmaPush(&ipmaAlpha, ipcoIndex); // Alpha shares the ispe prop if (image->profileFormat == AVIF_PROFILE_FORMAT_NCLX) { - avifBoxMarker colr = avifStreamWriteBox(&s, "colr", -1, 0); - avifStreamWriteChars(&s, "nclx", 4); // unsigned int(32) colour_type; - avifStreamWriteU16(&s, image->nclx.colourPrimaries); // unsigned int(16) colour_primaries; - avifStreamWriteU16(&s, image->nclx.transferCharacteristics); // unsigned int(16) transfer_characteristics; - avifStreamWriteU16(&s, image->nclx.matrixCoefficients); // unsigned int(16) matrix_coefficients; - avifStreamWriteU8(&s, image->nclx.fullRangeFlag & 0x80); // unsigned int(1) full_range_flag; - // unsigned int(7) reserved = 0; - avifStreamFinishBox(&s, colr); + avifBoxMarker colr = avifRWStreamWriteBox(&s, "colr", -1, 0); + avifRWStreamWriteChars(&s, "nclx", 4); // unsigned int(32) colour_type; + avifRWStreamWriteU16(&s, image->nclx.colourPrimaries); // unsigned int(16) colour_primaries; + avifRWStreamWriteU16(&s, image->nclx.transferCharacteristics); // unsigned int(16) transfer_characteristics; + avifRWStreamWriteU16(&s, image->nclx.matrixCoefficients); // unsigned int(16) matrix_coefficients; + avifRWStreamWriteU8(&s, image->nclx.fullRangeFlag & 0x80); // unsigned int(1) full_range_flag; + // unsigned int(7) reserved = 0; + avifRWStreamFinishBox(&s, colr); ++ipcoIndex; ipmaPush(&ipmaColor, ipcoIndex); } else if ((image->profileFormat == AVIF_PROFILE_FORMAT_ICC) && image->icc.data && (image->icc.size > 0)) { - avifBoxMarker colr = avifStreamWriteBox(&s, "colr", -1, 0); - avifStreamWriteChars(&s, "prof", 4); // unsigned int(32) colour_type; - avifStreamWrite(&s, image->icc.data, image->icc.size); - avifStreamFinishBox(&s, colr); + avifBoxMarker colr = avifRWStreamWriteBox(&s, "colr", -1, 0); + avifRWStreamWriteChars(&s, "prof", 4); // unsigned int(32) colour_type; + avifRWStreamWrite(&s, image->icc.data, image->icc.size); + avifRWStreamFinishBox(&s, colr); ++ipcoIndex; ipmaPush(&ipmaColor, ipcoIndex); } - avifBoxMarker pixiC = avifStreamWriteBox(&s, "pixi", 0, 0); - avifStreamWriteU8(&s, 3); // unsigned int (8) num_channels; - avifStreamWriteU8(&s, (uint8_t)image->depth); // unsigned int (8) bits_per_channel; - avifStreamWriteU8(&s, (uint8_t)image->depth); // unsigned int (8) bits_per_channel; - avifStreamWriteU8(&s, (uint8_t)image->depth); // unsigned int (8) bits_per_channel; - avifStreamFinishBox(&s, pixiC); + avifBoxMarker pixiC = avifRWStreamWriteBox(&s, "pixi", 0, 0); + avifRWStreamWriteU8(&s, 3); // unsigned int (8) num_channels; + avifRWStreamWriteU8(&s, (uint8_t)image->depth); // unsigned int (8) bits_per_channel; + avifRWStreamWriteU8(&s, (uint8_t)image->depth); // unsigned int (8) bits_per_channel; + avifRWStreamWriteU8(&s, (uint8_t)image->depth); // unsigned int (8) bits_per_channel; + avifRWStreamFinishBox(&s, pixiC); ++ipcoIndex; ipmaPush(&ipmaColor, ipcoIndex); @@ -286,10 +286,10 @@ ipmaPush(&ipmaColor, ipcoIndex); if (hasAlpha) { - avifBoxMarker pixiA = avifStreamWriteBox(&s, "pixi", 0, 0); - avifStreamWriteU8(&s, 1); // unsigned int (8) num_channels; - avifStreamWriteU8(&s, (uint8_t)image->depth); // unsigned int (8) bits_per_channel; - avifStreamFinishBox(&s, pixiA); + avifBoxMarker pixiA = avifRWStreamWriteBox(&s, "pixi", 0, 0); + avifRWStreamWriteU8(&s, 1); // unsigned int (8) num_channels; + avifRWStreamWriteU8(&s, (uint8_t)image->depth); // unsigned int (8) bits_per_channel; + avifRWStreamFinishBox(&s, pixiA); ++ipcoIndex; ipmaPush(&ipmaAlpha, ipcoIndex); @@ -299,70 +299,70 @@ ++ipcoIndex; ipmaPush(&ipmaAlpha, ipcoIndex); - avifBoxMarker auxC = avifStreamWriteBox(&s, "auxC", 0, 0); - avifStreamWriteChars(&s, alphaURN, alphaURNSize); // string aux_type; - avifStreamFinishBox(&s, auxC); + avifBoxMarker auxC = avifRWStreamWriteBox(&s, "auxC", 0, 0); + avifRWStreamWriteChars(&s, alphaURN, alphaURNSize); // string aux_type; + avifRWStreamFinishBox(&s, auxC); ++ipcoIndex; ipmaPush(&ipmaAlpha, ipcoIndex); } } - avifStreamFinishBox(&s, ipco); + avifRWStreamFinishBox(&s, ipco); - avifBoxMarker ipma = avifStreamWriteBox(&s, "ipma", 0, 0); + avifBoxMarker ipma = avifRWStreamWriteBox(&s, "ipma", 0, 0); { int ipmaCount = hasAlpha ? 2 : 1; - avifStreamWriteU32(&s, ipmaCount); // unsigned int(32) entry_count; + avifRWStreamWriteU32(&s, ipmaCount); // unsigned int(32) entry_count; - avifStreamWriteU16(&s, 1); // unsigned int(16) item_ID; - avifStreamWriteU8(&s, ipmaColor.count); // unsigned int(8) association_count; - for (int i = 0; i < ipmaColor.count; ++i) { // - avifStreamWriteU8(&s, ipmaColor.associations[i]); // bit(1) essential; unsigned int(7) property_index; + avifRWStreamWriteU16(&s, 1); // unsigned int(16) item_ID; + avifRWStreamWriteU8(&s, ipmaColor.count); // unsigned int(8) association_count; + for (int i = 0; i < ipmaColor.count; ++i) { // + avifRWStreamWriteU8(&s, ipmaColor.associations[i]); // bit(1) essential; unsigned int(7) property_index; } if (hasAlpha) { - avifStreamWriteU16(&s, 2); // unsigned int(16) item_ID; - avifStreamWriteU8(&s, ipmaAlpha.count); // unsigned int(8) association_count; - for (int i = 0; i < ipmaAlpha.count; ++i) { // - avifStreamWriteU8(&s, ipmaAlpha.associations[i]); // bit(1) essential; unsigned int(7) property_index; + avifRWStreamWriteU16(&s, 2); // unsigned int(16) item_ID; + avifRWStreamWriteU8(&s, ipmaAlpha.count); // unsigned int(8) association_count; + for (int i = 0; i < ipmaAlpha.count; ++i) { // + avifRWStreamWriteU8(&s, ipmaAlpha.associations[i]); // bit(1) essential; unsigned int(7) property_index; } } } - avifStreamFinishBox(&s, ipma); + avifRWStreamFinishBox(&s, ipma); } - avifStreamFinishBox(&s, iprp); + avifRWStreamFinishBox(&s, iprp); // ----------------------------------------------------------------------- // Finish meta box - avifStreamFinishBox(&s, meta); + avifRWStreamFinishBox(&s, meta); // ----------------------------------------------------------------------- // Write mdat - avifBoxMarker mdat = avifStreamWriteBox(&s, "mdat", -1, 0); + avifBoxMarker mdat = avifRWStreamWriteBox(&s, "mdat", -1, 0); uint32_t colorOBUOffset = (uint32_t)s.offset; - avifStreamWrite(&s, colorOBU.data, colorOBU.size); + avifRWStreamWrite(&s, colorOBU.data, colorOBU.size); uint32_t alphaOBUOffset = (uint32_t)s.offset; - avifStreamWrite(&s, alphaOBU.data, alphaOBU.size); - avifStreamFinishBox(&s, mdat); + avifRWStreamWrite(&s, alphaOBU.data, alphaOBU.size); + avifRWStreamFinishBox(&s, mdat); // ----------------------------------------------------------------------- // Finish up stream // Set offsets needed in meta box based on where we eventually wrote mdat - size_t prevOffset = avifStreamOffset(&s); + size_t prevOffset = avifRWStreamOffset(&s); if (colorOBUOffsetOffset != 0) { - avifStreamSetOffset(&s, colorOBUOffsetOffset); - avifStreamWriteU32(&s, colorOBUOffset); + avifRWStreamSetOffset(&s, colorOBUOffsetOffset); + avifRWStreamWriteU32(&s, colorOBUOffset); } if (alphaOBUOffsetOffset != 0) { - avifStreamSetOffset(&s, alphaOBUOffsetOffset); - avifStreamWriteU32(&s, alphaOBUOffset); + avifRWStreamSetOffset(&s, alphaOBUOffsetOffset); + avifRWStreamWriteU32(&s, alphaOBUOffset); } - avifStreamSetOffset(&s, prevOffset); + avifRWStreamSetOffset(&s, prevOffset); // Close write stream - avifStreamFinishWrite(&s); + avifRWStreamFinishWrite(&s); // ----------------------------------------------------------------------- // IO stats @@ -382,8 +382,8 @@ if (codec[AVIF_CODEC_PLANES_ALPHA]) { avifCodecDestroy(codec[AVIF_CODEC_PLANES_ALPHA]); } - avifRawDataFree(&colorOBU); - avifRawDataFree(&alphaOBU); + avifRWDataFree(&colorOBU); + avifRWDataFree(&alphaOBU); return result; } @@ -415,17 +415,17 @@ return AVIF_TRUE; } -static void writeConfigBox(avifStream * s, avifCodecConfigurationBox * cfg) +static void writeConfigBox(avifRWStream * s, avifCodecConfigurationBox * cfg) { - avifBoxMarker av1C = avifStreamWriteBox(s, "av1C", -1, 0); + avifBoxMarker av1C = avifRWStreamWriteBox(s, "av1C", -1, 0); // unsigned int (1) marker = 1; // unsigned int (7) version = 1; - avifStreamWriteU8(s, 0x80 | 0x1); + avifRWStreamWriteU8(s, 0x80 | 0x1); // unsigned int (3) seq_profile; // unsigned int (5) seq_level_idx_0; - avifStreamWriteU8(s, (uint8_t)((cfg->seqProfile & 0x7) << 5) | (uint8_t)(cfg->seqLevelIdx0 & 0x1f)); + avifRWStreamWriteU8(s, (uint8_t)((cfg->seqProfile & 0x7) << 5) | (uint8_t)(cfg->seqLevelIdx0 & 0x1f)); uint8_t bits = 0; bits |= (cfg->seqTier0 & 0x1) << 7; // unsigned int (1) seq_tier_0; @@ -435,7 +435,7 @@ bits |= (cfg->chromaSubsamplingX & 0x1) << 3; // unsigned int (1) chroma_subsampling_x; bits |= (cfg->chromaSubsamplingY & 0x1) << 2; // unsigned int (1) chroma_subsampling_y; bits |= (cfg->chromaSamplePosition & 0x3); // unsigned int (2) chroma_sample_position; - avifStreamWriteU8(s, bits); + avifRWStreamWriteU8(s, bits); // unsigned int (3) reserved = 0; // unsigned int (1) initial_presentation_delay_present; @@ -444,7 +444,7 @@ // } else { // unsigned int (4) reserved = 0; // } - avifStreamWriteU8(s, 0); + avifRWStreamWriteU8(s, 0); - avifStreamFinishBox(s, av1C); + avifRWStreamFinishBox(s, av1C); }
diff --git a/tests/aviffuzz.c b/tests/aviffuzz.c index 88d633c..326e0db 100644 --- a/tests/aviffuzz.c +++ b/tests/aviffuzz.c
@@ -35,12 +35,12 @@ return 1; } - avifRawData raw = AVIF_RAW_DATA_EMPTY; - avifRawDataRealloc(&raw, inputFileSize); + avifRWData raw = AVIF_DATA_EMPTY; + avifRWDataRealloc(&raw, inputFileSize); if (fread(raw.data, 1, inputFileSize, inputFile) != inputFileSize) { fprintf(stderr, "Failed to read %zu bytes: %s\n", inputFileSize, inputFilename); fclose(inputFile); - avifRawDataFree(&raw); + avifRWDataFree(&raw); return 1; } @@ -49,7 +49,7 @@ avifDecoder * decoder = avifDecoderCreate(); // avifDecoderSetSource(decoder, AVIF_DECODER_SOURCE_PRIMARY_ITEM); - avifResult result = avifDecoderParse(decoder, &raw); + avifResult result = avifDecoderParse(decoder, (avifROData *)&raw); if (result == AVIF_RESULT_OK) { for (int loop = 0; loop < 2; ++loop) { printf("Image decoded: %s\n", inputFilename); @@ -79,7 +79,7 @@ printf("ERROR: Failed to decode image: %s\n", avifResultToString(result)); } - avifRawDataFree(&raw); + avifRWDataFree(&raw); avifDecoderDestroy(decoder); return 0; }