Skip to content
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

[Secure Code Delivery] Stream Updates to a Chronicle #797

Open
paragonie-scott opened this issue Jul 9, 2017 · 18 comments
Open

[Secure Code Delivery] Stream Updates to a Chronicle #797

paragonie-scott opened this issue Jul 9, 2017 · 18 comments
Labels

Comments

@paragonie-scott
Copy link

Hi Packagist team.

I've been working on trying to make secure automatic updates available to software developers the world over, as discussed here, here, and here

There are many challenges involved (and several differing threat models), but in general, these are the problems that such a secure automatic update solution needs to solve:

  • Reproducibility
  • Authenticity
    • Cryptographic signatures with trusted public keys
  • Userbase Consistency
    • (The focus of this ticket) -- everyone sees the same thing
  • Freshness
    • TLS or timestamped online signatures prevents downgrade ("Denial of Update") attacks
    • Needs to be run at a regular interval (e.g. 15 minutes)
  • Availability
  • Implementation security
    • Privilege separation

However, we don't need to go whole hog on a total solution to this problem right out of the gate; and in fact, many of these challenges are irrelevant to Packagist. (This information is given just to provide background to the overall problem being solved.)

I'd like to propose a plan that allows Packagist that only solves two problems:

  1. Userbase consistency verification, for all tagged releases.
  2. Public key trust, for implementing cryptographic signatures in Composer (or a Composer plugin)

Solution

  1. Setup a Chronicle instance.
  2. Update Packagist's backend to publish all of the following events to the Packagist Chronicle from step one:
    • Software releases
    • Added public keys per vendor
    • Revoked public keys per vendor
  3. Update Packagist's UI to add a space for public key additions/revocations

That's it?

More-or-less, yeah.

If this gets closed, I'll grant the Packagist Chronicle access to cross-sign onto a Chronicle that PIE is setting up for large projects to cross-sign onto. It may be wise to setup several other Chronicles that replicate the Packagist Chronicle.

The rest of the work needs to be done elsewhere.

What does this give us?

Like I said: Userbase consistency verification. All software updates will now be auditable; verifiable by anyone. That's a win that even ambitious projects like The Update Framework doesn't currently provide.

In addition, by tracking public key additions/removals, we can obviate the need to setup a certificate authority (and all the X.509/ASN.1 headaches), while still providing the same security guarantees.

We would be, in effect, creating a PKI based on public key pinning and certificate transparency for the PHP community from day one. No more unaccountable single points of failure, like the TLS certificate authority system in the days before CT. (If successful, I intend to replicate this effort in other software ecosystems.)

@Ocramius
Copy link
Contributor

Ocramius commented Jul 10, 2017

This would be practically feasible only with PHP 7.2 and libsodium in it (feature freeze coming up fast!).

I already worked on WoT signatures in https://github.com/Roave/composer-gpg-verify, but that only works for git and gpg.

In order for this to work, we also need:

  • A release tool that makes it easy to sign zip packages (github and co generate and re-hash them periodically, which is useless)
  • A setup tool to make gpg more approachable to folks that don't understand asymmetric crypto
  • Rely only on either the openssl or sodium extensions for all operations in order to ensure compatibility for all those folks running on an "unfortunate" system setup (windows)

@paragonie-scott
Copy link
Author

paragonie-scott commented Jul 10, 2017

This would be practically feasible only with PHP 7.2 and libsodium in it (feature freeze coming up fast!).

https://github.com/paragonie/sodium_compat implements Ed25519 and BLAKE2b in userland (a.k.a. pure PHP, without binary dependencies).

@Ocramius
Copy link
Contributor

Yes, but is it merged yet? 😋

@JABirchall
Copy link

Yes, but is it merged yet? 😋

No, libsodium isn't merged into php 7.2 yet.

@Ocramius
Copy link
Contributor

So let's halt everything here until then ;-)

@paragonie-scott
Copy link
Author

So let's halt everything here until then ;-)

I don't see the logic in this suggestion. The change I've proposed doesn't require PHP 7.2. Our public test server doesn't even have libsodium installed, it only uses sodium_compat.

The only place this suggestion makes sense is for a client-side implementation (i.e. in Composer), which is outside the scope of this particular Github issue. We can feed data into a Chronicle now and worry about building the tooling for verifying it after the fact.

@Ayesh
Copy link

Ayesh commented Jul 10, 2017

Is there any way to do this with git push hooks, and a Composer plugin? The git hook for a new tag would log the new release to one or more Chronicles, and the Composer plugin would check the authenticity with Chronicles they trust. I think this makes more sense because Packagist is not hosting the code, unlike Debian repos or npm.

I suppose this would give some time for vendors to see how important this is, and could make it easier to move into packagist if users want it there. I don't have any stats, but I'm sure packagist gets thousands of releases everyday, and there are server costs to consider too, such as the costs to run Chronicles, etc.

@Ocramius
Copy link
Contributor

Ocramius commented Jul 10, 2017 via email

@paragonie-scott
Copy link
Author

paragonie-scott commented Jul 11, 2017

What's the point of a server-side implementation if the clients don't verify anything?

All the proposed solution here does is push update metadata into a read-only data structure.

Instead of blocking all conversation on whatever php-src is doing (this is, by the way, implicitly what you suggested upthread; since there are other discussions that probably need to happen and only those would be affected by the availability of libsodium or sodium-compat, while this one is not), we should proceed unimpeded.

The solution is trivial, but details matter: What metadata gets written?

If and only if a complementary change is made to Composer, How do we want to separate software releases from however public keys are going to be stapled on later? How are we going to handle vendor public key reservations?

Halting everything because Internals hasn't merged the pull request yet (despite all outstanding blockers being removed) buys us nothing.

Even if a code signing feature can't be agreed upon in other contexts, the very act of making all software releases verifiable is a security win. You can't guarantee software authenticity, but you still get auditability. Since PHP is a scripting language, you don't have to worry about reproducible builds (unless you're delivering a .phar), so 2/3 isn't bad.

EDIT: Also, Chronicle is a JSON API. The signatures go in a header. If you don't have sodium_compat but you do trust HTTPS, you can just query it and trust the results.

@Ocramius
Copy link
Contributor

Ocramius commented Jul 11, 2017 via email

@paragonie-scott
Copy link
Author

@Ayesh

Is there any way to do this with git push hooks, and a Composer plugin?

There is, but it requires writing a bit of code for both sides of the equation.

I don't have any stats, but I'm sure packagist gets thousands of releases everyday, and there are server costs to consider too, such as the costs to run Chronicles, etc.

That sounds like a few megabytes of disk usage per day. Libsodium is fast. The bottleneck will be bandwidth more than anything. Further, I'm willing to help with this problem. :)

@paragonie-scott
Copy link
Author

Okay, now that libsodium has been merged, what are the obstacles remaining in order for this to be considered by the Packagist team?

@alcohol
Copy link
Member

alcohol commented Aug 1, 2017

Eh, from my part, lack of knowledge mostly. I have to read up a lot xD

Same might go for the others. We've also been very busy with our daily jobs.

@paragonie-scott
Copy link
Author

That's fair. I've spoken with @Seldaek briefly, who concurs with being busy with daily jobs.

I gave a talk about this at DEFCON's Crypto & Privacy Village. When the video's available, that might help a little.

@paragonie-scott
Copy link
Author

I'm working on a formal plan for the PKI I alluded to in my original post in this issue. You can read more about it here, if you're interested: paragonie-scott/public-projects#5

@sebastianbergmann
Copy link

@paragonie-scott Is that video you mentioned in #797 (comment) available yet? Thanks!

@joepie91
Copy link

joepie91 commented Jun 8, 2018

@sebastianbergmann It seems to be available here: https://media.defcon.org/DEF%20CON%2025/DEF%20CON%2025%20villages/DEF%20CON%2025%20Crypto%20and%20Privacy%20Village%20-%20Scott%20Arciszewski%20-%20The%20How%20and%20Why%20for%20Secure%20Automatic%20Patch%20Management.mp4

(It did not play correctly for me in a browser, you may need to view it in a standalone media player to get video output as well.)

@paragonie-scott
Copy link
Author

It loads in VLC Media Player.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

7 participants