Skip to content

Commit 1f13ec2

Browse files
committed
Add set definition
1 parent 99ca09d commit 1f13ec2

36 files changed

+690
-26
lines changed

examples/message_printer/message_printer.h

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
#include <mfast.h>
44
#include <iostream>
55
#include <boost/io/ios_state.hpp>
6+
#include <bitset>
67

78
using namespace mfast;
89

@@ -130,5 +131,10 @@ class message_printer
130131
}
131132
--indent_;
132133
}
134+
135+
void visit(const set_cref& ref)
136+
{
137+
os_ << "0b" << std::bitset<16>{ref.value()};
138+
}
133139
};
134140

src/fast_type_gen/CMakeLists.txt

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,10 @@ else()
1010
add_executable (fast_type_gen)
1111
target_sources(fast_type_gen PRIVATE ${headers} ${sources})
1212

13+
if(XETRA_FAST_SPECIFICATION)
14+
target_compile_definitions(fast_type_gen PRIVATE XETRA_FAST_SPECIFICATION)
15+
endif(XETRA_FAST_SPECIFICATION)
16+
1317
target_link_libraries (fast_type_gen PRIVATE
1418
mfast_xml_parser_static
1519
mfast_static

src/fast_type_gen/codegen_base.cpp

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -216,6 +216,20 @@ class type_name_finder : public field_instruction_visitor {
216216
dependency_->insert(inst->cpp_ns());
217217
}
218218
}
219+
220+
virtual void visit(const set_field_instruction *inst,
221+
void *pIndex) override {
222+
if (inst->ref_instruction()) {
223+
inst->ref_instruction()->accept(*this, pIndex);
224+
} else if (inst->cpp_ns() == nullptr || inst->cpp_ns()[0] == 0 ||
225+
strcmp(caller_cpp_ns_, inst->cpp_ns()) == 0) {
226+
name_ = inst->name();
227+
} else {
228+
name_ = std::string(inst->cpp_ns()) + "::" + inst->name();
229+
if (dependency_)
230+
dependency_->insert(inst->cpp_ns());
231+
}
232+
}
219233
};
220234

221235
std::string codegen_base::cpp_type_of(const mfast::field_instruction *inst,

src/fast_type_gen/cpp_gen.cpp

Lines changed: 65 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -658,6 +658,71 @@ void cpp_gen::visit(const mfast::enum_field_instruction *inst, void *pIndex) {
658658
}
659659
}
660660

661+
void cpp_gen::visit(const mfast::set_field_instruction *inst, void *pIndex)
662+
{
663+
std::string name(cpp_name(inst));
664+
std::string qualified_name = name;
665+
std::string instruction_variable_name;
666+
std::stringstream elements_variable_name;
667+
std::stringstream num_elements_name;
668+
std::stringstream instruction_type;
669+
if (inst->ref_instruction())
670+
qualified_name = cpp_type_of(inst);
671+
if (pIndex == nullptr)
672+
{
673+
out_ << "const " << qualified_name << "::instruction_type*\n" << name
674+
<< "::instruction()\n"
675+
<< "{\n";
676+
instruction_variable_name = " the_instruction";
677+
instruction_type << qualified_name << "::instruction_type";
678+
}
679+
else
680+
{
681+
add_to_instruction_list(name);
682+
instruction_variable_name = prefix_string() + name + "_instruction";
683+
instruction_type << cref_scope() << name << "_cref::instruction_type";
684+
}
685+
if (inst->ref_instruction())
686+
{
687+
elements_variable_name << qualified_name << "::instruction()->elements()";
688+
num_elements_name << qualified_name << "::instruction()->num_elements()";
689+
instruction_type.str(qualified_name + "::instruction_type");
690+
}
691+
else
692+
{
693+
elements_variable_name << "elements";
694+
num_elements_name << inst->num_elements();
695+
out_ << "static const char* elements[] = {\n";
696+
for (auto i = 0ul; i < inst->num_elements(); ++i)
697+
{
698+
if (i != 0)
699+
out_ << ",\n";
700+
out_ << " \"" << inst->elements()[i] << "\"";
701+
}
702+
out_ << "};\n";
703+
}
704+
std::string context = gen_op_context(inst->name(), inst->op_context());
705+
out_ << "const static " << instruction_type.str() << "\n"
706+
<< instruction_variable_name << "(\n"
707+
<< " " << get_operator_name(inst) << ",\n"
708+
<< " " << get_presence(inst) << ",\n"
709+
<< " " << inst->id() << ", // id\n"
710+
<< " \"" << inst->name() << "\", // name\n"
711+
<< " \"" << inst->ns() << "\", // ns\n"
712+
<< " " << context << ", // opContext\n"
713+
<< " int_value_storage<uint64_t>("
714+
<< inst->initial_value().get<uint64_t>() << "), // initial_value\n"
715+
<< " " << elements_variable_name.str() << ", // element names\n"
716+
<< " " << num_elements_name.str() << ",// num elements\n"
717+
<< " nullptr, // ref_instruction\n"
718+
<< " nullptr, // cpp_ns\n"
719+
<< " " << inst->tag() << "); // tag\n\n";
720+
if (pIndex == nullptr) {
721+
out_ << " return &the_instruction;\n"
722+
<< "}\n\n";
723+
}
724+
}
725+
661726
void cpp_gen::generate(const mfast::aggregate_view_info &info) {
662727
std::string my_name = cpp_name(info.name_);
663728

src/fast_type_gen/cpp_gen.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,7 @@ class cpp_gen : public codegen_base {
3838
virtual void visit(const mfast::uint64_vector_field_instruction *,
3939
void *) override;
4040
virtual void visit(const mfast::enum_field_instruction *, void *) override;
41+
virtual void visit(const mfast::set_field_instruction *, void *) override;
4142

4243
private:
4344
virtual void generate(const mfast::aggregate_view_info &info);

src/fast_type_gen/hpp_gen.cpp

Lines changed: 82 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -672,6 +672,88 @@ void hpp_gen::visit(const mfast::enum_field_instruction *inst, void *pIndex) {
672672
}
673673
}
674674

675+
void hpp_gen::visit(const mfast::set_field_instruction *inst, void *pIndex)
676+
{
677+
std::string name(cpp_name(inst));
678+
if (inst->ref_instruction() == nullptr)
679+
{
680+
header_cref_ << indent << "struct " << export_symbol_uppercase_ << name
681+
<< "\n" << indent << "{\n" << indent << " enum element {\n";
682+
for (auto i = 0ul; i < inst->num_elements(); ++i)
683+
{
684+
header_cref_ << indent << " " << cpp_name(inst->elements()[i]);
685+
if (i == 0)
686+
header_cref_ << " = 1";
687+
else
688+
header_cref_ << " = 1 << " << i;
689+
if (i + 1 < inst->num_elements())
690+
header_cref_ << ",\n";
691+
}
692+
header_cref_ << "\n" << indent << " };\n" << indent
693+
<< " using instruction_type = "
694+
<< "mfast::set_field_instruction_ex<"
695+
<< name << ">;\n" << indent
696+
<< " static const instruction_type* instruction();\n"
697+
<< indent << "};\n\n";
698+
header_cref_ << indent << "class " << name << "_cref\n" << indent
699+
<< " : public mfast::set_cref_ex<" << name << "_cref, "
700+
<< name << ">\n" << indent << "{\n" << indent << " public:\n"
701+
<< indent << " using base_type = mfast::set_cref_ex<"
702+
<< name << "_cref, " << name << ">;\n" << indent
703+
<< " using element_type = " << name << "::element;\n"
704+
<< indent << " using instruction_type = " << name
705+
<< "::instruction_type;\n" << indent << " "
706+
<< name << "_cref(\n" << indent
707+
<< " const mfast::value_storage* storage=nullptr,\n" << indent
708+
<< " instruction_cptr instruction=nullptr);\n\n"
709+
<< indent << " explicit " << name
710+
<< "_cref(const field_cref& other);\n\n" << indent
711+
<< " element_type value() const;\n\n";
712+
for (auto i = 0ul; i < inst->num_elements_; ++i)
713+
{
714+
std::string element_name = cpp_name(inst->elements_[i]);
715+
header_cref_ << indent << " bool has_" << element_name << "() const;\n";
716+
}
717+
header_cref_ << indent << "};\n\n";
718+
header_mref_ << indent << "class " << name << "_mref\n" << indent
719+
<< " : public mfast::set_mref_ex<" << name << "_mref, "
720+
<< name << "_cref>\n" << indent << "{\n" << indent
721+
<< " public:\n" << indent
722+
<< " using base_type = mfast::set_mref_ex<" << name
723+
<< "_mref, " << name << "_cref>;\n" << indent
724+
<< " using element_type = " << name << "::element;\n"
725+
<< indent << " " << name << "_mref(\n" << indent
726+
<< " mfast::allocator* alloc=nullptr,\n" << indent
727+
<< " mfast::value_storage* storage=nullptr,\n" << indent
728+
<< " instruction_cptr instruction=nullptr);\n"
729+
<< indent << " explicit " << name
730+
<< "_mref(const mfast::field_mref_base& other);\n\n";
731+
for (auto i = 0ul; i < inst->num_elements_; ++i)
732+
{
733+
std::string element_name = cpp_name(inst->elements_[i]);
734+
header_mref_ << indent << " void set_" << element_name << "() const;\n";
735+
header_mref_ << indent << " void unset_" << element_name << "() const;\n";
736+
}
737+
header_mref_ << indent << "};\n\n";
738+
}
739+
if (pIndex) {
740+
std::string ret_type = cpp_type_of(inst, &dependency_);
741+
header_cref_ << indent << ret_type << "_cref get_" << name << "() const;\n";
742+
header_cref_ << indent << ret_type << "_cref try_get_" << name << "() const;\n";
743+
if (inst->field_operator() != mfast::operator_constant)
744+
header_mref_ << indent << ret_type << "_mref set_" << name << "() const;\n";
745+
if (inst->optional()) {
746+
header_mref_ << indent << "void omit_" << name << "() const;\n";
747+
}
748+
} else {
749+
content_ << header_cref_.str() << header_mref_.str();
750+
header_cref_.clear();
751+
header_cref_.str("");
752+
header_mref_.clear();
753+
header_mref_.str("");
754+
}
755+
}
756+
675757
void hpp_gen::generate(const mfast::aggregate_view_info &info) {
676758
std::string ns_prefix;
677759
std::string my_name = cpp_name(info.name_);

src/fast_type_gen/hpp_gen.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,7 @@ class hpp_gen : public codegen_base {
4040
virtual void visit(const mfast::template_instruction *, void *) override;
4141
virtual void visit(const mfast::templateref_instruction *, void *) override;
4242
virtual void visit(const mfast::enum_field_instruction *, void *) override;
43+
virtual void visit(const mfast::set_field_instruction *, void *) override;
4344

4445
private:
4546
void gen_primitive(const char *cpp_type,

src/fast_type_gen/inl_gen.cpp

Lines changed: 80 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -127,6 +127,11 @@ struct ext_cref_type_getter : mfast::field_instruction_visitor {
127127
out_ << "ext_cref<enum_cref, " << get_operator_tag(inst) << ", "
128128
<< get_properties_type(inst) << ">";
129129
}
130+
131+
virtual void visit(const set_field_instruction *inst, void *) override {
132+
out_ << "ext_cref<set_cref, " << get_operator_tag(inst) << ", "
133+
<< get_properties_type(inst) << ">";
134+
}
130135
};
131136

132137
std::string get_ext_cref_type(const field_instruction *inst) {
@@ -260,6 +265,11 @@ struct ext_mref_type_getter : mfast::field_instruction_visitor {
260265
out_ << "ext_mref<enum_mref, " << get_operator_tag(inst) << ", "
261266
<< get_properties_type(inst) << ">";
262267
}
268+
269+
virtual void visit(const set_field_instruction *inst, void *) override {
270+
out_ << "ext_mref<set_mref, " << get_operator_tag(inst) << ", "
271+
<< get_properties_type(inst) << ">";
272+
}
263273
};
264274

265275
std::string get_ext_mref_type(const field_instruction *inst) {
@@ -1045,6 +1055,76 @@ void inl_gen::visit(const mfast::enum_field_instruction *inst, void *pIndex) {
10451055
gen_accessors(inst, name, cref_type_name, mref_type_name, pIndex);
10461056
}
10471057

1058+
void inl_gen::visit(const mfast::set_field_instruction *inst, void *pIndex)
1059+
{
1060+
std::string name(cpp_name(inst));
1061+
std::string cref_type_name = cref_scope_.str() + name + "_cref";
1062+
std::string mref_type_name = mref_scope_.str() + name + "_mref";
1063+
if (inst->ref_instruction() == nullptr)
1064+
{
1065+
out_ << "inline\n" << cref_type_name << "::" << name << "_cref(\n"
1066+
<< " const mfast::value_storage* storage,\n"
1067+
<< " " << cref_type_name << "::instruction_cptr instruction)\n"
1068+
<< " : base_type(storage, instruction)\n"
1069+
<< "{\n"
1070+
<< "}\n\n"
1071+
<< "inline\n" << cref_type_name << "::" << name << "_cref(\n"
1072+
<< " const mfast::field_cref& other)\n"
1073+
<< " : base_type(other)\n"
1074+
<< "{\n"
1075+
<< "}\n\n"
1076+
<< "inline\n" << mref_type_name << "::" << name << "_mref(\n"
1077+
<< " mfast::allocator* alloc,\n"
1078+
<< " mfast::value_storage* storage,\n"
1079+
<< " " << mref_type_name << "::instruction_cptr instruction)\n"
1080+
<< " : base_type(alloc, storage, instruction)\n"
1081+
<< "{\n"
1082+
<< "}\n\n"
1083+
<< "inline\n" << mref_type_name << "::" << name << "_mref(\n"
1084+
<< " const mfast::field_mref_base& other)\n"
1085+
<< " : base_type(other)\n"
1086+
<< "{\n"
1087+
<< "}\n\n"
1088+
<< "inline\n" << cref_type_name << "::element_type\n" << cref_type_name
1089+
<< "::value() const\n"
1090+
<< "{\n"
1091+
<< " return static_cast<" << name
1092+
<< "::element>(base_type::value());\n"
1093+
<< "}\n\n";
1094+
for (auto i = 0ul; i < inst->num_elements_; ++i)
1095+
{
1096+
std::string element_name = cpp_name(inst->elements_[i]);
1097+
out_ << "inline\n"
1098+
<< "bool " << cref_type_name << "::has_" << element_name
1099+
<< "() const\n"
1100+
<< "{\n"
1101+
<< " return this->value() & " << name << "::" << element_name
1102+
<< ";\n"
1103+
<< "}\n\n"
1104+
<< "inline\n"
1105+
<< "void " << mref_type_name << "::set_" << element_name
1106+
<< "() const\n"
1107+
<< "{\n"
1108+
<< " auto tmp = this->value() | "
1109+
<< name << "::" << element_name << ";\n"
1110+
<< " return this->as(static_cast<element_type>(tmp));\n"
1111+
<< "}\n\n"
1112+
<< "inline\n"
1113+
<< "void " << mref_type_name << "::unset_" << element_name
1114+
<< "() const\n"
1115+
<< "{\n"
1116+
<< " auto tmp = this->value() & ~"
1117+
<< name << "::" << element_name << ";\n"
1118+
<< " return this->as(static_cast<element_type>(tmp));\n"
1119+
<< "}\n\n";
1120+
}
1121+
}
1122+
std::string ret_type = cpp_type_of(inst, nullptr);
1123+
auto ret_cref = ret_type + "_cref";
1124+
auto ret_mref = ret_type + "_mref";
1125+
gen_accessors(inst, name, ret_cref, ret_mref, pIndex);
1126+
}
1127+
10481128
void inl_gen::gen_accessors(const mfast::field_instruction *inst,
10491129
const std::string &name,
10501130
const std::string &cref_type_name,

src/fast_type_gen/inl_gen.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,7 @@ class inl_gen : public codegen_base {
3535
virtual void visit(const mfast::template_instruction *, void *) override;
3636
virtual void visit(const mfast::templateref_instruction *, void *) override;
3737
virtual void visit(const mfast::enum_field_instruction *, void *) override;
38+
virtual void visit(const mfast::set_field_instruction *, void *) override;
3839

3940
private:
4041
virtual void traverse(const mfast::group_field_instruction *inst,

src/mfast/coder/common/dictionary_builder.cpp

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -385,4 +385,13 @@ void dictionary_builder::visit(const enum_field_instruction *src_inst,
385385
get_dictionary_storage(dest->name(), dest->ns(), dest->op_context_,
386386
field_type_uint64, &dest->prev_storage_, dest);
387387
}
388+
389+
void dictionary_builder::visit(const set_field_instruction *src_inst,
390+
void *dest_inst) {
391+
auto& dest = *static_cast<set_field_instruction**>(dest_inst);
392+
dest = src_inst->clone(alloc_);
393+
dest->prev_value_ =
394+
get_dictionary_storage(dest->name(), dest->ns(), dest->op_context_,
395+
field_type_uint64, &dest->prev_storage_, dest);
396+
}
388397
}

0 commit comments

Comments
 (0)