| 143 | } |
| 144 | |
| 145 | inline Status ParseKeyValueMap(const std::byte* data, uint64_t maxSize, KeyValueMap* output) { |
| 146 | uint32_t sizeInBytes = 0; |
| 147 | if (auto status = ParseUint32(data, maxSize, &sizeInBytes); !status.ok()) { |
| 148 | return status; |
| 149 | } |
| 150 | if (sizeInBytes > (maxSize - 4)) { |
| 151 | const auto msg = |
| 152 | StrCat("key-value map size ", sizeInBytes, " exceeds remaining bytes ", (maxSize - 4)); |
| 153 | return Status(StatusCode::InvalidRecord, msg); |
| 154 | } |
| 155 | |
| 156 | // Account for the byte size prefix in sizeInBytes to make the bounds checking |
| 157 | // below simpler |
| 158 | sizeInBytes += 4; |
| 159 | |
| 160 | output->clear(); |
| 161 | uint64_t pos = 4; |
| 162 | while (pos < sizeInBytes) { |
| 163 | std::string_view key; |
| 164 | if (auto status = ParseStringView(data + pos, sizeInBytes - pos, &key); !status.ok()) { |
| 165 | const auto msg = StrCat("cannot read key-value map key at pos ", pos, ": ", status.message); |
| 166 | return Status{StatusCode::InvalidRecord, msg}; |
| 167 | } |
| 168 | pos += 4 + key.size(); |
| 169 | std::string_view value; |
| 170 | if (auto status = ParseStringView(data + pos, sizeInBytes - pos, &value); !status.ok()) { |
| 171 | const auto msg = StrCat("cannot read key-value map value for key \"", key, "\" at pos ", pos, |
| 172 | ": ", status.message); |
| 173 | return Status{StatusCode::InvalidRecord, msg}; |
| 174 | } |
| 175 | pos += 4 + value.size(); |
| 176 | output->emplace(key, value); |
| 177 | } |
| 178 | return StatusCode::Success; |
| 179 | } |
| 180 | |
| 181 | inline std::string MagicToHex(const std::byte* data) { |
| 182 | return internal::ToHex(data[0]) + internal::ToHex(data[1]) + internal::ToHex(data[2]) + |
nothing calls this directly
no test coverage detected