Description
This is a proposal to be able to select os/user
implementation in a manner similar to that of net
(i.e. with netgo
/netcgo
build tags).
Currently, os/user lookup functions have two implementations:
- cgo_lookup_unix.go, which relies on libc;
- lookup_unix.go, which is pure Go and parses
/etc/passwd
and/etc/group
.
When building a static binary (which uses os/user) with glibc on Linux, the following warnings are produced by the linker:
/tmp/go-link-007474721/000001.o: In function `mygetgrouplist':
/usr/lib/go-1.9/src/os/user/getgrouplist_unix.go:15: warning:
Using 'getgrouplist' in statically linked applications requires
at runtime the shared libraries from the glibc version used for linking
/tmp/go-link-007474721/000001.o: In function `mygetgrgid_r':
/usr/lib/go-1.9/src/os/user/cgo_lookup_unix.go:38: warning:
Using 'getgrgid_r' in statically linked applications requires
at runtime the shared libraries from the glibc version used for linking
...
Those warnings are valid and should not be ignored, and the resulting binary can not be used without libnss_*.so
files, which is defeating one of the major reasons to make a static binary.
The problem can be solved in a few ways:
- Recompile glibc with
--enable-static-nss
and use some linker flags as suggested by the glibc FAQ. - Use some other libc implementation, like musl.
- Have
go build
use pure Go os/user implementation.
Now, 1 and 2 are not always practical or even possible, and the only way to use 3 is setting CGO_ENABLED=0
in environment before invoking go build
. The problem is, cgo is completely disabled and there is no way to link any C libraries to a binary.
Therefore, it makes sense to add some build tags to be able to explicitly choose either os/user implementation, in a way similar to that for net
package, where netgo
and netcgo
build tags can be used to select either libc-based or pure Go resolver implementation.