Skip to content

[Future] Code Signing and Enhanced Security Against Supply-Chain Attacks #6941

Description

@paragonie-scott

Before I begin, here's some supplementary reading material. I'll try to make this feature request make sense without reading any of this material, but in case I fail this should fill in any of the gaps:


Background

Supply-chain attacks against package managers are an underappreciated threat. Even if we assume that the only entities capable of pulling off such an attack are in the employ of government agencies around the world, there is no guarantee that such exploits will never be used (especially in a time of international conflict).

A supply-chain attack against a package manager (i.e. Packagist) would involve gaining privileged access to the package manager infrastructure (GitHub, the Packagist servers) in order to deliver malware when someone attempts to install/update a dependency. These attacks can either be targeted (e.g. only towards IP addresses in a given country) or widespread (e.g. all Symfony users).

Unfortunately, most of the security industry gravitates towards the red team side of affairs, where they're incentivized to build better attacks rather than designing resilient infrastructure, so it's likely that the day the threat of supply-chain attacks becomes tangible, there will be little-to-no recourse unless proactive measures are taken, starting today.

A lot of the groundwork has been laid by other projects (i.e. The Update Framework), but as of 2017-12-26 there are no package managers deployed at scale that solve this problem adequately.

Mitigating Supply-Chain Attacks Against Composer/Packagist

First, we need mechanisms built into Composer and Packagist for developers to:

  1. Register public keys for their project's namespaces.
    • Probably nobody except @sebastianbergmann should be able to issue public keys for the phpunit vendor, for example.
  2. Sign their releases using one of their secret keys.

There's a few other things that are implied here (i.e. the ability to generated Ed25519 keypairs). I plan on developing a composer plugin in the coming weeks that handles this, but it will need a corresponding API built into Packagist to receive public keys and signed release metadata.

Aside: I'm open to alternative proposals for getting signed release metadata into Packagist, but directly signing/releasing them from the command line is by far the best UX design I could come up with.

  • Creating a signed file and expecting users to attach it while filling out the "New Release" form on Github seems too error-prone.
  • Wrapping git tag -s seemed complicated and too locked into git (no love for Mercurial, SVN, etc.)
  • Creating a file and committing/tagging for the user seems undesirable for most projects.
  • (Your idea might be better than mine!)

Next, Packagist will need to stream all software updates and signatures to a Chronicle instance. It's a good idea to also publish new public key<->vendor associations here too.

Finally, integrate with Herd (either directly or via a Composer plugin) to verify all future updates.

Once these pieces are in place:

  • Vendors will be able to sign their own software updates. (Tentatively, composer release <version>.)
  • Vendors will own their own signing keys.
    • In emergency situations, the "core vendor" for the ecosystem (i.e. Composer) can issue revocations and/or new keys, and the client-side can choose whether or not to accept these core-signed key changes. This is a break-glass feature that cannot be abused silently, and users can outright disable in their configuration.
  • Users will be able to verify that:
    1. The update they're seeing really came from the vendor.
    2. They're seeing the same updates that everyone else in the world sees.
    3. (Knowing the git commit data): They can reproduce the same .zip, .tar.gz, etc. from the source code.

Current Progress of this Project

  • Chronicle (developed by P.I.E.)
  • Herd (developed by P.I.E.)
  • Quill, for writing to a Chronicle (developed by P.I.E.)
  • Composer - plugins and/or core changes described above (P.I.E. will develop these soon)
  • Packagist - necessary changes to accommodate this feature

I'm not sure what an appropriate milestone is, but I'd consider making this a v2.0 feature (assuming we can elevate the PHP requirement to 7.0+ for Composer v2 and use sodium_compat so we don't have to go further and make it 7.2+).

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions