How to correctly compile static libraries on Windows?

╰─❯ zig cc -static -o miniaudio-static.lib miniaudio.o
LLD Link... lld-link: error: undefined symbol: WinMain
>>> referenced by E:\scoop\global\apps\zig-dev\0.13.0-dev.30\lib\libc\mingw\crt\crtexewin.c:67
>>>               mingw32.lib(crtexewin.obj):(main)

Another question, how can I add msvc target? (i have installed msvc build tools)

find no msvc target by

zig targets | jq '.libc'
...
  "wasm32-freestanding-musl",
  "wasm32-wasi-musl",
  "x86_64-linux-gnu",
  "x86_64-linux-gnux32",
  "x86_64-linux-musl",
  "x86_64-windows-gnu",
  "x86_64-macos-none"
]

The windows msvc targets are:

  • x86-windows-msvc
  • x86_64-windows-msvc
  • aarch64-windows-msvc
1 Like

not found

╰─❯ zig targets | jq '.libc'
[
  "aarch64_be-linux-gnu",
  "aarch64_be-linux-musl",
  "aarch64_be-windows-gnu",
  "aarch64-linux-gnu",
  "aarch64-linux-musl",
  "aarch64-windows-gnu",
  "aarch64-macos-none",
  "armeb-linux-gnueabi",
  "armeb-linux-gnueabihf",
  "armeb-linux-musleabi",
  "armeb-linux-musleabihf",
  "armeb-windows-gnu",
  "arm-linux-gnueabi",
  "arm-linux-gnueabihf",
  "arm-linux-musleabi",
  "arm-linux-musleabihf",
  "thumb-linux-gnueabi",
  "thumb-linux-gnueabihf",
  "thumb-linux-musleabi",
  "thumb-linux-musleabihf",
  "arm-windows-gnu",
  "csky-linux-gnueabi",
  "csky-linux-gnueabihf",
  "x86-linux-gnu",
  "x86-linux-musl",
  "x86-windows-gnu",
  "m68k-linux-gnu",
  "m68k-linux-musl",
  "mips64el-linux-gnuabi64",
  "mips64el-linux-gnuabin32",
  "mips64el-linux-musl",
  "mips64-linux-gnuabi64",
  "mips64-linux-gnuabin32",
  "mips64-linux-musl",
  "mipsel-linux-gnueabi",
  "mipsel-linux-gnueabihf",
  "mipsel-linux-musl",
  "mips-linux-gnueabi",
  "mips-linux-gnueabihf",
  "mips-linux-musl",
  "powerpc64le-linux-gnu",
  "powerpc64le-linux-musl",
  "powerpc64-linux-gnu",
  "powerpc64-linux-musl",
  "powerpc-linux-gnueabi",
  "powerpc-linux-gnueabihf",
  "powerpc-linux-musl",
  "riscv64-linux-gnu",
  "riscv64-linux-musl",
  "s390x-linux-gnu",
  "s390x-linux-musl",
  "sparc-linux-gnu",
  "sparc64-linux-gnu",
  "wasm32-freestanding-musl",
  "wasm32-wasi-musl",
  "x86_64-linux-gnu",
  "x86_64-linux-gnux32",
  "x86_64-linux-musl",
  "x86_64-windows-gnu",
  "x86_64-macos-none"
]

libc are not targets but available C libraries.
zig targets | jq .abi gives you the list of ABIs
Example:

❯ zig cc --target=x86_64-windows-msvc -print-effective-triple
x86_64-unknown-windows-msvc19.20.0
3 Likes

How to correctly compile static libraries on Windows?

You can create a .lib file with the following command:

zig ar rc miniaudio-static.lib miniaudio.o
3 Likes

Why is the lib compiled with zigcc much larger than the lib compiled directly with cl?

i see, this is what i want

zig  lib /OUT:miniaudio-zigcc-static.lib miniaudio.obj

Sorry, I still want to ask a question

cc can not use msvc target?

zig cc -c -o miniaudio-zigcc.obj miniaudio.c -v -target x86_64-windows-msvc

error: unable to create compilation: LibCStdLibHeaderNotFound

It cannot find where Windows SDK or MS Visual C runtime is installed.

I am using the following include paths to cross compile to windows:

if (target.result.abi == std.Target.Abi.msvc) {
        exe.addIncludePath(.{ .cwd_relative = "/.../sdk/include/ucrt" });
        exe.addIncludePath(.{ .cwd_relative = "/.../crt/include" });
        exe.addLibraryPath(.{ .cwd_relative = "/.../crt/lib/x86_64" });
        exe.addLibraryPath(.{ .cwd_relative = "/.../sdk/lib/ucrt/x86_64" });
        exe.addLibraryPath(.{ .cwd_relative = "/.../sdk/lib/um/x86_64" });
    }

In the command line, you can add the include paths using the switch -I

It still failed. Forget it, I’ll give up.

Thanks your patience :wink:

zig cc -c -o miniaudio-zigcc.obj miniaudio.c -v -target x86_64-windows-msvc -I 'E:\install\Microsoft Visual Studio\2019\BuildTools\VC\Tools\MSVC\14.29.30133\include' -I 'E:\install\Microsoft Visual Studio\2019\BuildTools\VC\Tools\MSVC\14.29.30133\lib\x86' -I 'E:\install\Microsoft Visual Studio\2019\BuildTools\VC\Tools\MSVC\14.29.30133\lib\x64'

error: unable to create compilation: LibCStdLibHeaderNotFound

-I does not help because in windows it tries to locate the windows sdk and the visual studio.
Visual studio installs some powershell and command links that setup the environment for building.
Try to call it from an command line environment where cl works.

In fact I have been testing it in cl environment

zig cc should handle the include directories for you. It seems like Zig is unable to detect your MSVC/SDK install, though.

zig cc -c -o test-zigcc.obj test.c -v -target x86_64-windows-msvc

works for me.

What does

zig libc -includes -target x86_64-windows-msvc

output for you? For me it is:

C:\Program Files (x86)\Windows Kits\10\Include\10.0.22621.0\ucrt
C:\Program Files\Microsoft Visual Studio\2022\Community\VC\Tools\MSVC\14.39.33519\include
C:\Program Files\Microsoft Visual Studio\2022\Community\VC\Tools\MSVC\14.39.33519\atlmfc\include
C:\Program Files (x86)\Windows Kits\10\Include\10.0.22621.0\um
C:\Program Files (x86)\Windows Kits\10\Include\10.0.22621.0\shared

My output is

╰─❯ zig libc -includes -target x86_64-windows-msvc
error: unable to detect libc for target x86_64-windows.win8_1...win10_fe-msvc: LibCStdLibHeaderNotFound
error: the following build command failed with exit code 1:
C:\Users\zzz\AppData\Local\zig\o\27c5e7292e0e1ee2db4d603bb8987ffa\libc.exe E:\scoop\global\apps\zig-dev\0.13.0-dev.30\lib -includes -target x86_64-windows-msvc
1 Like

In the environment that cl.exe works in, try

echo %INCLUDE%

or for PowerShell

echo $env:INCLUDE

and post the result.

╰─❯ echo $env:INCLUDE
E:\install\Microsoft Visual Studio\2019\BuildTools\VC\Tools\MSVC\14.29.30133\include;C:\Program Files (x86)\Windows Kits\10\include\10.0.19041.0\ucrt;C:\Program Files (x86)\Windows Kits\10\include\10.0.19041.0\shared;C:\Program Files (x86)\Windows Kits\10\include\10.0.19041.0\um;C:\Program Files (x86)\Windows Kits\10\include\10.0.19041.0\winrt;C:\Program Files (x86)\Windows Kits\10\include\10.0.19041.0\cppwinrt
╭╴🪟 $psh me\test-zig\miniaudio.zig via ↯ v0.13.0-dev.30+6fd09f8d2
╰─❯ zig libc -includes -target x86_64-windows-msvc
error: unable to detect libc for target x86_64-windows.win8_1...win10_fe-msvc: LibCStdLibHeaderNotFound
error: the following build command failed with exit code 1:
C:\Users\zzz\AppData\Local\zig\o\27c5e7292e0e1ee2db4d603bb8987ffa\libc.exe E:\scoop\global\apps\zig-dev\0.13.0-dev.30\lib -includes -target x86_64-windows-msvc
1 Like

Thanks, so my theory is that Zig is either not finding your Windows 10 SDK installation, or its trying to use the wrong version of the SDK. Here’s a zip with a libc.exe that has some debug printing added:

https://www.ryanliptak.com/misc/zig-libc-debug.zip

It’ll print something like:

Installation.find: found from KitsRoot10
windows10sdk: C:\Program Files (x86)\Windows Kits\10 version: 10.0.22621.0
msvc_lib_dir: C:\Program Files\Microsoft Visual Studio\2022\Community\VC\Tools\MSVC\14.39.33519\Lib\x64
checking for stdlib.h in C:\Program Files (x86)\Windows Kits\10\Include\10.0.22621.0\ucrt

If you wouldn’t mind, extract and run it like so:

libc.exe <path to zig lib dir> -includes -target x86_64-windows-msvc

Judging from the output of your failing zig libc command, that should probably be this for you:

libc.exe E:\scoop\global\apps\zig-dev\0.13.0-dev.30\lib -includes -target x86_64-windows-msvc
1 Like
╰─❯ .\libc.exe E:\scoop\global\apps\zig-dev\0.13.0-dev.30\lib -includes -target x86_64-windows-msvc
Installation.find: found from KitsRoot10
windows10sdk: C:\Program Files (x86)\Windows Kits\10 version: 10.0.19041.0
error: unable to detect libc for target x86_64-windows.win8_1...win10_fe-msvc: LibCStdLibHeaderNotFound
1 Like

Ah, interesting, it’s actually failing to find your MSVC install. Try again with this:

https://www.ryanliptak.com/misc/zig-libc-debug-2.zip

(same thing but with more debug printing added)

1 Like