| author | |
| committer | |
| log | 02886a8b93ccfe652ac5797784bddc398047f7eb |
| tree | 3632552b4d7434277fb0ab88fbfc229ab0585528 |
| parent | c0b774fbc65e3e406a38d37b02fffda7c5d3df26 |
5 files changed, 39 insertions(+), 28 deletions(-)
BRANCH_TODO-1| ... | @@ -1,4 +1,3 @@ | ... | @@ -1,4 +1,3 @@ |
| 1 | * support rpaths in ELF linker code | ||
| 2 | * musl | 1 | * musl |
| 3 | * implement proper parsing of LLD stderr/stdout and exposing compile errors | 2 | * implement proper parsing of LLD stderr/stdout and exposing compile errors |
| 4 | * tests passing with -Dskip-non-native | 3 | * tests passing with -Dskip-non-native |
src/Compilation.zig+2| ... | @@ -316,6 +316,7 @@ pub const InitOptions = struct { | ... | @@ -316,6 +316,7 @@ pub const InitOptions = struct { |
| 316 | function_sections: ?bool = null, | 316 | function_sections: ?bool = null, |
| 317 | linker_allow_shlib_undefined: ?bool = null, | 317 | linker_allow_shlib_undefined: ?bool = null, |
| 318 | linker_bind_global_refs_locally: ?bool = null, | 318 | linker_bind_global_refs_locally: ?bool = null, |
| 319 | each_lib_rpath: ?bool = null, | ||
| 319 | disable_c_depfile: bool = false, | 320 | disable_c_depfile: bool = false, |
| 320 | linker_z_nodelete: bool = false, | 321 | linker_z_nodelete: bool = false, |
| 321 | linker_z_defs: bool = false, | 322 | linker_z_defs: bool = false, |
| ... | @@ -714,6 +715,7 @@ pub fn create(gpa: *Allocator, options: InitOptions) !*Compilation { | ... | @@ -714,6 +715,7 @@ pub fn create(gpa: *Allocator, options: InitOptions) !*Compilation { |
| 714 | .error_return_tracing = error_return_tracing, | 715 | .error_return_tracing = error_return_tracing, |
| 715 | .llvm_cpu_features = llvm_cpu_features, | 716 | .llvm_cpu_features = llvm_cpu_features, |
| 716 | .is_compiler_rt_or_libc = options.is_compiler_rt_or_libc, | 717 | .is_compiler_rt_or_libc = options.is_compiler_rt_or_libc, |
| 718 | .each_lib_rpath = options.each_lib_rpath orelse false, | ||
| 717 | }); | 719 | }); |
| 718 | errdefer bin_file.destroy(); | 720 | errdefer bin_file.destroy(); |
| 719 | comp.* = .{ | 721 | comp.* = .{ |
src/link.zig+1| ... | @@ -65,6 +65,7 @@ pub const Options = struct { | ... | @@ -65,6 +65,7 @@ pub const Options = struct { |
| 65 | dll_export_fns: bool, | 65 | dll_export_fns: bool, |
| 66 | error_return_tracing: bool, | 66 | error_return_tracing: bool, |
| 67 | is_compiler_rt_or_libc: bool, | 67 | is_compiler_rt_or_libc: bool, |
| 68 | each_lib_rpath: bool, | ||
| 68 | gc_sections: ?bool = null, | 69 | gc_sections: ?bool = null, |
| 69 | allow_shlib_undefined: ?bool = null, | 70 | allow_shlib_undefined: ?bool = null, |
| 70 | linker_script: ?[]const u8 = null, | 71 | linker_script: ?[]const u8 = null, |
src/link/Elf.zig+31-27| ... | @@ -1272,6 +1272,8 @@ fn linkWithLLD(self: *Elf, comp: *Compilation) !void { | ... | @@ -1272,6 +1272,8 @@ fn linkWithLLD(self: *Elf, comp: *Compilation) !void { |
| 1272 | ch.hash.add(self.base.options.rdynamic); | 1272 | ch.hash.add(self.base.options.rdynamic); |
| 1273 | ch.hash.addListOfBytes(self.base.options.extra_lld_args); | 1273 | ch.hash.addListOfBytes(self.base.options.extra_lld_args); |
| 1274 | ch.hash.addListOfBytes(self.base.options.lib_dirs); | 1274 | ch.hash.addListOfBytes(self.base.options.lib_dirs); |
| 1275 | ch.hash.addListOfBytes(self.base.options.rpath_list); | ||
| 1276 | ch.hash.add(self.base.options.each_lib_rpath); | ||
| 1275 | ch.hash.add(self.base.options.is_compiler_rt_or_libc); | 1277 | ch.hash.add(self.base.options.is_compiler_rt_or_libc); |
| 1276 | ch.hash.add(self.base.options.z_nodelete); | 1278 | ch.hash.add(self.base.options.z_nodelete); |
| 1277 | ch.hash.add(self.base.options.z_defs); | 1279 | ch.hash.add(self.base.options.z_defs); |
| ... | @@ -1392,7 +1394,7 @@ fn linkWithLLD(self: *Elf, comp: *Compilation) !void { | ... | @@ -1392,7 +1394,7 @@ fn linkWithLLD(self: *Elf, comp: *Compilation) !void { |
| 1392 | } | 1394 | } |
| 1393 | 1395 | ||
| 1394 | const full_out_path = if (directory.path) |dir_path| | 1396 | const full_out_path = if (directory.path) |dir_path| |
| 1395 | try std.fs.path.join(arena, &[_][]const u8{dir_path, self.base.options.sub_path}) | 1397 | try fs.path.join(arena, &[_][]const u8{dir_path, self.base.options.sub_path}) |
| 1396 | else | 1398 | else |
| 1397 | self.base.options.sub_path; | 1399 | self.base.options.sub_path; |
| 1398 | try argv.append("-o"); | 1400 | try argv.append("-o"); |
| ... | @@ -1420,32 +1422,34 @@ fn linkWithLLD(self: *Elf, comp: *Compilation) !void { | ... | @@ -1420,32 +1422,34 @@ fn linkWithLLD(self: *Elf, comp: *Compilation) !void { |
| 1420 | } | 1422 | } |
| 1421 | } | 1423 | } |
| 1422 | 1424 | ||
| 1423 | // TODO rpaths | 1425 | // rpaths |
| 1424 | // TODO add to cache hash above too | 1426 | var rpath_table = std.StringHashMap(void).init(self.base.allocator); |
| 1425 | //for (size_t i = 0; i < g->rpath_list.length; i += 1) { | 1427 | defer rpath_table.deinit(); |
| 1426 | // Buf *rpath = g->rpath_list.at(i); | 1428 | for (self.base.options.rpath_list) |rpath| { |
| 1427 | // add_rpath(lj, rpath); | 1429 | if ((try rpath_table.fetchPut(rpath, {})) == null) { |
| 1428 | //} | 1430 | try argv.append("-rpath"); |
| 1429 | //if (g->each_lib_rpath) { | 1431 | try argv.append(rpath); |
| 1430 | // for (size_t i = 0; i < g->lib_dirs.length; i += 1) { | 1432 | } |
| 1431 | // const char *lib_dir = g->lib_dirs.at(i); | 1433 | } |
| 1432 | // for (size_t i = 0; i < g->link_libs_list.length; i += 1) { | 1434 | if (self.base.options.each_lib_rpath) { |
| 1433 | // LinkLib *link_lib = g->link_libs_list.at(i); | 1435 | var test_path = std.ArrayList(u8).init(self.base.allocator); |
| 1434 | // if (buf_eql_str(link_lib->name, "c")) { | 1436 | defer test_path.deinit(); |
| 1435 | // continue; | 1437 | for (self.base.options.lib_dirs) |lib_dir_path| { |
| 1436 | // } | 1438 | for (self.base.options.system_libs) |link_lib| { |
| 1437 | // bool does_exist; | 1439 | test_path.shrinkRetainingCapacity(0); |
| 1438 | // Buf *test_path = buf_sprintf("%s/lib%s.so", lib_dir, buf_ptr(link_lib->name)); | 1440 | const sep = fs.path.sep_str; |
| 1439 | // if (os_file_exists(test_path, &does_exist) != ErrorNone) { | 1441 | try test_path.writer().print("{}" ++ sep ++ "lib{}.so", .{ lib_dir_path, link_lib }); |
| 1440 | // zig_panic("link: unable to check if file exists: %s", buf_ptr(test_path)); | 1442 | fs.cwd().access(test_path.items, .{}) catch |err| switch (err) { |
| 1441 | // } | 1443 | error.FileNotFound => continue, |
| 1442 | // if (does_exist) { | 1444 | else => |e| return e, |
| 1443 | // add_rpath(lj, buf_create_from_str(lib_dir)); | 1445 | }; |
| 1444 | // break; | 1446 | if ((try rpath_table.fetchPut(lib_dir_path, {})) == null) { |
| 1445 | // } | 1447 | try argv.append("-rpath"); |
| 1446 | // } | 1448 | try argv.append(lib_dir_path); |
| 1447 | // } | 1449 | } |
| 1448 | //} | 1450 | } |
| 1451 | } | ||
| 1452 | } | ||
| 1449 | 1453 | ||
| 1450 | for (self.base.options.lib_dirs) |lib_dir| { | 1454 | for (self.base.options.lib_dirs) |lib_dir| { |
| 1451 | try argv.append("-L"); | 1455 | try argv.append("-L"); |
src/main.zig+5| ... | @@ -251,6 +251,7 @@ const usage_build_generic = | ... | @@ -251,6 +251,7 @@ const usage_build_generic = |
| 251 | \\ -L[d], --library-directory [d] Add a directory to the library search path | 251 | \\ -L[d], --library-directory [d] Add a directory to the library search path |
| 252 | \\ -T[script] Use a custom linker script | 252 | \\ -T[script] Use a custom linker script |
| 253 | \\ --dynamic-linker [path] Set the dynamic interpreter path (usually ld.so) | 253 | \\ --dynamic-linker [path] Set the dynamic interpreter path (usually ld.so) |
| 254 | \\ --each-lib-rpath Add rpath for each used dynamic library | ||
| 254 | \\ --version [ver] Dynamic library semver | 255 | \\ --version [ver] Dynamic library semver |
| 255 | \\ -rdynamic Add all symbols to the dynamic symbol table | 256 | \\ -rdynamic Add all symbols to the dynamic symbol table |
| 256 | \\ -rpath [path] Add directory to the runtime library search path | 257 | \\ -rpath [path] Add directory to the runtime library search path |
| ... | @@ -361,6 +362,7 @@ pub fn buildOutputType( | ... | @@ -361,6 +362,7 @@ pub fn buildOutputType( |
| 361 | var use_lld: ?bool = null; | 362 | var use_lld: ?bool = null; |
| 362 | var use_clang: ?bool = null; | 363 | var use_clang: ?bool = null; |
| 363 | var link_eh_frame_hdr = false; | 364 | var link_eh_frame_hdr = false; |
| 365 | var each_lib_rpath = false; | ||
| 364 | var libc_paths_file: ?[]const u8 = null; | 366 | var libc_paths_file: ?[]const u8 = null; |
| 365 | var machine_code_model: std.builtin.CodeModel = .default; | 367 | var machine_code_model: std.builtin.CodeModel = .default; |
| 366 | var runtime_args_start: ?usize = null; | 368 | var runtime_args_start: ?usize = null; |
| ... | @@ -613,6 +615,8 @@ pub fn buildOutputType( | ... | @@ -613,6 +615,8 @@ pub fn buildOutputType( |
| 613 | if (i + 1 >= args.len) fatal("expected parameter after {}", .{arg}); | 615 | if (i + 1 >= args.len) fatal("expected parameter after {}", .{arg}); |
| 614 | i += 1; | 616 | i += 1; |
| 615 | override_lib_dir = args[i]; | 617 | override_lib_dir = args[i]; |
| 618 | } else if (mem.eql(u8, arg, "--each-lib-rpath")) { | ||
| 619 | each_lib_rpath = true; | ||
| 616 | } else if (mem.eql(u8, arg, "--enable-cache")) { | 620 | } else if (mem.eql(u8, arg, "--enable-cache")) { |
| 617 | enable_cache = true; | 621 | enable_cache = true; |
| 618 | } else if (mem.eql(u8, arg, "--test-cmd-bin")) { | 622 | } else if (mem.eql(u8, arg, "--test-cmd-bin")) { |
| ... | @@ -1421,6 +1425,7 @@ pub fn buildOutputType( | ... | @@ -1421,6 +1425,7 @@ pub fn buildOutputType( |
| 1421 | .color = color, | 1425 | .color = color, |
| 1422 | .time_report = time_report, | 1426 | .time_report = time_report, |
| 1423 | .is_test = arg_mode == .zig_test, | 1427 | .is_test = arg_mode == .zig_test, |
| 1428 | .each_lib_rpath = each_lib_rpath, | ||
| 1424 | .test_evented_io = test_evented_io, | 1429 | .test_evented_io = test_evented_io, |
| 1425 | .test_filter = test_filter, | 1430 | .test_filter = test_filter, |
| 1426 | .test_name_prefix = test_name_prefix, | 1431 | .test_name_prefix = test_name_prefix, |