diff options
author | Boris Kolpackov <boris@codesynthesis.com> | 2020-04-28 08:48:53 +0200 |
---|---|---|
committer | Boris Kolpackov <boris@codesynthesis.com> | 2020-05-27 15:47:28 +0200 |
commit | b808c255b6a9ddba085bf5646e7d20ec344f2e2d (patch) | |
tree | 32730291f7e6de8ef0a227905520dd66fb4ec0f3 /libbuild2/parser.hxx | |
parent | 3552356a87402727e663131994fa87f48b3cd4fb (diff) |
Initial support for ad hoc recipes (still work in progress)
Diffstat (limited to 'libbuild2/parser.hxx')
-rw-r--r-- | libbuild2/parser.hxx | 43 |
1 files changed, 36 insertions, 7 deletions
diff --git a/libbuild2/parser.hxx b/libbuild2/parser.hxx index c55e14f..bc01e08 100644 --- a/libbuild2/parser.hxx +++ b/libbuild2/parser.hxx @@ -26,7 +26,9 @@ namespace build2 explicit parser (context& c, stage s = stage::rest) - : fail ("error", &path_), ctx (c), stage_ (s) {} + : fail ("error", &path_), info ("info", &path_), + ctx (c), + stage_ (s) {} // Issue diagnostics and throw failed in case of an error. // @@ -109,6 +111,11 @@ namespace build2 const target_type* = nullptr, string = string ()); + void + parse_recipe (token&, token_type&, + const token&, + small_vector<shared_ptr<adhoc_rule>, 1>&); + // Ad hoc target names inside < ... >. // struct adhoc_names_loc @@ -246,6 +253,9 @@ namespace build2 build2::value value; }; + friend ostream& + operator<< (ostream&, const attribute&); + struct attributes: small_vector<attribute, 1> { location loc; // Start location. @@ -479,6 +489,12 @@ namespace build2 // If qual is not empty, then its pair member should indicate the kind // of qualification: ':' -- target, '/' -- scope. // + // Note that this function is called even during pre-parse with the result + // unused. In this case a valid name will only be provided for variables + // with literal names (for example, $x, $(x)). For computed variables (for + // example, $($x ? X : Y)) it will be empty (along with qual, which can + // only be non-empty for a computed variable). + // virtual lookup lookup_variable (name&& qual, string&& name, const location&); @@ -525,8 +541,14 @@ namespace build2 // If the current token is newline, then get the next token. Otherwise, // fail unless the current token is eos (i.e., optional newline at the end - // of stream). If the after argument is not \0, use it in diagnostics as - // the token after which the newline was expectd. + // of stream). Use the after token in diagnostics as the token after which + // the newline was expected. + // + token_type + next_after_newline (token&, token_type&, const token& after); + + // As above but the after argument is a single-character token. If it is + // \0, then it is ignored. // token_type next_after_newline (token&, token_type&, char after = '\0'); @@ -568,10 +590,10 @@ namespace build2 } void - mode (lexer_mode m, char ps = '\0') + mode (lexer_mode m, char ps = '\0', uintptr_t d = 0) { if (replay_ != replay::play) - lexer_->mode (m, ps); + lexer_->mode (m, ps, nullopt, d); else // As a sanity check, make sure the mode matches the next token. Note // that we don't check the attributes flags or the pair separator @@ -612,8 +634,10 @@ namespace build2 // with the lexer directly (e.g., the keyword() test). Replays also cannot // nest. For now we don't enforce any of this. // - // Note also that the peeked token is not part of the replay, until it - // is "got". + // Note also that the peeked token is not part of the replay until it is + // "got". In particular, this means that we cannot peek past the replay + // sequence (since we will get the peeked token as the first token of + // the replay). // void replay_save () @@ -628,6 +652,8 @@ namespace build2 assert ((replay_ == replay::save && !replay_data_.empty ()) || (replay_ == replay::play && replay_i_ == replay_data_.size ())); + assert (!peeked_); + if (replay_ == replay::save) replay_path_ = path_; // Save old path. @@ -638,6 +664,8 @@ namespace build2 void replay_stop () { + assert (!peeked_); + if (replay_ == replay::play) path_ = replay_path_; // Restore old path. @@ -726,6 +754,7 @@ namespace build2 // protected: const fail_mark fail; + const basic_mark info; // Parser state. // |