Help building a C app that links to libsystemd

I’m working on a proof-of-concept:

However, when I run zig build, I get stuff like:

error: ld.lld: undefined symbol: sd_bus_open_user
    note: referenced by main.c:56
    note:               /scratch4/yoe/mgr/zig-cache/o/65e9521a0e743fd7e872cb98008a5618/main.o:(main)
error: ld.lld: undefined symbol: sd_bus_add_object_vtable
    note: referenced by main.c:63
    note:               /scratch4/yoe/mgr/zig-cache/o/65e9521a0e743fd7e872cb98008a5618/main.o:(main)
error: ld.lld: undefined symbol: sd_bus_request_name
    note: referenced by main.c:75
    note:               /scratch4/yoe/mgr/zig-cache/o/65e9521a0e743fd7e872cb98008a5618/main.o:(main)
error: ld.lld: undefined symbol: sd_bus_process
    note: referenced by main.c:83
    note:               /scratch4/yoe/mgr/zig-cache/o/65e9521a0e743fd7e872cb98008a5618/main.o:(main)
error: ld.lld: undefined symbol: sd_bus_wait
...

Appreciate any pointers or examples I can following.

Hey @cbrake, welcome!

I had an issue like this recently and I forgot to link the system library to my executable.

Here’s an example:

// If you are compiling multiple objects that have the same
// library dependencies, make a helper function to attach them in one go.
fn linkLibraries(b: *std.Build, obj: *std.Build.Step.Compile) void {
    // Link a static library (archive file)
    obj.addObjectFile(b.path("src/lib/mp_kernels.a"));

    // Enable searching for libraries prefixed with "lib",
    // such as "libcudart.so" or "libfoo.so"
    obj.addLibraryPath(b.path("deps/cuda/lib64"));

    // Perform a search for libraries in specified paths.
    // Note that the "lib" prefix has been omitted, such as in "cudart",
    // which actually has the name "libcudart.so"
    obj.linkSystemLibrary("cudart");
    obj.linkSystemLibrary("nvrtc");
    obj.linkSystemLibrary("cuda");

    // Link system libc
    obj.linkLibC();
}

From: Build system tricks

Here is my build file:

const std = @import("std");

pub fn build(b: *std.Build) void {
    const target = b.standardTargetOptions(.{});
    const exe = b.addExecutable(.{
        .name = "mgr",
        .target = target,
    });

    exe.addCSourceFile(.{
        .file = b.path("main.c"),
        .flags = &[_][]const u8{},
    });

    exe.linkLibC();
    exe.linkSystemLibrary("systemd");
    b.installArtifact(exe);
}

I am attempting to link the systemd lib, but perhaps I’m not doing it right.

The following lib exists:

[cbrake@ceres ~]$ ls -l /usr/lib/libsystemd.so
lrwxrwxrwx 1 root root 15 Jun 18 14:57 /usr/lib/libsystemd.so -> libsystemd.so.0

It seems the symbols exist in the lib:

[cbrake@ceres ~]$ readelf -Ws /usr/lib/libsystemd.so | grep sd_bus_open_user
   435: 0000000000040e80   568 FUNC    GLOBAL DEFAULT   13 sd_bus_open_user_with_description@@LIBSYSTEMD_239
   481: 00000000000410c0    12 FUNC    GLOBAL DEFAULT   13 sd_bus_open_user@@LIBSYSTEMD_221
   661: 0000000000041570   355 FUNC    GLOBAL DEFAULT   13 sd_bus_open_user_machine@@LIBSYSTEMD_248

Maybe try zig build --verbose-cc --verbose-link to see what commands are being run.

[cbrake@ceres mgr]$ zig build --verbose-cc --verbose-link
install
└─ install mgr
   └─ zig build-exe mgr Debug native 11 errors
error: ld.lld: undefined symbol: sd_bus_open_user
    note: referenced by main.c:56
    note:               /scratch4/yoe/mgr/zig-cache/o/65e9521a0e743fd7e872cb98008a5618/main.o:(main)
error: ld.lld: undefined symbol: sd_bus_add_object_vtable
    note: referenced by main.c:63
    note:               /scratch4/yoe/mgr/zig-cache/o/65e9521a0e743fd7e872cb98008a5618/main.o:(main)
error: ld.lld: undefined symbol: sd_bus_request_name
    note: referenced by main.c:75
    note:               /scratch4/yoe/mgr/zig-cache/o/65e9521a0e743fd7e872cb98008a5618/main.o:(main)
error: ld.lld: undefined symbol: sd_bus_process
    note: referenced by main.c:83
    note:               /scratch4/yoe/mgr/zig-cache/o/65e9521a0e743fd7e872cb98008a5618/main.o:(main)
error: ld.lld: undefined symbol: sd_bus_wait
    note: referenced by main.c:92
    note:               /scratch4/yoe/mgr/zig-cache/o/65e9521a0e743fd7e872cb98008a5618/main.o:(main)
error: ld.lld: undefined symbol: sd_bus_slot_unref
    note: referenced by main.c:100
    note:               /scratch4/yoe/mgr/zig-cache/o/65e9521a0e743fd7e872cb98008a5618/main.o:(main)
error: ld.lld: undefined symbol: sd_bus_unref
    note: referenced by main.c:101
    note:               /scratch4/yoe/mgr/zig-cache/o/65e9521a0e743fd7e872cb98008a5618/main.o:(main)
error: ld.lld: undefined symbol: sd_bus_message_read
    note: referenced by main.c:12
    note:               /scratch4/yoe/mgr/zig-cache/o/65e9521a0e743fd7e872cb98008a5618/main.o:(method_multiply)
    note: referenced by main.c:27
    note:               /scratch4/yoe/mgr/zig-cache/o/65e9521a0e743fd7e872cb98008a5618/main.o:(method_divide)
error: ld.lld: undefined symbol: sd_bus_reply_method_return
    note: referenced by main.c:19
    note:               /scratch4/yoe/mgr/zig-cache/o/65e9521a0e743fd7e872cb98008a5618/main.o:(method_multiply)
    note: referenced by main.c:39
    note:               /scratch4/yoe/mgr/zig-cache/o/65e9521a0e743fd7e872cb98008a5618/main.o:(method_divide)
error: ld.lld: undefined symbol: sd_bus_error_set_const
    note: referenced by main.c:35
    note:               /scratch4/yoe/mgr/zig-cache/o/65e9521a0e743fd7e872cb98008a5618/main.o:(method_divide)
error: ld.lld: undefined symbol: sd_bus_object_vtable_format
    note: referenced by main.c
    note:               /scratch4/yoe/mgr/zig-cache/o/65e9521a0e743fd7e872cb98008a5618/main.o:(calculator_vtable)
error: ld.lld --error-limit=0 --entry _start -z stack-size=16777216 --image-base=16777216 --eh-frame-hdr -znow -m elf_x86_64 -o /scratch4/yoe/mgr/zig-cache/o/19de657a1d80d1e0a3e01b2464e4ade7/mgr /usr/lib/gcc/x86_64-pc-linux-gnu/14.1.1/../../../../lib/crt1.o /usr/lib/gcc/x86_64-pc-linux-gnu/14.1.1/../../../../lib/crti.o -L /usr/lib/gcc/x86_64-pc-linux-gnu/14.1.1/../../../../lib -dynamic-linker /lib64/ld-linux-x86-64.so.2 /scratch4/yoe/mgr/zig-cache/o/65e9521a0e743fd7e872cb98008a5618/main.o --as-needed -lm -lpthread -lc -ldl -lrt -lutil /home/cbrake/.cache/zig/o/08cdbdaa2a4d4d98dabc24567ac5e8d5/libcompiler_rt.a /usr/lib/gcc/x86_64-pc-linux-gnu/14.1.1/../../../../lib/crtn.o
                                                                                                                      
error: the following command failed with 11 compilation errors:
/usr/bin/zig build-exe /scratch4/yoe/mgr/main.c -ODebug -Mroot -lc --verbose-link --verbose-cc --cache-dir /scratch4/yoe/mgr/zig-cache --global-cache-dir /home/cbrake/.cache/zig --name mgr --listen=-
Build Summary: 0/3 steps succeeded; 1 failed (disable with --summary none)
install transitive failure
└─ install mgr transitive failure
   └─ zig build-exe mgr Debug native 11 errors
error: the following build command failed with exit code 1:
/scratch4/yoe/mgr/zig-cache/o/ff0a4416b81815c5ee4cba068fa93522/build /usr/bin/zig /scratch4/yoe/mgr /scratch4/yoe/mgr/zig-cache /home/cbrake/.cache/zig --seed 0x5078cc4e -Z5f9d7a959d19f7bd --verbose-cc --verbose-link
[cbrake@ceres mgr]$

I don’t see systemd referenced above – odd …

1 Like

Someone on Discord told me what the problem was:

exe.linkSystemLibrary(“libsystemd”) will do. The name here follows pkg-config.

This change fixes it:

diff --git a/build.zig b/build.zig
index dbb1c4b..0ca4616 100644
--- a/build.zig
+++ b/build.zig
@@ -13,6 +13,6 @@ pub fn build(b: *std.Build) void {
     });

     exe.linkLibC();
-    exe.linkSystemLibrary("systemd");
+    exe.linkSystemLibrary("libsystemd");
     b.installArtifact(exe);
 }
2 Likes