aboutsummaryrefslogtreecommitdiff
path: root/build2
diff options
context:
space:
mode:
authorBoris Kolpackov <boris@codesynthesis.com>2016-03-19 09:49:58 +0200
committerBoris Kolpackov <boris@codesynthesis.com>2016-03-28 16:03:34 +0200
commitbfbf2c9d3b2c79e0effa294c69d98b13154c0178 (patch)
treea6079a75131b3bfa74d2514cec73064846292826 /build2
parentcf59a5fa548cfa72ab0b56334afea5c031faf27b (diff)
Change pairs semantics from separated to unseparated
Before we use to recognize 'x @ y' as a pair. Now it has to be written unseparated, as 'x@y'. See tests/pairs for details on the new semantics.
Diffstat (limited to 'build2')
-rw-r--r--build2/parser.cxx43
1 files changed, 29 insertions, 14 deletions
diff --git a/build2/parser.cxx b/build2/parser.cxx
index c7f75b3..e1d63aa 100644
--- a/build2/parser.cxx
+++ b/build2/parser.cxx
@@ -1368,7 +1368,7 @@ namespace build2
{
// If pair is not 0, then it is an index + 1 of the first half of
// the pair for which we are parsing the second halves, e.g.,
- // a={b c d{e f} {}}.
+ // a@{b c d{e f} {}}.
//
// Buffer that is used to collect the complete name in case of
@@ -1380,8 +1380,8 @@ namespace build2
string concat;
// Number of names in the last group. This is used to detect when
- // we need to add an empty first pair element (e.g., {@y}) or when
- // we have a for now unsupported multi-name LHS (e.g., {x y}@z).
+ // we need to add an empty first pair element (e.g., @y) or when
+ // we have a (for now unsupported) multi-name LHS (e.g., {x y}@z).
//
size_t count (0);
@@ -1402,15 +1402,11 @@ namespace build2
}
else if (!first)
{
- // If we are chunking, stop at the next separated token. Unless
- // current or next token is a pair separator, since we want the
- // "x @ y" pair to be parsed as a single chunk.
+ // If we are chunking, stop at the next separated token.
//
- bool p (t.type == type::pair_separator); // Current token.
-
next (t, tt);
- if (chunk && t.separated && (tt != type::pair_separator && !p))
+ if (chunk && t.separated)
break;
}
@@ -1811,12 +1807,15 @@ namespace build2
if (pair != 0)
fail (t) << "nested pair on the right hand side of a pair";
- if (count > 1)
- fail (t) << "multiple names on the left hand side of a pair";
+ // Catch '@@'. Maybe we can use for something later (e.g., escaping).
+ //
+ if (!ns.empty () && ns.back ().pair)
+ fail (t) << "double pair separator";
- if (count == 0)
+ if (t.separated || count == 0)
{
- // Empty LHS, (e.g., {@y}), create an empty name.
+ // Empty LHS, (e.g., @y), create an empty name. The second test
+ // will be in effect if we have something like v=@y.
//
ns.emplace_back (pp,
(dp != nullptr ? *dp : dir_path ()),
@@ -1824,9 +1823,25 @@ namespace build2
string ());
count = 1;
}
+ else if (count > 1)
+ fail (t) << "multiple names on the left hand side of a pair";
ns.back ().pair = true;
tt = peek ();
+
+ // If the next token is separated, then we have an empty RHS. Note
+ // that the case where it is not a name/group (e.g., a newline/eos)
+ // is handled below, once we are out of the loop.
+ //
+ if (peeked ().separated)
+ {
+ ns.emplace_back (pp,
+ (dp != nullptr ? *dp : dir_path ()),
+ (tp != nullptr ? *tp : string ()),
+ string ());
+ count = 0;
+ }
+
continue;
}
@@ -1853,7 +1868,7 @@ namespace build2
fail (t) << "expected name instead of " << t;
}
- // Handle the empty RHS in a pair, (e.g., {y@}).
+ // Handle the empty RHS in a pair, (e.g., y@).
//
if (!ns.empty () && ns.back ().pair)
{