@@ -4981,6 +4981,10 @@ class parser
4981
4981
4982
4982
std::unique_ptr<translation_unit_node> parse_tree = {};
4983
4983
4984
+ // Store declarations generated in a metafunction. Append them after the declaration for the meta function has been
4985
+ // finished.
4986
+ std::vector<std::unique_ptr<declaration_node>> metafunction_declarations = {};
4987
+
4984
4988
// Keep a stack of current capture groups (contracts/decls still being parsed)
4985
4989
std::vector<capture_group*> current_capture_groups = {};
4986
4990
@@ -5152,6 +5156,22 @@ class parser
5152
5156
}
5153
5157
5154
5158
5159
+ auto parse_one_prepare (
5160
+ std::vector<token> const & tokens_,
5161
+ std::deque<token>& generated_tokens_
5162
+ )
5163
+ -> void
5164
+ {
5165
+ parse_kind = " source string during code generation" ;
5166
+
5167
+ // Set per-parse state for the duration of this call
5168
+ tokens = &tokens_;
5169
+ generated_tokens = &generated_tokens_;
5170
+
5171
+ pos = 0 ;
5172
+ }
5173
+
5174
+
5155
5175
// -----------------------------------------------------------------------
5156
5176
// parse_one_statement
5157
5177
//
@@ -5160,22 +5180,17 @@ class parser
5160
5180
//
5161
5181
// Each call parses one statement and returns its parse tree.
5162
5182
//
5163
- auto parse_one_declaration (
5183
+ auto parse_one_statement (
5164
5184
std::vector<token> const & tokens_,
5165
5185
std::deque<token>& generated_tokens_
5166
5186
)
5167
5187
-> std::unique_ptr<statement_node>
5168
5188
{
5169
- parse_kind = " source string during code generation" ;
5170
-
5171
- // Set per-parse state for the duration of this call
5172
- tokens = &tokens_;
5173
- generated_tokens = &generated_tokens_;
5189
+ parse_one_prepare (tokens_, generated_tokens_);
5174
5190
5175
5191
// Parse one declaration - we succeed if the parse succeeded,
5176
5192
// and there were no new errors, and all tokens were consumed
5177
5193
auto errors_size = std::ssize (errors);
5178
- pos = 0 ;
5179
5194
if (auto d = statement ();
5180
5195
d
5181
5196
&& std::ssize (errors) == errors_size
@@ -5188,6 +5203,35 @@ class parser
5188
5203
return {};
5189
5204
}
5190
5205
5206
+ // -----------------------------------------------------------------------
5207
+ // parse_one_declaration
5208
+ //
5209
+ // tokens input tokens for this section of Cpp2 source code
5210
+ // generated_tokens a shared place to store generated tokens
5211
+ //
5212
+ // Each call parses one declaration and returns its parse tree.
5213
+ //
5214
+ auto parse_one_declaration (
5215
+ std::vector<token> const & tokens_,
5216
+ std::deque<token>& generated_tokens_
5217
+ )
5218
+ -> std::unique_ptr<declaration_node>
5219
+ {
5220
+ parse_one_prepare (tokens_, generated_tokens_);
5221
+
5222
+ auto errors_size = std::ssize (errors);
5223
+ if (auto d = declaration ();
5224
+ d
5225
+ && std::ssize (errors) == errors_size
5226
+ && done ()
5227
+ )
5228
+ {
5229
+ return d;
5230
+ }
5231
+
5232
+ return {};
5233
+ }
5234
+
5191
5235
5192
5236
// -----------------------------------------------------------------------
5193
5237
// Get a set of pointers to just the declarations in the given token map section
@@ -5210,7 +5254,8 @@ class parser
5210
5254
if (decl->position ().lineno > last_line) {
5211
5255
break ;
5212
5256
}
5213
- if (decl->position ().lineno >= first_line) {
5257
+ if (decl->position ().lineno >= first_line ||
5258
+ decl->position ().lineno < 0 ) { // Add generated declarations from metafunctions
5214
5259
ret.push_back ( decl.get () );
5215
5260
}
5216
5261
}
@@ -8720,6 +8765,13 @@ class parser
8720
8765
auto n = std::make_unique<translation_unit_node>();
8721
8766
for (auto d = declaration (); d; d = declaration ()) {
8722
8767
n->declarations .push_back ( std::move (d) );
8768
+
8769
+ // Add declarations generated by metafunctions.
8770
+ for (auto & md : metafunction_declarations) {
8771
+ n->declarations .push_back ( std::move (md));
8772
+ }
8773
+
8774
+ metafunction_declarations.clear ();
8723
8775
}
8724
8776
return n;
8725
8777
}
0 commit comments