archlinux / archlinux-repro

Tools to reproduce arch linux packages
MIT License
131 stars 36 forks source link

old keyring in BUILDINFO breaks reproducibillity when requiring sha1-sigs #127

Open anthraxx opened 9 months ago

anthraxx commented 9 months ago

Currently we cannot reproduce packages that require old archlinux-keyring that were still depending on sha1 signatures. The reason is, that modern gnupg versions reject and ignore signatures that were done using a sha1 algo for security reasons. This leads to dropping Arch Linux main key signature on packagers keys, which ultimately means the web-of-trust schema using the ownertrust model in gpg drops down to marginal trust instead of full trust. This happens, when the threshold falls below 3 signatures.

The current code responsible is as follows: https://github.com/archlinux/archlinux-repro/blob/75dfdc6bb72c32597b10f85a189cf5e642113df6/repro.in#L430-L432

The root trust comes from the currently used bootstrap image: https://github.com/archlinux/archlinux-repro/blob/75dfdc6bb72c32597b10f85a189cf5e642113df6/repro.in#L18-L19

This extracts the old keyring package like archlinux-keyring-20220224-1-any and pacstrap's it into the keyring cache. This subsequently resolves the dependencies, installing a new gnupg 2.4. Afterwards the hooks consume the old keyring with the new gnupg, leading to the drop of legacy signatures.

Example: libmnl-1.0.5-1-x86_64.pkg.tar.zst is one of the affected packages, which installs archlinux-keyring-20220224-1-any. This results in error: 'cache/findutils-4.9.0-1-x86_64.pkg.tar.zst': invalid or corrupted package (PGP signature).

Solutions:

  1. On a long term, the easiest solution would be to not do web-of-trust on every client system but only ship a curated list of currently valid and trusted packaging keys. The web-of-trust would be the responsibility of the entity creating a keyring package. For example Arch Linux upstream repo with their main signing keys acting as CA would still do web-of-trust checks when releasing a new keyring artifact. But this would be done once instead of on every client system. The threat would remain the same as currently, as with the current model a malicious keyring upstream maintainer can also add mutliple malicious main signing keys to reach a threshold of 3.
  2. As solution 1 is a none trivial change in pacman itself, we need other measures trying to tackle this. A simple idea of just "reproducing" the environment as recorded in the .BUILDINFO of the keyring will lead to similar issues, depending on a package inside the .BUILDINFO which isn't trusted anymore with the parent boostrap image. This means we either need to break the chain of trust by ignoring signatures once between latest bootstrap image and the keyring required for reproduction or we need to use individual bootstrap images taking back to the same time as the required keyring was built.
  3. We can simply try to ignore this underlying issue and declare it a problem for future us if a comparable situation happens again, while rebuilding all packages in Arch Linux that used a keyring which requires gnupg <2.4.
kpcyrd commented 9 months ago

On a long term, the easiest solution would be to not do web-of-trust on every client system but only ship a curated list of currently valid and trusted packaging keys.

These approaches are not mutually exclusive, shipping a "trust-resolved" keyring file can be done without changing any other code or how pacman verifies packages. Having this file available in the archlinux-keyring package would allow more software to better integrate with Arch Linux package signatures (e.g. archlinux-repro but also repro-env).

This approach has been suggested previously because it also makes it easier to reason about which keys you trust, because the sha256 of a file is much easier to compare than the state machine inside of /etc/pacman.d/gnupg/.

If "resolving the trust graph" is done inside of the archlinux-keyring build() function the web-of-trust path would automatically get verified through reproducible Arch Linux volunteer infrastructure, and anybody can trivially do so too by running:

archlinux-repro -dn ./archlinux-keyring-XXXXXXXX-1-any.pkg.tar.zst

How the resolved file is generated could be iterated over in the future, but having the file available for use by future us seems like something we should start doing sooner than later.

The threat would remain the same as currently, as with the current model a malicious keyring upstream maintainer can also add mutliple malicious main signing keys to reach a threshold of 3.

FWIW since December 2022 there's a public bypass for disabling the web-of-trust using a single signature from any trusted packager. Configuring trust through simple files that are easy to reason about would make this kind of backdoor harder to hide from e.g. archlinux-userland-fs-cmp however.