44 " command = cat $in > $out\n" 47 " command = date > $out\n" 49 "build result: cat in_1.cc in-2.O\n"));
51 ASSERT_EQ(3u, state.bindings_.GetRules().size());
52 const Rule* rule = state.
bindings_.GetRules().begin()->second;
55 rule->GetBinding(
"command")->Serialize());
69 " rspfile_content = a\n" 75 " #indented comment\n" 77 " command = cat $in > $out\n" 79 " restat = 1 # comment\n" 81 "build result: cat in_1.cc in-2.O\n" 84 ASSERT_EQ(2u, state.bindings_.GetRules().size());
85 const Rule* rule = state.
bindings_.GetRules().begin()->second;
87 Edge* edge = state.GetNode(
"result", 0)->in_edge();
97 " command = cat $in > $out\n" 99 "build result: cat in_1.cc in-2.O\n" 104 EXPECT_EQ(
"1", state.bindings_.LookupVariable(
"variable"));
110 " command = cat $rspfile > $out\n" 111 " rspfile = $rspfile\n" 112 " rspfile_content = $in\n" 114 "build out: cat_rsp in\n" 115 " rspfile=out.rsp\n"));
117 ASSERT_EQ(2u, state.bindings_.GetRules().size());
118 const Rule* rule = state.
bindings_.GetRules().begin()->second;
121 rule->GetBinding(
"command")->Serialize());
122 EXPECT_EQ(
"[$rspfile]", rule->GetBinding(
"rspfile")->Serialize());
123 EXPECT_EQ(
"[$in]", rule->GetBinding(
"rspfile_content")->Serialize());
129 " command = cat $in_newline > $out\n" 131 "build out: cat_rsp in in2\n" 132 " rspfile=out.rsp\n"));
134 ASSERT_EQ(2u, state.bindings_.GetRules().size());
135 const Rule* rule = state.
bindings_.GetRules().begin()->second;
137 EXPECT_EQ(
"[cat ][$in_newline][ > ][$out]",
138 rule->GetBinding(
"command")->Serialize());
140 Edge* edge = state.edges_[0];
141 EXPECT_EQ(
"cat in\nin2 > out", edge->EvaluateCommand());
146 "l = one-letter-test\n" 148 " command = ld $l $extra $with_under -o $out $in\n" 151 "with_under = -under\n" 152 "build a: link b c\n" 154 "nested2 = $nested1/2\n" 155 "build supernested: link x\n" 156 " extra = $nested2/3\n"));
159 Edge* edge = state.edges_[0];
160 EXPECT_EQ(
"ld one-letter-test -pthread -under -o a b c",
161 edge->EvaluateCommand());
162 EXPECT_EQ(
"1/2", state.bindings_.LookupVariable(
"nested2"));
164 edge = state.edges_[1];
165 EXPECT_EQ(
"ld one-letter-test 1/2/3 -under -o supernested x",
166 edge->EvaluateCommand());
173 " command = cmd $foo $in $out\n" 175 "build inner: cmd a\n" 177 "build outer: cmd b\n" 182 EXPECT_EQ(
"cmd baz a inner", state.edges_[0]->EvaluateCommand());
183 EXPECT_EQ(
"cmd bar b outer", state.edges_[1]->EvaluateCommand());
189 " command = foo bar $\n" 192 "build a: link c $\n" 195 ASSERT_EQ(2u, state.bindings_.GetRules().size());
196 const Rule* rule = state.
bindings_.GetRules().begin()->second;
198 EXPECT_EQ(
"[foo bar baz]", rule->GetBinding(
"command")->Serialize());
206 EXPECT_EQ(
"bar\\baz", state.bindings_.LookupVariable(
"foo"));
207 EXPECT_EQ(
"bar\\ baz", state.bindings_.LookupVariable(
"foo2"));
212 "# this is a comment\n" 213 "foo = not # a comment\n"));
214 EXPECT_EQ(
"not # a comment", state.bindings_.LookupVariable(
"foo"));
220 " command = ${out}bar$$baz$$$\n" 225 EXPECT_EQ(
"$dollar", state.bindings_.LookupVariable(
"x"));
227 EXPECT_EQ(
"$dollarbar$baz$blah", state.edges_[0]->EvaluateCommand());
229 EXPECT_EQ(
"'$dollar'bar$baz$blah", state.edges_[0]->EvaluateCommand());
236 " command = something\n" 237 "build foo$ bar: spaces $$one two$$$ three\n" 240 EXPECT_EQ(state.edges_[0]->outputs_[0]->path(),
"foo bar");
241 EXPECT_EQ(state.edges_[0]->inputs_[0]->path(),
"$one");
242 EXPECT_EQ(state.edges_[0]->inputs_[1]->path(),
"two$ three");
243 EXPECT_EQ(state.edges_[0]->EvaluateCommand(),
"something");
249 " command = cat $in > $out\n" 250 "build out: cat in/1 in//2\n" 252 "build in/2: cat\n"));
264 " command = cat $in > $out\n" 265 "build out: cat in\\1 in\\\\2\n" 267 "build in\\2: cat\n"));
269 Node* node = state.LookupNode(
"in/1");;
272 node = state.LookupNode(
"in/2");
283 " command = cat $in > $out\n" 285 "build $dir/exe: cat src\n"));
294 " command = cat $in > $out\n" 295 "build ./out.o: cat ./bar/baz/../foo.cc\n"));
307 " command = cat $in > $out\n" 308 "build ./out.o: cat ./bar/baz/../foo.cc\n" 309 "build .\\out2.o: cat .\\bar/baz\\..\\foo.cc\n" 310 "build .\\out3.o: cat .\\bar\\baz\\..\\foo3.cc\n" 320 EXPECT_FALSE(state.LookupNode(
".\\bar/baz\\..\\foo.cc"));
321 EXPECT_FALSE(state.LookupNode(
".\\bar/baz\\..\\foo3.cc"));
322 Node* node = state.LookupNode(
"bar/foo.cc");
325 node = state.LookupNode(
"bar/foo3.cc");
334 " command = cat $in > $out\n" 335 "build out1 out2: cat in1\n" 336 "build out1: cat in2\n" 337 "build final: cat out1\n" 346 " command = cat $in > $out\n" 347 "build out: cat in\n" 348 "build out: cat in\n" 355 const char kInput[] =
357 " command = cat $in > $out\n" 358 "build out1 out2: cat in1\n" 359 "build out1: cat in2\n" 360 "build final: cat out1\n";
366 EXPECT_EQ(
"input:5: multiple rules generate out1 [-w dupbuild=err]\n", err);
370 fs_.Create(
"sub.ninja",
372 " command = cat $in > $out\n" 373 "build out1 out2: cat in1\n" 374 "build out1: cat in2\n" 375 "build final: cat out1\n");
376 const char kInput[] =
377 "subninja sub.ninja\n";
383 EXPECT_EQ(
"sub.ninja:5: multiple rules generate out1 [-w dupbuild=err]\n",
392 Node* node = state.LookupNode(
"a");
398 const char kInput[] =
399 "build a: phony a\n";
407 Node* node = state.LookupNode(
"a");
416 " command = rule run $out\n" 417 "build subninja: build include default foo.cc\n" 418 "default subninja\n"));
427 EXPECT_EQ(
"input:1: expected '=', got eof\n" 438 EXPECT_EQ(
"input:1: expected '=', got eof\n" 449 EXPECT_EQ(
"input:1: expected '=', got identifier\n" 471 EXPECT_EQ(
"input:2: expected '=', got identifier\n" 482 EXPECT_EQ(
"input:1: bad $-escape (literal $ must be written as $$)\n" 493 EXPECT_EQ(
"input:2: bad $-escape (literal $ must be written as $$)\n" 524 EXPECT_EQ(
"input:1: unknown build rule 'y'\n" 535 EXPECT_EQ(
"input:1: expected build command name\n" 546 "build x: cat $\n :\n",
548 EXPECT_EQ(
"input:4: expected newline, got ':'\n" 560 EXPECT_EQ(
"input:2: expected 'command =' line\n", err);
570 " command = echo\n", &err));
571 EXPECT_EQ(
"input:3: duplicate rule 'cat'\n" 583 " rspfile = cat.rsp\n", &err));
585 "input:4: rspfile and rspfile_content need to be both specified\n",
594 " command = ${fafsd\n" 597 EXPECT_EQ(
"input:2: bad $-escape (literal $ must be written as $$)\n" 598 " command = ${fafsd\n" 610 "build $.: cat foo\n",
612 EXPECT_EQ(
"input:3: bad $-escape (literal $ must be written as $$)\n" 613 "build $.: cat foo\n" 625 "build $: cat foo\n",
627 EXPECT_EQ(
"input:3: expected ':', got newline ($ also escapes ':')\n" 639 EXPECT_EQ(
"input:1: expected rule name\n" 653 EXPECT_EQ(
"input:3: unexpected variable 'othervar'\n" 664 "build $.: cc bar.cc\n",
666 EXPECT_EQ(
"input:3: bad $-escape (literal $ must be written as $$)\n" 667 "build $.: cc bar.cc\n" 678 EXPECT_EQ(
"input:3: expected variable name\n" 689 "build $: cc bar.cc\n",
691 EXPECT_EQ(
"input:3: expected ':', got newline ($ also escapes ':')\n" 692 "build $: cc bar.cc\n" 703 EXPECT_EQ(
"input:1: expected target name\n" 715 EXPECT_EQ(
"input:1: unknown target 'nonexistent'\n" 716 "default nonexistent\n" 729 EXPECT_EQ(
"input:4: expected newline, got ':'\n" 752 "build $a: r $c\n", &err));
767 " generator = 1\n", &err));
768 EXPECT_EQ(
"input:4: unexpected indent\n", err);
776 EXPECT_EQ(
"input:1: expected pool name\n" 778 " ^ near here", err);
786 EXPECT_EQ(
"input:2: expected 'depth =' line\n", err);
795 "pool foo\n", &err));
796 EXPECT_EQ(
"input:3: duplicate pool 'foo'\n" 807 " depth = -1\n", &err));
808 EXPECT_EQ(
"input:2: invalid pool depth\n" 819 " bar = 1\n", &err));
820 EXPECT_EQ(
"input:2: unexpected variable 'bar'\n" 833 " pool = unnamed_pool\n" 834 "build out: run in\n", &err));
835 EXPECT_EQ(
"input:5: unknown pool name 'unnamed_pool'\n", err);
844 EXPECT_EQ(
"loading 'build.ninja': No such file or directory", err);
852 "build a.o b.o: cc c.cc\n",
862 "build a.o b.o: cc c.cc\n",
864 EXPECT_EQ(
"input:5: multiple outputs aren't (yet?) supported by depslog; " 865 "bring this up on the mailing list if it affects you\n", err);
869 fs_.Create(
"test.ninja",
871 "build $builddir/inner: varref\n");
873 "builddir = some_dir/\n" 875 " command = varref $var\n" 877 "build $builddir/outer: varref\n" 878 "subninja test.ninja\n" 879 "build $builddir/outer2: varref\n"));
882 EXPECT_EQ(
"test.ninja", fs_.files_read_[0]);
888 EXPECT_EQ(
"varref outer", state.edges_[0]->EvaluateCommand());
889 EXPECT_EQ(
"varref inner", state.edges_[1]->EvaluateCommand());
890 EXPECT_EQ(
"varref outer", state.edges_[2]->EvaluateCommand());
897 EXPECT_EQ(
"input:1: loading 'foo.ninja': No such file or directory\n" 898 "subninja foo.ninja\n" 905 fs_.Create(
"test.ninja",
"rule cat\n" 911 "subninja test.ninja\n", &err));
916 fs_.Create(
"rules.ninja",
"rule cat\n" 918 fs_.Create(
"test.ninja",
"include rules.ninja\n" 923 "subninja test.ninja\n" 924 "build y : cat\n", &err));
928 fs_.Create(
"include.ninja",
"var = inner\n");
931 "include include.ninja\n"));
934 EXPECT_EQ(
"include.ninja", fs_.files_read_[0]);
935 EXPECT_EQ(
"inner", state.bindings_.LookupVariable(
"var"));
939 fs_.Create(
"include.ninja",
"build\n");
943 EXPECT_EQ(
"include.ninja:1: expected path\n" 952 " command = cat $in > $out\n" 953 "build foo: cat bar | baz\n"));
955 Edge* edge = state.LookupNode(
"foo")->in_edge();
961 "rule cat\n command = cat $in > $out\n" 962 "build foo: cat bar || baz\n"));
964 Edge* edge = state.LookupNode(
"foo")->in_edge();
971 " command = cat $in > $out\n" 972 "build foo | imp: cat bar\n"));
974 Edge* edge = state.LookupNode(
"imp")->in_edge();
982 " command = cat $in > $out\n" 983 "build foo | : cat bar\n"));
985 Edge* edge = state.LookupNode(
"foo")->in_edge();
993 " command = cat $in > $out\n" 994 "build foo baz | foo baq foo: cat bar\n"));
996 Edge* edge = state.LookupNode(
"foo")->in_edge();
1006 " command = cat $in > $out\n" 1007 "build foo foo foo | foo foo foo foo: cat bar\n"));
1009 Edge* edge = state.LookupNode(
"foo")->in_edge();
1019 " command = cat $in > $out\n" 1020 "build | imp : cat bar\n", &err));
1025 "rule cat\n command = cat $in > $out\n" 1026 "build a: cat foo\n" 1027 "build b: cat foo\n" 1028 "build c: cat foo\n" 1029 "build d: cat foo\n"));
1032 EXPECT_EQ(4u, state.DefaultNodes(&err).size());
1038 "rule cat\n command = cat $in > $out\n" 1039 "build a: cat a\n"));
1042 EXPECT_EQ(0u, state.DefaultNodes(&err).size());
1043 EXPECT_EQ(
"could not determine root nodes of build graph", err);
1048 "rule cat\n command = cat $in > $out\n" 1049 "build a: cat foo\n" 1050 "build b: cat foo\n" 1051 "build c: cat foo\n" 1052 "build d: cat foo\n" 1055 "default $third\n"));
1058 vector<Node*> nodes = state.DefaultNodes(&err);
1070 " description = compilaci\xC3\xB3\n"));
1081 "pool link_pool\r\n" 1082 " depth = 15\r\n\r\n" 1084 " command = something$expand \r\n" 1085 " description = YAY!\r\n",
An implementation of DiskInterface that uses an in-memory representation of disk state.
bool Load(const string &filename, string *err, Lexer *parent=NULL)
Load and parse a file.
void AssertParse(State *state, const char *input, ManifestParserOptions opts)
PhonyCycleAction phony_cycle_action_
Information about a node in the dependency graph: the file, whether it's dirty, mtime, etc.
uint64_t slash_bits() const
bool is_implicit_out(size_t index) const
An edge in the dependency graph; links between Nodes using Rules.
bool is_order_only(size_t index)
bool is_implicit(size_t index)
An invokable build command and associated metadata (description, etc.).
TEST_F(ParserTest, Empty)
void VerifyGraph(const State &state)
void AssertParse(const char *input)
#define ASSERT_NO_FATAL_FAILURE(a)
Global state (file status) for a single run.
DupeEdgeAction dupe_edge_action_
bool ParseTest(const string &input, string *err)
Parse a text string of input. Used by tests.
vector< Node * > outputs_