summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRandy Abernethy <ra@apache.org>2015-08-01 22:57:02 -0700
committerRandy Abernethy <ra@apache.org>2015-08-01 22:57:02 -0700
commit8dbe5f60a7c1401302e10aec41069f9c385d34a1 (patch)
tree86898a14c76a1d246b08480195918ef74e213769
parent54f392b8fd90d53deabbf107565ec92c985d47f5 (diff)
downloadthrift-8dbe5f60a7c1401302e10aec41069f9c385d34a1.tar.gz
THRIFT-2199:Remove dense protocol
Client: C++ library and compiler Patch: Randy Abernethy
-rw-r--r--compiler/cpp/src/generate/t_cpp_generator.cc242
-rw-r--r--compiler/cpp/src/generate/t_json_generator.cc6
-rw-r--r--compiler/cpp/src/main.cc37
-rw-r--r--compiler/cpp/src/parse/parse.cc12
-rw-r--r--compiler/cpp/src/parse/t_base_type.h8
-rw-r--r--compiler/cpp/src/parse/t_field.h9
-rw-r--r--compiler/cpp/src/parse/t_list.h9
-rw-r--r--compiler/cpp/src/parse/t_map.h11
-rw-r--r--compiler/cpp/src/parse/t_service.h5
-rw-r--r--compiler/cpp/src/parse/t_set.h9
-rw-r--r--compiler/cpp/src/parse/t_struct.h27
-rw-r--r--compiler/cpp/src/parse/t_type.h53
-rw-r--r--compiler/cpp/src/parse/t_typedef.h17
-rwxr-xr-xlib/cpp/CMakeLists.txt1
-rwxr-xr-xlib/cpp/Makefile.am3
-rw-r--r--lib/cpp/libthrift.vcxproj2
-rw-r--r--lib/cpp/libthrift.vcxproj.filters8
-rw-r--r--lib/cpp/src/thrift/TReflectionLocal.h92
-rw-r--r--lib/cpp/src/thrift/Thrift.h7
-rw-r--r--lib/cpp/src/thrift/protocol/TBinaryProtocol.h2
-rw-r--r--lib/cpp/src/thrift/protocol/TDenseProtocol.cpp753
-rw-r--r--lib/cpp/src/thrift/protocol/TDenseProtocol.h228
-rw-r--r--lib/cpp/test/CMakeLists.txt8
-rw-r--r--lib/cpp/test/DenseProtoTest.cpp485
-rwxr-xr-xlib/cpp/test/Makefile.am21
25 files changed, 17 insertions, 2038 deletions
diff --git a/compiler/cpp/src/generate/t_cpp_generator.cc b/compiler/cpp/src/generate/t_cpp_generator.cc
index f591107d9..e351f8a46 100644
--- a/compiler/cpp/src/generate/t_cpp_generator.cc
+++ b/compiler/cpp/src/generate/t_cpp_generator.cc
@@ -58,9 +58,6 @@ public:
iter = parsed_options.find("pure_enums");
gen_pure_enums_ = (iter != parsed_options.end());
- iter = parsed_options.find("dense");
- gen_dense_ = (iter != parsed_options.end());
-
iter = parsed_options.find("include_prefix");
use_include_prefix_ = (iter != parsed_options.end());
@@ -132,7 +129,6 @@ public:
void generate_assignment_operator(std::ofstream& out, t_struct* tstruct);
void generate_move_assignment_operator(std::ofstream& out, t_struct* tstruct);
void generate_assignment_helper(std::ofstream& out, t_struct* tstruct, bool is_move);
- void generate_struct_fingerprint(std::ofstream& out, t_struct* tstruct, bool is_definition);
void generate_struct_reader(std::ofstream& out, t_struct* tstruct, bool pointers = false);
void generate_struct_writer(std::ofstream& out, t_struct* tstruct, bool pointers = false);
void generate_struct_result_writer(std::ofstream& out, t_struct* tstruct, bool pointers = false);
@@ -231,7 +227,6 @@ public:
bool name_params = true);
std::string argument_list(t_struct* tstruct, bool name_params = true, bool start_comma = false);
std::string type_to_enum(t_type* ttype);
- std::string local_reflection_name(const char*, t_type* ttype, bool external = false);
void generate_enum_constant_list(std::ofstream& f,
const vector<t_enum_value*>& constants,
@@ -244,10 +239,6 @@ public:
t_struct* tstruct,
bool external = false);
- // These handles checking gen_dense_ and checking for duplicates.
- void generate_local_reflection(std::ofstream& out, t_type* ttype, bool is_definition);
- void generate_local_reflection_pointer(std::ofstream& out, t_type* ttype);
-
bool is_reference(t_field* tfield) { return tfield->get_reference(); }
bool is_complex_type(t_type* ttype) {
@@ -273,11 +264,6 @@ private:
bool gen_pure_enums_;
/**
- * True if we should generate local reflection metadata for TDenseProtocol.
- */
- bool gen_dense_;
-
- /**
* True if we should generate templatized reader/writer methods.
*/
bool gen_templates_;
@@ -333,11 +319,6 @@ private:
std::ofstream f_service_;
std::ofstream f_service_tcc_;
- /**
- * When generating local reflections, make sure we don't generate duplicates.
- */
- std::set<std::string> reflected_fingerprints_;
-
// The ProcessorGenerator is used to generate parts of the code,
// so it needs access to many of our protected members and methods.
//
@@ -418,12 +399,6 @@ void t_cpp_generator::init_generator() {
f_types_tcc_ << "#include \"" << get_include_prefix(*get_program()) << program_name_
<< "_types.h\"" << endl << endl;
- // If we are generating local reflection metadata, we need to include
- // the definition of TypeSpec.
- if (gen_dense_) {
- f_types_impl_ << "#include <thrift/TReflectionLocal.h>" << endl << endl;
- }
-
// The swap() code needs <algorithm> for std::swap()
f_types_impl_ << "#include <algorithm>" << endl;
// for operator<<
@@ -553,9 +528,6 @@ void t_cpp_generator::generate_enum(t_enum* tenum) {
<< tenum->get_name() << "Values"
<< ", _k" << tenum->get_name() << "Names), "
<< "::apache::thrift::TEnumIterator(-1, NULL, NULL));" << endl << endl;
-
- generate_local_reflection(f_types_, tenum, false);
- generate_local_reflection(f_types_impl_, tenum, true);
}
/**
@@ -753,10 +725,6 @@ void t_cpp_generator::generate_forward_declaration(t_struct* tstruct) {
void t_cpp_generator::generate_cpp_struct(t_struct* tstruct, bool is_exception) {
generate_struct_declaration(f_types_, tstruct, is_exception, false, true, true, true);
generate_struct_definition(f_types_impl_, f_types_impl_, tstruct);
- generate_struct_fingerprint(f_types_impl_, tstruct, true);
- generate_local_reflection(f_types_, tstruct, false);
- generate_local_reflection(f_types_impl_, tstruct, true);
- generate_local_reflection_pointer(f_types_impl_, tstruct);
std::ofstream& out = (gen_templates_ ? f_types_tcc_ : f_types_impl_);
generate_struct_reader(out, tstruct);
@@ -957,9 +925,6 @@ void t_cpp_generator::generate_struct_declaration(ofstream& out,
<< " public:" << endl << endl;
indent_up();
- // Put the fingerprint up top for all to see.
- generate_struct_fingerprint(out, tstruct, false);
-
if (!pointers) {
// Copy constructor
indent(out) << tstruct->get_name() << "(const " << tstruct->get_name() << "&);" << endl;
@@ -1025,12 +990,6 @@ void t_cpp_generator::generate_struct_declaration(ofstream& out,
out << endl << indent() << "virtual ~" << tstruct->get_name() << "() throw();" << endl;
}
- // Pointer to this structure's reflection local typespec.
- if (gen_dense_) {
- indent(out) << "static ::apache::thrift::reflection::local::TypeSpec* local_reflection;" << endl
- << endl;
- }
-
// Declare all fields
for (m_iter = members.begin(); m_iter != members.end(); ++m_iter) {
indent(out) << declare_field(*m_iter,
@@ -1187,165 +1146,6 @@ void t_cpp_generator::generate_struct_definition(ofstream& out,
}
out << endl;
}
-/**
- * Writes the fingerprint of a struct to either the header or implementation.
- *
- * @param out Output stream
- * @param tstruct The struct
- */
-void t_cpp_generator::generate_struct_fingerprint(ofstream& out,
- t_struct* tstruct,
- bool is_definition) {
- string stat, nspace, comment;
- if (is_definition) {
- stat = "";
- nspace = tstruct->get_name() + "::";
- comment = " ";
- } else {
- stat = "static ";
- nspace = "";
- comment = "; // ";
- }
-
- if (!tstruct->has_fingerprint()) {
- tstruct->generate_fingerprint(); // lazy fingerprint generation
- }
- if (tstruct->has_fingerprint()) {
- out << indent() << stat << "const char* " << nspace << "ascii_fingerprint" << comment << "= \""
- << tstruct->get_ascii_fingerprint() << "\";" << endl << indent() << stat << "const uint8_t "
- << nspace << "binary_fingerprint[" << t_type::fingerprint_len << "]" << comment << "= {";
- const char* comma = "";
- for (int i = 0; i < t_type::fingerprint_len; i++) {
- out << comma << "0x" << t_struct::byte_to_hex(tstruct->get_binary_fingerprint()[i]);
- comma = ",";
- }
- out << "};" << endl << endl;
- }
-}
-
-/**
- * Writes the local reflection of a type (either declaration or definition).
- */
-void t_cpp_generator::generate_local_reflection(std::ofstream& out,
- t_type* ttype,
- bool is_definition) {
- if (!gen_dense_) {
- return;
- }
- ttype = get_true_type(ttype);
- string key = ttype->get_ascii_fingerprint() + (is_definition ? "-defn" : "-decl");
- assert(ttype->has_fingerprint()); // test AFTER get due to lazy fingerprint generation
-
- // Note that we have generated this fingerprint. If we already did, bail out.
- if (!reflected_fingerprints_.insert(key).second) {
- return;
- }
- // Let each program handle its own structures.
- if (ttype->get_program() != NULL && ttype->get_program() != program_) {
- return;
- }
-
- // Do dependencies.
- if (ttype->is_list()) {
- generate_local_reflection(out, ((t_list*)ttype)->get_elem_type(), is_definition);
- } else if (ttype->is_set()) {
- generate_local_reflection(out, ((t_set*)ttype)->get_elem_type(), is_definition);
- } else if (ttype->is_map()) {
- generate_local_reflection(out, ((t_map*)ttype)->get_key_type(), is_definition);
- generate_local_reflection(out, ((t_map*)ttype)->get_val_type(), is_definition);
- } else if (ttype->is_struct() || ttype->is_xception()) {
- // Hacky hacky. For efficiency and convenience, we need a dummy "T_STOP"
- // type at the end of our typespec array. Unfortunately, there is no
- // T_STOP type, so we use the global void type, and special case it when
- // generating its typespec.
-
- const vector<t_field*>& members = ((t_struct*)ttype)->get_sorted_members();
- vector<t_field*>::const_iterator m_iter;
- for (m_iter = members.begin(); m_iter != members.end(); ++m_iter) {
- generate_local_reflection(out, (**m_iter).get_type(), is_definition);
- }
- generate_local_reflection(out, g_type_void, is_definition);
-
- // For definitions of structures, do the arrays of metas and field specs also.
- if (is_definition) {
- out << indent() << "::apache::thrift::reflection::local::FieldMeta" << endl << indent()
- << local_reflection_name("metas", ttype) << "[] = {" << endl;
- indent_up();
- for (m_iter = members.begin(); m_iter != members.end(); ++m_iter) {
- indent(out) << "{ " << (*m_iter)->get_key() << ", "
- << (((*m_iter)->get_req() == t_field::T_OPTIONAL) ? "true" : "false") << " },"
- << endl;
- }
- // Zero for the T_STOP marker.
- indent(out) << "{ 0, false }" << endl << "};" << endl;
- indent_down();
-
- out << indent() << "::apache::thrift::reflection::local::TypeSpec*" << endl << indent()
- << local_reflection_name("specs", ttype) << "[] = {" << endl;
- indent_up();
- for (m_iter = members.begin(); m_iter != members.end(); ++m_iter) {
- indent(out) << "&" << local_reflection_name("typespec", (*m_iter)->get_type(), true) << ","
- << endl;
- }
- indent(out) << "&" << local_reflection_name("typespec", g_type_void) << "," << endl;
- indent_down();
- indent(out) << "};" << endl;
- }
- }
-
- out << indent() << "// " << ttype->get_fingerprint_material() << endl << indent()
- << (is_definition ? "" : "extern ") << "::apache::thrift::reflection::local::TypeSpec" << endl
- << local_reflection_name("typespec", ttype) << (is_definition ? "(" : ";") << endl;
-
- if (!is_definition) {
- out << endl;
- return;
- }
-
- indent_up();
-
- if (ttype->is_void()) {
- indent(out) << "::apache::thrift::protocol::T_STOP";
- } else {
- indent(out) << type_to_enum(ttype);
- }
-
- if (ttype->is_struct()) {
- out << "," << endl << indent() << type_name(ttype) << "::binary_fingerprint," << endl
- << indent() << local_reflection_name("metas", ttype) << "," << endl << indent()
- << local_reflection_name("specs", ttype);
- } else if (ttype->is_list()) {
- out << "," << endl << indent() << "&"
- << local_reflection_name("typespec", ((t_list*)ttype)->get_elem_type(), true) << "," << endl
- << indent() << "NULL";
- } else if (ttype->is_set()) {
- out << "," << endl << indent() << "&"
- << local_reflection_name("typespec", ((t_set*)ttype)->get_elem_type(), true) << "," << endl
- << indent() << "NULL";
- } else if (ttype->is_map()) {
- out << "," << endl << indent() << "&"
- << local_reflection_name("typespec", ((t_map*)ttype)->get_key_type(), true) << "," << endl
- << indent() << "&"
- << local_reflection_name("typespec", ((t_map*)ttype)->get_val_type(), true);
- }
-
- out << ");" << endl << endl;
-
- indent_down();
-}
-
-/**
- * Writes the structure's static pointer to its local reflection typespec
- * into the implementation file.
- */
-void t_cpp_generator::generate_local_reflection_pointer(std::ofstream& out, t_type* ttype) {
- if (!gen_dense_) {
- return;
- }
- indent(out) << "::apache::thrift::reflection::local::TypeSpec* " << ttype->get_name()
- << "::local_reflection = " << endl << indent() << " &"
- << local_reflection_name("typespec", ttype) << ";" << endl << endl;
-}
/**
* Makes a helper function to gen a struct reader.
@@ -4519,47 +4319,6 @@ string t_cpp_generator::type_to_enum(t_type* type) {
throw "INVALID TYPE IN type_to_enum: " + type->get_name();
}
-/**
- * Returns the symbol name of the local reflection of a type.
- */
-string t_cpp_generator::local_reflection_name(const char* prefix, t_type* ttype, bool external) {
- ttype = get_true_type(ttype);
-
- // We have to use the program name as part of the identifier because
- // if two thrift "programs" are compiled into one actual program
- // you would get a symbol collision if they both defined list<i32>.
- // trlo = Thrift Reflection LOcal.
- string prog;
- string name;
- string nspace;
-
- // TODO(dreiss): Would it be better to pregenerate the base types
- // and put them in Thrift.{h,cpp} ?
-
- if (ttype->is_base_type()) {
- prog = program_->get_name();
- name = ttype->get_ascii_fingerprint();
- } else if (ttype->is_enum()) {
- assert(ttype->get_program() != NULL);
- prog = ttype->get_program()->get_name();
- name = ttype->get_ascii_fingerprint();
- } else if (ttype->is_container()) {
- prog = program_->get_name();
- name = ttype->get_ascii_fingerprint();
- } else {
- assert(ttype->is_struct() || ttype->is_xception());
- assert(ttype->get_program() != NULL);
- prog = ttype->get_program()->get_name();
- name = ttype->get_ascii_fingerprint();
- }
-
- if (external && ttype->get_program() != NULL && ttype->get_program() != program_) {
- nspace = namespace_prefix(ttype->get_program()->get_namespace("cpp"));
- }
-
- return nspace + "trlo_" + prefix + "_" + prog + "_" + name;
-}
-
string t_cpp_generator::get_include_prefix(const t_program& program) const {
string include_prefix = program.get_include_prefix();
if (!use_include_prefix_ || (include_prefix.size() > 0 && include_prefix[0] == '/')) {
@@ -4586,6 +4345,5 @@ THRIFT_REGISTER_GENERATOR(
" Omits generation of default operators ==, != and <\n"
" templates: Generate templatized reader/writer methods.\n"
" pure_enums: Generate pure enums instead of wrapper classes.\n"
- " dense: Generate type specifications for the dense protocol.\n"
" include_prefix: Use full include paths in generated files.\n"
" moveable_types: Generate move constructors and assignment operators.\n")
diff --git a/compiler/cpp/src/generate/t_json_generator.cc b/compiler/cpp/src/generate/t_json_generator.cc
index 154a64d87..3f44a8206 100644
--- a/compiler/cpp/src/generate/t_json_generator.cc
+++ b/compiler/cpp/src/generate/t_json_generator.cc
@@ -701,10 +701,8 @@ string t_json_generator::get_type_name(t_type* ttype) {
if (ttype->is_xception()) {
return "exception";
}
- if (ttype->is_base_type() && ((t_base_type*)ttype)->is_binary()) {
- return "binary";
- }
- return ttype->get_fingerprint_material();
+ //if (ttype->is_base_type() && ((t_base_type*)ttype)->is_binary()) {
+ return "binary";
}
string t_json_generator::get_qualified_name(t_type* ttype) {
diff --git a/compiler/cpp/src/main.cc b/compiler/cpp/src/main.cc
index a337cc693..e11d9b04c 100644
--- a/compiler/cpp/src/main.cc
+++ b/compiler/cpp/src/main.cc
@@ -631,43 +631,6 @@ void dump_docstrings(t_program* program) {
}
/**
- * Call generate_fingerprint for every structure and enum.
- */
-void generate_all_fingerprints(t_program* program) {
- const vector<t_struct*>& structs = program->get_structs();
- vector<t_struct*>::const_iterator s_iter;
- for (s_iter = structs.begin(); s_iter != structs.end(); ++s_iter) {
- t_struct* st = *s_iter;
- st->generate_fingerprint();
- }
-
- const vector<t_struct*>& xceptions = program->get_xceptions();
- vector<t_struct*>::const_iterator x_iter;
- for (x_iter = xceptions.begin(); x_iter != xceptions.end(); ++x_iter) {
- t_struct* st = *x_iter;
- st->generate_fingerprint();
- }
-
- const vector<t_enum*>& enums = program->get_enums();
- vector<t_enum*>::const_iterator e_iter;
- for (e_iter = enums.begin(); e_iter != enums.end(); ++e_iter) {
- t_enum* e = *e_iter;
- e->generate_fingerprint();
- }
-
- g_type_void->generate_fingerprint();
-
- // If you want to generate fingerprints for implicit structures, start here.
- /*
- const vector<t_service*>& services = program->get_services();
- vector<t_service*>::const_iterator v_iter;
- for (v_iter = services.begin(); v_iter != services.end(); ++v_iter) {
- t_service* sv = *v_iter;
- }
- */
-}
-
-/**
* Emits a warning on list<byte>, binary type is typically a much better choice.
*/
void check_for_list_of_bytes(t_type* list_elem_type) {
diff --git a/compiler/cpp/src/parse/parse.cc b/compiler/cpp/src/parse/parse.cc
index 7f94bab0a..b22ee5281 100644
--- a/compiler/cpp/src/parse/parse.cc
+++ b/compiler/cpp/src/parse/parse.cc
@@ -20,20 +20,8 @@
#include "t_type.h"
#include "t_typedef.h"
-#include "md5.h"
#include "main.h"
-void t_type::generate_fingerprint() {
- if (!has_fingerprint()) {
- pdebug("generating fingerprint for %s", get_name().c_str());
- std::string material = get_fingerprint_material();
- md5_state_t ctx;
- md5_init(&ctx);
- md5_append(&ctx, (md5_byte_t*)(material.data()), (int)material.size());
- md5_finish(&ctx, (md5_byte_t*)fingerprint_);
- }
-}
-
t_type* t_type::get_true_type() {
t_type* type = this;
while (type->is_typedef()) {
diff --git a/compiler/cpp/src/parse/t_base_type.h b/compiler/cpp/src/parse/t_base_type.h
index 34ff9616c..9be1f803b 100644
--- a/compiler/cpp/src/parse/t_base_type.h
+++ b/compiler/cpp/src/parse/t_base_type.h
@@ -73,14 +73,6 @@ public:
bool is_base_type() const { return true; }
- virtual std::string get_fingerprint_material() const {
- std::string rv = t_base_name(base_);
- if (rv == "(unknown)") {
- throw "BUG: Can't get fingerprint material for this base type.";
- }
- return rv;
- }
-
static std::string t_base_name(t_base tbase) {
switch (tbase) {
case TYPE_VOID:
diff --git a/compiler/cpp/src/parse/t_field.h b/compiler/cpp/src/parse/t_field.h
index c4e30e37d..eece7bb14 100644
--- a/compiler/cpp/src/parse/t_field.h
+++ b/compiler/cpp/src/parse/t_field.h
@@ -86,15 +86,6 @@ public:
t_struct* get_xsd_attrs() { return xsd_attrs_; }
- // This is not the same function as t_type::get_fingerprint_material,
- // but it does the same thing.
- std::string get_fingerprint_material() const {
- std::ostringstream keystm;
- keystm << key_;
- return keystm.str() + ":" + ((req_ == T_OPTIONAL) ? "opt-" : "")
- + type_->get_fingerprint_material();
- }
-
/**
* Comparator to sort fields in ascending order by key.
* Make this a functor instead of a function to help GCC inline it.
diff --git a/compiler/cpp/src/parse/t_list.h b/compiler/cpp/src/parse/t_list.h
index e121d1d51..ac0d98152 100644
--- a/compiler/cpp/src/parse/t_list.h
+++ b/compiler/cpp/src/parse/t_list.h
@@ -34,15 +34,6 @@ public:
bool is_list() const { return true; }
- virtual std::string get_fingerprint_material() const {
- return "list<" + elem_type_->get_fingerprint_material() + ">";
- }
-
- virtual void generate_fingerprint() {
- t_type::generate_fingerprint();
- elem_type_->generate_fingerprint();
- }
-
private:
t_type* elem_type_;
};
diff --git a/compiler/cpp/src/parse/t_map.h b/compiler/cpp/src/parse/t_map.h
index 479514756..269aeab58 100644
--- a/compiler/cpp/src/parse/t_map.h
+++ b/compiler/cpp/src/parse/t_map.h
@@ -37,17 +37,6 @@ public:
bool is_map() const { return true; }
- virtual std::string get_fingerprint_material() const {
- return "map<" + key_type_->get_fingerprint_material() + ","
- + val_type_->get_fingerprint_material() + ">";
- }
-
- virtual void generate_fingerprint() {
- t_type::generate_fingerprint();
- key_type_->generate_fingerprint();
- val_type_->generate_fingerprint();
- }
-
private:
t_type* key_type_;
t_type* val_type_;
diff --git a/compiler/cpp/src/parse/t_service.h b/compiler/cpp/src/parse/t_service.h
index 1f499724f..2b01f9c45 100644
--- a/compiler/cpp/src/parse/t_service.h
+++ b/compiler/cpp/src/parse/t_service.h
@@ -51,11 +51,6 @@ public:
t_service* get_extends() { return extends_; }
- virtual std::string get_fingerprint_material() const {
- // Services should never be used in fingerprints.
- throw "BUG: Can't get fingerprint material for service.";
- }
-
private:
std::vector<t_function*> functions_;
t_service* extends_;
diff --git a/compiler/cpp/src/parse/t_set.h b/compiler/cpp/src/parse/t_set.h
index ccfc7013a..8a4648050 100644
--- a/compiler/cpp/src/parse/t_set.h
+++ b/compiler/cpp/src/parse/t_set.h
@@ -34,15 +34,6 @@ public:
bool is_set() const { return true; }
- virtual std::string get_fingerprint_material() const {
- return "set<" + elem_type_->get_fingerprint_material() + ">";
- }
-
- virtual void generate_fingerprint() {
- t_type::generate_fingerprint();
- elem_type_->generate_fingerprint();
- }
-
private:
t_type* elem_type_;
};
diff --git a/compiler/cpp/src/parse/t_struct.h b/compiler/cpp/src/parse/t_struct.h
index 228267673..93cb08966 100644
--- a/compiler/cpp/src/parse/t_struct.h
+++ b/compiler/cpp/src/parse/t_struct.h
@@ -133,33 +133,6 @@ public:
bool is_union() const { return is_union_; }
- virtual std::string get_fingerprint_material() const {
- std::string rv = "{";
- bool do_reserve = (members_in_id_order_.size() > 1);
- size_t estimation = 0;
- members_type::const_iterator m_iter;
- for (m_iter = members_in_id_order_.begin(); m_iter != members_in_id_order_.end(); ++m_iter) {
- rv += (*m_iter)->get_fingerprint_material();
- rv += ";";
-
- if (do_reserve) {
- estimation = members_in_id_order_.size() * rv.size() + 16;
- rv.reserve(estimation);
- do_reserve = false;
- }
- }
- rv += "}";
- return rv;
- }
-
- virtual void generate_fingerprint() {
- t_type::generate_fingerprint();
- members_type::const_iterator m_iter;
- for (m_iter = members_in_id_order_.begin(); m_iter != members_in_id_order_.end(); ++m_iter) {
- (*m_iter)->get_type()->generate_fingerprint();
- }
- }
-
t_field* get_field_by_name(std::string field_name) {
members_type::const_iterator m_iter;
for (m_iter = members_in_id_order_.begin(); m_iter != members_in_id_order_.end(); ++m_iter) {
diff --git a/compiler/cpp/src/parse/t_type.h b/compiler/cpp/src/parse/t_type.h
index 20409f391..416cc6fa3 100644
--- a/compiler/cpp/src/parse/t_type.h
+++ b/compiler/cpp/src/parse/t_type.h
@@ -64,45 +64,6 @@ public:
t_type* get_true_type();
- // Return a string that uniquely identifies this type
- // from any other thrift type in the world, as far as
- // TDenseProtocol is concerned.
- // We don't cache this, which is a little sloppy,
- // but the compiler is so fast that it doesn't really matter.
- virtual std::string get_fingerprint_material() const = 0;
-
- // Fingerprint should change whenever (and only when)
- // the encoding via TDenseProtocol changes.
- static const int fingerprint_len = 16;
-
- // Call this before trying get_*_fingerprint().
- virtual void generate_fingerprint();
-
- bool has_fingerprint() const {
- for (int i = 0; i < fingerprint_len; i++) {
- if (fingerprint_[i] != 0) {
- return true;
- }
- }
- return false;
- }
-
- const uint8_t* get_binary_fingerprint() {
- if (!has_fingerprint()) // lazy fingerprint generation, right now only used with the c++
- // generator
- generate_fingerprint();
- return fingerprint_;
- }
-
- std::string get_ascii_fingerprint() {
- std::string rv;
- const uint8_t* fp = get_binary_fingerprint();
- for (int i = 0; i < fingerprint_len; i++) {
- rv += byte_to_hex(fp[i]);
- }
- return rv;
- }
-
// This function will break (maybe badly) unless 0 <= num <= 16.
static char nybble_to_xdigit(int num) {
if (num < 10) {
@@ -122,22 +83,16 @@ public:
std::map<std::string, std::string> annotations_;
protected:
- t_type() : program_(NULL) { memset(fingerprint_, 0, sizeof(fingerprint_)); }
+ t_type() : program_(NULL) { ; }
- t_type(t_program* program) : program_(program) { memset(fingerprint_, 0, sizeof(fingerprint_)); }
+ t_type(t_program* program) : program_(program) { ; }
- t_type(t_program* program, std::string name) : program_(program), name_(name) {
- memset(fingerprint_, 0, sizeof(fingerprint_));
- }
+ t_type(t_program* program, std::string name) : program_(program), name_(name) { ; }
- t_type(std::string name) : program_(NULL), name_(name) {
- memset(fingerprint_, 0, sizeof(fingerprint_));
- }
+ t_type(std::string name) : program_(NULL), name_(name) { ; }
t_program* program_;
std::string name_;
-
- uint8_t fingerprint_[fingerprint_len];
};
/**
diff --git a/compiler/cpp/src/parse/t_typedef.h b/compiler/cpp/src/parse/t_typedef.h
index 105190929..a39a246d2 100644
--- a/compiler/cpp/src/parse/t_typedef.h
+++ b/compiler/cpp/src/parse/t_typedef.h
@@ -57,23 +57,6 @@ public:
bool is_typedef() const { return true; }
- virtual std::string get_fingerprint_material() const {
- if (!seen_) {
- seen_ = true;
- std::string ret = get_type()->get_fingerprint_material();
- seen_ = false;
- return ret;
- }
- return "";
- }
-
- virtual void generate_fingerprint() {
- t_type::generate_fingerprint();
- if (!get_type()->has_fingerprint()) {
- get_type()->generate_fingerprint();
- }
- }
-
private:
t_type* type_;
std::string symbolic_;
diff --git a/lib/cpp/CMakeLists.txt b/lib/cpp/CMakeLists.txt
index d6107bc34..4c7caebad 100755
--- a/lib/cpp/CMakeLists.txt
+++ b/lib/cpp/CMakeLists.txt
@@ -43,7 +43,6 @@ set( thriftcpp_SOURCES
src/thrift/processor/PeekProcessor.cpp
src/thrift/protocol/TBase64Utils.cpp
src/thrift/protocol/TDebugProtocol.cpp
- src/thrift/protocol/TDenseProtocol.cpp
src/thrift/protocol/TJSONProtocol.cpp
src/thrift/protocol/TMultiplexedProtocol.cpp
src/thrift/protocol/TProtocol.cpp
diff --git a/lib/cpp/Makefile.am b/lib/cpp/Makefile.am
index 7f2d4315a..4e5cde7f4 100755
--- a/lib/cpp/Makefile.am
+++ b/lib/cpp/Makefile.am
@@ -72,7 +72,6 @@ libthrift_la_SOURCES = src/thrift/TApplicationException.cpp \
src/thrift/concurrency/Util.cpp \
src/thrift/processor/PeekProcessor.cpp \
src/thrift/protocol/TDebugProtocol.cpp \
- src/thrift/protocol/TDenseProtocol.cpp \
src/thrift/protocol/TJSONProtocol.cpp \
src/thrift/protocol/TBase64Utils.cpp \
src/thrift/protocol/TMultiplexedProtocol.cpp \
@@ -153,7 +152,6 @@ include_thrift_HEADERS = \
src/thrift/TDispatchProcessor.h \
src/thrift/Thrift.h \
src/thrift/TOutput.h \
- src/thrift/TReflectionLocal.h \
src/thrift/TProcessor.h \
src/thrift/TApplicationException.h \
src/thrift/TLogging.h \
@@ -184,7 +182,6 @@ include_protocol_HEADERS = \
src/thrift/protocol/TBinaryProtocol.tcc \
src/thrift/protocol/TCompactProtocol.h \
src/thrift/protocol/TCompactProtocol.tcc \
- src/thrift/protocol/TDenseProtocol.h \
src/thrift/protocol/TDebugProtocol.h \
src/thrift/protocol/TBase64Utils.h \
src/thrift/protocol/TJSONProtocol.h \
diff --git a/lib/cpp/libthrift.vcxproj b/lib/cpp/libthrift.vcxproj
index 1fc08b883..b4f1c501c 100644
--- a/lib/cpp/libthrift.vcxproj
+++ b/lib/cpp/libthrift.vcxproj
@@ -46,7 +46,6 @@
<ClCompile Include="src\thrift\processor\PeekProcessor.cpp"/>
<ClCompile Include="src\thrift\protocol\TBase64Utils.cpp" />
<ClCompile Include="src\thrift\protocol\TDebugProtocol.cpp"/>
- <ClCompile Include="src\thrift\protocol\TDenseProtocol.cpp"/>
<ClCompile Include="src\thrift\protocol\TJSONProtocol.cpp"/>
<ClCompile Include="src\thrift\protocol\TMultiplexedProtocol.cpp"/>
<ClCompile Include="src\thrift\server\TSimpleServer.cpp"/>
@@ -84,7 +83,6 @@
<ClInclude Include="src\thrift\processor\TMultiplexedProcessor.h" />
<ClInclude Include="src\thrift\protocol\TBinaryProtocol.h" />
<ClInclude Include="src\thrift\protocol\TDebugProtocol.h" />
- <ClInclude Include="src\thrift\protocol\TDenseProtocol.h" />
<ClInclude Include="src\thrift\protocol\TJSONProtocol.h" />
<ClInclude Include="src\thrift\protocol\TMultiplexedProtocol.h" />
<ClInclude Include="src\thrift\protocol\TProtocol.h" />
diff --git a/lib/cpp/libthrift.vcxproj.filters b/lib/cpp/libthrift.vcxproj.filters
index 4effa8729..ec21886f6 100644
--- a/lib/cpp/libthrift.vcxproj.filters
+++ b/lib/cpp/libthrift.vcxproj.filters
@@ -27,9 +27,6 @@
<ClCompile Include="src\thrift\protocol\TDebugProtocol.cpp">
<Filter>protocol</Filter>
</ClCompile>
- <ClCompile Include="src\thrift\protocol\TDenseProtocol.cpp">
- <Filter>protocol</Filter>
- </ClCompile>
<ClCompile Include="src\thrift\protocol\TBase64Utils.cpp">
<Filter>protocol</Filter>
</ClCompile>
@@ -206,9 +203,6 @@
<ClInclude Include="src\thrift\protocol\TMultiplexedProtocol.h">
<Filter>protocol</Filter>
</ClInclude>
- <ClInclude Include="src\thrift\protocol\TDenseProtocol.h">
- <Filter>protocol</Filter>
- </ClInclude>
<ClInclude Include="src\thrift\protocol\TDebugProtocol.h">
<Filter>protocol</Filter>
</ClInclude>
@@ -280,4 +274,4 @@
<Filter>windows\tr1</Filter>
</None>
</ItemGroup>
-</Project> \ No newline at end of file
+</Project>
diff --git a/lib/cpp/src/thrift/TReflectionLocal.h b/lib/cpp/src/thrift/TReflectionLocal.h
deleted file mode 100644
index 2fc53c882..000000000
--- a/lib/cpp/src/thrift/TReflectionLocal.h
+++ /dev/null
@@ -1,92 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements. See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership. The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License. You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing,
- * software distributed under the License is distributed on an
- * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- * KIND, either express or implied. See the License for the
- * specific language governing permissions and limitations
- * under the License.
- */
-
-#ifndef _THRIFT_TREFLECTIONLOCAL_H_
-#define _THRIFT_TREFLECTIONLOCAL_H_ 1
-
-#include <stdint.h>
-#include <cstring>
-#include <thrift/protocol/TProtocol.h>
-
-/**
- * Local Reflection is a blanket term referring to the the structure
- * and generation of this particular representation of Thrift types.
- * (It is called local because it cannot be serialized by Thrift).
- *
- */
-
-namespace apache {
-namespace thrift {
-namespace reflection {
-namespace local {
-
-using apache::thrift::protocol::TType;
-
-// We include this many bytes of the structure's fingerprint when serializing
-// a top-level structure. Long enough to make collisions unlikely, short
-// enough to not significantly affect the amount of memory used.
-const int FP_PREFIX_LEN = 4;
-
-struct FieldMeta {
- int16_t tag;
- bool is_optional;
-};
-
-struct TypeSpec {
- TType ttype;
- uint8_t fp_prefix[FP_PREFIX_LEN];
-
- // Use an anonymous union here so we can fit two TypeSpecs in one cache line.
- union {
- struct {
- // Use parallel arrays here for denser packing (of the arrays).
- FieldMeta* metas;
- TypeSpec** specs;
- } tstruct;
- struct {
- TypeSpec* subtype1;
- TypeSpec* subtype2;
- } tcontainer;
- };
-
- // Static initialization of unions isn't really possible,
- // so take the plunge and use constructors.
- // Hopefully they'll be evaluated at compile time.
-
- TypeSpec(TType ttype) : ttype(ttype) { std::memset(fp_prefix, 0, FP_PREFIX_LEN); }
-
- TypeSpec(TType ttype, const uint8_t* fingerprint, FieldMeta* metas, TypeSpec** specs)
- : ttype(ttype) {
- std::memcpy(fp_prefix, fingerprint, FP_PREFIX_LEN);
- tstruct.metas = metas;
- tstruct.specs = specs;
- }
-
- TypeSpec(TType ttype, TypeSpec* subtype1, TypeSpec* subtype2) : ttype(ttype) {
- std::memset(fp_prefix, 0, FP_PREFIX_LEN);
- tcontainer.subtype1 = subtype1;
- tcontainer.subtype2 = subtype2;
- }
-};
-}
-}
-}
-} // apache::thrift::reflection::local
-
-#endif // #ifndef _THRIFT_TREFLECTIONLOCAL_H_
diff --git a/lib/cpp/src/thrift/Thrift.h b/lib/cpp/src/thrift/Thrift.h
index 962b921ac..e8e70eba0 100644
--- a/lib/cpp/src/thrift/Thrift.h
+++ b/lib/cpp/src/thrift/Thrift.h
@@ -96,13 +96,6 @@ protected:
std::string message_;
};
-// Forward declare this structure used by TDenseProtocol
-namespace reflection {
-namespace local {
-struct TypeSpec;
-}
-}
-
class TDelayedException {
public:
template <class E>
diff --git a/lib/cpp/src/thrift/protocol/TBinaryProtocol.h b/lib/cpp/src/thrift/protocol/TBinaryProtocol.h
index 7291988c5..e0650cf67 100644
--- a/lib/cpp/src/thrift/protocol/TBinaryProtocol.h
+++ b/lib/cpp/src/thrift/protocol/TBinaryProtocol.h
@@ -39,7 +39,7 @@ class TBinaryProtocolT : public TVirtualProtocol<TBinaryProtocolT<Transport_, By
protected:
static const int32_t VERSION_MASK = ((int32_t)0xffff0000);
static const int32_t VERSION_1 = ((int32_t)0x80010000);
- // VERSION_2 (0x80020000) is taken by TDenseProtocol.
+ // VERSION_2 (0x80020000) was taken by TDenseProtocol (which has since been removed)
public:
TBinaryProtocolT(boost::shared_ptr<Transport_> trans)
diff --git a/lib/cpp/src/thrift/protocol/TDenseProtocol.cpp b/lib/cpp/src/thrift/protocol/TDenseProtocol.cpp
deleted file mode 100644
index 259c68e8a..000000000
--- a/lib/cpp/src/thrift/protocol/TDenseProtocol.cpp
+++ /dev/null
@@ -1,753 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements. See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership. The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License. You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing,
- * software distributed under the License is distributed on an
- * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- * KIND, either express or implied. See the License for the
- * specific language governing permissions and limitations
- * under the License.
- */
-
-/*
-
-IMPLEMENTATION DETAILS
-
-TDenseProtocol was designed to have a smaller serialized form than
-TBinaryProtocol. This is accomplished using two techniques. The first is
-variable-length integer encoding. We use the same technique that the Standard
-MIDI File format uses for "variable-length quantities"
-(http://en.wikipedia.org/wiki/Variable-length_quantity).
-All integers (including i16, but not byte) are first cast to uint64_t,
-then written out as variable-length quantities. This has the unfortunate side
-effect that all negative numbers require 10 bytes, but negative numbers tend
-to be far less common than positive ones.
-
-The second technique eliminating the field ids used by TBinaryProtocol. This
-decision required support from the Thrift compiler and also sacrifices some of
-the backward and forward compatibility of TBinaryProtocol.
-
-We considered implementing this technique by generating separate readers and
-writers for the dense protocol (this is how Pillar, Thrift's predecessor,
-worked), but this idea had a few problems:
-- Our abstractions go out the window.
-- We would have to maintain a second code generator.
-- Preserving compatibility with old versions of the structures would be a
- nightmare.
-
-Therefore, we chose an alternate implementation that stored the description of
-the data neither in the data itself (like TBinaryProtocol) nor in the
-serialization code (like Pillar), but instead in a separate data structure,
-called a TypeSpec. TypeSpecs are generated by the Thrift compiler
-(specifically in the t_cpp_generator), and their structure should be
-documented there (TODO(dreiss): s/should be/is/).
-
-We maintain a stack of TypeSpecs within the protocol so it knows where the
-generated code is in the reading/writing process. For example, if we are
-writing an i32 contained in a struct bar, contained in a struct foo, then the
-stack would look like: TOP , i32 , struct bar , struct foo , BOTTOM.
-The following invariant: whenever we are about to read/write an object
-(structBegin, containerBegin, or a scalar), the TypeSpec on the top of the
-stack must match the type being read/written. The main reasons that this
-invariant must be maintained is that if we ever start reading a structure, we
-must have its exact TypeSpec in order to pass the right tags to the
-deserializer.
-
-We use the following strategies for maintaining this invariant:
-
-- For structures, we have a separate stack of indexes, one for each structure
- on the TypeSpec stack. These are indexes into the list of fields in the
- structure's TypeSpec. When we {read,write}FieldBegin, we push on the
- TypeSpec for the field.
-- When we begin writing a list or set, we push on the TypeSpec for the
- element type.
-- For maps, we have a separate stack of booleans, one for each map on the
- TypeSpec stack. The boolean is true if we are writing the key for that
- map, and false if we are writing the value. Maps are the trickiest case
- because the generated code does not call any protocol method between
- the key and the value. As a result, we potentially have to switch
- between map key state and map value state after reading/writing any object.
-- This job is handled by the stateTransition method. It is called after
- reading/writing every object. It pops the current TypeSpec off the stack,
- then optionally pushes a new one on, depending on what the next TypeSpec is.
- If it is a struct, the job is left to the next writeFieldBegin. If it is a
- set or list, the just-popped typespec is pushed back on. If it is a map,
- the top of the key/value stack is toggled, and the appropriate TypeSpec
- is pushed.
-
-Optional fields are a little tricky also. We write a zero byte if they are
-absent and prefix them with an 0x01 byte if they are present
-*/
-
-#include <stdint.h>
-#include <thrift/protocol/TDenseProtocol.h>
-#include <thrift/TReflectionLocal.h>
-
-// Leaving this on for now. Disabling it will turn off asserts, which should
-// give a performance boost. When we have *really* thorough test cases,
-// we should drop this.
-#define DEBUG_TDENSEPROTOCOL
-
-// NOTE: Assertions should *only* be used to detect bugs in code,
-// either in TDenseProtocol itself, or in code using it.
-// (For example, using the wrong TypeSpec.)
-// Invalid data should NEVER cause an assertion failure,
-// no matter how grossly corrupted, nor how ingeniously crafted.
-#ifdef DEBUG_TDENSEPROTOCOL
-#undef NDEBUG
-#else
-#define NDEBUG
-#endif
-#include <cassert>
-
-using std::string;
-
-#ifdef __GNUC__
-#define UNLIKELY(val) (__builtin_expect((val), 0))
-#else
-#define UNLIKELY(val) (val)
-#endif
-
-namespace apache {
-namespace thrift {
-namespace protocol {
-
-const int TDenseProtocol::FP_PREFIX_LEN = apache::thrift::reflection::local::FP_PREFIX_LEN;
-
-// Top TypeSpec. TypeSpec of the structure being encoded.
-#define TTS (ts_stack_.back()) // type = TypeSpec*
-// InDeX. Index into TTS of the current/next field to encode.
-#define IDX (idx_stack_.back()) // type = int
-// Field TypeSpec. TypeSpec of the current/next field to encode.
-#define FTS (TTS->tstruct.specs[IDX]) // type = TypeSpec*
-// Field MeTa. Metadata of the current/next field to encode.
-#define FMT (TTS->tstruct.metas[IDX]) // type = FieldMeta
-// SubType 1/2. TypeSpec of the first/second subtype of this container.
-#define ST1 (TTS->tcontainer.subtype1)
-#define ST2 (TTS->tcontainer.subtype2)
-
-/**
- * Checks that @c ttype is indeed the ttype that we should be writing,
- * according to our typespec. Aborts if the test fails and debugging in on.
- */
-inline void TDenseProtocol::checkTType(const TType ttype) {
- assert(!ts_stack_.empty());
- assert(TTS->ttype == ttype);
-}
-
-/**
- * Makes sure that the TypeSpec stack is correct for the next object.
- * See top-of-file comments.
- */
-inline void TDenseProtocol::stateTransition() {
- TypeSpec* old_tts = ts_stack_.back();
- ts_stack_.pop_back();
-
- // If this is the end of the top-level write, we should have just popped
- // the TypeSpec passed to the constructor.
- if (ts_stack_.empty()) {
- assert(old_tts == type_spec_);
- return;
- }
-
- switch (TTS->ttype) {
-
- case T_STRUCT:
- assert(old_tts == FTS);
- break;
-
- case T_LIST:
- case T_SET:
- assert(old_tts == ST1);
- ts_stack_.push_back(old_tts);
- break;
-
- case T_MAP:
- assert(old_tts == (mkv_stack_.back() ? ST1 : ST2));
- mkv_stack_.back() = !mkv_stack_.back();
- ts_stack_.push_back(mkv_stack_.back() ? ST1 : ST2);
- break;
-
- default:
- assert(!"Invalid TType in stateTransition.");
- break;
- }
-}
-
-/*
- * Variable-length quantity functions.
- */
-
-inline uint32_t TDenseProtocol::vlqRead(uint64_t& vlq) {
- uint32_t used = 0;
- uint64_t val = 0;
- uint8_t buf[10]; // 64 bits / (7 bits/byte) = 10 bytes.
- uint32_t buf_size = sizeof(buf);
- const uint8_t* borrowed = trans_->borrow(buf, &buf_size);
-
- // Fast path. TODO(dreiss): Make it faster.
- if (borrowed != NULL) {
- while (true) {
- uint8_t byte = borrowed[used];
- used++;
- val = (val << 7) | (byte & 0x7f);
- if (!(byte & 0x80)) {
- vlq = val;
- trans_->consume(used);
- return used;
- }
- // Have to check for invalid data so we don't crash.
- if (UNLIKELY(used == sizeof(buf))) {
- resetState();
- throw TProtocolException(TProtocolException::INVALID_DATA,
- "Variable-length int over 10 bytes.");
- }
- }
- }
-
- // Slow path.
- else {
- while (true) {
- uint8_t byte;
- used += trans_->readAll(&byte, 1);
- val = (val << 7) | (byte & 0x7f);
- if (!(byte & 0x80)) {
- vlq = val;
- return used;
- }
- // Might as well check for invalid data on the slow path too.
- if (UNLIKELY(used >= sizeof(buf))) {
- resetState();
- throw TProtocolException(TProtocolException::INVALID_DATA,
- "Variable-length int over 10 bytes.");
- }
- }
- }
-}
-
-inline uint32_t TDenseProtocol::vlqWrite(uint64_t vlq) {
- uint8_t buf[10]; // 64 bits / (7 bits/byte) = 10 bytes.
- int32_t pos = sizeof(buf) - 1;
-
- // Write the thing from back to front.
- buf[pos] = vlq & 0x7f;
- vlq >>= 7;
- pos--;
-
- while (vlq > 0) {
- assert(pos >= 0);
- buf[pos] = static_cast<uint8_t>(vlq | 0x80);
- vlq >>= 7;
- pos--;
- }
-
- // Back up one step before writing.
- pos++;
-
- trans_->write(buf + pos, static_cast<uint32_t>(sizeof(buf) - pos));
- return static_cast<uint32_t>(sizeof(buf) - pos);
-}
-
-/*
- * Writing functions.
- */
-
-uint32_t TDenseProtocol::writeMessageBegin(const std::string& name,
- const TMessageType messageType,
- const int32_t seqid) {
- throw TException("TDenseProtocol doesn't work with messages (yet).");
-
- int32_t version = (VERSION_2) | ((int32_t)messageType);
- uint32_t wsize = 0;
- wsize += subWriteI32(version);
- wsize += subWriteString(name);
- wsize += subWriteI32(seqid);
- return wsize;
-}
-
-uint32_t TDenseProtocol::writeMessageEnd() {
- return 0;
-}
-
-uint32_t TDenseProtocol::writeStructBegin(const char* name) {
- (void)name;
- uint32_t xfer = 0;
-
- // The TypeSpec stack should be empty if this is the top-level read/write.
- // If it is, we push the TypeSpec passed to the constructor.
- if (ts_stack_.empty()) {
- assert(standalone_);
-
- if (type_spec_ == NULL) {
- resetState();
- throw TException("TDenseProtocol: No type specified.");
- } else {
- assert(type_spec_->ttype == T_STRUCT);
- ts_stack_.push_back(type_spec_);
- // Write out a prefix of the structure fingerprint.
- trans_->write(type_spec_->fp_prefix, FP_PREFIX_LEN);
- xfer += FP_PREFIX_LEN;
- }
- }
-
- // We need a new field index for this structure.
- idx_stack_.push_back(0);
- return 0;
-}
-
-uint32_t TDenseProtocol::writeStructEnd() {
- idx_stack_.pop_back();
- stateTransition();
- return 0;
-}
-
-uint32_t TDenseProtocol::writeFieldBegin(const char* name,
- const TType fieldType,
- const int16_t fieldId) {
- (void)name;
- uint32_t xfer = 0;
-
- // Skip over optional fields.
- while (FMT.tag != fieldId) {
- // TODO(dreiss): Old meta here.
- assert(FTS->ttype != T_STOP);
- assert(FMT.is_optional);
- // Write a zero byte so the reader can skip it.
- xfer += subWriteBool(false);
- // And advance to the next field.
- IDX++;
- }
-
- // TODO(dreiss): give a better exception.
- assert(FTS->ttype == fieldType);
-
- if (FMT.is_optional) {
- subWriteBool(true);
- xfer += 1;
- }
-
- // writeFieldStop shares all lot of logic up to this point.
- // Instead of replicating it all, we just call this method from that one
- // and use a gross special case here.
- if (UNLIKELY(FTS->ttype != T_STOP)) {
- // For normal fields, push the TypeSpec that we're about to use.
- ts_stack_.push_back(FTS);
- }
- return xfer;
-}
-
-uint32_t TDenseProtocol::writeFieldEnd() {
- // Just move on to the next field.
- IDX++;
- return 0;
-}
-
-uint32_t TDenseProtocol::writeFieldStop() {
- return TDenseProtocol::writeFieldBegin("", T_STOP, 0);
-}
-
-uint32_t TDenseProtocol::writeMapBegin(const TType keyType,
- const TType valType,
- const uint32_t size) {
- checkTType(T_MAP);
-
- assert(keyType == ST1->ttype);
- assert(valType == ST2->ttype);
-
- ts_stack_.push_back(ST1);
- mkv_stack_.push_back(true);
-
- return subWriteI32((int32_t)size);
-}
-
-uint32_t TDenseProtocol::writeMapEnd() {
- // Pop off the value type, as well as our entry in the map key/value stack.
- // stateTransition takes care of popping off our TypeSpec.
- ts_stack_.pop_back();
- mkv_stack_.pop_back();
- stateTransition();
- return 0;
-}
-
-uint32_t TDenseProtocol::writeListBegin(const TType elemType, const uint32_t size) {
- checkTType(T_LIST);
-
- assert(elemType == ST1->ttype);
- ts_stack_.push_back(ST1);
- return subWriteI32((int32_t)size);
-}
-
-uint32_t TDenseProtocol::writeListEnd() {
- // Pop off the element type. stateTransition takes care of popping off ours.
- ts_stack_.pop_back();
- stateTransition();
- return 0;
-}
-
-uint32_t TDenseProtocol::writeSetBegin(const TType elemType, const uint32_t size) {
- checkTType(T_SET);
-
- assert(elemType == ST1->ttype);
- ts_stack_.push_back(ST1);
- return subWriteI32((int32_t)size);
-}
-
-uint32_t TDenseProtocol::writeSetEnd() {
- // Pop off the element type. stateTransition takes care of popping off ours.
- ts_stack_.pop_back();
- stateTransition();
- return 0;
-}
-
-uint32_t TDenseProtocol::writeBool(const bool value) {
- checkTType(T_BOOL);
- stateTransition();
- return TBinaryProtocol::writeBool(value);
-}
-
-uint32_t TDenseProtocol::writeByte(const int8_t byte) {
- checkTType(T_BYTE);
- stateTransition();
- return TBinaryProtocol::writeByte(byte);
-}
-
-uint32_t TDenseProtocol::writeI16(const int16_t i16) {
- checkTType(T_I16);
- stateTransition();
- return vlqWrite(i16);
-}
-
-uint32_t TDenseProtocol::writeI32(const int32_t i32) {
- checkTType(T_I32);
- stateTransition();
- return vlqWrite(i32);
-}
-
-uint32_t TDenseProtocol::writeI64(const int64_t i64) {
- checkTType(T_I64);
- stateTransition();
- return vlqWrite(i64);
-}
-
-uint32_t TDenseProtocol::writeDouble(const double dub) {
- checkTType(T_DOUBLE);
- stateTransition();
- return TBinaryProtocol::writeDouble(dub);
-}
-
-uint32_t TDenseProtocol::writeString(const std::string& str) {
- checkTType(T_STRING);
- stateTransition();
- return subWriteString(str);
-}
-
-uint32_t TDenseProtocol::writeBinary(const std::string& str) {
- return TDenseProtocol::writeString(str);
-}
-
-inline uint32_t TDenseProtocol::subWriteI32(const int32_t i32) {
- return vlqWrite(i32);
-}
-
-uint32_t TDenseProtocol::subWriteString(const std::string& str) {
- if (str.size() > static_cast<size_t>((std::numeric_limits<int32_t>::max)()))
- throw TProtocolException(TProtocolException::SIZE_LIMIT);
- uint32_t size = static_cast<uint32_t>(str.size());
- uint32_t xfer = subWriteI32((int32_t)size);
- if (size > 0) {
- trans_->write((uint8_t*)str.data(), size);
- }
- return xfer + size;
-}
-
-/*
- * Reading functions
- *
- * These have a lot of the same logic as the writing functions, so if
- * something is confusing, look for comments in the corresponding writer.
- */
-
-uint32_t TDenseProtocol::readMessageBegin(std::string& name,
- TMessageType& messageType,
- int32_t& seqid) {
- throw TException("TDenseProtocol doesn't work with messages (yet).");
-
- uint32_t xfer = 0;
- int32_t sz;
- xfer += subReadI32(sz);
-
- if (sz < 0) {
- // Check for correct version number
- int32_t version = sz & VERSION_MASK;
- if (version != VERSION_2) {
- throw TProtocolException(TProtocolException::BAD_VERSION, "Bad version identifier");
- }
- messageType = (TMessageType)(sz & 0x000000ff);
- xfer += subReadString(name);
- xfer += subReadI32(seqid);
- } else {
- throw TProtocolException(TProtocolException::BAD_VERSION,
- "No version identifier... old protocol client in strict mode?");
- }
- return xfer;
-}
-
-uint32_t TDenseProtocol::readMessageEnd() {
- return 0;
-}
-
-uint32_t TDenseProtocol::readStructBegin(string& name) {
- (void)name;
- uint32_t xfer = 0;
-
- if (ts_stack_.empty()) {
- assert(standalone_);
-
- if (type_spec_ == NULL) {
- resetState();
- throw TException("TDenseProtocol: No type specified.");
- } else {
- assert(type_spec_->ttype == T_STRUCT);
- ts_stack_.push_back(type_spec_);
-
- // Check the fingerprint prefix.
- uint8_t buf[FP_PREFIX_LEN];
- xfer += trans_->read(buf, FP_PREFIX_LEN);
- if (std::memcmp(buf, type_spec_->fp_prefix, FP_PREFIX_LEN) != 0) {
- resetState();
- throw TProtocolException(TProtocolException::INVALID_DATA,
- "Fingerprint in data does not match type_spec.");
- }
- }
- }
-
- // We need a new field index for this structure.
- idx_stack_.push_back(0);
- return 0;
-}
-
-uint32_t TDenseProtocol::readStructEnd() {
- idx_stack_.pop_back();
- stateTransition();
- return 0;
-}
-
-uint32_t TDenseProtocol::readFieldBegin(string& name, TType& fieldType, int16_t& fieldId) {
- (void)name;
- uint32_t xfer = 0;
-
- // For optional fields, check to see if they are there.
- while (FMT.is_optional) {
- bool is_present;
- xfer += subReadBool(is_present);
- if (is_present) {
- break;
- }
- IDX++;
- }
-
- // Once we hit a mandatory field, or an optional field that is present,
- // we know that FMT and FTS point to the appropriate field.
-
- fieldId = FMT.tag;
- fieldType = FTS->ttype;
-
- // Normally, we push the TypeSpec that we are about to read,
- // but no reading is done for T_STOP.
- if (FTS->ttype != T_STOP) {
- ts_stack_.push_back(FTS);
- }
- return xfer;
-}
-
-uint32_t TDenseProtocol::readFieldEnd() {
- IDX++;
- return 0;
-}
-
-uint32_t TDenseProtocol::readMapBegin(TType& keyType, TType& valType, uint32_t& size) {
- checkTType(T_MAP);
-
- uint32_t xfer = 0;
- int32_t sizei;
- xfer += subReadI32(sizei);
- if (sizei < 0) {
- resetState();
- throw TProtocolException(TProtocolException::NEGATIVE_SIZE);
- } else if (container_limit_ && sizei > container_limit_) {
- resetState();
- throw TProtocolException(TProtocolException::SIZE_LIMIT);
- }
- size = (uint32_t)sizei;
-
- keyType = ST1->ttype;
- valType = ST2->ttype;
-
- ts_stack_.push_back(ST1);
- mkv_stack_.push_back(true);
-
- return xfer;
-}
-
-uint32_t TDenseProtocol::readMapEnd() {
- ts_stack_.pop_back();
- mkv_stack_.pop_back();
- stateTransition();
- return 0;
-}
-
-uint32_t TDenseProtocol::readListBegin(TType& elemType, uint32_t& size) {
- checkTType(T_LIST);
-
- uint32_t xfer = 0;
- int32_t sizei;
- xfer += subReadI32(sizei);
- if (sizei < 0) {
- resetState();
- throw TProtocolException(TProtocolException::NEGATIVE_SIZE);
- } else if (container_limit_ && sizei > container_limit_) {
- resetState();
- throw TProtocolException(TProtocolException::SIZE_LIMIT);
- }
- size = (uint32_t)sizei;
-
- elemType = ST1->ttype;
-
- ts_stack_.push_back(ST1);
-
- return xfer;
-}
-
-uint32_t TDenseProtocol::readListEnd() {
- ts_stack_.pop_back();
- stateTransition();
- return 0;
-}
-
-uint32_t TDenseProtocol::readSetBegin(TType& elemType, uint32_t& size) {
- checkTType(T_SET);
-
- uint32_t xfer = 0;
- int32_t sizei;
- xfer += subReadI32(sizei);
- if (sizei < 0) {
- resetState();
- throw TProtocolException(TProtocolException::NEGATIVE_SIZE);
- } else if (container_limit_ && sizei > container_limit_) {
- resetState();
- throw TProtocolException(TProtocolException::SIZE_LIMIT);
- }
- size = (uint32_t)sizei;
-
- elemType = ST1->ttype;
-
- ts_stack_.push_back(ST1);
-
- return xfer;
-}
-
-uint32_t TDenseProtocol::readSetEnd() {
- ts_stack_.pop_back();
- stateTransition();
- return 0;
-}
-
-uint32_t TDenseProtocol::readBool(bool& value) {
- checkTType(T_BOOL);
- stateTransition();
- return TBinaryProtocol::readBool(value);
-}
-
-uint32_t TDenseProtocol::readByte(int8_t& byte) {
- checkTType(T_BYTE);
- stateTransition();
- return TBinaryProtocol::readByte(byte);
-}
-
-uint32_t TDenseProtocol::readI16(int16_t& i16) {
- checkTType(T_I16);
- stateTransition();
- uint64_t u64;
- uint32_t rv = vlqRead(u64);
- int64_t val = (int64_t)u64;
- if (UNLIKELY(val > INT16_MAX || val < INT16_MIN)) {
- resetState();
- throw TProtocolException(TProtocolException::INVALID_DATA, "i16 out of range.");
- }
- i16 = (int16_t)val;
- return rv;
-}
-
-uint32_t TDenseProtocol::readI32(int32_t& i32) {
- checkTType(T_I32);
- stateTransition();
- uint64_t u64;
- uint32_t rv = vlqRead(u64);
- int64_t val = (int64_t)u64;
- if (UNLIKELY(val > INT32_MAX || val < INT32_MIN)) {
- resetState();
- throw TProtocolException(TProtocolException::INVALID_DATA, "i32 out of range.");
- }
- i32 = (int32_t)val;
- return rv;
-}
-
-uint32_t TDenseProtocol::readI64(int64_t& i64) {
- checkTType(T_I64);
- stateTransition();
- uint64_t u64;
- uint32_t rv = vlqRead(u64);
- int64_t val = (int64_t)u64;
- if (UNLIKELY(val > INT64_MAX || val < INT64_MIN)) {
- resetState();
- throw TProtocolException(TProtocolException::INVALID_DATA, "i64 out of range.");
- }
- i64 = (int64_t)val;
- return rv;
-}
-
-uint32_t TDenseProtocol::readDouble(double& dub) {
- checkTType(T_DOUBLE);
- stateTransition();
- return TBinaryProtocol::readDouble(dub);
-}
-
-uint32_t TDenseProtocol::readString(std::string& str) {
- checkTType(T_STRING);
- stateTransition();
- return subReadString(str);
-}
-
-uint32_t TDenseProtocol::readBinary(std::string& str) {
- return TDenseProtocol::readString(str);
-}
-
-uint32_t TDenseProtocol::subReadI32(int32_t& i32) {
- uint64_t u64;
- uint32_t rv = vlqRead(u64);
- int64_t val = (int64_t)u64;
- if (UNLIKELY(val > INT32_MAX || val < INT32_MIN)) {
- resetState();
- throw TProtocolException(TProtocolException::INVALID_DATA, "i32 out of range.");
- }
- i32 = (int32_t)val;
- return rv;
-}
-
-uint32_t TDenseProtocol::subReadString(std::string& str) {
- uint32_t xfer;
- int32_t size;
- xfer = subReadI32(size);
- return xfer + readStringBody(str, size);
-}
-}
-}
-} // apache::thrift::protocol
diff --git a/lib/cpp/src/thrift/protocol/TDenseProtocol.h b/lib/cpp/src/thrift/protocol/TDenseProtocol.h
deleted file mode 100644
index d7a119a1e..000000000
--- a/lib/cpp/src/thrift/protocol/TDenseProtocol.h
+++ /dev/null
@@ -1,228 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements. See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership. The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License. You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing,
- * software distributed under the License is distributed on an
- * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- * KIND, either express or implied. See the License for the
- * specific language governing permissions and limitations
- * under the License.
- */
-
-#ifndef _THRIFT_PROTOCOL_TDENSEPROTOCOL_H_
-#define _THRIFT_PROTOCOL_TDENSEPROTOCOL_H_ 1
-
-#include <thrift/protocol/TBinaryProtocol.h>
-
-namespace apache {
-namespace thrift {
-namespace protocol {
-
-/**
- * !!!WARNING!!!
- * This class is still highly experimental. Incompatible changes
- * WILL be made to it without notice. DO NOT USE IT YET unless
- * you are coordinating your testing with the author.
- *
- * The dense protocol is designed to use as little space as possible.
- *
- * There are two types of dense protocol instances. Standalone instances
- * are not used for RPC and just encoded and decode structures of
- * a predetermined type. Non-standalone instances are used for RPC.
- * Currently, only standalone instances exist.
- *
- * To use a standalone dense protocol object, you must set the type_spec
- * property (either in the constructor, or with setTypeSpec) to the local
- * reflection TypeSpec of the structures you will write to (or read from) the
- * protocol instance.
- *
- * BEST PRACTICES:
- * - Never use optional for primitives or containers.
- * - Only use optional for structures if they are very big and very rarely set.
- * - All integers are variable-length, so you can use i64 without bloating.
- * - NEVER EVER change the struct definitions IN ANY WAY without either
- * changing your cache keys or talking to dreiss.
- *
- * TODO(dreiss): New class write with old meta.
- *
- * We override all of TBinaryProtocol's methods.
- * We inherit so that we can explicitly call TBPs's primitive-writing
- * methods within our versions.
- *
- */
-class TDenseProtocol : public TVirtualProtocol<TDenseProtocol, TBinaryProtocol> {
-protected:
- static const int32_t VERSION_MASK = ((int32_t)0xffff0000);
- // VERSION_1 (0x80010000) is taken by TBinaryProtocol.
- static const int32_t VERSION_2 = ((int32_t)0x80020000);
-
-public:
- typedef apache::thrift::reflection::local::TypeSpec TypeSpec;
- static const int FP_PREFIX_LEN;
-
- /**
- * @param tran The transport to use.
- * @param type_spec The TypeSpec of the structures using this protocol.
- */
- TDenseProtocol(boost::shared_ptr<TTransport> trans, TypeSpec* type_spec = NULL)
- : TVirtualProtocol<TDenseProtocol, TBinaryProtocol>(trans),
- type_spec_(type_spec),
- standalone_(true) {}
-
- void setTypeSpec(TypeSpec* type_spec) { type_spec_ = type_spec; }
- TypeSpec* getTypeSpec() { return type_spec_; }
-
- /*
- * Writing functions.
- */
-
- uint32_t writeMessageBegin(const std::string& name,
- const TMessageType messageType,
- const int32_t seqid);
-
- uint32_t writeMessageEnd();
-
- uint32_t writeStructBegin(const char* name);
-
- uint32_t writeStructEnd();
-
- uint32_t writeFieldBegin(const char* name, const TType fieldType, const int16_t fieldId);
-
- uint32_t writeFieldEnd();
-
- uint32_t writeFieldStop();
-
- uint32_t writeMapBegin(const TType keyType, const TType valType, const uint32_t size);
-
- uint32_t writeMapEnd();
-
- uint32_t writeListBegin(const TType elemType, const uint32_t size);
-
- uint32_t writeListEnd();
-
- uint32_t writeSetBegin(const TType elemType, const uint32_t size);
-
- uint32_t writeSetEnd();
-
- uint32_t writeBool(const bool value);
-
- uint32_t writeByte(const int8_t byte);
-
- uint32_t writeI16(const int16_t i16);
-
- uint32_t writeI32(const int32_t i32);
-
- uint32_t writeI64(const int64_t i64);
-
- uint32_t writeDouble(const double dub);
-
- uint32_t writeString(const std::string& str);
-
- uint32_t writeBinary(const std::string& str);
-
- /*
- * Helper writing functions (don't do state transitions).
- */
- inline uint32_t subWriteI32(const int32_t i32);
-
- inline uint32_t subWriteString(const std::string& str);
-
- uint32_t subWriteBool(const bool value) { return TBinaryProtocol::writeBool(value); }
-
- /*
- * Reading functions
- */
-
- uint32_t readMessageBegin(std::string& name, TMessageType& messageType, int32_t& seqid);
-
- uint32_t readMessageEnd();
-
- uint32_t readStructBegin(std::string& name);
-
- uint32_t readStructEnd();
-
- uint32_t readFieldBegin(std::string& name, TType& fieldType, int16_t& fieldId);
-
- uint32_t readFieldEnd();
-
- uint32_t readMapBegin(TType& keyType, TType& valType, uint32_t& size);
-
- uint32_t readMapEnd();
-
- uint32_t readListBegin(TType& elemType, uint32_t& size);
-
- uint32_t readListEnd();
-
- uint32_t readSetBegin(TType& elemType, uint32_t& size);
-
- uint32_t readSetEnd();
-
- uint32_t readBool(bool& value);
- // Provide the default readBool() implementation for std::vector<bool>
- using TVirtualProtocol<TDenseProtocol, TBinaryProtocol>::readBool;
-
- uint32_t readByte(int8_t& byte);
-
- uint32_t readI16(int16_t& i16);
-
- uint32_t readI32(int32_t& i32);
-
- uint32_t readI64(int64_t& i64);
-
- uint32_t readDouble(double& dub);
-
- uint32_t readString(std::string& str);
-
- uint32_t readBinary(std::string& str);
-
- /*
- * Helper reading functions (don't do state transitions).
- */
- inline uint32_t subReadI32(int32_t& i32);
-
- inline uint32_t subReadString(std::string& str);
-
- uint32_t subReadBool(bool& value) { return TBinaryProtocol::readBool(value); }
-
-private:
- // Implementation functions, documented in the .cpp.
- inline void checkTType(const TType ttype);
- inline void stateTransition();
-
- // Read and write variable-length integers.
- // Uses the same technique as the MIDI file format.
- inline uint32_t vlqRead(uint64_t& vlq);
- inline uint32_t vlqWrite(uint64_t vlq);
-
- // Called before throwing an exception to make the object reusable.
- void resetState() {
- ts_stack_.clear();
- idx_stack_.clear();
- mkv_stack_.clear();
- }
-
- // TypeSpec of the top-level structure to write,
- // for standalone protocol objects.
- TypeSpec* type_spec_;
-
- std::vector<TypeSpec*> ts_stack_; // TypeSpec stack.
- std::vector<int> idx_stack_; // InDeX stack.
- std::vector<bool> mkv_stack_; // Map Key/Vlue stack.
- // True = key, False = value.
-
- // True iff this is a standalone instance (no RPC).
- bool standalone_;
-};
-}
-}
-} // apache::thrift::protocol
-
-#endif // #ifndef _THRIFT_PROTOCOL_TDENSEPROTOCOL_H_
diff --git a/lib/cpp/test/CMakeLists.txt b/lib/cpp/test/CMakeLists.txt
index 80c685250..9913f6c92 100644
--- a/lib/cpp/test/CMakeLists.txt
+++ b/lib/cpp/test/CMakeLists.txt
@@ -325,7 +325,7 @@ endif()
add_custom_command(OUTPUT gen-cpp/DebugProtoTest_types.cpp gen-cpp/DebugProtoTest_types.h gen-cpp/EmptyService.cpp gen-cpp/EmptyService.h
- COMMAND thrift-compiler --gen cpp:dense ${PROJECT_SOURCE_DIR}/test/DebugProtoTest.thrift
+ COMMAND thrift-compiler --gen cpp ${PROJECT_SOURCE_DIR}/test/DebugProtoTest.thrift
)
add_custom_command(OUTPUT gen-cpp/EnumTest_types.cpp gen-cpp/EnumTest_types.h
@@ -337,7 +337,7 @@ add_custom_command(OUTPUT gen-cpp/TypedefTest_types.cpp gen-cpp/TypedefTest_type
)
add_custom_command(OUTPUT gen-cpp/OptionalRequiredTest_types.cpp gen-cpp/OptionalRequiredTest_types.h
- COMMAND thrift-compiler --gen cpp:dense ${PROJECT_SOURCE_DIR}/test/OptionalRequiredTest.thrift
+ COMMAND thrift-compiler --gen cpp ${PROJECT_SOURCE_DIR}/test/OptionalRequiredTest.thrift
)
add_custom_command(OUTPUT gen-cpp/Recursive_types.cpp gen-cpp/Recursive_types.h
@@ -345,11 +345,11 @@ add_custom_command(OUTPUT gen-cpp/Recursive_types.cpp gen-cpp/Recursive_types.h
)
add_custom_command(OUTPUT gen-cpp/Service.cpp gen-cpp/StressTest_types.cpp
- COMMAND thrift-compiler --gen cpp:dense ${PROJECT_SOURCE_DIR}/test/StressTest.thrift
+ COMMAND thrift-compiler --gen cpp ${PROJECT_SOURCE_DIR}/test/StressTest.thrift
)
add_custom_command(OUTPUT gen-cpp/SecondService.cpp gen-cpp/ThriftTest_constants.cpp gen-cpp/ThriftTest.cpp gen-cpp/ThriftTest_types.cpp gen-cpp/ThriftTest_types.h
- COMMAND thrift-compiler --gen cpp:dense ${PROJECT_SOURCE_DIR}/test/ThriftTest.thrift
+ COMMAND thrift-compiler --gen cpp ${PROJECT_SOURCE_DIR}/test/ThriftTest.thrift
)
add_custom_command(OUTPUT gen-cpp/ChildService.cpp gen-cpp/ChildService.h gen-cpp/ParentService.cpp gen-cpp/ParentService.h gen-cpp/proc_types.cpp gen-cpp/proc_types.h
diff --git a/lib/cpp/test/DenseProtoTest.cpp b/lib/cpp/test/DenseProtoTest.cpp
deleted file mode 100644
index 0beaa380b..000000000
--- a/lib/cpp/test/DenseProtoTest.cpp
+++ /dev/null
@@ -1,485 +0,0 @@
-/*
- * Licensed to the Apache Software Foundation (ASF) under one
- * or more contributor license agreements. See the NOTICE file
- * distributed with this work for additional information
- * regarding copyright ownership. The ASF licenses this file
- * to you under the Apache License, Version 2.0 (the
- * "License"); you may not use this file except in compliance
- * with the License. You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing,
- * software distributed under the License is distributed on an
- * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- * KIND, either express or implied. See the License for the
- * specific language governing permissions and limitations
- * under the License.
- */
-
-/*
-../compiler/cpp/thrift --gen cpp:dense DebugProtoTest.thrift
-../compiler/cpp/thrift --gen cpp:dense OptionalRequiredTest.thrift
-g++ -Wall -g -I../lib/cpp/src -I/usr/local/include/boost-1_33_1 \
- gen-cpp/OptionalRequiredTest_types.cpp \
- gen-cpp/DebugProtoTest_types.cpp \
- DenseProtoTest.cpp ../lib/cpp/.libs/libthrift.a -o DenseProtoTest
-./DenseProtoTest
-*/
-
-// I do this to reach into the guts of TDenseProtocol. Sorry.
-#define private public
-#define inline
-
-#undef NDEBUG
-#include <cstdlib>
-#include <cassert>
-#include <cmath>
-#include <string>
-#include "gen-cpp/DebugProtoTest_types.h"
-#include "gen-cpp/OptionalRequiredTest_types.h"
-#include <thrift/protocol/TDenseProtocol.h>
-#include <thrift/transport/TBufferTransports.h>
-
-#define BOOST_TEST_MODULE DenseProtoTest
-#include <boost/test/unit_test.hpp>
-
-using std::string;
-using boost::shared_ptr;
-using namespace thrift::test;
-using namespace thrift::test::debug;
-using namespace apache::thrift::transport;
-using namespace apache::thrift::protocol;
-
-// Can't use memcmp here. GCC is too smart.
-bool my_memeq(const char* str1, const char* str2, int len) {
- for (int i = 0; i < len; i++) {
- if (str1[i] != str2[i]) {
- return false;
- }
- }
- return true;
-}
-
-BOOST_AUTO_TEST_CASE(test_dense_proto_1) {
- OneOfEach ooe;
- ooe.im_true = true;
- ooe.im_false = false;
- ooe.a_bite = 0xd6;
- ooe.integer16 = 27000;
- ooe.integer32 = 1 << 24;
- ooe.integer64 = (uint64_t)6000 * 1000 * 1000;
- ooe.double_precision = M_PI;
- ooe.some_characters = "Debug THIS!";
- ooe.zomg_unicode = "\xd7\n\a\t";
-
- // cout << apache::thrift::ThriftDebugString(ooe) << endl << endl;
-
- Nesting n;
- n.my_ooe = ooe;
- n.my_ooe.integer16 = 16;
- n.my_ooe.integer32 = 32;
- n.my_ooe.integer64 = 64;
- n.my_ooe.double_precision = (std::sqrt(5) + 1) / 2;
- n.my_ooe.some_characters = ":R (me going \"rrrr\")";
- n.my_ooe.zomg_unicode = "\xd3\x80\xe2\x85\xae\xce\x9d\x20"
- "\xd0\x9d\xce\xbf\xe2\x85\xbf\xd0\xbe\xc9\xa1\xd0\xb3\xd0\xb0\xcf\x81\xe2\x84\x8e"
- "\x20\xce\x91\x74\x74\xce\xb1\xe2\x85\xbd\xce\xba\xc7\x83\xe2\x80\xbc";
- n.my_bonk.type = 31337;
- n.my_bonk.message = "I am a bonk... xor!";
-
- // cout << apache::thrift::ThriftDebugString(n) << endl << endl;
-
- HolyMoley hm;
-
- hm.big.push_back(ooe);
- hm.big.push_back(n.my_ooe);
- hm.big[0].a_bite = 0x22;
- hm.big[1].a_bite = 0x33;
-
- std::vector<std::string> stage1;
- stage1.push_back("and a one");
- stage1.push_back("and a two");
- hm.contain.insert(stage1);
- stage1.clear();
- stage1.push_back("then a one, two");
- stage1.push_back("three!");
- stage1.push_back("FOUR!!");
- hm.contain.insert(stage1);
- stage1.clear();
- hm.contain.insert(stage1);
-
- std::vector<Bonk> stage2;
- hm.bonks["nothing"] = stage2;
- stage2.resize(stage2.size() + 1);
- stage2.back().type = 1;
- stage2.back().message = "Wait.";
- stage2.resize(stage2.size() + 1);
- stage2.back().type = 2;
- stage2.back().message = "What?";
- hm.bonks["something"] = stage2;
- stage2.clear();
- stage2.resize(stage2.size() + 1);
- stage2.back().type = 3;
- stage2.back().message = "quoth";
- stage2.resize(stage2.size() + 1);
- stage2.back().type = 4;
- stage2.back().message = "the raven";
- stage2.resize(stage2.size() + 1);
- stage2.back().type = 5;
- stage2.back().message = "nevermore";
- hm.bonks["poe"] = stage2;
-
- // cout << apache::thrift::ThriftDebugString(hm) << endl << endl;
-
- shared_ptr<TMemoryBuffer> buffer(new TMemoryBuffer());
- shared_ptr<TDenseProtocol> proto(new TDenseProtocol(buffer));
- proto->setTypeSpec(HolyMoley::local_reflection);
-
- hm.write(proto.get());
- HolyMoley hm2;
- hm2.read(proto.get());
-
- BOOST_CHECK(hm == hm2);
-}
-
-/*
- * Following Testcases are currently disabled, because vlqWrite and vlqRead are
- * private members.
- */
-#if 0
-#define checkout(i, c) \
- { \
- uint64_t vlq; \
- buffer->resetBuffer(); \
- proto->vlqWrite(i); \
- proto->getTransport()->flush(); \
- BOOST_CHECK(my_memeq(buffer->getBufferAsString().data(), c, sizeof(c) - 1));\
- proto->vlqRead(vlq); \
- assert(vlq == i); \
- }
-
-BOOST_AUTO_TEST_CASE(test_dense_proto_2) {
- // Let's test out the variable-length ints, shall we?
- shared_ptr<TMemoryBuffer> buffer(new TMemoryBuffer());
- shared_ptr<TDenseProtocol> proto(new TDenseProtocol(buffer));
-
- proto->setTypeSpec(HolyMoley::local_reflection);
-
- checkout(0x00000000, "\x00");
- checkout(0x00000040, "\x40");
- checkout(0x0000007F, "\x7F");
- checkout(0x00000080, "\x81\x00");
- checkout(0x00002000, "\xC0\x00");
- checkout(0x00003FFF, "\xFF\x7F");
- checkout(0x00004000, "\x81\x80\x00");
- checkout(0x00100000, "\xC0\x80\x00");
- checkout(0x001FFFFF, "\xFF\xFF\x7F");
- checkout(0x00200000, "\x81\x80\x80\x00");
- checkout(0x08000000, "\xC0\x80\x80\x00");
- checkout(0x0FFFFFFF, "\xFF\xFF\xFF\x7F");
- checkout(0x10000000, "\x81\x80\x80\x80\x00");
- checkout(0x20000000, "\x82\x80\x80\x80\x00");
- checkout(0x1FFFFFFF, "\x81\xFF\xFF\xFF\x7F");
- checkout(0xFFFFFFFF, "\x8F\xFF\xFF\xFF\x7F");
-
- checkout(0x0000000100000000ull, "\x90\x80\x80\x80\x00");
- checkout(0x0000000200000000ull, "\xA0\x80\x80\x80\x00");
- checkout(0x0000000300000000ull, "\xB0\x80\x80\x80\x00");
- checkout(0x0000000700000000ull, "\xF0\x80\x80\x80\x00");
- checkout(0x00000007F0000000ull, "\xFF\x80\x80\x80\x00");
- checkout(0x00000007FFFFFFFFull, "\xFF\xFF\xFF\xFF\x7F");
- checkout(0x0000000800000000ull, "\x81\x80\x80\x80\x80\x00");
- checkout(0x1FFFFFFFFFFFFFFFull, "\x9F\xFF\xFF\xFF\xFF\xFF\xFF\xFF\x7F");
- checkout(0x7FFFFFFFFFFFFFFFull, "\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFF\x7F");
- checkout(0xFFFFFFFFFFFFFFFFull, "\x81\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFF\x7F");
-}
-
-BOOST_AUTO_TEST_CASE(test_dense_proto_3) {
- // Test out the slow path with a TBufferedTransport.
- shared_ptr<TMemoryBuffer> buffer(new TMemoryBuffer());
- shared_ptr<TDenseProtocol> proto(new TDenseProtocol(buffer));
- shared_ptr<TBufferedTransport> buff_trans(new TBufferedTransport(buffer, 3));
-
- proto->setTypeSpec(HolyMoley::local_reflection);
- proto.reset(new TDenseProtocol(buff_trans));
-
- checkout(0x0000000100000000ull, "\x90\x80\x80\x80\x00");
- checkout(0x0000000200000000ull, "\xA0\x80\x80\x80\x00");
- checkout(0x0000000300000000ull, "\xB0\x80\x80\x80\x00");
- checkout(0x0000000700000000ull, "\xF0\x80\x80\x80\x00");
- checkout(0x00000007F0000000ull, "\xFF\x80\x80\x80\x00");
- checkout(0x00000007FFFFFFFFull, "\xFF\xFF\xFF\xFF\x7F");
- checkout(0x0000000800000000ull, "\x81\x80\x80\x80\x80\x00");
- checkout(0x1FFFFFFFFFFFFFFFull, "\x9F\xFF\xFF\xFF\xFF\xFF\xFF\xFF\x7F");
- checkout(0x7FFFFFFFFFFFFFFFull, "\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFF\x7F");
- checkout(0xFFFFFFFFFFFFFFFFull, "\x81\xFF\xFF\xFF\xFF\xFF\xFF\xFF\xFF\x7F");
-}
-#endif
-
-// Test optional stuff.
-BOOST_AUTO_TEST_CASE(test_dense_proto_4_1) {
- shared_ptr<TMemoryBuffer> buffer(new TMemoryBuffer());
- shared_ptr<TDenseProtocol> proto(new TDenseProtocol(buffer));
- proto.reset(new TDenseProtocol(buffer));
- proto->setTypeSpec(ManyOpt::local_reflection);
-
- ManyOpt mo1, mo2;
- mo1.opt1 = 923759347;
- mo1.opt2 = 392749274;
- mo1.opt3 = 395739402;
- mo1.def4 = 294730928;
- mo1.opt5 = 394309218;
- mo1.opt6 = 832194723;
- mo1.__isset.opt1 = true;
- mo1.__isset.opt2 = true;
- mo1.__isset.opt3 = true;
- mo1.__isset.def4 = true;
- mo1.__isset.opt5 = true;
- mo1.__isset.opt6 = true;
-
- mo1.write(proto.get());
- mo2.read(proto.get());
-
- BOOST_CHECK(mo2.__isset.opt1 == true);
- BOOST_CHECK(mo2.__isset.opt2 == true);
- BOOST_CHECK(mo2.__isset.opt3 == true);
- BOOST_CHECK(mo2.__isset.def4 == true);
- BOOST_CHECK(mo2.__isset.opt5 == true);
- BOOST_CHECK(mo2.__isset.opt6 == true);
-
- BOOST_CHECK(mo1 == mo2);
-}
-
-BOOST_AUTO_TEST_CASE(test_dense_proto_4_2) {
- shared_ptr<TMemoryBuffer> buffer(new TMemoryBuffer());
- shared_ptr<TDenseProtocol> proto(new TDenseProtocol(buffer));
- proto.reset(new TDenseProtocol(buffer));
- proto->setTypeSpec(ManyOpt::local_reflection);
-
- ManyOpt mo1, mo2;
- mo1.opt1 = 923759347;
- mo1.opt2 = 392749274;
- mo1.opt3 = 395739402;
- mo1.def4 = 294730928;
- mo1.opt5 = 394309218;
- mo1.opt6 = 832194723;
- mo1.__isset.opt1 = false;
- mo1.__isset.opt2 = true;
- mo1.__isset.opt3 = false;
- mo1.__isset.def4 = true;
- mo1.__isset.opt5 = false;
- mo1.__isset.opt6 = true;
-
- mo1.write(proto.get());
- mo2.read(proto.get());
-
- BOOST_CHECK(mo2.__isset.opt1 == false);
- BOOST_CHECK(mo2.__isset.opt2 == true);
- BOOST_CHECK(mo2.__isset.opt3 == false);
- BOOST_CHECK(mo2.__isset.def4 == true);
- BOOST_CHECK(mo2.__isset.opt5 == false);
- BOOST_CHECK(mo2.__isset.opt6 == true);
-
- BOOST_CHECK(mo1 == mo2);
-}
-
-BOOST_AUTO_TEST_CASE(test_dense_proto_4_3) {
- shared_ptr<TMemoryBuffer> buffer(new TMemoryBuffer());
- shared_ptr<TDenseProtocol> proto(new TDenseProtocol(buffer));
- proto.reset(new TDenseProtocol(buffer));
- proto->setTypeSpec(ManyOpt::local_reflection);
-
- ManyOpt mo1, mo2;
- mo1.opt1 = 923759347;
- mo1.opt2 = 392749274;
- mo1.opt3 = 395739402;
- mo1.def4 = 294730928;
- mo1.opt5 = 394309218;
- mo1.opt6 = 832194723;
- mo1.__isset.opt1 = true;
- mo1.__isset.opt2 = false;
- mo1.__isset.opt3 = true;
- mo1.__isset.def4 = true;
- mo1.__isset.opt5 = true;
- mo1.__isset.opt6 = false;
-
- mo1.write(proto.get());
- mo2.read(proto.get());
-
- BOOST_CHECK(mo2.__isset.opt1 == true);
- BOOST_CHECK(mo2.__isset.opt2 == false);
- BOOST_CHECK(mo2.__isset.opt3 == true);
- BOOST_CHECK(mo2.__isset.def4 == true);
- BOOST_CHECK(mo2.__isset.opt5 == true);
- BOOST_CHECK(mo2.__isset.opt6 == false);
-
- BOOST_CHECK(mo1 == mo2);
-}
-
-BOOST_AUTO_TEST_CASE(test_dense_proto_4_4) {
- shared_ptr<TMemoryBuffer> buffer(new TMemoryBuffer());
- shared_ptr<TDenseProtocol> proto(new TDenseProtocol(buffer));
- proto.reset(new TDenseProtocol(buffer));
- proto->setTypeSpec(ManyOpt::local_reflection);
-
- ManyOpt mo1, mo2;
- mo1.opt1 = 923759347;
- mo1.opt2 = 392749274;
- mo1.opt3 = 395739402;
- mo1.def4 = 294730928;
- mo1.opt5 = 394309218;
- mo1.opt6 = 832194723;
- mo1.__isset.opt1 = false;
- mo1.__isset.opt2 = false;
- mo1.__isset.opt3 = true;
- mo1.__isset.def4 = true;
- mo1.__isset.opt5 = false;
- mo1.__isset.opt6 = false;
-
- mo1.write(proto.get());
- mo2.read(proto.get());
-
- BOOST_CHECK(mo2.__isset.opt1 == false);
- BOOST_CHECK(mo2.__isset.opt2 == false);
- BOOST_CHECK(mo2.__isset.opt3 == true);
- BOOST_CHECK(mo2.__isset.def4 == true);
- BOOST_CHECK(mo2.__isset.opt5 == false);
- BOOST_CHECK(mo2.__isset.opt6 == false);
-
- BOOST_CHECK(mo1 == mo2);
-}
-
-BOOST_AUTO_TEST_CASE(test_dense_proto_4_5) {
- shared_ptr<TMemoryBuffer> buffer(new TMemoryBuffer());
- shared_ptr<TDenseProtocol> proto(new TDenseProtocol(buffer));
- proto.reset(new TDenseProtocol(buffer));
- proto->setTypeSpec(ManyOpt::local_reflection);
-
- ManyOpt mo1, mo2;
- mo1.opt1 = 923759347;
- mo1.opt2 = 392749274;
- mo1.opt3 = 395739402;
- mo1.def4 = 294730928;
- mo1.opt5 = 394309218;
- mo1.opt6 = 832194723;
- mo1.__isset.opt1 = false;
- mo1.__isset.opt2 = false;
- mo1.__isset.opt3 = false;
- mo1.__isset.def4 = true;
- mo1.__isset.opt5 = false;
- mo1.__isset.opt6 = false;
-
- mo1.write(proto.get());
- mo2.read(proto.get());
-
- BOOST_CHECK(mo2.__isset.opt1 == false);
- BOOST_CHECK(mo2.__isset.opt2 == false);
- BOOST_CHECK(mo2.__isset.opt3 == false);
- BOOST_CHECK(mo2.__isset.def4 == true);
- BOOST_CHECK(mo2.__isset.opt5 == false);
- BOOST_CHECK(mo2.__isset.opt6 == false);
-
- BOOST_CHECK(mo1 == mo2);
-}
-
-// Test fingerprint checking stuff.
-BOOST_AUTO_TEST_CASE(test_dense_proto_5_1) {
- shared_ptr<TMemoryBuffer> buffer(new TMemoryBuffer());
- shared_ptr<TDenseProtocol> proto(new TDenseProtocol(buffer));
-
- // Default and required have the same fingerprint.
- Tricky1 t1;
- Tricky3 t3;
- BOOST_CHECK(string(Tricky1::ascii_fingerprint) == Tricky3::ascii_fingerprint);
- proto->setTypeSpec(Tricky1::local_reflection);
- t1.im_default = 227;
- t1.write(proto.get());
- proto->setTypeSpec(Tricky3::local_reflection);
- t3.read(proto.get());
- BOOST_CHECK(t3.im_required == 227);
-}
-
-BOOST_AUTO_TEST_CASE(test_dense_proto_5_2) {
- shared_ptr<TMemoryBuffer> buffer(new TMemoryBuffer());
- shared_ptr<TDenseProtocol> proto(new TDenseProtocol(buffer));
-
- // Optional changes things.
- Tricky1 t1;
- Tricky2 t2;
- BOOST_CHECK(string(Tricky1::ascii_fingerprint) != Tricky2::ascii_fingerprint);
- proto->setTypeSpec(Tricky1::local_reflection);
- t1.im_default = 227;
- t1.write(proto.get());
- try {
- proto->setTypeSpec(Tricky2::local_reflection);
- t2.read(proto.get());
- BOOST_CHECK(false);
- } catch (TProtocolException& ex) {
- buffer->resetBuffer();
- }
-}
-
-BOOST_AUTO_TEST_CASE(test_dense_proto_5_3) {
- shared_ptr<TMemoryBuffer> buffer(new TMemoryBuffer());
- shared_ptr<TDenseProtocol> proto(new TDenseProtocol(buffer));
-
- // Holy cow. We can use the Tricky1 typespec with the Tricky2 structure.
- Tricky1 t1;
- Tricky2 t2;
- proto->setTypeSpec(Tricky1::local_reflection);
- t1.im_default = 227;
- t1.write(proto.get());
- t2.read(proto.get());
- BOOST_CHECK(t2.__isset.im_optional == true);
- BOOST_CHECK(t2.im_optional == 227);
-}
-
-BOOST_AUTO_TEST_CASE(test_dense_proto_5_4) {
- shared_ptr<TMemoryBuffer> buffer(new TMemoryBuffer());
- shared_ptr<TDenseProtocol> proto(new TDenseProtocol(buffer));
-
- // And totally off the wall.
- Tricky1 t1;
- OneOfEach ooe2;
- BOOST_CHECK(string(Tricky1::ascii_fingerprint) != OneOfEach::ascii_fingerprint);
- proto->setTypeSpec(Tricky1::local_reflection);
- t1.im_default = 227;
- t1.write(proto.get());
- try {
- proto->setTypeSpec(OneOfEach::local_reflection);
- ooe2.read(proto.get());
- BOOST_CHECK(false);
- } catch (TProtocolException& ex) {
- buffer->resetBuffer();
- }
-}
-
-BOOST_AUTO_TEST_CASE(test_dense_proto_6) {
- // Okay, this is really off the wall.
- // Just don't crash.
- shared_ptr<TMemoryBuffer> buffer(new TMemoryBuffer());
- shared_ptr<TDenseProtocol> proto(new TDenseProtocol(buffer));
-
- BOOST_TEST_MESSAGE("Starting fuzz test. This takes a while.");
- std::srand(12345);
- for (int i = 0; i < 2000; i++) {
- if (i % 100 == 0) {
- BOOST_TEST_MESSAGE("Do " << i / 100 << "/" << 2000 / 100);
- }
- buffer->resetBuffer();
- // Make sure the fingerprint prefix is right.
- buffer->write(Nesting::binary_fingerprint, 4);
- for (int j = 0; j < 1024 * 1024; j++) {
- uint8_t r = std::rand();
- buffer->write(&r, 1);
- }
- Nesting n;
- proto->setTypeSpec(OneOfEach::local_reflection);
- try {
- n.read(proto.get());
- } catch (TProtocolException& ex) {
- } catch (TTransportException& ex) {
- }
- }
-}
diff --git a/lib/cpp/test/Makefile.am b/lib/cpp/test/Makefile.am
index 70efa6b9a..dadbe38e5 100755
--- a/lib/cpp/test/Makefile.am
+++ b/lib/cpp/test/Makefile.am
@@ -89,8 +89,7 @@ check_PROGRAMS = \
TFileTransportTest \
link_test \
OpenSSLManualInitTest \
- EnumTest \
- DenseProtoTest
+ EnumTest
if AMX_HAVE_LIBEVENT
noinst_PROGRAMS += \
@@ -276,16 +275,6 @@ RecursiveTest_LDADD = \
$(BOOST_TEST_LDADD)
#
-# DenseProtoTest
-#
-DenseProtoTest_SOURCES = \
- DenseProtoTest.cpp
-
-DenseProtoTest_LDADD = \
- libtestgencpp.la \
- $(BOOST_TEST_LDADD)
-
-#
# SpecializationTest
#
SpecializationTest_SOURCES = \
@@ -337,7 +326,7 @@ OpenSSLManualInitTest_LDADD = \
THRIFT = $(top_builddir)/compiler/cpp/thrift
gen-cpp/DebugProtoTest_types.cpp gen-cpp/DebugProtoTest_types.h gen-cpp/EmptyService.cpp gen-cpp/EmptyService.h: $(top_srcdir)/test/DebugProtoTest.thrift
- $(THRIFT) --gen cpp:dense $<
+ $(THRIFT) --gen cpp $<
gen-cpp/EnumTest_types.cpp gen-cpp/EnumTest_types.h: $(top_srcdir)/test/EnumTest.thrift
$(THRIFT) --gen cpp $<
@@ -346,16 +335,16 @@ gen-cpp/TypedefTest_types.cpp gen-cpp/TypedefTest_types.h: $(top_srcdir)/test/Ty
$(THRIFT) --gen cpp $<
gen-cpp/OptionalRequiredTest_types.cpp gen-cpp/OptionalRequiredTest_types.h: $(top_srcdir)/test/OptionalRequiredTest.thrift
- $(THRIFT) --gen cpp:dense $<
+ $(THRIFT) --gen cpp $<
gen-cpp/Recursive_types.cpp gen-cpp/Recursive_types.h: $(top_srcdir)/test/Recursive.thrift
$(THRIFT) --gen cpp $<
gen-cpp/Service.cpp gen-cpp/StressTest_types.cpp: $(top_srcdir)/test/StressTest.thrift
- $(THRIFT) --gen cpp:dense $<
+ $(THRIFT) --gen cpp $<
gen-cpp/SecondService.cpp gen-cpp/ThriftTest_constants.cpp gen-cpp/ThriftTest.cpp gen-cpp/ThriftTest_types.cpp gen-cpp/ThriftTest_types.h: $(top_srcdir)/test/ThriftTest.thrift
- $(THRIFT) --gen cpp:dense $<
+ $(THRIFT) --gen cpp $<
gen-cpp/ChildService.cpp gen-cpp/ChildService.h gen-cpp/ParentService.cpp gen-cpp/ParentService.h gen-cpp/proc_types.cpp gen-cpp/proc_types.h: processor/proc.thrift
$(THRIFT) --gen cpp:templates,cob_style $<