MCPcopy Create free account
hub / github.com/apple/foundationdb / decodeKVFragment

Function decodeKVFragment

fdbserver/KeyValueStoreSQLite.actor.cpp:591–638  ·  view source on GitHub ↗

Decode (key, index, value) tuple. A present() Optional will always be returned UNLESS partial is true. If partial is true then the return will not be present() unless at least the full key and index were in the encoded buffer. The value returned will be 0 or more value bytes, however many were available. Note that a short encoded buffer must at *least* contain the header length varint.

Source from the content-addressed store, hash-verified

589// more value bytes, however many were available.
590// Note that a short encoded buffer must at *least* contain the header length varint.
591Optional<KeyValueRef> decodeKVFragment(StringRef encoded, uint32_t* index = nullptr, bool partial = false) {
592 uint8_t const* d = encoded.begin();
593 uint64_t h, len1, len2;
594 d += sqlite3GetVarint(d, (u64*)&h);
595
596 // Make sure entire header is present, else return nothing
597 if (partial && encoded.size() < h)
598 return Optional<KeyValueRef>();
599
600 d += sqlite3GetVarint(d, (u64*)&len1);
601 const uint8_t indexLen = *d++;
602 ASSERT(indexLen <= 4);
603 d += sqlite3GetVarint(d, (u64*)&len2);
604 ASSERT(d == encoded.begin() + h);
605 ASSERT(len1 >= 12 && !(len1 & 1));
606 ASSERT(len2 >= 12 && !(len2 & 1));
607 len1 = (len1 - 12) / 2;
608 len2 = (len2 - 12) / 2;
609
610 if (partial) {
611 // If the key and index aren't complete, return nothing.
612 if (d + len1 + indexLen > encoded.end())
613 return Optional<KeyValueRef>();
614 // Encoded size shouldn't be *larger* than the record described by the header no matter what.
615 ASSERT(d + len1 + indexLen + len2 >= encoded.end());
616 // Shorten value length to be whatever bytes remain after the header/key/index
617 len2 = std::min(len2, (uint64_t)(encoded.end() - indexLen - len1 - d));
618 } else {
619 // But for non partial records encoded size should be exactly the size of the described record.
620 ASSERT(d + len1 + indexLen + len2 == encoded.end());
621 }
622
623 // Decode big endian index
624 if (index != nullptr) {
625 if (indexLen == 0)
626 *index = 0;
627 else {
628 const uint8_t* begin = d + len1;
629 const uint8_t* end = begin + indexLen;
630 *index = (uint8_t)*begin++;
631 while (begin < end) {
632 *index <<= 8;
633 *index |= *begin++;
634 }
635 }
636 }
637 return KeyValueRef(KeyRef(d, len1), KeyRef(d + len1 + indexLen, len2));
638}
639
640KeyValueRef decodeKVPrefix(StringRef encoded, int maxLength) {
641 uint8_t const* d = encoded.begin();

Callers 4

clearMethod · 0.85
fastClearMethod · 0.85
parseMethod · 0.85
getMethod · 0.85

Calls 5

KeyRefClass · 0.85
KeyValueRefClass · 0.50
beginMethod · 0.45
sizeMethod · 0.45
endMethod · 0.45

Tested by

no test coverage detected