-
-
Notifications
You must be signed in to change notification settings - Fork 13k
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
gobject-introspection: Use absolute shared library paths #12558
Conversation
The gi-r-scanner is generating a list of shared libraries that are referenced in the shared-library attribute of the <namespace/> element of the GIR file. However, this attribute only contains the names of the libraries and not the full store paths, like for example while preparing to package libblockdev, the following items were included in the shared-library attribute: /nix/store/...-libblockdev-1.3/lib/libblockdev.so.0 libm.so.6 libdmraid.so.1.0.0.rc16 libbd_utils.so.0 Unfortunately, loading such a library without setting LD_LIBRARY_PATH is going to fail finding libm.so.6 and libdmraid.so.1.0.0.rc16. Now the first attempt at solving this was to put absolute paths of all the libraries referenced in the shared-library attribute, but this also led up to including paths of build-time shared objects into that attribute: /nix/store/...-libblockdev-1.3/lib/libblockdev.so.0 /nix/store/...-glibc-2.21/lib/libm.so.6 /nix/store/...-dmraid-1.0.0.rc16/lib/libdmraid.so.1.0.0.rc16 /tmp/nix-build-libblockdev-1.3.drv-0/.../utils/.libs/libbd_utils.so.0 This of course is not what we want, so the final solution is to only use the absolute path whenever it is a Nix path and leave the library name as-is if the path doesn't reside within the store, like this: /nix/store/...-libblockdev-1.3/lib/libblockdev.so.0 /nix/store/...-glibc-2.21/lib/libm.so.6 /nix/store/...-dmraid-1.0.0.rc16/lib/libdmraid.so.1.0.0.rc16 libbd_utils.so.0 The downside of this approach is that if not even the output path of the library is in LD_LIBRARY_PATH, even loading of libbd_utils.so.0 could fail, so we need to patch the loader as well. Signed-off-by: aszlig <aszlig@redmoonstudios.org>
After patching up the shared libraries in c420de6 to use absolute paths, there are still some libraries left which do not get an absolute paths assigned. Those libraries are the ones which have an absolute path outside of the Nix store, so we assume that they're build products of the current build and make them absolute by prepending "$out/lib" or "$lib/lib" (depending on whether it's a multiple output derivation or not) to its basename. So for my test case, the resulting library paths now look like this: /nix/store/...-libblockdev-1.3/lib/libblockdev.so.0 /nix/store/...-glibc-2.21/lib/libm.so.6 /nix/store/...-dmraid-1.0.0.rc16/lib/libdmraid.so.1.0.0.rc16 /nix/store/...-libblockdev-1.3/lib/libbd_utils.so.0 Which is perfectly fine and everything gets resolved correctly after importing the library using GI. However, I didn't test it against other libraries and programs, so this still needs testing, especially for Darwin. Signed-off-by: aszlig <aszlig@redmoonstudios.org>
By analyzing the blame information on this pull request, we identified @lethalman, @lovek323 and @vcunat to be potential reviewers |
Which package is having problems such that we need this patch? |
@lethalman: A package that is not yet in |
@aszlig I'd like to understand the use case. Most of GI packages already work fine because the GIR has an absolute file with that patch. Would you elaborate on your case and why it doesn't work exactly? |
@lethalman: The GIR file has an absolute path, but not the shared libraries referenced in |
+ (?:lib%s[^A-Za-z0-9_-][^\s\(\)]*) | ||
+ ) | ||
+ ''' | ||
+ return re.compile(pattern % (nix_store_dir, re.escape(library_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.
Why not just leave absolute paths as absolute without checking for the exact nix store path? Didn't understand the comment.
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.
Because absolute paths weren't used in the first place. It's parsing the output of ldd
and just added all the basenames of the libraries found there.
The reason for still retaining the upstream behavior if it's not a Nix path is that the absolute paths of the temporary build directory will end up being there as well, see the commit message of c420de6.
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've improved the comment to make it hopefully more clear.
If no config.nix.storeDir has been set, don't fall back to "/nix/store" but use builtins.storeDir instead so we always should end up with the correct store path no matter whether config.nix.storeDir has been set. Thanks to @lethalman for pointing this out. Signed-off-by: aszlig <aszlig@redmoonstudios.org>
As the comment needed explanation, that it's about temporary build files, this should do better. Thanks again to @lethalman for pointing that out. Signed-off-by: aszlig <aszlig@redmoonstudios.org>
Once NixOS#7701 gets merged, we have another environment variable called $outputLib, which then points to another environment variable which is the final library output. This was brought up in discussion with @lethalman and @vcunat in: NixOS#12558 (comment) The closure-size branch is not yet merged into master, so this is only a preparation and we're still falling back to $out and $lib whenever $outputLib isn't available. Signed-off-by: aszlig <aszlig@redmoonstudios.org>
Tomorrow I'll try running gnome with this change. |
@lethalman: Did it work out well? |
@aszlig I cannot boot the latest unstable on virtualbox so I cannot test at the moment... if you feel it's working, or if anybody can test it on gnome3 and see that most apps work fine, feel free to push. |
@lethalman: Tested this against the following VM config and it seems to work fine, though I'm not a Gnome power user (or better: no Gnome user at all), so my tests probably aren't comprehensive enough: {
services.xserver.enable = true;
services.xserver.displayManager.gdm.enable = true;
services.xserver.desktopManager.gnome3.enable = true;
users.users.test = {
password = "test";
isNormalUser = true;
};
} Anything in particular I should test? |
@aszlig as long as most gnome apps are able to open (like gnome-tweak-tool, music, photos, clocks), it's ok. |
So far only .la files get correctly converted to absolute paths in the GIR file. However if there are .so files which depend on a particular library using GI, they still get only the basename of the .so file. This improves on the existing absolute_shlib_path.patch not only figuring out the absolute path of .so files but also falling back on the absolute path of $out/lib (or $lib/lib with multiple outputs) of the current build. With this, we should no longer need to resort to setting LD_LIBRARY_PATH for all programs that use GI libraries. I'm merging this because after more than a month no issues came up so far.
So far only
.la
files get correctly converted to absolute paths in the GIR file. However if there are.so
files which depend on a particular library using GI, they still get only the basename of the.so
file.This improves on the existing
absolute_shlib_path.patch
not only figuring out the absolute path of.so
files but also falling back on the absolute path of$out/lib
(or$lib/lib
with multiple outputs) of the current build.With this, we should no longer need to resort to setting
LD_LIBRARY_PATH
for all programs that use GI libraries.I have only done very limited testing and I'm not using Gnome, nor do I use OS X, so I don't know whether this will cause problems on any of these environments.
Cc: @lethalman and anyone who can test on Darwin :-)