mirror of
https://github.com/google/flatbuffers.git
synced 2026-06-03 12:21:23 +00:00
Size verifier fix 2 (#8740)
* Fixes to make SizeVerifier work. In particular change all the places in the Flatbuffers library and generated code that were using `Verifier` to instead use `VerifierTemplate<TrackBufferSize>` and wrap them all inside `template <bool TrackBufferSize = false>`. Also add unit tests for SizeVerifier. * Format using `sh scripts/clang-format-git.sh` * Use `B` rather than `TrackBufferSize` for the name of the template parameter. * Update generated files.
This commit is contained in:
@@ -681,17 +681,20 @@ class CppGenerator : public BaseGenerator {
|
||||
code_.SetValue("ID", "nullptr");
|
||||
}
|
||||
|
||||
code_ += "template <bool B = false>";
|
||||
code_ += "inline bool Verify{{STRUCT_NAME}}Buffer(";
|
||||
code_ += " ::flatbuffers::Verifier &verifier) {";
|
||||
code_ += " return verifier.VerifyBuffer<{{CPP_NAME}}>({{ID}});";
|
||||
code_ += " ::flatbuffers::VerifierTemplate<B> &verifier) {";
|
||||
code_ += " return verifier.template VerifyBuffer<{{CPP_NAME}}>({{ID}});";
|
||||
code_ += "}";
|
||||
code_ += "";
|
||||
|
||||
code_ += "template <bool B = false>";
|
||||
code_ += "inline bool VerifySizePrefixed{{STRUCT_NAME}}Buffer(";
|
||||
code_ += " ::flatbuffers::Verifier &verifier) {";
|
||||
code_ += " ::flatbuffers::VerifierTemplate<B> &verifier) {";
|
||||
code_ +=
|
||||
" return "
|
||||
"verifier.VerifySizePrefixedBuffer<{{CPP_NAME}}{{SIZE_T}}>({{ID}});";
|
||||
"verifier.template "
|
||||
"VerifySizePrefixedBuffer<{{CPP_NAME}}{{SIZE_T}}>({{ID}});";
|
||||
code_ += "}";
|
||||
code_ += "";
|
||||
|
||||
@@ -1102,19 +1105,31 @@ class CppGenerator : public BaseGenerator {
|
||||
}
|
||||
}
|
||||
|
||||
// For the initial declaration, we specify the template parameters,
|
||||
// including template default arguments.
|
||||
std::string UnionVerifyTemplateDecl() { return "template <bool B = false>"; }
|
||||
|
||||
// For the subsequent definition, we must not redeclare the template default
|
||||
// arguments.
|
||||
std::string UnionVerifyTemplateDef() { return "template <bool B>"; }
|
||||
|
||||
// Should be used in conjunction with
|
||||
// UnionVerifyTemplateDecl()/UnionVerifyTemplateDef().
|
||||
std::string UnionVerifySignature(const EnumDef& enum_def) {
|
||||
return "bool Verify" + Name(enum_def) +
|
||||
"(::flatbuffers::Verifier &verifier, const void *obj, " +
|
||||
Name(enum_def) + " type)";
|
||||
"(::flatbuffers::VerifierTemplate<B> &verifier, " +
|
||||
"const void *obj, " + Name(enum_def) + " type)";
|
||||
}
|
||||
|
||||
// Should be used in conjunction with
|
||||
// UnionVerifyTemplateDecl()/UnionVerifyTemplateDef().
|
||||
std::string UnionVectorVerifySignature(const EnumDef& enum_def) {
|
||||
const std::string name = Name(enum_def);
|
||||
const std::string& type =
|
||||
opts_.scoped_enums ? name
|
||||
: GenTypeBasic(enum_def.underlying_type, false);
|
||||
return "bool Verify" + name + "Vector" +
|
||||
"(::flatbuffers::Verifier &verifier, " +
|
||||
"(::flatbuffers::VerifierTemplate<B> &verifier, " +
|
||||
"const ::flatbuffers::Vector<::flatbuffers::Offset<void>> "
|
||||
"*values, " +
|
||||
"const ::flatbuffers::Vector<" + type + "> *types)";
|
||||
@@ -1409,7 +1424,9 @@ class CppGenerator : public BaseGenerator {
|
||||
GenEnumObjectBasedAPI(enum_def);
|
||||
|
||||
if (enum_def.is_union) {
|
||||
code_ += UnionVerifyTemplateDecl();
|
||||
code_ += UnionVerifySignature(enum_def) + ";";
|
||||
code_ += UnionVerifyTemplateDecl();
|
||||
code_ += UnionVectorVerifySignature(enum_def) + ";";
|
||||
code_ += "";
|
||||
}
|
||||
@@ -1638,6 +1655,7 @@ class CppGenerator : public BaseGenerator {
|
||||
// on the wrong type.
|
||||
code_.SetValue("ENUM_NAME", Name(enum_def));
|
||||
|
||||
code_ += UnionVerifyTemplateDef();
|
||||
code_ += "inline " + UnionVerifySignature(enum_def) + " {";
|
||||
code_ += " switch (type) {";
|
||||
for (auto it = enum_def.Vals().begin(); it != enum_def.Vals().end(); ++it) {
|
||||
@@ -1654,7 +1672,7 @@ class CppGenerator : public BaseGenerator {
|
||||
code_.SetValue("ALIGN",
|
||||
NumToString(ev.union_type.struct_def->minalign));
|
||||
code_ +=
|
||||
" return verifier.VerifyField<{{TYPE}}>("
|
||||
" return verifier.template VerifyField<{{TYPE}}>("
|
||||
"static_cast<const uint8_t *>(obj), 0, {{ALIGN}});";
|
||||
} else {
|
||||
code_ += getptr;
|
||||
@@ -1678,6 +1696,7 @@ class CppGenerator : public BaseGenerator {
|
||||
code_ += "}";
|
||||
code_ += "";
|
||||
|
||||
code_ += UnionVerifyTemplateDef();
|
||||
code_ += "inline " + UnionVectorVerifySignature(enum_def) + " {";
|
||||
code_ += " if (!values || !types) return !values && !types;";
|
||||
code_ += " if (values->size() != types->size()) return false;";
|
||||
@@ -2412,7 +2431,7 @@ class CppGenerator : public BaseGenerator {
|
||||
code_.SetValue("CPP_NAME", nfn);
|
||||
// FIXME: file_identifier.
|
||||
code_ +=
|
||||
"{{PRE}}verifier.VerifyNestedFlatBuffer<{{CPP_NAME}}>"
|
||||
"{{PRE}}verifier.template VerifyNestedFlatBuffer<{{CPP_NAME}}>"
|
||||
"({{NAME}}(), nullptr)\\";
|
||||
} else if (field.flexbuffer) {
|
||||
code_ +=
|
||||
@@ -3001,7 +3020,10 @@ class CppGenerator : public BaseGenerator {
|
||||
|
||||
// Generate a verifier function that can check a buffer from an untrusted
|
||||
// source will never cause reads outside the buffer.
|
||||
code_ += " bool Verify(::flatbuffers::Verifier &verifier) const {";
|
||||
code_ += " template <bool B = false>";
|
||||
code_ +=
|
||||
" bool Verify(::flatbuffers::VerifierTemplate<B> "
|
||||
"&verifier) const {";
|
||||
code_ += " return VerifyTableStart(verifier)\\";
|
||||
for (const auto& field : struct_def.fields.vec) {
|
||||
if (field->deprecated) {
|
||||
|
||||
Reference in New Issue
Block a user