How to check for C preprocessor defines?

Hello,

I’m writing a kernel in C and experimenting with Zig for device drivers. I compile Zig files to object files before linking them them together to my kernel.

I pass C preprocessor defines via my Makefile:

$(ZIG) build-obj -cflags -D__print_serial -- file.zig

In C, I use:

#if defined(__print_serial)
    serial_write_string(buf);
#endif

How do I check if __print_serial is defined in Zig? I tried:

const c = @cImport({
    @cInclude("types.h");
});

const print_serial = @hasDecl(c, "__print_serial");

if (print_serial) {
    serial_write_string(buf);
}

Is this the correct approach? Or are there better approaches?

Thanks!

FYI, I found this post, but it discusses using build.zig: Check the presence of kernel macros in build.zig

I’m using a Makefile-based build system and passing defines via -cflags -D__print_serial --. I need to know if these Makefile-provided defines are accessible within @cImport(), or if there’s a different approach for Makefile-based builds.

Passing the cflag is currently an unresolved issue and is planned to be addressed together with moving @CImport to build.zig.

Proposal: allow setting cflags with @cImport · Issue #8676 · ziglang/zig

move @cImport to the build system · Issue #20630 · ziglang/zig

Supplement: It seems feasible to pass cflags to the translate-C command. Since @CImport will be removed, not following up in @CImport. Currently, the default behavior of calling translate-C in build.zig does not pass cflags, but that’s fine because we can override this part of the logic in build.zig to pass them in.

1 Like