// Copyright 2023 Google LLC // SPDX-License-Identifier: BSD-2-Clause #include #include #include #include #include "avif/internal.h" #include "aviftest_helpers.h" #include "gtest/gtest.h" namespace libavif { namespace { //------------------------------------------------------------------------------ TEST(StreamTest, Roundtrip) { // TODO(yguyon): Check return values once pull request #1498 is merged. // Write some fields. testutil::AvifRwData rw_data; avifRWStream rw_stream; avifRWStreamStart(&rw_stream, &rw_data); EXPECT_EQ(avifRWStreamOffset(&rw_stream), size_t{0}); const uint8_t rw_somedata[] = {3, 1, 4}; EXPECT_EQ(avifRWStreamWrite(&rw_stream, rw_somedata, sizeof(rw_somedata)), AVIF_RESULT_OK); const char rw_somechars[] = "somechars"; EXPECT_EQ( avifRWStreamWriteChars(&rw_stream, rw_somechars, sizeof(rw_somechars)), AVIF_RESULT_OK); const char rw_box_type[] = "type"; avifBoxMarker rw_box_marker; EXPECT_EQ(avifRWStreamWriteBox(&rw_stream, rw_box_type, /*contentSize=*/0, &rw_box_marker), AVIF_RESULT_OK); const uint8_t rw_someu8 = 0xAA; EXPECT_EQ(avifRWStreamWriteU8(&rw_stream, rw_someu8), AVIF_RESULT_OK); const int rw_full_box_version = 7; const uint32_t rw_full_box_flags = 0x555; avifBoxMarker rw_full_box_marker; EXPECT_EQ(avifRWStreamWriteFullBox(&rw_stream, rw_box_type, /*contentSize=*/0, rw_full_box_version, rw_full_box_flags, &rw_full_box_marker), AVIF_RESULT_OK); const uint16_t rw_someu16 = 0xAABB; EXPECT_EQ(avifRWStreamWriteU16(&rw_stream, rw_someu16), AVIF_RESULT_OK); avifRWStreamFinishBox(&rw_stream, rw_full_box_marker); avifRWStreamFinishBox(&rw_stream, rw_box_marker); const uint32_t rw_someu32 = 0xAABBCCDD; EXPECT_EQ(avifRWStreamWriteU32(&rw_stream, rw_someu32), AVIF_RESULT_OK); size_t offset = avifRWStreamOffset(&rw_stream); const uint32_t rw_somevarint_1byte = 240; EXPECT_EQ(avifRWStreamWriteVarInt(&rw_stream, rw_somevarint_1byte), AVIF_RESULT_OK); EXPECT_EQ(avifRWStreamOffset(&rw_stream), offset + 1); offset = avifRWStreamOffset(&rw_stream); const uint32_t rw_somevarint_2bytes = 241; EXPECT_EQ(avifRWStreamWriteVarInt(&rw_stream, rw_somevarint_2bytes), AVIF_RESULT_OK); EXPECT_EQ(avifRWStreamOffset(&rw_stream), offset + 2); const uint64_t rw_someu64 = 0xAABBCCDDEEFF0011; EXPECT_EQ(avifRWStreamWriteU64(&rw_stream, rw_someu64), AVIF_RESULT_OK); const size_t rw_somebitcount = 6; const uint32_t rw_somebits = (1 << rw_somebitcount) - 2; EXPECT_EQ(avifRWStreamWriteBits(&rw_stream, rw_somebits, rw_somebitcount), AVIF_RESULT_OK); const size_t rw_maxbitcount = sizeof(uint32_t) * 8; const uint32_t rw_maxbits = std::numeric_limits::max(); EXPECT_EQ(avifRWStreamWriteBits(&rw_stream, rw_maxbits, rw_maxbitcount), AVIF_RESULT_OK); offset = avifRWStreamOffset(&rw_stream); const uint32_t rw_somevarint_3bytes = 2288; EXPECT_EQ(avifRWStreamWriteVarInt(&rw_stream, rw_somevarint_3bytes), AVIF_RESULT_OK); const uint32_t rw_somevarint_4bytes = 67824; EXPECT_EQ(avifRWStreamWriteVarInt(&rw_stream, rw_somevarint_4bytes), AVIF_RESULT_OK); EXPECT_EQ(avifRWStreamOffset(&rw_stream), offset + 3 + 4); const uint32_t rw_somebit = 1; EXPECT_EQ(avifRWStreamWriteBits(&rw_stream, rw_somebit, /*bitCount=*/1), AVIF_RESULT_OK); // Pad till byte alignment. EXPECT_EQ(avifRWStreamWriteBits(&rw_stream, rw_somebit, /*bitCount=*/1), AVIF_RESULT_OK); offset = avifRWStreamOffset(&rw_stream); const uint32_t rw_somevarint_5bytes = std::numeric_limits::max(); EXPECT_EQ(avifRWStreamWriteVarInt(&rw_stream, rw_somevarint_5bytes), AVIF_RESULT_OK); EXPECT_EQ(avifRWStreamOffset(&rw_stream), offset + 5); const size_t num_zeros = 10000; EXPECT_EQ(avifRWStreamWriteZeros(&rw_stream, /*byteCount=*/num_zeros), AVIF_RESULT_OK); avifRWStreamFinishWrite(&rw_stream); // Read and compare the fields. avifDiagnostics diag; avifDiagnosticsClearError(&diag); avifROData ro_data = {rw_data.data, rw_data.size}; avifROStream ro_stream; avifROStreamStart(&ro_stream, &ro_data, &diag, "diagContext"); EXPECT_EQ(avifROStreamCurrent(&ro_stream), ro_data.data); EXPECT_EQ(avifROStreamOffset(&ro_stream), size_t{0}); EXPECT_TRUE(avifROStreamHasBytesLeft(&ro_stream, rw_data.size)); EXPECT_FALSE(avifROStreamHasBytesLeft(&ro_stream, rw_data.size + 1)); EXPECT_EQ(avifROStreamRemainingBytes(&ro_stream), rw_data.size); std::vector ro_somedata(sizeof(rw_somedata)); EXPECT_TRUE( avifROStreamRead(&ro_stream, ro_somedata.data(), ro_somedata.size())); EXPECT_TRUE(std::equal(rw_somedata, rw_somedata + sizeof(rw_somedata), ro_somedata.data())); std::vector ro_somechars(sizeof(rw_somechars)); EXPECT_TRUE(avifROStreamReadString(&ro_stream, ro_somechars.data(), ro_somechars.size())); EXPECT_TRUE(std::equal(rw_somechars, rw_somechars + sizeof(rw_somechars), ro_somechars.data())); avifBoxHeader ro_box_header; EXPECT_TRUE(avifROStreamReadBoxHeader(&ro_stream, &ro_box_header)); EXPECT_TRUE(std::equal(rw_box_type, rw_box_type + 4, ro_box_header.type)); uint8_t ro_someu8; EXPECT_TRUE(avifROStreamRead(&ro_stream, &ro_someu8, /*size=*/1)); EXPECT_EQ(rw_someu8, ro_someu8); avifBoxHeader ro_full_box_header; EXPECT_TRUE(avifROStreamReadBoxHeader(&ro_stream, &ro_full_box_header)); EXPECT_TRUE( std::equal(rw_box_type, rw_box_type + 4, ro_full_box_header.type)); uint8_t ro_full_box_version; uint32_t ro_full_box_flags; EXPECT_TRUE(avifROStreamReadVersionAndFlags(&ro_stream, &ro_full_box_version, &ro_full_box_flags)); EXPECT_EQ(rw_full_box_version, ro_full_box_version); EXPECT_EQ(rw_full_box_flags, ro_full_box_flags); uint16_t ro_someu16; EXPECT_TRUE(avifROStreamReadU16(&ro_stream, &ro_someu16)); EXPECT_EQ(rw_someu16, ro_someu16); uint32_t ro_someu32; EXPECT_TRUE(avifROStreamReadU32(&ro_stream, &ro_someu32)); EXPECT_EQ(rw_someu32, ro_someu32); uint32_t ro_somevarint_1byte; EXPECT_TRUE(avifROStreamReadVarInt(&ro_stream, &ro_somevarint_1byte)); EXPECT_EQ(rw_somevarint_1byte, ro_somevarint_1byte); uint32_t ro_somevarint_2bytes; EXPECT_TRUE(avifROStreamReadVarInt(&ro_stream, &ro_somevarint_2bytes)); EXPECT_EQ(rw_somevarint_2bytes, ro_somevarint_2bytes); uint64_t ro_someu64; EXPECT_TRUE(avifROStreamReadU64(&ro_stream, &ro_someu64)); EXPECT_EQ(rw_someu64, ro_someu64); uint32_t ro_somebits; EXPECT_TRUE(avifROStreamReadBits(&ro_stream, &ro_somebits, rw_somebitcount)); EXPECT_EQ(rw_somebits, ro_somebits); uint32_t ro_maxbits; EXPECT_TRUE(avifROStreamReadBits(&ro_stream, &ro_maxbits, rw_maxbitcount)); EXPECT_EQ(rw_maxbits, ro_maxbits); uint32_t ro_somevarint_3bytes; EXPECT_TRUE(avifROStreamReadVarInt(&ro_stream, &ro_somevarint_3bytes)); EXPECT_EQ(rw_somevarint_3bytes, ro_somevarint_3bytes); uint32_t ro_somevarint_4bytes; EXPECT_TRUE(avifROStreamReadVarInt(&ro_stream, &ro_somevarint_4bytes)); EXPECT_EQ(rw_somevarint_4bytes, ro_somevarint_4bytes); uint8_t ro_somebit; EXPECT_TRUE(avifROStreamReadBits8(&ro_stream, &ro_somebit, /*bitCount=*/1)); EXPECT_EQ(rw_somebit, ro_somebit); EXPECT_TRUE(avifROStreamReadBits8(&ro_stream, &ro_somebit, /*bitCount=*/1)); EXPECT_EQ(rw_somebit, ro_somebit); uint32_t ro_somevarint_5bytes; EXPECT_TRUE(avifROStreamReadVarInt(&ro_stream, &ro_somevarint_5bytes)); EXPECT_EQ(rw_somevarint_5bytes, ro_somevarint_5bytes); EXPECT_TRUE(avifROStreamSkip(&ro_stream, /*byteCount=*/num_zeros)); EXPECT_FALSE(avifROStreamSkip(&ro_stream, /*byteCount=*/1)); } //------------------------------------------------------------------------------ } // namespace } // namespace libavif