Autofill: Add WalletIntegrationAvailable() to components.
[chromium-blink-merge.git] / tools / gn / ninja_binary_target_writer_unittest.cc
blobdf5f5a7168d32989bcce0b1c39bee0b511c84a9e
1 // Copyright (c) 2013 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #include <sstream>
7 #include "testing/gtest/include/gtest/gtest.h"
8 #include "tools/gn/ninja_binary_target_writer.h"
9 #include "tools/gn/target.h"
10 #include "tools/gn/test_with_scope.h"
12 TEST(NinjaBinaryTargetWriter, SourceSet) {
13 TestWithScope setup;
14 Err err;
16 setup.build_settings()->SetBuildDir(SourceDir("//out/Debug/"));
17 setup.settings()->set_target_os(Settings::WIN);
19 Target target(setup.settings(), Label(SourceDir("//foo/"), "bar"));
20 target.set_output_type(Target::SOURCE_SET);
21 target.visibility().SetPublic();
22 target.sources().push_back(SourceFile("//foo/input1.cc"));
23 target.sources().push_back(SourceFile("//foo/input2.cc"));
24 // Also test object files, which should be just passed through to the
25 // dependents to link.
26 target.sources().push_back(SourceFile("//foo/input3.o"));
27 target.sources().push_back(SourceFile("//foo/input4.obj"));
28 target.SetToolchain(setup.toolchain());
29 ASSERT_TRUE(target.OnResolved(&err));
31 // Source set itself.
33 std::ostringstream out;
34 NinjaBinaryTargetWriter writer(&target, out);
35 writer.Run();
37 const char expected[] =
38 "defines =\n"
39 "include_dirs =\n"
40 "cflags =\n"
41 "cflags_c =\n"
42 "cflags_cc =\n"
43 "cflags_objc =\n"
44 "cflags_objcc =\n"
45 "root_out_dir = .\n"
46 "target_out_dir = obj/foo\n"
47 "target_output_name = bar\n"
48 "\n"
49 "build obj/foo/bar.input1.o: cxx ../../foo/input1.cc\n"
50 "build obj/foo/bar.input2.o: cxx ../../foo/input2.cc\n"
51 "\n"
52 "build obj/foo/bar.stamp: stamp obj/foo/bar.input1.o "
53 "obj/foo/bar.input2.o ../../foo/input3.o ../../foo/input4.obj\n";
54 std::string out_str = out.str();
55 EXPECT_EQ(expected, out_str);
58 // A shared library that depends on the source set.
59 Target shlib_target(setup.settings(), Label(SourceDir("//foo/"), "shlib"));
60 shlib_target.set_output_type(Target::SHARED_LIBRARY);
61 shlib_target.public_deps().push_back(LabelTargetPair(&target));
62 shlib_target.SetToolchain(setup.toolchain());
63 ASSERT_TRUE(shlib_target.OnResolved(&err));
66 std::ostringstream out;
67 NinjaBinaryTargetWriter writer(&shlib_target, out);
68 writer.Run();
70 const char expected[] =
71 "defines =\n"
72 "include_dirs =\n"
73 "cflags =\n"
74 "cflags_c =\n"
75 "cflags_cc =\n"
76 "cflags_objc =\n"
77 "cflags_objcc =\n"
78 "root_out_dir = .\n"
79 "target_out_dir = obj/foo\n"
80 "target_output_name = libshlib\n"
81 "\n"
82 "\n"
83 // Ordering of the obj files here should come out in the order
84 // specified, with the target's first, followed by the source set's, in
85 // order.
86 "build ./libshlib.so: solink obj/foo/bar.input1.o "
87 "obj/foo/bar.input2.o ../../foo/input3.o ../../foo/input4.obj "
88 "|| obj/foo/bar.stamp\n"
89 " ldflags =\n"
90 " libs =\n"
91 " output_extension = .so\n";
92 std::string out_str = out.str();
93 EXPECT_EQ(expected, out_str);
96 // A static library that depends on the source set (should not link it).
97 Target stlib_target(setup.settings(), Label(SourceDir("//foo/"), "stlib"));
98 stlib_target.set_output_type(Target::STATIC_LIBRARY);
99 stlib_target.public_deps().push_back(LabelTargetPair(&target));
100 stlib_target.SetToolchain(setup.toolchain());
101 ASSERT_TRUE(stlib_target.OnResolved(&err));
104 std::ostringstream out;
105 NinjaBinaryTargetWriter writer(&stlib_target, out);
106 writer.Run();
108 const char expected[] =
109 "defines =\n"
110 "include_dirs =\n"
111 "cflags =\n"
112 "cflags_c =\n"
113 "cflags_cc =\n"
114 "cflags_objc =\n"
115 "cflags_objcc =\n"
116 "root_out_dir = .\n"
117 "target_out_dir = obj/foo\n"
118 "target_output_name = libstlib\n"
119 "\n"
120 "\n"
121 // There are no sources so there are no params to alink. (In practice
122 // this will probably fail in the archive tool.)
123 "build obj/foo/libstlib.a: alink || obj/foo/bar.stamp\n"
124 " ldflags =\n"
125 " libs =\n"
126 " output_extension = \n";
127 std::string out_str = out.str();
128 EXPECT_EQ(expected, out_str);
131 // Make the static library 'complete', which means it should be linked.
132 stlib_target.set_complete_static_lib(true);
134 std::ostringstream out;
135 NinjaBinaryTargetWriter writer(&stlib_target, out);
136 writer.Run();
138 const char expected[] =
139 "defines =\n"
140 "include_dirs =\n"
141 "cflags =\n"
142 "cflags_c =\n"
143 "cflags_cc =\n"
144 "cflags_objc =\n"
145 "cflags_objcc =\n"
146 "root_out_dir = .\n"
147 "target_out_dir = obj/foo\n"
148 "target_output_name = libstlib\n"
149 "\n"
150 "\n"
151 // Ordering of the obj files here should come out in the order
152 // specified, with the target's first, followed by the source set's, in
153 // order.
154 "build obj/foo/libstlib.a: alink obj/foo/bar.input1.o "
155 "obj/foo/bar.input2.o ../../foo/input3.o ../../foo/input4.obj "
156 "|| obj/foo/bar.stamp\n"
157 " ldflags =\n"
158 " libs =\n"
159 " output_extension = \n";
160 std::string out_str = out.str();
161 EXPECT_EQ(expected, out_str);
165 // This tests that output extension overrides apply, and input dependencies
166 // are applied.
167 TEST(NinjaBinaryTargetWriter, ProductExtensionAndInputDeps) {
168 TestWithScope setup;
169 Err err;
171 setup.build_settings()->SetBuildDir(SourceDir("//out/Debug/"));
172 setup.settings()->set_target_os(Settings::LINUX);
174 // An action for our library to depend on.
175 Target action(setup.settings(), Label(SourceDir("//foo/"), "action"));
176 action.set_output_type(Target::ACTION_FOREACH);
177 action.visibility().SetPublic();
178 action.SetToolchain(setup.toolchain());
179 ASSERT_TRUE(action.OnResolved(&err));
181 // A shared library w/ the product_extension set to a custom value.
182 Target target(setup.settings(), Label(SourceDir("//foo/"), "shlib"));
183 target.set_output_type(Target::SHARED_LIBRARY);
184 target.set_output_extension(std::string("so.6"));
185 target.sources().push_back(SourceFile("//foo/input1.cc"));
186 target.sources().push_back(SourceFile("//foo/input2.cc"));
187 target.public_deps().push_back(LabelTargetPair(&action));
188 target.SetToolchain(setup.toolchain());
189 ASSERT_TRUE(target.OnResolved(&err));
191 std::ostringstream out;
192 NinjaBinaryTargetWriter writer(&target, out);
193 writer.Run();
195 const char expected[] =
196 "defines =\n"
197 "include_dirs =\n"
198 "cflags =\n"
199 "cflags_c =\n"
200 "cflags_cc =\n"
201 "cflags_objc =\n"
202 "cflags_objcc =\n"
203 "root_out_dir = .\n"
204 "target_out_dir = obj/foo\n"
205 "target_output_name = libshlib\n"
206 "\n"
207 "build obj/foo/shlib.inputdeps.stamp: stamp obj/foo/action.stamp\n"
208 "build obj/foo/libshlib.input1.o: cxx ../../foo/input1.cc"
209 " || obj/foo/shlib.inputdeps.stamp\n"
210 "build obj/foo/libshlib.input2.o: cxx ../../foo/input2.cc"
211 " || obj/foo/shlib.inputdeps.stamp\n"
212 "\n"
213 "build ./libshlib.so.6: solink obj/foo/libshlib.input1.o "
214 // The order-only dependency here is stricly unnecessary since the
215 // sources list this as an order-only dep. See discussion in the code
216 // that writes this.
217 "obj/foo/libshlib.input2.o || obj/foo/action.stamp\n"
218 " ldflags =\n"
219 " libs =\n"
220 " output_extension = .so.6\n";
222 std::string out_str = out.str();
223 EXPECT_EQ(expected, out_str);
226 TEST(NinjaBinaryTargetWriter, EmptyProductExtension) {
227 TestWithScope setup;
228 Err err;
230 setup.build_settings()->SetBuildDir(SourceDir("//out/Debug/"));
231 setup.settings()->set_target_os(Settings::LINUX);
233 // This test is the same as ProductExtension, except that
234 // we call set_output_extension("") and ensure that we still get the default.
235 Target target(setup.settings(), Label(SourceDir("//foo/"), "shlib"));
236 target.set_output_type(Target::SHARED_LIBRARY);
237 target.set_output_extension(std::string());
238 target.sources().push_back(SourceFile("//foo/input1.cc"));
239 target.sources().push_back(SourceFile("//foo/input2.cc"));
241 target.SetToolchain(setup.toolchain());
242 ASSERT_TRUE(target.OnResolved(&err));
244 std::ostringstream out;
245 NinjaBinaryTargetWriter writer(&target, out);
246 writer.Run();
248 const char expected[] =
249 "defines =\n"
250 "include_dirs =\n"
251 "cflags =\n"
252 "cflags_c =\n"
253 "cflags_cc =\n"
254 "cflags_objc =\n"
255 "cflags_objcc =\n"
256 "root_out_dir = .\n"
257 "target_out_dir = obj/foo\n"
258 "target_output_name = libshlib\n"
259 "\n"
260 "build obj/foo/libshlib.input1.o: cxx ../../foo/input1.cc\n"
261 "build obj/foo/libshlib.input2.o: cxx ../../foo/input2.cc\n"
262 "\n"
263 "build ./libshlib.so: solink obj/foo/libshlib.input1.o "
264 "obj/foo/libshlib.input2.o\n"
265 " ldflags =\n"
266 " libs =\n"
267 " output_extension = .so\n";
269 std::string out_str = out.str();
270 EXPECT_EQ(expected, out_str);
273 TEST(NinjaBinaryTargetWriter, SourceSetDataDeps) {
274 TestWithScope setup;
275 setup.build_settings()->SetBuildDir(SourceDir("//out/Debug/"));
276 setup.settings()->set_target_os(Settings::LINUX);
278 Err err;
280 // This target is a data (runtime) dependency of the intermediate target.
281 Target data(setup.settings(), Label(SourceDir("//foo/"), "data_target"));
282 data.set_output_type(Target::EXECUTABLE);
283 data.visibility().SetPublic();
284 data.SetToolchain(setup.toolchain());
285 ASSERT_TRUE(data.OnResolved(&err));
287 // Intermediate source set target.
288 Target inter(setup.settings(), Label(SourceDir("//foo/"), "inter"));
289 inter.set_output_type(Target::SOURCE_SET);
290 inter.visibility().SetPublic();
291 inter.data_deps().push_back(LabelTargetPair(&data));
292 inter.SetToolchain(setup.toolchain());
293 inter.sources().push_back(SourceFile("//foo/inter.cc"));
294 ASSERT_TRUE(inter.OnResolved(&err)) << err.message();
296 // Write out the intermediate target.
297 std::ostringstream inter_out;
298 NinjaBinaryTargetWriter inter_writer(&inter, inter_out);
299 inter_writer.Run();
301 // The intermediate source set will be a stamp file that depends on the
302 // object files, and will have an order-only dependency on its data dep and
303 // data file.
304 const char inter_expected[] =
305 "defines =\n"
306 "include_dirs =\n"
307 "cflags =\n"
308 "cflags_c =\n"
309 "cflags_cc =\n"
310 "cflags_objc =\n"
311 "cflags_objcc =\n"
312 "root_out_dir = .\n"
313 "target_out_dir = obj/foo\n"
314 "target_output_name = inter\n"
315 "\n"
316 "build obj/foo/inter.inter.o: cxx ../../foo/inter.cc\n"
317 "\n"
318 "build obj/foo/inter.stamp: stamp obj/foo/inter.inter.o || "
319 "./data_target\n";
320 EXPECT_EQ(inter_expected, inter_out.str());
322 // Final target.
323 Target exe(setup.settings(), Label(SourceDir("//foo/"), "exe"));
324 exe.set_output_type(Target::EXECUTABLE);
325 exe.public_deps().push_back(LabelTargetPair(&inter));
326 exe.SetToolchain(setup.toolchain());
327 exe.sources().push_back(SourceFile("//foo/final.cc"));
328 ASSERT_TRUE(exe.OnResolved(&err));
330 std::ostringstream final_out;
331 NinjaBinaryTargetWriter final_writer(&exe, final_out);
332 final_writer.Run();
334 // The final output depends on both object files (one from the final target,
335 // one from the source set) and has an order-only dependency on the source
336 // set's stamp file and the final target's data file. The source set stamp
337 // dependency will create an implicit order-only dependency on the data
338 // target.
339 const char final_expected[] =
340 "defines =\n"
341 "include_dirs =\n"
342 "cflags =\n"
343 "cflags_c =\n"
344 "cflags_cc =\n"
345 "cflags_objc =\n"
346 "cflags_objcc =\n"
347 "root_out_dir = .\n"
348 "target_out_dir = obj/foo\n"
349 "target_output_name = exe\n"
350 "\n"
351 "build obj/foo/exe.final.o: cxx ../../foo/final.cc\n"
352 "\n"
353 "build ./exe: link obj/foo/exe.final.o obj/foo/inter.inter.o || "
354 "obj/foo/inter.stamp\n"
355 " ldflags =\n"
356 " libs =\n"
357 " output_extension = \n";
358 EXPECT_EQ(final_expected, final_out.str());