17 #ifndef FLATBUFFERS_H_ 18 #define FLATBUFFERS_H_ 23 #ifndef FLATBUFFERS_CPP98_STL 24 # include <functional> 27 #if defined(FLATBUFFERS_NAN_DEFAULTS) 35 template<
typename T>
inline bool IsTheSameAs(T e, T def) {
return e == def; }
37 #if defined(FLATBUFFERS_NAN_DEFAULTS) && \ 38 defined(FLATBUFFERS_HAS_NEW_STRTOD) && (FLATBUFFERS_HAS_NEW_STRTOD > 0) 40 template<
typename T>
inline bool IsFloatTheSameAs(T e, T def) {
41 return (e == def) || ((def != def) && (e != e));
43 template<>
inline bool IsTheSameAs<float>(
float e,
float def) {
44 return IsFloatTheSameAs(e, def);
46 template<>
inline bool IsTheSameAs<double>(
double e,
double def) {
47 return IsFloatTheSameAs(e, def);
55 inline bool IsOutRange(
const T &v,
const T &low,
const T &high) {
56 return (v < low) || (high < v);
61 inline bool IsInRange(
const T &v,
const T &low,
const T &high) {
79 FLATBUFFERS_LITTLEENDIAN);
83 template<
typename T> FLATBUFFERS_CONSTEXPR
size_t AlignOf() {
89 return __alignof__(T);
108 static const size_t element_stride =
sizeof(T);
109 static return_type
Read(
const uint8_t *p, uoffset_t i) {
110 return EndianScalar((reinterpret_cast<const T *>(p))[i]);
116 static const size_t element_stride =
sizeof(uoffset_t);
117 static return_type
Read(
const uint8_t *p, uoffset_t i) {
118 p += i *
sizeof(uoffset_t);
119 return reinterpret_cast<return_type
>(p + ReadScalar<uoffset_t>(p));
125 static const size_t element_stride =
sizeof(T);
126 static return_type
Read(
const uint8_t *p, uoffset_t i) {
127 return reinterpret_cast<const T *
>(p + i *
sizeof(T));
151 #if !defined(FLATBUFFERS_CPP98_STL) 156 #endif // !defined(FLATBUFFERS_CPP98_STL) 160 return data_ == other.
data_;
164 return data_ < other.
data_;
168 return data_ != other.
data_;
225 template<
typename Iterator>
228 :
std::reverse_iterator<Iterator>(iter) {}
231 return *(std::reverse_iterator<Iterator>::current);
235 return *(std::reverse_iterator<Iterator>::current);
252 uoffset_t
size()
const {
return EndianScalar(length_); }
256 uoffset_t Length()
const {
return size(); }
262 return_type
Get(uoffset_t i)
const {
272 template<
typename E> E
GetEnum(uoffset_t i)
const {
273 return static_cast<E
>(Get(i));
278 template<
typename U>
const U *
GetAs(uoffset_t i)
const {
279 return reinterpret_cast<const U *
>(Get(i));
285 return reinterpret_cast<const String *
>(Get(i));
289 return reinterpret_cast<const void *
>(Data() +
o);
298 reverse_iterator
rbegin() {
return reverse_iterator(end() - 1); }
300 return const_reverse_iterator(end() - 1);
303 reverse_iterator
rend() {
return reverse_iterator(begin() - 1); }
304 const_reverse_iterator
rend()
const {
305 return const_reverse_iterator(begin() - 1);
312 const_reverse_iterator
crbegin()
const {
return rbegin(); }
314 const_reverse_iterator
crend()
const {
return rend(); }
320 WriteScalar(
data() + i, val);
328 static_assert(
sizeof(T) ==
sizeof(uoffset_t),
"Unrelated types");
329 WriteScalar(
data() + i,
330 static_cast<uoffset_t>(val - (Data() + i *
sizeof(uoffset_t))));
341 return reinterpret_cast<const uint8_t *
>(&length_ + 1);
344 uint8_t *
Data() {
return reinterpret_cast<uint8_t *
>(&length_ + 1); }
347 const T *
data()
const {
return reinterpret_cast<const T *
>(Data()); }
348 T *
data() {
return reinterpret_cast<T *
>(Data()); }
351 void *search_result = std::bsearch(
354 if (!search_result) {
358 const uint8_t *element =
reinterpret_cast<const uint8_t *
>(search_result);
376 template<
typename K>
static int KeyCompare(
const void *ap,
const void *bp) {
377 const K *key =
reinterpret_cast<const K *
>(ap);
378 const uint8_t *
data =
reinterpret_cast<const uint8_t *
>(bp);
383 return -table->KeyCompareWithValue(*key);
391 uoffset_t
size()
const {
return EndianScalar(length_); }
394 return reinterpret_cast<const uint8_t *
>(&length_ + 1);
396 uint8_t *
Data() {
return reinterpret_cast<uint8_t *
>(&length_ + 1); }
408 #ifndef FLATBUFFERS_CPP98_STL 409 template<
typename T,
typename U>
411 static_assert(std::is_base_of<T, U>::value,
"Unrelated types");
415 template<
typename T,
typename U>
417 static_assert(std::is_base_of<T, U>::value,
"Unrelated types");
425 return v ? v->
size() : 0;
429 template<
typename T, u
int16_t length>
class Array {
444 FLATBUFFERS_CONSTEXPR uint16_t
size()
const {
return length; }
446 return_type
Get(uoffset_t i)
const {
456 template<
typename E> E
GetEnum(uoffset_t i)
const {
457 return static_cast<E
>(Get(i));
460 const_iterator
begin()
const {
return const_iterator(Data(), 0); }
461 const_iterator
end()
const {
return const_iterator(Data(), size()); }
464 return const_reverse_iterator(end());
466 const_reverse_iterator
rend()
const {
return const_reverse_iterator(end()); }
468 const_iterator
cbegin()
const {
return begin(); }
469 const_iterator
cend()
const {
return end(); }
471 const_reverse_iterator
crbegin()
const {
return rbegin(); }
472 const_reverse_iterator
crend()
const {
return rend(); }
482 return const_cast<T *
>(&
data()[i]);
489 const uint8_t *
Data()
const {
return data_; }
491 uint8_t *
Data() {
return data_; }
494 const T *
data()
const {
return reinterpret_cast<const T *
>(Data()); }
495 T *
data() {
return reinterpret_cast<T *
>(Data()); }
500 const auto p1 =
reinterpret_cast<const uint8_t *
>(src.data());
501 const auto p2 = Data();
503 !(p2 >= p1 && p2 < (p1 + length)));
509 !scalar_tag::value ||
sizeof(T) == 1 || FLATBUFFERS_LITTLEENDIAN > (),
517 WriteScalar(
data() + i, val);
522 *(GetMutablePointer(i)) = val;
526 flatbuffers::span<const T, length> src) {
530 std::memcpy(
data(), src.data(), length *
sizeof(T));
535 flatbuffers::span<const T, length> src) {
536 for (size_type k = 0; k < length; k++) { Mutate(k, src[k]); }
544 #if defined(__cpp_constexpr) 550 uint8_t data_[length *
sizeof(T)];
555 Array(
const Array &);
556 Array &operator=(
const Array &);
561 template<
typename T, u
int16_t length>
class Array<
Offset<T>, length> {
567 const uint8_t *
Data()
const {
return data_; }
586 template<
typename T, u
int16_t length>
591 template<
typename T, u
int16_t length>
596 template<
typename E,
typename T, u
int16_t length>
598 static_assert(
sizeof(E) ==
sizeof(T),
"invalid enum type E");
602 template<
typename E,
typename T, u
int16_t length>
604 static_assert(
sizeof(E) ==
sizeof(T),
"invalid enum type E");
611 const char *b_data, uoffset_t b_size) {
612 const auto cmp = memcmp(a_data, b_data, (std::min)(a_size, b_size));
613 return cmp == 0 ? a_size < b_size : cmp < 0;
617 const char *
c_str()
const {
return reinterpret_cast<const char *
>(Data()); }
618 std::string
str()
const {
return std::string(c_str(), size()); }
621 #ifdef FLATBUFFERS_HAS_STRING_VIEW 622 flatbuffers::string_view string_view()
const {
623 return flatbuffers::string_view(c_str(), size());
625 #endif // FLATBUFFERS_HAS_STRING_VIEW 636 return str ? str->
str() :
"";
642 return str ? str->
c_str() :
"";
645 #ifdef FLATBUFFERS_HAS_STRING_VIEW 648 static inline flatbuffers::string_view GetStringView(
const String *str) {
649 return str ? str->string_view() : flatbuffers::string_view();
651 #endif // FLATBUFFERS_HAS_STRING_VIEW 660 virtual uint8_t *allocate(
size_t size) = 0;
663 virtual void deallocate(uint8_t *p,
size_t size) = 0;
671 size_t new_size,
size_t in_use_back,
672 size_t in_use_front) {
674 uint8_t *new_p = allocate(new_size);
675 memcpy_downward(old_p, old_size, new_p, new_size, in_use_back,
677 deallocate(old_p, old_size);
687 size_t new_size,
size_t in_use_back,
688 size_t in_use_front) {
689 memcpy(new_p + new_size - in_use_back, old_p + old_size - in_use_back,
691 memcpy(new_p, old_p, in_use_front);
698 uint8_t *
allocate(
size_t size) FLATBUFFERS_OVERRIDE {
699 return new uint8_t[size];
702 void deallocate(uint8_t *p,
size_t) FLATBUFFERS_OVERRIDE {
delete[] p; }
704 static void dealloc(
void *p,
size_t) {
delete[]
static_cast<uint8_t *
>(p); }
712 return allocator ? allocator->
allocate(size)
724 size_t old_size,
size_t new_size,
725 size_t in_use_back,
size_t in_use_front) {
727 in_use_back, in_use_front)
729 old_p, old_size, new_size, in_use_back, in_use_front);
738 : allocator_(nullptr),
739 own_allocator_(false),
746 size_t reserved, uint8_t *cur,
size_t sz)
747 : allocator_(allocator),
748 own_allocator_(own_allocator),
755 #if !defined(FLATBUFFERS_CPP98_STL) 758 : allocator_(other.allocator_),
759 own_allocator_(other.own_allocator_),
761 reserved_(other.reserved_),
767 #endif // !defined(FLATBUFFERS_CPP98_STL) 771 #if !defined(FLATBUFFERS_CPP98_STL) 774 if (
this == &other)
return *
this;
778 allocator_ = other.allocator_;
779 own_allocator_ = other.own_allocator_;
781 reserved_ = other.reserved_;
790 #endif // !defined(FLATBUFFERS_CPP98_STL) 795 const uint8_t *
data()
const {
return cur_; }
797 uint8_t *
data() {
return cur_; }
799 size_t size()
const {
return size_; }
802 #if 0 // disabled for now due to the ordering of classes in this header 804 bool Verify()
const {
805 Verifier verifier(
data(), size());
806 return verifier.Verify<T>(
nullptr);
810 const T* GetRoot()
const {
811 return flatbuffers::GetRoot<T>(
data());
816 return flatbuffers::GetRoot<T>(
data());
822 #if !defined(FLATBUFFERS_CPP98_STL) 826 FLATBUFFERS_DELETE_FUNC(
829 #endif // !defined(FLATBUFFERS_CPP98_STL) 841 if (buf_)
Deallocate(allocator_, buf_, reserved_);
842 if (own_allocator_ && allocator_) {
delete allocator_; }
847 allocator_ =
nullptr;
848 own_allocator_ =
false;
865 bool own_allocator,
size_t buffer_minalign)
866 : allocator_(allocator),
867 own_allocator_(own_allocator),
868 initial_size_(initial_size),
869 buffer_minalign_(buffer_minalign),
876 #if !defined(FLATBUFFERS_CPP98_STL) 880 #endif // defined(FLATBUFFERS_CPP98_STL) 895 other.
buf_ =
nullptr;
896 other.
cur_ =
nullptr;
901 #if !defined(FLATBUFFERS_CPP98_STL) 910 #endif // defined(FLATBUFFERS_CPP98_STL) 925 cur_ = buf_ + reserved_;
936 if (own_allocator_ && allocator_) {
delete allocator_; }
937 allocator_ =
nullptr;
938 own_allocator_ =
false;
942 if (buf_)
Deallocate(allocator_, buf_, reserved_);
949 allocated_bytes = reserved_;
950 offset =
static_cast<size_t>(cur_ - buf_);
962 DetachedBuffer fb(allocator_, own_allocator_, buf_, reserved_, cur_,
964 if (own_allocator_) {
965 allocator_ =
nullptr;
966 own_allocator_ =
false;
975 if (len > static_cast<size_t>(cur_ - scratch_)) { reallocate(len); }
983 size_t space = ensure_space(len);
992 return static_cast<uoffset_t
>(reserved_ -
static_cast<size_t>(cur_ - buf_));
996 return static_cast<uoffset_t
>(scratch_ - buf_);
1016 uint8_t *
data_at(
size_t offset)
const {
return buf_ + reserved_ - offset; }
1018 void push(
const uint8_t *bytes,
size_t num) {
1019 if (num > 0) { memcpy(make_space(num), bytes, num); }
1024 make_space(
sizeof(T));
1025 *
reinterpret_cast<T *
>(cur_) = little_endian_t;
1029 ensure_space(
sizeof(T));
1030 *
reinterpret_cast<T *
>(scratch_) = t;
1031 scratch_ +=
sizeof(T);
1037 make_space(zero_pad_bytes);
1038 for (
size_t i = 0; i < zero_pad_bytes; i++) cur_[i] = 0;
1044 memset(make_space(zero_pad_bytes), 0, zero_pad_bytes);
1047 void pop(
size_t bytes_to_remove) { cur_ += bytes_to_remove; }
1048 void scratch_pop(
size_t bytes_to_remove) { scratch_ -= bytes_to_remove; }
1083 auto old_reserved = reserved_;
1084 auto old_size = size();
1085 auto old_scratch_size = scratch_size();
1087 (std::max)(len, old_reserved ? old_reserved / 2 : initial_size_);
1088 reserved_ = (reserved_ + buffer_minalign_ - 1) & ~(buffer_minalign_ - 1);
1091 old_size, old_scratch_size);
1093 buf_ =
Allocate(allocator_, reserved_);
1095 cur_ = buf_ + reserved_ - old_size;
1096 scratch_ = buf_ + old_scratch_size;
1103 const int fixed_fields = 2;
1104 return static_cast<voffset_t
>((field_id + fixed_fields) *
sizeof(voffset_t));
1107 template<
typename T,
typename Alloc>
1108 const T *
data(
const std::vector<T, Alloc> &v) {
1112 return v.empty() ?
reinterpret_cast<const T *
>(&t) : &v.front();
1114 template<
typename T,
typename Alloc> T *
data(std::vector<T, Alloc> &v) {
1118 return v.empty() ?
reinterpret_cast<T *
>(&t) : &v.front();
1146 size_t initial_size = 1024,
Allocator *allocator =
nullptr,
1147 bool own_allocator =
false,
1148 size_t buffer_minalign = AlignOf<largest_scalar_t>())
1149 : buf_(initial_size, allocator, own_allocator, buffer_minalign),
1155 force_defaults_(false),
1156 dedup_vtables_(true),
1157 string_pool(nullptr) {
1163 #if !defined(FLATBUFFERS_CPP98_STL) 1167 #endif // #if !defined(FLATBUFFERS_CPP98_STL) 1168 : buf_(1024,
nullptr,
false, AlignOf<largest_scalar_t>()),
1174 force_defaults_(
false),
1175 dedup_vtables_(
true),
1176 string_pool(
nullptr) {
1185 #if !defined(FLATBUFFERS_CPP98_STL) 1195 #endif // defined(FLATBUFFERS_CPP98_STL) 1200 buf_.swap(other.
buf_);
1212 if (string_pool)
delete string_pool;
1228 if (string_pool) string_pool->clear();
1248 return flatbuffers::span<uint8_t>(buf_.data(), buf_.size());
1262 return buf_.release();
1269 return buf_.release();
1283 return buf_.release_raw(size, offset);
1297 void Finished()
const {
1319 void Pad(
size_t num_bytes) { buf_.fill(num_bytes); }
1321 void TrackMinAlign(
size_t elem_size) {
1322 if (elem_size > minalign_) minalign_ = elem_size;
1325 void Align(
size_t elem_size) {
1326 TrackMinAlign(elem_size);
1327 buf_.fill(PaddingBytes(buf_.size(), elem_size));
1330 void PushFlatBuffer(
const uint8_t *bytes,
size_t size) {
1331 PushBytes(bytes, size);
1335 void PushBytes(
const uint8_t *bytes,
size_t size) { buf_.push(bytes, size); }
1337 void PopBytes(
size_t amount) { buf_.pop(amount); }
1339 template<
typename T>
void AssertScalarT() {
1345 template<
typename T> uoffset_t PushElement(T element) {
1347 T litle_endian_element = EndianScalar(element);
1349 buf_.push_small(litle_endian_element);
1353 template<
typename T> uoffset_t PushElement(
Offset<T> off) {
1355 return PushElement(ReferTo(off.
o));
1360 void TrackField(voffset_t field, uoffset_t off) {
1362 buf_.scratch_push_small(fl);
1364 max_voffset_ = (std::max)(max_voffset_, field);
1368 template<
typename T>
void AddElement(voffset_t field, T e, T def) {
1370 if (
IsTheSameAs(e, def) && !force_defaults_)
return;
1371 auto off = PushElement(e);
1372 TrackField(field, off);
1375 template<
typename T>
void AddElement(voffset_t field, T e) {
1376 auto off = PushElement(e);
1377 TrackField(field, off);
1380 template<
typename T>
void AddOffset(voffset_t field,
Offset<T> off) {
1381 if (off.
IsNull())
return;
1382 AddElement(field, ReferTo(off.
o), static_cast<uoffset_t>(0));
1385 template<
typename T>
void AddStruct(voffset_t field,
const T *structptr) {
1386 if (!structptr)
return;
1387 Align(AlignOf<T>());
1388 buf_.push_small(*structptr);
1389 TrackField(field, GetSize());
1392 void AddStructOffset(voffset_t field, uoffset_t off) {
1393 TrackField(field, off);
1399 uoffset_t ReferTo(uoffset_t off) {
1401 Align(
sizeof(uoffset_t));
1404 return GetSize() - off +
static_cast<uoffset_t
>(
sizeof(uoffset_t));
1423 uoffset_t StartTable() {
1432 uoffset_t EndTable(uoffset_t start) {
1437 auto vtableoffsetloc = PushElement<soffset_t>(0);
1444 (std::max)(static_cast<voffset_t>(max_voffset_ +
sizeof(voffset_t)),
1446 buf_.fill_big(max_voffset_);
1447 auto table_object_size = vtableoffsetloc - start;
1450 WriteScalar<voffset_t>(buf_.data() +
sizeof(voffset_t),
1451 static_cast<voffset_t>(table_object_size));
1452 WriteScalar<voffset_t>(buf_.data(), max_voffset_);
1454 for (
auto it = buf_.scratch_end() - num_field_loc *
sizeof(
FieldLoc);
1455 it < buf_.scratch_end(); it +=
sizeof(
FieldLoc)) {
1456 auto field_location =
reinterpret_cast<FieldLoc *
>(it);
1457 auto pos =
static_cast<voffset_t
>(vtableoffsetloc - field_location->off);
1460 !ReadScalar<voffset_t>(buf_.data() + field_location->id));
1461 WriteScalar<voffset_t>(buf_.data() + field_location->id, pos);
1464 auto vt1 =
reinterpret_cast<voffset_t *
>(buf_.data());
1465 auto vt1_size = ReadScalar<voffset_t>(vt1);
1466 auto vt_use = GetSize();
1469 if (dedup_vtables_) {
1470 for (
auto it = buf_.scratch_data(); it < buf_.scratch_end();
1471 it +=
sizeof(uoffset_t)) {
1472 auto vt_offset_ptr =
reinterpret_cast<uoffset_t *
>(it);
1473 auto vt2 =
reinterpret_cast<voffset_t *
>(buf_.data_at(*vt_offset_ptr));
1474 auto vt2_size = ReadScalar<voffset_t>(vt2);
1475 if (vt1_size != vt2_size || 0 != memcmp(vt2, vt1, vt1_size))
continue;
1476 vt_use = *vt_offset_ptr;
1477 buf_.pop(GetSize() - vtableoffsetloc);
1482 if (vt_use == GetSize()) { buf_.scratch_push_small(vt_use); }
1488 WriteScalar(buf_.data_at(vtableoffsetloc),
1489 static_cast<soffset_t
>(vt_use) -
1490 static_cast<soffset_t>(vtableoffsetloc));
1493 return vtableoffsetloc;
1496 FLATBUFFERS_ATTRIBUTE(deprecated(
"call the version above instead"))
1497 uoffset_t EndTable(uoffset_t start, voffset_t ) {
1498 return EndTable(start);
1503 template<
typename T>
void Required(
Offset<T> table, voffset_t field);
1505 uoffset_t StartStruct(
size_t alignment) {
1510 uoffset_t EndStruct() {
return GetSize(); }
1512 void ClearOffsets() {
1513 buf_.scratch_pop(num_field_loc *
sizeof(
FieldLoc));
1520 void PreAlign(
size_t len,
size_t alignment) {
1521 TrackMinAlign(alignment);
1522 buf_.fill(PaddingBytes(GetSize() + len, alignment));
1524 template<
typename T>
void PreAlign(
size_t len) {
1526 PreAlign(len,
sizeof(T));
1536 PreAlign<uoffset_t>(len + 1);
1538 PushBytes(reinterpret_cast<const uint8_t *>(str), len);
1539 PushElement(static_cast<uoffset_t>(len));
1547 return CreateString(str, strlen(str));
1554 return CreateString(str, strlen(str));
1561 return CreateString(str.c_str(), str.length());
1565 #ifdef FLATBUFFERS_HAS_STRING_VIEW 1570 return CreateString(str.data(), str.size());
1572 #endif // FLATBUFFERS_HAS_STRING_VIEW 1579 return str ? CreateString(str->
c_str(), str->
size()) : 0;
1587 return CreateString(str.c_str(), str.length());
1599 auto size_before_string = buf_.size();
1602 auto off = CreateString(str, len);
1603 auto it = string_pool->find(off);
1605 if (it != string_pool->end()) {
1607 buf_.pop(buf_.size() - size_before_string);
1611 string_pool->insert(off);
1615 #ifdef FLATBUFFERS_HAS_STRING_VIEW 1616 Offset<String> CreateSharedString(
const flatbuffers::string_view str) {
1622 return CreateSharedString(str.data(), str.size());
1631 return CreateSharedString(str, strlen(str));
1640 return CreateSharedString(str.c_str(), str.length());
1650 return CreateSharedString(str->
c_str(), str->
size());
1654 uoffset_t EndVector(
size_t len) {
1657 return PushElement(static_cast<uoffset_t>(len));
1660 void StartVector(
size_t len,
size_t elemsize) {
1663 PreAlign<uoffset_t>(len * elemsize);
1664 PreAlign(len * elemsize, elemsize);
1672 void ForceVectorAlignment(
size_t len,
size_t elemsize,
size_t alignment) {
1674 PreAlign(len * elemsize, alignment);
1678 void ForceStringAlignment(
size_t len,
size_t alignment) {
1680 PreAlign((len + 1) *
sizeof(
char), alignment);
1696 StartVector(len,
sizeof(T));
1699 #if FLATBUFFERS_LITTLEENDIAN 1700 PushBytes(reinterpret_cast<const uint8_t *>(v), len *
sizeof(T));
1702 if (
sizeof(T) == 1) {
1703 PushBytes(reinterpret_cast<const uint8_t *>(v), len);
1705 for (
auto i = len; i > 0; ) {
1706 PushElement(v[--i]);
1714 template<
typename T>
1717 for (
auto i = len; i > 0;) { PushElement(v[--i]); }
1728 return CreateVector(
data(v), v.size());
1735 StartVector(v.size(),
sizeof(uint8_t));
1736 for (
auto i = v.size(); i > 0;) {
1737 PushElement(static_cast<uint8_t>(v[--i]));
1743 #ifndef FLATBUFFERS_CPP98_STL 1752 const std::function<T (
size_t i)> &f) {
1753 std::vector<T> elems(vector_size);
1754 for (
size_t i = 0; i < vector_size; i++) elems[i] = f(i);
1755 return CreateVector(elems);
1769 template<
typename T,
typename F,
typename S>
1771 std::vector<T> elems(vector_size);
1772 for (
size_t i = 0; i < vector_size; i++) elems[i] = f(i, state);
1773 return CreateVector(elems);
1783 const std::vector<std::string> &v) {
1784 std::vector<Offset<String>> offsets(v.size());
1785 for (
size_t i = 0; i < v.size(); i++) offsets[i] = CreateString(v[i]);
1786 return CreateVector(offsets);
1796 template<
typename T>
1798 StartVector(len *
sizeof(T) / AlignOf<T>(), AlignOf<T>());
1799 PushBytes(reinterpret_cast<const uint8_t *>(v),
sizeof(T) * len);
1813 template<
typename T,
typename S>
1815 const S *v,
size_t len, T((*
const pack_func)(
const S &))) {
1817 std::vector<T> vv(len);
1818 std::transform(v, v + len, vv.begin(), pack_func);
1819 return CreateVectorOfStructs<T>(
data(vv), vv.size());
1830 template<
typename T,
typename S>
1833 extern T Pack(
const S &);
1834 return CreateVectorOfNativeStructs(v, len, Pack);
1838 #ifndef FLATBUFFERS_CPP98_STL 1848 size_t vector_size,
const std::function<
void(
size_t i, T *)> &filler) {
1849 T* structs = StartVectorOfStructs<T>(vector_size);
1850 for (
size_t i = 0; i < vector_size; i++) {
1854 return EndVectorOfStructs<T>(vector_size);
1868 template<
typename T,
typename F,
typename S>
1871 T *structs = StartVectorOfStructs<T>(vector_size);
1872 for (
size_t i = 0; i < vector_size; i++) {
1873 f(i, structs, state);
1876 return EndVectorOfStructs<T>(vector_size);
1885 template<
typename T,
typename Alloc>
1887 const std::vector<T, Alloc> &v) {
1888 return CreateVectorOfStructs(
data(v), v.size());
1901 template<
typename T,
typename S>
1903 const std::vector<S> &v, T((*
const pack_func)(
const S &))) {
1904 return CreateVectorOfNativeStructs<T, S>(
data(v), v.size(), pack_func);
1915 template<
typename T,
typename S>
1917 const std::vector<S> &v) {
1918 return CreateVectorOfNativeStructs<T, S>(
data(v), v.size());
1922 template<
typename T>
struct StructKeyComparator {
1923 bool operator()(
const T &a,
const T &b)
const {
1924 return a.KeyCompareLessThan(&b);
1927 FLATBUFFERS_DELETE_FUNC(
1928 StructKeyComparator &
operator=(
const StructKeyComparator &));
1939 template<
typename T>
1941 return CreateVectorOfSortedStructs(
data(*v), v->size());
1952 template<
typename T,
typename S>
1954 std::vector<S> *v) {
1955 return CreateVectorOfSortedNativeStructs<T, S>(
data(*v), v->size());
1966 template<
typename T>
1968 std::sort(v, v + len, StructKeyComparator<T>());
1969 return CreateVectorOfStructs(v, len);
1981 template<
typename T,
typename S>
1984 extern T Pack(
const S &);
1985 typedef T (*Pack_t)(
const S &);
1986 std::vector<T> vv(len);
1987 std::transform(v, v + len, vv.begin(),
static_cast<Pack_t &
>(Pack));
1988 return CreateVectorOfSortedStructs<T>(vv, len);
1992 template<
typename T>
struct TableKeyComparator {
1994 TableKeyComparator(
const TableKeyComparator &other) : buf_(other.buf_) {}
1996 auto table_a =
reinterpret_cast<T *
>(buf_.data_at(a.
o));
1997 auto table_b =
reinterpret_cast<T *
>(buf_.data_at(b.
o));
1998 return table_a->KeyCompareLessThan(table_b);
2003 FLATBUFFERS_DELETE_FUNC(
2004 TableKeyComparator &
operator=(
const TableKeyComparator &other));
2016 template<
typename T>
2019 std::sort(v, v + len, TableKeyComparator<T>(buf_));
2020 return CreateVector(v, len);
2030 template<
typename T>
2033 return CreateVectorOfSortedTables(
data(*v), v->size());
2046 StartVector(len, elemsize);
2047 buf_.make_space(len * elemsize);
2048 auto vec_start = GetSize();
2049 auto vec_end = EndVector(len);
2050 *buf = buf_.data_at(vec_start);
2062 template<
typename T>
2065 return CreateUninitializedVector(len,
sizeof(T),
2066 reinterpret_cast<uint8_t **>(buf));
2069 template<
typename T>
2072 return CreateUninitializedVector(len,
sizeof(T),
2073 reinterpret_cast<uint8_t **>(buf));
2079 template<
typename T,
typename U>
2083 StartVector(len,
sizeof(T));
2084 for (
auto i = len; i > 0;) { PushElement(static_cast<T>(v[--i])); }
2091 Align(AlignOf<T>());
2092 buf_.push_small(structobj);
2097 static const size_t kFileIdentifierLength = 4;
2102 template<
typename T>
2104 Finish(root.
o, file_identifier,
false);
2114 template<
typename T>
2116 const char *file_identifier =
nullptr) {
2117 Finish(root.
o, file_identifier,
true);
2121 buf_.swap_allocator(other.
buf_);
2129 void Finish(uoffset_t root,
const char *file_identifier,
bool size_prefix) {
2131 buf_.clear_scratch();
2133 PreAlign((size_prefix ?
sizeof(uoffset_t) : 0) +
sizeof(uoffset_t) +
2134 (file_identifier ? kFileIdentifierLength : 0),
2136 if (file_identifier) {
2138 PushBytes(reinterpret_cast<const uint8_t *>(file_identifier),
2139 kFileIdentifierLength);
2141 PushElement(ReferTo(root));
2142 if (size_prefix) { PushElement(GetSize()); }
2175 auto stra =
reinterpret_cast<const String *
>(buf_->
data_at(a.
o));
2176 auto strb =
reinterpret_cast<const String *
>(buf_->
data_at(b.
o));
2191 StartVector(vector_size *
sizeof(T) / AlignOf<T>(), AlignOf<T>());
2192 return reinterpret_cast<T *
>(buf_.
make_space(vector_size *
sizeof(T)));
2197 template<
typename T>
2206 template<
typename T> T *GetMutableRoot(
void *buf) {
2208 return reinterpret_cast<T *
>(
2209 reinterpret_cast<uint8_t *
>(buf) +
2210 EndianScalar(*reinterpret_cast<uoffset_t *>(buf)));
2213 template<
typename T>
const T *GetRoot(
const void *buf) {
2214 return GetMutableRoot<T>(
const_cast<void *
>(buf));
2217 template<
typename T>
const T *GetSizePrefixedRoot(
const void *buf) {
2218 return GetRoot<T>(
reinterpret_cast<const uint8_t *
>(buf) +
sizeof(uoffset_t));
2224 template<
typename T>
2230 template<
typename T>
2232 return GetMutableTemporaryPointer<T>(fbb, offset);
2242 inline const char *GetBufferIdentifier(
const void *buf,
2243 bool size_prefixed =
false) {
2244 return reinterpret_cast<const char *
>(buf) +
2245 ((size_prefixed) ? 2 *
sizeof(uoffset_t) :
sizeof(uoffset_t));
2249 inline bool BufferHasIdentifier(
const void *buf,
const char *identifier,
2250 bool size_prefixed =
false) {
2251 return strncmp(GetBufferIdentifier(buf, size_prefixed), identifier,
2256 class Verifier FLATBUFFERS_FINAL_CLASS {
2258 Verifier(
const uint8_t *buf,
size_t buf_len, uoffset_t _max_depth = 64,
2259 uoffset_t _max_tables = 1000000,
bool _check_alignment =
true)
2263 max_depth_(_max_depth),
2265 max_tables_(_max_tables),
2267 check_alignment_(_check_alignment) {
2272 bool Check(
bool ok)
const {
2274 #ifdef FLATBUFFERS_DEBUG_VERIFICATION_FAILURE 2277 #ifdef FLATBUFFERS_TRACK_VERIFIER_BUFFER_SIZE 2286 bool Verify(
size_t elem,
size_t elem_len)
const {
2288 #ifdef FLATBUFFERS_TRACK_VERIFIER_BUFFER_SIZE 2289 auto upper_bound = elem + elem_len;
2290 if (upper_bound_ < upper_bound)
2291 upper_bound_ = upper_bound;
2294 return Check(elem_len < size_ && elem <= size_ - elem_len);
2297 template<
typename T>
bool VerifyAlignment(
size_t elem)
const {
2298 return Check((elem & (
sizeof(T) - 1)) == 0 || !check_alignment_);
2302 template<
typename T>
bool Verify(
size_t elem)
const {
2303 return VerifyAlignment<T>(elem) && Verify(elem,
sizeof(T));
2306 bool VerifyFromPointer(
const uint8_t *p,
size_t len) {
2307 auto o =
static_cast<size_t>(p - buf_);
2308 return Verify(
o, len);
2312 bool Verify(
const uint8_t *base, voffset_t elem_off,
size_t elem_len)
const {
2313 return Verify(static_cast<size_t>(base - buf_) + elem_off, elem_len);
2316 template<
typename T>
2317 bool Verify(
const uint8_t *base, voffset_t elem_off)
const {
2318 return Verify(static_cast<size_t>(base - buf_) + elem_off,
sizeof(T));
2322 template<
typename T>
bool VerifyTable(
const T *table) {
2323 return !table || table->Verify(*
this);
2327 template<
typename T>
bool VerifyVector(
const Vector<T> *vec)
const {
2328 return !vec || VerifyVectorOrString(reinterpret_cast<const uint8_t *>(vec),
2334 return VerifyVector(
reinterpret_cast<const Vector<T> *
>(vec));
2338 bool VerifyString(
const String *str)
const {
2340 return !str || (VerifyVectorOrString(reinterpret_cast<const uint8_t *>(str),
2343 Check(buf_[end] ==
'\0'));
2347 bool VerifyVectorOrString(
const uint8_t *vec,
size_t elem_size,
2348 size_t *end =
nullptr)
const {
2349 auto veco =
static_cast<size_t>(vec - buf_);
2351 if (!Verify<uoffset_t>(veco))
return false;
2354 auto size = ReadScalar<uoffset_t>(vec);
2355 auto max_elems = FLATBUFFERS_MAX_BUFFER_SIZE / elem_size;
2356 if (!Check(size < max_elems))
2358 auto byte_size =
sizeof(size) + elem_size * size;
2359 if (end) *end = veco + byte_size;
2360 return Verify(veco, byte_size);
2366 for (uoffset_t i = 0; i < vec->size(); i++) {
2367 if (!VerifyString(vec->Get(i)))
return false;
2374 template<
typename T>
bool VerifyVectorOfTables(
const Vector<
Offset<T>> *vec) {
2376 for (uoffset_t i = 0; i < vec->size(); i++) {
2377 if (!vec->Get(i)->Verify(*
this))
return false;
2383 __supress_ubsan__(
"unsigned-integer-overflow")
bool VerifyTableStart(
2384 const uint8_t *table) {
2386 auto tableo =
static_cast<size_t>(table - buf_);
2387 if (!Verify<soffset_t>(tableo))
return false;
2390 auto vtableo = tableo -
static_cast<size_t>(ReadScalar<soffset_t>(table));
2392 return VerifyComplexity() && Verify<voffset_t>(vtableo) &&
2393 VerifyAlignment<voffset_t>(ReadScalar<voffset_t>(buf_ + vtableo)) &&
2394 Verify(vtableo, ReadScalar<voffset_t>(buf_ + vtableo));
2397 template<
typename T>
2398 bool VerifyBufferFromStart(
const char *identifier,
size_t start) {
2399 if (identifier && !Check((size_ >= 2 *
sizeof(flatbuffers::uoffset_t) &&
2400 BufferHasIdentifier(buf_ + start, identifier)))) {
2405 auto o = VerifyOffset(start);
2406 return o &&
reinterpret_cast<const T *
>(buf_ + start +
o)->Verify(*
this)
2408 #ifdef FLATBUFFERS_TRACK_VERIFIER_BUFFER_SIZE 2409 && GetComputedSize()
2416 template<
typename T>
bool VerifyBuffer() {
return VerifyBuffer<T>(
nullptr); }
2418 template<
typename T>
bool VerifyBuffer(
const char *identifier) {
2419 return VerifyBufferFromStart<T>(identifier, 0);
2422 template<
typename T>
bool VerifySizePrefixedBuffer(
const char *identifier) {
2423 return Verify<uoffset_t>(0U) &&
2424 ReadScalar<uoffset_t>(buf_) == size_ -
sizeof(uoffset_t) &&
2425 VerifyBufferFromStart<T>(identifier,
sizeof(uoffset_t));
2428 uoffset_t VerifyOffset(
size_t start)
const {
2429 if (!Verify<uoffset_t>(start))
return 0;
2430 auto o = ReadScalar<uoffset_t>(buf_ + start);
2432 if (!Check(
o != 0))
return 0;
2434 if (!Check(static_cast<soffset_t>(
o) >= 0))
return 0;
2437 if (!Verify(start +
o, 1))
return 0;
2441 uoffset_t VerifyOffset(
const uint8_t *base, voffset_t start)
const {
2442 return VerifyOffset(static_cast<size_t>(base - buf_) + start);
2449 bool VerifyComplexity() {
2452 return Check(depth_ <= max_depth_ && num_tables_ <= max_tables_);
2462 size_t GetComputedSize()
const {
2464 #ifdef FLATBUFFERS_TRACK_VERIFIER_BUFFER_SIZE 2465 uintptr_t size = upper_bound_;
2467 size = (size - 1 +
sizeof(uoffset_t)) & ~(
sizeof(uoffset_t) - 1);
2468 return (size > size_) ? 0 : size;
2479 const uint8_t *buf_;
2482 uoffset_t max_depth_;
2483 uoffset_t num_tables_;
2484 uoffset_t max_tables_;
2485 mutable size_t upper_bound_;
2486 bool check_alignment_;
2492 struct BufferRefBase {};
2493 template<
typename T>
struct BufferRef : BufferRefBase {
2494 BufferRef() : buf(
nullptr), len(0), must_free(
false) {}
2495 BufferRef(uint8_t *_buf, uoffset_t _len)
2496 : buf(_buf), len(_len), must_free(
false) {}
2499 if (must_free) free(buf);
2502 const T *GetRoot()
const {
return flatbuffers::GetRoot<T>(buf); }
2505 Verifier verifier(buf, len);
2506 return verifier.VerifyBuffer<T>(
nullptr);
2518 class Struct FLATBUFFERS_FINAL_CLASS {
2520 template<
typename T> T GetField(uoffset_t
o)
const {
2521 return ReadScalar<T>(&data_[
o]);
2524 template<
typename T> T GetStruct(uoffset_t o)
const {
2525 return reinterpret_cast<T
>(&data_[
o]);
2528 const uint8_t *GetAddressOf(uoffset_t o)
const {
return &data_[
o]; }
2529 uint8_t *GetAddressOf(uoffset_t o) {
return &data_[
o]; }
2535 Struct(
const Struct &);
2536 Struct &operator=(
const Struct &);
2545 const uint8_t *GetVTable()
const {
2546 return data_ - ReadScalar<soffset_t>(data_);
2551 voffset_t GetOptionalFieldOffset(voffset_t field)
const {
2553 auto vtable = GetVTable();
2555 auto vtsize = ReadScalar<voffset_t>(vtable);
2558 return field < vtsize ? ReadScalar<voffset_t>(vtable + field) : 0;
2561 template<
typename T> T GetField(voffset_t field, T defaultval)
const {
2562 auto field_offset = GetOptionalFieldOffset(field);
2563 return field_offset ? ReadScalar<T>(data_ + field_offset) : defaultval;
2566 template<
typename P> P GetPointer(voffset_t field) {
2567 auto field_offset = GetOptionalFieldOffset(field);
2568 auto p = data_ + field_offset;
2569 return field_offset ?
reinterpret_cast<P
>(p + ReadScalar<uoffset_t>(p))
2572 template<
typename P> P GetPointer(voffset_t field)
const {
2573 return const_cast<Table *
>(
this)->GetPointer<P>(field);
2576 template<
typename P> P GetStruct(voffset_t field)
const {
2577 auto field_offset = GetOptionalFieldOffset(field);
2578 auto p =
const_cast<uint8_t *
>(data_ + field_offset);
2579 return field_offset ?
reinterpret_cast<P
>(p) :
nullptr;
2582 template<
typename Raw,
typename Face>
2583 flatbuffers::Optional<Face> GetOptional(voffset_t field)
const {
2584 auto field_offset = GetOptionalFieldOffset(field);
2585 auto p = data_ + field_offset;
2586 return field_offset ? Optional<Face>(
static_cast<Face
>(ReadScalar<Raw>(p)))
2590 template<
typename T>
bool SetField(voffset_t field, T val, T def) {
2591 auto field_offset = GetOptionalFieldOffset(field);
2593 WriteScalar(data_ + field_offset, val);
2596 template<
typename T>
bool SetField(voffset_t field, T val) {
2597 auto field_offset = GetOptionalFieldOffset(field);
2598 if (!field_offset)
return false;
2599 WriteScalar(data_ + field_offset, val);
2603 bool SetPointer(voffset_t field,
const uint8_t *val) {
2604 auto field_offset = GetOptionalFieldOffset(field);
2605 if (!field_offset)
return false;
2606 WriteScalar(data_ + field_offset,
2607 static_cast<uoffset_t>(val - (data_ + field_offset)));
2611 uint8_t *GetAddressOf(voffset_t field) {
2612 auto field_offset = GetOptionalFieldOffset(field);
2613 return field_offset ? data_ + field_offset :
nullptr;
2615 const uint8_t *GetAddressOf(voffset_t field)
const {
2616 return const_cast<Table *
>(
this)->GetAddressOf(field);
2619 bool CheckField(voffset_t field)
const {
2620 return GetOptionalFieldOffset(field) != 0;
2625 bool VerifyTableStart(Verifier &verifier)
const {
2626 return verifier.VerifyTableStart(data_);
2630 template<
typename T>
2631 bool VerifyField(
const Verifier &verifier, voffset_t field)
const {
2634 auto field_offset = GetOptionalFieldOffset(field);
2636 return !field_offset || verifier.Verify<T>(data_, field_offset);
2640 template<
typename T>
2641 bool VerifyFieldRequired(
const Verifier &verifier, voffset_t field)
const {
2642 auto field_offset = GetOptionalFieldOffset(field);
2643 return verifier.Check(field_offset != 0) &&
2644 verifier.Verify<T>(data_, field_offset);
2648 bool VerifyOffset(
const Verifier &verifier, voffset_t field)
const {
2649 auto field_offset = GetOptionalFieldOffset(field);
2650 return !field_offset || verifier.VerifyOffset(data_, field_offset);
2653 bool VerifyOffsetRequired(
const Verifier &verifier, voffset_t field)
const {
2654 auto field_offset = GetOptionalFieldOffset(field);
2655 return verifier.Check(field_offset != 0) &&
2656 verifier.VerifyOffset(data_, field_offset);
2663 Table(
const Table &other);
2664 Table &operator=(
const Table &);
2672 inline flatbuffers::Optional<bool> Table::GetOptional<uint8_t, bool>(
2673 voffset_t field)
const {
2674 auto field_offset = GetOptionalFieldOffset(field);
2675 auto p = data_ + field_offset;
2676 return field_offset ? Optional<bool>(ReadScalar<uint8_t>(p) != 0)
2680 template<
typename T>
2681 void FlatBufferBuilder::Required(
Offset<T> table, voffset_t field) {
2682 auto table_ptr =
reinterpret_cast<const Table *
>(buf_.data_at(table.
o));
2683 bool ok = table_ptr->GetOptionalFieldOffset(field) != 0;
2693 inline const uint8_t *GetBufferStartFromRootPointer(
const void *root) {
2694 auto table =
reinterpret_cast<const Table *
>(root);
2695 auto vtable = table->GetVTable();
2697 auto start = (std::min)(vtable, reinterpret_cast<const uint8_t *>(root));
2699 start =
reinterpret_cast<const uint8_t *
>(
reinterpret_cast<uintptr_t
>(start) &
2700 ~(
sizeof(uoffset_t) - 1));
2711 "file_identifier is assumed to be the same size as uoffset_t");
2712 for (
auto possible_roots = FLATBUFFERS_MAX_ALIGNMENT /
sizeof(uoffset_t) + 1;
2713 possible_roots; possible_roots--) {
2714 start -=
sizeof(uoffset_t);
2715 if (ReadScalar<uoffset_t>(start) + start ==
2716 reinterpret_cast<const uint8_t *
>(root))
2728 inline uoffset_t GetPrefixedSize(
const uint8_t *buf) {
2729 return ReadScalar<uoffset_t>(buf);
2735 struct NativeTable {};
2745 typedef uint64_t hash_value_t;
2747 #ifdef FLATBUFFERS_CPP98_STL 2748 typedef void (*resolver_function_t)(
void **pointer_adr, hash_value_t hash);
2749 typedef hash_value_t (*rehasher_function_t)(
void *pointer);
2751 typedef std::function<void (void **pointer_adr, hash_value_t hash)>
2752 resolver_function_t;
2753 typedef std::function<hash_value_t (void *pointer)> rehasher_function_t;
2764 template<
typename T>
2765 bool IsFieldPresent(
const T *table,
typename T::FlatBuffersVTableOffset field) {
2767 return reinterpret_cast<const Table *
>(table)->CheckField(
2768 static_cast<voffset_t>(field));
2774 inline int LookupEnum(
const char **names,
const char *name) {
2775 for (
const char **p = names; *p; p++)
2776 if (!strcmp(*p, name))
return static_cast<int>(p - names);
2791 #if defined(_MSC_VER) 2792 #define FLATBUFFERS_MANUALLY_ALIGNED_STRUCT(alignment) \ 2794 struct __declspec(align(alignment)) 2795 #define FLATBUFFERS_STRUCT_END(name, size) \ 2797 static_assert(sizeof(name) == size, "compiler breaks packing rules") 2798 #elif defined(__GNUC__) || defined(__clang__) || defined(__ICCARM__) 2799 #define FLATBUFFERS_MANUALLY_ALIGNED_STRUCT(alignment) \ 2800 _Pragma("pack(1)") \ 2801 struct __attribute__((aligned(alignment))) 2802 #define FLATBUFFERS_STRUCT_END(name, size) \ 2804 static_assert(sizeof(name) == size, "compiler breaks packing rules") 2806 #error Unknown compiler, please define structure alignment macros 2820 enum SequenceType { ST_TABLE, ST_STRUCT, ST_UNION, ST_ENUM };
2824 #define FLATBUFFERS_GEN_ELEMENTARY_TYPES(ET) \ 2838 ET(ET_SEQUENCE) // See SequenceType. 2840 enum ElementaryType {
2841 #define FLATBUFFERS_ET(E) E, 2842 FLATBUFFERS_GEN_ELEMENTARY_TYPES(FLATBUFFERS_ET)
2843 #undef FLATBUFFERS_ET 2846 inline const char *
const *ElementaryTypeNames() {
2847 static const char *
const names[] = {
2848 #define FLATBUFFERS_ET(E) #E, 2849 FLATBUFFERS_GEN_ELEMENTARY_TYPES(FLATBUFFERS_ET)
2850 #undef FLATBUFFERS_ET 2862 unsigned short base_type : 4;
2864 unsigned short is_repeating : 1;
2866 signed short sequence_ref : 11;
2869 static_assert(
sizeof(TypeCode) == 2,
"TypeCode");
2874 typedef const TypeTable *(*TypeFunction)();
2879 const TypeCode *type_codes;
2880 const TypeFunction *type_refs;
2881 const int16_t *array_sizes;
2882 const int64_t *values;
2883 const char *
const *names;
2897 #if !defined(_WIN32) && !defined(__CYGWIN__) 2899 extern volatile __attribute__((weak))
const char *flatbuffer_version_string;
2900 volatile __attribute__((weak))
const char *flatbuffer_version_string =
2902 FLATBUFFERS_STRING(FLATBUFFERS_VERSION_MAJOR)
"." 2903 FLATBUFFERS_STRING(FLATBUFFERS_VERSION_MINOR)
"." 2904 FLATBUFFERS_STRING(FLATBUFFERS_VERSION_REVISION);
2906 #endif // !defined(_WIN32) && !defined(__CYGWIN__) 2908 #define FLATBUFFERS_DEFINE_BITMASK_OPERATORS(E, T)\ 2909 inline E operator | (E lhs, E rhs){\ 2910 return E(T(lhs) | T(rhs));\ 2912 inline E operator & (E lhs, E rhs){\ 2913 return E(T(lhs) & T(rhs));\ 2915 inline E operator ^ (E lhs, E rhs){\ 2916 return E(T(lhs) ^ T(rhs));\ 2918 inline E operator ~ (E lhs){\ 2921 inline E operator |= (E &lhs, E rhs){\ 2925 inline E operator &= (E &lhs, E rhs){\ 2929 inline E operator ^= (E &lhs, E rhs){\ 2933 inline bool operator !(E rhs) \ 2935 return !bool(T(rhs)); \ 2942 #endif // FLATBUFFERS_H_ FLATBUFFERS_CONSTEXPR size_t AlignOf()
virtual uint8_t * reallocate_downward(uint8_t *old_p, size_t old_size, size_t new_size, size_t in_use_back, size_t in_use_front)
Offset< Vector< const T * > > CreateVectorOfSortedStructs(T *v, size_t len)
Serialize an array of structs into a FlatBuffer vector in sorted order.
const_reverse_iterator rbegin() const
const T * data(const std::vector< T, Alloc > &v)
flatbuffers::conditional< scalar_tag::value, T, const T * >::type IndirectHelperType
VectorIterator & operator+=(const uoffset_t &offset)
void Mutate(uoffset_t i, const T &val)
const U * GetAs(uoffset_t i) const
VectorIterator< T, return_type > const_iterator
uint8_t * allocate(size_t size) FLATBUFFERS_OVERRIDE
Allocator * get_custom_allocator()
void memcpy_downward(uint8_t *old_p, size_t old_size, uint8_t *new_p, size_t new_size, size_t in_use_back, size_t in_use_front)
IndirectHelper< T >::return_type return_type
VectorIterator operator++(int)
StringOffsetMap * string_pool
VectorIterator operator-(const uoffset_t &offset) const
VectorIterator< T, typename IndirectHelper< T >::mutable_return_type > iterator
Offset< Vector< const T * > > CreateVectorOfSortedStructs(std::vector< T > *v)
Serialize a std::vector of structs into a FlatBuffer vector in sorted order.
void fill(size_t zero_pad_bytes)
void ForceDefaults(bool fd)
In order to save space, fields that are set to their default value don't get serialized into the buff...
Offset< const T * > CreateStruct(const T &structobj)
Write a struct by itself, typically to be part of a union.
FLATBUFFERS_ATTRIBUTE(deprecated("use Release() instead")) DetachedBuffer ReleaseBufferPointer()
Get the released pointer to the serialized buffer.
const_reverse_iterator crend() const
const uint8_t * Data() const
bool IsTheSameAs(T e, T def)
vector_downward(vector_downward &&other)
static int KeyCompare(const void *ap, const void *bp)
Vector< Offset< T > > * VectorCast(Vector< Offset< U >> *ptr)
Offset< Vector< const T * > > CreateVectorOfStructs(size_t vector_size, F f, S *state)
Serialize an array of structs into a FlatBuffer vector.
const_iterator cbegin() const
Offset< Vector< T > > CreateUninitializedVector(size_t len, T **buf)
Specialized version of CreateVector for non-copying use cases. Write the data any time later to the r...
voffset_t FieldIndexToOffset(voffset_t field_id)
return_type operator[](uoffset_t i) const
VectorIterator & operator=(const VectorIterator &other)
void CopyFromSpanImpl(flatbuffers::integral_constant< bool, true >, flatbuffers::span< const T, length > src)
void MutateOffset(uoffset_t i, const uint8_t *val)
const uint8_t * Data() const
void Finish(Offset< T > root, const char *file_identifier=nullptr)
Finish serializing a buffer by writing the root offset.
Offset< Vector< T > > CreateVector(const std::vector< T > &v)
Serialize a std::vector into a FlatBuffer vector.
const uint8_t * Data() const
difference_type operator-(const VectorIterator &other) const
VectorIterator operator+(const uoffset_t &offset) const
static void dealloc(void *p, size_t)
void MutateImpl(flatbuffers::integral_constant< bool, true >, uoffset_t i, const T &val)
const_reverse_iterator rbegin() const
Array< E, length > & CastToArrayOfEnum(T(&arr)[length])
void swap(linb::any &lhs, linb::any &rhs) noexcept
VectorReverseIterator< const_iterator > const_reverse_iterator
const_iterator begin() const
const char * c_str() const
void MutateImpl(flatbuffers::integral_constant< bool, false >, uoffset_t i, const T &val)
const uint8_t * Data() const
VectorIterator(const uint8_t *data, uoffset_t i)
Offset< String > CreateString(const char *str, size_t len)
Store a string in the buffer, which can contain any binary data.
return_type LookupByKey(K key) const
vector_downward(size_t initial_size, Allocator *allocator, bool own_allocator, size_t buffer_minalign)
uint8_t * scratch_data() const
bool operator<(const VectorIterator &other) const
Offset< String > CreateString(const char *str)
Store a string in the buffer, which is null-terminated.
const uint8_t * data() const
IndirectHelper< T >::mutable_return_type mutable_return_type
return_type operator[](uoffset_t i) const
Offset< Vector< Offset< String > > > CreateVectorOfStrings(const std::vector< std::string > &v)
Serialize a std::vector<std::string> into a FlatBuffer vector. This is a convenience function for a c...
Offset< Vector< const T * > > CreateVectorOfSortedNativeStructs(std::vector< S > *v)
Serialize a std::vector of native structs into a FlatBuffer vector in sorted order.
Offset< Vector< const T * > > CreateVectorOfNativeStructs(const std::vector< S > &v, T((*const pack_func)(const S &)))
Serialize a std::vector of native structs into a FlatBuffer vector.
uoffset_t scratch_size() const
void SwapBufAllocator(FlatBufferBuilder &other)
FlatBufferBuilder(size_t initial_size=1024, Allocator *allocator=nullptr, bool own_allocator=false, size_t buffer_minalign=AlignOf< largest_scalar_t >())
Default constructor for FlatBufferBuilder.
void swap(vector_downward &other)
static bool StringLessThan(const char *a_data, uoffset_t a_size, const char *b_data, uoffset_t b_size)
T * StartVectorOfStructs(size_t vector_size)
ptrdiff_t difference_type
void CopyFromSpanImpl(flatbuffers::integral_constant< bool, false >, flatbuffers::span< const T, length > src)
const_iterator cend() const
Offset< String > CreateString(const T &str)
Store a string in the buffer, which can contain any binary data.
Helper class to hold data needed in creation of a FlatBuffer. To serialize data, you typically call o...
VectorIterator< T, typename IndirectHelper< T >::return_type > const_iterator
static return_type Read(const uint8_t *p, uoffset_t i)
FLATBUFFERS_ATTRIBUTE(deprecated("use size() instead")) uoffset_t Length() const
Array< T, length > & CastToArray(T(&arr)[length])
uint8_t * GetCurrentBufferPointer() const
Get a pointer to an unfinished buffer.
const vector_downward * buf_
const_reverse_iterator crbegin() const
uint8_t * make_space(size_t len)
DetachedBuffer(DetachedBuffer &&other)
flatbuffers::integral_constant< bool, flatbuffers::is_scalar< T >::value > scalar_tag
uint8_t * ReallocateDownward(Allocator *allocator, uint8_t *old_p, size_t old_size, size_t new_size, size_t in_use_back, size_t in_use_front)
bool operator==(const VectorIterator &other) const
void Deallocate(Allocator *allocator, uint8_t *p, size_t size)
void push(const uint8_t *bytes, size_t num)
void pop(size_t bytes_to_remove)
VectorIterator & operator--()
uint8_t * Allocate(Allocator *allocator, size_t size)
void DedupVtables(bool dedup)
By default vtables are deduped in order to save space.
Iterator::value_type operator*() const
E GetEnum(uoffset_t i) const
void Mutate(uoffset_t i, const T &val)
void push_small(const T &little_endian_t)
vector_downward & operator=(vector_downward &&other)
virtual uint8_t * allocate(size_t size)=0
return_type Get(uoffset_t i) const
bool operator()(const Offset< String > &a, const Offset< String > &b) const
Offset< Vector< const T * > > CreateVectorOfNativeStructs(const S *v, size_t len)
Serialize an array of native structs into a FlatBuffer vector.
flatbuffers::conditional< scalar_tag::value, void, T * >::type GetMutablePointer(uoffset_t i) const
static std::string GetString(const String *str)
FLATBUFFERS_CONSTEXPR uint16_t size() const
DetachedBuffer Release()
Get the released DetachedBuffer.
Offset< String > CreateString(char *str)
Store a string in the buffer, which is null-terminated.
FlatBufferBuilder & operator=(FlatBufferBuilder &&other)
Move assignment operator for FlatBufferBuilder.
const_reverse_iterator rend() const
VectorIterator operator--(int)
void deallocate(uint8_t *p, size_t) FLATBUFFERS_OVERRIDE
Offset< Vector< const T * > > CreateVectorOfNativeStructs(const std::vector< S > &v)
Serialize a std::vector of native structs into a FlatBuffer vector.
void Finish(uoffset_t root, const char *file_identifier, bool size_prefix)
Offset< Vector< uint8_t > > CreateVector(const std::vector< bool > &v)
bool operator<(const String &o) const
void scratch_pop(size_t bytes_to_remove)
void fill_big(size_t zero_pad_bytes)
void scratch_push_small(const T &t)
uint8_t * scratch_end() const
Offset< Vector< T > > CreateVector(size_t vector_size, F f, S *state)
Serialize values returned by a function into a FlatBuffer vector. This is a convenience function that...
Offset< Vector< const T * > > CreateVectorOfSortedNativeStructs(S *v, size_t len)
Serialize an array of native structs into a FlatBuffer vector in sorted order.
void CopyFromSpan(flatbuffers::span< const T, length > src)
Offset< Vector< const T * > > CreateVectorOfStructs(const T *v, size_t len)
Serialize an array of structs into a FlatBuffer vector.
#define FLATBUFFERS_ASSERT
VectorReverseIterator< const_iterator > const_reverse_iterator
bool IsInRange(const T &v, const T &low, const T &high)
Offset< Vector< Offset< T > > > CreateVectorOfSortedTables(Offset< T > *v, size_t len)
Serialize an array of table offsets as a vector in the buffer in sorted order.
Offset< Vector< const T * > > CreateVectorOfStructs(const std::vector< T, Alloc > &v)
Serialize a std::vector of structs into a FlatBuffer vector.
const_reverse_iterator rend() const
void reallocate(size_t len)
uoffset_t GetSize() const
The current size of the serialized buffer, counting from the end.
uoffset_t CreateUninitializedVector(size_t len, size_t elemsize, uint8_t **buf)
Specialized version of CreateVector for non-copying use cases. Write the data any time later to the r...
flatbuffers::span< uint8_t > GetBufferSpan() const
Get the serialized buffer (after you call Finish()) as a span.
static const size_t kFileIdentifierLength
The length of a FlatBuffer file header.
Iterator::value_type operator->() const
VectorReverseIterator< iterator > reverse_iterator
Offset< Vector< const T * > > CreateUninitializedVectorOfStructs(size_t len, T **buf)
Offset< Vector< T > > CreateVector(const T *v, size_t len)
Serialize an array into a FlatBuffer vector.
std::random_access_iterator_tag iterator_category
static size_t VectorLength(const Vector< T > *v)
std::set< Offset< String >, StringOffsetCompare > StringOffsetMap
uint8_t * data_at(size_t offset) const
StringOffsetCompare(const vector_downward &buf)
reverse_iterator rbegin()
Offset< String > CreateSharedString(const char *str, size_t len)
Store a string in the buffer, which can contain any binary data. If a string with this exact contents...
bool IsOutRange(const T &v, const T &low, const T &high)
mutable_return_type GetMutableObject(uoffset_t i) const
Offset< Vector< const T * > > EndVectorOfStructs(size_t vector_size)
VectorReverseIterator(Iterator iter)
void swap(message_t &a, message_t &b) ZMQ_NOTHROW
size_t ensure_space(size_t len)
DetachedBuffer(Allocator *allocator, bool own_allocator, uint8_t *buf, size_t reserved, uint8_t *cur, size_t sz)
return_type Get(uoffset_t i) const
DetachedBuffer & operator=(DetachedBuffer &&other)
const_iterator end() const
const_reverse_iterator crend() const
VectorIterator(const VectorIterator &other)
VectorIterator & operator=(VectorIterator &&other)
VectorIterator & operator++()
Offset< String > CreateSharedString(const std::string &str)
Store a string in the buffer, which can contain any binary data. If a string with this exact contents...
void FinishSizePrefixed(Offset< T > root, const char *file_identifier=nullptr)
Finish a buffer with a 32 bit size field pre-fixed (size of the buffer following the size field)...
Offset< String > CreateString(const String *str)
Store a string in the buffer, which can contain any binary data.
uint8_t * ReleaseRaw(size_t &size, size_t &offset)
Get the released pointer to the serialized buffer.
void Clear()
Reset all the state in this FlatBufferBuilder so it can be reused to construct another buffer...
static return_type Read(const uint8_t *p, uoffset_t i)
const_iterator cbegin() const
Offset< Vector< Offset< T > > > CreateVector(const Offset< T > *v, size_t len)
const_iterator begin() const
Offset< String > CreateString(const std::string &str)
Store a string in the buffer, which can contain any binary data.
static const char * GetCstring(const String *str)
static return_type Read(const uint8_t *p, uoffset_t i)
VectorIterator & operator-=(const uoffset_t &offset)
const void * GetStructFromOffset(size_t o) const
uint8_t * release_raw(size_t &allocated_bytes, size_t &offset)
E GetEnum(uoffset_t i) const
void Swap(FlatBufferBuilder &other)
const String * GetAsString(uoffset_t i) const
IndirectHelper< IndirectHelperType >::return_type return_type
Offset< Vector< Offset< T > > > CreateVectorOfSortedTables(std::vector< Offset< T >> *v)
Serialize an array of table offsets as a vector in the buffer in sorted order.
const_iterator end() const
FlatBufferBuilder(FlatBufferBuilder &&other)
Move constructor for FlatBufferBuilder.
bool operator!=(const VectorIterator &other) const
virtual void deallocate(uint8_t *p, size_t size)=0
Offset< void > Union() const
size_t GetBufferMinAlignment() const
get the minimum alignment this buffer needs to be accessed properly. This is only known once all elem...
void swap_allocator(vector_downward &other)
Offset< String > CreateSharedString(const String *str)
Store a string in the buffer, which can contain any binary data. If a string with this exact contents...
Offset< Vector< const T * > > CreateVectorOfNativeStructs(const S *v, size_t len, T((*const pack_func)(const S &)))
Serialize an array of native structs into a FlatBuffer vector.
const_iterator cend() const
const_reverse_iterator crbegin() const
uint8_t * GetBufferPointer() const
Get the serialized buffer (after you call Finish()).
return_type operator[](uoffset_t) const
Offset< Vector< T > > CreateVectorScalarCast(const U *v, size_t len)