-
-
Notifications
You must be signed in to change notification settings - Fork 14.6k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
glibc: Add an environment variable for specifying an NSS search path #111194
base: staging
Are you sure you want to change the base?
Conversation
With this, you can set $NIX_GLIBC_NSS_PATH to a colon-separated list of directories in which glibc will look for NSS modules. In environments where nscd cannot be used, this allows dealing with non-standard NSS modules in a less sledgehammer-y way than setting $LD_LIBRARY_PATH (which affects everything, and in particular could cause ABI incompatibilities). The default value is /nix/run/glibc-nss-path/${out-hash}:/nix/run/glibc-nss-path where out-hash is the hash part of glibc.out (e.g. /nix/run/glibc-nss-path/0cjq75a1cgwd7ccxsp9warzjax1kr7ag). Thus, glibc will look for an NSS module named libnss_mymachines.so.2 at /nix/run/glibc-nss-path/0cjq75a1cgwd7ccxsp9warzjax1kr7ag/libnss_mymachines.so.2 and /nix/run/glibc-nss-path/libnss_mymachines.so.2 These are tried *after* the default search locations (i.e. $LD_LIBRARY_PATH and glibc.out/lib) so they don't override any current behaviour. The use of /nix/run rather than /run is because the user may have write access to /nix but not to /run. On NixOS, it's intended than /nix/run is a symlink / bind-mount to /run.
This would really help me, what is needed to make this happen? |
I was able to make the google-oslogin test work without nscd with a version of this.
This creates problems for extra-utils, since it will be interpreted as a reference by Nix but nuke-refs can't remove it.
Hmm, I think it might be better to keep it in line with |
Looks like the patch doesn't apply anymore after glibc moved some stuff around: bminor/glibc@f8847d8. Moving the fallback module loading logic after this line seems to work: |
#138178 re-rolls parts of this, by loading nss modules from We can probably get along with a static set of paths to look in.
I'd propose adding a second path in a followup to #138178, that looks in I don't think we should use Using that approach, nix-built binaries running on non-NixOS, without nscd installed will just use whatever NSS modules are configured by the other distro itself, without the need to also manually install them through Nix. |
Not necessarily, they might be in e.g. /lib/x86_64-linux-gnu. I would say to stick to your guns and just do /run/nss-modules. Whatever solution non-NixOS users are using for /run/opengl-drivers/lib would apply here, whether that's manually creating the directory and symlinking the distro's files there, or mounting it with nix-user-chroot. |
No should do be doing that. /run is a tmpfs and it is way easier to just use nixGL which collects env variables which point to the correct shared objects which in the end is similar to this PR. Alternatively you can also just wrap the final binary and set the correct env variables. I am doing that to get mpv hardware acceleration working with home-manager on Debian. |
+ size_t shlib_pathlen = (end - pos) + 1 + strlen (shlib_name) + 1; | ||
+ if (shlib_pathlen < sizeof(shlib_path)) | ||
+ { | ||
+ __stpcpy (__stpcpy (__stpncpy (shlib_path, pos, end - pos), "/"), shlib_name); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is memcpy not better here given that we already calulate the string length?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Alternative would be good old snprintf
...
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm just following the surrounding code here, didn't want to deviate from the coding style.
+ const char *end = __strchrnul(pos, ':'); | ||
+ if (pos != end) | ||
+ { | ||
+ char shlib_path[1024]; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
How about:
+ char shlib_path[1024]; | |
+ char shlib_path[PATH_MAX]; |
Not that it PATH_MAX is not a lie..
Okay, #138178 (comment) explains the per-glibc out-hash path very well. I noticed that the new self-reference in libc.so causes issues when building a NixOS VM. I think it could cause issues for bootstrap-tools as well. So I guess we need to either truncate/rot13 the hash to thwart Nix's dependency detection, or nuke the hash in places like this. |
As this need keeps coming up, it makes sense to have a single well-understood escape hatch that is common for each use-case. I'd rather avoid the proliferation of NIX_SOMETHING_PATH env vars for each thing. A single
Random thought about the default value: With the generic pivot approach one can imagine a default re-using the specialisation mechanism at
This would have the default for NIX_PIVOT_PATH be Security considerations? This overall issue may need an RFC? |
Just a small note, I think a better name for such an env var is |
I marked this as stale due to inactivity. → More info |
Thie explicitly only affects NSS module loading. I don't think that env var name is very helpful in conveying the message. |
As written in https://flokli.de/posts/2022-11-18-nsncd/, I still think we should get something around the lines of this patch into glibc, either here in nixpkgs, or upstream. |
There is some progress? |
With this, you can set
$NIX_GLIBC_NSS_PATH
to a colon-separated list of directories in which glibc will look for NSS modules. In environments where nscd cannot be used, this allows dealing with non-standard NSS modules in a less sledgehammer-y way than setting$LD_LIBRARY_PATH
(which affects everything, and in particular could cause ABI incompatibilities).The default value is
/nix/run/glibc-nss-path/${out-hash}:/nix/run/glibc-nss-path
where
out-hash
is the hash part ofglibc.out
(e.g./nix/run/glibc-nss-path/0cjq75a1cgwd7ccxsp9warzjax1kr7ag
). Thus,glibc
will look for an NSS module namedlibnss_mymachines.so.2
at/nix/run/glibc-nss-path/0cjq75a1cgwd7ccxsp9warzjax1kr7ag/libnss_mymachines.so.2
and
/nix/run/glibc-nss-path/libnss_mymachines.so.2
These are tried after the default search locations (i.e.
$LD_LIBRARY_PATH
andglibc.out/lib
) so they don't override any current behaviour.The use of
/nix/run
rather than/run
is because the user may have write access to/nix
but not to/run
. On NixOS, it's intended than/nix/run
is a symlink / bind-mount to/run
.Motivation for this change
This does for NSS modules what
/run/opengl-driver
does for our OpenGL support. In particular it's intended for non-NixOS, non-nscd environments that require non-standard NSS modules.Maybe instead of
NIX_GLIBC_NSS_PATH
we could use a generic environment variable as suggested in https://gist.github.com/Infinisil/3366e7dfc9a01f6eeb25b5cb475cc585 (and then look forout-hash/nss
andnss
relative to the directories in that variable).Things done
sandbox
innix.conf
on non-NixOS linux)nix-shell -p nixpkgs-review --run "nixpkgs-review wip"
./result/bin/
)nix path-info -S
before and after)