Open perillo opened 1 year ago
In the Zig Language Reference there are two example of linking a Zig library to a C program in the "Exporting a C Library" and "Mixing Object Files" sections. Both examples fail.
These are the issues I found:
Static linking using a C compiler fails
Using the
mathtest.zig
examplezig build-lib -femit-h mathtest.zig gcc -o test -static -I $(zig env | jq -r .lib_dir) test.c -L . -lmathtest ./test
/usr/bin/ld: ./libmathtest.a(./libmathtest.a.o): in function `debug.readElfDebugInfo': /home/manlio/.local/share/sdk/zig/master/lib/std/debug.zig:939: undefined reference to `__zig_probe_stack' /usr/bin/ld: ./libmathtest.a(./libmathtest.a.o): in function `fs.Dir.openFile': /home/manlio/.local/share/sdk/zig/master/lib/std/fs.zig:1099: undefined reference to `__zig_probe_stack' /usr/bin/ld: ./libmathtest.a(./libmathtest.a.o): in function `debug.printLineFromFileAnyOs__anon_5459': /home/manlio/.local/share/sdk/zig/master/lib/std/debug.zig:1164: undefined reference to `__zig_probe_stack' /usr/bin/ld: ./libmathtest.a(./libmathtest.a.o): in function `dwarf.DwarfInfo.getLineNumberInfo': /home/manlio/.local/share/sdk/zig/master/lib/std/dwarf.zig:1090: undefined reference to `__zig_probe_stack' /usr/bin/ld: ./libmathtest.a(./libmathtest.a.o): in function `debug.panicExtra__anon_5748': /home/manlio/.local/share/sdk/zig/master/lib/std/debug.zig:297: undefined reference to `__zig_probe_stack' /usr/bin/ld: ./libmathtest.a(./libmathtest.a.o):/home/manlio/.local/share/sdk/zig/master/lib/std/debug.zig:297: more undefined references to `__zig_probe_stack' follow collect2: error: ld returned 1 exit status
You have built the library in debug mode. If you build in releaseFast or small mode the error will not occur, or add -fcompiler-rt
in build-lib. https://github.com/ziglang/zig/issues/6817#issuecomment-736129115
You have built the library in debug mode. If you build in releaseFast or small mode the error will not occur, or add
-fcompiler-rt
in build-lib. #6817 (comment)
Thanks.
Scratch my last comment. This issue goes away if you explicitly pass -fcompiler-rt
. Whether this should be automatic I'll leave to @andrewrk, so reopening.
Scratch my last comment. This issue goes away if you explicitly pass
-fcompiler-rt
. Whether this should be automatic I'll leave to @andrewrk, so reopening.
I converted the 3 different issues into separate tasks.
I'm not sure about the last task, since the (currently disabled) test-gen-h
test suite expects clean C code: https://github.com/ziglang/zig/blob/master/test/gen_h.zig.
A problem with this approach is name collision.
Hello! With the latest versions of zig on MacOS (I tried version 0.10 and 0.11 and 0.12 and compiled from main/HEAD) this example now segfaults. Instead of opening a new bug I thought I would just add it here.
zig build-lib -femit-h mathtest.zig
➞ zig build-lib -femit-h mathtest.zig
AST Lowering [519] target/aarch64.zig... thread 604505 panic: reached unreachable code
/Projects/zig/lib/std/debug.zig:342:14: 0x109fa4c7c in assert (zig)
if (!ok) unreachable; // assertion failure
/Projects/zig/src/Module.zig:5343:19: 0x10a08705c in allocateNewDecl (zig)
assert(@intFromEnum(decl_index) == mod_emit_h.allocated_emit_h.len);
/Projects/zig/src/Module.zig:3912:51: 0x10a22b0fc in semaFile (zig)
const new_decl_index = try mod.allocateNewDecl(new_namespace_index, 0, null);
/Projects/zig/src/Module.zig:3888:24: 0x10a22ae81 in semaPkg (zig)
return mod.semaFile(file);
/Projects/zig/src/Compilation.zig:3323:27: 0x10a25b19d in processOneJob (zig)
module.semaPkg(pkg) catch |err| switch (err) {
/Projects/zig/src/Compilation.zig:3151:30: 0x10a0cddfe in performAllTheWork (zig)
try processOneJob(comp, work_item, main_progress_node);
/Projects/zig/src/Compilation.zig:2058:31: 0x10a0c9929 in update (zig)
try comp.performAllTheWork(main_progress_node);
/Projects/zig/src/main.zig:4098:24: 0x10a0fa161 in updateModule (zig)
try comp.update(main_progress_node);
I added a debug print statement right before this block where the assertion is shown in Module.zig
if (@intFromEnum(decl_index) >= mod_emit_h.allocated_emit_h.len) {
try mod_emit_h.allocated_emit_h.append(gpa, .{});
assert(@intFromEnum(decl_index) == mod_emit_h.allocated_emit_h.len);
}
allocated_emit_h = segmented_list.SegmentedList(Module.EmitH,0) decl_index = Module.Decl.Index(0) allocated_emit_h.len = 0
It looks like the situation is (pseudo-code)
if 0 >= 0
list.append
assert 0 == 1
If the append succeeds, the assert always fails.
Every once in a while I re-test this, and now the error message has changed:
thread 17539456 panic: regressed compiler feature: emit-h should hook into updateExports, not decl analysis, which is too early to know about @export calls
It looks like this check was added here: https://github.com/ziglang/zig/commit/00da182e68
In the Zig Language Reference there are two example of linking a Zig library to a C program in the "Exporting a C Library" and "Mixing Object Files" sections. Both examples fail.
These are the issues I found:
[x] Static linking using a C compiler fails
Using the
mathtest.zig
exampleI'm not sure if this works as expected. When using
zig build
the generated executable is dynamically linked.See #14099.
[ ] Setting
LibExeObjStep.emit_h
to true, does not emit the header file a second time when the header file is removedWhen
mathtest.h
does not exists,zig build
will create it, but if I remove the file,zig build
will not create it again.The reason is that the build system always enables caching, but the generated header file is not cached in the artifact directory.
See #14606.
[ ]
zig build
should automatically includezig.h
header whenemit_h
is set to true.When an executable links a library with
emit_h
set to true, the build system should automatically append the path tozig_dir
toexe.include_dirs
.See #14576.
Thanks.