[Date Prev][Date Next] [Thread Prev][Thread Next] [Date Index] [Thread Index]

Re: Is there still a point in installing libgcrypt to /lib instead of /usr/lib



On Tue, 18 Feb 2020 at 23:20:11 +0100, Andreas Henriksson wrote:
>    a debhelper addon which runs after
>    dh_install, detects files in /lib, /bin and /sbin, moves them
>    into /usr and generates the needed postinst code doing the compat
>    symlinks for non-merged systems.

This could work for non-Essential packages, or for Essential packages
whose paths are not, in practice, hard-coded.

However, for Essential packages, I don't think this would be implementable
in postinst, except by having the postinst be a statically-linked binary
with no dependencies, or a busybox-static sh script. Otherwise we get
this situation:

- starting point: /lib64/ld-linux-x86-64.so.2 exists,
  /usr/lib64/ld-linux-x86-64.so.2 does not
- (preinst runs, if any)
- new libc6 is unpacked: now /usr/lib64/ld-linux-x86-64.so.2 exists,
  and /lib64/ld-linux-x86-64.so.2 does not
- postinst runs
    - if it's dynamically linked: /lib64/ld-linux-x86-64.so.2
      doesn't exist so it fails to start
    - if it's a script with a dynamically-linked interpreter: ditto
    - if it runs dynamically-linked executables: ditto

This is most obviously a problem for /lib64/ld-linux-x86-64.so.2 and its
equivalents on other architectures, but would also impact /bin/sh,
/bin/ln, /bin/dash, /bin/bash and so on.

One possible approach that occurs to me would be for dpkg to gain
functionality that lets packages declare in metadata "I'm moving /bin/foo
to /usr/bin/foo with a compat symlink", in such a way that dpkg itself,
during unpack, would run the equivalent of this:

    assert /usr/bin/foo is in new .deb
    assert /bin/foo is not in new .deb

    if ! test /bin -ef /usr/bin; then
        rm -f /bin/foo
        # ideally this is relative, but absolute would be OK
        ln -fns ../usr/bin/foo /bin/foo
    fi

Then during build, instead of generating a postinst, the debhelper addon
that you propose would generate the necessary dpkg metadata for any files
that it moved into /usr, together with a suitably-versioned dependency.

Honestly, that still seems to me like a lot of work, compared with doing
a one-time transition to usrmerge-style merged-/usr; but if people feel
strongly enough about usrmerge being wrong...

To complete the transition to merged-/usr, this would still need a
conversion step at some later time that recursively checks /bin /sbin and
/lib*, checks whether every file in the directory is a non-dpkg-managed
symlink whose realpath() is the same as the realpath() of /usr/PATH,
and if they all are, deletes the entire symlink farm and replaces it
with a simple symlink like bin -> usr/bin, lib -> usr/lib.

> The third option that I see as a no-go is that each package maintainer
> implements this on their own

For Essential packages, this has the same problem.

> (Also when/if doing b/ or the 'no-go' option someone might want to think
> about how per-package symlinks generated in postinst is going to play
> nice with Essential: yes packages which are supposed to work
> unconfigured.)

This is also true, but "the package itself doesn't install" is even worse
than packages that make use of its Essential functionality not working.

    smcv


Reply to: