summaryrefslogtreecommitdiffstats
path: root/openpgp/src/cert/builder.rs
diff options
context:
space:
mode:
authorJustus Winter <justus@sequoia-pgp.org>2020-12-14 16:37:33 +0100
committerJustus Winter <justus@sequoia-pgp.org>2020-12-14 16:37:33 +0100
commit8c50ba96a5434aeefbf44e0d034072dfc6669521 (patch)
tree7c6a5d31c22dac12fa97c4545de873a3605c7b2e /openpgp/src/cert/builder.rs
parent7e57122f0bd6db27c6e2f0c7deac1333256e5146 (diff)
openpgp: Change general purpose keys to have a signing subkey.
- Certificates with a primary key that is not signing capable, and a subkey that is, are strictly more secure than ones that combine signing and certification capabilities in the primary key. - If the owner of a certificate with a signing-capable primary key can be tricked into creating a binary signature over carefully chosen attacker-controlled data, this signature can be repurposed to bind arbitrary attacker-controlled components to the certificate using a chosen-prefix collision attack on the hash function (see e.g. "SHA-1 is a Shambles" for a similar attack). - Having a separate signing-subkey mitigates the attack, because signatures by the signing subkey cannot bind components to the certificate.
Diffstat (limited to 'openpgp/src/cert/builder.rs')
-rw-r--r--openpgp/src/cert/builder.rs18
1 files changed, 12 insertions, 6 deletions
diff --git a/openpgp/src/cert/builder.rs b/openpgp/src/cert/builder.rs
index 15d0a350..627bd4f0 100644
--- a/openpgp/src/cert/builder.rs
+++ b/openpgp/src/cert/builder.rs
@@ -233,9 +233,10 @@ impl CertBuilder<'_> {
/// Generates a general-purpose certificate.
///
/// The returned builder is set to generate a certificate with a
- /// certification- and signature-capable primary key, and an
- /// encryption-capable subkey. The subkey is marked as being
- /// appropriate for both data in transit and data at rest.
+ /// certification-capable primary key, a signing-capable subkye,
+ /// and an encryption-capable subkey. The encryption subkey is
+ /// marked as being appropriate for both data in transit and data
+ /// at rest.
///
/// # Examples
///
@@ -248,7 +249,7 @@ impl CertBuilder<'_> {
/// CertBuilder::general_purpose(None,
/// Some("Alice Lovelace <alice@example.org>"))
/// .generate()?;
- /// # assert_eq!(cert.keys().count(), 2);
+ /// # assert_eq!(cert.keys().count(), 3);
/// # assert_eq!(cert.userids().count(), 1);
/// # Ok(())
/// # }
@@ -262,14 +263,19 @@ impl CertBuilder<'_> {
ciphersuite: ciphersuite.into().unwrap_or(Default::default()),
primary: KeyBlueprint {
flags: KeyFlags::empty()
- .set_certification()
- .set_signing(),
+ .set_certification(),
validity: Some(time::Duration::new(3 * 52 * 7 * 24 * 60 * 60, 0)),
ciphersuite: None,
},
subkeys: vec![
KeyBlueprint {
flags: KeyFlags::empty()
+ .set_signing(),
+ validity: None,
+ ciphersuite: None,
+ },
+ KeyBlueprint {
+ flags: KeyFlags::empty()
.set_transport_encryption()
.set_storage_encryption(),
validity: None,