diff --git a/doc/OpenPGP b/doc/OpenPGP index 96223d71d..794f6694e 100644 --- a/doc/OpenPGP +++ b/doc/OpenPGP @@ -9,6 +9,15 @@ =================== GnuPG (>=1.0.3) is in compliance with RFC2440 despite these exceptions: + * With GnuPG >= 2.1.0 all support for version 3 keys has been + removed. Thus there is no more compatibility with PGP-2. Users + who need to be able to decrypt old PGP 2 messages should use + GnuPG 1.4.x along with the option --allow-weak-digest-algos. + + * With GnuPG >= 2.1.0 all signatures (on messages and keys) are + created using version 4 signatures. Support for verifying + version 3 signature is still available. + * (9.2) states that IDEA SHOULD be implemented. This is not done due to patent problems. UPDATE: Since version 1.4.13 (or GnuPG 2.x with Libgcrypt 1.6) diff --git a/doc/gpg.texi b/doc/gpg.texi index 2997b6436..cddf46238 100644 --- a/doc/gpg.texi +++ b/doc/gpg.texi @@ -2129,6 +2129,7 @@ platforms that have different line ending conventions (UNIX-like to Mac, Mac to Windows, etc). @option{--no-textmode} disables this option, and is the default. +@ifclear gpgtwoone @item --force-v3-sigs @itemx --no-force-v3-sigs @opindex force-v3-sigs @@ -2147,6 +2148,15 @@ Defaults to no. Always use v4 key signatures even on v3 keys. This option also changes the default hash algorithm for v3 RSA keys from MD5 to SHA-1. @option{--no-force-v4-certs} disables this option. +@end ifclear + +@ifset gpgtwoone +@item --force-v3-sigs +@itemx --no-force-v3-sigs +@item --force-v4-certs +@itemx --no-force-v4-certs +These options are obsolete and have no effect since GnuPG 2.1. +@end ifset @item --force-mdc @opindex force-mdc @@ -2301,8 +2311,12 @@ compression algorithms none and ZIP. This also disables --throw-keyids, and making signatures with signing subkeys as PGP 6 does not understand signatures made by signing subkeys. -This option implies @option{--disable-mdc --escape-from-lines ---force-v3-sigs}. +@ifclear gpgtwoone +This option implies @option{--disable-mdc --escape-from-lines --force-v3-sigs}. +@end ifclear +@ifset gpgtwoone +This option implies @option{--disable-mdc --escape-from-lines}. +@end ifset @item --pgp7 @opindex pgp7 diff --git a/g10/build-packet.c b/g10/build-packet.c index af0de3b41..c04abab54 100644 --- a/g10/build-packet.c +++ b/g10/build-packet.c @@ -291,24 +291,13 @@ do_key (iobuf_t out, int ctb, PKT_public_key *pk) int i, nskey, npkey; iobuf_t a = iobuf_temp(); /* Build in a self-enlarging buffer. */ - /* Write the version number - if none is specified, use 3 */ + /* Write the version number - if none is specified, use 4 */ if ( !pk->version ) - iobuf_put ( a, 3 ); + iobuf_put ( a, 4 ); else iobuf_put ( a, pk->version ); write_32 (a, pk->timestamp ); - /* v3 needs the expiration time. */ - if ( pk->version < 4 ) - { - u16 ndays; - if ( pk->expiredate ) - ndays = (u16)((pk->expiredate - pk->timestamp) / 86400L); - else - ndays = 0; - write_16(a, ndays); - } - iobuf_put (a, pk->pubkey_algo ); /* Get number of secret and public parameters. They are held in one @@ -347,45 +336,37 @@ do_key (iobuf_t out, int ctb, PKT_public_key *pk) /* Build the header for protected (encrypted) secret parameters. */ if (ski->is_protected) { - if ( is_RSA (pk->pubkey_algo) && pk->version < 4 && !ski->s2k.mode ) + /* OpenPGP protection according to rfc2440. */ + iobuf_put (a, ski->sha1chk? 0xfe : 0xff); + iobuf_put (a, ski->algo); + if (ski->s2k.mode >= 1000) { - /* The simple rfc1991 (v3) way. */ - iobuf_put (a, ski->algo ); - iobuf_write (a, ski->iv, ski->ivlen); + /* These modes are not possible in OpenPGP, we use them + to implement our extensions, 101 can be viewed as a + private/experimental extension (this is not specified + in rfc2440 but the same scheme is used for all other + algorithm identifiers). */ + iobuf_put (a, 101); + iobuf_put (a, ski->s2k.hash_algo); + iobuf_write (a, "GNU", 3 ); + iobuf_put (a, ski->s2k.mode - 1000); } else { - /* OpenPGP protection according to rfc2440. */ - iobuf_put (a, ski->sha1chk? 0xfe : 0xff); - iobuf_put (a, ski->algo); - if (ski->s2k.mode >= 1000) - { - /* These modes are not possible in OpenPGP, we use - them to implement our extensions, 101 can be - viewed as a private/experimental extension (this - is not specified in rfc2440 but the same scheme - is used for all other algorithm identifiers). */ - iobuf_put (a, 101); - iobuf_put (a, ski->s2k.hash_algo); - iobuf_write (a, "GNU", 3 ); - iobuf_put (a, ski->s2k.mode - 1000); - } - else - { - iobuf_put (a, ski->s2k.mode); - iobuf_put (a, ski->s2k.hash_algo); - } - - if (ski->s2k.mode == 1 || ski->s2k.mode == 3) - iobuf_write (a, ski->s2k.salt, 8); - - if (ski->s2k.mode == 3) - iobuf_put (a, ski->s2k.count); - - /* For our special modes 1001, 1002 we do not need an IV. */ - if (ski->s2k.mode != 1001 && ski->s2k.mode != 1002) - iobuf_write (a, ski->iv, ski->ivlen); + iobuf_put (a, ski->s2k.mode); + iobuf_put (a, ski->s2k.hash_algo); } + + if (ski->s2k.mode == 1 || ski->s2k.mode == 3) + iobuf_write (a, ski->s2k.salt, 8); + + if (ski->s2k.mode == 3) + iobuf_put (a, ski->s2k.count); + + /* For our special modes 1001, 1002 we do not need an IV. */ + if (ski->s2k.mode != 1001 && ski->s2k.mode != 1002) + iobuf_write (a, ski->iv, ski->ivlen); + } else /* Not protected. */ iobuf_put (a, 0 ); @@ -400,7 +381,7 @@ do_key (iobuf_t out, int ctb, PKT_public_key *pk) /* The serial number gets stored in the IV field. */ iobuf_write (a, ski->iv, ski->ivlen); } - else if (ski->is_protected && pk->version >= 4) + else if (ski->is_protected) { /* The secret key is protected - write it out as it is. */ byte *p; @@ -410,20 +391,6 @@ do_key (iobuf_t out, int ctb, PKT_public_key *pk) p = gcry_mpi_get_opaque (pk->pkey[npkey], &ndatabits); iobuf_write (a, p, (ndatabits+7)/8 ); } - else if (ski->is_protected) - { - /* The secret key is protected the old v4 way. */ - for ( ; i < nskey; i++ ) - { - byte *p; - unsigned int ndatabits; - - assert (gcry_mpi_get_flag (pk->pkey[i], GCRYMPI_FLAG_OPAQUE)); - p = gcry_mpi_get_opaque (pk->pkey[i], &ndatabits); - iobuf_write (a, p, (ndatabits+7)/8); - } - write_16 (a, ski->csum ); - } else { /* Non-protected key. */ diff --git a/g10/filter.h b/g10/filter.h index 40c51343d..731ad0fba 100644 --- a/g10/filter.h +++ b/g10/filter.h @@ -152,7 +152,7 @@ int cipher_filter( void *opaque, int control, int text_filter( void *opaque, int control, iobuf_t chain, byte *buf, size_t *ret_len); int copy_clearsig_text (iobuf_t out, iobuf_t inp, gcry_md_hd_t md, - int escape_dash, int escape_from, int pgp2mode); + int escape_dash, int escape_from); /*-- progress.c --*/ progress_filter_context_t *new_progress_context (void); diff --git a/g10/gpg.c b/g10/gpg.c index 57deb8d60..1df44fe7c 100644 --- a/g10/gpg.c +++ b/g10/gpg.c @@ -272,10 +272,6 @@ enum cmd_and_opt_values oShowPhotos, oNoShowPhotos, oPhotoViewer, - oForceV3Sigs, - oNoForceV3Sigs, - oForceV4Certs, - oNoForceV4Certs, oForceMDC, oNoForceMDC, oDisableMDC, @@ -525,10 +521,6 @@ static ARGPARSE_OPTS opts[] = { ARGPARSE_s_n (oQuiet, "quiet", "@"), ARGPARSE_s_n (oNoTTY, "no-tty", "@"), - ARGPARSE_s_n (oForceV3Sigs, "force-v3-sigs", "@"), - ARGPARSE_s_n (oNoForceV3Sigs, "no-force-v3-sigs", "@"), - ARGPARSE_s_n (oForceV4Certs, "force-v4-certs", "@"), - ARGPARSE_s_n (oNoForceV4Certs, "no-force-v4-certs", "@"), ARGPARSE_s_n (oForceMDC, "force-mdc", "@"), ARGPARSE_s_n (oNoForceMDC, "no-force-mdc", "@"), ARGPARSE_s_n (oDisableMDC, "disable-mdc", "@"), @@ -810,6 +802,10 @@ static ARGPARSE_OPTS opts[] = { ARGPARSE_s_n (oNoop, "no-sk-comments", "@"), ARGPARSE_s_n (oNoop, "compress-keys", "@"), ARGPARSE_s_n (oNoop, "compress-sigs", "@"), + ARGPARSE_s_n (oNoop, "force-v3-sigs", "@"), + ARGPARSE_s_n (oNoop, "no-force-v3-sigs", "@"), + ARGPARSE_s_n (oNoop, "force-v4-certs", "@"), + ARGPARSE_s_n (oNoop, "no-force-v4-certs", "@"), ARGPARSE_end () }; @@ -2535,7 +2531,6 @@ main (int argc, char **argv) opt.allow_freeform_uid = 1; opt.pgp2_workarounds = 0; opt.escape_from = 1; - opt.force_v3_sigs = 0; opt.not_dash_escaped = 0; opt.def_cipher_algo = 0; opt.def_digest_algo = 0; @@ -2553,7 +2548,6 @@ main (int argc, char **argv) opt.allow_freeform_uid = 1; opt.pgp2_workarounds = 0; opt.escape_from = 0; - opt.force_v3_sigs = 0; opt.not_dash_escaped = 0; opt.def_cipher_algo = 0; opt.def_digest_algo = 0; @@ -2637,10 +2631,7 @@ main (int argc, char **argv) opt.verify_options&=~VERIFY_SHOW_PHOTOS; break; case oPhotoViewer: opt.photo_viewer = pargs.r.ret_str; break; - case oForceV3Sigs: opt.force_v3_sigs = 1; break; - case oNoForceV3Sigs: opt.force_v3_sigs = 0; break; - case oForceV4Certs: opt.force_v4_certs = 1; break; - case oNoForceV4Certs: opt.force_v4_certs = 0; break; + case oForceMDC: opt.force_mdc = 1; break; case oNoForceMDC: opt.force_mdc = 0; break; case oDisableMDC: opt.disable_mdc = 1; break; @@ -3288,15 +3279,17 @@ main (int argc, char **argv) /* Do these after the switch(), so they can override settings. */ if(PGP6) { + /* That does not anymore work becuase we have no more support + for v3 signatures. */ opt.disable_mdc=1; opt.escape_from=1; - opt.force_v3_sigs=1; opt.ask_sig_expire=0; } else if(PGP7) { + /* That does not anymore work because we have no more support + for v3 signatures. */ opt.escape_from=1; - opt.force_v3_sigs=1; opt.ask_sig_expire=0; } else if(PGP8) diff --git a/g10/keyedit.c b/g10/keyedit.c index 308576da0..a8e6f5d18 100644 --- a/g10/keyedit.c +++ b/g10/keyedit.c @@ -536,14 +536,10 @@ sign_uids (estream_t fp, { u32 sk_keyid[2], pk_keyid[2]; char *p, *trust_regexp = NULL; - int force_v4 = 0, class = 0, selfsig = 0; + int class = 0, selfsig = 0; u32 duration = 0, timestamp = 0; byte trust_depth = 0, trust_value = 0; - if (local || nonrevocable || trust - || opt.cert_policy_url || opt.cert_notations) - force_v4 = 1; - pk = sk_rover->pk; keyid_from_pk (pk, sk_keyid); @@ -567,14 +563,7 @@ sign_uids (estream_t fp, /* Is this a self-sig? */ if (pk_keyid[0] == sk_keyid[0] && pk_keyid[1] == sk_keyid[1]) - { - selfsig = 1; - /* Do not force a v4 sig here, otherwise it would - be difficult to remake a v3 selfsig. If this - is a v3->v4 promotion case, then we set - force_v4 later anyway. */ - force_v4 = 0; - } + selfsig = 1; } else if (node->pkt->pkttype == PKT_USER_ID) { @@ -716,7 +705,6 @@ sign_uids (estream_t fp, "it to an OpenPGP self-" "signature? (y/N) "))) { - force_v4 = 1; node->flag |= NODFLG_DELSIG; xfree (user); continue; @@ -860,7 +848,6 @@ sign_uids (estream_t fp, passphrase, etc). */ timestamp = now; duration = primary_pk->expiredate - now; - force_v4 = 1; } cpr_kill_prompt (); @@ -879,9 +866,6 @@ sign_uids (estream_t fp, duration = parse_expire_string (opt.def_cert_expire); } - if (duration) - force_v4 = 1; - if (selfsig) ; else @@ -1041,7 +1025,7 @@ sign_uids (estream_t fp, node->pkt->pkt.user_id, NULL, pk, - 0x13, 0, force_v4 ? 4 : 0, 0, 0, + 0x13, 0, 0, 0, keygen_add_std_prefs, primary_pk, NULL); else @@ -1049,7 +1033,7 @@ sign_uids (estream_t fp, node->pkt->pkt.user_id, NULL, pk, - class, 0, force_v4 ? 4 : 0, + class, 0, timestamp, duration, sign_mk_attrib, &attrib, NULL); @@ -3290,7 +3274,7 @@ menu_adduid (KBNODE pub_keyblock, int photo, const char *photo_name) if (!uid) return 0; - err = make_keysig_packet (&sig, pk, uid, NULL, pk, 0x13, 0, 0, 0, 0, + err = make_keysig_packet (&sig, pk, uid, NULL, pk, 0x13, 0, 0, 0, keygen_add_std_prefs, pk, NULL); if (err) { @@ -3674,9 +3658,7 @@ menu_addrevoker (ctrl_t ctrl, kbnode_t pub_keyblock, int sensitive) break; } - /* The 1F signature must be at least v4 to carry the revocation key - subpacket. */ - rc = make_keysig_packet (&sig, pk, NULL, NULL, pk, 0x1F, 0, 4, 0, 0, + rc = make_keysig_packet (&sig, pk, NULL, NULL, pk, 0x1F, 0, 0, 0, keygen_add_revkey, &revkey, NULL); if (rc) { @@ -4966,7 +4948,7 @@ reloop: /* (must use this, because we are modifing the list) */ } rc = make_keysig_packet (&sig, primary_pk, unode->pkt->pkt.user_id, - NULL, signerkey, 0x30, 0, 0, 0, 0, + NULL, signerkey, 0x30, 0, 0, 0, sign_mk_attrib, &attrib, NULL); free_public_key (signerkey); if (rc) @@ -5058,7 +5040,7 @@ menu_revuid (KBNODE pub_keyblock) node->flag &= ~NODFLG_SELUID; rc = make_keysig_packet (&sig, pk, uid, NULL, pk, 0x30, 0, - (reason == NULL) ? 3 : 0, timestamp, 0, + timestamp, 0, sign_mk_attrib, &attrib, NULL); if (rc) { @@ -5122,7 +5104,7 @@ menu_revkey (KBNODE pub_keyblock) return 0; rc = make_keysig_packet (&sig, pk, NULL, NULL, pk, - 0x20, 0, opt.force_v4_certs ? 4 : 0, 0, 0, + 0x20, 0, 0, 0, revocation_reason_build_cb, reason, NULL); if (rc) { @@ -5183,7 +5165,7 @@ menu_revsubkey (KBNODE pub_keyblock) node->flag &= ~NODFLG_SELKEY; rc = make_keysig_packet (&sig, mainpk, NULL, subpk, mainpk, - 0x28, 0, 0, 0, 0, sign_mk_attrib, &attrib, + 0x28, 0, 0, 0, sign_mk_attrib, &attrib, NULL); if (rc) { diff --git a/g10/keygen.c b/g10/keygen.c index 6079ff0b7..80954527c 100644 --- a/g10/keygen.c +++ b/g10/keygen.c @@ -812,7 +812,7 @@ make_backsig (PKT_signature *sig, PKT_public_key *pk, cache_public_key (sub_pk); err = make_keysig_packet (&backsig, pk, NULL, sub_pk, sub_psk, 0x19, - 0, 0, timestamp, 0, NULL, NULL, cache_nonce); + 0, timestamp, 0, NULL, NULL, cache_nonce); if (err) log_error ("make_keysig_packet failed for backsig: %s\n", g10_errstr(err)); else @@ -922,7 +922,7 @@ write_direct_sig (KBNODE root, PKT_public_key *psk, /* Make the signature. */ err = make_keysig_packet (&sig, pk, NULL,NULL, psk, 0x1F, - 0, 0, timestamp, 0, + 0, timestamp, 0, keygen_add_revkey, revkey, cache_nonce); if (err) { @@ -977,7 +977,7 @@ write_selfsigs (KBNODE root, PKT_public_key *psk, /* Make the signature. */ err = make_keysig_packet (&sig, pk, uid, NULL, psk, 0x13, - 0, 0, timestamp, 0, + 0, timestamp, 0, keygen_add_std_prefs, pk, cache_nonce); if (err) { @@ -1036,12 +1036,12 @@ write_keybinding (KBNODE root, PKT_public_key *pri_psk, PKT_public_key *sub_psk, oduap.usage = use; oduap.pk = sub_pk; err = make_keysig_packet (&sig, pri_pk, NULL, sub_pk, pri_psk, 0x18, - 0, 0, timestamp, 0, + 0, timestamp, 0, keygen_add_key_flags_and_expire, &oduap, cache_nonce); if (err) { - log_error ("make_keysig_packet failed: %s\n", g10_errstr (err)); + log_error ("make_keysig_packeto failed: %s\n", g10_errstr (err)); return err; } diff --git a/g10/keyid.c b/g10/keyid.c index 8b4eeb1f2..662806b3e 100644 --- a/g10/keyid.c +++ b/g10/keyid.c @@ -147,10 +147,6 @@ hash_public_key (gcry_md_hd_t md, PKT_public_key *pk) size_t nbytes; int npkey = pubkey_get_npkey (pk->pubkey_algo); - /* Two extra bytes for the expiration date in v3 */ - if(pk->version<4) - n+=2; - /* FIXME: We can avoid the extra malloc by calling only the first mpi_print here which computes the required length and calling the real mpi_print only at the end. The speed advantage would only be @@ -211,16 +207,6 @@ hash_public_key (gcry_md_hd_t md, PKT_public_key *pk) gcry_md_putc ( md, pk->timestamp >> 8 ); gcry_md_putc ( md, pk->timestamp ); - if(pk->version<4) - { - u16 days=0; - if(pk->expiredate) - days=(u16)((pk->expiredate - pk->timestamp) / 86400L); - - gcry_md_putc ( md, days >> 8 ); - gcry_md_putc ( md, days ); - } - gcry_md_putc ( md, pk->pubkey_algo ); if(npkey==0 && pk->pkey[0] @@ -432,18 +418,6 @@ keyid_from_pk (PKT_public_key *pk, u32 *keyid) keyid[1] = pk->keyid[1]; lowbits = keyid[1]; } - else if( pk->version < 4 ) - { - if( is_RSA(pk->pubkey_algo) ) - { - lowbits = (pubkey_get_npkey (pk->pubkey_algo) ? - v3_keyid ( pk->pkey[0], keyid ) : 0); /* From n. */ - pk->keyid[0] = keyid[0]; - pk->keyid[1] = keyid[1]; - } - else - pk->keyid[0]=pk->keyid[1]=keyid[0]=keyid[1]=lowbits=0xFFFFFFFF; - } else { const byte *dp; @@ -706,66 +680,20 @@ colon_expirestr_from_sig (PKT_signature *sig) byte * fingerprint_from_pk (PKT_public_key *pk, byte *array, size_t *ret_len) { - byte *buf; const byte *dp; - size_t len, nbytes; - int i; + size_t len; + gcry_md_hd_t md; - if ( pk->version < 4 ) - { - if ( is_RSA(pk->pubkey_algo) ) - { - /* RSA in version 3 packets is special. */ - gcry_md_hd_t md; - - if (gcry_md_open (&md, DIGEST_ALGO_MD5, 0)) - BUG (); - if ( pubkey_get_npkey (pk->pubkey_algo) > 1 ) - { - for (i=0; i < 2; i++) - { - if (gcry_mpi_print (GCRYMPI_FMT_USG, NULL, 0, - &nbytes, pk->pkey[i])) - BUG (); - /* fixme: Better allocate BUF on the stack */ - buf = xmalloc (nbytes); - if (gcry_mpi_print (GCRYMPI_FMT_USG, buf, nbytes, - NULL, pk->pkey[i])) - BUG (); - gcry_md_write (md, buf, nbytes); - xfree (buf); - } - } - gcry_md_final (md); - if (!array) - array = xmalloc (16); - len = 16; - memcpy (array, gcry_md_read (md, DIGEST_ALGO_MD5), 16); - gcry_md_close(md); - } - else - { - if (!array) - array = xmalloc(16); - len = 16; - memset (array,0,16); - } - } - else - { - gcry_md_hd_t md; - - md = do_fingerprint_md(pk); - dp = gcry_md_read( md, 0 ); - len = gcry_md_get_algo_dlen (gcry_md_get_algo (md)); - assert( len <= MAX_FINGERPRINT_LEN ); - if (!array) - array = xmalloc ( len ); - memcpy (array, dp, len ); - pk->keyid[0] = dp[12] << 24 | dp[13] << 16 | dp[14] << 8 | dp[15] ; - pk->keyid[1] = dp[16] << 24 | dp[17] << 16 | dp[18] << 8 | dp[19] ; - gcry_md_close( md); - } + md = do_fingerprint_md(pk); + dp = gcry_md_read( md, 0 ); + len = gcry_md_get_algo_dlen (gcry_md_get_algo (md)); + assert( len <= MAX_FINGERPRINT_LEN ); + if (!array) + array = xmalloc ( len ); + memcpy (array, dp, len ); + pk->keyid[0] = dp[12] << 24 | dp[13] << 16 | dp[14] << 8 | dp[15] ; + pk->keyid[1] = dp[16] << 24 | dp[17] << 16 | dp[18] << 8 | dp[19] ; + gcry_md_close( md); if (ret_len) *ret_len = len; diff --git a/g10/options.h b/g10/options.h index edd31a9c2..0875eb529 100644 --- a/g10/options.h +++ b/g10/options.h @@ -74,8 +74,6 @@ struct int no_armor; int list_packets; /* list-packets mode: 1=normal, 2=invoked by command*/ int def_cipher_algo; - int force_v3_sigs; - int force_v4_certs; int force_mdc; int disable_mdc; int def_digest_algo; diff --git a/g10/packet.h b/g10/packet.h index b1b82d75b..ba43638fa 100644 --- a/g10/packet.h +++ b/g10/packet.h @@ -530,7 +530,7 @@ int ask_for_detached_datafile( gcry_md_hd_t md, gcry_md_hd_t md2, int make_keysig_packet( PKT_signature **ret_sig, PKT_public_key *pk, PKT_user_id *uid, PKT_public_key *subpk, PKT_public_key *pksk, int sigclass, int digest_algo, - int sigversion, u32 timestamp, u32 duration, + u32 timestamp, u32 duration, int (*mksubpkt)(PKT_signature *, void *), void *opaque, const char *cache_nonce); diff --git a/g10/parse-packet.c b/g10/parse-packet.c index f7b2079b0..50da17cb9 100644 --- a/g10/parse-packet.c +++ b/g10/parse-packet.c @@ -1901,53 +1901,6 @@ parse_onepass_sig (IOBUF inp, int pkttype, unsigned long pktlen, } -static gcry_mpi_t -read_protected_v3_mpi (IOBUF inp, unsigned long *length) -{ - int c; - unsigned int nbits, nbytes; - unsigned char *buf, *p; - gcry_mpi_t val; - - if (*length < 2) - { - log_error ("mpi too small\n"); - return NULL; - } - - if ((c = iobuf_get (inp)) == -1) - return NULL; - --*length; - nbits = c << 8; - if ((c = iobuf_get (inp)) == -1) - return NULL; - --*length; - nbits |= c; - - if (nbits > 16384) - { - log_error ("mpi too large (%u bits)\n", nbits); - return NULL; - } - nbytes = (nbits + 7) / 8; - buf = p = xmalloc (2 + nbytes); - *p++ = nbits >> 8; - *p++ = nbits; - for (; nbytes && *length; nbytes--, --*length) - *p++ = iobuf_get (inp); - if (nbytes) - { - log_error ("packet shorter than mpi\n"); - xfree (buf); - return NULL; - } - - /* Convert buffer into an opaque MPI. */ - val = gcry_mpi_set_opaque (NULL, buf, (p - buf) * 8); - return val; -} - - static int parse_key (IOBUF inp, int pkttype, unsigned long pktlen, byte * hdr, int hdrlen, PACKET * pkt) @@ -1956,7 +1909,6 @@ parse_key (IOBUF inp, int pkttype, unsigned long pktlen, int i, version, algorithm; unsigned long timestamp, expiredate, max_expiredate; int npkey, nskey; - int is_v4 = 0; int rc = 0; u32 keyid[2]; PKT_public_key *pk; @@ -1991,8 +1943,19 @@ parse_key (IOBUF inp, int pkttype, unsigned long pktlen, return 0; } else if (version == 4) - is_v4 = 1; - else if (version != 2 && version != 3) + { + /* The only supported version. Use an older gpg + versions (i.e. gpg 1.4 to parse v3 packets). */ + } + else if (version == 2 || version == 3) + { + log_info ("packet(%d) with obsolete version %d\n", pkttype, version); + if (list_mode) + es_fprintf (listfp, ":key packet: [obsolete version %d]\n", version); + err = gpg_error (GPG_ERR_INV_PACKET); + goto leave; + } + else { log_error ("packet(%d) with unknown version %d\n", pkttype, version); if (list_mode) @@ -2012,23 +1975,8 @@ parse_key (IOBUF inp, int pkttype, unsigned long pktlen, timestamp = read_32 (inp); pktlen -= 4; - if (is_v4) - { - expiredate = 0; /* have to get it from the selfsignature */ - max_expiredate = 0; - } - else - { - unsigned short ndays; - ndays = read_16 (inp); - pktlen -= 2; - if (ndays) - expiredate = timestamp + ndays * 86400L; - else - expiredate = 0; - - max_expiredate = expiredate; - } + expiredate = 0; /* have to get it from the selfsignature */ + max_expiredate = 0; algorithm = iobuf_get_noeof (inp); pktlen--; if (list_mode) @@ -2145,7 +2093,7 @@ parse_key (IOBUF inp, int pkttype, unsigned long pktlen, ski->s2k.hash_algo = iobuf_get_noeof (inp); pktlen--; /* Check for the special GNU extension. */ - if (is_v4 && ski->s2k.mode == 101) + if (ski->s2k.mode == 101) { for (i = 0; i < 4 && pktlen; i++, pktlen--) temp[i] = iobuf_get_noeof (inp); @@ -2312,7 +2260,7 @@ parse_key (IOBUF inp, int pkttype, unsigned long pktlen, 10 * 8); pktlen = 0; } - else if (is_v4 && ski->is_protected) + else if (ski->is_protected) { /* Ugly: The length is encrypted too, so we read all stuff * up to the end of the packet into the first SKEY @@ -2331,29 +2279,18 @@ parse_key (IOBUF inp, int pkttype, unsigned long pktlen, } else { - /* The v3 method: The mpi length is not encrypted. */ + /* Not encrypted. */ for (i = npkey; i < nskey; i++) { - if (ski->is_protected) - { - pk->pkey[i] = read_protected_v3_mpi (inp, &pktlen); - if (pk->pkey[i]) - gcry_mpi_set_flag (pk->pkey[i], GCRYMPI_FLAG_USER1); - if (list_mode) - es_fprintf (listfp, "\tskey[%d]: [v3 protected]\n", i); - } - else - { - unsigned int n = pktlen; - pk->pkey[i] = mpi_read (inp, &n, 0); - pktlen -= n; - if (list_mode) - { - es_fprintf (listfp, "\tskey[%d]: ", i); - mpi_print (listfp, pk->pkey[i], mpi_print_mode); - es_putc ('\n', listfp); - } - } + unsigned int n = pktlen; + pk->pkey[i] = mpi_read (inp, &n, 0); + pktlen -= n; + if (list_mode) + { + es_fprintf (listfp, "\tskey[%d]: ", i); + mpi_print (listfp, pk->pkey[i], mpi_print_mode); + es_putc ('\n', listfp); + } if (!pk->pkey[i]) err = gpg_error (GPG_ERR_INV_PACKET); diff --git a/g10/revoke.c b/g10/revoke.c index 81b5d6de5..6b9e709fe 100644 --- a/g10/revoke.c +++ b/g10/revoke.c @@ -338,7 +338,7 @@ gen_desig_revoke( const char *uname, strlist_t locusr ) /* create it */ rc = make_keysig_packet( &sig, pk, NULL, NULL, pk2, 0x20, 0, - 0, 0, 0, + 0, 0, revocation_reason_build_cb, reason, NULL); if( rc ) { @@ -465,7 +465,6 @@ create_revocation (const char *filename, push_armor_filter (afx, out); rc = make_keysig_packet (&sig, psk, NULL, NULL, psk, 0x20, 0, - opt.force_v4_certs? 4:0, 0, 0, revocation_reason_build_cb, reason, cache_nonce); if (rc) @@ -649,16 +648,13 @@ gen_revoke (const char *uname) goto leave; } - if (psk->version >= 4 || opt.force_v4_certs) + /* Get the reason for the revocation. */ + reason = ask_revocation_reason (1, 0, 1); + if (!reason) { - /* Get the reason for the revocation. */ - reason = ask_revocation_reason (1, 0, 1); - if (!reason) - { - /* user decided to cancel */ - rc = 0; - goto leave; - } + /* User decided to cancel. */ + rc = 0; + goto leave; } if (!opt.armor) diff --git a/g10/sign.c b/g10/sign.c index bd78c1750..e7d4a6888 100644 --- a/g10/sign.c +++ b/g10/sign.c @@ -155,30 +155,32 @@ mk_notation_policy_etc (PKT_signature *sig, static void hash_uid (gcry_md_hd_t md, int sigversion, const PKT_user_id *uid) { - if ( sigversion >= 4 ) { - byte buf[5]; + byte buf[5]; - if(uid->attrib_data) { - buf[0] = 0xd1; /* indicates an attribute packet */ - buf[1] = uid->attrib_len >> 24; /* always use 4 length bytes */ - buf[2] = uid->attrib_len >> 16; - buf[3] = uid->attrib_len >> 8; - buf[4] = uid->attrib_len; - } - else { - buf[0] = 0xb4; /* indicates a userid packet */ - buf[1] = uid->len >> 24; /* always use 4 length bytes */ - buf[2] = uid->len >> 16; - buf[3] = uid->len >> 8; - buf[4] = uid->len; - } - gcry_md_write( md, buf, 5 ); + (void)sigversion; + + if (uid->attrib_data) + { + buf[0] = 0xd1; /* Indicates an attribute packet. */ + buf[1] = uid->attrib_len >> 24; /* Always use 4 length bytes. */ + buf[2] = uid->attrib_len >> 16; + buf[3] = uid->attrib_len >> 8; + buf[4] = uid->attrib_len; } + else + { + buf[0] = 0xb4; /* Indicates a userid packet. */ + buf[1] = uid->len >> 24; /* Always use 4 length bytes. */ + buf[2] = uid->len >> 16; + buf[3] = uid->len >> 8; + buf[4] = uid->len; + } + gcry_md_write( md, buf, 5 ); - if(uid->attrib_data) - gcry_md_write (md, uid->attrib_data, uid->attrib_len ); - else - gcry_md_write (md, uid->name, uid->len ); + if (uid->attrib_data) + gcry_md_write (md, uid->attrib_data, uid->attrib_len ); + else + gcry_md_write (md, uid->name, uid->len ); } @@ -188,45 +190,38 @@ hash_uid (gcry_md_hd_t md, int sigversion, const PKT_user_id *uid) static void hash_sigversion_to_magic (gcry_md_hd_t md, const PKT_signature *sig) { - if (sig->version >= 4) - gcry_md_putc (md, sig->version); - gcry_md_putc (md, sig->sig_class); - if (sig->version < 4) { - u32 a = sig->timestamp; - gcry_md_putc (md, (a >> 24) & 0xff ); - gcry_md_putc (md, (a >> 16) & 0xff ); - gcry_md_putc (md, (a >> 8) & 0xff ); - gcry_md_putc (md, a & 0xff ); - } - else { - byte buf[6]; - size_t n; + byte buf[6]; + size_t n; - gcry_md_putc (md, sig->pubkey_algo); - gcry_md_putc (md, sig->digest_algo); - if (sig->hashed) { - n = sig->hashed->len; - gcry_md_putc (md, (n >> 8) ); - gcry_md_putc (md, n ); - gcry_md_write (md, sig->hashed->data, n ); - n += 6; - } - else { - gcry_md_putc (md, 0); /* always hash the length of the subpacket*/ - gcry_md_putc (md, 0); - n = 6; - } - /* add some magic */ - buf[0] = sig->version; - buf[1] = 0xff; - buf[2] = n >> 24; /* hmmm, n is only 16 bit, so this is always 0 */ - buf[3] = n >> 16; - buf[4] = n >> 8; - buf[5] = n; - gcry_md_write (md, buf, 6); + gcry_md_putc (md, sig->version); + gcry_md_putc (md, sig->sig_class); + gcry_md_putc (md, sig->pubkey_algo); + gcry_md_putc (md, sig->digest_algo); + if (sig->hashed) + { + n = sig->hashed->len; + gcry_md_putc (md, (n >> 8) ); + gcry_md_putc (md, n ); + gcry_md_write (md, sig->hashed->data, n ); + n += 6; } + else + { + gcry_md_putc (md, 0); /* Always hash the length of the subpacket. */ + gcry_md_putc (md, 0); + n = 6; + } + /* Add some magic. */ + buf[0] = sig->version; + buf[1] = 0xff; + buf[2] = n >> 24; /* (n is only 16 bit, so this is always 0) */ + buf[3] = n >> 16; + buf[4] = n >> 8; + buf[5] = n; + gcry_md_write (md, buf, 6); } + /* Perform the sign operation. If CACHE_NONCE is given the agent is advised to use that cached passphrase fro the key. */ static int @@ -520,26 +515,6 @@ hash_for (PKT_public_key *pk) } -/* Return true iff all keys in SK_LIST are old style (v3 RSA). */ -static int -only_old_style (SK_LIST sk_list) -{ - SK_LIST sk_rover = NULL; - int old_style = 0; - - for (sk_rover = sk_list; sk_rover; sk_rover = sk_rover->next) - { - PKT_public_key *pk = sk_rover->pk; - - if (pk->pubkey_algo == PUBKEY_ALGO_RSA && pk->version < 4) - old_style = 1; - else - return 0; - } - return old_style; -} - - static void print_status_sig_created (PKT_public_key *pk, PKT_signature *sig, int what) { @@ -705,10 +680,8 @@ write_signature_packets (SK_LIST sk_list, IOBUF out, gcry_md_hd_t hash, /* Build the signature packet. */ sig = xmalloc_clear (sizeof *sig); - if (opt.force_v3_sigs) - sig->version = 3; - else if (duration || opt.sig_policy_url - || opt.sig_notations || opt.sig_keyserver_url) + if (duration || opt.sig_policy_url + || opt.sig_notations || opt.sig_keyserver_url) sig->version = 4; else sig->version = pk->version; @@ -727,11 +700,8 @@ write_signature_packets (SK_LIST sk_list, IOBUF out, gcry_md_hd_t hash, if (gcry_md_copy (&md, hash)) BUG (); - if (sig->version >= 4) - { - build_sig_subpkt_from_sig (sig); - mk_notation_policy_etc (sig, pk, NULL); - } + build_sig_subpkt_from_sig (sig); + mk_notation_policy_etc (sig, pk, NULL); hash_sigversion_to_magic (md, sig); gcry_md_final (md); @@ -814,13 +784,10 @@ sign_file (ctrl_t ctrl, strlist_t filenames, int detached, strlist_t locusr, && (rc=setup_symkey(&efx.symkey_s2k,&efx.symkey_dek))) goto leave; - if(!opt.force_v3_sigs) - { - if(opt.ask_sig_expire && !opt.batch) - duration=ask_expire_interval(1,opt.def_sig_expire); - else - duration=parse_expire_string(opt.def_sig_expire); - } + if (opt.ask_sig_expire && !opt.batch) + duration = ask_expire_interval(1,opt.def_sig_expire); + else + duration = parse_expire_string(opt.def_sig_expire); /* Note: In the old non-agent version the following call used to unprotect the secret key. This is now done on demand by the agent. */ @@ -1123,30 +1090,22 @@ clearsign_file( const char *fname, strlist_t locusr, const char *outfile ) int rc = 0; SK_LIST sk_list = NULL; SK_LIST sk_rover = NULL; - int old_style = 0; - int only_md5 = 0; u32 duration=0; pfx = new_progress_context (); afx = new_armor_context (); init_packet( &pkt ); - if(!opt.force_v3_sigs) - { - if(opt.ask_sig_expire && !opt.batch) - duration=ask_expire_interval(1,opt.def_sig_expire); - else - duration=parse_expire_string(opt.def_sig_expire); - } + if (opt.ask_sig_expire && !opt.batch) + duration = ask_expire_interval (1,opt.def_sig_expire); + else + duration = parse_expire_string (opt.def_sig_expire); /* Note: In the old non-agent version the following call used to unprotect the secret key. This is now done on demand by the agent. */ if( (rc=build_sk_list( locusr, &sk_list, PUBKEY_USAGE_SIG )) ) goto leave; - if(!duration ) - old_style = only_old_style( sk_list ); - /* prepare iobufs */ inp = iobuf_open(fname); if (inp && is_secured_file (iobuf_get_fd (inp))) @@ -1184,18 +1143,7 @@ clearsign_file( const char *fname, strlist_t locusr, const char *outfile ) iobuf_writestr(out, "-----BEGIN PGP SIGNED MESSAGE-----" LF ); - for (sk_rover = sk_list; sk_rover; sk_rover = sk_rover->next) - { - if (hash_for (sk_rover->pk) == DIGEST_ALGO_MD5) - only_md5 = 1; - else - { - only_md5 = 0; - break; - } - } - - if( !(old_style && only_md5) ) { + { const char *s; int any = 0; byte hashs_seen[256]; @@ -1234,8 +1182,8 @@ clearsign_file( const char *fname, strlist_t locusr, const char *outfile ) if ( DBG_HASHING ) gcry_md_debug ( textmd, "clearsign" ); - copy_clearsig_text( out, inp, textmd, !opt.not_dash_escaped, - opt.escape_from, (old_style && only_md5) ); + copy_clearsig_text (out, inp, textmd, !opt.not_dash_escaped, + opt.escape_from); /* fixme: check for read errors */ /* now write the armor */ @@ -1292,13 +1240,10 @@ sign_symencrypt_file (const char *fname, strlist_t locusr) memset( &cfx, 0, sizeof cfx); init_packet( &pkt ); - if(!opt.force_v3_sigs) - { - if(opt.ask_sig_expire && !opt.batch) - duration=ask_expire_interval(1,opt.def_sig_expire); - else - duration=parse_expire_string(opt.def_sig_expire); - } + if (opt.ask_sig_expire && !opt.batch) + duration = ask_expire_interval (1, opt.def_sig_expire); + else + duration = parse_expire_string (opt.def_sig_expire); /* Note: In the old non-agent version the following call used to unprotect the secret key. This is now done on demand by the agent. */ @@ -1441,52 +1386,39 @@ sign_symencrypt_file (const char *fname, strlist_t locusr) * applied (actually: dropped) when a v3 key is used. TIMESTAMP is * the timestamp to use for the signature. 0 means "now" */ int -make_keysig_packet( PKT_signature **ret_sig, PKT_public_key *pk, +make_keysig_packet (PKT_signature **ret_sig, PKT_public_key *pk, PKT_user_id *uid, PKT_public_key *subpk, PKT_public_key *pksk, int sigclass, int digest_algo, - int sigversion, u32 timestamp, u32 duration, + u32 timestamp, u32 duration, int (*mksubpkt)(PKT_signature *, void *), void *opaque, const char *cache_nonce) { PKT_signature *sig; int rc=0; + int sigversion; gcry_md_hd_t md; assert( (sigclass >= 0x10 && sigclass <= 0x13) || sigclass == 0x1F || sigclass == 0x20 || sigclass == 0x18 || sigclass == 0x19 || sigclass == 0x30 || sigclass == 0x28 ); - if (opt.force_v4_certs) - sigversion = 4; - + sigversion = 4; if (sigversion < pksk->version) sigversion = pksk->version; - /* If you are making a signature on a v4 key using your v3 key, it - doesn't make sense to generate a v3 sig. After all, no v3-only - PGP implementation could understand the v4 key in the first - place. Note that this implies that a signature on an attribute - uid is usually going to be v4 as well, since they are not - generally found on v3 keys. */ - if (sigversion < pk->version) - sigversion = pk->version; - if( !digest_algo ) { - /* Basically, this means use SHA1 always unless it's a v3 RSA - key making a v3 cert (use MD5), or the user specified - something (use whatever they said), or it's DSA (use the - best match). They still can't pick an inappropriate hash - for DSA or the signature will fail. Note that this still - allows the caller of make_keysig_packet to override the - user setting if it must. */ + /* Basically, this means use SHA1 always unless the user + specified something (use whatever they said), or it's DSA + (use the best match). They still can't pick an + inappropriate hash for DSA or the signature will fail. + Note that this still allows the caller of + make_keysig_packet to override the user setting if it + must. */ if(opt.cert_digest_algo) digest_algo=opt.cert_digest_algo; - else if(pksk->pubkey_algo == PUBKEY_ALGO_RSA - && pk->version<4 && sigversion<4) - digest_algo = DIGEST_ALGO_MD5; else if(pksk->pubkey_algo == PUBKEY_ALGO_DSA) digest_algo = match_dsa_hash (gcry_mpi_get_nbits (pksk->pkey[1])/8); else if (pksk->pubkey_algo == PUBKEY_ALGO_ECDSA @@ -1533,16 +1465,14 @@ make_keysig_packet( PKT_signature **ret_sig, PKT_public_key *pk, if(duration) sig->expiredate=sig->timestamp+duration; sig->sig_class = sigclass; - if( sig->version >= 4 ) - { - build_sig_subpkt_from_sig( sig ); - mk_notation_policy_etc (sig, pk, pksk); - } + + build_sig_subpkt_from_sig( sig ); + mk_notation_policy_etc (sig, pk, pksk); /* Crucial that the call to mksubpkt comes LAST before the calls to finalize the sig as that makes it possible for the mksubpkt function to get a reliable pointer to the subpacket area. */ - if( sig->version >= 4 && mksubpkt ) + if (mksubpkt) rc = (*mksubpkt)( sig, opaque ); if( !rc ) { @@ -1627,17 +1557,14 @@ update_keysig_packet( PKT_signature **ret_sig, duration of 1) since build-packet.c:build_sig_subpkt_from_sig detects this case. */ - if( sig->version >= 4 ) - { - /* Put the updated timestamp into the sig. Note that this - will automagically lower any sig expiration dates to - correctly correspond to the differences in the timestamps - (i.e. the duration will shrink). */ - build_sig_subpkt_from_sig( sig ); + /* Put the updated timestamp into the sig. Note that this will + automagically lower any sig expiration dates to correctly + correspond to the differences in the timestamps (i.e. the + duration will shrink). */ + build_sig_subpkt_from_sig( sig ); - if (mksubpkt) - rc = (*mksubpkt)(sig, opaque); - } + if (mksubpkt) + rc = (*mksubpkt)(sig, opaque); if (!rc) { hash_sigversion_to_magic (md, sig); diff --git a/g10/textfilter.c b/g10/textfilter.c index 14bf69962..394d9c3bb 100644 --- a/g10/textfilter.c +++ b/g10/textfilter.c @@ -161,7 +161,7 @@ text_filter( void *opaque, int control, */ int copy_clearsig_text( IOBUF out, IOBUF inp, gcry_md_hd_t md, - int escape_dash, int escape_from, int pgp2mode ) + int escape_dash, int escape_from) { unsigned int maxlen; byte *buffer = NULL; /* malloced buffer */ @@ -170,10 +170,7 @@ copy_clearsig_text( IOBUF out, IOBUF inp, gcry_md_hd_t md, int truncated = 0; int pending_lf = 0; - if( !opt.pgp2_workarounds ) - pgp2mode = 0; - - if( !escape_dash ) + if( !escape_dash ) escape_from = 0; write_status_begin_signing (md); @@ -194,9 +191,7 @@ copy_clearsig_text( IOBUF out, IOBUF inp, gcry_md_hd_t md, gcry_md_putc ( md, '\n' ); } gcry_md_write ( md, buffer, - len_without_trailing_chars (buffer, n, - pgp2mode? - " \r\n":" \t\r\n")); + len_without_trailing_chars (buffer, n, " \t\r\n")); } else gcry_md_write ( md, buffer, n ); diff --git a/tests/openpgp/defs.inc b/tests/openpgp/defs.inc index 2faa4c25a..b7320d562 100755 --- a/tests/openpgp/defs.inc +++ b/tests/openpgp/defs.inc @@ -24,7 +24,7 @@ dsa_usrname1="pgp5" # we use the sub key because we do not yet have the logic to to derive # the first encryption key from a keyblock (I guess) (Well of course # we have this by now and the notation below will lookup the primary -# first and the search for the encryption subkey.) +# first and then search for the encryption subkey.) dsa_usrname2="0xCB879DE9"