Branch data Line data Source code
1 : : /*
2 : : * Copyright (c) 2015 Andrew Kelley
3 : : *
4 : : * This file is part of zig, which is MIT licensed.
5 : : * See http://opensource.org/licenses/MIT
6 : : */
7 : :
8 : : #include "ast_render.hpp"
9 : : #include "buffer.hpp"
10 : : #include "codegen.hpp"
11 : : #include "compiler.hpp"
12 : : #include "config.h"
13 : : #include "error.hpp"
14 : : #include "os.hpp"
15 : : #include "target.hpp"
16 : : #include "libc_installation.hpp"
17 : : #include "userland.h"
18 : : #include "glibc.hpp"
19 : :
20 : : #include <stdio.h>
21 : :
22 : 0 : static int print_error_usage(const char *arg0) {
23 : 0 : fprintf(stderr, "See `%s --help` for detailed usage information\n", arg0);
24 : 0 : return EXIT_FAILURE;
25 : : }
26 : :
27 : 0 : static int print_full_usage(const char *arg0, FILE *file, int return_code) {
28 : 0 : fprintf(file,
29 : : "Usage: %s [command] [options]\n"
30 : : "\n"
31 : : "Commands:\n"
32 : : " build build project from build.zig\n"
33 : : " build-exe [source] create executable from source or object files\n"
34 : : " build-lib [source] create library from source or object files\n"
35 : : " build-obj [source] create object from source or assembly\n"
36 : : " builtin show the source code of that @import(\"builtin\")\n"
37 : : " cc C compiler\n"
38 : : " fmt parse files and render in canonical zig format\n"
39 : : " id print the base64-encoded compiler id\n"
40 : : " init-exe initialize a `zig build` application in the cwd\n"
41 : : " init-lib initialize a `zig build` library in the cwd\n"
42 : : " libc [paths_file] Display native libc paths file or validate one\n"
43 : : " run [source] [-- [args]] create executable and run immediately\n"
44 : : " translate-c [source] convert c code to zig code\n"
45 : : " translate-c-2 [source] experimental self-hosted translate-c\n"
46 : : " targets list available compilation targets\n"
47 : : " test [source] create and run a test build\n"
48 : : " version print version number and exit\n"
49 : : " zen print zen of zig and exit\n"
50 : : "\n"
51 : : "Compile Options:\n"
52 : : " --c-source [options] [file] compile C source code\n"
53 : : " --cache-dir [path] override the local cache directory\n"
54 : : " --cache [auto|off|on] build in cache, print output path to stdout\n"
55 : : " --color [auto|off|on] enable or disable colored error messages\n"
56 : : " --disable-gen-h do not generate a C header file (.h)\n"
57 : : " --disable-valgrind omit valgrind client requests in debug builds\n"
58 : : " --enable-valgrind include valgrind client requests release builds\n"
59 : : " -fstack-check enable stack probing in unsafe builds\n"
60 : : " -fno-stack-check disable stack probing in safe builds\n"
61 : : " --emit [asm|bin|llvm-ir] emit a specific file format as compilation output\n"
62 : : " -fPIC enable Position Independent Code\n"
63 : : " -fno-PIC disable Position Independent Code\n"
64 : : " -ftime-report print timing diagnostics\n"
65 : : " --libc [file] Provide a file which specifies libc paths\n"
66 : : " --name [name] override output name\n"
67 : : " --output-dir [dir] override output directory (defaults to cwd)\n"
68 : : " --pkg-begin [name] [path] make pkg available to import and push current pkg\n"
69 : : " --pkg-end pop current pkg\n"
70 : : " --main-pkg-path set the directory of the root package\n"
71 : : " --release-fast build with optimizations on and safety off\n"
72 : : " --release-safe build with optimizations on and safety on\n"
73 : : " --release-small build with size optimizations on and safety off\n"
74 : : " --single-threaded source may assume it is only used single-threaded\n"
75 : : " -dynamic create a shared library (.so; .dll; .dylib)\n"
76 : : " --strip exclude debug symbols\n"
77 : : " -target [name] <arch><sub>-<os>-<abi> see the targets command\n"
78 : : " -target-glibc [version] target a specific glibc version (default: 2.17)\n"
79 : : " --verbose-tokenize enable compiler debug output for tokenization\n"
80 : : " --verbose-ast enable compiler debug output for AST parsing\n"
81 : : " --verbose-link enable compiler debug output for linking\n"
82 : : " --verbose-ir enable compiler debug output for Zig IR\n"
83 : : " --verbose-llvm-ir enable compiler debug output for LLVM IR\n"
84 : : " --verbose-cimport enable compiler debug output for C imports\n"
85 : : " --verbose-cc enable compiler debug output for C compilation\n"
86 : : " -dirafter [dir] same as -isystem but do it last\n"
87 : : " -isystem [dir] add additional search path for other .h files\n"
88 : : " -mllvm [arg] (unsupported) forward an arg to LLVM's option processing\n"
89 : : " --override-std-dir [arg] override path to Zig standard library\n"
90 : : " --override-lib-dir [arg] override path to Zig lib library\n"
91 : : " -ffunction-sections places each function in a seperate section\n"
92 : : "\n"
93 : : "Link Options:\n"
94 : : " --bundle-compiler-rt for static libraries, include compiler-rt symbols\n"
95 : : " --dynamic-linker [path] set the path to ld.so\n"
96 : : " --each-lib-rpath add rpath for each used dynamic library\n"
97 : : " --library [lib] link against lib\n"
98 : : " --forbid-library [lib] make it an error to link against lib\n"
99 : : " --library-path [dir] add a directory to the library search path\n"
100 : : " --linker-script [path] use a custom linker script\n"
101 : : " --version-script [path] provide a version .map file\n"
102 : : " --object [obj] add object file to build\n"
103 : : " -L[dir] alias for --library-path\n"
104 : : " -l[lib] alias for --library\n"
105 : : " -rdynamic add all symbols to the dynamic symbol table\n"
106 : : " -rpath [path] add directory to the runtime library search path\n"
107 : : " --subsystem [subsystem] (windows) /SUBSYSTEM:<subsystem> to the linker\n"
108 : : " -F[dir] (darwin) add search path for frameworks\n"
109 : : " -framework [name] (darwin) link against framework\n"
110 : : " -mios-version-min [ver] (darwin) set iOS deployment target\n"
111 : : " -mmacosx-version-min [ver] (darwin) set Mac OS X deployment target\n"
112 : : " --ver-major [ver] dynamic library semver major version\n"
113 : : " --ver-minor [ver] dynamic library semver minor version\n"
114 : : " --ver-patch [ver] dynamic library semver patch version\n"
115 : : "\n"
116 : : "Test Options:\n"
117 : : " --test-filter [text] skip tests that do not match filter\n"
118 : : " --test-name-prefix [text] add prefix to all tests\n"
119 : : " --test-cmd [arg] specify test execution command one arg at a time\n"
120 : : " --test-cmd-bin appends test binary path to test cmd args\n"
121 : : , arg0);
122 : 0 : return return_code;
123 : : }
124 : :
125 : 0 : static int print_libc_usage(const char *arg0, FILE *file, int return_code) {
126 : 0 : fprintf(file,
127 : : "Usage: %s libc\n"
128 : : "\n"
129 : : "Detect the native libc installation and print the resulting paths to stdout.\n"
130 : : "You can save this into a file and then edit the paths to create a cross\n"
131 : : "compilation libc kit. Then you can pass `--libc [file]` for Zig to use it.\n"
132 : : "\n"
133 : : "When compiling natively and no `--libc` argument provided, Zig automatically\n"
134 : : "creates zig-cache/native_libc.txt so that it does not have to detect libc\n"
135 : : "on every invocation. You can remove this file to have Zig re-detect the\n"
136 : : "native libc.\n"
137 : : "\n\n"
138 : : "Usage: %s libc [file]\n"
139 : : "\n"
140 : : "Parse a libc installation text file and validate it.\n"
141 : : , arg0, arg0);
142 : 0 : return return_code;
143 : : }
144 : :
145 : 0 : static bool arch_available_in_llvm(ZigLLVM_ArchType arch) {
146 : : LLVMTargetRef target_ref;
147 : 0 : char *err_msg = nullptr;
148 : : char triple_string[128];
149 : 0 : sprintf(triple_string, "%s-unknown-unknown-unknown", ZigLLVMGetArchTypeName(arch));
150 : 0 : return !LLVMGetTargetFromTriple(triple_string, &target_ref, &err_msg);
151 : : }
152 : :
153 : 0 : static int print_target_list(FILE *f) {
154 : : ZigTarget native;
155 : 0 : get_native_target(&native);
156 : :
157 : 0 : fprintf(f, "Architectures:\n");
158 : 0 : size_t arch_count = target_arch_count();
159 [ # # ]: 0 : for (size_t arch_i = 0; arch_i < arch_count; arch_i += 1) {
160 : 0 : ZigLLVM_ArchType arch = target_arch_enum(arch_i);
161 [ # # ]: 0 : if (!arch_available_in_llvm(arch))
162 : 0 : continue;
163 : 0 : const char *arch_name = target_arch_name(arch);
164 : 0 : SubArchList sub_arch_list = target_subarch_list(arch);
165 : 0 : size_t sub_count = target_subarch_count(sub_arch_list);
166 [ # # ]: 0 : const char *arch_native_str = (native.arch == arch) ? " (native)" : "";
167 : 0 : fprintf(f, " %s%s\n", arch_name, arch_native_str);
168 [ # # ]: 0 : for (size_t sub_i = 0; sub_i < sub_count; sub_i += 1) {
169 : 0 : ZigLLVM_SubArchType sub = target_subarch_enum(sub_arch_list, sub_i);
170 : 0 : const char *sub_name = target_subarch_name(sub);
171 [ # # ][ # # ]: 0 : const char *sub_native_str = (native.arch == arch && native.sub_arch == sub) ? " (native)" : "";
172 : 0 : fprintf(f, " %s%s\n", sub_name, sub_native_str);
173 : : }
174 : : }
175 : :
176 : 0 : fprintf(f, "\nOperating Systems:\n");
177 : 0 : size_t os_count = target_os_count();
178 [ # # ]: 0 : for (size_t i = 0; i < os_count; i += 1) {
179 : 0 : Os os_type = target_os_enum(i);
180 [ # # ]: 0 : const char *native_str = (native.os == os_type) ? " (native)" : "";
181 : 0 : fprintf(f, " %s%s\n", target_os_name(os_type), native_str);
182 : : }
183 : :
184 : 0 : fprintf(f, "\nC ABIs:\n");
185 : 0 : size_t abi_count = target_abi_count();
186 [ # # ]: 0 : for (size_t i = 0; i < abi_count; i += 1) {
187 : 0 : ZigLLVM_EnvironmentType abi = target_abi_enum(i);
188 [ # # ]: 0 : const char *native_str = (native.abi == abi) ? " (native)" : "";
189 : 0 : fprintf(f, " %s%s\n", target_abi_name(abi), native_str);
190 : : }
191 : :
192 : 0 : fprintf(f, "\nAvailable libcs:\n");
193 : 0 : size_t libc_count = target_libc_count();
194 [ # # ]: 0 : for (size_t i = 0; i < libc_count; i += 1) {
195 : : ZigTarget libc_target;
196 : 0 : target_libc_enum(i, &libc_target);
197 [ # # ]: 0 : bool is_native = native.arch == libc_target.arch &&
198 [ # # ][ # # ]: 0 : native.os == libc_target.os &&
199 : 0 : native.abi == libc_target.abi;
200 [ # # ]: 0 : const char *native_str = is_native ? " (native)" : "";
201 : 0 : fprintf(f, " %s-%s-%s%s\n", target_arch_name(libc_target.arch),
202 : : target_os_name(libc_target.os), target_abi_name(libc_target.abi), native_str);
203 : : }
204 : :
205 : 0 : fprintf(f, "\nAvailable glibc versions:\n");
206 : : ZigGLibCAbi *glibc_abi;
207 : : Error err;
208 [ # # ]: 0 : if ((err = glibc_load_metadata(&glibc_abi, get_zig_lib_dir(), true))) {
209 : 0 : return EXIT_FAILURE;
210 : : }
211 [ # # ]: 0 : for (size_t i = 0; i < glibc_abi->all_versions.length; i += 1) {
212 : 0 : ZigGLibCVersion *this_ver = &glibc_abi->all_versions.at(i);
213 [ # # ]: 0 : bool is_native = native.glibc_version != nullptr &&
214 [ # # ]: 0 : native.glibc_version->major == this_ver->major &&
215 [ # # ][ # # ]: 0 : native.glibc_version->minor == this_ver->minor &&
216 : 0 : native.glibc_version->patch == this_ver->patch;
217 [ # # ]: 0 : const char *native_str = is_native ? " (native)" : "";
218 [ # # ]: 0 : if (this_ver->patch == 0) {
219 : 0 : fprintf(f, " %d.%d%s\n", this_ver->major, this_ver->minor, native_str);
220 : : } else {
221 : 0 : fprintf(f, " %d.%d.%d%s\n", this_ver->major, this_ver->minor, this_ver->patch, native_str);
222 : : }
223 : : }
224 : 0 : return EXIT_SUCCESS;
225 : : }
226 : :
227 : : enum Cmd {
228 : : CmdNone,
229 : : CmdBuild,
230 : : CmdBuiltin,
231 : : CmdRun,
232 : : CmdTargets,
233 : : CmdTest,
234 : : CmdTranslateC,
235 : : CmdTranslateCUserland,
236 : : CmdVersion,
237 : : CmdZen,
238 : : CmdLibC,
239 : : };
240 : :
241 : : static const char *default_zig_cache_name = "zig-cache";
242 : :
243 : : struct CliPkg {
244 : : const char *name;
245 : : const char *path;
246 : : ZigList<CliPkg *> children;
247 : : CliPkg *parent;
248 : : };
249 : :
250 : 16 : static void add_package(CodeGen *g, CliPkg *cli_pkg, ZigPackage *pkg) {
251 [ - + ]: 16 : for (size_t i = 0; i < cli_pkg->children.length; i += 1) {
252 : 0 : CliPkg *child_cli_pkg = cli_pkg->children.at(i);
253 : :
254 : 0 : Buf *dirname = buf_alloc();
255 : 0 : Buf *basename = buf_alloc();
256 : 0 : os_path_split(buf_create_from_str(child_cli_pkg->path), dirname, basename);
257 : :
258 : 0 : ZigPackage *child_pkg = codegen_create_package(g, buf_ptr(dirname), buf_ptr(basename),
259 : 0 : buf_ptr(buf_sprintf("%s.%s", buf_ptr(&pkg->pkg_path), child_cli_pkg->name)));
260 : 0 : auto entry = pkg->package_table.put_unique(buf_create_from_str(child_cli_pkg->name), child_pkg);
261 [ # # ]: 0 : if (entry) {
262 : 0 : ZigPackage *existing_pkg = entry->value;
263 : 0 : Buf *full_path = buf_alloc();
264 : 0 : os_path_join(&existing_pkg->root_src_dir, &existing_pkg->root_src_path, full_path);
265 : 0 : fprintf(stderr, "Unable to add package '%s'->'%s': already exists as '%s'\n",
266 : : child_cli_pkg->name, child_cli_pkg->path, buf_ptr(full_path));
267 : 0 : exit(EXIT_FAILURE);
268 : : }
269 : :
270 : 0 : add_package(g, child_cli_pkg, child_pkg);
271 : : }
272 : 16 : }
273 : :
274 : : enum CacheOpt {
275 : : CacheOptAuto,
276 : : CacheOptOn,
277 : : CacheOptOff,
278 : : };
279 : :
280 : 18 : static bool get_cache_opt(CacheOpt opt, bool default_value) {
281 [ + - - - ]: 18 : switch (opt) {
282 : 18 : case CacheOptAuto:
283 : 18 : return default_value;
284 : 0 : case CacheOptOn:
285 : 0 : return true;
286 : 0 : case CacheOptOff:
287 : 0 : return false;
288 : : }
289 : 0 : zig_unreachable();
290 : : }
291 : :
292 : 0 : static int zig_error_no_build_file(void) {
293 : 0 : fprintf(stderr,
294 : : "No 'build.zig' file found, in the current directory or any parent directories.\n"
295 : : "Initialize a 'build.zig' template file with `zig init-lib` or `zig init-exe`,\n"
296 : : "or see `zig --help` for more options.\n"
297 : : );
298 : 0 : return EXIT_FAILURE;
299 : : }
300 : :
301 : : extern "C" int ZigClang_main(int argc, char **argv);
302 : :
303 : 98 : int main(int argc, char **argv) {
304 : 98 : stage2_attach_segfault_handler();
305 : :
306 : 98 : char *arg0 = argv[0];
307 : : Error err;
308 : :
309 [ + - ][ + + ]: 98 : if (argc == 2 && strcmp(argv[1], "BUILD_INFO") == 0) {
310 : 2 : printf("%s\n%s\n%s\n%s\n%s\n%s\n",
311 : : ZIG_CMAKE_BINARY_DIR,
312 : : ZIG_CXX_COMPILER,
313 : : ZIG_LLVM_CONFIG_EXE,
314 : : ZIG_LLD_INCLUDE_PATH,
315 : : ZIG_LLD_LIBRARIES,
316 : : ZIG_DIA_GUIDS_LIB);
317 : 98 : return 0;
318 : : }
319 : :
320 [ + - ][ + + ]: 96 : if (argc >= 2 && (strcmp(argv[1], "cc") == 0 ||
[ + + ]
321 [ + + ]: 26 : strcmp(argv[1], "-cc1") == 0 || strcmp(argv[1], "-cc1as") == 0))
322 : : {
323 : 78 : return ZigClang_main(argc, argv);
324 : : }
325 : :
326 : : // Must be before all os.hpp function calls.
327 : 18 : os_init();
328 : :
329 [ # # ][ - + ]: 18 : if (argc == 2 && strcmp(argv[1], "id") == 0) {
330 : : Buf *compiler_id;
331 [ # # ]: 0 : if ((err = get_compiler_id(&compiler_id))) {
332 : 0 : fprintf(stderr, "Unable to determine compiler id: %s\n", err_str(err));
333 : 0 : return EXIT_FAILURE;
334 : : }
335 : 0 : printf("%s\n", buf_ptr(compiler_id));
336 : 0 : return EXIT_SUCCESS;
337 : : }
338 : :
339 : : enum InitKind {
340 : : InitKindNone,
341 : : InitKindExe,
342 : : InitKindLib,
343 : : };
344 : 18 : InitKind init_kind = InitKindNone;
345 [ + - ]: 18 : if (argc >= 2) {
346 : 18 : const char *init_cmd = argv[1];
347 [ - + ]: 18 : if (strcmp(init_cmd, "init-exe") == 0) {
348 : 0 : init_kind = InitKindExe;
349 [ - + ]: 18 : } else if (strcmp(init_cmd, "init-lib") == 0) {
350 : 0 : init_kind = InitKindLib;
351 : : }
352 [ - + ]: 18 : if (init_kind != InitKindNone) {
353 [ # # ]: 0 : if (argc >= 3) {
354 : 0 : fprintf(stderr, "Unexpected extra argument: %s\n", argv[2]);
355 : 0 : return print_error_usage(arg0);
356 : : }
357 : 0 : Buf *cmd_template_path = buf_alloc();
358 : 0 : os_path_join(get_zig_special_dir(get_zig_lib_dir()), buf_create_from_str(init_cmd), cmd_template_path);
359 : 0 : Buf *build_zig_path = buf_alloc();
360 : 0 : os_path_join(cmd_template_path, buf_create_from_str("build.zig"), build_zig_path);
361 : 0 : Buf *src_dir_path = buf_alloc();
362 : 0 : os_path_join(cmd_template_path, buf_create_from_str("src"), src_dir_path);
363 : 0 : Buf *main_zig_path = buf_alloc();
364 : 0 : os_path_join(src_dir_path, buf_create_from_str("main.zig"), main_zig_path);
365 : :
366 : 0 : Buf *cwd = buf_alloc();
367 [ # # ]: 0 : if ((err = os_get_cwd(cwd))) {
368 : 0 : fprintf(stderr, "Unable to get cwd: %s\n", err_str(err));
369 : 0 : return EXIT_FAILURE;
370 : : }
371 : 0 : Buf *cwd_basename = buf_alloc();
372 : 0 : os_path_split(cwd, nullptr, cwd_basename);
373 : :
374 : 0 : Buf *build_zig_contents = buf_alloc();
375 [ # # ]: 0 : if ((err = os_fetch_file_path(build_zig_path, build_zig_contents))) {
376 : 0 : fprintf(stderr, "Unable to read %s: %s\n", buf_ptr(build_zig_path), err_str(err));
377 : 0 : return EXIT_FAILURE;
378 : : }
379 : 0 : Buf *modified_build_zig_contents = buf_alloc();
380 [ # # ]: 0 : for (size_t i = 0; i < buf_len(build_zig_contents); i += 1) {
381 : 0 : char c = buf_ptr(build_zig_contents)[i];
382 [ # # ]: 0 : if (c == '$') {
383 : 0 : buf_append_buf(modified_build_zig_contents, cwd_basename);
384 : : } else {
385 : 0 : buf_append_char(modified_build_zig_contents, c);
386 : : }
387 : : }
388 : :
389 : 0 : Buf *main_zig_contents = buf_alloc();
390 [ # # ]: 0 : if ((err = os_fetch_file_path(main_zig_path, main_zig_contents))) {
391 : 0 : fprintf(stderr, "Unable to read %s: %s\n", buf_ptr(main_zig_path), err_str(err));
392 : 0 : return EXIT_FAILURE;
393 : : }
394 : :
395 : 0 : Buf *out_build_zig_path = buf_create_from_str("build.zig");
396 : 0 : Buf *out_src_dir_path = buf_create_from_str("src");
397 : 0 : Buf *out_main_zig_path = buf_alloc();
398 : 0 : os_path_join(out_src_dir_path, buf_create_from_str("main.zig"), out_main_zig_path);
399 : :
400 : : bool already_exists;
401 [ # # ]: 0 : if ((err = os_file_exists(out_build_zig_path, &already_exists))) {
402 : 0 : fprintf(stderr, "Unable test existence of %s: %s\n", buf_ptr(out_build_zig_path), err_str(err));
403 : 0 : return EXIT_FAILURE;
404 : : }
405 [ # # ]: 0 : if (already_exists) {
406 : 0 : fprintf(stderr, "This file would be overwritten: %s\n", buf_ptr(out_build_zig_path));
407 : 0 : return EXIT_FAILURE;
408 : : }
409 : :
410 [ # # ]: 0 : if ((err = os_make_dir(out_src_dir_path))) {
411 : 0 : fprintf(stderr, "Unable to make directory: %s: %s\n", buf_ptr(out_src_dir_path), err_str(err));
412 : 0 : return EXIT_FAILURE;
413 : : }
414 [ # # ]: 0 : if ((err = os_write_file(out_build_zig_path, modified_build_zig_contents))) {
415 : 0 : fprintf(stderr, "Unable to write file: %s: %s\n", buf_ptr(out_build_zig_path), err_str(err));
416 : 0 : return EXIT_FAILURE;
417 : : }
418 [ # # ]: 0 : if ((err = os_write_file(out_main_zig_path, main_zig_contents))) {
419 : 0 : fprintf(stderr, "Unable to write file: %s: %s\n", buf_ptr(out_main_zig_path), err_str(err));
420 : 0 : return EXIT_FAILURE;
421 : : }
422 : 0 : fprintf(stderr, "Created %s\n", buf_ptr(out_build_zig_path));
423 : 0 : fprintf(stderr, "Created %s\n", buf_ptr(out_main_zig_path));
424 [ # # ]: 0 : if (init_kind == InitKindExe) {
425 : 0 : fprintf(stderr, "\nNext, try `zig build --help` or `zig build run`\n");
426 [ # # ]: 0 : } else if (init_kind == InitKindLib) {
427 : 0 : fprintf(stderr, "\nNext, try `zig build --help` or `zig build test`\n");
428 : : } else {
429 : 0 : zig_unreachable();
430 : : }
431 : :
432 : 18 : return EXIT_SUCCESS;
433 : : }
434 : : }
435 : :
436 : 18 : Cmd cmd = CmdNone;
437 : 18 : EmitFileType emit_file_type = EmitFileTypeBinary;
438 : 18 : const char *in_file = nullptr;
439 : 18 : Buf *output_dir = nullptr;
440 : 18 : bool strip = false;
441 : 18 : bool is_dynamic = false;
442 : 18 : OutType out_type = OutTypeUnknown;
443 : 18 : const char *out_name = nullptr;
444 : 18 : bool verbose_tokenize = false;
445 : 18 : bool verbose_ast = false;
446 : 18 : bool verbose_link = false;
447 : 18 : bool verbose_ir = false;
448 : 18 : bool verbose_llvm_ir = false;
449 : 18 : bool verbose_cimport = false;
450 : 18 : bool verbose_cc = false;
451 : 18 : ErrColor color = ErrColorAuto;
452 : 18 : CacheOpt enable_cache = CacheOptAuto;
453 : 18 : Buf *dynamic_linker = nullptr;
454 : 18 : const char *libc_txt = nullptr;
455 : 18 : ZigList<const char *> clang_argv = {0};
456 : 18 : ZigList<const char *> lib_dirs = {0};
457 : 18 : ZigList<const char *> link_libs = {0};
458 : 18 : ZigList<const char *> forbidden_link_libs = {0};
459 : 18 : ZigList<const char *> framework_dirs = {0};
460 : 18 : ZigList<const char *> frameworks = {0};
461 : 18 : bool have_libc = false;
462 : 18 : const char *target_string = nullptr;
463 : 18 : bool rdynamic = false;
464 : 18 : const char *mmacosx_version_min = nullptr;
465 : 18 : const char *mios_version_min = nullptr;
466 : 18 : const char *linker_script = nullptr;
467 : 18 : Buf *version_script = nullptr;
468 : 18 : const char *target_glibc = nullptr;
469 : 18 : ZigList<const char *> rpath_list = {0};
470 : 18 : bool each_lib_rpath = false;
471 : 18 : ZigList<const char *> objects = {0};
472 : 18 : ZigList<CFile *> c_source_files = {0};
473 : 18 : const char *test_filter = nullptr;
474 : 18 : const char *test_name_prefix = nullptr;
475 : 18 : size_t ver_major = 0;
476 : 18 : size_t ver_minor = 0;
477 : 18 : size_t ver_patch = 0;
478 : 18 : bool timing_info = false;
479 : 18 : const char *cache_dir = nullptr;
480 : 18 : CliPkg *cur_pkg = allocate<CliPkg>(1);
481 : 18 : BuildMode build_mode = BuildModeDebug;
482 : 18 : ZigList<const char *> test_exec_args = {0};
483 : 18 : int runtime_args_start = -1;
484 : 18 : bool system_linker_hack = false;
485 : 18 : TargetSubsystem subsystem = TargetSubsystemAuto;
486 : 18 : bool want_single_threaded = false;
487 : 18 : bool disable_gen_h = false;
488 : 18 : bool bundle_compiler_rt = false;
489 : 18 : Buf *override_std_dir = nullptr;
490 : 18 : Buf *override_lib_dir = nullptr;
491 : 18 : Buf *main_pkg_path = nullptr;
492 : 18 : ValgrindSupport valgrind_support = ValgrindSupportAuto;
493 : 18 : WantPIC want_pic = WantPICAuto;
494 : 18 : WantStackCheck want_stack_check = WantStackCheckAuto;
495 : 18 : bool function_sections = false;
496 : :
497 : 18 : ZigList<const char *> llvm_argv = {0};
498 : 18 : llvm_argv.append("zig (LLVM option parsing)");
499 : :
500 [ + + ][ + - ]: 18 : if (argc >= 2 && strcmp(argv[1], "build") == 0) {
501 : 2 : Buf zig_exe_path_buf = BUF_INIT;
502 [ - + ]: 2 : if ((err = os_self_exe_path(&zig_exe_path_buf))) {
503 : 0 : fprintf(stderr, "Unable to determine path to zig's own executable\n");
504 : 0 : return EXIT_FAILURE;
505 : : }
506 : 2 : const char *zig_exe_path = buf_ptr(&zig_exe_path_buf);
507 : 2 : const char *build_file = nullptr;
508 : :
509 : 2 : init_all_targets();
510 : :
511 : 2 : ZigList<const char *> args = {0};
512 : 2 : args.append(NULL); // placeholder
513 : 2 : args.append(zig_exe_path);
514 : 2 : args.append(NULL); // placeholder
515 : 2 : args.append(NULL); // placeholder
516 [ + + ]: 6 : for (int i = 2; i < argc; i += 1) {
517 [ - + ]: 4 : if (strcmp(argv[i], "--help") == 0) {
518 : 0 : args.append(argv[i]);
519 [ + + ][ - + ]: 4 : } else if (i + 1 < argc && strcmp(argv[i], "--build-file") == 0) {
520 : 0 : build_file = argv[i + 1];
521 : 0 : i += 1;
522 [ + + ][ - + ]: 4 : } else if (i + 1 < argc && strcmp(argv[i], "--cache-dir") == 0) {
523 : 0 : cache_dir = argv[i + 1];
524 : 0 : i += 1;
525 [ + + ][ - + ]: 4 : } else if (i + 1 < argc && strcmp(argv[i], "--override-std-dir") == 0) {
526 : 0 : override_std_dir = buf_create_from_str(argv[i + 1]);
527 : 0 : i += 1;
528 : :
529 : 0 : args.append("--override-std-dir");
530 : 0 : args.append(buf_ptr(override_std_dir));
531 [ + + ][ - + ]: 4 : } else if (i + 1 < argc && strcmp(argv[i], "--override-lib-dir") == 0) {
532 : 0 : override_lib_dir = buf_create_from_str(argv[i + 1]);
533 : 0 : i += 1;
534 : :
535 : 0 : args.append("--override-lib-dir");
536 : 0 : args.append(buf_ptr(override_lib_dir));
537 : : } else {
538 : 4 : args.append(argv[i]);
539 : : }
540 : : }
541 : :
542 [ + - ]: 2 : Buf *zig_lib_dir = (override_lib_dir == nullptr) ? get_zig_lib_dir() : override_lib_dir;
543 : :
544 : 2 : Buf *build_runner_path = buf_alloc();
545 : 2 : os_path_join(get_zig_special_dir(zig_lib_dir), buf_create_from_str("build_runner.zig"), build_runner_path);
546 : :
547 : : ZigTarget target;
548 : 2 : get_native_target(&target);
549 : :
550 [ - + ]: 2 : Buf *build_file_buf = buf_create_from_str((build_file != nullptr) ? build_file : "build.zig");
551 : 2 : Buf build_file_abs = os_path_resolve(&build_file_buf, 1);
552 : 2 : Buf build_file_basename = BUF_INIT;
553 : 2 : Buf build_file_dirname = BUF_INIT;
554 : 2 : os_path_split(&build_file_abs, &build_file_dirname, &build_file_basename);
555 : :
556 : : for (;;) {
557 : : bool build_file_exists;
558 [ - + ]: 4 : if ((err = os_file_exists(&build_file_abs, &build_file_exists))) {
559 : 0 : fprintf(stderr, "unable to check existence of '%s': %s\n", buf_ptr(&build_file_abs), err_str(err));
560 : 0 : return 1;
561 : : }
562 [ + + ]: 4 : if (build_file_exists)
563 : 2 : break;
564 : :
565 [ - + ]: 2 : if (build_file != nullptr) {
566 : : // they asked for a specific build file path. only look for that one
567 : 0 : return zig_error_no_build_file();
568 : : }
569 : :
570 : 2 : Buf *next_dir = buf_alloc();
571 : 2 : os_path_dirname(&build_file_dirname, next_dir);
572 [ - + ]: 2 : if (buf_eql_buf(&build_file_dirname, next_dir)) {
573 : : // no more parent directories to search, give up
574 : 0 : return zig_error_no_build_file();
575 : : }
576 : 2 : os_path_join(next_dir, &build_file_basename, &build_file_abs);
577 : 2 : buf_init_from_buf(&build_file_dirname, next_dir);
578 : 2 : }
579 : :
580 : 2 : Buf full_cache_dir = BUF_INIT;
581 [ + - ]: 2 : if (cache_dir == nullptr) {
582 : 2 : os_path_join(&build_file_dirname, buf_create_from_str(default_zig_cache_name), &full_cache_dir);
583 : : } else {
584 : 0 : Buf *cache_dir_buf = buf_create_from_str(cache_dir);
585 : 0 : full_cache_dir = os_path_resolve(&cache_dir_buf, 1);
586 : : }
587 : :
588 : : CodeGen *g = codegen_create(main_pkg_path, build_runner_path, &target, OutTypeExe,
589 : 2 : BuildModeDebug, override_lib_dir, override_std_dir, nullptr, &full_cache_dir, false);
590 : 2 : g->valgrind_support = valgrind_support;
591 : 2 : g->enable_time_report = timing_info;
592 : 2 : codegen_set_out_name(g, buf_create_from_str("build"));
593 : :
594 : 2 : args.items[2] = buf_ptr(&build_file_dirname);
595 : 2 : args.items[3] = buf_ptr(&full_cache_dir);
596 : :
597 : 2 : ZigPackage *build_pkg = codegen_create_package(g, buf_ptr(&build_file_dirname),
598 : 2 : buf_ptr(&build_file_basename), "std.special");
599 : 2 : g->root_package->package_table.put(buf_create_from_str("@build"), build_pkg);
600 : 2 : g->enable_cache = get_cache_opt(enable_cache, true);
601 : 2 : codegen_build_and_link(g);
602 : :
603 : : Termination term;
604 : 2 : args.items[0] = buf_ptr(&g->output_file_path);
605 : 2 : os_spawn_process(args, &term);
606 [ - + ][ + - ]: 2 : if (term.how != TerminationIdClean || term.code != 0) {
607 : 0 : fprintf(stderr, "\nBuild failed. The following command failed:\n");
608 : 0 : const char *prefix = "";
609 [ # # ]: 0 : for (size_t i = 0; i < args.length; i += 1) {
610 : 0 : fprintf(stderr, "%s%s", prefix, args.at(i));
611 : 0 : prefix = " ";
612 : : }
613 : 0 : fprintf(stderr, "\n");
614 : : }
615 [ + - ]: 2 : return (term.how == TerminationIdClean) ? term.code : -1;
616 [ + - ][ - + ]: 16 : } else if (argc >= 2 && strcmp(argv[1], "fmt") == 0) {
617 : 0 : return stage2_fmt(argc, argv);
618 : : }
619 : :
620 [ + + ]: 116 : for (int i = 1; i < argc; i += 1) {
621 : 100 : char *arg = argv[i];
622 : :
623 [ + + ]: 100 : if (arg[0] == '-') {
624 [ - + ]: 68 : if (strcmp(arg, "--") == 0) {
625 [ # # ]: 0 : if (cmd == CmdRun) {
626 : 0 : runtime_args_start = i + 1;
627 : 0 : break; // rest of the args are for the program
628 : : } else {
629 : 0 : fprintf(stderr, "Unexpected end-of-parameter mark: %s\n", arg);
630 : : }
631 [ - + ]: 68 : } else if (strcmp(arg, "--release-fast") == 0) {
632 : 0 : build_mode = BuildModeFastRelease;
633 [ - + ]: 68 : } else if (strcmp(arg, "--release-safe") == 0) {
634 : 0 : build_mode = BuildModeSafeRelease;
635 [ - + ]: 68 : } else if (strcmp(arg, "--release-small") == 0) {
636 : 0 : build_mode = BuildModeSmallRelease;
637 [ - + ]: 68 : } else if (strcmp(arg, "--help") == 0) {
638 [ # # ]: 0 : if (cmd == CmdLibC) {
639 : 0 : return print_libc_usage(arg0, stdout, EXIT_SUCCESS);
640 : : } else {
641 : 0 : return print_full_usage(arg0, stdout, EXIT_SUCCESS);
642 : : }
643 [ - + ]: 68 : } else if (strcmp(arg, "--strip") == 0) {
644 : 0 : strip = true;
645 [ - + ]: 68 : } else if (strcmp(arg, "-dynamic") == 0) {
646 : 0 : is_dynamic = true;
647 [ - + ]: 68 : } else if (strcmp(arg, "--verbose-tokenize") == 0) {
648 : 0 : verbose_tokenize = true;
649 [ - + ]: 68 : } else if (strcmp(arg, "--verbose-ast") == 0) {
650 : 0 : verbose_ast = true;
651 [ - + ]: 68 : } else if (strcmp(arg, "--verbose-link") == 0) {
652 : 0 : verbose_link = true;
653 [ - + ]: 68 : } else if (strcmp(arg, "--verbose-ir") == 0) {
654 : 0 : verbose_ir = true;
655 [ - + ]: 68 : } else if (strcmp(arg, "--verbose-llvm-ir") == 0) {
656 : 0 : verbose_llvm_ir = true;
657 [ - + ]: 68 : } else if (strcmp(arg, "--verbose-cimport") == 0) {
658 : 0 : verbose_cimport = true;
659 [ - + ]: 68 : } else if (strcmp(arg, "--verbose-cc") == 0) {
660 : 0 : verbose_cc = true;
661 [ - + ]: 68 : } else if (strcmp(arg, "-rdynamic") == 0) {
662 : 0 : rdynamic = true;
663 [ - + ]: 68 : } else if (strcmp(arg, "--each-lib-rpath") == 0) {
664 : 0 : each_lib_rpath = true;
665 [ - + ]: 68 : } else if (strcmp(arg, "-ftime-report") == 0) {
666 : 0 : timing_info = true;
667 [ - + ]: 68 : } else if (strcmp(arg, "--enable-valgrind") == 0) {
668 : 0 : valgrind_support = ValgrindSupportEnabled;
669 [ - + ]: 68 : } else if (strcmp(arg, "--disable-valgrind") == 0) {
670 : 0 : valgrind_support = ValgrindSupportDisabled;
671 [ - + ]: 68 : } else if (strcmp(arg, "-fPIC") == 0) {
672 : 0 : want_pic = WantPICEnabled;
673 [ - + ]: 68 : } else if (strcmp(arg, "-fno-PIC") == 0) {
674 : 0 : want_pic = WantPICDisabled;
675 [ - + ]: 68 : } else if (strcmp(arg, "-fstack-check") == 0) {
676 : 0 : want_stack_check = WantStackCheckEnabled;
677 [ - + ]: 68 : } else if (strcmp(arg, "-fno-stack-check") == 0) {
678 : 0 : want_stack_check = WantStackCheckDisabled;
679 [ - + ]: 68 : } else if (strcmp(arg, "--system-linker-hack") == 0) {
680 : 0 : system_linker_hack = true;
681 [ + + ]: 68 : } else if (strcmp(arg, "--single-threaded") == 0) {
682 : 8 : want_single_threaded = true;
683 [ - + ]: 60 : } else if (strcmp(arg, "--disable-gen-h") == 0) {
684 : 0 : disable_gen_h = true;
685 [ - + ]: 60 : } else if (strcmp(arg, "--bundle-compiler-rt") == 0) {
686 : 0 : bundle_compiler_rt = true;
687 [ - + ]: 60 : } else if (strcmp(arg, "--test-cmd-bin") == 0) {
688 : 0 : test_exec_args.append(nullptr);
689 [ - + ][ # # ]: 60 : } else if (arg[1] == 'L' && arg[2] != 0) {
690 : : // alias for --library-path
691 : 0 : lib_dirs.append(&arg[2]);
692 [ - + ][ # # ]: 60 : } else if (arg[1] == 'l' && arg[2] != 0) {
693 : : // alias for --library
694 : 0 : const char *l = &arg[2];
695 [ # # ]: 0 : if (strcmp(l, "c") == 0)
696 : 0 : have_libc = true;
697 : 0 : link_libs.append(l);
698 [ - + ][ # # ]: 60 : } else if (arg[1] == 'F' && arg[2] != 0) {
699 : 0 : framework_dirs.append(&arg[2]);
700 [ - + ]: 60 : } else if (strcmp(arg, "--pkg-begin") == 0) {
701 [ # # ]: 0 : if (i + 2 >= argc) {
702 : 0 : fprintf(stderr, "Expected 2 arguments after --pkg-begin\n");
703 : 0 : return print_error_usage(arg0);
704 : : }
705 : 0 : CliPkg *new_cur_pkg = allocate<CliPkg>(1);
706 : 0 : i += 1;
707 : 0 : new_cur_pkg->name = argv[i];
708 : 0 : i += 1;
709 : 0 : new_cur_pkg->path = argv[i];
710 : 0 : new_cur_pkg->parent = cur_pkg;
711 : 0 : cur_pkg->children.append(new_cur_pkg);
712 : 0 : cur_pkg = new_cur_pkg;
713 [ - + ]: 60 : } else if (strcmp(arg, "--pkg-end") == 0) {
714 [ # # ]: 0 : if (cur_pkg->parent == nullptr) {
715 : 0 : fprintf(stderr, "Encountered --pkg-end with no matching --pkg-begin\n");
716 : 0 : return EXIT_FAILURE;
717 : : }
718 : 0 : cur_pkg = cur_pkg->parent;
719 [ - + ]: 60 : } else if (strcmp(arg, "-ffunction-sections") == 0) {
720 : 0 : function_sections = true;
721 [ - + ]: 60 : } else if (i + 1 >= argc) {
722 : 0 : fprintf(stderr, "Expected another argument after %s\n", arg);
723 : 0 : return print_error_usage(arg0);
724 : : } else {
725 : 60 : i += 1;
726 [ - + ]: 60 : if (strcmp(arg, "--output-dir") == 0) {
727 : 0 : output_dir = buf_create_from_str(argv[i]);
728 [ - + ]: 60 : } else if (strcmp(arg, "--color") == 0) {
729 [ # # ]: 0 : if (strcmp(argv[i], "auto") == 0) {
730 : 0 : color = ErrColorAuto;
731 [ # # ]: 0 : } else if (strcmp(argv[i], "on") == 0) {
732 : 0 : color = ErrColorOn;
733 [ # # ]: 0 : } else if (strcmp(argv[i], "off") == 0) {
734 : 0 : color = ErrColorOff;
735 : : } else {
736 : 0 : fprintf(stderr, "--color options are 'auto', 'on', or 'off'\n");
737 : 0 : return print_error_usage(arg0);
738 : : }
739 [ - + ]: 60 : } else if (strcmp(arg, "--cache") == 0) {
740 [ # # ]: 0 : if (strcmp(argv[i], "auto") == 0) {
741 : 0 : enable_cache = CacheOptAuto;
742 [ # # ]: 0 : } else if (strcmp(argv[i], "on") == 0) {
743 : 0 : enable_cache = CacheOptOn;
744 [ # # ]: 0 : } else if (strcmp(argv[i], "off") == 0) {
745 : 0 : enable_cache = CacheOptOff;
746 : : } else {
747 : 0 : fprintf(stderr, "--cache options are 'auto', 'on', or 'off'\n");
748 : 0 : return print_error_usage(arg0);
749 : : }
750 [ - + ]: 60 : } else if (strcmp(arg, "--emit") == 0) {
751 [ # # ]: 0 : if (strcmp(argv[i], "asm") == 0) {
752 : 0 : emit_file_type = EmitFileTypeAssembly;
753 [ # # ]: 0 : } else if (strcmp(argv[i], "bin") == 0) {
754 : 0 : emit_file_type = EmitFileTypeBinary;
755 [ # # ]: 0 : } else if (strcmp(argv[i], "llvm-ir") == 0) {
756 : 0 : emit_file_type = EmitFileTypeLLVMIr;
757 : : } else {
758 : 0 : fprintf(stderr, "--emit options are 'asm', 'bin', or 'llvm-ir'\n");
759 : 0 : return print_error_usage(arg0);
760 : : }
761 [ + + ]: 60 : } else if (strcmp(arg, "--name") == 0) {
762 : 16 : out_name = argv[i];
763 [ - + ]: 44 : } else if (strcmp(arg, "--dynamic-linker") == 0) {
764 : 0 : dynamic_linker = buf_create_from_str(argv[i]);
765 [ - + ]: 44 : } else if (strcmp(arg, "--libc") == 0) {
766 : 0 : libc_txt = argv[i];
767 [ - + ]: 44 : } else if (strcmp(arg, "-isystem") == 0) {
768 : 0 : clang_argv.append("-isystem");
769 : 0 : clang_argv.append(argv[i]);
770 [ - + ]: 44 : } else if (strcmp(arg, "-dirafter") == 0) {
771 : 0 : clang_argv.append("-dirafter");
772 : 0 : clang_argv.append(argv[i]);
773 [ - + ]: 44 : } else if (strcmp(arg, "-mllvm") == 0) {
774 : 0 : clang_argv.append("-mllvm");
775 : 0 : clang_argv.append(argv[i]);
776 : :
777 : 0 : llvm_argv.append(argv[i]);
778 [ - + ]: 44 : } else if (strcmp(arg, "--override-std-dir") == 0) {
779 : 0 : override_std_dir = buf_create_from_str(argv[i]);
780 [ - + ]: 44 : } else if (strcmp(arg, "--override-lib-dir") == 0) {
781 : 0 : override_lib_dir = buf_create_from_str(argv[i]);
782 [ - + ]: 44 : } else if (strcmp(arg, "--main-pkg-path") == 0) {
783 : 0 : main_pkg_path = buf_create_from_str(argv[i]);
784 [ + - ][ - + ]: 44 : } else if (strcmp(arg, "--library-path") == 0 || strcmp(arg, "-L") == 0) {
785 : 0 : lib_dirs.append(argv[i]);
786 [ - + ]: 44 : } else if (strcmp(arg, "-F") == 0) {
787 : 0 : framework_dirs.append(argv[i]);
788 [ + + ][ - + ]: 44 : } else if (strcmp(arg, "--library") == 0 || strcmp(arg, "-l") == 0) {
789 [ + - ]: 4 : if (strcmp(argv[i], "c") == 0)
790 : 4 : have_libc = true;
791 : 4 : link_libs.append(argv[i]);
792 [ - + ]: 40 : } else if (strcmp(arg, "--forbid-library") == 0) {
793 : 0 : forbidden_link_libs.append(argv[i]);
794 [ - + ]: 40 : } else if (strcmp(arg, "--object") == 0) {
795 : 0 : objects.append(argv[i]);
796 [ - + ]: 40 : } else if (strcmp(arg, "--c-source") == 0) {
797 : 0 : CFile *c_file = allocate<CFile>(1);
798 : : for (;;) {
799 [ # # ]: 0 : if (argv[i][0] == '-') {
800 : 0 : c_file->args.append(argv[i]);
801 : 0 : i += 1;
802 [ # # ]: 0 : if (i < argc) {
803 : 0 : continue;
804 : : }
805 : :
806 : 0 : break;
807 : : } else {
808 : 0 : c_file->source_path = argv[i];
809 : 0 : c_source_files.append(c_file);
810 : 0 : break;
811 : : }
812 : : }
813 [ + + ]: 40 : } else if (strcmp(arg, "--cache-dir") == 0) {
814 : 16 : cache_dir = argv[i];
815 [ + + ]: 24 : } else if (strcmp(arg, "-target") == 0) {
816 : 8 : target_string = argv[i];
817 [ - + ]: 16 : } else if (strcmp(arg, "-mmacosx-version-min") == 0) {
818 : 0 : mmacosx_version_min = argv[i];
819 [ - + ]: 16 : } else if (strcmp(arg, "-mios-version-min") == 0) {
820 : 0 : mios_version_min = argv[i];
821 [ - + ]: 16 : } else if (strcmp(arg, "-framework") == 0) {
822 : 0 : frameworks.append(argv[i]);
823 [ - + ]: 16 : } else if (strcmp(arg, "--linker-script") == 0) {
824 : 0 : linker_script = argv[i];
825 [ - + ]: 16 : } else if (strcmp(arg, "--version-script") == 0) {
826 : 0 : version_script = buf_create_from_str(argv[i]);
827 [ - + ]: 16 : } else if (strcmp(arg, "-target-glibc") == 0) {
828 : 0 : target_glibc = argv[i];
829 [ - + ]: 16 : } else if (strcmp(arg, "-rpath") == 0) {
830 : 0 : rpath_list.append(argv[i]);
831 [ - + ]: 16 : } else if (strcmp(arg, "--test-filter") == 0) {
832 : 0 : test_filter = argv[i];
833 [ + - ]: 16 : } else if (strcmp(arg, "--test-name-prefix") == 0) {
834 : 16 : test_name_prefix = argv[i];
835 [ # # ]: 0 : } else if (strcmp(arg, "--ver-major") == 0) {
836 : 0 : ver_major = atoi(argv[i]);
837 [ # # ]: 0 : } else if (strcmp(arg, "--ver-minor") == 0) {
838 : 0 : ver_minor = atoi(argv[i]);
839 [ # # ]: 0 : } else if (strcmp(arg, "--ver-patch") == 0) {
840 : 0 : ver_patch = atoi(argv[i]);
841 [ # # ]: 0 : } else if (strcmp(arg, "--test-cmd") == 0) {
842 : 0 : test_exec_args.append(argv[i]);
843 [ # # ]: 0 : } else if (strcmp(arg, "--subsystem") == 0) {
844 [ # # ]: 0 : if (strcmp(argv[i], "console") == 0) {
845 : 0 : subsystem = TargetSubsystemConsole;
846 [ # # ]: 0 : } else if (strcmp(argv[i], "windows") == 0) {
847 : 0 : subsystem = TargetSubsystemWindows;
848 [ # # ]: 0 : } else if (strcmp(argv[i], "posix") == 0) {
849 : 0 : subsystem = TargetSubsystemPosix;
850 [ # # ]: 0 : } else if (strcmp(argv[i], "native") == 0) {
851 : 0 : subsystem = TargetSubsystemNative;
852 [ # # ]: 0 : } else if (strcmp(argv[i], "efi_application") == 0) {
853 : 0 : subsystem = TargetSubsystemEfiApplication;
854 [ # # ]: 0 : } else if (strcmp(argv[i], "efi_boot_service_driver") == 0) {
855 : 0 : subsystem = TargetSubsystemEfiBootServiceDriver;
856 [ # # ]: 0 : } else if (strcmp(argv[i], "efi_rom") == 0) {
857 : 0 : subsystem = TargetSubsystemEfiRom;
858 [ # # ]: 0 : } else if (strcmp(argv[i], "efi_runtime_driver") == 0) {
859 : 0 : subsystem = TargetSubsystemEfiRuntimeDriver;
860 : : } else {
861 : 0 : fprintf(stderr, "invalid: --subsystem %s\n"
862 : : "Options are:\n"
863 : : " console\n"
864 : : " windows\n"
865 : : " posix\n"
866 : : " native\n"
867 : : " efi_application\n"
868 : : " efi_boot_service_driver\n"
869 : : " efi_rom\n"
870 : : " efi_runtime_driver\n"
871 : 0 : , argv[i]);
872 : 0 : return EXIT_FAILURE;
873 : : }
874 : : } else {
875 : 0 : fprintf(stderr, "Invalid argument: %s\n", arg);
876 : 68 : return print_error_usage(arg0);
877 : : }
878 : : }
879 [ + + ]: 32 : } else if (cmd == CmdNone) {
880 [ - + ]: 16 : if (strcmp(arg, "build-exe") == 0) {
881 : 0 : cmd = CmdBuild;
882 : 0 : out_type = OutTypeExe;
883 [ - + ]: 16 : } else if (strcmp(arg, "build-obj") == 0) {
884 : 0 : cmd = CmdBuild;
885 : 0 : out_type = OutTypeObj;
886 [ - + ]: 16 : } else if (strcmp(arg, "build-lib") == 0) {
887 : 0 : cmd = CmdBuild;
888 : 0 : out_type = OutTypeLib;
889 [ - + ]: 16 : } else if (strcmp(arg, "run") == 0) {
890 : 0 : cmd = CmdRun;
891 : 0 : out_type = OutTypeExe;
892 [ - + ]: 16 : } else if (strcmp(arg, "version") == 0) {
893 : 0 : cmd = CmdVersion;
894 [ - + ]: 16 : } else if (strcmp(arg, "zen") == 0) {
895 : 0 : cmd = CmdZen;
896 [ - + ]: 16 : } else if (strcmp(arg, "libc") == 0) {
897 : 0 : cmd = CmdLibC;
898 [ - + ]: 16 : } else if (strcmp(arg, "translate-c") == 0) {
899 : 0 : cmd = CmdTranslateC;
900 [ - + ]: 16 : } else if (strcmp(arg, "translate-c-2") == 0) {
901 : 0 : cmd = CmdTranslateCUserland;
902 [ + - ]: 16 : } else if (strcmp(arg, "test") == 0) {
903 : 16 : cmd = CmdTest;
904 : 16 : out_type = OutTypeExe;
905 [ # # ]: 0 : } else if (strcmp(arg, "targets") == 0) {
906 : 0 : cmd = CmdTargets;
907 [ # # ]: 0 : } else if (strcmp(arg, "builtin") == 0) {
908 : 0 : cmd = CmdBuiltin;
909 : : } else {
910 : 0 : fprintf(stderr, "Unrecognized command: %s\n", arg);
911 : 0 : return print_error_usage(arg0);
912 : : }
913 : : } else {
914 [ + - - - ]: 16 : switch (cmd) {
915 : 16 : case CmdBuild:
916 : : case CmdRun:
917 : : case CmdTranslateC:
918 : : case CmdTranslateCUserland:
919 : : case CmdTest:
920 : : case CmdLibC:
921 [ + - ]: 16 : if (!in_file) {
922 : 16 : in_file = arg;
923 : : } else {
924 : 0 : fprintf(stderr, "Unexpected extra parameter: %s\n", arg);
925 : 0 : return print_error_usage(arg0);
926 : : }
927 : 16 : break;
928 : 0 : case CmdBuiltin:
929 : : case CmdVersion:
930 : : case CmdZen:
931 : : case CmdTargets:
932 : 0 : fprintf(stderr, "Unexpected extra parameter: %s\n", arg);
933 : 0 : return print_error_usage(arg0);
934 : 0 : case CmdNone:
935 : 0 : zig_unreachable();
936 : : }
937 : : }
938 : : }
939 : :
940 [ - + ]: 16 : if (cur_pkg->parent != nullptr) {
941 : 0 : fprintf(stderr, "Unmatched --pkg-begin\n");
942 : 0 : return EXIT_FAILURE;
943 : : }
944 : :
945 : 16 : init_all_targets();
946 : :
947 : : ZigTarget target;
948 [ + + ]: 16 : if (target_string == nullptr) {
949 : 8 : get_native_target(&target);
950 [ - + ]: 8 : if (target_glibc != nullptr) {
951 : 0 : fprintf(stderr, "-target-glibc provided but no -target parameter\n");
952 : 0 : return print_error_usage(arg0);
953 : : }
954 : : } else {
955 [ - + ]: 8 : if ((err = target_parse_triple(&target, target_string))) {
956 [ # # ][ # # ]: 0 : if (err == ErrorUnknownArchitecture && target.arch != ZigLLVM_UnknownArch) {
957 : 0 : fprintf(stderr, "'%s' requires a sub-architecture. Try one of these:\n",
958 : : target_arch_name(target.arch));
959 : 0 : SubArchList sub_arch_list = target_subarch_list(target.arch);
960 : 0 : size_t subarch_count = target_subarch_count(sub_arch_list);
961 [ # # ]: 0 : for (size_t sub_i = 0; sub_i < subarch_count; sub_i += 1) {
962 : 0 : ZigLLVM_SubArchType sub = target_subarch_enum(sub_arch_list, sub_i);
963 : 0 : fprintf(stderr, " %s%s\n", target_arch_name(target.arch), target_subarch_name(sub));
964 : : }
965 : 0 : return print_error_usage(arg0);
966 : : } else {
967 : 0 : fprintf(stderr, "invalid target: %s\n", err_str(err));
968 : 0 : return print_error_usage(arg0);
969 : : }
970 : : }
971 [ - + ]: 8 : if (target_is_glibc(&target)) {
972 : 0 : target.glibc_version = allocate<ZigGLibCVersion>(1);
973 : :
974 [ # # ]: 0 : if (target_glibc != nullptr) {
975 [ # # ]: 0 : if ((err = target_parse_glibc_version(target.glibc_version, target_glibc))) {
976 : 0 : fprintf(stderr, "invalid glibc version '%s': %s\n", target_glibc, err_str(err));
977 : 0 : return print_error_usage(arg0);
978 : : }
979 : : } else {
980 : : // Default cross-compiling glibc version
981 : 0 : *target.glibc_version = {2, 17, 0};
982 : : }
983 [ - + ]: 8 : } else if (target_glibc != nullptr) {
984 : 0 : fprintf(stderr, "'%s' is not a glibc-compatible target", target_string);
985 : 0 : return print_error_usage(arg0);
986 : : }
987 : : }
988 : :
989 [ - + ][ # # ]: 16 : if (output_dir != nullptr && enable_cache == CacheOptOn) {
990 : 0 : fprintf(stderr, "`--output-dir` is incompatible with --cache on.\n");
991 : 0 : return print_error_usage(arg0);
992 : : }
993 : :
994 [ + + ][ - + ]: 16 : if (target_requires_pic(&target, have_libc) && want_pic == WantPICDisabled) {
[ - + ]
995 : 0 : Buf triple_buf = BUF_INIT;
996 : 0 : target_triple_zig(&triple_buf, &target);
997 : 0 : fprintf(stderr, "`--disable-pic` is incompatible with target '%s'\n", buf_ptr(&triple_buf));
998 : 0 : return print_error_usage(arg0);
999 : : }
1000 : :
1001 [ - + ][ # # ]: 16 : if (emit_file_type != EmitFileTypeBinary && in_file == nullptr) {
1002 : 0 : fprintf(stderr, "A root source file is required when using `--emit asm` or `--emit llvm-ir`\n");
1003 : 0 : return print_error_usage(arg0);
1004 : : }
1005 : :
1006 [ - + ]: 16 : if (llvm_argv.length > 1) {
1007 : 0 : llvm_argv.append(nullptr);
1008 : 0 : ZigLLVMParseCommandLineOptions(llvm_argv.length - 1, llvm_argv.items);
1009 : : }
1010 : :
1011 [ - - + - : 16 : switch (cmd) {
- - - - ]
1012 : 0 : case CmdLibC: {
1013 [ # # ]: 0 : if (in_file) {
1014 : : ZigLibCInstallation libc;
1015 [ # # ]: 0 : if ((err = zig_libc_parse(&libc, buf_create_from_str(in_file), &target, true)))
1016 : 0 : return EXIT_FAILURE;
1017 : 0 : return EXIT_SUCCESS;
1018 : : }
1019 : : ZigLibCInstallation libc;
1020 [ # # ]: 0 : if ((err = zig_libc_find_native(&libc, true)))
1021 : 0 : return EXIT_FAILURE;
1022 : 0 : zig_libc_render(&libc, stdout);
1023 : 0 : return EXIT_SUCCESS;
1024 : : }
1025 : 0 : case CmdBuiltin: {
1026 : : CodeGen *g = codegen_create(main_pkg_path, nullptr, &target,
1027 : 0 : out_type, build_mode, override_lib_dir, override_std_dir, nullptr, nullptr, false);
1028 : 0 : codegen_set_strip(g, strip);
1029 [ # # ]: 0 : for (size_t i = 0; i < link_libs.length; i += 1) {
1030 : 0 : LinkLib *link_lib = codegen_add_link_lib(g, buf_create_from_str(link_libs.at(i)));
1031 : 0 : link_lib->provided_explicitly = true;
1032 : : }
1033 : 0 : g->subsystem = subsystem;
1034 : 0 : g->valgrind_support = valgrind_support;
1035 : 0 : g->want_pic = want_pic;
1036 : 0 : g->want_stack_check = want_stack_check;
1037 : 0 : g->want_single_threaded = want_single_threaded;
1038 : 0 : Buf *builtin_source = codegen_generate_builtin_source(g);
1039 [ # # ]: 0 : if (fwrite(buf_ptr(builtin_source), 1, buf_len(builtin_source), stdout) != buf_len(builtin_source)) {
1040 : 0 : fprintf(stderr, "unable to write to stdout: %s\n", strerror(ferror(stdout)));
1041 : 0 : return EXIT_FAILURE;
1042 : : }
1043 : 0 : return EXIT_SUCCESS;
1044 : : }
1045 : 16 : case CmdRun:
1046 : : case CmdBuild:
1047 : : case CmdTranslateC:
1048 : : case CmdTranslateCUserland:
1049 : : case CmdTest:
1050 : : {
1051 [ - + ][ # # ]: 16 : if (cmd == CmdBuild && !in_file && objects.length == 0 &&
[ # # ][ # # ]
1052 : 0 : c_source_files.length == 0)
1053 : : {
1054 : 0 : fprintf(stderr,
1055 : : "Expected at least one of these things:\n"
1056 : : " * Zig root source file argument\n"
1057 : : " * --object argument\n"
1058 : : " * --c-source argument\n");
1059 : 0 : return print_error_usage(arg0);
1060 [ + - ][ + - ]: 16 : } else if ((cmd == CmdTranslateC || cmd == CmdTranslateCUserland ||
[ - + ]
1061 [ # # ][ - + ]: 16 : cmd == CmdTest || cmd == CmdRun) && !in_file)
1062 : : {
1063 : 0 : fprintf(stderr, "Expected source file argument.\n");
1064 : 0 : return print_error_usage(arg0);
1065 [ - + ][ # # ]: 16 : } else if (cmd == CmdRun && emit_file_type != EmitFileTypeBinary) {
1066 : 0 : fprintf(stderr, "Cannot run non-executable file.\n");
1067 : 0 : return print_error_usage(arg0);
1068 : : }
1069 : :
1070 [ - + ][ # # ]: 16 : assert(cmd != CmdBuild || out_type != OutTypeUnknown);
1071 : :
1072 [ + - ][ - + ]: 16 : bool need_name = (cmd == CmdBuild || cmd == CmdTranslateC || cmd == CmdTranslateCUserland);
[ + - ]
1073 : :
1074 [ - + ]: 16 : if (cmd == CmdRun) {
1075 : 0 : out_name = "run";
1076 : : }
1077 : :
1078 : 16 : Buf *in_file_buf = nullptr;
1079 : :
1080 [ + - ]: 16 : Buf *buf_out_name = (cmd == CmdTest) ? buf_create_from_str("test") :
1081 [ # # ]: 0 : (out_name == nullptr) ? nullptr : buf_create_from_str(out_name);
1082 : :
1083 [ + - ]: 16 : if (in_file) {
1084 : 16 : in_file_buf = buf_create_from_str(in_file);
1085 : :
1086 [ # # ][ - + ]: 16 : if (need_name && buf_out_name == nullptr) {
1087 : 0 : Buf basename = BUF_INIT;
1088 : 0 : os_path_split(in_file_buf, nullptr, &basename);
1089 : 0 : buf_out_name = buf_alloc();
1090 : 16 : os_path_extname(&basename, buf_out_name, nullptr);
1091 : : }
1092 : : }
1093 : :
1094 [ - + ][ # # ]: 16 : if (need_name && buf_out_name == nullptr && c_source_files.length == 1) {
[ # # ]
1095 : 0 : Buf basename = BUF_INIT;
1096 : 0 : os_path_split(buf_create_from_str(c_source_files.at(0)->source_path), nullptr, &basename);
1097 : 0 : buf_out_name = buf_alloc();
1098 : 0 : os_path_extname(&basename, buf_out_name, nullptr);
1099 : : }
1100 : :
1101 [ - + ][ # # ]: 16 : if (need_name && buf_out_name == nullptr) {
1102 : 0 : fprintf(stderr, "--name [name] not provided and unable to infer\n\n");
1103 : 0 : return print_error_usage(arg0);
1104 : : }
1105 : :
1106 [ + - ][ + - ]: 16 : Buf *zig_root_source_file = (cmd == CmdTranslateC || cmd == CmdTranslateCUserland) ?
1107 : : nullptr : in_file_buf;
1108 : :
1109 [ - + ][ # # ]: 16 : if (cmd == CmdRun && buf_out_name == nullptr) {
1110 : 0 : buf_out_name = buf_create_from_str("run");
1111 : : }
1112 : 16 : ZigLibCInstallation *libc = nullptr;
1113 [ - + ]: 16 : if (libc_txt != nullptr) {
1114 : 0 : libc = allocate<ZigLibCInstallation>(1);
1115 [ # # ]: 0 : if ((err = zig_libc_parse(libc, buf_create_from_str(libc_txt), &target, true))) {
1116 : 0 : fprintf(stderr, "Unable to parse --libc text file: %s\n", err_str(err));
1117 : 0 : return EXIT_FAILURE;
1118 : : }
1119 : : }
1120 : : Buf *cache_dir_buf;
1121 [ - + ]: 16 : if (cache_dir == nullptr) {
1122 [ # # ]: 0 : if (cmd == CmdRun) {
1123 : 0 : cache_dir_buf = get_stage1_cache_path();
1124 : : } else {
1125 : 0 : cache_dir_buf = buf_create_from_str(default_zig_cache_name);
1126 : : }
1127 : : } else {
1128 : 16 : cache_dir_buf = buf_create_from_str(cache_dir);
1129 : : }
1130 : 16 : CodeGen *g = codegen_create(main_pkg_path, zig_root_source_file, &target, out_type, build_mode,
1131 : 16 : override_lib_dir, override_std_dir, libc, cache_dir_buf, cmd == CmdTest);
1132 [ - + ]: 16 : if (llvm_argv.length >= 2) codegen_set_llvm_argv(g, llvm_argv.items + 1, llvm_argv.length - 2);
1133 : 16 : g->valgrind_support = valgrind_support;
1134 : 16 : g->want_pic = want_pic;
1135 : 16 : g->want_stack_check = want_stack_check;
1136 : 16 : g->subsystem = subsystem;
1137 : :
1138 : 16 : g->enable_time_report = timing_info;
1139 : 16 : codegen_set_out_name(g, buf_out_name);
1140 : 16 : codegen_set_lib_version(g, ver_major, ver_minor, ver_patch);
1141 : 16 : g->want_single_threaded = want_single_threaded;
1142 : 16 : codegen_set_linker_script(g, linker_script);
1143 : 16 : g->version_script_path = version_script;
1144 [ - + ]: 16 : if (each_lib_rpath)
1145 : 0 : codegen_set_each_lib_rpath(g, each_lib_rpath);
1146 : :
1147 : 16 : codegen_set_clang_argv(g, clang_argv.items, clang_argv.length);
1148 : :
1149 : 16 : codegen_set_strip(g, strip);
1150 : 16 : g->is_dynamic = is_dynamic;
1151 : 16 : g->dynamic_linker_path = dynamic_linker;
1152 : 16 : g->verbose_tokenize = verbose_tokenize;
1153 : 16 : g->verbose_ast = verbose_ast;
1154 : 16 : g->verbose_link = verbose_link;
1155 : 16 : g->verbose_ir = verbose_ir;
1156 : 16 : g->verbose_llvm_ir = verbose_llvm_ir;
1157 : 16 : g->verbose_cimport = verbose_cimport;
1158 : 16 : g->verbose_cc = verbose_cc;
1159 : 16 : g->output_dir = output_dir;
1160 : 16 : g->disable_gen_h = disable_gen_h;
1161 : 16 : g->bundle_compiler_rt = bundle_compiler_rt;
1162 : 16 : codegen_set_errmsg_color(g, color);
1163 : 16 : g->system_linker_hack = system_linker_hack;
1164 : 16 : g->function_sections = function_sections;
1165 : :
1166 [ - + ]: 16 : for (size_t i = 0; i < lib_dirs.length; i += 1) {
1167 : 0 : codegen_add_lib_dir(g, lib_dirs.at(i));
1168 : : }
1169 [ - + ]: 16 : for (size_t i = 0; i < framework_dirs.length; i += 1) {
1170 : 0 : g->framework_dirs.append(framework_dirs.at(i));
1171 : : }
1172 [ + + ]: 20 : for (size_t i = 0; i < link_libs.length; i += 1) {
1173 : 4 : LinkLib *link_lib = codegen_add_link_lib(g, buf_create_from_str(link_libs.at(i)));
1174 : 4 : link_lib->provided_explicitly = true;
1175 : : }
1176 [ - + ]: 16 : for (size_t i = 0; i < forbidden_link_libs.length; i += 1) {
1177 : 0 : Buf *forbidden_link_lib = buf_create_from_str(forbidden_link_libs.at(i));
1178 : 0 : codegen_add_forbidden_lib(g, forbidden_link_lib);
1179 : : }
1180 [ - + ]: 16 : for (size_t i = 0; i < frameworks.length; i += 1) {
1181 : 0 : codegen_add_framework(g, frameworks.at(i));
1182 : : }
1183 [ - + ]: 16 : for (size_t i = 0; i < rpath_list.length; i += 1) {
1184 : 0 : codegen_add_rpath(g, rpath_list.at(i));
1185 : : }
1186 : :
1187 : 16 : codegen_set_rdynamic(g, rdynamic);
1188 [ # # ][ - + ]: 16 : if (mmacosx_version_min && mios_version_min) {
1189 : 0 : fprintf(stderr, "-mmacosx-version-min and -mios-version-min options not allowed together\n");
1190 : 0 : return EXIT_FAILURE;
1191 : : }
1192 : :
1193 [ - + ]: 16 : if (mmacosx_version_min) {
1194 : 0 : codegen_set_mmacosx_version_min(g, buf_create_from_str(mmacosx_version_min));
1195 : : }
1196 : :
1197 [ - + ]: 16 : if (mios_version_min) {
1198 : 0 : codegen_set_mios_version_min(g, buf_create_from_str(mios_version_min));
1199 : : }
1200 : :
1201 [ - + ]: 16 : if (test_filter) {
1202 : 0 : codegen_set_test_filter(g, buf_create_from_str(test_filter));
1203 : : }
1204 : :
1205 [ + - ]: 16 : if (test_name_prefix) {
1206 : 16 : codegen_set_test_name_prefix(g, buf_create_from_str(test_name_prefix));
1207 : : }
1208 : :
1209 : 16 : add_package(g, cur_pkg, g->root_package);
1210 : :
1211 [ + - ][ + - ]: 16 : if (cmd == CmdBuild || cmd == CmdRun || cmd == CmdTest) {
[ + - ]
1212 : 16 : g->c_source_files = c_source_files;
1213 [ - + ]: 16 : for (size_t i = 0; i < objects.length; i += 1) {
1214 : 0 : codegen_add_object(g, buf_create_from_str(objects.at(i)));
1215 : : }
1216 : : }
1217 : :
1218 : :
1219 [ + - ][ - + ]: 16 : if (cmd == CmdBuild || cmd == CmdRun) {
1220 : 0 : codegen_set_emit_file_type(g, emit_file_type);
1221 : :
1222 : 0 : g->enable_cache = get_cache_opt(enable_cache, cmd == CmdRun);
1223 : 0 : codegen_build_and_link(g);
1224 [ # # ]: 0 : if (timing_info)
1225 : 0 : codegen_print_timing_report(g, stdout);
1226 : :
1227 [ # # ]: 0 : if (cmd == CmdRun) {
1228 : 0 : const char *exec_path = buf_ptr(&g->output_file_path);
1229 : 0 : ZigList<const char*> args = {0};
1230 : :
1231 : 0 : args.append(exec_path);
1232 [ # # ]: 0 : if (runtime_args_start != -1) {
1233 [ # # ]: 0 : for (int i = runtime_args_start; i < argc; ++i) {
1234 : 0 : args.append(argv[i]);
1235 : : }
1236 : : }
1237 : 0 : args.append(nullptr);
1238 : :
1239 : 0 : os_execv(exec_path, args.items);
1240 : :
1241 : 0 : args.pop();
1242 : : Termination term;
1243 : 0 : os_spawn_process(args, &term);
1244 : 0 : return term.code;
1245 [ # # ]: 0 : } else if (cmd == CmdBuild) {
1246 [ # # ]: 0 : if (g->enable_cache) {
1247 : : #if defined(ZIG_OS_WINDOWS)
1248 : : buf_replace(&g->output_file_path, '/', '\\');
1249 : : #endif
1250 [ # # ]: 0 : if (printf("%s\n", buf_ptr(&g->output_file_path)) < 0)
1251 : 0 : return EXIT_FAILURE;
1252 : : }
1253 : 0 : return EXIT_SUCCESS;
1254 : : } else {
1255 : 0 : zig_unreachable();
1256 : : }
1257 [ + - ][ - + ]: 16 : } else if (cmd == CmdTranslateC || cmd == CmdTranslateCUserland) {
1258 : 0 : codegen_translate_c(g, in_file_buf, stdout, cmd == CmdTranslateCUserland);
1259 [ # # ]: 0 : if (timing_info)
1260 : 0 : codegen_print_timing_report(g, stderr);
1261 : 0 : return EXIT_SUCCESS;
1262 [ + - ]: 16 : } else if (cmd == CmdTest) {
1263 : 16 : codegen_set_emit_file_type(g, emit_file_type);
1264 : :
1265 : : ZigTarget native;
1266 : 16 : get_native_target(&native);
1267 : :
1268 : 16 : g->enable_cache = get_cache_opt(enable_cache, output_dir == nullptr);
1269 : 16 : codegen_build_and_link(g);
1270 : :
1271 [ - + ]: 16 : if (timing_info) {
1272 : 0 : codegen_print_timing_report(g, stdout);
1273 : : }
1274 : :
1275 : 16 : Buf *test_exe_path_unresolved = &g->output_file_path;
1276 : 16 : Buf *test_exe_path = buf_alloc();
1277 : 16 : *test_exe_path = os_path_resolve(&test_exe_path_unresolved, 1);
1278 : :
1279 [ - + ]: 16 : if (emit_file_type != EmitFileTypeBinary) {
1280 : 0 : fprintf(stderr, "Created %s but skipping execution because it is non executable.\n",
1281 : : buf_ptr(test_exe_path));
1282 : 0 : return 0;
1283 : : }
1284 : :
1285 [ - + ]: 16 : for (size_t i = 0; i < test_exec_args.length; i += 1) {
1286 [ # # ]: 0 : if (test_exec_args.items[i] == nullptr) {
1287 : 0 : test_exec_args.items[i] = buf_ptr(test_exe_path);
1288 : : }
1289 : : }
1290 : :
1291 [ + + ]: 16 : if (!target_can_exec(&native, &target)) {
1292 : 8 : fprintf(stderr, "Created %s but skipping execution because it is non-native.\n",
1293 : : buf_ptr(test_exe_path));
1294 : 8 : return 0;
1295 : : }
1296 : :
1297 : : Termination term;
1298 [ + - ]: 8 : if (test_exec_args.length == 0) {
1299 : 8 : test_exec_args.append(buf_ptr(test_exe_path));
1300 : : }
1301 : 8 : os_spawn_process(test_exec_args, &term);
1302 [ - + ][ + - ]: 8 : if (term.how != TerminationIdClean || term.code != 0) {
1303 : 0 : fprintf(stderr, "\nTests failed. Use the following command to reproduce the failure:\n");
1304 : 0 : fprintf(stderr, "%s\n", buf_ptr(test_exe_path));
1305 : : }
1306 [ + - ]: 16 : return (term.how == TerminationIdClean) ? term.code : -1;
1307 : : } else {
1308 : 0 : zig_unreachable();
1309 : : }
1310 : : }
1311 : 0 : case CmdVersion:
1312 : 0 : printf("%s\n", ZIG_VERSION_STRING);
1313 : 0 : return EXIT_SUCCESS;
1314 : 0 : case CmdZen: {
1315 : : const char *ptr;
1316 : : size_t len;
1317 : 0 : stage2_zen(&ptr, &len);
1318 : 0 : fwrite(ptr, len, 1, stdout);
1319 : 0 : return EXIT_SUCCESS;
1320 : : }
1321 : 0 : case CmdTargets:
1322 : 0 : return print_target_list(stdout);
1323 : 0 : case CmdNone:
1324 : 0 : return print_full_usage(arg0, stderr, EXIT_FAILURE);
1325 : : }
1326 : 0 : }
|