// Copyright 2016 Google Inc. All Rights Reserved. #include "entry_writer.h" #include "log.h" namespace wvcdm { namespace oemprofiler { static const uint64_t MAX_VALUES_FOR_BYTES[8] = { 0x000000000000001F, 0x0000000000001FFF, 0x00000000001FFFFF, 0x000000001FFFFFFF, 0x0000001FFFFFFFFF, 0x00001FFFFFFFFFFF, 0x001FFFFFFFFFFFFF, 0x1FFFFFFFFFFFFFFF }; static const uint64_t CODE_FOR_BYTES[8] = { 0x0000000000000000, 0x0000000000002000, 0x0000000000400000, 0x0000000060000000, 0x0000008000000000, 0x0000A00000000000, 0x00C0000000000000, 0xE000000000000000 }; EntryWriter::EntryWriter() : write_head_(0){ } const uint8_t* EntryWriter::GetData() const { return bytes_; } size_t EntryWriter::GetSize() const { return write_head_; } int EntryWriter::WriteU8(uint8_t value) { return Write(value); } int EntryWriter::WriteU16(uint16_t value) { return Write(value); } int EntryWriter::WriteU32(uint32_t value) { return Write(value); } int EntryWriter::WriteU64(uint64_t value) { return Write(value); } int EntryWriter::WriteVLV(uint64_t value) { for (size_t i = 0; i < sizeof(uint64_t); i++) { if (value <= MAX_VALUES_FOR_BYTES[i]) { return Write(value | CODE_FOR_BYTES[i], i + 1); } } LOGE("writeVariableLengthValue - value too large for variable length value"); return -1; } int EntryWriter::Write(uint64_t v, size_t num_bytes) { if (num_bytes > sizeof(uint64_t)) { LOGE("read - cannot read %zu bytes when 8 bytes are the max", num_bytes); return -1; } if (GetFreeSpace() < num_bytes) { LOGE("write - cannot write %zu when there are only %zu bytes remaining", num_bytes, GetFreeSpace()); return -1; } for (int i = num_bytes; i > 0; i--) { bytes_[write_head_] = GetByte(v, i - 1); write_head_++; } return static_cast(num_bytes); } void EntryWriter::Clear() { write_head_ = 0; } size_t EntryWriter::GetFreeSpace() const { return kBufferSize - write_head_; } template int EntryWriter::Write(T v) { // start the values at index 1 so that the number of bytes // line up with the shift value static const size_t shifts[8] = { 0, 8, 16, 24, 32, 40, 48, 56 }; if (GetFreeSpace() < sizeof(T)) { LOGE("write - cannot write %zu when there are only %zu bytes remaining", sizeof(T), GetFreeSpace()); return -1; // there is not enough room } for (int i = sizeof(T) - 1; i >= 0; i--) { bytes_[write_head_] = (uint8_t)((v >> shifts[i]) & 0xFF); write_head_++; } return (int)sizeof(T); } uint8_t EntryWriter::GetByte(uint64_t value, size_t byte_index) { return static_cast(0xFF & (value >> (byte_index * 8))); } } // oem profiler } // wvcdm