diff options
author | Jean-Philippe Andre <jp.andre@samsung.com> | 2017-11-22 16:54:57 +0900 |
---|---|---|
committer | Jean-Philippe Andre <jp.andre@samsung.com> | 2017-12-05 10:14:03 +0900 |
commit | 5425baa9061753356d450a3c736669341e1b1570 (patch) | |
tree | a008cad3e6be4c7d5a2f5e79425ddf27cc6a6a68 /src/lib/eolian_cxx | |
parent | a597084db7b3a8a4bc7320b68aee7cbb34c6da43 (diff) |
cxx: Add support for function pointers
This was tested on the function pointer Efl.Ui.Format_Func_Cb
Diffstat (limited to 'src/lib/eolian_cxx')
-rw-r--r-- | src/lib/eolian_cxx/grammar/converting_argument.hpp | 24 | ||||
-rw-r--r-- | src/lib/eolian_cxx/grammar/function_declaration.hpp | 8 | ||||
-rw-r--r-- | src/lib/eolian_cxx/grammar/function_definition.hpp | 19 | ||||
-rw-r--r-- | src/lib/eolian_cxx/grammar/header.hpp | 1 | ||||
-rw-r--r-- | src/lib/eolian_cxx/grammar/klass_def.hpp | 60 | ||||
-rw-r--r-- | src/lib/eolian_cxx/grammar/parameter.hpp | 29 | ||||
-rw-r--r-- | src/lib/eolian_cxx/grammar/type_function_declaration.hpp | 121 | ||||
-rw-r--r-- | src/lib/eolian_cxx/grammar/types_definition.hpp | 38 |
8 files changed, 275 insertions, 25 deletions
diff --git a/src/lib/eolian_cxx/grammar/converting_argument.hpp b/src/lib/eolian_cxx/grammar/converting_argument.hpp index 230608ffc3..eb7ef57376 100644 --- a/src/lib/eolian_cxx/grammar/converting_argument.hpp +++ b/src/lib/eolian_cxx/grammar/converting_argument.hpp | |||
@@ -33,24 +33,12 @@ struct converting_argument_generator | |||
33 | bool generate(OutputIterator sink, attributes::parameter_def const& param, Context const& ctx) const | 33 | bool generate(OutputIterator sink, attributes::parameter_def const& param, Context const& ctx) const |
34 | { | 34 | { |
35 | attributes::qualifier_def qualifier = param.type.original_type.visit(attributes::get_qualifier_visitor{}); | 35 | attributes::qualifier_def qualifier = param.type.original_type.visit(attributes::get_qualifier_visitor{}); |
36 | bool is_function_ptr = param.type.original_type.visit(this->is_function_ptr); | 36 | if (param.type.original_type.visit(this->is_function_ptr)) |
37 | if(is_function_ptr) | 37 | { |
38 | return as_generator | 38 | // FIXME: This supports only one function pointer. |
39 | ( | 39 | return as_generator("fw->data_to_c(), fw->func_to_c(), fw->free_to_c()") |
40 | attribute_reorder<-1, -1, 2, -1, -1, -1, -1> | 40 | .generate(sink, param, ctx); |
41 | ( | 41 | } |
42 | " ::efl::eolian::data_function_ptr_to_c<" << c_type | ||
43 | << ", " << parameter_type | ||
44 | << ">(" << string << ")" | ||
45 | |||
46 | ", ::efl::eolian::function_ptr_to_c<" << c_type | ||
47 | << ", " << parameter_type | ||
48 | << ">()" | ||
49 | ", ::efl::eolian::free_function_ptr_to_c<" << c_type | ||
50 | << ", " << parameter_type | ||
51 | << ">()" | ||
52 | ) | ||
53 | ).generate(sink, param, ctx); | ||
54 | else | 42 | else |
55 | return as_generator | 43 | return as_generator |
56 | ( | 44 | ( |
diff --git a/src/lib/eolian_cxx/grammar/function_declaration.hpp b/src/lib/eolian_cxx/grammar/function_declaration.hpp index e98fbf0a3a..641ae6560c 100644 --- a/src/lib/eolian_cxx/grammar/function_declaration.hpp +++ b/src/lib/eolian_cxx/grammar/function_declaration.hpp | |||
@@ -1,3 +1,4 @@ | |||
1 | |||
1 | #ifndef EOLIAN_CXX_FUNCTION_DECLARATION_HH | 2 | #ifndef EOLIAN_CXX_FUNCTION_DECLARATION_HH |
2 | #define EOLIAN_CXX_FUNCTION_DECLARATION_HH | 3 | #define EOLIAN_CXX_FUNCTION_DECLARATION_HH |
3 | 4 | ||
@@ -42,6 +43,13 @@ struct function_declaration_generator | |||
42 | !as_generator("#ifdef " << *(string << "_") << string << "_" << string << "_BETA\n") | 43 | !as_generator("#ifdef " << *(string << "_") << string << "_" << string << "_BETA\n") |
43 | .generate(sink, std::make_tuple(_klass_name.namespaces, _klass_name.eolian_name, suffix), add_upper_case_context(ctx))) | 44 | .generate(sink, std::make_tuple(_klass_name.namespaces, _klass_name.eolian_name, suffix), add_upper_case_context(ctx))) |
44 | return false; | 45 | return false; |
46 | |||
47 | std::string template_statement(f.template_statement()); | ||
48 | if (!template_statement.empty() && | ||
49 | !as_generator(template_statement << " ") | ||
50 | .generate(sink, attributes::unused, ctx)) | ||
51 | return false; | ||
52 | |||
45 | if(!as_generator | 53 | if(!as_generator |
46 | ("::efl::eolian::return_traits<" << grammar::type(true) << ">::type " << string << "(" << (parameter % ", ") << ") const;\n") | 54 | ("::efl::eolian::return_traits<" << grammar::type(true) << ">::type " << string << "(" << (parameter % ", ") << ") const;\n") |
47 | .generate(sink, std::make_tuple(f.return_type, escape_keyword(f.name), f.parameters), ctx)) | 55 | .generate(sink, std::make_tuple(f.return_type, escape_keyword(f.name), f.parameters), ctx)) |
diff --git a/src/lib/eolian_cxx/grammar/function_definition.hpp b/src/lib/eolian_cxx/grammar/function_definition.hpp index 50bd9970c5..55f56216fd 100644 --- a/src/lib/eolian_cxx/grammar/function_definition.hpp +++ b/src/lib/eolian_cxx/grammar/function_definition.hpp | |||
@@ -17,6 +17,7 @@ | |||
17 | #include "grammar/attribute_conditional.hpp" | 17 | #include "grammar/attribute_conditional.hpp" |
18 | #include "grammar/attribute_reorder.hpp" | 18 | #include "grammar/attribute_reorder.hpp" |
19 | #include "grammar/type_impl.hpp" | 19 | #include "grammar/type_impl.hpp" |
20 | #include "grammar/eps.hpp" | ||
20 | 21 | ||
21 | namespace efl { namespace eolian { namespace grammar { | 22 | namespace efl { namespace eolian { namespace grammar { |
22 | 23 | ||
@@ -52,12 +53,24 @@ struct function_definition_generator | |||
52 | !as_generator("#ifdef " << *(string << "_") << string << "_PROTECTED\n") | 53 | !as_generator("#ifdef " << *(string << "_") << string << "_PROTECTED\n") |
53 | .generate(sink, std::make_tuple(_klass_name.namespaces, _klass_name.eolian_name), add_upper_case_context(ctx))) | 54 | .generate(sink, std::make_tuple(_klass_name.namespaces, _klass_name.eolian_name), add_upper_case_context(ctx))) |
54 | return false; | 55 | return false; |
55 | 56 | ||
57 | std::string template_statement(f.template_statement()); | ||
58 | if (!template_statement.empty() && | ||
59 | !as_generator(template_statement << "\n") | ||
60 | .generate(sink, attributes::unused, ctx)) | ||
61 | return false; | ||
62 | |||
56 | if(!as_generator | 63 | if(!as_generator |
57 | ("inline ::efl::eolian::return_traits<" << grammar::type(true) << ">::type " << string << "::" << string << "(" << (parameter % ", ") << ") const\n{\n") | 64 | ("inline ::efl::eolian::return_traits<" << grammar::type(true) << ">::type " << string << "::" << string << "(" << (parameter % ", ") << ") const\n{\n") |
58 | .generate(sink, std::make_tuple(f.return_type, _klass_name.eolian_name, escape_keyword(f.name), f.parameters), ctx)) | 65 | .generate(sink, std::make_tuple(f.return_type, _klass_name.eolian_name, escape_keyword(f.name), f.parameters), ctx)) |
59 | return false; | 66 | return false; |
60 | 67 | ||
68 | std::vector<std::string> opening_statements(f.opening_statements()); | ||
69 | if (!opening_statements.empty() && | ||
70 | !as_generator(scope_tab << *(string) << "\n") | ||
71 | .generate(sink, std::make_tuple(opening_statements), ctx)) | ||
72 | return false; | ||
73 | |||
61 | auto out_declaration = | 74 | auto out_declaration = |
62 | attribute_conditional([] (attributes::parameter_def const& p) -> bool | 75 | attribute_conditional([] (attributes::parameter_def const& p) -> bool |
63 | { return p.direction == attributes::parameter_direction::out; }) | 76 | { return p.direction == attributes::parameter_direction::out; }) |
@@ -118,8 +131,8 @@ struct function_definition_generator | |||
118 | scope_tab << "::efl::eolian::assign_out<" << parameter_type << ", " << c_type | 131 | scope_tab << "::efl::eolian::assign_out<" << parameter_type << ", " << c_type |
119 | << | 132 | << |
120 | ( | 133 | ( |
121 | attribute_conditional([] (attributes::type_def const& type) | 134 | attribute_conditional([] (attributes::type_def const& typ) |
122 | { return type.original_type.visit(attributes::get_qualifier_visitor{}) & qualifier_info::is_own; }) | 135 | { return typ.original_type.visit(attributes::get_qualifier_visitor{}) & qualifier_info::is_own; }) |
123 | [ | 136 | [ |
124 | ", true" | 137 | ", true" |
125 | ] | eps | 138 | ] | eps |
diff --git a/src/lib/eolian_cxx/grammar/header.hpp b/src/lib/eolian_cxx/grammar/header.hpp index 63a6095949..4f1df9233f 100644 --- a/src/lib/eolian_cxx/grammar/header.hpp +++ b/src/lib/eolian_cxx/grammar/header.hpp | |||
@@ -24,6 +24,7 @@ auto class_header = | |||
24 | << "#include <Eina.hh>\n" | 24 | << "#include <Eina.hh>\n" |
25 | "#include <Eo.hh>\n" | 25 | "#include <Eo.hh>\n" |
26 | << *header_include_directive // sequence<string> | 26 | << *header_include_directive // sequence<string> |
27 | << string // extra header <string> | ||
27 | << *class_declaration // sequence<class> | class | 28 | << *class_declaration // sequence<class> | class |
28 | << *class_forward_declaration // sequence<class> | class | 29 | << *class_forward_declaration // sequence<class> | class |
29 | << "\nnamespace eo_cxx {\n" | 30 | << "\nnamespace eo_cxx {\n" |
diff --git a/src/lib/eolian_cxx/grammar/klass_def.hpp b/src/lib/eolian_cxx/grammar/klass_def.hpp index edfadc05bb..f7b12af578 100644 --- a/src/lib/eolian_cxx/grammar/klass_def.hpp +++ b/src/lib/eolian_cxx/grammar/klass_def.hpp | |||
@@ -433,6 +433,7 @@ struct function_def | |||
433 | std::string filename; | 433 | std::string filename; |
434 | bool is_beta; | 434 | bool is_beta; |
435 | bool is_protected; | 435 | bool is_protected; |
436 | bool is_function_pointer; | ||
436 | 437 | ||
437 | friend inline bool operator==(function_def const& lhs, function_def const& rhs) | 438 | friend inline bool operator==(function_def const& lhs, function_def const& rhs) |
438 | { | 439 | { |
@@ -442,17 +443,27 @@ struct function_def | |||
442 | && lhs.c_name == rhs.c_name | 443 | && lhs.c_name == rhs.c_name |
443 | && lhs.filename == rhs.filename | 444 | && lhs.filename == rhs.filename |
444 | && lhs.is_beta == rhs.is_beta | 445 | && lhs.is_beta == rhs.is_beta |
445 | && lhs.is_protected == rhs.is_protected; | 446 | && lhs.is_protected == rhs.is_protected |
447 | && lhs.is_function_pointer == rhs.is_function_pointer; | ||
446 | } | 448 | } |
447 | friend inline bool operator!=(function_def const& lhs, function_def const& rhs) | 449 | friend inline bool operator!=(function_def const& lhs, function_def const& rhs) |
448 | { | 450 | { |
449 | return !(lhs == rhs); | 451 | return !(lhs == rhs); |
450 | } | 452 | } |
451 | 453 | function_def() = default; | |
452 | function_def(type_def return_type, std::string name, std::vector<parameter_def> parameters | 454 | function_def(type_def return_type, std::string name, std::vector<parameter_def> parameters |
453 | , std::string c_name, std::string filename, bool is_beta) | 455 | , std::string c_name, std::string filename, bool is_beta) |
454 | : return_type(return_type), name(name), parameters(parameters), c_name(c_name), filename(filename), is_beta(is_beta) {} | 456 | : return_type(return_type), name(name), parameters(parameters), c_name(c_name), filename(filename), is_beta(is_beta) {} |
455 | function_def() = default; | 457 | function_def(type_def _return_type, std::string const& _name, |
458 | std::vector<parameter_def> const& _parameters, | ||
459 | std::string const& _c_name, | ||
460 | bool _is_beta = false, | ||
461 | bool _is_protected = false, | ||
462 | bool _is_function_pointer = false) | ||
463 | : return_type(_return_type), name(_name), parameters(_parameters), | ||
464 | c_name(_c_name), is_beta(_is_beta), is_protected(_is_protected), | ||
465 | is_function_pointer(_is_function_pointer) {} | ||
466 | |||
456 | function_def( ::Eolian_Function const* function, Eolian_Function_Type type, Eolian_Unit const* unit) | 467 | function_def( ::Eolian_Function const* function, Eolian_Function_Type type, Eolian_Unit const* unit) |
457 | : return_type(void_) | 468 | : return_type(void_) |
458 | { | 469 | { |
@@ -517,6 +528,49 @@ struct function_def | |||
517 | is_protected = eolian_function_scope_get(function, type) == EOLIAN_SCOPE_PROTECTED; | 528 | is_protected = eolian_function_scope_get(function, type) == EOLIAN_SCOPE_PROTECTED; |
518 | is_protected = eolian_function_scope_get(function, type) == EOLIAN_SCOPE_PROTECTED; | 529 | is_protected = eolian_function_scope_get(function, type) == EOLIAN_SCOPE_PROTECTED; |
519 | } | 530 | } |
531 | |||
532 | std::string template_statement() const | ||
533 | { | ||
534 | std::string statement; | ||
535 | char template_typename = 'F'; | ||
536 | for (auto const& param : this->parameters) | ||
537 | { | ||
538 | attributes::regular_type_def const* typ = | ||
539 | efl::eina::get<attributes::regular_type_def>(¶m.type.original_type); | ||
540 | if (typ && typ->is_function_ptr) | ||
541 | { | ||
542 | char typenam[2] = { 0, }; | ||
543 | typenam[0] = template_typename++; | ||
544 | if (statement.empty()) | ||
545 | statement = std::string("template <typename ") + typenam; | ||
546 | else | ||
547 | statement += std::string(", typename ") + typenam; | ||
548 | } | ||
549 | } | ||
550 | if (statement.empty()) return statement; | ||
551 | else return statement + ">"; | ||
552 | } | ||
553 | |||
554 | std::vector<std::string> opening_statements() const | ||
555 | { | ||
556 | // FIXME: Supports only one function pointer | ||
557 | std::vector<std::string> statements; | ||
558 | char template_typename = 'F'; | ||
559 | for (auto const& param : this->parameters) | ||
560 | { | ||
561 | attributes::regular_type_def const* typ = | ||
562 | efl::eina::get<attributes::regular_type_def>(¶m.type.original_type); | ||
563 | if (typ && typ->is_function_ptr) | ||
564 | { | ||
565 | char typenam[2] = { 0, }; | ||
566 | typenam[0] = template_typename++; | ||
567 | std::string statement = "auto fw = new ::efl::eolian::function_wrapper<"; | ||
568 | statement += param.c_type + ", " + typenam + ">(" + param.param_name + ");"; | ||
569 | statements.push_back(statement); | ||
570 | } | ||
571 | } | ||
572 | return statements; | ||
573 | } | ||
520 | }; | 574 | }; |
521 | 575 | ||
522 | template <> | 576 | template <> |
diff --git a/src/lib/eolian_cxx/grammar/parameter.hpp b/src/lib/eolian_cxx/grammar/parameter.hpp index f9e625a514..5d8d3aef5c 100644 --- a/src/lib/eolian_cxx/grammar/parameter.hpp +++ b/src/lib/eolian_cxx/grammar/parameter.hpp | |||
@@ -25,6 +25,12 @@ struct parameter_type_generator | |||
25 | dir = "in"; | 25 | dir = "in"; |
26 | break; | 26 | break; |
27 | } | 27 | } |
28 | |||
29 | attributes::regular_type_def const* typ = | ||
30 | efl::eina::get<attributes::regular_type_def>(¶m.type.original_type); | ||
31 | if (typ && typ->is_function_ptr) | ||
32 | return as_generator("F").generate(sink, attributes::unused, context); | ||
33 | |||
28 | return as_generator | 34 | return as_generator |
29 | ( | 35 | ( |
30 | " ::efl::eolian::" << string << "_traits<" | 36 | " ::efl::eolian::" << string << "_traits<" |
@@ -44,6 +50,8 @@ struct attributes_needed<parameter_type_generator> : std::integral_constant<int, | |||
44 | 50 | ||
45 | parameter_type_generator const parameter_type = {}; | 51 | parameter_type_generator const parameter_type = {}; |
46 | 52 | ||
53 | |||
54 | /* */ | ||
47 | struct parameter_generator | 55 | struct parameter_generator |
48 | { | 56 | { |
49 | template <typename OutputIterator, typename Context> | 57 | template <typename OutputIterator, typename Context> |
@@ -59,9 +67,28 @@ template <> | |||
59 | struct is_generator<parameter_generator> : std::true_type {}; | 67 | struct is_generator<parameter_generator> : std::true_type {}; |
60 | namespace type_traits { | 68 | namespace type_traits { |
61 | template <> | 69 | template <> |
62 | struct attributes_needed<parameter_generator> : std::integral_constant<int, 1> {}; | 70 | struct attributes_needed<parameter_generator> : std::integral_constant<int, 1> {}; |
63 | } | 71 | } |
64 | parameter_generator const parameter = {}; | 72 | parameter_generator const parameter = {}; |
73 | |||
74 | |||
75 | /* */ | ||
76 | struct parameter_as_argument_generator | ||
77 | { | ||
78 | template <typename OutputIterator, typename Context> | ||
79 | bool generate(OutputIterator sink, attributes::parameter_def const& param, Context const& context) const | ||
80 | { | ||
81 | return as_generator(parameter_type << "(" << string << ")").generate(sink, std::make_tuple(param, param.param_name), context); | ||
82 | } | ||
83 | }; | ||
84 | |||
85 | template <> | ||
86 | struct is_eager_generator<parameter_as_argument_generator> : std::true_type {}; | ||
87 | namespace type_traits { | ||
88 | template <> | ||
89 | struct attributes_needed<parameter_as_argument_generator> : std::integral_constant<int, 1> {}; | ||
90 | } | ||
91 | parameter_as_argument_generator const parameter_as_argument = {}; | ||
65 | 92 | ||
66 | } } } | 93 | } } } |
67 | 94 | ||
diff --git a/src/lib/eolian_cxx/grammar/type_function_declaration.hpp b/src/lib/eolian_cxx/grammar/type_function_declaration.hpp new file mode 100644 index 0000000000..eccedf8f4a --- /dev/null +++ b/src/lib/eolian_cxx/grammar/type_function_declaration.hpp | |||
@@ -0,0 +1,121 @@ | |||
1 | #ifndef EOLIAN_CXX_TYPE_FUNCTION_DECLARATION_HH | ||
2 | #define EOLIAN_CXX_TYPE_FUNCTION_DECLARATION_HH | ||
3 | |||
4 | #include "grammar/generator.hpp" | ||
5 | #include "grammar/klass_def.hpp" | ||
6 | |||
7 | #include "grammar/string.hpp" | ||
8 | #include "grammar/indentation.hpp" | ||
9 | #include "grammar/list.hpp" | ||
10 | #include "grammar/alternative.hpp" | ||
11 | #include "grammar/type.hpp" | ||
12 | #include "grammar/parameter.hpp" | ||
13 | #include "grammar/keyword.hpp" | ||
14 | #include "grammar/converting_argument.hpp" | ||
15 | #include "grammar/eps.hpp" | ||
16 | |||
17 | namespace efl { namespace eolian { namespace grammar { | ||
18 | |||
19 | /** This generates the caller struct for function pointers. */ | ||
20 | struct type_function_declaration_generator { | ||
21 | type_function_declaration_generator() {} | ||
22 | |||
23 | template <typename OutputIterator, typename Context> | ||
24 | bool generate(OutputIterator sink, attributes::function_def const& f, Context const& ctx) const | ||
25 | { | ||
26 | std::string guard = f.c_name + "_defined"; | ||
27 | |||
28 | if (!as_generator("#ifndef " << string << "\n" << | ||
29 | "#define " << string << "\n") | ||
30 | .generate(sink, std::make_tuple(guard, guard), add_upper_case_context(ctx))) | ||
31 | return false; | ||
32 | |||
33 | // efl::eolian::function_wrapper<T, F> | ||
34 | if (!as_generator("namespace efl { namespace eolian {\n") | ||
35 | .generate(sink, attributes::unused, add_lower_case_context(ctx))) | ||
36 | return false; | ||
37 | |||
38 | if (!as_generator( | ||
39 | "template <typename F>\n" | ||
40 | "struct function_wrapper<" << string << ", F> {\n" | ||
41 | << scope_tab << "function_wrapper(F cxx_func) : _cxx_func(cxx_func) {}\n" | ||
42 | ).generate(sink, f.c_name, ctx)) | ||
43 | return false; | ||
44 | |||
45 | if (!as_generator( | ||
46 | scope_tab << "void *data_to_c() { return static_cast<void *>(this); }\n" | ||
47 | << scope_tab << string << " func_to_c() const { return &caller; }\n" | ||
48 | << scope_tab << "Eina_Free_Cb free_to_c() const { return &deleter; }\n" | ||
49 | << "private:\n" | ||
50 | << scope_tab << "F _cxx_func;\n" | ||
51 | << scope_tab << "static void deleter(void *data) {\n" | ||
52 | << scope_tab << scope_tab << "delete static_cast<function_wrapper<" << string << ", F>*>(data);\n" | ||
53 | << scope_tab << "}\n" | ||
54 | ).generate(sink, std::make_tuple(f.c_name, f.c_name), ctx)) | ||
55 | return false; | ||
56 | |||
57 | std::vector<std::string> c_args; | ||
58 | for (auto itr : f.parameters) | ||
59 | c_args.push_back(", " + itr.c_type + " " + itr.param_name); | ||
60 | if (!as_generator( | ||
61 | scope_tab << "static " << string << " caller(void *cxx_call_data" | ||
62 | << *(string) << ") {\n" | ||
63 | << scope_tab << scope_tab << "auto fw = static_cast<function_wrapper<" | ||
64 | << string << ", F>*>(cxx_call_data);\n" | ||
65 | ).generate(sink, std::make_tuple(f.return_type.c_type, c_args, f.c_name), ctx)) | ||
66 | return false; | ||
67 | |||
68 | if (f.return_type != attributes::void_ | ||
69 | && !as_generator(scope_tab << scope_tab << "auto __return_value =\n") | ||
70 | .generate(sink, attributes::unused, ctx)) | ||
71 | return false; | ||
72 | |||
73 | if (!f.parameters.empty()) | ||
74 | { | ||
75 | std::vector<attributes::parameter_def> params; | ||
76 | for (auto itr = f.parameters.begin() + 1; itr != f.parameters.end(); itr++) | ||
77 | params.push_back(*itr); | ||
78 | if (!as_generator( | ||
79 | scope_tab << scope_tab << "fw->_cxx_func(" << parameter_as_argument << *(", " << parameter_as_argument) << ");\n" | ||
80 | ).generate(sink, std::make_tuple(*f.parameters.begin(), params), ctx)) | ||
81 | return false; | ||
82 | } | ||
83 | |||
84 | if (f.return_type != attributes::void_ | ||
85 | && !as_generator(scope_tab << scope_tab << "return ::efl::eolian::convert_to_c<" | ||
86 | << type << ">(__return_value);\n") | ||
87 | .generate(sink, f.return_type, ctx)) | ||
88 | return false; | ||
89 | |||
90 | if (!as_generator(scope_tab << "}\n").generate(sink, attributes::unused, ctx)) | ||
91 | return false; | ||
92 | |||
93 | if (!as_generator("};\n" | ||
94 | "} }\n" | ||
95 | "#endif\n\n") | ||
96 | .generate(sink, attributes::unused, ctx)) | ||
97 | return false; | ||
98 | |||
99 | return true; | ||
100 | } | ||
101 | }; | ||
102 | |||
103 | template <> | ||
104 | struct is_eager_generator<type_function_declaration_generator> : std::true_type {}; | ||
105 | |||
106 | namespace type_traits { | ||
107 | template <> | ||
108 | struct attributes_needed<type_function_declaration_generator> : std::integral_constant<int, 1> {}; | ||
109 | } | ||
110 | |||
111 | struct type_function_declaration_terminal | ||
112 | { | ||
113 | type_function_declaration_generator operator()() const | ||
114 | { | ||
115 | return type_function_declaration_generator{}; | ||
116 | } | ||
117 | } const type_function_declaration = {}; | ||
118 | |||
119 | } } } | ||
120 | |||
121 | #endif | ||
diff --git a/src/lib/eolian_cxx/grammar/types_definition.hpp b/src/lib/eolian_cxx/grammar/types_definition.hpp new file mode 100644 index 0000000000..e4c40737d6 --- /dev/null +++ b/src/lib/eolian_cxx/grammar/types_definition.hpp | |||
@@ -0,0 +1,38 @@ | |||
1 | #ifndef EOLIAN_CXX_TYPES_DEFINITION_HH | ||
2 | #define EOLIAN_CXX_TYPES_DEFINITION_HH | ||
3 | |||
4 | #include "header_guards.hpp" | ||
5 | #include "eps.hpp" | ||
6 | #include "string.hpp" | ||
7 | #include "sequence.hpp" | ||
8 | #include "kleene.hpp" | ||
9 | #include "header_include_directive.hpp" | ||
10 | #include "type_function_declaration.hpp" | ||
11 | |||
12 | namespace efl { namespace eolian { namespace grammar { | ||
13 | |||
14 | struct types_definition_generator | ||
15 | { | ||
16 | template <typename OutputIterator, typename Context> | ||
17 | bool generate(OutputIterator sink, std::vector<attributes::function_def> const& functions, Context const& ctx) const | ||
18 | { | ||
19 | if(!as_generator(*(type_function_declaration())) | ||
20 | .generate(sink, functions, ctx)) | ||
21 | return false; | ||
22 | return true; | ||
23 | } | ||
24 | }; | ||
25 | |||
26 | template <> | ||
27 | struct is_eager_generator<types_definition_generator> : std::true_type {}; | ||
28 | |||
29 | namespace type_traits { | ||
30 | template <> | ||
31 | struct attributes_needed<types_definition_generator> : std::integral_constant<int, 1> {}; | ||
32 | } | ||
33 | |||
34 | types_definition_generator const types_definition = {}; | ||
35 | |||
36 | } } } | ||
37 | |||
38 | #endif | ||