1 // Copyright 2010 The Kyua Authors.
2 // All rights reserved.
3 //
4 // Redistribution and use in source and binary forms, with or without
5 // modification, are permitted provided that the following conditions are
6 // met:
7 //
8 // * Redistributions of source code must retain the above copyright
9 //   notice, this list of conditions and the following disclaimer.
10 // * Redistributions in binary form must reproduce the above copyright
11 //   notice, this list of conditions and the following disclaimer in the
12 //   documentation and/or other materials provided with the distribution.
13 // * Neither the name of Google Inc. nor the names of its contributors
14 //   may be used to endorse or promote products derived from this software
15 //   without specific prior written permission.
16 //
17 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
18 // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
19 // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
20 // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
21 // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
22 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
23 // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
24 // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
25 // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
26 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
27 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
28 
29 #include "engine/kyuafile.hpp"
30 
31 extern "C" {
32 #include <unistd.h>
33 }
34 
35 #include <stdexcept>
36 #include <typeinfo>
37 
38 #include <atf-c++.hpp>
39 #include <lutok/operations.hpp>
40 #include <lutok/state.ipp>
41 #include <lutok/test_utils.hpp>
42 
43 #include "engine/atf.hpp"
44 #include "engine/exceptions.hpp"
45 #include "engine/plain.hpp"
46 #include "engine/scheduler.hpp"
47 #include "engine/tap.hpp"
48 #include "model/metadata.hpp"
49 #include "model/test_program.hpp"
50 #include "utils/config/tree.ipp"
51 #include "utils/datetime.hpp"
52 #include "utils/env.hpp"
53 #include "utils/format/macros.hpp"
54 #include "utils/fs/operations.hpp"
55 #include "utils/optional.ipp"
56 
57 namespace config = utils::config;
58 namespace datetime = utils::datetime;
59 namespace fs = utils::fs;
60 namespace scheduler = engine::scheduler;
61 
62 using utils::none;
63 
64 
65 ATF_TEST_CASE_WITHOUT_HEAD(kyuafile__load__empty);
ATF_TEST_CASE_BODY(kyuafile__load__empty)66 ATF_TEST_CASE_BODY(kyuafile__load__empty)
67 {
68     scheduler::scheduler_handle handle = scheduler::setup();
69 
70     atf::utils::create_file("config", "syntax(2)\n");
71 
72     const engine::kyuafile suite = engine::kyuafile::load(
73         fs::path("config"), none, config::tree(), handle);
74     ATF_REQUIRE_EQ(fs::path("."), suite.source_root());
75     ATF_REQUIRE_EQ(fs::path("."), suite.build_root());
76     ATF_REQUIRE_EQ(0, suite.test_programs().size());
77 
78     handle.cleanup();
79 }
80 
81 
82 ATF_TEST_CASE_WITHOUT_HEAD(kyuafile__load__real_interfaces);
ATF_TEST_CASE_BODY(kyuafile__load__real_interfaces)83 ATF_TEST_CASE_BODY(kyuafile__load__real_interfaces)
84 {
85     scheduler::scheduler_handle handle = scheduler::setup();
86 
87     atf::utils::create_file(
88         "config",
89         "syntax(2)\n"
90         "test_suite('one-suite')\n"
91         "atf_test_program{name='1st'}\n"
92         "atf_test_program{name='2nd', test_suite='first'}\n"
93         "plain_test_program{name='3rd'}\n"
94         "tap_test_program{name='4th', test_suite='second'}\n"
95         "include('dir/config')\n");
96 
97     fs::mkdir(fs::path("dir"), 0755);
98     atf::utils::create_file(
99         "dir/config",
100         "syntax(2)\n"
101         "atf_test_program{name='1st', test_suite='other-suite'}\n"
102         "include('subdir/config')\n");
103 
104     fs::mkdir(fs::path("dir/subdir"), 0755);
105     atf::utils::create_file(
106         "dir/subdir/config",
107         "syntax(2)\n"
108         "atf_test_program{name='5th', test_suite='last-suite'}\n");
109 
110     atf::utils::create_file("1st", "");
111     atf::utils::create_file("2nd", "");
112     atf::utils::create_file("3rd", "");
113     atf::utils::create_file("4th", "");
114     atf::utils::create_file("dir/1st", "");
115     atf::utils::create_file("dir/subdir/5th", "");
116 
117     const engine::kyuafile suite = engine::kyuafile::load(
118         fs::path("config"), none, config::tree(), handle);
119     ATF_REQUIRE_EQ(fs::path("."), suite.source_root());
120     ATF_REQUIRE_EQ(fs::path("."), suite.build_root());
121     ATF_REQUIRE_EQ(6, suite.test_programs().size());
122 
123     ATF_REQUIRE_EQ("atf", suite.test_programs()[0]->interface_name());
124     ATF_REQUIRE_EQ(fs::path("1st"), suite.test_programs()[0]->relative_path());
125     ATF_REQUIRE_EQ("one-suite", suite.test_programs()[0]->test_suite_name());
126 
127     ATF_REQUIRE_EQ("atf", suite.test_programs()[1]->interface_name());
128     ATF_REQUIRE_EQ(fs::path("2nd"), suite.test_programs()[1]->relative_path());
129     ATF_REQUIRE_EQ("first", suite.test_programs()[1]->test_suite_name());
130 
131     ATF_REQUIRE_EQ("plain", suite.test_programs()[2]->interface_name());
132     ATF_REQUIRE_EQ(fs::path("3rd"), suite.test_programs()[2]->relative_path());
133     ATF_REQUIRE_EQ("one-suite", suite.test_programs()[2]->test_suite_name());
134 
135     ATF_REQUIRE_EQ("tap", suite.test_programs()[3]->interface_name());
136     ATF_REQUIRE_EQ(fs::path("4th"), suite.test_programs()[3]->relative_path());
137     ATF_REQUIRE_EQ("second", suite.test_programs()[3]->test_suite_name());
138 
139     ATF_REQUIRE_EQ("atf", suite.test_programs()[4]->interface_name());
140     ATF_REQUIRE_EQ(fs::path("dir/1st"),
141                    suite.test_programs()[4]->relative_path());
142     ATF_REQUIRE_EQ("other-suite", suite.test_programs()[4]->test_suite_name());
143 
144     ATF_REQUIRE_EQ("atf", suite.test_programs()[5]->interface_name());
145     ATF_REQUIRE_EQ(fs::path("dir/subdir/5th"),
146                    suite.test_programs()[5]->relative_path());
147     ATF_REQUIRE_EQ("last-suite", suite.test_programs()[5]->test_suite_name());
148 
149     handle.cleanup();
150 }
151 
152 
153 ATF_TEST_CASE_WITHOUT_HEAD(kyuafile__load__mock_interfaces);
ATF_TEST_CASE_BODY(kyuafile__load__mock_interfaces)154 ATF_TEST_CASE_BODY(kyuafile__load__mock_interfaces)
155 {
156     scheduler::scheduler_handle handle = scheduler::setup();
157 
158     std::shared_ptr< scheduler::interface > mock_interface(
159         new engine::plain_interface());
160 
161     scheduler::register_interface("some", mock_interface);
162     scheduler::register_interface("random", mock_interface);
163     scheduler::register_interface("names", mock_interface);
164 
165     atf::utils::create_file(
166         "config",
167         "syntax(2)\n"
168         "test_suite('one-suite')\n"
169         "some_test_program{name='1st'}\n"
170         "random_test_program{name='2nd'}\n"
171         "names_test_program{name='3rd'}\n");
172 
173     atf::utils::create_file("1st", "");
174     atf::utils::create_file("2nd", "");
175     atf::utils::create_file("3rd", "");
176 
177     const engine::kyuafile suite = engine::kyuafile::load(
178         fs::path("config"), none, config::tree(), handle);
179     ATF_REQUIRE_EQ(fs::path("."), suite.source_root());
180     ATF_REQUIRE_EQ(fs::path("."), suite.build_root());
181     ATF_REQUIRE_EQ(3, suite.test_programs().size());
182 
183     ATF_REQUIRE_EQ("some", suite.test_programs()[0]->interface_name());
184     ATF_REQUIRE_EQ(fs::path("1st"), suite.test_programs()[0]->relative_path());
185 
186     ATF_REQUIRE_EQ("random", suite.test_programs()[1]->interface_name());
187     ATF_REQUIRE_EQ(fs::path("2nd"), suite.test_programs()[1]->relative_path());
188 
189     ATF_REQUIRE_EQ("names", suite.test_programs()[2]->interface_name());
190     ATF_REQUIRE_EQ(fs::path("3rd"), suite.test_programs()[2]->relative_path());
191 
192     handle.cleanup();
193 }
194 
195 
196 ATF_TEST_CASE_WITHOUT_HEAD(kyuafile__load__metadata);
ATF_TEST_CASE_BODY(kyuafile__load__metadata)197 ATF_TEST_CASE_BODY(kyuafile__load__metadata)
198 {
199     scheduler::scheduler_handle handle = scheduler::setup();
200 
201     atf::utils::create_file(
202         "config",
203         "syntax(2)\n"
204         "atf_test_program{name='1st', test_suite='first',"
205         " allowed_architectures='amd64 i386', timeout=15}\n"
206         "plain_test_program{name='2nd', test_suite='second',"
207         " required_files='foo /bar//baz', required_user='root',"
208         " ['custom.a-number']=123, ['custom.a-bool']=true}\n");
209     atf::utils::create_file("1st", "");
210     atf::utils::create_file("2nd", "");
211 
212     const engine::kyuafile suite = engine::kyuafile::load(
213         fs::path("config"), none, config::tree(), handle);
214     ATF_REQUIRE_EQ(2, suite.test_programs().size());
215 
216     ATF_REQUIRE_EQ("atf", suite.test_programs()[0]->interface_name());
217     ATF_REQUIRE_EQ(fs::path("1st"), suite.test_programs()[0]->relative_path());
218     ATF_REQUIRE_EQ("first", suite.test_programs()[0]->test_suite_name());
219     const model::metadata md1 = model::metadata_builder()
220         .add_allowed_architecture("amd64")
221         .add_allowed_architecture("i386")
222         .set_timeout(datetime::delta(15, 0))
223         .build();
224     ATF_REQUIRE_EQ(md1, suite.test_programs()[0]->get_metadata());
225 
226     ATF_REQUIRE_EQ("plain", suite.test_programs()[1]->interface_name());
227     ATF_REQUIRE_EQ(fs::path("2nd"), suite.test_programs()[1]->relative_path());
228     ATF_REQUIRE_EQ("second", suite.test_programs()[1]->test_suite_name());
229     const model::metadata md2 = model::metadata_builder()
230         .add_required_file(fs::path("foo"))
231         .add_required_file(fs::path("/bar/baz"))
232         .add_custom("a-bool", "true")
233         .add_custom("a-number", "123")
234         .set_required_user("root")
235         .build();
236     ATF_REQUIRE_EQ(md2, suite.test_programs()[1]->get_metadata());
237 
238     handle.cleanup();
239 }
240 
241 
242 ATF_TEST_CASE_WITHOUT_HEAD(kyuafile__load__current_directory);
ATF_TEST_CASE_BODY(kyuafile__load__current_directory)243 ATF_TEST_CASE_BODY(kyuafile__load__current_directory)
244 {
245     scheduler::scheduler_handle handle = scheduler::setup();
246 
247     atf::utils::create_file(
248         "config",
249         "syntax(2)\n"
250         "atf_test_program{name='one', test_suite='first'}\n"
251         "include('config2')\n");
252 
253     atf::utils::create_file(
254         "config2",
255         "syntax(2)\n"
256         "test_suite('second')\n"
257         "atf_test_program{name='two'}\n");
258 
259     atf::utils::create_file("one", "");
260     atf::utils::create_file("two", "");
261 
262     const engine::kyuafile suite = engine::kyuafile::load(
263         fs::path("config"), none, config::tree(), handle);
264     ATF_REQUIRE_EQ(fs::path("."), suite.source_root());
265     ATF_REQUIRE_EQ(fs::path("."), suite.build_root());
266     ATF_REQUIRE_EQ(2, suite.test_programs().size());
267     ATF_REQUIRE_EQ(fs::path("one"), suite.test_programs()[0]->relative_path());
268     ATF_REQUIRE_EQ("first", suite.test_programs()[0]->test_suite_name());
269     ATF_REQUIRE_EQ(fs::path("two"),
270                    suite.test_programs()[1]->relative_path());
271     ATF_REQUIRE_EQ("second", suite.test_programs()[1]->test_suite_name());
272 
273     handle.cleanup();
274 }
275 
276 
277 ATF_TEST_CASE_WITHOUT_HEAD(kyuafile__load__other_directory);
ATF_TEST_CASE_BODY(kyuafile__load__other_directory)278 ATF_TEST_CASE_BODY(kyuafile__load__other_directory)
279 {
280     scheduler::scheduler_handle handle = scheduler::setup();
281 
282     fs::mkdir(fs::path("root"), 0755);
283     atf::utils::create_file(
284         "root/config",
285         "syntax(2)\n"
286         "test_suite('abc')\n"
287         "atf_test_program{name='one'}\n"
288         "include('dir/config')\n");
289 
290     fs::mkdir(fs::path("root/dir"), 0755);
291     atf::utils::create_file(
292         "root/dir/config",
293         "syntax(2)\n"
294         "test_suite('foo')\n"
295         "atf_test_program{name='two', test_suite='def'}\n"
296         "atf_test_program{name='three'}\n");
297 
298     atf::utils::create_file("root/one", "");
299     atf::utils::create_file("root/dir/two", "");
300     atf::utils::create_file("root/dir/three", "");
301 
302     const engine::kyuafile suite = engine::kyuafile::load(
303         fs::path("root/config"), none, config::tree(), handle);
304     ATF_REQUIRE_EQ(fs::path("root"), suite.source_root());
305     ATF_REQUIRE_EQ(fs::path("root"), suite.build_root());
306     ATF_REQUIRE_EQ(3, suite.test_programs().size());
307     ATF_REQUIRE_EQ(fs::path("one"), suite.test_programs()[0]->relative_path());
308     ATF_REQUIRE_EQ("abc", suite.test_programs()[0]->test_suite_name());
309     ATF_REQUIRE_EQ(fs::path("dir/two"),
310                    suite.test_programs()[1]->relative_path());
311     ATF_REQUIRE_EQ("def", suite.test_programs()[1]->test_suite_name());
312     ATF_REQUIRE_EQ(fs::path("dir/three"),
313                    suite.test_programs()[2]->relative_path());
314     ATF_REQUIRE_EQ("foo", suite.test_programs()[2]->test_suite_name());
315 
316     handle.cleanup();
317 }
318 
319 
320 ATF_TEST_CASE_WITHOUT_HEAD(kyuafile__load__build_directory);
ATF_TEST_CASE_BODY(kyuafile__load__build_directory)321 ATF_TEST_CASE_BODY(kyuafile__load__build_directory)
322 {
323     scheduler::scheduler_handle handle = scheduler::setup();
324 
325     fs::mkdir(fs::path("srcdir"), 0755);
326     atf::utils::create_file(
327         "srcdir/config",
328         "syntax(2)\n"
329         "test_suite('abc')\n"
330         "atf_test_program{name='one'}\n"
331         "include('dir/config')\n");
332 
333     fs::mkdir(fs::path("srcdir/dir"), 0755);
334     atf::utils::create_file(
335         "srcdir/dir/config",
336         "syntax(2)\n"
337         "test_suite('foo')\n"
338         "atf_test_program{name='two', test_suite='def'}\n"
339         "atf_test_program{name='three'}\n");
340 
341     fs::mkdir(fs::path("builddir"), 0755);
342     atf::utils::create_file("builddir/one", "");
343     fs::mkdir(fs::path("builddir/dir"), 0755);
344     atf::utils::create_file("builddir/dir/two", "");
345     atf::utils::create_file("builddir/dir/three", "");
346 
347     const engine::kyuafile suite = engine::kyuafile::load(
348         fs::path("srcdir/config"), utils::make_optional(fs::path("builddir")),
349         config::tree(), handle);
350     ATF_REQUIRE_EQ(fs::path("srcdir"), suite.source_root());
351     ATF_REQUIRE_EQ(fs::path("builddir"), suite.build_root());
352     ATF_REQUIRE_EQ(3, suite.test_programs().size());
353     ATF_REQUIRE_EQ(fs::path("builddir/one").to_absolute(),
354                    suite.test_programs()[0]->absolute_path());
355     ATF_REQUIRE_EQ(fs::path("one"), suite.test_programs()[0]->relative_path());
356     ATF_REQUIRE_EQ("abc", suite.test_programs()[0]->test_suite_name());
357     ATF_REQUIRE_EQ(fs::path("builddir/dir/two").to_absolute(),
358                    suite.test_programs()[1]->absolute_path());
359     ATF_REQUIRE_EQ(fs::path("dir/two"),
360                    suite.test_programs()[1]->relative_path());
361     ATF_REQUIRE_EQ("def", suite.test_programs()[1]->test_suite_name());
362     ATF_REQUIRE_EQ(fs::path("builddir/dir/three").to_absolute(),
363                    suite.test_programs()[2]->absolute_path());
364     ATF_REQUIRE_EQ(fs::path("dir/three"),
365                    suite.test_programs()[2]->relative_path());
366     ATF_REQUIRE_EQ("foo", suite.test_programs()[2]->test_suite_name());
367 
368     handle.cleanup();
369 }
370 
371 
372 ATF_TEST_CASE_WITHOUT_HEAD(kyuafile__load__absolute_paths_are_stable);
ATF_TEST_CASE_BODY(kyuafile__load__absolute_paths_are_stable)373 ATF_TEST_CASE_BODY(kyuafile__load__absolute_paths_are_stable)
374 {
375     scheduler::scheduler_handle handle = scheduler::setup();
376 
377     atf::utils::create_file(
378         "config",
379         "syntax(2)\n"
380         "atf_test_program{name='one', test_suite='first'}\n");
381     atf::utils::create_file("one", "");
382 
383     const engine::kyuafile suite = engine::kyuafile::load(
384         fs::path("config"), none, config::tree(), handle);
385 
386     const fs::path previous_dir = fs::current_path();
387     fs::mkdir(fs::path("other"), 0755);
388     // Change the directory.  We want later calls to absolute_path() on the test
389     // programs to return references to previous_dir instead.
390     ATF_REQUIRE(::chdir("other") != -1);
391 
392     ATF_REQUIRE_EQ(fs::path("."), suite.source_root());
393     ATF_REQUIRE_EQ(fs::path("."), suite.build_root());
394     ATF_REQUIRE_EQ(1, suite.test_programs().size());
395     ATF_REQUIRE_EQ(previous_dir / "one",
396                    suite.test_programs()[0]->absolute_path());
397     ATF_REQUIRE_EQ(fs::path("one"), suite.test_programs()[0]->relative_path());
398     ATF_REQUIRE_EQ("first", suite.test_programs()[0]->test_suite_name());
399 
400     handle.cleanup();
401 }
402 
403 
404 ATF_TEST_CASE_WITHOUT_HEAD(kyuafile__load__fs_calls_are_relative);
ATF_TEST_CASE_BODY(kyuafile__load__fs_calls_are_relative)405 ATF_TEST_CASE_BODY(kyuafile__load__fs_calls_are_relative)
406 {
407     scheduler::scheduler_handle handle = scheduler::setup();
408 
409     atf::utils::create_file(
410         "Kyuafile",
411         "syntax(2)\n"
412         "if fs.exists('one') then\n"
413         "    plain_test_program{name='one', test_suite='first'}\n"
414         "end\n"
415         "if fs.exists('two') then\n"
416         "    plain_test_program{name='two', test_suite='first'}\n"
417         "end\n"
418         "include('dir/Kyuafile')\n");
419     atf::utils::create_file("one", "");
420     fs::mkdir(fs::path("dir"), 0755);
421     atf::utils::create_file(
422         "dir/Kyuafile",
423         "syntax(2)\n"
424         "if fs.exists('one') then\n"
425         "    plain_test_program{name='one', test_suite='first'}\n"
426         "end\n"
427         "if fs.exists('two') then\n"
428         "    plain_test_program{name='two', test_suite='first'}\n"
429         "end\n");
430     atf::utils::create_file("dir/two", "");
431 
432     const engine::kyuafile suite = engine::kyuafile::load(
433         fs::path("Kyuafile"), none, config::tree(), handle);
434 
435     ATF_REQUIRE_EQ(2, suite.test_programs().size());
436     ATF_REQUIRE_EQ(fs::current_path() / "one",
437                    suite.test_programs()[0]->absolute_path());
438     ATF_REQUIRE_EQ(fs::current_path() / "dir/two",
439                    suite.test_programs()[1]->absolute_path());
440 
441     handle.cleanup();
442 }
443 
444 
445 /// Verifies that load raises a load_error on a given input.
446 ///
447 /// \param file Name of the file to load.
448 /// \param regex Expression to match on load_error's contents.
449 static void
do_load_error_test(const char * file,const char * regex)450 do_load_error_test(const char* file, const char* regex)
451 {
452     scheduler::scheduler_handle handle = scheduler::setup();
453     ATF_REQUIRE_THROW_RE(engine::load_error, regex,
454                          engine::kyuafile::load(fs::path(file), none,
455                                                 config::tree(), handle));
456     handle.cleanup();
457 }
458 
459 
460 ATF_TEST_CASE_WITHOUT_HEAD(kyuafile__load__test_program_not_basename);
ATF_TEST_CASE_BODY(kyuafile__load__test_program_not_basename)461 ATF_TEST_CASE_BODY(kyuafile__load__test_program_not_basename)
462 {
463     atf::utils::create_file(
464         "config",
465         "syntax(2)\n"
466         "test_suite('abc')\n"
467         "atf_test_program{name='one'}\n"
468         "atf_test_program{name='./ls'}\n");
469 
470     atf::utils::create_file("one", "");
471     do_load_error_test("config", "./ls.*path components");
472 }
473 
474 
475 ATF_TEST_CASE_WITHOUT_HEAD(kyuafile__load__lua_error);
ATF_TEST_CASE_BODY(kyuafile__load__lua_error)476 ATF_TEST_CASE_BODY(kyuafile__load__lua_error)
477 {
478     atf::utils::create_file("config", "this syntax is invalid\n");
479 
480     do_load_error_test("config", ".*");
481 }
482 
483 
484 ATF_TEST_CASE_WITHOUT_HEAD(kyuafile__load__syntax__not_called);
ATF_TEST_CASE_BODY(kyuafile__load__syntax__not_called)485 ATF_TEST_CASE_BODY(kyuafile__load__syntax__not_called)
486 {
487     atf::utils::create_file("config", "");
488 
489     do_load_error_test("config", "syntax.* never called");
490 }
491 
492 
493 
494 ATF_TEST_CASE_WITHOUT_HEAD(kyuafile__load__syntax__deprecated_format);
ATF_TEST_CASE_BODY(kyuafile__load__syntax__deprecated_format)495 ATF_TEST_CASE_BODY(kyuafile__load__syntax__deprecated_format)
496 {
497     atf::utils::create_file("config", "syntax('foo', 1)\n");
498     do_load_error_test("config", "must be 'kyuafile'");
499 
500     atf::utils::create_file("config", "syntax('config', 2)\n");
501     do_load_error_test("config", "only takes one argument");
502 }
503 
504 
505 ATF_TEST_CASE_WITHOUT_HEAD(kyuafile__load__syntax__twice);
ATF_TEST_CASE_BODY(kyuafile__load__syntax__twice)506 ATF_TEST_CASE_BODY(kyuafile__load__syntax__twice)
507 {
508     atf::utils::create_file(
509         "config",
510         "syntax(2)\n"
511         "syntax(2)\n");
512 
513     do_load_error_test("config", "Can only call syntax.* once");
514 }
515 
516 
517 ATF_TEST_CASE_WITHOUT_HEAD(kyuafile__load__syntax__bad_version);
ATF_TEST_CASE_BODY(kyuafile__load__syntax__bad_version)518 ATF_TEST_CASE_BODY(kyuafile__load__syntax__bad_version)
519 {
520     atf::utils::create_file("config", "syntax(12)\n");
521 
522     do_load_error_test("config", "Unsupported file version 12");
523 }
524 
525 
526 ATF_TEST_CASE_WITHOUT_HEAD(kyuafile__load__test_suite__missing);
ATF_TEST_CASE_BODY(kyuafile__load__test_suite__missing)527 ATF_TEST_CASE_BODY(kyuafile__load__test_suite__missing)
528 {
529     atf::utils::create_file(
530         "config",
531         "syntax(2)\n"
532         "plain_test_program{name='one'}");
533 
534     atf::utils::create_file("one", "");
535 
536     do_load_error_test("config", "No test suite defined");
537 }
538 
539 
540 ATF_TEST_CASE_WITHOUT_HEAD(kyuafile__load__test_suite__twice);
ATF_TEST_CASE_BODY(kyuafile__load__test_suite__twice)541 ATF_TEST_CASE_BODY(kyuafile__load__test_suite__twice)
542 {
543     atf::utils::create_file(
544         "config",
545         "syntax(2)\n"
546         "test_suite('foo')\n"
547         "test_suite('bar')\n");
548 
549     do_load_error_test("config", "Can only call test_suite.* once");
550 }
551 
552 
553 ATF_TEST_CASE_WITHOUT_HEAD(kyuafile__load__missing_file);
ATF_TEST_CASE_BODY(kyuafile__load__missing_file)554 ATF_TEST_CASE_BODY(kyuafile__load__missing_file)
555 {
556     do_load_error_test("missing", "Load of 'missing' failed");
557 }
558 
559 
560 ATF_TEST_CASE_WITHOUT_HEAD(kyuafile__load__missing_test_program);
ATF_TEST_CASE_BODY(kyuafile__load__missing_test_program)561 ATF_TEST_CASE_BODY(kyuafile__load__missing_test_program)
562 {
563     atf::utils::create_file(
564         "config",
565         "syntax(2)\n"
566         "atf_test_program{name='one', test_suite='first'}\n"
567         "atf_test_program{name='two', test_suite='first'}\n");
568 
569     atf::utils::create_file("one", "");
570 
571     do_load_error_test("config", "Non-existent.*'two'");
572 }
573 
574 
ATF_INIT_TEST_CASES(tcs)575 ATF_INIT_TEST_CASES(tcs)
576 {
577     scheduler::register_interface(
578         "atf", std::shared_ptr< scheduler::interface >(
579             new engine::atf_interface()));
580     scheduler::register_interface(
581         "plain", std::shared_ptr< scheduler::interface >(
582             new engine::plain_interface()));
583     scheduler::register_interface(
584         "tap", std::shared_ptr< scheduler::interface >(
585             new engine::tap_interface()));
586 
587     ATF_ADD_TEST_CASE(tcs, kyuafile__load__empty);
588     ATF_ADD_TEST_CASE(tcs, kyuafile__load__real_interfaces);
589     ATF_ADD_TEST_CASE(tcs, kyuafile__load__mock_interfaces);
590     ATF_ADD_TEST_CASE(tcs, kyuafile__load__metadata);
591     ATF_ADD_TEST_CASE(tcs, kyuafile__load__current_directory);
592     ATF_ADD_TEST_CASE(tcs, kyuafile__load__other_directory);
593     ATF_ADD_TEST_CASE(tcs, kyuafile__load__build_directory);
594     ATF_ADD_TEST_CASE(tcs, kyuafile__load__absolute_paths_are_stable);
595     ATF_ADD_TEST_CASE(tcs, kyuafile__load__fs_calls_are_relative);
596     ATF_ADD_TEST_CASE(tcs, kyuafile__load__test_program_not_basename);
597     ATF_ADD_TEST_CASE(tcs, kyuafile__load__lua_error);
598     ATF_ADD_TEST_CASE(tcs, kyuafile__load__syntax__not_called);
599     ATF_ADD_TEST_CASE(tcs, kyuafile__load__syntax__deprecated_format);
600     ATF_ADD_TEST_CASE(tcs, kyuafile__load__syntax__twice);
601     ATF_ADD_TEST_CASE(tcs, kyuafile__load__syntax__bad_version);
602     ATF_ADD_TEST_CASE(tcs, kyuafile__load__test_suite__missing);
603     ATF_ADD_TEST_CASE(tcs, kyuafile__load__test_suite__twice);
604     ATF_ADD_TEST_CASE(tcs, kyuafile__load__missing_file);
605     ATF_ADD_TEST_CASE(tcs, kyuafile__load__missing_test_program);
606 }
607