Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Dynamic linked Go program when cross compile

Tags:

go

cgo

ld-preload

How to cross compile a Go program and still retain the dynamic linked to libc?

Context: The compiling host is macOS M1, target is Linux amd64. The default result is static linked. However I still want to have dynamic linked, esp for libc part to have LD_PRELOAD ability).

Trying to force dynamic linked like this

❯ CGO_ENABLED=1 GOARCH=amd64 GOOS=linux go build -o main cmd/server/main.go

# runtime/cgo
linux_syscall.c:67:13: error: call to undeclared function 'setresgid'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]
linux_syscall.c:67:13: note: did you mean 'setregid'?
/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX.sdk/usr/include/unistd.h:593:6: note: 'setregid' declared here
linux_syscall.c:73:13: error: call to undeclared function 'setresuid'; ISO C99 and later do not support implicit function declarations [-Wimplicit-function-declaration]
linux_syscall.c:73:13: note: did you mean 'setreuid'?
/Applications/Xcode.app/Contents/Developer/Platforms/MacOSX.platform/Developer/SDKs/MacOSX.sdk/usr/include/unistd.h:595:6: note: 'setreuid' declared here

Any suggestions to solve this? Many thanks

like image 736
user1929999 Avatar asked Sep 08 '25 17:09

user1929999


2 Answers

Thanks to @Kalis suggestion. What I missed is the cross compiler.

  1. Install cross compiler gcc
brew tap SergioBenitez/osxct
brew install x86_64-unknown-linux-gnu

Source: https://github.com/SergioBenitez/homebrew-osxct Another source: https://github.com/messense/homebrew-macos-cross-toolchains (haven't tested yet).

  1. Provide CC when compile
❯ CC=x86_64-unknown-linux-gnu-gcc CGO_ENABLED=1 GOARCH=amd64 GOOS=linux go build main.go
like image 54
user1929999 Avatar answered Sep 10 '25 08:09

user1929999


According to the documentation : Using cgo with the go command

Specifying GOOS and GOARCH is not enough , you need to specify also CC_FOR_TARGET or CC_FOR_${GOOS}_${GOARCH}. check this :

When cross-compiling, you must specify a C cross-compiler for cgo to use. You can do this by setting the generic CC_FOR_TARGET or the more specific CC_FOR_${GOOS}_${GOARCH} (for example, CC_FOR_linux_arm) environment variable when building the toolchain using make.bash, or you can set the CC environment variable any time you run the go tool.

like image 31
Kalis Avatar answered Sep 10 '25 09:09

Kalis