diff options
author | Werner Koch <wk@gnupg.org> | 2006-08-21 22:20:23 +0200 |
---|---|---|
committer | Werner Koch <wk@gnupg.org> | 2006-08-21 22:20:23 +0200 |
commit | 0ebd23fa76e5af72ad3dc33144efa45500101a1b (patch) | |
tree | f5b5f10a242e8d597c7fc599663a455350f0c43b | |
parent | disconnectafter wake-up bug fix by Bob Dunlop. (diff) | |
download | gnupg2-0ebd23fa76e5af72ad3dc33144efa45500101a1b.tar.xz gnupg2-0ebd23fa76e5af72ad3dc33144efa45500101a1b.zip |
Migrated more stuff to doc/
Migrated the gpg regression tests.
Some changes tp the gpg code to fix bugs and
for the use in testing.
make distcheck works now with gpg enabled.
87 files changed, 9634 insertions, 119 deletions
@@ -1,3 +1,10 @@ +2006-08-21 Werner Koch <wk@g10code.com> + + * configure.ac: Removed docbook tests. + (AC_CONFIG_FILES): Added gpgkeys_test and gpgkeys_mailto. + + * Makefile.am (DISTCHECK_CONFIGURE_FLAGS): Enable gpg. + 2006-08-17 Werner Koch <wk@g10code.com> * THANKS: Merged with the 1.4 one. diff --git a/Makefile.am b/Makefile.am index 119df3edb..8281496cf 100644 --- a/Makefile.am +++ b/Makefile.am @@ -22,6 +22,7 @@ ACLOCAL_AMFLAGS = -I m4 -I gl/m4 AUTOMAKE_OPTIONS = dist-bzip2 +DISTCHECK_CONFIGURE_FLAGS = --enable-gpg EXTRA_DIST = scripts/config.rpath autogen.sh README.CVS DISTCLEANFILES = g10defs.h @@ -17,6 +17,7 @@ Anthony Mulcahy anthony at kcn.ne.jp Ariel T Glenn ariel at columbia.edu Bernhard Herzog bh at intevation.de Bernhard Reiter bernhard de intevation.de +Bob Dunlop bob at xyzzy.org.uk Bob Mathews bobmathews at mindspring.com Bodo Moeller Bodo_Moeller at public.uni-hamburg.de Brendan O'Dea bod at debian.org @@ -115,6 +115,9 @@ might want to have an agent context for each service request Remove the whole stuff? ** qbits We pass a new qbit parameter to genkey - implement this in libgcrypt. +** skclist.c + As soon as we switch to libgcrypt 1.3 we should remove the hard + coded constant in random_is_faked. * common/ diff --git a/common/ChangeLog b/common/ChangeLog index c033b62d9..01777e4d0 100644 --- a/common/ChangeLog +++ b/common/ChangeLog @@ -1,3 +1,9 @@ +2006-08-21 Werner Koch <wk@g10code.com> + + * Makefile.am (libcommon_a_SOURCES): Added keyserver.h + + * openpgpdefs.h: New. Stripped from ..g10/packet.h. + 2006-08-16 Werner Koch <wk@g10code.com> * keyserver.h: Moved from ../include to here. diff --git a/common/Makefile.am b/common/Makefile.am index 7bf008caa..9bdc8dce6 100644 --- a/common/Makefile.am +++ b/common/Makefile.am @@ -30,6 +30,8 @@ AM_CFLAGS = $(LIBGCRYPT_CFLAGS) $(LIBASSUAN_CFLAGS) $(KSBA_CFLAGS) \ libcommon_a_SOURCES = \ util.h i18n.h \ errors.h \ + openpgpdefs.h \ + keyserver.h \ sexp-parse.h \ sexputil.c \ maperror.c \ @@ -56,7 +58,6 @@ libcommon_a_SOURCES = \ pka.c pka.h \ http.c http.h - libsimple_pwquery_a_SOURCES = \ simple-pwquery.c simple-pwquery.h asshelp.c asshelp.h diff --git a/common/openpgpdefs.h b/common/openpgpdefs.h new file mode 100644 index 000000000..bda70fd72 --- /dev/null +++ b/common/openpgpdefs.h @@ -0,0 +1,89 @@ +/* openpgpdefs.h - Constants from the OpenPGP standard (rfc2440) + * Copyright (C) 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005, + * 2006 Free Software Foundation, Inc. + * + * This file is part of GnuPG. + * + * GnuPG is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * GnuPG is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, + * USA. + */ + +#ifndef GNUPG_COMMON_OPENPGPDEFS_H +#define GNUPG_COMMON_OPENPGPDEFS_H + +typedef enum + { + PKT_NONE = 0, + PKT_PUBKEY_ENC = 1, /* Public key encrypted packet. */ + PKT_SIGNATURE = 2, /* Secret key encrypted packet. */ + PKT_SYMKEY_ENC = 3, /* Session key packet. */ + PKT_ONEPASS_SIG = 4, /* One pass sig packet. */ + PKT_SECRET_KEY = 5, /* Secret key. */ + PKT_PUBLIC_KEY = 6, /* Public key. */ + PKT_SECRET_SUBKEY = 7, /* Secret subkey. */ + PKT_COMPRESSED = 8, /* Compressed data packet. */ + PKT_ENCRYPTED = 9, /* Conventional encrypted data. */ + PKT_MARKER = 10, /* Marker packet. */ + PKT_PLAINTEXT = 11, /* Literal data packet. */ + PKT_RING_TRUST = 12, /* Keyring trust packet. */ + PKT_USER_ID = 13, /* User id packet. */ + PKT_PUBLIC_SUBKEY = 14, /* Public subkey. */ + PKT_OLD_COMMENT = 16, /* Comment packet from an OpenPGP draft. */ + PKT_ATTRIBUTE = 17, /* PGP's attribute packet. */ + PKT_ENCRYPTED_MDC = 18, /* Integrity protected encrypted data. */ + PKT_MDC = 19, /* Manipulation detection code packet. */ + PKT_COMMENT = 61, /* new comment packet (GnuPG specific). */ + PKT_GPG_CONTROL = 63 /* internal control packet (GnuPG specific). */ + } +pkttype_t; + + +typedef enum + { + SIGSUBPKT_TEST_CRITICAL = -3, + SIGSUBPKT_LIST_UNHASHED = -2, + SIGSUBPKT_LIST_HASHED = -1, + SIGSUBPKT_NONE = 0, + SIGSUBPKT_SIG_CREATED = 2, /* Signature creation time. */ + SIGSUBPKT_SIG_EXPIRE = 3, /* Signature expiration time. */ + SIGSUBPKT_EXPORTABLE = 4, /* Exportable. */ + SIGSUBPKT_TRUST = 5, /* Trust signature. */ + SIGSUBPKT_REGEXP = 6, /* Regular expression. */ + SIGSUBPKT_REVOCABLE = 7, /* Revocable. */ + SIGSUBPKT_KEY_EXPIRE = 9, /* Key expiration time. */ + SIGSUBPKT_ARR = 10, /* Additional recipient request. */ + SIGSUBPKT_PREF_SYM = 11, /* Preferred symmetric algorithms. */ + SIGSUBPKT_REV_KEY = 12, /* Revocation key. */ + SIGSUBPKT_ISSUER = 16, /* Issuer key ID. */ + SIGSUBPKT_NOTATION = 20, /* Notation data. */ + SIGSUBPKT_PREF_HASH = 21, /* Preferred hash algorithms. */ + SIGSUBPKT_PREF_COMPR = 22, /* Preferred compression algorithms. */ + SIGSUBPKT_KS_FLAGS = 23, /* Key server preferences. */ + SIGSUBPKT_PREF_KS = 24, /* Preferred key server. */ + SIGSUBPKT_PRIMARY_UID = 25, /* Primary user id. */ + SIGSUBPKT_POLICY = 26, /* Policy URL. */ + SIGSUBPKT_KEY_FLAGS = 27, /* Key flags. */ + SIGSUBPKT_SIGNERS_UID = 28, /* Signer's user id. */ + SIGSUBPKT_REVOC_REASON = 29, /* Reason for revocation. */ + SIGSUBPKT_FEATURES = 30, /* Feature flags. */ + + SIGSUBPKT_SIGNATURE = 32, /* Embedded signature. */ + + SIGSUBPKT_FLAG_CRITICAL = 128 + } +sigsubpkttype_t; + + +#endif /*GNUPG_COMMON_OPENPGPDEFS_H*/ diff --git a/configure.ac b/configure.ac index 99a074bc3..4ab9986a9 100644 --- a/configure.ac +++ b/configure.ac @@ -442,10 +442,7 @@ AC_PATH_PROG(PERL,"perl") AC_ISC_POSIX gl_EARLY AC_SYS_LARGEFILE -AC_CHECK_PROG(DOCBOOK_TO_MAN, docbook-to-man, yes, no) -AM_CONDITIONAL(HAVE_DOCBOOK_TO_MAN, test "$ac_cv_prog_DOCBOOK_TO_MAN" = yes) GNUPG_CHECK_FAQPROG -GNUPG_CHECK_DOCBOOK_TO_TEXI GNUPG_CHECK_USTAR @@ -1312,9 +1309,13 @@ sm/Makefile agent/Makefile scd/Makefile keyserver/Makefile +keyserver/gpgkeys_mailto +keyserver/gpgkeys_test +tools/gpg-zip tools/Makefile doc/Makefile tests/Makefile +tests/openpgp/Makefile ]) AC_OUTPUT diff --git a/doc/ChangeLog b/doc/ChangeLog index a697b2605..b70e70fdc 100644 --- a/doc/ChangeLog +++ b/doc/ChangeLog @@ -1,3 +1,7 @@ +2006-08-21 Werner Koch <wk@g10code.com> + + * Makefile.am: Added other doc files from gpg 1.4. + 2006-08-17 Werner Koch <wk@g10code.com> * Makefile.am: Added rules to build man pages. diff --git a/doc/DETAILS b/doc/DETAILS new file mode 100644 index 000000000..51a31a5b4 --- /dev/null +++ b/doc/DETAILS @@ -0,0 +1,1250 @@ + -*- text -*- +Format of colon listings +======================== +First an example: + +$ gpg --fixed-list-mode --with-colons --list-keys \ + --with-fingerprint --with-fingerprint wk@gnupg.org + +pub:f:1024:17:6C7EE1B8621CC013:899817715:1055898235::m:::scESC: +fpr:::::::::ECAF7590EB3443B5C7CF3ACB6C7EE1B8621CC013: +uid:f::::::::Werner Koch <wk@g10code.com>: +uid:f::::::::Werner Koch <wk@gnupg.org>: +sub:f:1536:16:06AD222CADF6A6E1:919537416:1036177416:::::e: +fpr:::::::::CF8BCC4B18DE08FCD8A1615906AD222CADF6A6E1: +sub:r:1536:20:5CE086B5B5A18FF4:899817788:1025961788:::::esc: +fpr:::::::::AB059359A3B81F410FCFF97F5CE086B5B5A18FF4: + +The double --with-fingerprint prints the fingerprint for the subkeys +too, --fixed-list-mode is themodern listing way printing dates in +seconds since Epoch and does not merge the first userID with the pub +record. + + + 1. Field: Type of record + pub = public key + crt = X.509 certificate + crs = X.509 certificate and private key available + sub = subkey (secondary key) + sec = secret key + ssb = secret subkey (secondary key) + uid = user id (only field 10 is used). + uat = user attribute (same as user id except for field 10). + sig = signature + rev = revocation signature + fpr = fingerprint: (fingerprint is in field 10) + pkd = public key data (special field format, see below) + grp = reserved for gpgsm + rvk = revocation key + tru = trust database information + spk = signature subpacket + + 2. Field: A letter describing the calculated trust. This is a single + letter, but be prepared that additional information may follow + in some future versions. (not used for secret keys) + o = Unknown (this key is new to the system) + i = The key is invalid (e.g. due to a missing self-signature) + d = The key has been disabled + (deprecated - use the 'D' in field 12 instead) + r = The key has been revoked + e = The key has expired + - = Unknown trust (i.e. no value assigned) + q = Undefined trust + '-' and 'q' may safely be treated as the same + value for most purposes + n = Don't trust this key at all + m = There is marginal trust in this key + f = The key is fully trusted + u = The key is ultimately trusted. This often means + that the secret key is available, but any key may + be marked as ultimately trusted. + 3. Field: length of key in bits. + 4. Field: Algorithm: 1 = RSA + 16 = Elgamal (encrypt only) + 17 = DSA (sometimes called DH, sign only) + 20 = Elgamal (sign and encrypt - don't use them!) + (for other id's see include/cipher.h) + 5. Field: KeyID + 6. Field: Creation Date (in UTC). For UID and UAT records, this is the + self-signature date. Note that the dae is usally printed + in seconds since epoch, however, we are migrating to an ISO + 8601 format (e.g. "19660205T091500"). This is currently + only relevant for X.509, A simple way to detect the format + is be scannning for the 'T'. + 7. Field: Key or user ID/user attribute expiration date or empty if none. + 8. Field: Used for serial number in crt records (used to be the Local-ID). + For UID and UAT records, this is a hash of the user ID contents + used to represent that exact user ID. For trust signatures, + this is the trust depth seperated by the trust value by a + space. + 9. Field: Ownertrust (primary public keys only) + This is a single letter, but be prepared that additional + information may follow in some future versions. For trust + signatures with a regular expression, this is the regular + expression value, quoted as in field 10. +10. Field: User-ID. The value is quoted like a C string to avoid + control characters (the colon is quoted "\x3a"). + This is not used with --fixed-list-mode in gpg. + A UAT record puts the attribute subpacket count here, a + space, and then the total attribute subpacket size. + In gpgsm the issuer name comes here + An FPR record stores the fingerprint here. + The fingerprint of an revocation key is stored here. +11. Field: Signature class. This is a 2 digit hexnumber followed by + either the letter 'x' for an exportable signature or the + letter 'l' for a local-only signature. + The class byte of an revocation key is also given here, + 'x' and 'l' ist used the same way. +12. Field: Key capabilities: + e = encrypt + s = sign + c = certify + a = authentication + A key may have any combination of them in any order. In + addition to these letters, the primary key has uppercase + versions of the letters to denote the _usable_ + capabilities of the entire key, and a potential letter 'D' + to indicate a disabled key. +13. Field: Used in FPR records for S/MIME keys to store the fingerprint of + the issuer certificate. This is useful to build the + certificate path based on certificates stored in the local + keyDB; it is only filled if the issue certificate is + available. The advantage of using this value is that it is + guaranteed to have been been build by the same lookup + algorithm as gpgsm uses. + For "uid" recods this lists the preferences n the sameway the + -edit menu does. + For "sig" records, this is the fingerprint of the key that + issued the signature. Note that this is only filled in if + the signature verified correctly. Note also that for + various technical reasons, this fingerprint is only + available if --no-sig-cache is used. + +14. Field Flag field used in the --edit menu output: + +15. Field Used in sec/sbb to print the serial number of a token + (internal protect mode 1002) or a '#' if that key is a + simple stub (internal protect mode 1001) + +All dates are displayed in the format yyyy-mm-dd unless you use the +option --fixed-list-mode in which case they are displayed as seconds +since Epoch. More fields may be added later, so parsers should be +prepared for this. When parsing a number the parser should stop at the +first non-number character so that additional information can later be +added. + +If field 1 has the tag "pkd", a listing looks like this: +pkd:0:1024:B665B1435F4C2 .... FF26ABB: + ! ! !-- the value + ! !------ for information number of bits in the value + !--------- index (eg. DSA goes from 0 to 3: p,q,g,y) + + +The "tru" trust database records have the fields: + + 2: Reason for staleness of trust. If this field is empty, then the + trustdb is not stale. This field may have multiple flags in it: + + o: Trustdb is old + t: Trustdb was built with a different trust model than the one we + are using now. + + 3: Trust model: + 0: Classic trust model, as used in PGP 2.x. + 1: PGP trust model, as used in PGP 6 and later. This is the same + as the classic trust model, except for the addition of trust + signatures. + + GnuPG before version 1.4 used the classic trust model by default. + GnuPG 1.4 and later uses the PGP trust model by default. + + 4: Date trustdb was created in seconds since 1/1/1970. + 5: Date trustdb will expire in seconds since 1/1/1970. + +The "spk" signature subpacket records have the fields: + + 2: Subpacket number as per RFC-2440 and later. + 3: Flags in hex. Currently the only two bits assigned are 1, to + indicate that the subpacket came from the hashed part of the + signature, and 2, to indicate the subpacket was marked critical. + 4: Length of the subpacket. Note that this is the length of the + subpacket, and not the length of field 5 below. Due to the need + for %-encoding, the length of field 5 may be up to 3x this value. + 5: The subpacket data. Printable ASCII is shown as ASCII, but other + values are rendered as %XX where XX is the hex value for the byte. + + +Format of the "--status-fd" output +================================== +Every line is prefixed with "[GNUPG:] ", followed by a keyword with +the type of the status line and a some arguments depending on the +type (maybe none); an application should always be prepared to see +more arguments in future versions. + + + NEWSIG + May be issued right before a signature verification starts. This + is useful to define a context for parsing ERROR status + messages. No arguments are currently defined. + + GOODSIG <long keyid> <username> + The signature with the keyid is good. For each signature only + one of the three codes GOODSIG, BADSIG or ERRSIG will be + emitted and they may be used as a marker for a new signature. + The username is the primary one encoded in UTF-8 and %XX + escaped. + + EXPSIG <long keyid> <username> + The signature with the keyid is good, but the signature is + expired. The username is the primary one encoded in UTF-8 and + %XX escaped. + + EXPKEYSIG <long keyid> <username> + The signature with the keyid is good, but the signature was + made by an expired key. The username is the primary one + encoded in UTF-8 and %XX escaped. + + REVKEYSIG <long keyid> <username> + The signature with the keyid is good, but the signature was + made by a revoked key. The username is the primary one + encoded in UTF-8 and %XX escaped. + + BADSIG <long keyid> <username> + The signature with the keyid has not been verified okay. + The username is the primary one encoded in UTF-8 and %XX + escaped. + + ERRSIG <long keyid> <pubkey_algo> <hash_algo> \ + <sig_class> <timestamp> <rc> + It was not possible to check the signature. This may be + caused by a missing public key or an unsupported algorithm. + A RC of 4 indicates unknown algorithm, a 9 indicates a missing + public key. The other fields give more information about + this signature. sig_class is a 2 byte hex-value. + + Note, that TIMESTAMP may either be a number with seconds since + epoch or an ISO 8601 string which can be detected by the + presence of the letter 'T' inside. + + VALIDSIG <fingerprint in hex> <sig_creation_date> <sig-timestamp> + <expire-timestamp> <sig-version> <reserved> <pubkey-algo> + <hash-algo> <sig-class> <primary-key-fpr> + + The signature with the keyid is good. This is the same as + GOODSIG but has the fingerprint as the argument. Both status + lines are emitted for a good signature. All arguments here + are on one long line. sig-timestamp is the signature creation + time in seconds after the epoch. expire-timestamp is the + signature expiration time in seconds after the epoch (zero + means "does not expire"). sig-version, pubkey-algo, hash-algo, + and sig-class (a 2-byte hex value) are all straight from the + signature packet. PRIMARY-KEY-FPR is the fingerprint of the + primary key or identical to the first argument. This is + useful to get back to the primary key without running gpg + again for this purpose. + + Note, that *-TIMESTAMP may either be a number with seconds + since epoch or an ISO 8601 string which can be detected by the + presence of the letter 'T' inside. + + SIG_ID <radix64_string> <sig_creation_date> <sig-timestamp> + This is emitted only for signatures of class 0 or 1 which + have been verified okay. The string is a signature id + and may be used in applications to detect replay attacks + of signed messages. Note that only DLP algorithms give + unique ids - others may yield duplicated ones when they + have been created in the same second. + + Note, that SIG-TIMESTAMP may either be a number with seconds + since epoch or an ISO 8601 string which can be detected by the + presence of the letter 'T' inside. + + + ENC_TO <long keyid> <keytype> <keylength> + The message is encrypted to this keyid. + keytype is the numerical value of the public key algorithm, + keylength is the length of the key or 0 if it is not known + (which is currently always the case). + + NODATA <what> + No data has been found. Codes for what are: + 1 - No armored data. + 2 - Expected a packet but did not found one. + 3 - Invalid packet found, this may indicate a non OpenPGP + message. + 4 - signature expected but not found + You may see more than one of these status lines. + + UNEXPECTED <what> + Unexpected data has been encountered + 0 - not further specified 1 + + + TRUST_UNDEFINED <error token> + TRUST_NEVER <error token> + TRUST_MARGINAL + TRUST_FULLY + TRUST_ULTIMATE + For good signatures one of these status lines are emitted + to indicate how trustworthy the signature is. The error token + values are currently only emiited by gpgsm. + + PKA_TRUST_GOOD <mailbox> + PKA_TRUST_BAD <mailbox> + Depending on the outcome of the PKA check one of the above + status codes is emitted in addition to a TRUST_* status. + Without PKA info available or + + SIGEXPIRED + This is deprecated in favor of KEYEXPIRED. + + KEYEXPIRED <expire-timestamp> + The key has expired. expire-timestamp is the expiration time + in seconds after the epoch. + + Note, that TIMESTAMP may either be a number with seconds since + epoch or an ISO 8601 string which can be detected by the + presence of the letter 'T' inside. + + KEYREVOKED + The used key has been revoked by its owner. No arguments yet. + + BADARMOR + The ASCII armor is corrupted. No arguments yet. + + RSA_OR_IDEA + The IDEA algorithms has been used in the data. A + program might want to fallback to another program to handle + the data if GnuPG failed. This status message used to be emitted + also for RSA but this has been dropped after the RSA patent expired. + However we can't change the name of the message. + + SHM_INFO + SHM_GET + SHM_GET_BOOL + SHM_GET_HIDDEN + + GET_BOOL + GET_LINE + GET_HIDDEN + GOT_IT + + NEED_PASSPHRASE <long main keyid> <long keyid> <keytype> <keylength> + Issued whenever a passphrase is needed. + keytype is the numerical value of the public key algorithm + or 0 if this is not applicable, keylength is the length + of the key or 0 if it is not known (this is currently always the case). + + NEED_PASSPHRASE_SYM <cipher_algo> <s2k_mode> <s2k_hash> + Issued whenever a passphrase for symmetric encryption is needed. + + NEED_PASSPHRASE_PIN <card_type> <chvno> [<serialno>] + Issued whenever a PIN is requested to unlock a card. + + MISSING_PASSPHRASE + No passphrase was supplied. An application which encounters this + message may want to stop parsing immediately because the next message + will probably be a BAD_PASSPHRASE. However, if the application + is a wrapper around the key edit menu functionality it might not + make sense to stop parsing but simply ignoring the following + BAD_PASSPHRASE. + + BAD_PASSPHRASE <long keyid> + The supplied passphrase was wrong or not given. In the latter case + you may have seen a MISSING_PASSPHRASE. + + GOOD_PASSPHRASE + The supplied passphrase was good and the secret key material + is therefore usable. + + DECRYPTION_FAILED + The symmetric decryption failed - one reason could be a wrong + passphrase for a symmetrical encrypted message. + + DECRYPTION_OKAY + The decryption process succeeded. This means, that either the + correct secret key has been used or the correct passphrase + for a conventional encrypted message was given. The program + itself may return an errorcode because it may not be possible to + verify a signature for some reasons. + + NO_PUBKEY <long keyid> + NO_SECKEY <long keyid> + The key is not available + + IMPORT_CHECK <long keyid> <fingerprint> <user ID> + This status is emitted in interactive mode right before + the "import.okay" prompt. + + IMPORTED <long keyid> <username> + The keyid and name of the signature just imported + + IMPORT_OK <reason> [<fingerprint>] + The key with the primary key's FINGERPRINT has been imported. + Reason flags: + 0 := Not actually changed + 1 := Entirely new key. + 2 := New user IDs + 4 := New signatures + 8 := New subkeys + 16 := Contains private key. + The flags may be ORed. + + IMPORT_PROBLEM <reason> [<fingerprint>] + Issued for each import failure. Reason codes are: + 0 := "No specific reason given". + 1 := "Invalid Certificate". + 2 := "Issuer Certificate missing". + 3 := "Certificate Chain too long". + 4 := "Error storing certificate". + + IMPORT_RES <count> <no_user_id> <imported> <imported_rsa> <unchanged> + <n_uids> <n_subk> <n_sigs> <n_revoc> <sec_read> <sec_imported> <sec_dups> <not_imported> + Final statistics on import process (this is one long line) + + FILE_START <what> <filename> + Start processing a file <filename>. <what> indicates the performed + operation: + 1 - verify + 2 - encrypt + 3 - decrypt + + FILE_DONE + Marks the end of a file processing which has been started + by FILE_START. + + BEGIN_DECRYPTION + END_DECRYPTION + Mark the start and end of the actual decryption process. These + are also emitted when in --list-only mode. + + BEGIN_ENCRYPTION <mdc_method> <sym_algo> + END_ENCRYPTION + Mark the start and end of the actual encryption process. + + BEGIN_SIGNING + Mark the start of the actual signing process. This may be used + as an indication that all requested secret keys are ready for + use. + + DELETE_PROBLEM reason_code + Deleting a key failed. Reason codes are: + 1 - No such key + 2 - Must delete secret key first + 3 - Ambigious specification + + PROGRESS what char cur total + Used by the primegen and Public key functions to indicate progress. + "char" is the character displayed with no --status-fd enabled, with + the linefeed replaced by an 'X'. "cur" is the current amount + done and "total" is amount to be done; a "total" of 0 indicates that + the total amount is not known. 100/100 may be used to detect the + end of operation. + Well known values for WHAT: + "pk_dsa" - DSA key generation + "pk_elg" - Elgamal key generation + "primegen" - Prime generation + "need_entropy" - Waiting for new entropy in the RNG + "file:XXX" - processing file XXX + (note that current gpg versions leave out the + "file:" prefix). + "tick" - generic tick without any special meaning - useful + for letting clients know that the server is + still working. + "starting_agent" - A gpg-agent was started because it is not + running as a daemon. + + + SIG_CREATED <type> <pubkey algo> <hash algo> <class> <timestamp> <key fpr> + A signature has been created using these parameters. + type: 'D' = detached + 'C' = cleartext + 'S' = standard + (only the first character should be checked) + class: 2 hex digits with the signature class + + Note, that TIMESTAMP may either be a number with seconds since + epoch or an ISO 8601 string which can be detected by the + presence of the letter 'T' inside. + + KEY_CREATED <type> <fingerprint> [<handle>] + A key has been created + type: 'B' = primary and subkey + 'P' = primary + 'S' = subkey + The fingerprint is one of the primary key for type B and P and + the one of the subkey for S. Handle is an arbitrary + non-whitespace string used to match key parameters from batch + key creation run. + + KEY_NOT_CREATED [<handle>] + The key from batch run has not been created due to errors. + + + SESSION_KEY <algo>:<hexdigits> + The session key used to decrypt the message. This message will + only be emitted when the special option --show-session-key + is used. The format is suitable to be passed to the option + --override-session-key + + NOTATION_NAME <name> + NOTATION_DATA <string> + name and string are %XX escaped; the data may be splitted + among several notation_data lines. + + USERID_HINT <long main keyid> <string> + Give a hint about the user ID for a certain keyID. + + POLICY_URL <string> + string is %XX escaped + + BEGIN_STREAM + END_STREAM + Issued by pipemode. + + INV_RECP <reason> <requested_recipient> + Issued for each unusable recipient. The reasons codes + currently in use are: + 0 := "No specific reason given". + 1 := "Not Found" + 2 := "Ambigious specification" + 3 := "Wrong key usage" + 4 := "Key revoked" + 5 := "Key expired" + 6 := "No CRL known" + 7 := "CRL too old" + 8 := "Policy mismatch" + 9 := "Not a secret key" + 10 := "Key not trusted" + + Note that this status is also used for gpgsm's SIGNER command + where it relates to signer's of course. + + NO_RECP <reserved> + Issued when no recipients are usable. + + ALREADY_SIGNED <long-keyid> + Warning: This is experimental and might be removed at any time. + + TRUNCATED <maxno> + The output was truncated to MAXNO items. This status code is issued + for certain external requests + + ERROR <error location> <error code> + + This is a generic error status message, it might be followed + by error location specific data. <error token> and + <error_location> should not contain a space. The error code + is a either a string commencing with a letter or such string + prefix with a numerical error code and an underscore; e.g.: + "151011327_EOF" + + ATTRIBUTE <fpr> <octets> <type> <index> <count> + <timestamp> <expiredate> <flags> + This is one long line issued for each attribute subpacket when + an attribute packet is seen during key listing. <fpr> is the + fingerprint of the key. <octets> is the length of the + attribute subpacket. <type> is the attribute type + (1==image). <index>/<count> indicates that this is the Nth + indexed subpacket of count total subpackets in this attribute + packet. <timestamp> and <expiredate> are from the + self-signature on the attribute packet. If the attribute + packet does not have a valid self-signature, then the + timestamp is 0. <flags> are a bitwise OR of: + 0x01 = this attribute packet is a primary uid + 0x02 = this attribute packet is revoked + 0x04 = this attribute packet is expired + + CARDCTRL <what> [<serialno>] + This is used to control smartcard operations. + Defined values for WHAT are: + 1 = Request insertion of a card. Serialnumber may be given + to request a specific card. + 2 = Request removal of a card. + 3 = Card with serialnumber detected + 4 = No card available. + 5 = No card reader available + + + PLAINTEXT <format> <timestamp> <filename> + This indicates the format of the plaintext that is about to be + written. The format is a 1 byte hex code that shows the + format of the plaintext: 62 ('b') is binary data, 74 ('t') is + text data with no character set specified, and 75 ('u') is + text data encoded in the UTF-8 character set. The timestamp + is in seconds since the epoch. If a filename is available it + gets printed as the third argument, percent-escaped as usual. + + PLAINTEXT_LENGTH <length> + This indicates the length of the plaintext that is about to be + written. Note that if the plaintext packet has partial length + encoding it is not possible to know the length ahead of time. + In that case, this status tag does not appear. + + SIG_SUBPACKET <type> <flags> <len> <data> + This indicates that a signature subpacket was seen. The + format is the same as the "spk" record above. + + SC_OP_FAILURE [<code>] + An operation on a smartcard definitely failed. Currently + there is no indication of the actual error code, but + application should be prepared to later accept more arguments. + Defined values for CODE are: + 0 - unspecified error (identically to a missing CODE) + 1 - canceled + 2 - bad PIN + + SC_OP_SUCCESS + A smart card operaion succeeded. This status is only printed + for certain operation and is mostly useful to check whether a + PIN change really worked. + + BACKUP_KEY_CREATED fingerprint fname + A backup key named FNAME has been created for the key with + KEYID. + + +Format of the "--attribute-fd" output +===================================== + +When --attribute-fd is set, during key listings (--list-keys, +--list-secret-keys) GnuPG dumps each attribute packet to the file +descriptor specified. --attribute-fd is intended for use with +--status-fd as part of the required information is carried on the +ATTRIBUTE status tag (see above). + +The contents of the attribute data is specified by 2440bis, but for +convenience, here is the Photo ID format, as it is currently the only +attribute defined: + + Byte 0-1: The length of the image header. Due to a historical + accident (i.e. oops!) back in the NAI PGP days, this is + a little-endian number. Currently 16 (0x10 0x00). + + Byte 2: The image header version. Currently 0x01. + + Byte 3: Encoding format. 0x01 == JPEG. + + Byte 4-15: Reserved, and currently unused. + + All other data after this header is raw image (JPEG) data. + + +Format of the "--list-config" output +==================================== + +--list-config outputs information about the GnuPG configuration for +the benefit of frontends or other programs that call GnuPG. There are +several list-config items, all colon delimited like the rest of the +--with-colons output. The first field is always "cfg" to indicate +configuration information. The second field is one of (with +examples): + +version: the third field contains the version of GnuPG. + + cfg:version:1.3.5 + +pubkey: the third field contains the public key algorithmdcaiphers + this version of GnuPG supports, separated by semicolons. The + algorithm numbers are as specified in RFC-2440. + + cfg:pubkey:1;2;3;16;17 + +cipher: the third field contains the symmetric ciphers this version of + GnuPG supports, separated by semicolons. The cipher numbers + are as specified in RFC-2440. + + cfg:cipher:2;3;4;7;8;9;10 + +digest: the third field contains the digest (hash) algorithms this + version of GnuPG supports, separated by semicolons. The + digest numbers are as specified in RFC-2440. + + cfg:digest:1;2;3;8;9;10 + +compress: the third field contains the compression algorithms this + version of GnuPG supports, separated by semicolons. The + algorithm numbers are as specified in RFC-2440. + + cfg:compress:0;1;2;3 + +group: the third field contains the name of the group, and the fourth + field contains the values that the group expands to, separated + by semicolons. + +For example, a group of: + group mynames = paige 0x12345678 joe patti + +would result in: + cfg:group:mynames:patti;joe;0x12345678;paige + + +Key generation +============== + Key generation shows progress by printing different characters to + stderr: + "." Last 10 Miller-Rabin tests failed + "+" Miller-Rabin test succeeded + "!" Reloading the pool with fresh prime numbers + "^" Checking a new value for the generator + "<" Size of one factor decreased + ">" Size of one factor increased + + The prime number for Elgamal is generated this way: + + 1) Make a prime number q of 160, 200, 240 bits (depending on the keysize) + 2) Select the length of the other prime factors to be at least the size + of q and calculate the number of prime factors needed + 3) Make a pool of prime numbers, each of the length determined in step 2 + 4) Get a new permutation out of the pool or continue with step 3 + if we have tested all permutations. + 5) Calculate a candidate prime p = 2 * q * p[1] * ... * p[n] + 1 + 6) Check that this prime has the correct length (this may change q if + it seems not to be possible to make a prime of the desired length) + 7) Check whether this is a prime using trial divisions and the + Miller-Rabin test. + 8) Continue with step 4 if we did not find a prime in step 7. + 9) Find a generator for that prime. + + This algorithm is based on Lim and Lee's suggestion from the + Crypto '97 proceedings p. 260. + + +Unattended key generation +========================= +This feature allows unattended generation of keys controlled by a +parameter file. To use this feature, you use --gen-key together with +--batch and feed the parameters either from stdin or from a file given +on the commandline. + +The format of this file is as follows: + o Text only, line length is limited to about 1000 chars. + o You must use UTF-8 encoding to specify non-ascii characters. + o Empty lines are ignored. + o Leading and trailing spaces are ignored. + o A hash sign as the first non white space character indicates a comment line. + o Control statements are indicated by a leading percent sign, the + arguments are separated by white space from the keyword. + o Parameters are specified by a keyword, followed by a colon. Arguments + are separated by white space. + o The first parameter must be "Key-Type", control statements + may be placed anywhere. + o Key generation takes place when either the end of the parameter file + is reached, the next "Key-Type" parameter is encountered or at the + control statement "%commit" + o Control statements: + %echo <text> + Print <text>. + %dry-run + Suppress actual key generation (useful for syntax checking). + %commit + Perform the key generation. An implicit commit is done + at the next "Key-Type" parameter. + %pubring <filename> + %secring <filename> + Do not write the key to the default or commandline given + keyring but to <filename>. This must be given before the first + commit to take place, duplicate specification of the same filename + is ignored, the last filename before a commit is used. + The filename is used until a new filename is used (at commit points) + and all keys are written to that file. If a new filename is given, + this file is created (and overwrites an existing one). + Both control statements must be given. + o The order of the parameters does not matter except for "Key-Type" + which must be the first parameter. The parameters are only for the + generated keyblock and parameters from previous key generations are not + used. Some syntactically checks may be performed. + The currently defined parameters are: + Key-Type: <algo-number>|<algo-string> + Starts a new parameter block by giving the type of the + primary key. The algorithm must be capable of signing. + This is a required parameter. + Key-Length: <length-in-bits> + Length of the key in bits. Default is 1024. + Key-Usage: <usage-list> + Space or comma delimited list of key usage, allowed values are + "encrypt", "sign", and "auth". This is used to generate the + key flags. Please make sure that the algorithm is capable of + this usage. Note that OpenPGP requires that all primary keys + are capable of certification, so no matter what usage is given + here, the "cert" flag will be on. If no Key-Usage is + specified, all the allowed usages for that particular + algorithm are used. + Subkey-Type: <algo-number>|<algo-string> + This generates a secondary key. Currently only one subkey + can be handled. + Subkey-Length: <length-in-bits> + Length of the subkey in bits. Default is 1024. + Subkey-Usage: <usage-list> + Similar to Key-Usage. + Passphrase: <string> + If you want to specify a passphrase for the secret key, + enter it here. Default is not to use any passphrase. + Name-Real: <string> + Name-Comment: <string> + Name-Email: <string> + The 3 parts of a key. Remember to use UTF-8 here. + If you don't give any of them, no user ID is created. + Expire-Date: <iso-date>|(<number>[d|w|m|y]) + Set the expiration date for the key (and the subkey). It + may either be entered in ISO date format (2000-08-15) or as + number of days, weeks, month or years. Without a letter days + are assumed. + Preferences: <string> + Set the cipher, hash, and compression preference values for + this key. This expects the same type of string as "setpref" + in the --edit menu. + Revoker: <algo>:<fpr> [sensitive] + Add a designated revoker to the generated key. Algo is the + public key algorithm of the designated revoker (i.e. RSA=1, + DSA=17, etc.) Fpr is the fingerprint of the designated + revoker. The optional "sensitive" flag marks the designated + revoker as sensitive information. Only v4 keys may be + designated revokers. + Handle: <string> + This is an optional parameter only used with the status lines + KEY_CREATED and KEY_NOT_CREATED. STRING may be up to 100 + characters and should not contain spaces. It is useful for + batch key generation to associate a key parameter block with a + status line. + Keyserver: <string> + This is an optional parameter that specifies the preferred + keyserver URL for the key. + + +Here is an example: +$ cat >foo <<EOF + %echo Generating a standard key + Key-Type: DSA + Key-Length: 1024 + Subkey-Type: ELG-E + Subkey-Length: 1024 + Name-Real: Joe Tester + Name-Comment: with stupid passphrase + Name-Email: joe@foo.bar + Expire-Date: 0 + Passphrase: abc + %pubring foo.pub + %secring foo.sec + # Do a commit here, so that we can later print "done" :-) + %commit + %echo done +EOF +$ gpg --batch --gen-key foo + [...] +$ gpg --no-default-keyring --secret-keyring ./foo.sec \ + --keyring ./foo.pub --list-secret-keys +/home/wk/work/gnupg-stable/scratch/foo.sec +------------------------------------------ +sec 1024D/915A878D 2000-03-09 Joe Tester (with stupid passphrase) <joe@foo.bar> +ssb 1024g/8F70E2C0 2000-03-09 + + + +Layout of the TrustDB +===================== +The TrustDB is built from fixed length records, where the first byte +describes the record type. All numeric values are stored in network +byte order. The length of each record is 40 bytes. The first record of +the DB is always of type 1 and this is the only record of this type. + +FIXME: The layout changed, document it here. + + Record type 0: + -------------- + Unused record, can be reused for any purpose. + + Record type 1: + -------------- + Version information for this TrustDB. This is always the first + record of the DB and the only one with type 1. + 1 byte value 1 + 3 bytes 'gpg' magic value + 1 byte Version of the TrustDB (2) + 1 byte marginals needed + 1 byte completes needed + 1 byte max_cert_depth + The three items are used to check whether the cached + validity value from the dir record can be used. + 1 u32 locked flags [not used] + 1 u32 timestamp of trustdb creation + 1 u32 timestamp of last modification which may affect the validity + of keys in the trustdb. This value is checked against the + validity timestamp in the dir records. + 1 u32 timestamp of last validation [currently not used] + (Used to keep track of the time, when this TrustDB was checked + against the pubring) + 1 u32 record number of keyhashtable [currently not used] + 1 u32 first free record + 1 u32 record number of shadow directory hash table [currently not used] + It does not make sense to combine this table with the key table + because the keyid is not in every case a part of the fingerprint. + 1 u32 record number of the trusthashtbale + + + Record type 2: (directory record) + -------------- + Informations about a public key certificate. + These are static values which are never changed without user interaction. + + 1 byte value 2 + 1 byte reserved + 1 u32 LID . (This is simply the record number of this record.) + 1 u32 List of key-records (the first one is the primary key) + 1 u32 List of uid-records + 1 u32 cache record + 1 byte ownertrust + 1 byte dirflag + 1 byte maximum validity of all the user ids + 1 u32 time of last validity check. + 1 u32 Must check when this time has been reached. + (0 = no check required) + + + Record type 3: (key record) + -------------- + Informations about a primary public key. + (This is mainly used to lookup a trust record) + + 1 byte value 3 + 1 byte reserved + 1 u32 LID + 1 u32 next - next key record + 7 bytes reserved + 1 byte keyflags + 1 byte pubkey algorithm + 1 byte length of the fingerprint (in bytes) + 20 bytes fingerprint of the public key + (This is the value we use to identify a key) + + Record type 4: (uid record) + -------------- + Informations about a userid + We do not store the userid but the hash value of the userid because that + is sufficient. + + 1 byte value 4 + 1 byte reserved + 1 u32 LID points to the directory record. + 1 u32 next next userid + 1 u32 pointer to preference record + 1 u32 siglist list of valid signatures + 1 byte uidflags + 1 byte validity of the key calculated over this user id + 20 bytes ripemd160 hash of the username. + + + Record type 5: (pref record) + -------------- + This record type is not anymore used. + + 1 byte value 5 + 1 byte reserved + 1 u32 LID; points to the directory record (and not to the uid record!). + (or 0 for standard preference record) + 1 u32 next + 30 byte preference data + + Record type 6 (sigrec) + ------------- + Used to keep track of key signatures. Self-signatures are not + stored. If a public key is not in the DB, the signature points to + a shadow dir record, which in turn has a list of records which + might be interested in this key (and the signature record here + is one). + + 1 byte value 6 + 1 byte reserved + 1 u32 LID points back to the dir record + 1 u32 next next sigrec of this uid or 0 to indicate the + last sigrec. + 6 times + 1 u32 Local_id of signatures dir or shadow dir record + 1 byte Flag: Bit 0 = checked: Bit 1 is valid (we have a real + directory record for this) + 1 = valid is set (but may be revoked) + + + + Record type 8: (shadow directory record) + -------------- + This record is used to reserve a LID for a public key. We + need this to create the sig records of other keys, even if we + do not yet have the public key of the signature. + This record (the record number to be more precise) will be reused + as the dir record when we import the real public key. + + 1 byte value 8 + 1 byte reserved + 1 u32 LID (This is simply the record number of this record.) + 2 u32 keyid + 1 byte pubkey algorithm + 3 byte reserved + 1 u32 hintlist A list of records which have references to + this key. This is used for fast access to + signature records which are not yet checked. + Note, that this is only a hint and the actual records + may not anymore hold signature records for that key + but that the code cares about this. + 18 byte reserved + + + + Record Type 10 (hash table) + -------------- + Due to the fact that we use fingerprints to lookup keys, we can + implement quick access by some simple hash methods, and avoid + the overhead of gdbm. A property of fingerprints is that they can be + used directly as hash values. (They can be considered as strong + random numbers.) + What we use is a dynamic multilevel architecture, which combines + hashtables, record lists, and linked lists. + + This record is a hashtable of 256 entries; a special property + is that all these records are stored consecutively to make one + big table. The hash value is simple the 1st, 2nd, ... byte of + the fingerprint (depending on the indirection level). + + When used to hash shadow directory records, a different table is used + and indexed by the keyid. + + 1 byte value 10 + 1 byte reserved + n u32 recnum; n depends on the record length: + n = (reclen-2)/4 which yields 9 for the current record length + of 40 bytes. + + the total number of such record which makes up the table is: + m = (256+n-1) / n + which is 29 for a record length of 40. + + To look up a key we use the first byte of the fingerprint to get + the recnum from this hashtable and look up the addressed record: + - If this record is another hashtable, we use 2nd byte + to index this hash table and so on. + - if this record is a hashlist, we walk all entries + until we found one a matching one. + - if this record is a key record, we compare the + fingerprint and to decide whether it is the requested key; + + + Record type 11 (hash list) + -------------- + see hash table for an explanation. + This is also used for other purposes. + + 1 byte value 11 + 1 byte reserved + 1 u32 next next hash list record + n times n = (reclen-5)/5 + 1 u32 recnum + + For the current record length of 40, n is 7 + + + + Record type 254 (free record) + --------------- + All these records form a linked list of unused records. + 1 byte value 254 + 1 byte reserved (0) + 1 u32 next_free + + + +Packet Headers +=============== + +GNUPG uses PGP 2 packet headers and also understands OpenPGP packet header. +There is one enhancement used with the old style packet headers: + + CTB bits 10, the "packet-length length bits", have values listed in + the following table: + + 00 - 1-byte packet-length field + 01 - 2-byte packet-length field + 10 - 4-byte packet-length field + 11 - no packet length supplied, unknown packet length + + As indicated in this table, depending on the packet-length length + bits, the remaining 1, 2, 4, or 0 bytes of the packet structure field + are a "packet-length field". The packet-length field is a whole + number field. The value of the packet-length field is defined to be + the value of the whole number field. + + A value of 11 is currently used in one place: on compressed data. + That is, a compressed data block currently looks like <A3 01 . . .>, + where <A3>, binary 10 1000 11, is an indefinite-length packet. The + proper interpretation is "until the end of the enclosing structure", + although it should never appear outermost (where the enclosing + structure is a file). + ++ This will be changed with another version, where the new meaning of ++ the value 11 (see below) will also take place. ++ ++ A value of 11 for other packets enables a special length encoding, ++ which is used in case, where the length of the following packet can ++ not be determined prior to writing the packet; especially this will ++ be used if large amounts of data are processed in filter mode. ++ ++ It works like this: After the CTB (with a length field of 11) a ++ marker field is used, which gives the length of the following datablock. ++ This is a simple 2 byte field (MSB first) containing the amount of data ++ following this field, not including this length field. After this datablock ++ another length field follows, which gives the size of the next datablock. ++ A value of 0 indicates the end of the packet. The maximum size of a ++ data block is limited to 65534, thereby reserving a value of 0xffff for ++ future extensions. These length markers must be inserted into the data ++ stream just before writing the data out. ++ ++ This 2 byte field is large enough, because the application must buffer ++ this amount of data to prepend the length marker before writing it out. ++ Data block sizes larger than about 32k doesn't make any sense. Note ++ that this may also be used for compressed data streams, but we must use ++ another packet version to tell the application that it can not assume, ++ that this is the last packet. + + +GNU extensions to the S2K algorithm +=================================== +S2K mode 101 is used to identify these extensions. +After the hash algorithm the 3 bytes "GNU" are used to make +clear that these are extensions for GNU, the next bytes gives the +GNU protection mode - 1000. Defined modes are: + 1001 - do not store the secret part at all + 1002 - a stub to access smartcards (not used in 1.2.x) + + +Pipemode +======== +NOTE: This is deprecated and will be removed in future versions. + +This mode can be used to perform multiple operations with one call to +gpg. It comes handy in cases where you have to verify a lot of +signatures. Currently we support only detached signatures. This mode +is a kludge to avoid running gpg n daemon mode and using Unix Domain +Sockets to pass the data to it. There is no easy portable way to do +this under Windows, so we use plain old pipes which do work well under +Windows. Because there is no way to signal multiple EOFs in a pipe we +have to embed control commands in the data stream: We distinguish +between a data state and a control state. Initially the system is in +data state but it won't accept any data. Instead it waits for +transition to control state which is done by sending a single '@' +character. While in control state the control command os expected and +this command is just a single byte after which the system falls back +to data state (but does not necesary accept data now). The simplest +control command is a '@' which just inserts this character into the +data stream. + +Here is the format we use for detached signatures: +"@<" - Begin of new stream +"@B" - Detached signature follows. + This emits a control packet (1,'B') +<detached_signature> +"@t" - Signed text follows. + This emits the control packet (2, 'B') +<signed_text> +"@." - End of operation. The final control packet forces signature + verification +"@>" - End of stream + + + + + + +Other Notes +=========== + * For packet version 3 we calculate the keyids this way: + RSA := low 64 bits of n + ELGAMAL := build a v3 pubkey packet (with CTB 0x99) and calculate + a rmd160 hash value from it. This is used as the + fingerprint and the low 64 bits are the keyid. + + * Revocation certificates consist only of the signature packet; + "import" knows how to handle this. The rationale behind it is + to keep them small. + + + + + + + +Keyserver Message Format +========================= + +The keyserver may be contacted by a Unix Domain socket or via TCP. + +The format of a request is: + +==== +command-tag +"Content-length:" digits +CRLF +======= + +Where command-tag is + +NOOP +GET <user-name> +PUT +DELETE <user-name> + + +The format of a response is: + +====== +"GNUPG/1.0" status-code status-text +"Content-length:" digits +CRLF +============ +followed by <digits> bytes of data + + +Status codes are: + + o 1xx: Informational - Request received, continuing process + + o 2xx: Success - The action was successfully received, understood, + and accepted + + o 4xx: Client Error - The request contains bad syntax or cannot be + fulfilled + + o 5xx: Server Error - The server failed to fulfill an apparently + valid request + + + +Documentation on HKP (the http keyserver protocol): + +A minimalistic HTTP server on port 11371 recognizes a GET for /pks/lookup. +The standard http URL encoded query parameters are this (always key=value): + +- op=index (like pgp -kv), op=vindex (like pgp -kvv) and op=get (like + pgp -kxa) + +- search=<stringlist>. This is a list of words that must occur in the key. + The words are delimited with space, points, @ and so on. The delimiters + are not searched for and the order of the words doesn't matter (but see + next option). + +- exact=on. This switch tells the hkp server to only report exact matching + keys back. In this case the order and the "delimiters" are important. + +- fingerprint=on. Also reports the fingerprints when used with 'index' or + 'vindex' + +The keyserver also recognizes http-POSTs to /pks/add. Use this to upload +keys. + + +A better way to do this would be a request like: + + /pks/lookup/<gnupg_formatierte_user_id>?op=<operation> + +This can be implemented using Hurd's translator mechanism. +However, I think the whole key server stuff has to be re-thought; +I have some ideas and probably create a white paper. + diff --git a/doc/HACKING b/doc/HACKING new file mode 100644 index 000000000..eee9f628b --- /dev/null +++ b/doc/HACKING @@ -0,0 +1,305 @@ + A Hacker's Guide to GNUPG + ================================ + (Some notes on GNUPG internals.) + + + ===> Under construction <======= + + +CVS Access +========== + +NOTE: CVS access has been disabled while we are migrating to Subversion. +Watch www.gnupg.org for instarctions on how to use the Subversion repository. + +Anonymous read-only CVS access is available: + + cvs -z3 -d :pserver:anoncvs@cvs.gnupg.org:/cvs/gnupg login + +use the password "anoncvs". To check out the the complete +archive use: + + cvs -z3 -d :pserver:anoncvs@cvs.gnupg.org:/cvs/gnupg \ + checkout -R STABLE-BRANCH-1-0 gnupg + +This service is provided to help you in hunting bugs and not to deliver +stable snapshots; it may happen that it even does not compile, so please +don't complain. CVS may put a high load on a server, so please don't poll +poll for new updates but wait for an announcement; to receive this you may +want to subscribe to: + + gnupg-commit-watchers@gnupg.org + +by sending a mail with subject "subscribe" to + + gnupg-commit-watchers-request@gnupg.org + + +You must run scripts/autogen.sh before doing the ./configure, +as this creates some needed while which are not in the CVS. +autogen.sh should checks that you have all required tools +installed. + + +RSYNC access +============ +The FTP archive is also available by anonymous rsync. A daily snapshot +of the CVS head revision is also available. See rsync(1) and try +"rsync ftp.gnupg.org::" to see available resources. + + + +Special Tools +============= +Documentation is based on the docbook DTD. Actually we have only the +man page for now. To build a man page you need the docbook-to-man +tool and all the other thinks needed for SGML processing. Debian +comes with the docbook tools and you only need this docbook-to-man +script which is comes with gtk-doc or download it from +ftp.openit.de:/pub/devel/sgml. If you don't have it everything +should still work fine but you will have only a dummy man page. + + +RFCs +==== + +1423 Privacy Enhancement for Internet Electronic Mail: + Part III: Algorithms, Modes, and Identifiers. + +1489 Registration of a Cyrillic Character Set. + +1750 Randomness Recommendations for Security. + +1991 PGP Message Exchange Formats. + +2015 MIME Security with Pretty Good Privacy (PGP). + +2144 The CAST-128 Encryption Algorithm. + +2279 UTF-8, a transformation format of ISO 10646. + +2440 OpenPGP. + + + +Debug Flags +----------- +Use the option "--debug n" to output debug information. This option +can be used multiple times, all values are ORed; n maybe prefixed with +0x to use hex-values. + + value used for + ----- ---------------------------------------------- + 1 packet reading/writing + 2 MPI details + 4 ciphers and primes (may reveal sensitive data) + 8 iobuf filter functions + 16 iobuf stuff + 32 memory allocation stuff + 64 caching + 128 show memory statistics at exit + 256 trust verification stuff + + + + +Directory Layout +---------------- + ./ Readme, configure + ./scripts Scripts needed by configure and others + ./doc Documentation + ./util General purpose utility function + ./mpi Multi precision integer library + ./cipher Cryptographic functions + ./g10 GnuPG application + ./tools Some helper and demo programs + ./keybox The keybox library (under construction) + ./gcrypt Stuff needed to build libgcrypt (under construction) + + +Detailed Roadmap +---------------- +g10/g10.c Main module with option parsing and all the stuff you have + to do on startup. Also has the exout handler and some + helper functions. +g10/sign.c Create signature and optionally encrypt + +g10/parse-packet.c +g10/build-packet.c +g10/free-packet.c + Parsing and creating of OpenPGP message packets. + +g10/getkey.c Key selection code +g10/pkclist.c Build a list of public keys +g10/skclist.c Build a list of secret keys +g10/ringedit.c Keyring I/O +g10/keydb.h + +g10/keyid.c Helper functions to get the keyid, fingerprint etc. + + +g10/trustdb.c +g10/trustdb.h +g10/tdbdump.c + Management of the trustdb.gpg + +g10/compress.c Filter to handle compression +g10/filter.h Declarations for all filter functions +g10/delkey.c Delete a key +g10/kbnode.c Helper for the KBNODE linked list +g10/main.h Prototypes and some constants +g10/mainproc.c Message processing +g10/armor.c Ascii armor filter +g10/mdfilter.c Filter to calculate hashs +g10/textfilter.c Filter to handle CR/LF and trailing white space +g10/cipher.c En-/Decryption filter +g10/misc.c Utlity functions +g10/options.h Structure with all the command line options + and related constants +g10/openfile.c Create/Open Files +g10/tdbio.c I/O handling for the trustdb.gpg +g10/tdbio.h +g10/hkp.h Keyserver access +g10/hkp.c +g10/packet.h Defintion of OpenPGP structures. +g10/passphrase.c Passphrase handling code +g10/pubkey-enc.c +g10/seckey-cert.c +g10/seskey.c +g10/import.c +g10/export.c +g10/comment.c +g10/status.c +g10/status.h +g10/sign.c +g10/plaintext.c +g10/encr-data.c +g10/encode.c +g10/revoke.c +g10/keylist.c +g10/sig-check.c +g10/signal.c +g10/helptext.c +g10/verify.c +g10/decrypt.c +g10/keyedit.c +g10/dearmor.c +g10/keygen.c + + + +Memory allocation +----------------- +Use only the functions: + + m_alloc() + m_alloc_clear() + m_strdup() + m_free() + +If you want to store a passphrase or some other sensitive data you may +want to use m_alloc_secure() instead of m_alloc(), as this puts the data +into a memory region which is protected from swapping (on some platforms). +m_free() works for both. This functions will not return if there is not +enough memory available. + + + +Logging +------- + + + + + + +Option parsing +--------------- +GNUPG does not use getopt or GNU getopt but functions of it's own. See +util/argparse.c for details. The advantage of these functions is that +it is more easy to display and maintain the help texts for the options. +The same option table is also used to parse resource files. + + + +What is an IOBUF +---------------- +This is the data structure used for most I/O of gnupg. It is similar +to System V Streams but much simpler. Because OpenPGP messages are nested +in different ways; the use of such a system has big advantages. Here is +an example, how it works: If the parser sees a packet header with a partial +length, it pushes the block_filter onto the IOBUF to handle these partial +length packets: from now on you don't have to worry about this. When it sees +a compressed packet it pushes the uncompress filter and the next read byte +is one which has already been uncompressed by this filter. Same goes for +enciphered packet, plaintext packets and so on. The file g10/encode.c +might be a good staring point to see how it is used - actually this is +the other way: constructing messages using pushed filters but it may be +easier to understand. + + +How to use the message digest functions +--------------------------------------- +cipher/md.c implements an interface to hash (message digest functions). + +a) If you have a common part of data and some variable parts + and you need to hash of the concatenated parts, you can use this: + md = md_open(...) + md_write( md, common_part ) + md1 = md_copy( md ) + md_write(md1, part1) + md_final(md1); + digest1 = md_read(md1) + md2 = md_copy( md ) + md_write(md2, part2) + md_final(md2); + digest2 = md_read(md2) + + An example are key signatures; the key packet is the common part + and the user-id packets are the variable parts. + +b) If you need a running digest you should use this: + md = md_open(...) + md_write( md, part1 ) + digest_of_part1 = md_digest( md ); + md_write( md, part2 ) + digest_of_part1_cat_part2 = md_digest( md ); + .... + +Both methods may be combined. [Please see the source for the real syntax] + + + + +How to use the cipher functions +------------------------------- +cipher/cipher.c implements the interface to symmetric encryption functions. +As usual you have a function to open a cipher (which returns a handle to be used +with all other functions), some functions to set the key and other stuff and +a encrypt and decrypt function which does the real work. You probably know +how to work with files - so it should really be easy to work with these +functions. Here is an example: + + CIPHER_HANDLE hd; + + hd = cipher_open( CIPHER_ALGO_TWOFISH, CIPHER_MODE_CFB, 0 ); + if( !hd ) + oops( use other function to check for the real error ); + rc = cipher_setkey( hd, key256bit, 32 ) ) + if( rc ) + oops( weak key or something like this ); + cipher_setiv( hd, some_IV_or_NULL_for_all_zeroes ); + cipher_encrypt( hd, plain, cipher, size ); + cipher_close( hd ); + + + +How to use the public key functions +----------------------------------- +cipher/pubkey.c implements the interface to asymmetric encryption and +signature functions. This is basically the same as with the symmetric +counterparts, but due to their nature it is a little bit more complicated. + + [Give an example] + + diff --git a/doc/KEYSERVER b/doc/KEYSERVER new file mode 100644 index 000000000..f63200a6b --- /dev/null +++ b/doc/KEYSERVER @@ -0,0 +1,83 @@ +Format of keyserver colon listings +================================== + +David Shaw <dshaw@jabberwocky.com> + +The machine readable response begins with an optional information +line: + +info:<version>:<count> + +<version> = this is the version of this protocol. Currently, this is + the number 1. + +<count> = the number of keys returned in this response. Note this is + the number of keys, and not the number of lines returned. + It should match the number of "pub:" lines returned. + +If this optional line is not included, or the version information is +not supplied, the version number is assumed to be 1. + +The key listings are made up of several lines per key. The first line +is for the primary key: + +pub:<fingerprint>:<algo>:<keylen>:<creationdate>:<expirationdate>:<flags> + +<fingerprint> = this is either the fingerprint or the keyid of the + key. Either the 16-digit or 8-digit keyids are + acceptable, but obviously the fingerprint is best. + Since it is not possible to calculate the keyid from a + V3 key fingerprint, for V3 keys this should be either + the 16-digit or 8-digit keyid only. + +<algo> = the algorithm number from RFC-2440. (i.e. 1==RSA, 17==DSA, + etc). + +<keylen> = the key length (i.e. 1024, 2048, 4096, etc.) + +<creationdate> = creation date of the key in standard RFC-2440 form + (i.e. number of seconds since 1/1/1970 UTC time) + +<expirationdate> = expiration date of the key in standard RFC-2440 + form (i.e. number of seconds since 1/1/1970 UTC time) + +<flags> = letter codes to indicate details of the key, if any. Flags + may be in any order. + + r == revoked + d == disabled + e == expired + +Following the "pub" line are one or more "uid" lines to indicate user +IDs on the key: + +uid:<escaped uid string>:<creationdate>:<expirationdate>:<flags> + +<escaped uid string> == the user ID string, with HTTP %-escaping for + anything that isn't 7-bit safe as well as for + the ":" character. Any other characters may + be escaped, as desired. + +creationdate, expirationdate, and flags mean the same here as before. +The information is taken from the self-sig, if any, and applies to the +user ID in question, and not to the key as a whole. + +Details: + +* All characters except for the <escaped uid string> are + case-insensitive. + +* Obviously, on a keyserver without integrated crypto, many of the + items given here are not fully trustworthy until the key is + downloaded and signatures checked. For example, the information + that a key is flagged "r" for revoked should be treated as + untrustworthy information until the key is checked on the client + side. + +* Empty fields are allowed. For example, a key with no expiration + date would have the <expirationdate> field empty. Also, a keyserver + that does not track a particular piece of information may leave that + field empty as well. I expect that the creation and expiration + dates for user IDs will be left empty in current keyservers. Colons + for empty fields on the end of each line may be left off, if + desired. diff --git a/doc/Makefile.am b/doc/Makefile.am index 8c1cdd767..73350fdc6 100644 --- a/doc/Makefile.am +++ b/doc/Makefile.am @@ -19,20 +19,22 @@ ## Process this file with automake to produce Makefile.in -EXTRA_DIST = gnupg-badge-openpgp.eps gnupg-badge-openpgp.jpg \ +EXTRA_DIST = DETAILS HACKING TRANSLATE OpenPGP KEYSERVER samplekeys.asc \ + gnupg-badge-openpgp.eps gnupg-badge-openpgp.jpg \ gnupg-badge-openpgp.pdf \ gnupg-card-architecture.eps gnupg-card-architecture.png \ gnupg-card-architecture.pdf \ - opt-homedir.texi see-also-note.texi + faq.raw FAQ faq.html \ + opt-homedir.texi see-also-note.texi BUILT_SOURCES = gnupg-card-architecture.eps gnupg-card-architecture.png \ - gnupg-card-architecture.pdf + gnupg-card-architecture.pdf FAQ faq.html noinst_PROGRAMS = yat2m info_TEXINFOS = gnupg.texi -dist_pkgdata_DATA = qualified.txt +dist_pkgdata_DATA = qualified.txt FAQ faq.html gnupg_TEXINFOS = \ gpg.texi gpgsm.texi gpg-agent.texi scdaemon.texi assuan.texi \ @@ -55,6 +57,9 @@ man_MANS = $(myman_pages) watchgnupg_SOURCE = gnupg.texi + +CLEANFILES = faq.raw.xref + DISTCLEANFILES = gnupg.tmp gnupg.ops yat2m-stamp.tmp yat2m-stamp \ $(myman_pages) @@ -74,6 +79,25 @@ yat2m_SOURCES = yat2m.c fig2dev -L pdf `test -f '$<' || echo '$(srcdir)/'`$< $@ +FAQ : faq.raw +if WORKING_FAQPROG + $(FAQPROG) -f $< $@ || $(FAQPROG) -f $< $@ +else + : Warning: missing faqprog.pl, cannot make $@ + echo "No $@ due to missing faqprog.pl" > $@ + echo "See ftp://ftp.gnupg.org/gcrypt/contrib/faqprog.pl" >> $@ +endif + +faq.html : faq.raw +if WORKING_FAQPROG + $(FAQPROG) -h -f $< $@ 2>&1 || $(FAQPROG) -h -f $< $@ +else + : Warning: missing faqprog.pl, cannot make $@ + echo "No $@ due to missing faqprog.pl" > $@ + echo "See ftp://ftp.gnupg.org/gcrypt/contrib/faqprog.pl" >> $@ +endif + + yat2m-stamp: $(myman_sources) @rm -f yat2m-stamp.tmp @touch yat2m-stamp.tmp diff --git a/doc/OpenPGP b/doc/OpenPGP new file mode 100644 index 000000000..a511ad7fd --- /dev/null +++ b/doc/OpenPGP @@ -0,0 +1,108 @@ + GnuPG and OpenPGP + ================= + + See RFC2440 for a description of OpenPGP. We have an annotated version + of this RFC online: http://www.gnupg.org/rfc2440.html + + + + Compatibility Notes + =================== + GnuPG (>=1.0.3) is in compliance with RFC2440 despite these exceptions: + + * (9.2) states that IDEA SHOULD be implemented. This is not done + due to patent problems. + + + All MAY features are implemented with this exception: + + * multi-part armored messages are not supported. + MIME (rfc2015) should be used instead. + + Most of the OPTIONAL stuff is implemented. + + There are a couple of options which can be used to override some + RFC requirements. This is always mentioned with the description + of that options. + + A special format of partial packet length exists for v3 packets + which can be considered to be in compliance with RFC1991; this + format is only created if a special option is active. + + GnuPG uses a S2K mode of 101 for GNU extensions to the secret key + protection algorithms. This number is not defined in OpenPGP, but + given the fact that this number is in a range which used at many + other places in OpenPGP for private/experimenat algorithm identifiers, + this should be not a so bad choice. The 3 bytes "GNU" are used + to identify this as a GNU extension - see the file DETAILS for a + definition of the used data formats. + + + + Some Notes on OpenPGP / PGP Compatibility: + ========================================== + + * PGP 5.x does not accept V4 signatures for anything other than + key material. The GnuPG option --force-v3-sigs mimics this + behavior. + + * PGP 5.x does not recognize the "five-octet" lengths in + new-format headers or in signature subpacket lengths. + + * PGP 5.0 rejects an encrypted session key if the keylength + differs from the S2K symmetric algorithm. This is a bug in its + validation function. + + * PGP 5.0 does not handle multiple one-pass signature headers and + trailers. Signing one will compress the one-pass signed literal + and prefix a V3 signature instead of doing a nested one-pass + signature. + + * When exporting a private key, PGP 2.x generates the header + "BEGIN PGP SECRET KEY BLOCK" instead of "BEGIN PGP PRIVATE KEY + BLOCK". All previous versions ignore the implied data type, and + look directly at the packet data type. + + * In a clear-signed signature, PGP 5.0 will figure out the correct + hash algorithm if there is no "Hash:" header, but it will reject + a mismatch between the header and the actual algorithm used. The + "standard" (i.e. Zimmermann/Finney/et al.) version of PGP 2.x + rejects the "Hash:" header and assumes MD5. There are a number + of enhanced variants of PGP 2.6.x that have been modified for + SHA-1 signatures. + + * PGP 5.0 can read an RSA key in V4 format, but can only recognize + it with a V3 keyid, and can properly use only a V3 format RSA + key. + + * Neither PGP 5.x nor PGP 6.0 recognize ElGamal Encrypt and Sign + keys. They only handle ElGamal Encrypt-only keys. + + + Parts of this document are taken from: + ====================================== + + OpenPGP Message Format + draft-ietf-openpgp-formats-07.txt + + + Copyright 1998 by The Internet Society. All Rights Reserved. + + This document and translations of it may be copied and furnished to + others, and derivative works that comment on or otherwise explain it + or assist in its implementation may be prepared, copied, published + and distributed, in whole or in part, without restriction of any + kind, provided that the above copyright notice and this paragraph + are included on all such copies and derivative works. However, this + document itself may not be modified in any way, such as by removing + the copyright notice or references to the Internet Society or other + Internet organizations, except as needed for the purpose of + developing Internet standards in which case the procedures for + copyrights defined in the Internet Standards process must be + followed, or as required to translate it into languages other than + English. + + The limited permissions granted above are perpetual and will not be + revoked by the Internet Society or its successors or assigns. + + diff --git a/doc/TRANSLATE b/doc/TRANSLATE new file mode 100644 index 000000000..1a2f266c9 --- /dev/null +++ b/doc/TRANSLATE @@ -0,0 +1,33 @@ +$Id$ + +Note for translators +-------------------- + +Some strings in GnuPG are for matching user input against. These +strings can accept multiple values that mean essentially the same +thing. + +For example, the string "yes" in English is "sÃ" in Spanish. However, +some users will type "si" (without the accent). To accomodate both +users, you can translate the string "yes" as "sÃ|si". You can have +any number of alternate matches seperated by the | character like +"sÃ|si|seguro". + +The strings that can be handled in this way are of the form "yes|yes", +(or "no|no", etc.) There should also be a comment in the .po file +directing you to this file. + + + +Sending new or updated translations +----------------------------------- + +Please note that we do not use the TP Robot but require that +translations are to be send by mail to translations@gnupg.org. We +also strongly advise to get subscribed to i18n@gnupg.org and request +assistance if it is not clear on how to translate certain strings. A +wrongly translated string may lead to a security problem. + +A copyright disclaimer to the FSF is required by all translators. + + diff --git a/doc/faq.raw b/doc/faq.raw new file mode 100644 index 000000000..cbab76b0c --- /dev/null +++ b/doc/faq.raw @@ -0,0 +1,1344 @@ +[$htmltitle=GnuPG FAQ] +[$htmlcharset=<meta http-equiv="content-type" content="text/html; charset=utf-8">] +[$sfaqheader=The GnuPG FAQ says:] +[$sfaqfooter= +The most recent version of the FAQ is available from +<http://www.gnupg.org/> +] +[$usenetheader= +] +[$maintainer=David D. Scribner, <faq 'at' gnupg.org>] +[$hGPGHTTP=http://www.gnupg.org] +[$hGPGFTP=ftp://ftp.gnupg.org] +[$hVERSION=1.2.2] + +[H body bgcolor=#ffffff text=#000000 link=#1f00ff alink=#ff0000 vlink=#9900dd] +[H h1]GnuPG Frequently Asked Questions[H /h1] + + +[H p] +Version: 1.6.3[H br] +Last-Modified: Jul 30, 2003[H br] +Maintained-by: [$maintainer] +[H /p] + + +This is the GnuPG FAQ. The latest HTML version is available +[H a href=[$hGPGHTTP]/documentation/faqs.html]here[H/a]. + +The index is generated automatically, so there may be errors. Not all +questions may be in the section they belong to. Suggestions about how +to improve the structure of this FAQ are welcome. + +Please send additions and corrections to the maintainer. It would be +most convenient if you could provide the answer to be included here +as well. Your help is very much appreciated! + +Please, don't send message like "This should be a FAQ - what's the +answer?". If it hasn't been asked before, it isn't a FAQ. In that case +you could search in the mailing list archive. + +[H hr] +<C> +[H hr] + + +<S> GENERAL + +<Q> What is GnuPG? + + [H a href=[$hGPGHTTP]]GnuPG[H /a] stands for GNU Privacy Guard and + is GNU's tool for secure communication and data storage. It can be + used to encrypt data and to create digital signatures. It includes + an advanced key management facility and is compliant with the + proposed OpenPGP Internet standard as described in [H a href=http://www.rfc-editor.org/]RFC 2440[H/a]. + As such, it is aimed to be compatible with PGP from PGP Corp. and + other OpenPGP tools + +<Q> Is GnuPG compatible with PGP? + + In general, yes. GnuPG and newer PGP releases should be implementing + the OpenPGP standard. But there are some interoperability problems. + See question <Rcompat> for details. + +<Q> Is GnuPG free to use for personal or commercial use? + + Yes. GnuPG is part of the GNU family of tools and applications built + and provided in accordance with the Free Software Foundation (FSF) + General Public License (GPL). Therefore the software is free to copy, + use, modify and distribute in accordance with that license. Please + read the file titled COPYING that accompanies the application for + more information. + +<Q> What conventions are used in this FAQ? + + Although GnuPG is being developed for several operating systems + (often in parallel), the conventions used in this FAQ reflect a + UNIX shell environment. For Win32 users, references to a shell + prompt (`$') should be interpreted as a command prompt (`>'), + directory names separated by a forward slash (`/') may need to be + converted to a back slash (`\'), and a tilde (`~') represents a + user's "home" directory (reference question <Rhomedir> for an example). + + Some command-lines presented in this FAQ are too long to properly + display in some browsers for the web page version of this file, and + have been split into two or more lines. For these commands please + remember to enter the entire command-string on one line or the + command will error, or at minimum not give the desired results. + + Please keep in mind that this FAQ contains information that may not + apply to your particular version, as new features and bug fixes are + added on a continuing basis (reference the NEWS file included with + the source or package for noteworthy changes between versions). One + item to note is that starting with GnuPG version 1.1.92 the file + containing user options and settings has been renamed from "options" + to "gpg.conf". Information in the FAQ that relates to the options + file may be interchangable with the newer gpg.conf file in many + instances. See question <Roptions> for details. + + +<S> SOURCES of INFORMATION + +<Q> Where can I find more information on GnuPG? + + On-line resources: + + [H ul] + [H li]The documentation page is located at [H a href=[$hGPGHTTP]/documentation/]<[$hGPGHTTP]/documentation/>[H/a]. + Also, have a look at the HOWTOs and the GNU Privacy Handbook (GPH, + available in English, Spanish and Russian). The latter provides a + detailed user's guide to GnuPG. You'll also find a document about how + to convert from PGP 2.x to GnuPG. + + [H li]At [H a href=[$hGPGHTTP]/documentation/mailing-lists.html]<[$hGPGHTTP]/documentation/mailing-lists.html>[H/a] you'll find + an online archive of the GnuPG mailing lists. Most interesting should + be gnupg-users for all user-related issues and gnupg-devel if you want + to get in touch with the developers. + + In addition, searchable archives can be found on MARC, e.g.: [H br] + gnupg-users: [H a href=http://marc.theaimsgroup.com/?l=gnupg-users&r=1&w=2]<http://marc.theaimsgroup.com/?l=gnupg-users&r=1&w=2>[H/a][H br] + gnupg-devel: [H a href=http://marc.theaimsgroup.com/?l=gnupg-devel&r=1&w=2]<http://marc.theaimsgroup.com/?l=gnupg-devel&r=1&w=2>[H/a][H br] + + [H b]PLEASE:[H /b] + Before posting to a list, read this FAQ and the available documentation. + In addition, search the list archive - maybe your question has already + been discussed. This way you help people focus on topics that have not + yet been resolved. + + [H li]The GnuPG source distribution contains a subdirectory: + + [H samp] + ./doc + [H /samp] + + where some additional documentation is located (mainly interesting + for hackers, not the casual user). + [H /ul] + +<Q> Where do I get GnuPG? + + You can download the GNU Privacy Guard from its primary FTP server + [H a href=[$hGPGFTP]/gcrypt/]<[$hGPGFTP]/gcrypt/>[H /a] or from one of the mirrors: + + [H a href=[$hGPGHTTP]/download/mirrors.html] + <[$hGPGHTTP]/download/mirrors.html> + [H /a] + + The current stable version is [$hVERSION]. Please upgrade to this version as + it includes additional features, functions and security fixes that may + not have existed in prior versions. + + +<S> INSTALLATION + +<Q> Which OSes does GnuPG run on? + + It should run on most Unices as well as Windows versions (including + Windows NT/2000) and Macintosh OS/X. A list of OSes reported to be OK + is presented at: + + [H a href=[$hGPGHTTP]/download/supported_systems.html] + <[$hGPGHTTP]/download/supported_systems.html> + [H /a] + +<Q> Which random data gatherer should I use? + + "Good" random numbers are crucial for the security of your encryption. + Different operating systems provide a variety of more or less quality + random data. Linux and *BSD provide kernel generated random data + through /dev/random - this should be the preferred choice on these + systems. Also Solaris users with the SUNWski package installed have + a /dev/random. In these cases, use the configure option: + + [H samp] + --enable-static-rnd=linux + [H /samp] + + In addition, there's also the kernel random device by Andi Maier + [H a href= http://www.cosy.sbg.ac.at/~andi/SUNrand/]<http://www.cosy.sbg.ac.at/~andi/SUNrand/>[H /a], but it's still beta. Use at your + own risk! + + On other systems, the Entropy Gathering Daemon (EGD) is a good choice. + It is a perl-daemon that monitors system activity and hashes it into + random data. See the download page [H a href=[$hGPGHTTP]/download/]<[$hGPGHTTP]/download/>[H /a] + to obtain EGD. Use: + + [H samp] + --enable-static-rnd=egd + [H /samp] + + here. + + If the above options do not work, you can use the random number + generator "unix". This is [H B]very[H /B] slow and should be avoided. The + random quality isn't very good so don't use it on sensitive data. + +<Didea> +<Q> How do I include support for RSA and IDEA? + + RSA is included as of GnuPG version 1.0.3. + + The official GnuPG distribution does not contain IDEA due to a patent + restriction. The patent does not expire before 2007 so don't expect + official support before then. + + However, there is an unofficial module to include it even in earlier + versions of GnuPG. It's available from + [H a href=ftp://ftp.gnupg.dk/pub/contrib-dk/]<ftp://ftp.gnupg.dk/pub/contrib-dk/>[H /a]. Look for: + + [H pre] + idea.c.gz (c module) + idea.c.gz.sig (signature file) + [H /pre] + + [H pre] + ideadll.zip (c module and win32 dll) + ideadll.zip.sig (signature file) + [H /pre] + + Compilation directives are in the headers of these files. You will + then need to add the following line to your ~/.gnupg/gpg.conf or + ~/.gnupg/options file: + + [H samp] + load-extension idea + [H /samp] + + +<S> USAGE + +<Q> What is the recommended key size? + + 1024 bit for DSA signatures; even for plain Elgamal signatures. + This is sufficient as the size of the hash is probably the weakest + link if the key size is larger than 1024 bits. Encryption keys may + have greater sizes, but you should then check the fingerprint of + this key: + + [H samp] + $ gpg --fingerprint <user ID> + [H /samp] + + As for the key algorithms, you should stick with the default (i.e., + DSA signature and Elgamal encryption). An Elgamal signing key has + the following disadvantages: the signature is larger, it is hard + to create such a key useful for signatures which can withstand some + real world attacks, you don't get any extra security compared to + DSA, and there might be compatibility problems with certain PGP + versions. It has only been introduced because at the time it was + not clear whether there was a patent on DSA. + +<Q> Why does it sometimes take so long to create keys? + + The problem here is that we need a lot of random bytes and for that + we (on Linux the /dev/random device) must collect some random data. + It is really not easy to fill the Linux internal entropy buffer; I + talked to Ted Ts'o and he commented that the best way to fill the + buffer is to play with your keyboard. Good security has its price. + What I do is to hit several times on the shift, control, alternate, + and caps lock keys, because these keys do not produce output to the + screen. This way you get your keys really fast (it's the same thing + PGP2 does). + + Another problem might be another program which eats up your random + bytes (a program (look at your daemons) that reads from /dev/random). + +<Q> And it really takes long when I work on a remote system. Why? + + Don't do this at all! You should never create keys or even use GnuPG + on a remote system because you normally have no physical control + over your secret key ring (which is in most cases vulnerable to + advanced dictionary attacks) - I strongly encourage everyone to only + create keys on a local computer (a disconnected laptop is probably + the best choice) and if you need it on your connected box (I know, + we all do this) be sure to have a strong password for both your + account and for your secret key, and that you can trust your system + administrator. + + When I check GnuPG on a remote system via ssh (I have no Alpha here) + ;-) I have the same problem. It takes a *very* long time to create + the keys, so I use a special option, --quick-random, to generate + insecure keys which are only good for some tests. + +<Q> What is the difference between options and commands? + + If you do a 'gpg --help', you will get two separate lists. The first + is a list of commands. The second is a list of options. Whenever you + run GPG, you [H b]must[H /b] pick exactly one command (with one exception, + see below). You [H b]may[H /b] pick one or more options. The command should, + just by convention, come at the end of the argument list, after all + the options. If the command takes a file (all the basic ones do), + the filename comes at the very end. So the basic way to run gpg is: + + [H samp] + $ gpg [--option something] [--option2] [--option3 something] --command file + [H /samp] + + Some options take arguments. For example, the --output option (which + can be abbreviated as -o) is an option that takes a filename. The + option's argument must follow immediately after the option itself, + otherwise gpg doesn't know which option the argument is supposed to + paired with. As an option, --output and its filename must come before + the command. The --recipient (-r) option takes a name or keyID to + encrypt the message to, which must come right after the -r option. + The --encrypt (or -e) command comes after all the options and is + followed by the file you wish to encrypt. Therefore in this example + the command-line issued would be: + + [H samp] + $ gpg -r alice -o secret.txt -e test.txt + [H /samp] + + If you write the options out in full, it is easier to read: + + [H samp] + $ gpg --recipient alice --output secret.txt --encrypt test.txt + [H /samp] + + If you're encrypting to a file with the extension ".txt", then you'd + probably expect to see ASCII-armored text in the file (not binary), + so you need to add the --armor (-a) option, which doesn't take any + arguments: + + [H samp] + $ gpg --armor --recipient alice --output secret.txt --encrypt test.txt + [H /samp] + + If you imagine square brackets around the optional parts, it becomes + a bit clearer: + + [H samp] + $ gpg [--armor] [--recipient alice] [--output secret.txt] --encrypt test.txt + [H /samp] + + The optional parts can be rearranged any way you want: + + [H samp] + $ gpg --output secret.txt --recipient alice --armor --encrypt test.txt + [H /samp] + + If your filename begins with a hyphen (e.g. "-a.txt"), GnuPG assumes + this is an option and may complain. To avoid this you have to either + use "./-a.txt", or stop the option and command processing with two + hyphens: "-- -a.txt". + + [H B]The exception to using only one command:[H /B] signing and encrypting + at the same time. For this you can combine both commands, such as in: + + [H samp] + $ gpg [--options] --sign --encrypt foo.txt + [H /samp] + +<Q> I can't delete a user ID on my secret keyring because it has + already been deleted on my public keyring. What can I do? + + Because you can only select from the public key ring, there is no + direct way to do this. However it is not very complicated to do + anyway. Create a new user ID with exactly the same name and you + will see that there are now two identical user IDs on the secret + ring. Now select this user ID and delete it. Both user IDs will be + removed from the secret ring. + +<Q> I can't delete my secret key because the public key disappeared. + What can I do? + + To select a key a search is always done on the public keyring, + therefore it is not possible to select a secret key without + having the public key. Normally it should never happen that the + public key got lost but the secret key is still available. The + reality is different, so GnuPG implements a special way to deal + with it: Simply use the long keyID to specify the key to delete, + which can be obtained by using the --with-colons options (it is + the fifth field in the lines beginning with "sec"). + + If you've lost your public key and need to recreate it instead + for continued use with your secret key, you may be able to use + gpgsplit as detailed in question <Rgpgsplit>. + +<Q> What are trust, validity and ownertrust? + + With GnuPG, the term "ownertrust" is used instead of "trust" to + help clarify that this is the value you have assigned to a key + to express how much you trust the owner of this key to correctly + sign (and thereby introduce) other keys. The "validity", or + calculated trust, is a value which indicates how much GnuPG + considers a key as being valid (that it really belongs to the + one who claims to be the owner of the key). For more information + on trust values see the chapter "The Web of Trust" in The GNU + Privacy Handbook. + +<Q> How do I sign a patch file? + + Use "gpg --clearsign --not-dash-escaped ...". The problem with + --clearsign is that all lines starting with a dash are quoted with + "- "; obviously diff produces many lines starting with a dash and + these are then quoted and that is not good for a patch ;-). To use + a patch file without removing the cleartext signature, the special + option --not-dash-escaped may be used to suppress generation of + these escape sequences. You should not mail such a patch because + spaces and line endings are also subject to the signature and a + mailer may not preserve these. If you want to mail a file you can + simply sign it using your MUA (Mail User Agent). + +<Q> Where is the "encrypt-to-self" option? + + Use "--encrypt-to your_keyID". You can use more than one of these + options. To temporarily override the use of this additional key, + you can use the option "--no-encrypt-to". + +<Q> How can I get rid of the Version and Comment headers in armored + messages? + + Use "--no-version --comment ''". Note that the left over blank line + is required by the protocol. + +<Q> What does the "You are using the xxxx character set." mean? + + This note is printed when UTF-8 mapping has to be done. Make sure + that the displayed character set is the one you have activated on + your system. Since "iso-8859-1" is the character set most used, + this is the default. You can change the charset with the option + "--charset". It is important that your active character set matches + the one displayed - if not, restrict yourself to plain 7 bit ASCII + and no mapping has to be done. + +<Q> How can I get list of key IDs used to encrypt a message? + + [H samp] + $ gpg --batch --decrypt --list-only --status-fd 1 2>/dev/null | + awk '/^\[GNUPG:\] ENC_TO / { print $3 }' + [H /samp] + +<Q> Why can't I decrypt files encrypted as symmetrical-only (-c) with + a version of GnuPG prior to 1.0.1. + + There was a bug in GnuPG versions prior to 1.0.1 which affected files + only if 3DES or Twofish was used for symmetric-only encryption (this has + never been the default). The bug has been fixed, but to enable decryption + of old files you should run gpg with the option "--emulate-3des-s2k-bug", + decrypt the file and encrypt it again without this option. + + NOTE: This option was removed in GnuPG development version 1.1.0 and later + updates, so you will need to use a version between 1.0.1 and 1.0.7 to + re-encrypt any affected files. + +<Q> How can I use GnuPG in an automated environment? + + You should use the option --batch and don't use passphrases as + there is usually no way to store it more securely than on the + secret keyring itself. The suggested way to create keys for an + automated environment is: + + On a secure machine: + [H ol] + [H li] If you want to do automatic signing, create a signing subkey + for your key (use the interactive key editing menu by issueing + the command 'gpg --edit-key keyID', enter "addkey" and select + the DSA key type). + [H li] Make sure that you use a passphrase (needed by the current + implementation). + [H li] gpg --export-secret-subkeys --no-comment foo >secring.auto + [H li] Copy secring.auto and the public keyring to a test directory. + [H li] Change to this directory. + [H li] gpg --homedir . --edit foo and use "passwd" to remove the + passphrase from the subkeys. You may also want to remove all + unused subkeys. + [H li] Copy secring.auto to a floppy and carry it to the target box. + [H /ol] + + On the target machine: + [H ol] + [H li] Install secring.auto as the secret keyring. + [H li] Now you can start your new service. It's also a good idea to + install an intrusion detection system so that you hopefully + get a notice of an successful intrusion, so that you in turn + can revoke all the subkeys installed on that machine and + install new subkeys. + [H /ol] + +<Q> Which email-client can I use with GnuPG? + + Using GnuPG to encrypt email is one of the most popular uses. + Several mail clients or mail user agents (MUAs) support GnuPG to + varying degrees. Simplifying a bit, there are two ways mail can be + encrypted with GnuPG: the "old style" ASCII armor (i.e. cleartext + encryption), and RFC 2015 style (previously PGP/MIME, now OpenPGP). + The latter has full MIME support. Some MUAs support only one of + them, so whichever you actually use depends on your needs as well + as the capabilities of your addressee. As well, support may be + native to the MUA, or provided via "plug-ins" or external tools. + + The following list is not exhaustive: + + [H pre] + MUA OpenPGP ASCII How? (N,P,T) + ------------------------------------------------------------- + Calypso N Y P (Unixmail) + Elm N Y T (mailpgp,morepgp) + Elm ME+ N Y N + Emacs/Gnus Y Y T (Mailcrypt,gpg.el) + Emacs/Mew Y Y N + Emacs/VM N Y T (Mailcrypt) + Evolution Y Y N + Exmh Y Y N + GNUMail.app Y Y P (PGPBundle) + GPGMail Y Y N + KMail (<=1.4.x) N Y N + KMail (1.5.x) Y(P) Y(N) P/N + Mozilla Y Y P (Enigmail) + Mulberry Y Y P + Mutt Y Y N + Sylpheed Y Y N + Sylpheed-claws Y Y N + TkRat Y Y N + XEmacs/Gnus Y Y T (Mailcrypt) + XEmacs/Mew Y Y N + XEmacs/VM N Y T (Mailcrypt) + XFmail Y Y N + + N - Native, P - Plug-in, T - External Tool + [H /pre] + + The following table lists proprietary MUAs. The GNU Project + suggests against the use of these programs, but they are listed + for interoperability reasons for your convenience. + + [H pre] + MUA OpenPGP ASCII How? (N,P,T) + ------------------------------------------------------------- + Apple Mail Y Y P (GPGMail) + Becky2 Y Y P (BkGnuPG) + Eudora Y Y P (EuroraGPG) + Eudora Pro Y Y P (EudoraGPG) + Lotus Notes N Y P + Netscape 4.x N Y P + Netscape 7.x Y Y P (Enigmail) + Novell Groupwise N Y P + Outlook N Y P (G-Data) + Outlook Express N Y P (GPGOE) + Pegasus N Y P (QDPGP,PM-PGP) + Pine N Y T (pgpenvelope,(gpg|pgp)4pine) + Postme N Y P (GPGPPL) + The Bat! N Y P (Ritlabs) + [H /pre] + + Good overviews of OpenPGP-support can be found at:[H br] + [H a href=http://www.openpgp.fr.st/courrier_en.html]<http://www.openpgp.fr.st/courrier_en.html>[H /a] and[H br] + [H a href=http://www.bretschneidernet.de/tips/secmua.html]<http://www.bretschneidernet.de/tips/secmua.html>[H /a]. + + Users of Win32 MUAs that lack OpenPGP support may look into + using GPGrelay [H a href=http://gpgrelay.sourceforge.net]<http://gpgrelay.sourceforge.net>[H /a], a small + email-relaying server that uses GnuPG to enable many email clients + to send and receive emails that conform to PGP-MIME (RFC 2015). + +<Q> Can't we have a gpg library? + + This has been frequently requested. However, the current viewpoint + of the GnuPG maintainers is that this would lead to several security + issues and will therefore not be implemented in the foreseeable + future. However, for some areas of application gpgme could do the + trick. You'll find it at [H a href=[$hGPGFTP]/gcrypt/alpha/gpgme]<[$hGPGFTP]/gcrypt/alpha/gpgme>[H /a]. + +<Q> I have successfully generated a revocation certificate, but I don't + understand how to send it to the key servers. + + Most keyservers don't accept a 'bare' revocation certificate. You + have to import the certificate into gpg first: + + [H samp] + $ gpg --import my-revocation.asc + [H /samp] + + then send the revoked key to the keyservers: + + [H samp] + $ gpg --keyserver certserver.pgp.com --send-keys mykeyid + [H /samp] + + (or use a keyserver web interface for this). + +<Dhomedir> +<Q> How do I put my keyring in a different directory? + + GnuPG keeps several files in a special homedir directory. These + include the options file, pubring.gpg, secring.gpg, trustdb.gpg, + and others. GnuPG will always create and use these files. On unices, + the homedir is usually ~/.gnupg; on Windows "C:\gnupg\". + + If you want to put your keyrings somewhere else, use the option: + + [H samp] + --homedir /my/path/ + [H /samp] + + to make GnuPG create all its files in that directory. Your keyring + will be "/my/path/pubring.gpg". This way you can store your secrets + on a floppy disk. Don't use "--keyring" as its purpose is to specify + additional keyring files. + +<Q> How do I verify signed packages? + + Before you can verify the signature that accompanies a package, + you must first have the vendor, organisation, or issueing person's + key imported into your public keyring. To prevent GnuPG warning + messages the key should also be validated (or locally signed). + + You will also need to download the detached signature file along + with the package. These files will usually have the same name as + the package, with either a binary (.sig) or ASCII armor (.asc) + extension. + + Once their key has been imported, and the package and accompanying + signature files have been downloaded, use: + + [H samp] + $ gpg --verify sigfile signed-file + [H /samp] + + If the signature file has the same base name as the package file, + the package can also be verified by specifying just the signature + file, as GnuPG will derive the package's file name from the name + given (less the .sig or .asc extension). For example, to verify a + package named foobar.tar.gz against its detached binary signature + file, use: + + [H samp] + $ gpg --verify foobar.tar.gz.sig + [H /samp] + +<Q> How do I export a keyring with only selected signatures (keys)? + + If you're wanting to create a keyring with only a subset of keys + selected from a master keyring (for a club, user group, or company + department for example), simply specify the keys you want to export: + + [H samp] + $ gpg --armor --export key1 key2 key3 key4 > keys1-4.asc + [H /samp] + +<Dgpgsplit> +<Q> I still have my secret key, but lost my public key. What can I do? + + All OpenPGP secret keys have a copy of the public key inside them, + and in a worst-case scenario, you can create yourself a new public + key using the secret key. + + A tool to convert a secret key into a public one has been included + (it's actually a new option for gpgsplit) and is available with GnuPG + versions 1.2.1 or later (or can be found in CVS). It works like this: + + [H samp] + $ gpgsplit --no-split --secret-to-public secret.gpg >publickey.gpg + [H /samp] + + One should first try to export the secret key and convert just this + one. Using the entire secret keyring should work too. After this has + been done, the publickey.gpg file can be imported into GnuPG as usual. + +<Q> Clearsigned messages sent from my web-mail account have an invalid + signature. Why? + + Check to make sure the settings for your web-based email account + do not use HTML formatting for the pasted clearsigned message. This can + alter the message with embedded HTML markup tags or spaces, resulting + in an invalid signature. The recipient may be able to copy the signed + message block to a text file for verification, or the web email + service may allow you to attach the clearsigned message as a file + if plaintext messages are not an option. + + +<S> COMPATIBILITY ISSUES + +<Dcompat> +<Q> How can I encrypt a message with GnuPG so that PGP is able to decrypt it? + + It depends on the PGP version. + + [H ul] + [H li]PGP 2.x[H br] + You can't do that because PGP 2.x normally uses IDEA which is not + supported by GnuPG as it is patented (see <Ridea>), but if you have a + modified version of PGP you can try this: + + [H samp] + $ gpg --rfc1991 --cipher-algo 3des ... + [H /samp] + + Please don't pipe the data to encrypt to gpg but provide it using a + filename; otherwise, PGP 2 will not be able to handle it. + + As for conventional encryption, you can't do this for PGP 2. + + [H li]PGP 5.x and higher[H br] + You need to provide two additional options: + + [H samp] + --compress-algo 1 --cipher-algo cast5 + [H /samp] + + You may also use "3des" instead of "cast5", and "blowfish" does not + work with all versions of PGP 5. You may also want to put: + + [H samp] + compress-algo 1 + [H /samp] + + into your ~/.gnupg/options file - this does not affect normal GnuPG + operation. + + This applies to conventional encryption as well. + [H /UL] + +<Q> How do I migrate from PGP 2.x to GnuPG? + + PGP 2 uses the RSA and IDEA encryption algorithms. Whereas the RSA + patent has expired and RSA is included as of GnuPG 1.0.3, the IDEA + algorithm is still patented until 2007. Under certain conditions you + may use IDEA even today. In that case, you may refer to Question + <Ridea> about how to add IDEA support to GnuPG and read + [H a href=[$hGPGHTTP]/gph/en/pgp2x.html]<[$hGPGHTTP]/gph/en/pgp2x.html>[H /a] to perform the migration. + +<Q> (removed) + + (empty) + +<Q> Why is PGP 5.x not able to encrypt messages with some keys? + + PGP, Inc. refuses to accept Elgamal keys of type 20 even for + encryption. They only support type 16 (which is identical at least + for decryption). To be more inter-operable, GnuPG (starting with + version 0.3.3) now also uses type 16 for the Elgamal subkey which is + created if the default key algorithm is chosen. You may add a type + 16 Elgamal key to your public key, which is easy as your key + signatures are still valid. + +<Q> Why is PGP 5.x not able to verify my messages? + + PGP 5.x does not accept v4 signatures for data material but OpenPGP + requests generation of v4 signatures for all kind of data, that's why + GnuPG defaults to them. Use the option "--force-v3-sigs" to generate + v3 signatures for data. + +<Q> How do I transfer owner trust values from PGP to GnuPG? + + There is a script in the tools directory to help you. After you have + imported the PGP keyring you can give this command: + + [H samp] + $ lspgpot pgpkeyring | gpg --import-ownertrust + [H /samp] + + where pgpkeyring is the original keyring and not the GnuPG keyring + you might have created in the first step. + +<Q> PGP does not like my secret key. + + Older PGPs probably bail out on some private comment packets used by + GnuPG. These packets are fully in compliance with OpenPGP; however + PGP is not really OpenPGP aware. A workaround is to export the + secret keys with this command: + + [H samp] + $ gpg --export-secret-keys --no-comment -a your-KeyID + [H /samp] + + Another possibility is this: by default, GnuPG encrypts your secret + key using the Blowfish symmetric algorithm. Older PGPs will only + understand 3DES, CAST5, or IDEA symmetric algorithms. Using the + following method you can re-encrypt your secret gpg key with a + different algo: + + [H samp] + $ gpg --s2k-cipher-algo=CAST5 --s2k-digest-algo=SHA1 + --compress-algo=1 --edit-key <username> + [H /samp] + + Then use passwd to change the password (just change it to the same + thing, but it will encrypt the key with CAST5 this time). + + Now you can export it and PGP should be able to handle it. + + For PGP 6.x the following options work to export a key: + + [H samp] + $ gpg --s2k-cipher-algo 3des --compress-algo 1 --rfc1991 + --export-secret-keys <KeyID> + [H /samp] + +<Doptions> +<Q> GnuPG no longer installs a ~/.gnupg/options file. Is it missing? + + No. The ~/.gnupg/options file has been renamed to ~/.gnupg/gpg.conf for + new installs as of version 1.1.92. If an existing ~/.gnupg/options file + is found during an upgrade it will still be used, but this change was + required to have a more consistent naming scheme with forthcoming tools. + An existing options file can be renamed to gpg.conf for users upgrading, + or receiving the message that the "old default options file" is ignored + (occurs if both a gpg.conf and an options file are found). + +<Q> How do you export GnuPG keys for use with PGP? + + This has come up fairly often, so here's the HOWTO: + + PGP can (for most key types) use secret keys generated by GnuPG. The + problems that come up occasionally are generally because GnuPG + supports a few more features from the OpenPGP standard than PGP does. + If your secret key has any of those features in use, then PGP will + reject the key or you will have problems communicating later. Note + that PGP doesn't do Elgamal signing keys at all, so they are not + usable with any version. + + These instructions should work for GnuPG 1.0.7 and later, and PGP + 7.0.3 and later. + + Start by editing the key. Most of this line is not really necessary + as the default values are correct, but it does not hurt to repeat the + values, as this will override them in case you have something else set + in your options file. + + [H samp] + $ gpg --s2k-cipher-algo cast5 --s2k-digest-algo sha1 --s2k-mode 3 + --simple-sk-checksum --edit KeyID + [H /samp] + + Turn off some features. Set the list of preferred ciphers, hashes, + and compression algorithms to things that PGP can handle. (Yes, I + know this is an odd list of ciphers, but this is what PGP itself uses, + minus IDEA). + + [H samp] + > setpref S9 S8 S7 S3 S2 S10 H2 H3 Z1 Z0 + [H /samp] + + Now put the list of preferences onto the key. + + [H samp] + > updpref + [H /samp] + + Finally we must decrypt and re-encrypt the key, making sure that we + encrypt with a cipher that PGP likes. We set this up in the --edit + line above, so now we just need to change the passphrase to make it + take effect. You can use the same passphrase if you like, or take + this opportunity to actually change it. + + [H samp] + > passwd + [H /samp] + + Save our work. + + [H samp] + > save + [H /samp] + + Now we can do the usual export: + + [H samp] + $ gpg --export KeyID > mypublickey.pgp[H br] + $ gpg --export-secret-key KeyID > mysecretkey.pgp + [H /samp] + + Thanks to David Shaw for this information! + + +<S> PROBLEMS and ERROR MESSAGES + +<Q> Why do I get "gpg: Warning: using insecure memory!" + + On many systems this program should be installed as setuid(root). + This is necessary to lock memory pages. Locking memory pages prevents + the operating system from writing them to disk and thereby keeping your + secret keys really secret. If you get no warning message about insecure + memory your operating system supports locking without being root. The + program drops root privileges as soon as locked memory is allocated. + + To setuid(root) permissions on the gpg binary you can either use: + + [H samp] + $ chmod u+s /path/to/gpg + [H /samp] + + or + + [H samp] + $ chmod 4755 /path/to/gpg + [H /samp] + + Some refrain from using setuid(root) unless absolutely required for + security reasons. Please check with your system administrator if you + are not able to make these determinations yourself. + + On UnixWare 2.x and 7.x you should install GnuPG with the 'plock' + privilege to get the same effect: + + [H samp] + $ filepriv -f plock /path/to/gpg + [H /samp] + + If you can't or don't want to install GnuPG setuid(root), you can + use the option "--no-secmem-warning" or put: + + [H samp] + no-secmem-warning + [H /samp] + + in your ~/.gnupg/options or ~/.gnupg/gpg.conf file (this disables + the warning). + + On some systems (e.g., Windows) GnuPG does not lock memory pages + and older GnuPG versions (<=1.0.4) issue the warning: + + [H samp] + gpg: Please note that you don't have secure memory + [H /samp] + + This warning can't be switched off by the above option because it + was thought to be too serious an issue. However, it confused users + too much, so the warning was eventually removed. + +<Q> Large File Support doesn't work ... + + LFS works correctly in post-1.0.4 versions. If configure doesn't + detect it, try a different (i.e., better) compiler. egcs 1.1.2 works + fine, other gccs sometimes don't. BTW, several compilation problems + of GnuPG 1.0.3 and 1.0.4 on HP-UX and Solaris were due to broken LFS + support. + +<Q> In the edit menu the trust values are not displayed correctly after + signing uids. Why? + + This happens because some information is stored immediately in + the trustdb, but the actual trust calculation can be done after the + save command. This is a "not easy to fix" design bug which will be + addressed in some future release. + +<Q> What does "skipping pubkey 1: already loaded" mean? + + As of GnuPG 1.0.3, the RSA algorithm is included. If you still have + a "load-extension rsa" in your options file, the above message + occurs. Just remove the load command from the options file. + +<Q> GnuPG 1.0.4 doesn't create ~/.gnupg ... + + That's a known bug, already fixed in newer versions. + +<Q> An Elgamal signature does not verify anymore since version 1.0.2 ... + + Use the option --emulate-md-encode-bug. + +<Q> Old versions of GnuPG can't verify Elgamal signatures + + Update to GnuPG 1.0.2 or newer. + +<Q> When I use --clearsign, the plain text has sometimes extra dashes + in it - why? + + This is called dash-escaped text and is required by OpenPGP. + It always happens when a line starts with a dash ("-") and is + needed to make the lines that structure signature and text + (i.e., "-----BEGIN PGP SIGNATURE-----") to be the only lines + that start with two dashes. + + If you use GnuPG to process those messages, the extra dashes + are removed. Good mail clients remove those extra dashes when + displaying such a message. + +<Q> What is the thing with "can't handle multiple signatures"? + + Due to different message formats GnuPG is not always able to split + a file with multiple signatures unambiguously into its parts. This + error message informs you that there is something wrong with the input. + + The only way to have multiple signatures in a file is by using the + OpenPGP format with one-pass-signature packets (which is GnuPG's + default) or the cleartext signed format. + +<Q> If I submit a key to a keyserver, nothing happens ... + + You are most likely using GnuPG 1.0.2 or older on Windows. That's + feature isn't yet implemented, but it's a bug not to say it. Newer + versions issue a warning. Upgrade to 1.0.4 or newer. + +<Q> I get "gpg: waiting for lock ..." + + A previous instance of gpg has most likely exited abnormally and left + a lock file. Go to ~/.gnupg and look for .*.lock files and remove them. + +<Q> Older gpg binaries (e.g., 1.0) have problems with keys from newer + gpg binaries ... + + As of 1.0.3, keys generated with gpg are created with preferences to + TWOFISH (and AES since 1.0.4) and that also means that they have the + capability to use the new MDC encryption method. This will go into + OpenPGP soon, and is also suppoted by PGP 7. This new method avoids + a (not so new) attack on all email encryption systems. + + This in turn means that pre-1.0.3 gpg binaries have problems with + newer keys. Because of security and bug fixes, you should keep your + GnuPG installation in a recent state anyway. As a workaround, you can + force gpg to use a previous default cipher algo by putting: + + [H samp] + cipher-algo cast5 + [H /samp] + + into your options file. + +<Q> With 1.0.4, I get "this cipher algorithm is deprecated ..." + + If you just generated a new key and get this message while + encrypting, you've witnessed a bug in 1.0.4. It uses the new AES + cipher Rijndael that is incorrectly being referred as "deprecated". + Ignore this warning, more recent versions of gpg are corrected. + +<Q> Some dates are displayed as ????-??-??. Why? + + Due to constraints in most libc implementations, dates beyond + 2038-01-19 can't be displayed correctly. 64-bit OSes are not + affected by this problem. To avoid printing wrong dates, GnuPG + instead prints some question marks. To see the correct value, you + can use the options --with-colons and --fixed-list-mode. + +<Q> I still have a problem. How do I report a bug? + + Are you sure that it's not been mentioned somewhere on the mailing + lists? Did you have a look at the bug list (you'll find a link to + the list of reported bugs on the documentation page). If you're not + sure about it being a bug, you can send mail to the gnupg-devel + list. Otherwise, use the GUUG bug tracking system + [H a href=http://bugs.guug.de/Reporting.html]<http://bugs.guug.de/Reporting.html>[H /a]. + +<Q> Why doesn't GnuPG support X.509 certificates? + + GnuPG, first and foremost, is an implementation of the OpenPGP + standard (RFC 2440), which is a competing infrastructure, different + from X.509. + + They are both public-key cryptosystems, but how the public keys are + actually handled is different. + +<Q> Why do national characters in my user ID look funny? + + According to OpenPGP, GnuPG encodes user ID strings (and other + things) using UTF-8. In this encoding of Unicode, most national + characters get encoded as two- or three-byte sequences. For + example, å (0xE5 in ISO-8859-1) becomes Ã¥ (0xC3, + 0xA5). This might also be the reason why keyservers can't find + your key. + +<Q> I get 'sed' errors when running ./configure on Mac OS X ... + + This will be fixed after GnuPG has been upgraded to autoconf-2.50. + Until then, find the line setting CDPATH in the configure script + and place an: + + [H samp] + unset CDPATH + [H /samp] + + statement below it. + +<Q> Why does GnuPG 1.0.6 bail out on keyrings used with 1.0.7? + + There is a small bug in 1.0.6 which didn't parse trust packets + correctly. You may want to apply this patch if you can't upgrade: + + [H a href=http://www.gnupg.org/developer/gpg-woody-fix.txt]<http://www.gnupg.org/developer/gpg-woody-fix.txt>[H /a] + +<Q> I upgraded to GnuPG version 1.0.7 and now it takes longer to load my + keyrings. What can I do? + + The way signature states are stored has changed so that v3 signatures + can be supported. You can use the new --rebuild-keydb-caches migration + command, which was built into this release and increases the speed of + many operations for existing keyrings. + +<Q> Doesn't a fully trusted user ID on a key prevent warning messages + when encrypting to other IDs on the key? + + No. That was actually a key validity bug in GnuPG 1.2.1 and earlier + versions. As part of the development of GnuPG 1.2.2, a bug was + discovered in the key validation code. This bug causes keys with + more than one user ID to give all user IDs on the key the amount of + validity given to the most-valid key. The bug has been fixed in GnuPG + release 1.2.2, and upgrading is the recommended fix for this problem. + More information and a patch for a some pre-1.2.2 versions of GnuPG + can be found at: + + [H a href=http://lists.gnupg.org/pipermail/gnupg-announce/2003q2/000268.html]<http://lists.gnupg.org/pipermail/gnupg-announce/2003q2/000268.html>[H /a] + +<Q> I just compiled GnuPG from source on my GNU/Linux RPM-based system + and it's not working. Why? + + Many GNU/Linux distributions that are RPM-based will install a + version of GnuPG as part of its standard installation, placing the + binaries in the /usr/bin directory. Later, compiling and installing + GnuPG from source other than from a source RPM won't normally + overwrite these files, as the default location for placement of + GnuPG binaries is in /usr/local/bin unless the '--prefix' switch + is used during compile to specify an alternate location. Since the + /usr/bin directory more than likely appears in your path before + /usr/local/bin, the older RPM-version binaries will continue to + be used when called since they were not replaced. + + To resolve this, uninstall the RPM-based version with 'rpm -e gnupg' + before installing the binaries compiled from source. If dependency + errors are displayed when attempting to uninstall the RPM (such as + when Red Hat's up2date is also installed, which uses GnuPG), uninstall + the RPM with 'rpm -e gnupg --nodeps' to force the uninstall. Any + dependent files should be automatically replaced during the install + of the compiled version. If the default /usr/local/bin directory is + used, some packages such as SuSE's Yast Online Update may need to be + configured to look for GnuPG binaries in the /usr/local/bin directory, + or symlinks can be created in /usr/bin that point to the binaries + located in /usr/local/bin. + + +<S> ADVANCED TOPICS + +<Q> How does this whole thing work? + + To generate a secret/public keypair, run: + + [H samp] + $ gpg --gen-key + [H /samp] + + and choose the default values. + + Data that is encrypted with a public key can only be decrypted by + the matching secret key. The secret key is protected by a password, + the public key is not. + + So to send your friend a message, you would encrypt your message + with his public key, and he would only be able to decrypt it by + having the secret key and putting in the password to use his secret + key. + + GnuPG is also useful for signing things. Files that are encrypted + with the secret key can be decrypted with the public key. To sign + something, a hash is taken of the data, and then the hash is in some + form encoded with the secret key. If someone has your public key, they + can verify that it is from you and that it hasn't changed by checking + the encoded form of the hash with the public key. + + A keyring is just a large file that stores keys. You have a public + keyring where you store yours and your friend's public keys. You have + a secret keyring that you keep your secret key on, and should be very + careful with. Never ever give anyone else access to it and use a *good* + passphrase to protect the data in it. + + You can 'conventionally' encrypt something by using the option 'gpg -c'. + It is encrypted using a passphrase, and does not use public and secret + keys. If the person you send the data to knows that passphrase, they + can decrypt it. This is usually most useful for encrypting things to + yourself, although you can encrypt things to your own public key in the + same way. It should be used for communication with partners you know + and where it is easy to exchange the passphrases (e.g. with your boy + friend or your wife). The advantage is that you can change the + passphrase from time to time and decrease the risk, that many old + messages may be decrypted by people who accidently got your passphrase. + + You can add and copy keys to and from your keyring with the 'gpg + --import' and 'gpg --export' command. 'gpg --export-secret-keys' will + export secret keys. This is normally not useful, but you can generate + the key on one machine then move it to another machine. + + Keys can be signed under the 'gpg --edit-key' option. When you sign a + key, you are saying that you are certain that the key belongs to the + person it says it comes from. You should be very sure that is really + that person: You should verify the key fingerprint with: + + [H samp] + $ gpg --fingerprint KeyID + [H /samp] + + over the phone (if you really know the voice of the other person), at + a key signing party (which are often held at computer conferences), + or at a meeting of your local GNU/Linux User Group. + + Hmm, what else. You may use the option '-o filename' to force output + to this filename (use '-' to force output to stdout). '-r' just lets + you specify the recipient (which public key you encrypt with) on the + command line instead of typing it interactively. + + Oh yeah, this is important. By default all data is encrypted in some + weird binary format. If you want to have things appear in ASCII text + that is readable, just add the '-a' option. But the preferred method + is to use a MIME aware mail reader (Mutt, Pine and many more). + + There is a small security glitch in the OpenPGP (and therefore GnuPG) + system; to avoid this you should always sign and encrypt a message + instead of only encrypting it. + +<Q> Why are some signatures with an ELG-E key valid? + + These are Elgamal keys generated by GnuPG in v3 (RFC 1991) packets. + The OpenPGP draft later changed the algorithm identifier for Elgamal + keys which are usable for signatures and encryption from 16 to 20. + GnuPG now uses 20 when it generates new Elgamal keys but still + accepts 16 (which is according to OpenPGP "encryption only") if this + key is in a v3 packet. GnuPG is the only program which had used + these v3 Elgamal keys - so this assumption is quite safe. + +<Q> How does the whole trust thing work? + + It works more or less like PGP. The difference is that the trust is + computed at the time it is needed. This is one of the reasons for + the trustdb which holds a list of valid key signatures. If you are + not running in batch mode you will be asked to assign a trust + parameter (ownertrust) to a key. + + You can see the validity (calculated trust value) using this + command. + + [H samp] + $ gpg --list-keys --with-colons + [H /samp] + + If the first field is "pub" or "uid", the second field shows you the + trust: + + [H pre] + o = Unknown (this key is new to the system) + e = The key has expired + q = Undefined (no value assigned) + n = Don't trust this key at all + m = There is marginal trust in this key + f = The key is full trusted + u = The key is ultimately trusted; this is only used + for keys for which the secret key is also available. + r = The key has been revoked + d = The key has been disabled + [H /pre] + + The value in the "pub" record is the best one of all "uid" records. + You can get a list of the assigned trust values (how much you trust + the owner to correctly sign another person's key) with: + + [H samp] + $ gpg --list-ownertrust + [H /samp] + + The first field is the fingerprint of the primary key, the second + field is the assigned value: + + [H pre] + - = No ownertrust value yet assigned or calculated. + n = Never trust this keyholder to correctly verify others signatures. + m = Have marginal trust in the keyholders capability to sign other + keys. + f = Assume that the key holder really knows how to sign keys. + u = No need to trust ourself because we have the secret key. + [H /pre] + + Keep these values confidential because they express your opinions + about others. PGP stores this information with the keyring thus it + is not a good idea to publish a PGP keyring instead of exporting the + keyring. GnuPG stores the trust in the trustdb.gpg file so it is okay + to give a gpg keyring away (but we have a --export command too). + +<Q> What kind of output is this: "key C26EE891.298, uid 09FB: ...."? + + This is the internal representation of a user ID in the trustdb. + "C26EE891" is the keyid, "298" is the local ID (a record number in + the trustdb) and "09FB" is the last two bytes of a ripe-md-160 hash + of the user ID for this key. + +<Q> How do I interpret some of the informational outputs? + + While checking the validity of a key, GnuPG sometimes prints some + information which is prefixed with information about the checked + item. + + [H samp] + "key 12345678.3456" + [H /samp] + + This is about the key with key ID 12345678 and the internal number + 3456, which is the record number of the so called directory record + in the trustdb. + + [H samp] + "uid 12345678.3456/ACDE" + [H /samp] + + This is about the user ID for the same key. To identify the user ID + the last two bytes of a ripe-md-160 over the user ID ring is printed. + + [H samp] + "sig 12345678.3456/ACDE/9A8B7C6D" + [H /samp] + + This is about the signature with key ID 9A8B7C6D for the above key + and user ID, if it is a signature which is direct on a key, the user + ID part is empty (..//..). + +<Q> Are the header lines of a cleartext signature part of the signed + material? + + No. For example you can add or remove "Comment:" lines. They have + a purpose like the mail header lines. However a "Hash:" line is + needed for OpenPGP signatures to tell the parser which hash + algorithm to use. + +<Q> What is the list of preferred algorithms? + + The list of preferred algorithms is a list of cipher, hash and + compression algorithms stored in the self-signature of a key during + key generation. When you encrypt a document, GnuPG uses this list + (which is then part of a public key) to determine which algorithms + to use. Basically it tells other people what algorithms the + recipient is able to handle and provides an order of preference. + +<Q> How do I change the list of preferred algorithms? + + In version 1.0.7 or later, you can use the edit menu and set the + new list of preference using the command "setpref"; the format of + this command resembles the output of the command "pref". The + preference is not changed immediately but the set preference will + be used when a new user ID is created. If you want to update the + preferences for existing user IDs, select those user IDs (or select + none to update all) and enter the command "updpref". Note that the + timestamp of the self-signature is increased by one second when + running this command. + + +<S> ACKNOWLEDGEMENTS + + Many thanks to Nils Ellmenreich for maintaining this FAQ file for + such a long time, Werner Koch for the original FAQ file, and to all + posters to gnupg-users and gnupg-devel. They all provided most of + the answers. + + Also thanks to Casper Dik for providing us with a script to generate + this FAQ (he uses it for the excellent Solaris2 FAQ). + +[H hr] + +Copyright (C) 2000, 2001, 2002, 2003 Free Software Foundation, Inc., +51 Franklin Street, Fifth Floor, Boston, MA 02111, USA + +Verbatim copying and distribution of this entire article is permitted in +any medium, provided this notice is preserved. diff --git a/doc/samplekeys.asc b/doc/samplekeys.asc new file mode 100644 index 000000000..21c36d89e --- /dev/null +++ b/doc/samplekeys.asc @@ -0,0 +1,461 @@ + pub 1024D/5B0358A2 1999-03-15 [expires: 2009-07-11] + uid Werner Koch <wk@gnupg.org> + uid Werner Koch <wk@g10code.com> + uid Werner Koch + uid Werner Koch <werner@fsfe.org> + sub 1024D/010A57ED 2004-03-21 [expires: 2007-12-31] + sub 2048R/C3680A6E 2006-01-01 [expires: 2007-12-31] + + pub 1024D/57548DCD 1998-07-07 [expired: 2005-12-31] + uid Werner Koch (gnupg sig) <dd9jn@gnu.org> + + pub 4096R/99242560 2002-01-28 + uid David M. Shaw <dshaw@jabberwocky.com> + sub 2048g/1643B926 2002-01-28 [expires: 2012-01-26] + sub 1024D/49E1CBC9 2002-01-28 [expires: 2012-01-26] + + pub 2048R/CA57AD7C 2004-12-06 + uid PGP Global Directory Verification Key + uid [jpeg image of size 3400] + + pub 1024D/B2D7795E 2001-01-04 + uid Philip R. Zimmermann <prz@mit.edu> + uid Philip R. Zimmermann <prz@acm.org> + uid [jpeg image of size 3369] + uid [jpeg image of size 3457] + uid Philip R. Zimmermann <prz@philzimmermann.com> + sub 3072g/A8E92834 2001-01-04 + + pub 1024R/1CE0C630 2006-01-01 [expires: 2008-12-31] + uid Werner Koch (dist sig) <dd9jn@gnu.org> + + +-----BEGIN PGP PUBLIC KEY BLOCK----- +Version: GnuPG v1.4.4-svn4128 (GNU/Linux) + +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 +ZUdQRwABARPJAKDmKL2Aeo6OWwcZKyqSWLD4drQxfgCguJ7k7XEuQr+tL0ndoin0 +RSQTkCHRzH//AAANOgEQAAEBAAAAAAAAAAAAAAAA/9j/4AAQSkZJRgABAQAAAQAB +AAD/2wBDAAoHBwgHBgoICAgLCgoLDhgQDg0NDh0VFhEYIx8lJCIfIiEmKzcvJik0 +KSEiMEExNDk7Pj4+JS5ESUM8SDc9Pjv/2wBDAQoLCw4NDhwQEBw7KCIoOzs7Ozs7 +Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozv/wAAR +CACQAHgDASIAAhEBAxEB/8QAHwAAAQUBAQEBAQEAAAAAAAAAAAECAwQFBgcICQoL +/8QAtRAAAgEDAwIEAwUFBAQAAAF9AQIDAAQRBRIhMUEGE1FhByJxFDKBkaEII0Kx +wRVS0fAkM2JyggkKFhcYGRolJicoKSo0NTY3ODk6Q0RFRkdISUpTVFVWV1hZWmNk +ZWZnaGlqc3R1dnd4eXqDhIWGh4iJipKTlJWWl5iZmqKjpKWmp6ipqrKztLW2t7i5 +usLDxMXGx8jJytLT1NXW19jZ2uHi4+Tl5ufo6erx8vP09fb3+Pn6/8QAHwEAAwEB +AQEBAQEBAQAAAAAAAAECAwQFBgcICQoL/8QAtREAAgECBAQDBAcFBAQAAQJ3AAEC +AxEEBSExBhJBUQdhcRMiMoEIFEKRobHBCSMzUvAVYnLRChYkNOEl8RcYGRomJygp +KjU2Nzg5OkNERUZHSElKU1RVVldYWVpjZGVmZ2hpanN0dXZ3eHl6goOEhYaHiImK +kpOUlZaXmJmaoqOkpaanqKmqsrO0tba3uLm6wsPExcbHyMnK0tPU1dbX2Nna4uPk +5ebn6Onq8vP09fb3+Pn6/9oADAMBAAIRAxEAPwDqKXFKDSEgDJOBXSeeHaoJrqKI +fMwqleanyUi/Osi4udqNLM+EUZJNNIlvsakuqjnYazbzxKlopLOHYfwqa5S/8QvO +xjtyY1z17msqWZpGAzuz1wP61LmuhrGk3udHceO9RL4gSNB6EbjVU+Ndd3YEir9U +Fc+nLYC49jWhbt5UW0RIGbpyKzuzbliuhuWfjnUw377ypQv3vk2/rXVaV4o07VFC +iUQzd43P8j3rzVpnLESIgHoopZJIYIxPDg89Vb7tNSZLppnsIIYAggj1FKa4XQ/G +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 +Cw4NDhwQEBw7KCIoOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7 +Ozs7Ozs7Ozs7Ozs7Ozv/wAARCACPAHUDASIAAhEBAxEB/8QAHwAAAQUBAQEBAQEA +AAAAAAAAAAECAwQFBgcICQoL/8QAtRAAAgEDAwIEAwUFBAQAAAF9AQIDAAQRBRIh +MUEGE1FhByJxFDKBkaEII0KxwRVS0fAkM2JyggkKFhcYGRolJicoKSo0NTY3ODk6 +Q0RFRkdISUpTVFVWV1hZWmNkZWZnaGlqc3R1dnd4eXqDhIWGh4iJipKTlJWWl5iZ +mqKjpKWmp6ipqrKztLW2t7i5usLDxMXGx8jJytLT1NXW19jZ2uHi4+Tl5ufo6erx +8vP09fb3+Pn6/8QAHwEAAwEBAQEBAQEBAQAAAAAAAAECAwQFBgcICQoL/8QAtREA +AgECBAQDBAcFBAQAAQJ3AAECAxEEBSExBhJBUQdhcRMiMoEIFEKRobHBCSMzUvAV +YnLRChYkNOEl8RcYGRomJygpKjU2Nzg5OkNERUZHSElKU1RVVldYWVpjZGVmZ2hp +anN0dXZ3eHl6goOEhYaHiImKkpOUlZaXmJmaoqOkpaanqKmqsrO0tba3uLm6wsPE +xcbHyMnK0tPU1dbX2Nna4uPk5ebn6Onq8vP09fb3+Pn6/9oADAMBAAIRAxEAPwD2 +aiiigAooooAKyNb8S6boUZN1Lulx8sS/eP8Ah+NZXjbxcdCt/sdjh7+UdcjES+p9 +68fvLyW6leaa4mmlY5kkL4AP1qXLsaQhfVnc6l8TdSncrYRRW6Zx03t/L+lYsvjj +XnA8zUZY8nI2kr/QVzlu0b8+S2R/HvJNWFgAYuwDFuvJ/lzms2/M2UbdDrLPxlrE +TK51CRxn7sm1gfzrs9F8b2d8ix3v+jyn+Ij5T/hXkQj8gZX5hnlCMZq9YShm8vzD +t7HuDQm0KUUz3ZHWRQ6MGU9CDkGnV5VZ6xf6FJ5qTlY8/Mh5Vh9K77QNfi1uEkJs +kUZI7EeorRSuYyjY16KKKogKKKKACiiigArO17VU0XR575sFkXCKf4mPQVo1wHxX +vfJ0yztw+N8hdh3IHA/nSew4q7PNdT1Ga9vpLi4kaaaRyWY8KDRYWCXkuG5Qc+gz +We8mWAUYz19TW9pbGJAScZ6msJuyO2nG7NOPTrcxhAMdOmOKp3eg36OWsw0qY4x2 +rVgkynIyfrite0bKDBrBNo3aOOtvDWr3dwPPjEKDOS1dJbeFJYY/3UqKxGC5TJ/W +t+Fdx4HNaMUSlM9yK1TbMJ2RwWo+GtXeMiaZLlByCo2mpvCOpTaDrKpdEmA/KxIw +Vz612rR4PPWue13T4RcwXBUBWYI5A6Z6GmpNMmyasejghgCDkHkGlrD8J3ck+lfZ +5m3SWreXu/vL/Cfy/lW5XQnc5GrMKKKKYgooooAK8j+LF4ZNchtmACQQjGDySefy +6V6jqeowaVp099cnEcK7j7+grwXxjq1xr2ovqYRUV8DaCTtA7VMmtjWnBv3jMgjM +0wAUnFbcCtHGFHOevtUek2RisUmkwS3O4HIqeWTaP3e0HPzMemfwrmk7s7oWSuat +k7BQG71v28OFUpjHt2rj7XWreH91NLGWPQ7W/qK6bTdYs5IgFuI8njGajlsPmubt +rmMGVuAo5q7GxWMcZBH51nmVDaIqMpErDJB7VcWf98Y+wXg9jVowlqTtIpGP6Vj+ +KNv/AAj1y4xuUAr9cjFajHnHWsvxG6DSij8h3H6c0yUW/Aju/n7xg7Rn6gkV2Fc1 +4Lg22MszD53IBPf1rpa6I7HNLcKKKKokKKKKAOQ+JchHhuOIMR5twufoATXkjOkj +qqAHLYAzxXq3xLikl0uzKAkCYg49SvFeYR2htbqKJyN3JODnNc837zO6l/DSNOLe +ijyuy7cEZzVG50jUbsmWKTamTny1GRzV4TAPtUZ+la2nyJbBWmZogScBhgfnWN7G +9jmrfR7/AM7ZJdq8GDw8Suf6VRtXubfUFjMZR8jATjP0r0jfbMM7ULHvgVyl3BFP +reICruTglTwvPr60+buKK1NeKe5S3W5liaNmHBTgKfU//WpJ/E13bYVJxM+MnEYy +K25LKNtPtkPCK4U/TNYF94IinuWfcUVjuDxnBBpITa7GppvitLnalxZzRseN6pkE +/TtUviOVbmC0jhdSGk+b26VlGz1PSpkEVz9sthgGN/vr7hq6PT7Qajq9os4ZI0Bf +YB1AOcH/AD3rSOrsYzVlc6bQrZrXR4EddrldzD3P+RWjRRXUcQUUUUAFFFFAGN4r +06bU9Blhtl3TIQ6qOrY7D8K8fvraW31JVmR0ZQPlYYI/Cvea8q+IVi0PiFrgnImj +BUY/P+VZTj1OijP7JyP2n/SMnPB9eldXpV/5kIRsbfQ9K4yTMbhmyMnvUg1FoGYy +I4THAXoPT+dYONztckkb2v69ZwSJa29qgLf6ybYPlHt7+9Q6JdWA1NWgYBMdBXOz +Tf2id0aFg3anW+l3Fkv2tmcL1A/wo5VYSl9x6+ghnswgcEOOcdvemWs7zQHgSMjF +GK+oNcZpd/Kl5Ct1JMIVAOA+M/WtGzu10nXHWObdbXZ8xCT3PVTSuRyHTymN1QeU +SwYcba1dHt1W5Z2xvVOg9z/9YVmC583GOM9BWtoTectzN/CZNi+4H/661p2uc9S6 +ia1FFFdBzBRRRQAUUVi6x4v0HQwft2oxK4/5ZodzfkOn40AbVcX8SrHdo6akg+e2 +ba2P7p/+v/OsDVvjhYws0elaZLO3Z5m2g/gM/wA6525+I+t+IQ+n3ywQ290rDy0j +wQMZHJOetS9jSKdzm7i+USAlhkZ56Dr1rd0vy5o9r4cuvzcg54rjLzNvcFMY55xW +3od8FKx4GR8zMemazlG6N4zfMap02KC6bEcTJ6Nx+tbumPYyRrb/AL+Jc/dBEig+ +wYcU20FtqSguuMcZ7mtCx8PrDMZGkJVGyB/Kuf1Oly7Ej6XcyebgQ3IZTtdl2OD2 +6cViw2lxeSrayYTyzklTnbg9veun1LUU021IDb5Dwi+vvXOaVfIJZJN4LF8YHuad +mTzHTqZEt/3eTIFwg7lu1dnpdn9g06K37gZb6nrXn0mvWujeVqOoI8ltG6/LHyS3 +b/Gu20TxRo3iCMNp16kj4yYm+Vx/wE10U1ZHJWd3oa9FFFamAUUUUAeF+KPijqur +I0Fq32K3PaJvmP1avPbi5kuZCWJOTyfWmzOzNinwxBRuPXtSNCe3hSIBiMv/ACp1 +vcbdThkbp5gz9KYzEL9agcE7vXND1Hexs6raecSVA3jkZ71nWdy1qWjkG3sQRWlB +di8tQ+cuvyuPcVFMsc3yyrz2P/16yi2tGdE4p+8jWsfEMNsU3H7vf+92rdt/FyiI +4Zcnt6GvPmsyv3HB46k4zUiQTRKF3gAHOd3ehwi9SVOSVrHT6nrjzSYMgJUjknOK +gsZnS4MrMVRerY/zk1mafAly2W3SAclgNoNWPNaW+kUDbFF8qovQHufr/hVqFkTz +XNG+v3v5T5oxGq4WM9AKxlMlheCS1leNkO5CrYI59a0XOPvAfX1rN1OPPIB5TB+l +USekeF/ipNEqWutKbhBwJ1Hzj6jv/nrXpWnaxp2rRCSxu4pwRnCtyPqOor5ht5G3 +Dca2bW+mtXEkEzxsDkMuQaCeVM+kqK8WsPiPr1rB5bXImx0MqbiPxoouTyM80jh8 +xyxHyg1KVx1qxEEeNfK5FI6euKZViq5IFJDGZA+Occ0sik9BVaYMqZUkFecjjFIk +sQtJZT7+iEjcPSt63W1mUNIRjFc9ZXhuD5FwQSwwre/oa3raW3+xlGwWPr1FRUj1 +RtSl0GmW1jdlWCNz2Y/40yCBNQZijq0aNtKp/X/P51nXk4RJdqYBPJJHJq74a2x6 +XM4I3NJyM46f5NaQgkyZVG9DRv7hNPsW8pQP4VA7k/8A66g06Hy7dcnJbkk9yetU +9TZpr+KHnKfO2fXoK0LYqYh1x6ZqpPUmJKy45z+XaqV8AUQ89x06VeccHA6896rX +SbrZj3Ug1JRjYKsQfXrVxX+Xg+4qCVQQD0NOhJYcdTSEtGWVkIyFU/gtFJGEywbA +568c0UFmUomil/dAtk9B3q/nzBjHTqKWBVjIPU45NMPDn3pkLQY6jBwRxTIoxJIE +7HjmpW4/OmQcXC+maBdTG2FHdckFDxWpp7yyyu+eMcD/AGj3qpdLsvpAMdTWxpkQ +jsVfpn5j+NVFXZCIL6N5YhG5GeWA6laTw/c+TJLYy4Al5TI/iHb8v5VYlwblAW6q +MZ9c1mztgSleCzAKR26c1T0dwL1sDNPNOed7HafYcCr8MnlSAZwrdSfWobSLZCij +0xRLlXHHDVBojSLZGSTz29KYFDK6nncMVHbTCSMqx+739RUJvWz+5A4/jbp+VIZS +nGFOAOKbC3zZzjr0pbjvnkk9qihyZAB34oFfU0IEO05BH9f0oq1hIkXIySKKBn// +2YhGBBARAgAGBQI8ZiQyAAoJEMdGNjmy13leJSIAoIx0Ql/m4Gf4ZZeFQ1Of+zq6 +499DAKCHBzmIEtE740kuUl5HGNvCJ4QbMLQtUGhpbGlwIFIuIFppbW1lcm1hbm4g +PHByekBwaGlsemltbWVybWFubi5jb20+iEwEEBECAAwFAj6+zxoFCwkIBwMACgkQ +x0Y2ObLXeV4M5gCgnemzKjFcpG5MpeFCTjVg24ptLhsAn03rO14zwfdxKS9ZSuGL +eBG+d/eUuQMNBDpU6CcQDADMHXdXJDhK4sTw6I4TZ5dOkhNh9tvrJQ4X/faY98h8 +ebByHTh1+/bBc8SDESYrQ2DD4+jWCv2hKCYLrqmus2UPogBTAaB81qujEh76DyrO +H3SET8rzF/OkQOnX0ne2Qi0CNsEmy2henXyYCQqNfi3t5F159dSST5sYjvwqp0t8 +MvZCV7cIfwgXcqK61qlC8wXo+VMROU+28W65Szgg2gGnVqMU6Y9AVfPQB8bLQ6mU +rfdMZIZJ+AyDvWXpF9Sh01D49Vlf3HZSTz09jdvOmeFXklnN/biudE/F/Ha8g8VH +MGHOfMlm/xX5u/2RXscBqtNbno2gpXI61Brwv0YAWCvl9Ij9WE5J280gtJ3kkQc2 +azNsOA1FHQ98iLMcfFstjvbzySPAQ/ClWxiNjrtVjLhdONM0/XwXV0OjHRhs3jMh +LLUq/zzhsSlAGBGNfISnCnLWhsQDGcgHKXrKlQzZlp+r0ApQmwJG0wg9ZqRdQZ+c +fL2JSyIZJrqrol7DVelMMm8AAgIMAI1RXgrY9LqHnvhnc1oGwhB7mORU7jwxKiGM +Lqzb0KM+GVTv1xAhhaYGm41/CuhnrOW3LPpjYWbrlXQh+9WJxHvO8UUI6FqEy6TV +yv5Cn3fo4wSr2wtkbFOMKWDCscZLtikxJmsQLtuk6YRGOjgX+fliYIckIfxDMI5z +37zSCNUSweIlUAGsLzLKSMovnHVX89ICsThC0wtuQE8aZBg7DxvHqMIeg7jdCNTN +upF8EwdmpZUnKgghkKn6fXdczj4079wNWxnxuNyHQsg7IytPzmfbjJ9dGU/SzsEW +Mubn0mOF/h2O4laKQlrBYROXKkDLzo5hFG7AJsjI1q4F5MrL5q9m8Xagu+nAfhSe +52kLTr87SOSPaVCmf0QRTDXVHA7qyr3NhPABTIp6s3TRxsJ/KJmXTUIijRu1xM7q +FArdzrs9qWgn2VUfz+Yfsu6qQwsMfm6CSnOZ53/xKit+pWRqSd7pviZHJIUIFdpV +mgqYMfNwfahJIyEz17HKHp3OLVsa7ohUBBgRAgAMBQI6VOgnBRsMAAAAABIJEMdG +Njmy13leB2VHUEcAAQHlbQCg+N+fI3bzqF9+fB50J5sFHVHM7hYAn0+9AfDl5ncn +r4D7ReMDlYoIZwRRmQILBDxUyXkBEACgg6vxNPigg9FQz14CkPtR/dEq3sCjK1r4 ++2oyeoRno+pqZ6Z7ZfphgA/q5woweFAGOg17KD2WXegoQ5pXbFvP+w9j9zm3g59X +zTRSzZgScelTibPnKy6g8r8GDAY6IQraR6pxe4297/NznqvRvKpTt5g1XP5LyjVB +sEv9HAYJE1vyy10qSQRtEz3QunUzfELNC4kiYNMZOnmgaFeW4APIIhWDtrrxqW3O +fjp1K4DAhqcnayrfvYbOtqh0sxJ246kvVc3Bc9pH6wDw/yub2deuPq6BZBLBJwrt +u/20qD0nsZ9is/5j0aL1MZuVmr7xKYqeehyzJ1WdpJK52qng9natYedS+GefKDIw +1Jq7ppQNWfVduTNITFTF0JswggjQuPqKT8Td5GCywQWN/kGHbp6EdybiUXZ+9fp4 +eek0UB5M+srSwbkF4hQ0mBrqlsaoji4CuXjc0c+Zx1D0pGfqqBCmvEV1tLul3U8h +0TzR4opUA8mLKegQp5cjh/dHz7zTPDxVgSr3blJ9FxI1Z69th/+jJj3q6joo3uW/ +5y8qQCrzdSCzs+TDEWwucZtJIuIhTct8AMPY/Ayt+Pf9jXfI+xSQgz3r7Eu5o+rE +u02/cthaOc4b3KYDtNkjLKszgiext1BYOq06R+Yyh2qgsg9azzkfudvvpwhCpJ7E +OxcdaP3bxwAGKbQlRGF2aWQgTS4gU2hhdyA8ZHNoYXdAamFiYmVyd29ja3kuY29t +PokCNAQTAQIAHgUCPFTJeQIbAwYLBwoDBAIDFQMCAxYCAQIeAQIXgAAKCRDbaY1x +mSQlYH7aD/wMq9ksbvAf9drjVP2u4rjZhLkHyc1zCp7rMXc5CdNgDNVyhl7+co/q +MeQBwk8SYEVedrZZ5Q7qjygjkKWp3qrLlw5PSydwCHaf5mlVg5E+5gt+RTkOi6FX +dE/5c0IrIB+MNI3jt3IeOqEhITWcnjDk4gIxm4z43tvXvf/fY33ohrQknApN9uYI +SoElzYGgnEZqX6P3p/8FB2+27A3t/Eshr6lLvVNEMgOlBY8te9TFvMJTMeSJXIQV +pvbz/LMF8uEboWVzRC77y7RcD8p+JP9V97qZGsiOYB+2MPGEvAhEPHxQZAbaBF+e +BFLzev+xmI36fHlFnAFiWikp0tYVLROgBhVGJUOJlDK+olfpxUqF+N8MfjeS01aH +Ly+Y6rkzC26AC/9j+Adka9mBXEiiA1vQcBfO4U45QhgDAl00yUW1gV4oNGZ9Yqsl +OhS/VHB61CjWwjnV3Jwkhscxux3rjj6TAwn5QmoO9kr3CqH1rzQXxTVruCJuwyuI +6aNeywINoubgDhqhOCPfqyzgdxfp5UAhy54ge9dqjfgHI2Q3WxxhD3mCdYgN89GZ +NpuH2lJkJZrRl7BimjqDeTlKYscZ1anrRgRpSoFDdUcMncySzW6cB1WSImj1aNWp +q58FxoJWcTy6lNesINeRjZ/r1eJBeN55P8+7DKGIsGkpftsqgXAqVbkCDQQ8VMsE +EAgA7lKuNHz6iYb+2pAZbxrjp5AHV86pbtVJQBWpGWkGLERGb6w2hYTL8YXr7Jgt +eBmy1a/+l5ZYjnZFQ8603eZRC1g+/krruWmfiJxE/HtHVcVSDUxXNJiE67DpSdGP +f8icIx3c91Xkui9ifS3VMSj1ezWLm5/OYF1utTQ5QiwrvzTuaCs8jWDUzxI77Fcz +QYQELuDmHevde4Ke66MeWCJabs9OQ6i61vurJrj1WQQ9pvXOzcbdoQFtAF/vGK82 +rnr0p5cDyes3S5lCKC4nIhvokHotCf63YUU6afG9OLp/ASlcp2h21vmtDp7xSg6D +7Ivn5cHtHnBvChG6vjQ9IO5gdwADBQgAnNF7z5VcV00LbYQxN1vX77iKwJ1aEZVS +YMrJnvthtJPM5alAsOQRRe85pgZsBfd2xgKbDZFsQaPei+n59nMPTxl68YsrYOWa +Be9IRnEKBYIHSVwDAGsEdxyOKgphNO7cQKcpRWdeqi9FQ11cWVLZrSqChmT9Z6uY +GLDabKwAhYl6TrEQ2J9OzM586LARZHb8m2MOcGrla+XZZannjEVfaei5on8IuhOL +alx/vx74C1qLi9B1fI/JyCsJlMQujkDrpz80hwIyavutLB9TdQZn8TuNqL/m7cpU +1YMbNIa/1Ow2Cio7zrhr/FvTX4KgMaGq6ukx7qWDDbME96BF57IMtIkCIgQYAQIA +DAUCPFTLBAUJEswDAAAKCRDbaY1xmSQlYPGsD/40gsxyQv4M8BFfPgnPEOYlSEBw +pibr+XRdq7q98n3F9ZlXjJHq74RhX6aotL10wpeMb6fcFKhmaMu8Nhx4PUP9+h11 +I7EwmMeLn2prG/sSbsgCY4tsEW08NbDzcXdj6+KvekpE6lYmOa4ORQTEODx81d9R +8DxcqUCYHYn+iYMbEDnBZmHgPc5hkGvBNj2F+dGs4n0iBvxFSBoTSzHb9XksG3/c +q8DdW59McJw1/nTyN2kLIvGjNqSeV+2P2oeh5NRJAHs9X5W+Zar+sqvlHDa1e0jq +2SrMhWdOD1qgTX3BzFyuhWW3IJLdcyFEp6NsC/L2eJdkWwclT1xhEvm8LEsB21nd +E2UNpIjOUcdFvEnYa84Di8ZpIvEvngG6q9tm5K14DXZYQczsN+rrOXgTYfxbEuCz +pFCg1DZaRQmWkXcywzo7F2YUgw1nFe9TlIrLJgXZcjg+ho3UNmquVr+qNV1IzYCk +E6I70J/Q3fuXOfVdM2V0JQTaWfBOUFowwVNyzI5XSl8TTwslsGN8roEAGBR33Jwh +By6TldhErnR1pvIOVt0kkGXbEqIIYONvfsdd2LIFZUfyegh8oFCJNDmKObKnuVyZ +H53Q3bgTn06D5TdBaCK9usVqUe+JZ1K4VLy+20kSiBqaLkel3417o+bqdpL3Uu8g +Xy1bsOhyo9m79ug8orkBogQ8VMvbEQQA9YjnqxRaPgKrbhTQqrzGMYBuP4QlbsQe +EDA3y94jlPK++edfyUGUTnquXHDKmPnLwsqszYZCsC35nVP8FOsg0eATYYAj5A9u +PDUXGQkW1eNQFGoh5p4SxBQZKlVJCAJyVgMxXDtUwDbjQ9CkOONrv1YlajDz9h9y +HfFUjQrC47sAoOX8LBxMJVdAqGMOQGcI2lTWTfq1BACabalqZ3571+ePoAEsqSxZ +elhHA/Se6oxlfxWNQilDGsgUSm53l7yeJn+8qZuiRm49wMlPZnzLA5isMAh0UyoT +SnPs8lnZDLbo4/s4H2Jz0+MahJSYtNtSKTNhuJv7Fh/kQGVltAaniUQeecoJK7Yx +hKbnvsXKzg7YEL2DLKDA4AP/RDeDRhK7ehXbkeONeJsOPjvjdATxSa7Io+GIUFB1 +CSLgaHfC43b8j7S5pEiZ8MOW+kwnP35G89h1K89nFpC47Xt8y/5DH4Z/tw3SdaEI +r8TSL3u/UOK4gZEc5uVhCGBAX/BdIYFWdO2UUjEaO3ox38lgH0HfNscqgN5zCEEc +6lmJAiIEGAECAAwFAjxUy9sFCRLMAwAACgkQ22mNcZkkJWAthQ//QCSN1sFaeqFQ +Eki7fg6E0n+t7mO+V1llNymp7G8Pq3iSI2d99oijVk2BQnrbhdLy+wjl9Lyyzfvv +aQ04QwAUvJNRgIaOpxkYb3z2tc31ho9eOYsQRmKxVzGWw1ii1OEnMBylsAaG58Gp +FI/5MTfucIlJBvXoESkHSoiyov2Pd1c3hJ/6OuFYbn5dvYplBi2K3pAq12OCmWti +cFvPTBpVlvTED0h+I133oO1e1Rx999u1/PQgLem5qfuz3wLv9r8qkXgy1AqdOEBN +svXSo09yWaDTKaZWb6k7viOq6k2aDOi4mr8qgrf8obs6fpOfg6WQw+DRL/T9KUHF +0EUSPVEMkbMc1V2iHURqXBGnIsa5JAi1eV1cMrp9T25DXWHlEfXRnPPjzTSJyJh2 +FmL9NnQrsmHf8f7DiR7uzCgA8+SZqRmr6o2j0FAPUrV4EmMYB7wTYPwPT7EXXmYs +8m0ovamXwGbIwT2Z/EGhOc3UdAQF232o156m097tib5HMbTT+8AcjX3TaeXDJpjI +35WybfJ8F2LEWmJsQwPC9MMCfy7SlW8BUqTBaelPvSYoKdLT6FOxtnoAVYn10WRI +F7LESySJqENspSpv3ACJ/q1jZN6cXYKFlvKLR5Be/MWtnZ2AXqwHmR/XYGtXI6FR +mNd6xrb+mP2QwkihMezVT+y2Q/EogXSJAmoEGAECAAwFCRLMAwAFAkQS4BkAUkcg +BBkRAgAGBQJEEuACAAoJEOJmXIdJ4cvJKsUAn3R2myTGfaAyxiDwL9l3ObofNnX9 +AJ46M4YTuhT9ETVc15IOaHY5VCLcUQkQ22mNcZkkJWCOtg//RVzC6tHMnmZXXA6j +slgca2yf/q0zJIULR9azhcraU3yy8OzjVorX1i5Xh5Rr3SmZkHiNUMrOK0jCzyM9 +ykBa58WOwwN1sZoNUQpUtmYja9kj/y444Atf0iIFW9TT4O31j25qEjz7cLZtmv+T +nzcSIaZekJrIZ/8D74eDqNrfy/WaAi0JK2iMiw4dqwLtIc2W7UTtXfSgiAtNrkp4 +smrO6AUI2Xas7D+3zZiMlIv//W3ZSTF0vHtyBdmvcEPrs6DdjhsM+L7QHLnxD7HD +86cvVh+9SzHelc5erhSWbwKMcZKykQ3uHhU9XCt60MYdbc8HHW92g0e9nEipZ7iS +23uDmzoKvfihtho2+j1w5uKM/S6N/fditlWJ9qHvLHVPLNKPp4DEHo4ns56LCY1c +RUX7N4TOWu2iVSdtzg8NFvhfnKyWkUTCYFuU64Jiq9XcJLMAn2AY02RzQcF8Lwbg +zdyINK9pC0y0lH9ZrN6QyGinxILPVtwLsWO17JpDvKQf4+rmR9nHQSsvGJ/FjCDy +dMx5HaT+TfC4KRR8BBgTDgZkq6cllbeC1qgCz3LXgai9pIlvT9httrVcpOL0QHnK +M5jd7R8JZ1dt5qlltuWsC8Dw52kEGiBn095qmY1FFd02BxL7y7sxHp81m31yTErh +o+HQlcXTIscl65wt2LwowPG0n2iZAQ0EQbPS8gEIAMtvZJvlBs6FEjN86De70Xff +yArVdlYkbwnBc/wNIZtASh/T5ihP/tsD7eHWWOHcsbSbwlQR2iWvEvP/wyC67ZMD +ZRCIzBFpEKFJW8GCQJFiSv3v6QKU2CaL48u5Q3XPi2ymp0TvrWdFW9SXbHhe8tMn +bWFTl5cYawL6oU/gR97wHmQf4V7EB+cU8/Oi7caNsNti/gJiLSnKFPGZq7HInJCt +D8xBS3REVGQvyoLNYJHYGYfeMzczRa3SgqfwLz59Yi1SHlT1/O/8r0Z479JXz7N0 +vgyt2oOy2Cpc2zbsf5Z4iBteVQYizSY40TpO0pnk9cbnMUzVvPW8N0Bhtjh5RYMA +EQEAAbQlUEdQIEdsb2JhbCBEaXJlY3RvcnkgVmVyaWZpY2F0aW9uIEtleYkBVgQQ +AQIAQAUCQlG0cAcLCQgHAwIKAhkBGRhsZGFwOi8va2V5c2VydmVyLnBncC5jb20F +GwMAAAADFgIBBR4BAAAABBUIAgoACgkQlxC4m8pXrXz35ggAnVHdAh2KqrvwSnPo +s73YdlVbeF9Lcbxs4oYPDCk6AHiDpjr2nxu48i1BiLea7aTEEwwAkcIa/3lCLP02 +NjGXq5gRnWpW/d0xtsaDDj8yYWusWGhEJsUlrq5Cz2KjwxNQHXRhHXEDR8vq9uzw +5EjCB0u69vlwNmo8+fa17YMNVdXaXsmXJlJciVHazdvGoscTzZOuKDHdaJmY8nJc +Cydk4qsFOiGOcFm5UOKPnzdBh31NKglqw/xh+1nTA2z5orsY4jVFIB6sWqutIcVQ +Yt/J78diAKFemkEOQe0kU5JZrY34E8pp4BmS6mfPyr8NtHFfMOAE4m8acFeaZK1X +6+uW59HMnv8AAA1ZARAAAQEAAAAAAAAAAAAAAAD/2P/gABBKRklGAAEBAAABAAEA +AP/bAEMACgcHCAcGCggICAsKCgsOGBAODQ0OHRUWERgjHyUkIh8iISYrNy8mKTQp +ISIwQTE0OTs+Pj4lLkRJQzxINz0+O//bAEMBCgsLDg0OHBAQHDsoIig7Ozs7Ozs7 +Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O//AABEI +AJAAeAMBIgACEQEDEQH/xAAfAAABBQEBAQEBAQAAAAAAAAAAAQIDBAUGBwgJCgv/ +xAC1EAACAQMDAgQDBQUEBAAAAX0BAgMABBEFEiExQQYTUWEHInEUMoGRoQgjQrHB +FVLR8CQzYnKCCQoWFxgZGiUmJygpKjQ1Njc4OTpDREVGR0hJSlNUVVZXWFlaY2Rl +ZmdoaWpzdHV2d3h5eoOEhYaHiImKkpOUlZaXmJmaoqOkpaanqKmqsrO0tba3uLm6 +wsPExcbHyMnK0tPU1dbX2Nna4eLj5OXm5+jp6vHy8/T19vf4+fr/xAAfAQADAQEB +AQEBAQEBAAAAAAAAAQIDBAUGBwgJCgv/xAC1EQACAQIEBAMEBwUEBAABAncAAQID +EQQFITEGEkFRB2FxEyIygQgUQpGhscEJIzNS8BVictEKFiQ04SXxFxgZGiYnKCkq +NTY3ODk6Q0RFRkdISUpTVFVWV1hZWmNkZWZnaGlqc3R1dnd4eXqCg4SFhoeIiYqS +k5SVlpeYmZqio6Slpqeoqaqys7S1tre4ubrCw8TFxsfIycrS09TV1tfY2dri4+Tl +5ufo6ery8/T19vf4+fr/2gAMAwEAAhEDEQA/APZqKrX99BptnJd3L7YoxkmuGvvi +zZRkrZWbykdGbgVpClOp8KJlOMdz0KivILj4p6xM2IYYoV/Op7PxX4mv18xJSVBz +leP61v8AVKiV5WRHtovY9YorzD/hMdat/vygsOoIqeD4l3URAubVJB3K8Gk8JVWy +uHtYnpFFc5oXjXTtcnFsivFORna3+NdEDmueUXF2kjRNPVC0UUVIwooooAKKKKAC +iiigDmPiG5XwjdYPXAP614dX0D4l0+HVNKNncFxHK3JQgEYBPGQfSuCfwBpCnia9 +/GVP/iK9DC4iFKDUjnq05Sd0eeL94V6X4N1HTRpqxzzLE6DnPfiq0HgXQHdkku75 +GHT51/8AiKst4H0aE4W/vRj/AGkP/slXWr0asbNsmFOcHcx9euLee/le1x5WTgjo +ea5+Z+TXayeFNMQbf7QvMdeqf/EUz/hCtLkUN9qvSD38xP8A4irhiqUUkmJ0pt3O +f8Iz+V4ihcsFA6knHpXr0ev6QkeJNUtAw6jzlyP1rzy48HaZaW7TxvcyOrKNsrKV +OWA6BR61u6TpkVqRIqlcrj5Rx+NcWJqRqT5om1OLirM6mPX9GmbbHqtmzennrn+d +X1ZXUMjBlPQg5BrnjAjqcbWHtzWFqGmySTma1le1dchXtXMZx9R1/Guexpc9Aorh +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 +K86tEx0ucCiY15h8 +=yJFz +-----END PGP PUBLIC KEY BLOCK----- diff --git a/g10/ChangeLog b/g10/ChangeLog index 426dd8ca6..03a97363f 100644 --- a/g10/ChangeLog +++ b/g10/ChangeLog @@ -1,3 +1,17 @@ +2006-08-21 Werner Koch <wk@g10code.com> + + * skclist.c (random_is_faked): Implemented. + (is_insecure): Also test for the old uppercase version of the + insecure string. + * gpg.c (main): Renamed --quick-random to debug-quick-quick-random. + + * gpg.c (print_mds): Do not use the USE_SHA macros. + + * mainproc.c (proc_encrypted): Remove assign inside condition for + better readibility. + + * packet.h: Moved consts to new header ../common/openpgpdefs.h. + 2006-08-16 Werner Koch <wk@g10code.com> * keyserver.c (GPGKEYS_PREFIX): Rename to gpg2keys_. This is so @@ -568,7 +568,7 @@ static ARGPARSE_OPTS opts[] = { { oPasswdFile, "passphrase-file",2, "@" }, { oCommandFD, "command-fd",1, "@" }, { oCommandFile, "command-file",2, "@" }, - { oQuickRandom, "quick-random", 0, "@"}, + { oQuickRandom, "debug-quick-random", 0, "@"}, { oNoVerbose, "no-verbose", 0, "@"}, { oTrustDBName, "trustdb-name", 2, "@" }, { oNoSecmemWarn, "no-secmem-warning", 0, "@" }, @@ -2152,8 +2152,9 @@ main (int argc, char **argv ) gcry_control (GCRYCTL_SET_VERBOSITY, (int)opt.verbose); opt.list_sigs=0; break; - /* Disabled for now: - case oQuickRandom: quick_random_gen(1); break;*/ + case oQuickRandom: + gcry_control (GCRYCTL_ENABLE_QUICK_RANDOM, 0); + break; case oEmitVersion: opt.no_version=0; break; case oNoEmitVersion: opt.no_version=1; break; case oCompletesNeeded: opt.completes_needed = pargs.r.ret_int; break; @@ -2162,17 +2163,17 @@ main (int argc, char **argv ) case oTrustDBName: trustdb_name = pargs.r.ret_str; break; case oDefaultKey: opt.def_secret_key = pargs.r.ret_str; break; case oDefRecipient: - if( *pargs.r.ret_str ) - opt.def_recipient = make_username(pargs.r.ret_str); - break; + if( *pargs.r.ret_str ) + opt.def_recipient = make_username(pargs.r.ret_str); + break; case oDefRecipientSelf: - xfree(opt.def_recipient); opt.def_recipient = NULL; - opt.def_recipient_self = 1; - break; + xfree(opt.def_recipient); opt.def_recipient = NULL; + opt.def_recipient_self = 1; + break; case oNoDefRecipient: - xfree(opt.def_recipient); opt.def_recipient = NULL; - opt.def_recipient_self = 0; - break; + xfree(opt.def_recipient); opt.def_recipient = NULL; + opt.def_recipient_self = 0; + break; case oNoOptions: opt.no_homedir_creation = 1; break; /* no-options */ case oHomedir: break; case oNoBatch: opt.batch = 0; break; @@ -4031,14 +4032,14 @@ print_mds( const char *fname, int algo ) gcry_md_enable (md, GCRY_MD_MD5); gcry_md_enable (md, GCRY_MD_SHA1); gcry_md_enable (md, GCRY_MD_RMD160); -#ifdef USE_SHA256 - gcry_md_enable (md, DIGEST_ALGO_SHA224); - gcry_md_enable (md, GCRY_MD_SHA256); -#endif -#ifdef USE_SHA512 - gcry_md_enable (md, GCRY_MD_SHA384); - gcry_md_enable (md, GCRY_MD_SHA512); -#endif + if (!openpgp_md_test_algo (DIGEST_ALGO_SHA224)) + gcry_md_enable (md, DIGEST_ALGO_SHA224); + if (!openpgp_md_test_algo (GCRY_MD_SHA256)) + gcry_md_enable (md, GCRY_MD_SHA256); + if (!openpgp_md_test_algo (GCRY_MD_SHA384)) + gcry_md_enable (md, GCRY_MD_SHA384); + if (!openpgp_md_test_algo (GCRY_MD_SHA512)) + gcry_md_enable (md, GCRY_MD_SHA512); } while( (n=fread( buf, 1, DIM(buf), fp )) ) @@ -4054,15 +4055,14 @@ print_mds( const char *fname, int algo ) print_hashline( md, GCRY_MD_MD5, fname ); print_hashline( md, GCRY_MD_SHA1, fname ); print_hashline( md, GCRY_MD_RMD160, fname ); -#ifdef USE_SHA256 - if (!gcry_md_test_algo (DIGEST_ALGO_SHA224) + if (!gcry_md_test_algo (DIGEST_ALGO_SHA224)) print_hashline (md, DIGEST_ALGO_SHA224, fname); - print_hashline( md, GCRY_MD_SHA256, fname ); -#endif -#ifdef USE_SHA512 - print_hashline( md, GCRY_MD_SHA384, fname ); - print_hashline( md, GCRY_MD_SHA512, fname ); -#endif + if (!gcry_md_test_algo (GCRY_MD_SHA256)) + print_hashline( md, GCRY_MD_SHA256, fname ); + if (!gcry_md_test_algo (GCRY_MD_SHA384)) + print_hashline ( md, GCRY_MD_SHA384, fname ); + if (!gcry_md_test_algo (GCRY_MD_SHA512)) + print_hashline ( md, GCRY_MD_SHA512, fname ); } } else { @@ -4072,15 +4072,14 @@ print_mds( const char *fname, int algo ) print_hex( md, GCRY_MD_MD5, fname ); print_hex( md, GCRY_MD_SHA1, fname ); print_hex( md, GCRY_MD_RMD160, fname ); -#ifdef USE_SHA256 - if (!gcry_md_test_algo (DIGEST_ALGO_SHA224) + if (!gcry_md_test_algo (DIGEST_ALGO_SHA224)) print_hex (md, DIGEST_ALGO_SHA224, fname); - print_hex( md, GCRY_MD_SHA256, fname ); -#endif -#ifdef USE_SHA512 - print_hex( md, GCRY_MD_SHA384, fname ); - print_hex( md, GCRY_MD_SHA512, fname ); -#endif + if (!gcry_md_test_algo (GCRY_MD_SHA256)) + print_hex( md, GCRY_MD_SHA256, fname ); + if (!gcry_md_test_algo (GCRY_MD_SHA384)) + print_hex( md, GCRY_MD_SHA384, fname ); + if (!gcry_md_test_algo (GCRY_MD_SHA512)) + print_hex( md, GCRY_MD_SHA512, fname ); } } } diff --git a/g10/keydb.h b/g10/keydb.h index f48acd3c6..b58512068 100644 --- a/g10/keydb.h +++ b/g10/keydb.h @@ -190,6 +190,7 @@ int select_algo_from_prefs( PK_LIST pk_list, int preftype, int select_mdc_from_pklist (PK_LIST pk_list); /*-- skclist.c --*/ +int random_is_faked (void); void release_sk_list( SK_LIST sk_list ); int build_sk_list( STRLIST locusr, SK_LIST *ret_sk_list, int unlock, unsigned use ); diff --git a/g10/keygen.c b/g10/keygen.c index 063c775e9..32bccbb5f 100644 --- a/g10/keygen.c +++ b/g10/keygen.c @@ -1949,11 +1949,9 @@ ask_user_id( int mode ) if( *amail ) p = stpcpy(stpcpy(stpcpy(p," <"), amail),">"); - /* append a warning if we do not have dev/random - * or it is switched into quick testmode */ - /* FIXME: see skclist.c:random_is_faked */ - /* if( quick_random_gen(-1) ) */ - /* strcpy(p, " (INSECURE!)" ); */ + /* Append a warning if the RNG is switched into fake mode. */ + if ( random_is_faked () ) + strcpy(p, " (insecure!)" ); /* print a note in case that UTF8 mapping has to be done */ for(p=uid; *p; p++ ) { diff --git a/g10/keyserver-internal.h b/g10/keyserver-internal.h index a5e6e8c37..fe08a6b71 100644 --- a/g10/keyserver-internal.h +++ b/g10/keyserver-internal.h @@ -23,7 +23,7 @@ #define _KEYSERVER_INTERNAL_H_ #include <time.h> -#include "keyserver.h" +#include "../common/keyserver.h" #include "../common/iobuf.h" #include "types.h" diff --git a/g10/mainproc.c b/g10/mainproc.c index ca5ea9ade..45d9d34a5 100644 --- a/g10/mainproc.c +++ b/g10/mainproc.c @@ -508,8 +508,9 @@ proc_encrypted( CTX c, PACKET *pkt ) } else { - /* assume this is old style conventional encrypted data */ - if ( (algo = opt.def_cipher_algo)) + /* Assume this is old style conventional encrypted data. */ + algo = opt.def_cipher_algo; + if ( algo ) log_info (_("assuming %s encrypted data\n"), gcry_cipher_algo_name (algo)); else if ( gcry_cipher_test_algo (CIPHER_ALGO_IDEA) ) @@ -680,6 +681,8 @@ proc_plaintext( CTX c, PACKET *pkt ) } rc = handle_plaintext( pt, &c->mfx, c->sigs_only, clearsig ); + if (rc) + log_debug ("handle_plaintext failed: err=%d\n", rc); if( gpg_err_code (rc) == GPG_ERR_ENOENT && !c->sigs_only) { #warning We need to change the test for the error code diff --git a/g10/packet.h b/g10/packet.h index 54eeda1a9..2aaf3b902 100644 --- a/g10/packet.h +++ b/g10/packet.h @@ -28,32 +28,10 @@ #include "../jnlib/strlist.h" #include "cipher.h" #include "filter.h" +#include "../common/openpgpdefs.h" #define DEBUG_PARSE_PACKET 1 -typedef enum { - PKT_NONE =0, - PKT_PUBKEY_ENC =1, /* public key encrypted packet */ - PKT_SIGNATURE =2, /* secret key encrypted packet */ - PKT_SYMKEY_ENC =3, /* session key packet (OpenPGP)*/ - PKT_ONEPASS_SIG =4, /* one pass sig packet (OpenPGP)*/ - PKT_SECRET_KEY =5, /* secret key */ - PKT_PUBLIC_KEY =6, /* public key */ - PKT_SECRET_SUBKEY =7, /* secret subkey (OpenPGP) */ - PKT_COMPRESSED =8, /* compressed data packet */ - PKT_ENCRYPTED =9, /* conventional encrypted data */ - PKT_MARKER =10, /* marker packet (OpenPGP) */ - PKT_PLAINTEXT =11, /* plaintext data with filename and mode */ - PKT_RING_TRUST =12, /* keyring trust packet */ - PKT_USER_ID =13, /* user id packet */ - PKT_PUBLIC_SUBKEY =14, /* public subkey (OpenPGP) */ - PKT_OLD_COMMENT =16, /* comment packet from an OpenPGP draft */ - PKT_ATTRIBUTE =17, /* PGP's attribute packet */ - PKT_ENCRYPTED_MDC =18, /* integrity protected encrypted data */ - PKT_MDC =19, /* manipulation detection code packet */ - PKT_COMMENT =61, /* new comment packet (private) */ - PKT_GPG_CONTROL =63 /* internal control packet */ -} pkttype_t; typedef struct packet_struct PACKET; @@ -373,38 +351,6 @@ struct packet_struct { (a)->pkt.generic = NULL; \ } while(0) -typedef enum { - SIGSUBPKT_TEST_CRITICAL=-3, - SIGSUBPKT_LIST_UNHASHED=-2, - SIGSUBPKT_LIST_HASHED =-1, - SIGSUBPKT_NONE = 0, - SIGSUBPKT_SIG_CREATED = 2, /* signature creation time */ - SIGSUBPKT_SIG_EXPIRE = 3, /* signature expiration time */ - SIGSUBPKT_EXPORTABLE = 4, /* exportable */ - SIGSUBPKT_TRUST = 5, /* trust signature */ - SIGSUBPKT_REGEXP = 6, /* regular expression */ - SIGSUBPKT_REVOCABLE = 7, /* revocable */ - SIGSUBPKT_KEY_EXPIRE = 9, /* key expiration time */ - SIGSUBPKT_ARR =10, /* additional recipient request */ - SIGSUBPKT_PREF_SYM =11, /* preferred symmetric algorithms */ - SIGSUBPKT_REV_KEY =12, /* revocation key */ - SIGSUBPKT_ISSUER =16, /* issuer key ID */ - SIGSUBPKT_NOTATION =20, /* notation data */ - SIGSUBPKT_PREF_HASH =21, /* preferred hash algorithms */ - SIGSUBPKT_PREF_COMPR =22, /* preferred compression algorithms */ - SIGSUBPKT_KS_FLAGS =23, /* key server preferences */ - SIGSUBPKT_PREF_KS =24, /* preferred key server */ - SIGSUBPKT_PRIMARY_UID =25, /* primary user id */ - SIGSUBPKT_POLICY =26, /* policy URL */ - SIGSUBPKT_KEY_FLAGS =27, /* key flags */ - SIGSUBPKT_SIGNERS_UID =28, /* signer's user id */ - SIGSUBPKT_REVOC_REASON =29, /* reason for revocation */ - SIGSUBPKT_FEATURES =30, /* feature flags */ - - SIGSUBPKT_SIGNATURE =32, /* embedded signature */ - - SIGSUBPKT_FLAG_CRITICAL=128 -} sigsubpkttype_t; struct notation { diff --git a/g10/skclist.c b/g10/skclist.c index d8f3b2dc1..d9a9d5e9f 100644 --- a/g10/skclist.c +++ b/g10/skclist.c @@ -35,16 +35,26 @@ #include "i18n.h" #include "cipher.h" +#ifndef GCRYCTL_FAKED_RANDOM_P +#define GCRYCTL_FAKED_RANDOM_P 51 +#endif -/* There is currently no way to get the status of the quick random - generator flag from libgcrypt and it is not clear whether this - faked RNG is really a good idea. Thus for now we use this stub - function but we should consider to entirely remove this fake RNG - stuff. */ -static int +/* Return true if Libgcrypt's RNG is in faked mode. */ +int random_is_faked (void) { - return 0; + /* We use a runtime check to allow for slow migrattion of libgcrypt. + We can't use the constant becuase that one is actually an enum + value. */ + gpg_error_t err = gcry_control ( 51 /*GCRYCTL_FAKED_RANDOM_P*/, 0); + + if (!err) + return 0; + if (gpg_err_code (err) != GPG_ERR_INV_OP) + return 1; + log_info ("WARNING: libgcrypt too old.\n"); + log_info (" can't check whether we are in faked RNG mode\n"); + return 0; /* Need to return false. */ } @@ -82,7 +92,8 @@ is_insecure( PKT_secret_key *sk ) continue; /* skip attribute packets */ if ( strstr( id->name, "(insecure!)" ) || strstr( id->name, "not secure" ) - || strstr( id->name, "do not use" ) ) { + || strstr( id->name, "do not use" ) + || strstr( id->name, "(INSECURE!)" ) ) { insecure = 1; break; } diff --git a/tests/ChangeLog b/tests/ChangeLog index f12d9afbe..c7ce33dfe 100644 --- a/tests/ChangeLog +++ b/tests/ChangeLog @@ -1,3 +1,8 @@ +2006-08-21 Werner Koch <wk@g10code.com> + + * Makefile.am (SUBDIRS): New. + * openpgp/: New. + 2006-06-08 Marcus Brinkmann <marcus@g10code.de> * asschk.c (__func__) [__STDC_VERSION__ < 199901L && __GNUC__ >= 2]: diff --git a/tests/Makefile.am b/tests/Makefile.am index 38b64c6ea..c4f7dd457 100644 --- a/tests/Makefile.am +++ b/tests/Makefile.am @@ -29,6 +29,7 @@ # #SUBDIRS = . ${pkits} +SUBDIRS = openpgp GPGSM = ../sm/gpgsm diff --git a/tests/openpgp/ChangeLog b/tests/openpgp/ChangeLog new file mode 100644 index 000000000..fc71f260b --- /dev/null +++ b/tests/openpgp/ChangeLog @@ -0,0 +1,276 @@ +2006-08-21 Werner Koch <wk@g10code.com> + + Copied tests from 1.4 and adjusted paths. + +2006-04-19 David Shaw <dshaw@jabberwocky.com> + + * sigs.test, mds.test: Add tests for SHA-224, SHA-384, and + SHA-512. + +2006-04-11 Werner Koch <wk@g10code.com> + + * armor.test: New. + +2006-03-09 Werner Koch <wk@g10code.com> + + * defs.inc: Removed Basishm by proper redirection. + +2006-03-06 Werner Koch <wk@g10code.com> + + * defs.inc: Print error messages also to stderr. Allow for + verbose environment variable. + (linefeed): New. + (suspend_error, resume_error): New. + * verify.test: More tests. + * multisig.test: Better error printing. + (sig_1ls1ls_valid, sig_ls_valid): Moved to the non-valid group. + +2006-02-14 Werner Koch <wk@gnupg.org> + + * verify.test: New. + +2005-06-21 Werner Koch <wk@g10code.com> + + * conventional.test (algos): Uhh ohh, cut+paste error and not + tested. + +2005-06-02 Werner Koch <wk@g10code.com> + + * conventional.test: have_cipher_algo now requires uppercase + algorithm names. Changed. Noted by John R. Shannon. + +2004-02-09 David Shaw <dshaw@jabberwocky.com> + + * clearsig.test, sigs.test: Properly detect RSA being missing, and + use the proper key for doing an RSA test. + +2003-12-31 David Shaw <dshaw@jabberwocky.com> + + * clearsig.test, conventional-mdc.test, conventional.test, + defs.inc, encrypt-dsa.test, encrypt.test, genkey1024.test, + plain-1.asc, plain-1-pgp.asc, plain-2.asc, plain-3.asc, + pubring.asc, secring.asc, sigs.test: Rework tests to work properly + with a gpg binary that doesn't have all ciphers and all pk algos. + Basically, we test for the ciphers we have, only test signing with + non-160-bit hashes with RSA (we test all hashes as hashes). Test + all key lengths of AES. + +2003-12-05 David Shaw <dshaw@jabberwocky.com> + + * Makefile.am: Reenable tests now that the Elgamal signature keys + are gone. + + * defs.inc, pubring.asc, secring.asc, plain-1.asc, plain-2.asc, + plain-3.asc: Remove the old v3 Elgamal keys and replace with + RSA+Elgamal and RSA s+e. + +2003-12-03 David Shaw <dshaw@jabberwocky.com> + + * options: Remove emulate-md-encode-bug. + +2003-11-27 Werner Koch <wk@gnupg.org> + + * Makefile.am (TESTS): Temporary remove tests using ElG signatures. + +2003-09-04 David Shaw <dshaw@jabberwocky.com> + + * mds.test, sigs.test: Remove TIGER/192 and make SHA-256 optional + (since it might not be compiled in). + +2003-07-10 David Shaw <dshaw@jabberwocky.com> + + * Makefile.am: Add --no-permission-warning to avoid spurious + warning when importing demo keys. + +2003-05-27 Werner Koch <wk@gnupg.org> + + * Makefile.am (CLEANFILES): Add gpg.conf + +2003-05-26 David Shaw <dshaw@jabberwocky.com> + + * defs.inc (pgmname): Make sure there is a valid options + file. (From wk on stable branch) + + * mds.test: Note that missing algorithms are not errors. + +2003-04-23 David Shaw <dshaw@jabberwocky.com> + + * Makefile.am, options.in: Rename options.in to options since it + no longer needs to be a generated file. + + * sigs.test: TODO note to add the new SHAs when we start + generating them. + + * mds.test: Test the new SHAs. + +2002-05-10 Werner Koch <wk@gnupg.org> + + * Makefile.am: Add gpg_dearmor to all targets where it is used. + Noted by Andreas Haumer. + +2002-04-19 Werner Koch <wk@gnupg.org> + + * signencrypt-dsa.test, sigs-dsa.test: Don't check with MD5 as + this is not valid with DSA signatures. + +2001-12-22 Werner Koch <wk@gnupg.org> + + * options.in: Add no-permission-warning. + +2001-12-21 Werner Koch <wk@gnupg.org> + + * Makefile.am (distclean-local): prefix mkdemodirs with srcdir + (DISTCLEANFILES): Add random_seed. + +2001-12-19 Werner Koch <wk@gnupg.org> + + * options.in: Remove load-extension tiger + * Makefile.am (./options): append it if there is such a module. + +2001-10-23 Werner Koch <wk@gnupg.org> + + * defs.inc, Makefile.am: Do not use $srcdir when invoking gpg. + Write the logfile to the current directory. + +2001-09-28 Werner Koch <wk@gnupg.org> + + * defs.inc: Write a log file for each test. + * run-gpg, run-gpgm, run-gpg.patterns: Removed. Replaced in all + tests by a simple macro from defs.inc. + * Makefile.am (CLEANFILES): Remove log files. + (./gpg_dearmor): create it and use it instead of the macro. + This is needed in multisig.test due to IFS tricks. + + * armsignencrypt.test, signencrypt-dsa.test, signencrypt.test, + armencryptp.test, armencrypt.test, encryptp.test, seat.test, + encrypt-dsa.test, encrypt.test: Use --always-trust because the + test are not designed to check the validity. + +2001-09-06 Werner Koch <wk@gnupg.org> + + * genkey1024.test: Simplified by using a parameter file. + +2001-05-30 Werner Koch <wk@gnupg.org> + + * multisig.test (IFS): Reset IFS just before the test. + +2001-04-30 Werner Koch <wk@gnupg.org> + + * multisig.test: Add an set +x to avoid ksh problems + +2001-04-28 Werner Koch <wk@gnupg.org> + + * run-gpg.patterns: a v3 test key expired yesterday, suppress the + messages. + +2001-03-27 Werner Koch <wk@gnupg.org> + + * defs.inc: Removed creation of options file. + * options.in: New. + * Makefile.am: Create options file and fixed import of pubdemo.asc. + + * run-gpg.patterns (gpg): Add some more patterns. + +2001-03-20 Werner Koch <wk@gnupg.org> + + * Makefile.am: Import the pubdemo.asc file + + * sigs.test (hash_algo_list): s/tiger/tiger192/ + +2001-03-19 Werner Koch <wk@gnupg.org> + + * mkdemodirs (GPGDEMO): Add --allow-secret-key-import to all gpg + invocations. Use echon -n instead of an argument with \c. + +2001-02-12 Werner Koch <wk@gnupg.org> + + * multisig.test: new + * Makefile.am (TESTS): Added. + +2000-10-18 Werner Koch <wk@gnupg.org> + + * conventional-mdc.test: Add Rijndael and fix for empty plain texts. + +Thu Feb 10 17:39:44 CET 2000 Werner Koch <wk@gnupg.de> + + * mkdemodirs: Fixed the --clean loop. + +Thu Jan 13 19:31:58 CET 2000 Werner Koch <wk@gnupg.de> + + * defs.inc (chdir): Removed becuase it is unsused an plain old sh + does not like this name. Reported by Alec Habig. + +Tue Oct 26 20:02:23 1999 Werner Koch (wk@gnupg.org) + + * Makefile.am (GPG_DEARMOR): New and use --no-options. + +Tue Aug 31 17:20:44 CEST 1999 Werner Koch <wk@isil.d.shuttle.de> + + * defs.inc: set LC_ALL empty + +Wed Aug 4 10:34:18 CEST 1999 Werner Koch <wk@isil.d.shuttle.de> + + * defs.inc (echo_n): New and used instead of /bin/echo "\c" + +Sun Apr 18 10:11:28 CEST 1999 Werner Koch <wk@isil.d.shuttle.de> + + * mkdemodirs: New + * signdemokey: New. + * Makefile.am (distclean-local): New. + +Wed Mar 17 13:09:03 CET 1999 Werner Koch <wk@isil.d.shuttle.de> + + * mds.test: replaced the "echo -n" + +Mon Mar 8 20:47:17 CET 1999 Werner Koch <wk@isil.d.shuttle.de> + + * pubdemo.asc, secdemo.asc: New. + +Fri Feb 19 15:49:15 CET 1999 Werner Koch <wk@isil.d.shuttle.de> + + * genkey1024.test: Be really quiet. + +1999-01-01 Geoff Keating <geoffk@ozemail.com.au> + + * Makefile.am (CLEANFILES): Also delete trustdb and any leftover + lockfiles. + +Fri Nov 27 15:30:24 CET 1998 Werner Koch <wk@isil.d.shuttle.de> + + * clearsig.test: Some more test cases. + +Sun Oct 25 18:19:35 1998 Werner Koch (wk@isil.d.shuttle.de) + + * mds.test: Check whether TIGER is available. + * sigs.tesr: Ditto. + +Wed Sep 23 12:25:07 1998 Werner Koch (wk@isil.d.shuttle.de) + + * run-gpg.patterns: New (because Solaris fgrep does not like -f -). + +Mon Aug 10 21:33:38 1998 Werner Koch (wk@(none)) + + * genkey1024.test: Ariel fixed this. + +Wed Jul 8 10:43:47 1998 Werner Koch (wk@isil.d.shuttle.de) + + * seat.test: New. + +Mon May 18 15:40:02 1998 Werner Koch (wk@isil.d.shuttle.de) + + * Makefile.am: Now uses mk-tdata to produce random test data. + + * ChangeLog: New. + + + Copyright 1998, 1999, 2000, 2001 Free Software Foundation, Inc. + + This file is free software; as a special exception the author gives + unlimited permission to copy and/or distribute it, with or without + modifications, as long as this notice is preserved. + + This file is distributed in the hope that it will be useful, but + WITHOUT ANY WARRANTY, to the extent permitted by law; without even the + implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + + diff --git a/tests/openpgp/Makefile.am b/tests/openpgp/Makefile.am new file mode 100644 index 000000000..64775a034 --- /dev/null +++ b/tests/openpgp/Makefile.am @@ -0,0 +1,107 @@ +# Copyright (C) 1998, 1999, 2000, 2001, 2003 Free Software Foundation, Inc. +# +# This file is part of GnuPG. +# +# GnuPG is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2 of the License, or +# (at your option) any later version. +# +# GnuPG is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software +# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA + +# Process this file with automake to create Makefile.in + +GPG_IMPORT = ../../g10/gpg2 --homedir . \ + --quiet --yes --no-permission-warning --import + +TESTS = version.test mds.test \ + decrypt.test decrypt-dsa.test \ + sigs.test sigs-dsa.test \ + encrypt.test encrypt-dsa.test \ + seat.test clearsig.test encryptp.test detach.test \ + armsigs.test armencrypt.test armencryptp.test \ + signencrypt.test signencrypt-dsa.test \ + armsignencrypt.test armdetach.test \ + armdetachm.test detachm.test genkey1024.test \ + conventional.test conventional-mdc.test \ + multisig.test verify.test armor.test + + +TEST_FILES = pubring.asc secring.asc plain-1o.asc plain-2o.asc plain-3o.asc \ + plain-1.asc plain-2.asc plain-3.asc plain-1-pgp.asc \ + pubring.pkr.asc secring.skr.asc secdemo.asc pubdemo.asc \ + gpg.conf.tmpl + +DATA_FILES = data-500 data-9000 data-32000 data-80000 plain-large + +EXTRA_DIST = defs.inc $(TESTS) $(TEST_FILES) \ + mkdemodirs signdemokey +CLEANFILES = prepared.stamp x y yy z out err $(DATA_FILES) \ + plain-1 plain-2 plain-3 trustdb.gpg *.lock .\#lk* \ + *.test.log gpg_dearmor gpg.conf \ + pubring.gpg secring.gpg pubring.pkr secring.skr +DISTCLEANFILES = pubring.gpg~ random_seed + + +all-local: prepared.stamp + +distclean-local: + $(srcdir)/mkdemodirs --clean + +prepared.stamp: ./pubring.gpg ./secring.gpg ./plain-1 ./plain-2 ./plain-3 \ + ./pubring.pkr ./secring.skr ./gpg_dearmor $(DATA_FILES) + $(GPG_IMPORT) $(srcdir)/pubdemo.asc + echo timestamp >./prepared.stamp + +./gpg_dearmor: + echo '#!/bin/sh' >./gpg_dearmor + echo "../../g10/gpg2 --no-options --no-greeting \ + --no-secmem-warning --batch --dearmor" >>./gpg_dearmor + chmod 755 ./gpg_dearmor + +./pubring.gpg: $(srcdir)/pubring.asc $(srcdir)/pubdemo.asc ./gpg_dearmor + ./gpg_dearmor > ./pubring.gpg < $(srcdir)/pubring.asc + +./secring.gpg: $(srcdir)/secring.asc ./gpg_dearmor + ./gpg_dearmor > ./secring.gpg < $(srcdir)/secring.asc + +./pubring.pkr: $(srcdir)/pubring.pkr.asc ./gpg_dearmor + ./gpg_dearmor > ./pubring.pkr < $(srcdir)/pubring.pkr.asc + +./secring.skr: $(srcdir)/secring.skr.asc ./gpg_dearmor + ./gpg_dearmor > ./secring.skr < $(srcdir)/secring.skr.asc + +./plain-1: $(srcdir)/plain-1o.asc ./gpg_dearmor + ./gpg_dearmor > ./plain-1 < $(srcdir)/plain-1o.asc + +./plain-2: $(srcdir)/plain-2o.asc ./gpg_dearmor + ./gpg_dearmor > ./plain-2 < $(srcdir)/plain-2o.asc + +./plain-3: $(srcdir)/plain-3o.asc ./gpg_dearmor + ./gpg_dearmor > ./plain-3 < $(srcdir)/plain-3o.asc + + +data-500: + ../../tools/mk-tdata 500 >data-500 +data-9000: + ../../tools/mk-tdata 9000 >data-9000 +data-32000: + ../../tools/mk-tdata 32000 >data-32000 +data-80000: + ../../tools/mk-tdata 80000 >data-80000 +plain-large: + cat $(srcdir)/../../doc/HACKING \ + $(srcdir)/../../doc/DETAILS \ + $(srcdir)/../../doc/FAQ >plain-large + +# To speed up key generation we create a dummy random seed file +random_seed: + ../../tools/mk-tdata 600 + diff --git a/tests/openpgp/armdetach.test b/tests/openpgp/armdetach.test new file mode 100755 index 000000000..c445d6ce6 --- /dev/null +++ b/tests/openpgp/armdetach.test @@ -0,0 +1,11 @@ +#!/bin/sh + +. $srcdir/defs.inc || exit 3 + + +#info Checking armored detached signatures +for i in $plain_files $data_files ; do + echo "$usrpass1" | $GPG --passphrase-fd 0 -sab -o x --yes $i + $GPG -o /dev/null --yes x <$i || error "$i: bad signature" +done + diff --git a/tests/openpgp/armdetachm.test b/tests/openpgp/armdetachm.test new file mode 100755 index 000000000..f1958424c --- /dev/null +++ b/tests/openpgp/armdetachm.test @@ -0,0 +1,9 @@ +#!/bin/sh + +. $srcdir/defs.inc || exit 3 + +#info Checking armored detached signatures of multiple files +i="$plain_files $data_files" +echo "$usrpass1" | $GPG --passphrase-fd 0 -sab -o x --yes $i +cat $i | $GPG -o /dev/null --yes x || error "$i: bad signature" + diff --git a/tests/openpgp/armencrypt.test b/tests/openpgp/armencrypt.test new file mode 100755 index 000000000..356d1bda7 --- /dev/null +++ b/tests/openpgp/armencrypt.test @@ -0,0 +1,11 @@ +#!/bin/sh + +. $srcdir/defs.inc || exit 3 + +#info Checking armored encryption +for i in $plain_files $data_files ; do + $GPG --always-trust -ea -o x --yes -r "$usrname2" $i + $GPG -o y --yes x + cmp $i y || error "$i: mismatch" +done + diff --git a/tests/openpgp/armencryptp.test b/tests/openpgp/armencryptp.test new file mode 100755 index 000000000..d18c56b7e --- /dev/null +++ b/tests/openpgp/armencryptp.test @@ -0,0 +1,12 @@ +#!/bin/sh + +. $srcdir/defs.inc || exit 3 + +#info Checking armored encryption with a pipe +for i in $plain_files $data_files ; do + $GPG --always-trust -ea --yes -r "$usrname2" < $i | tee x | $GPG -o y --yes + cmp $i y || error "$i: mismatch" + $GPG --yes < x > y + cmp $i y || error "$i: mismatch" +done + diff --git a/tests/openpgp/armor.test b/tests/openpgp/armor.test new file mode 100755 index 000000000..2efcf3260 --- /dev/null +++ b/tests/openpgp/armor.test @@ -0,0 +1,181 @@ +#!/bin/sh +# Regression tests pertaining to the armoring. + +. $srcdir/defs.inc || exit 3 + +armored_key_8192='-----BEGIN PGP PUBLIC KEY BLOCK----- +Version: SKS 1.0.9 + +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 +=oXxa +-----END PGP PUBLIC KEY BLOCK----- +' + +# Bug solved 2005-04-07: +# Try importing the attached key file. As the key is exactly 8192 +# bytes long, radix64_read is called twice - the first time to read +# the 8192 bytes, and then once again, to handle the pad '=' on the +# last four character radix64 block '0uI='. gpg bails out with +# gpg: [don't know]: invalid packet (ctb=2d) +# On a read for only the = sign, radix64_read returns -1 for EOF. +# This causes the iobuf code to pop the armor filter and thus the next +# byte read is the '-' from the END header line, causing an error. +i=armored_key_8192 +info "checking: $i" +eval "(IFS=; echo \"\$$i\")" >x +$GPG --import x || error "the $i bug is back in town" + + + + diff --git a/tests/openpgp/armsignencrypt.test b/tests/openpgp/armsignencrypt.test new file mode 100755 index 000000000..24b9575ad --- /dev/null +++ b/tests/openpgp/armsignencrypt.test @@ -0,0 +1,13 @@ +#!/bin/sh + +. $srcdir/defs.inc || exit 3 + + +#info Checking armored signing and encryption +for i in $plain_files $data_files ; do + echo "$usrpass1" | $GPG --passphrase-fd 0 --always-trust \ + -sae -o x --yes -r "$usrname2" $i + $GPG -o y --yes x + cmp $i y || error "$i: mismatch" +done + diff --git a/tests/openpgp/armsigs.test b/tests/openpgp/armsigs.test new file mode 100755 index 000000000..aecc06429 --- /dev/null +++ b/tests/openpgp/armsigs.test @@ -0,0 +1,11 @@ +#!/bin/sh + +. $srcdir/defs.inc || exit 3 + +#info Checking armored signatures +for i in $plain_files $data_files ; do + echo "$usrpass1" | $GPG --passphrase-fd 0 -sa -o x --yes $i + $GPG -o y --yes x + cmp $i y || error "$i: mismatch" +done + diff --git a/tests/openpgp/clearsig.test b/tests/openpgp/clearsig.test new file mode 100755 index 000000000..8217f2f49 --- /dev/null +++ b/tests/openpgp/clearsig.test @@ -0,0 +1,102 @@ +#!/bin/sh + +# Fixme: we should not only do a --verify but also the output. + +. $srcdir/defs.inc || exit 3 + +# ====================================== +# I can't compare the out because plain-3 has no LF as last charcater +# but the output has always one. I do not thinkl this is a bug, because +# it is clear text and not binary text. +# ====================================== +for i in $plain_files plain-large ; do + echo "$usrpass1" | $GPG --passphrase-fd 0 -sat -o x --yes $i + $GPG --verify x +done + + +# ====================================== +# and once more to check rfc1991 +# ====================================== + +if have_pubkey_algo "RSA"; then + for i in $plain_files plain-large ; do + $GPG -u $usrname3 --rfc1991 --digest-algo md5 -sat -o x --yes $i + $GPG --verify x + done +fi + +# ====================================== +# and one with long lines +# ====================================== +cat >y <<EOF +xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxyx + +xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx +EOF +echo "$usrpass1" | $GPG --passphrase-fd 0 --clearsign -o x --yes y +$GPG --verify x + + +# ====================================== +# and one with only one long lines +# ====================================== +cat >y <<EOF +xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxyx +EOF +echo "$usrpass1" | $GPG --passphrase-fd 0 --clearsign -o x --yes y +$GPG --verify x + + +# ====================================== +# and one with an empty body +# ====================================== +cat >y <<EOF +EOF +echo "$usrpass1" | $GPG --passphrase-fd 0 --clearsign -o x --yes y +$GPG --verify x + + +# ====================================== +# and one with one empty line at the end +# ====================================== +cat >y <<EOF +line 1 +line 2 +line 3 +there is a blank line after this + +EOF +echo "$usrpass1" | $GPG --passphrase-fd 0 --clearsign -o x --yes y +$GPG --verify x + + +# ====================================== +# I think this file will be constructed wrong (gpg 0.9.3) +# but it should verify okay anyway. +# ====================================== +echo "this is a sig test" >y +echo_n " " >>y +echo "$usrpass1" | $GPG --passphrase-fd 0 --clearsign -o x --yes y +$GPG --verify x + + +# ====================================== +# check our special diff mode +# ====================================== +cat >y <<EOF +--- mainproc.c Tue Jun 27 09:28:11 2000 ++++ mainproc.c~ Thu Jun 8 22:50:25 2000 +@@ -1190,16 +1190,13 @@ + md_enable( c->mfx.md, n1->pkt->pkt.signature->digest_algo); + } + /* ask for file and hash it */ +- if( c->sigs_only ) { ++ if( c->sigs_only ) + rc = hash_datafiles( c->mfx.md, NULL, + c->signed_data, c->sigfilename, + n1? (n1->pkt->pkt.onepass_sig->sig_class == 0x01):0 ); +EOF +echo "$usrpass1" | $GPG --passphrase-fd 0 \ + --not-dash-escaped --clearsign -o x --yes y +$GPG --verify x diff --git a/tests/openpgp/conventional-mdc.test b/tests/openpgp/conventional-mdc.test new file mode 100755 index 000000000..95a6ba476 --- /dev/null +++ b/tests/openpgp/conventional-mdc.test @@ -0,0 +1,42 @@ +#!/bin/sh + +. $srcdir/defs.inc || exit 3 + +algos="3des" + +if have_cipher_algo "idea"; then + algos="$algos idea" +fi + +if have_cipher_algo "cast5"; then + algos="$algos idea" +fi + +if have_cipher_algo "blowfish"; then + algos="$algos idea" +fi + +if have_cipher_algo "aes"; then + algos="$algos aes aes192 aes256" +fi + +if have_cipher_algo "twofish"; then + algos="$algos twofish" +fi + +#info Checking conventional encryption +for i in 0 1 2 3 9 10 11 19 20 21 22 23 39 40 41 8192 32000 ; do + for ciph in $algos; do + # *BSD's dd can't cope with a count of 0 + if test "$i" = "0"; then + : >z + else + dd if=data-80000 of=z bs=1 count=$i 2>/dev/null + fi + echo "Hier spricht HAL" | $GPG --passphrase-fd 0 \ + --force-mdc --cipher $ciph -c -o x --yes z + echo "Hier spricht HAL" | $GPG --passphrase-fd 0 \ + -o y --yes x + cmp z y || error "$ciph/$i: mismatch" + done +done diff --git a/tests/openpgp/conventional.test b/tests/openpgp/conventional.test new file mode 100755 index 000000000..2fd273028 --- /dev/null +++ b/tests/openpgp/conventional.test @@ -0,0 +1,37 @@ +#!/bin/sh + +. $srcdir/defs.inc || exit 3 + +#info Checking conventional encryption +for i in plain-2 data-32000 ; do + echo "Hier spricht HAL" | $GPG --passphrase-fd 0 -c -o x --yes $i + echo "Hier spricht HAL" | $GPG --passphrase-fd 0 -o y --yes x + cmp $i y || error "$i: mismatch" +done + +algos="3des" + +if have_cipher_algo "CAST5"; then + algos="$algos cast5" +fi + +if have_cipher_algo "BLOWFISH"; then + algos="$algos blowfish" +fi + +if have_cipher_algo "AES"; then + algos="$algos aes aes192 aes256" +fi + +if have_cipher_algo "TWOFISH"; then + algos="$algos twofish" +fi + +for a in $algos; do + for i in plain-1 data-80000 ; do + echo "Hier spricht HAL" | $GPG --passphrase-fd 0 \ + --cipher-algo $a -c -o x --yes $i + echo "Hier spricht HAL" | $GPG --passphrase-fd 0 -o y --yes x + cmp $i y || error "$i: ($a) mismatch" + done +done diff --git a/tests/openpgp/decrypt-dsa.test b/tests/openpgp/decrypt-dsa.test new file mode 100755 index 000000000..6dc7dc459 --- /dev/null +++ b/tests/openpgp/decrypt-dsa.test @@ -0,0 +1,10 @@ +#!/bin/sh + +. $srcdir/defs.inc || exit 3 + +#info Checking decryption of supplied DSA encrypted file +for i in "plain-1" ; do + $GPG $dsa_keyrings -o y --yes $srcdir/$i-pgp.asc + cmp $i y || error "$i: mismatch" +done + diff --git a/tests/openpgp/decrypt.test b/tests/openpgp/decrypt.test new file mode 100755 index 000000000..aab416750 --- /dev/null +++ b/tests/openpgp/decrypt.test @@ -0,0 +1,10 @@ +#!/bin/sh + +. $srcdir/defs.inc || exit 3 + +#info Checking decryption of supplied files +for i in $plain_files ; do + echo "$usrpass1" | $GPG --passphrase-fd 0 -o y --yes $srcdir/$i.asc + cmp $i y || error "$i: mismatch" +done + diff --git a/tests/openpgp/defs.inc b/tests/openpgp/defs.inc new file mode 100755 index 000000000..694e9ee1c --- /dev/null +++ b/tests/openpgp/defs.inc @@ -0,0 +1,160 @@ +# definitions for the check scripts + +#-------------------------------- +#------ constants --------------- +#-------------------------------- + +# Note that usrpass1 is also used in Makefile.am +usrname1="one" +usrpass1="def" +usrname2="two" +usrpass2="" +usrname3="three" +usrpass3="" + + +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) +dsa_usrname2="0xCB879DE9" + +dsa_keyrings="--keyring ./pubring.pkr --secret-keyring ./secring.skr" + + +plain_files="plain-1 plain-2 plain-3" +data_files="data-500 data-9000 data-32000 data-80000" +exp_files="" + +# The testscripts expect the original language +LANG= +LANGUAGE= +LC_ALL= +LC_MESSAGES= + +# Internal use. +defs_stop_on_error=no +defs_error_seen=no + +#-------------------------------- +#------ utility functions ------- +#-------------------------------- + +fatal () { + echo "$pgmname: fatal:" $* >&2 + echo "$pgmname: fatal:" $* >&5 + exit 1; +} + +error () { + echo "$pgmname:" $* >&2 + defs_error_seen=yes + echo "$pgmname:" $* >&5 + if [ x$defs_stop_on_error != xyes ]; then + exit 1 + fi +} + +# Call this at the start of a test and resume_error at the end to keep +# on running all subtests without immediately exiting on error. +suspend_error () { + defs_stop_on_error=yes +} + +resume_error () { + if [ x$defs_error_seen = xyes ]; then + exit 1 + fi + defs_stop_on_error=no + defs_error_seen=no +} + +info () { + echo "$pgmname:" $* >&2 + if [ -n "${verbose+set}" ]; then + echo "$pgmname:" $* >&5 + fi +} + +linefeed () { + echo >&2 +} + + +echo_n_init=no +echo_n () { + if test "$echo_n_init" = "no"; then + if (echo "testing\c"; echo 1,2,3) | grep c >/dev/null; then + if (echo -n testing; echo 1,2,3) | sed s/-n/xn/ | grep xn >/dev/null; then + echo_n_n= + echo_n_c=' +' + else + echo_n_n='-n' + echo_n_c= + fi + else + echo_n_n= + echo_n_c='\c' + fi + echo_n_init=yes + fi + echo $echo_n_n "${1}$echo_n_c" +} + + +#cleanup () { +# rm $cleanup_files 2>/dev/null || true +# echo "#empty" >./gpg.conf +#} + + +#add_cleanup () { +# cleanup_files="$cleanup_files $*" +#} + +have_pubkey_algo () { + if ../../g10/gpg2 --homedir . --version | grep "Pubkey:.*$1" >/dev/null + then + true + else + false + fi +} + +have_cipher_algo () { + if ../../g10/gpg2 --homedir . --version | grep "Cipher:.*$1" >/dev/null + then + true + else + false + fi +} + +have_hash_algo () { + if ../../g10/gpg2 --homedir . --version | grep "Hash:.*$1" >/dev/null + then + true + else + false + fi +} + +set -e +pgmname=`basename $0` +#trap cleanup SIGHUP SIGINT SIGQUIT + +[ -z "$srcdir" ] && fatal "not called from make" + +# Make sure we have a valid option files even with VPATH builds. +if [ -f ./gpg.conf ]; then + : +elif [ -f $srcdir/gpg.conf.tmpl ]; then + cat $srcdir/gpg.conf.tmpl >gpg.conf +fi + +GPG="../../g10/gpg2 --no-permission-warning --homedir . " + +exec 5>&2 2>${pgmname}.log + +: +# end diff --git a/tests/openpgp/detach.test b/tests/openpgp/detach.test new file mode 100755 index 000000000..6a3ae05c5 --- /dev/null +++ b/tests/openpgp/detach.test @@ -0,0 +1,10 @@ +#!/bin/sh + +. $srcdir/defs.inc || exit 3 + +#info Checking detached signatures +for i in $plain_files $data_files ; do + echo "$usrpass1" | $GPG --passphrase-fd 0 -sb -o x --yes $i + $GPG -o /dev/null --yes x <$i || error "$i: bad signature" +done + diff --git a/tests/openpgp/detachm.test b/tests/openpgp/detachm.test new file mode 100755 index 000000000..dc60bb239 --- /dev/null +++ b/tests/openpgp/detachm.test @@ -0,0 +1,9 @@ +#!/bin/sh + +. $srcdir/defs.inc || exit 3 + +#info Checking detached signatures of multiple files +i="$plain_files $data_files" +echo "$usrpass1" | $GPG --passphrase-fd 0 -sb -o x --yes $i +cat $i | $GPG -o /dev/null --yes x || error "$i: bad signature" + diff --git a/tests/openpgp/encrypt-dsa.test b/tests/openpgp/encrypt-dsa.test new file mode 100755 index 000000000..0c6333c21 --- /dev/null +++ b/tests/openpgp/encrypt-dsa.test @@ -0,0 +1,41 @@ +#!/bin/sh + +. $srcdir/defs.inc || exit 3 + +#info Checking encryption +for i in $plain_files $data_files ; do + $GPG $dsa_keyrings --always-trust -e -o x --yes -r "$dsa_usrname2" $i + $GPG $dsa_keyrings -o y --yes x + cmp $i y || error "$i: mismatch" +done + +algos="3des" + +if have_cipher_algo "idea"; then + algos="$algos idea" +fi + +if have_cipher_algo "cast5"; then + algos="$algos idea" +fi + +if have_cipher_algo "blowfish"; then + algos="$algos idea" +fi + +if have_cipher_algo "aes"; then + algos="$algos aes aes192 aes256" +fi + +if have_cipher_algo "twofish"; then + algos="$algos twofish" +fi + +for ca in $algos ; do + for i in $plain_files $data_files ; do + $GPG $dsa_keyrings --always-trust --cipher-algo $ca -e \ + -o x --yes -r "$dsa_usrname2" $i + $GPG $dsa_keyrings -o y --yes x + cmp $i y || error "$i: mismatch" + done +done diff --git a/tests/openpgp/encrypt.test b/tests/openpgp/encrypt.test new file mode 100755 index 000000000..44f26a17a --- /dev/null +++ b/tests/openpgp/encrypt.test @@ -0,0 +1,40 @@ +#!/bin/sh + +. $srcdir/defs.inc || exit 3 + +#info Checking encryption +for i in $plain_files $data_files ; do + $GPG --always-trust -e -o x --yes -r "$usrname2" $i + $GPG -o y --yes x + cmp $i y || error "$i: mismatch" +done + +algos="3des" + +if have_cipher_algo "idea"; then + algos="$algos idea" +fi + +if have_cipher_algo "cast5"; then + algos="$algos idea" +fi + +if have_cipher_algo "blowfish"; then + algos="$algos idea" +fi + +if have_cipher_algo "aes"; then + algos="$algos aes aes192 aes256" +fi + +if have_cipher_algo "twofish"; then + algos="$algos twofish" +fi + +for ca in $algos ; do + for i in $plain_files $data_files ; do + $GPG --always-trust -e -o x --yes -r "$usrname2" --cipher-algo $ca $i + $GPG -o y --yes x + cmp $i y || error "$i: mismatch" + done +done diff --git a/tests/openpgp/encryptp.test b/tests/openpgp/encryptp.test new file mode 100755 index 000000000..7df24efec --- /dev/null +++ b/tests/openpgp/encryptp.test @@ -0,0 +1,10 @@ +#!/bin/sh + +. $srcdir/defs.inc || exit 3 + +#info Checking encryption with a pipe +for i in $plain_files $data_files ; do + $GPG --always-trust -e --yes -r "$usrname2" <$i | $GPG --yes > y + cmp $i y || error "$i: mismatch" +done + diff --git a/tests/openpgp/genkey1024.test b/tests/openpgp/genkey1024.test new file mode 100755 index 000000000..e17e8c91c --- /dev/null +++ b/tests/openpgp/genkey1024.test @@ -0,0 +1,31 @@ +#!/bin/sh + +. $srcdir/defs.inc || exit 3 + +../../g10/gpg2 --quiet --batch --debug-quick-random --homedir . --gen-key <<EOF +Key-Type: DSA +Key-Length: 1024 +Subkey-Type: ELG +Subkey-Length: 1024 +Name-Real: Harry H. +Name-Comment: test key +Name-Email: hh@@ddorf.de +Expire-Date: 1 +Passphrase: abc +%commit +EOF + +if have_pubkey_algo "RSA"; then +../../g10/gpg2 --quiet --batch --debug-quick-random --homedir . --gen-key <<EOF +Key-Type: RSA +Key-Length: 1024 +Key-Usage: sign,encrypt +Name-Real: Harry A. +Name-Comment: RSA test key +Name-Email: hh@@ddorf.de +Expire-Date: 2 +Passphrase: abc +%commit +EOF +fi + diff --git a/tests/openpgp/gpg.conf.tmpl b/tests/openpgp/gpg.conf.tmpl new file mode 100644 index 000000000..7060a6610 --- /dev/null +++ b/tests/openpgp/gpg.conf.tmpl @@ -0,0 +1,5 @@ +no-greeting +no-secmem-warning +no-permission-warning +batch +no-auto-check-trustdb diff --git a/tests/openpgp/mds.test b/tests/openpgp/mds.test new file mode 100755 index 000000000..6551d18e0 --- /dev/null +++ b/tests/openpgp/mds.test @@ -0,0 +1,69 @@ +#!/bin/sh + + +. $srcdir/defs.inc || exit 3 + + +test_one () { + if [ "`grep $1 y | sed -e 's/:[^:]*:\(.*\):/\1/'`" != "$2" ]; then + failed="$failed $1" + fi +} + +failed="" + +#info Checking message digests +cat /dev/null | $GPG --with-colons --print-mds >y +# MD5 +test_one ":1:" "D41D8CD98F00B204E9800998ECF8427E" +# SHA-1 +test_one ":2:" "DA39A3EE5E6B4B0D3255BFEF95601890AFD80709" +# RMD160 +test_one ":3:" "9C1185A5C5E9FC54612808977EE8F548B2258D31" +# SHA-224 +if have_hash_algo "SHA224"; then + test_one ":11:" "D14A028C2A3A2BC9476102BB288234C415A2B01F828EA62AC5B3E42F" +else + echo "Hash algorithm SHA-224 is not installed (not an error)" +fi +# SHA-256 +if have_hash_algo "SHA256"; then + test_one ":8:" "E3B0C44298FC1C149AFBF4C8996FB92427AE41E4649B934CA495991B7852B855" +else + echo "Hash algorithm SHA-256 is not installed (not an error)" +fi +# SHA-384 +if have_hash_algo "SHA384"; then + test_one ":9:" "38B060A751AC96384CD9327EB1B1E36A21FDB71114BE07434C0CC7BF63F6E1DA274EDEBFE76F65FBD51AD2F14898B95B" +else + echo "Hash algorithm SHA-384 is not installed (not an error)" +fi +# SHA-512 +if have_hash_algo "SHA512"; then + test_one ":10:" "CF83E1357EEFB8BDF1542850D66D8007D620E4050B5715DC83F4A921D36CE9CE47D0D13C5D85F2B0FF8318D2877EEC2F63B931BD47417A81A538327AF927DA3E" +else + echo "Hash algorithm SHA-512 is not installed (not an error)" +fi + +[ "$failed" != "" ] && error "$failed failed for empty string" + +echo_n "abcdefghijklmnopqrstuvwxyz" | $GPG --with-colons --print-mds >y +test_one ":1:" "C3FCD3D76192E4007DFB496CCA67E13B" +test_one ":2:" "32D10C7B8CF96570CA04CE37F2A19D84240D3A89" +test_one ":3:" "F71C27109C692C1B56BBDCEB5B9D2865B3708DBC" +if have_hash_algo "SHA224"; then + test_one ":11:" "45A5F72C39C5CFF2522EB3429799E49E5F44B356EF926BCF390DCCC2" +fi +if have_hash_algo "SHA256"; then + test_one ":8:" "71C480DF93D6AE2F1EFAD1447C66C9525E316218CF51FC8D9ED832F2DAF18B73" +fi +if have_hash_algo "SHA384"; then + test_one ":9:" "FEB67349DF3DB6F5924815D6C3DC133F091809213731FE5C7B5F4999E463479FF2877F5F2936FA63BB43784B12F3EBB4" +fi +if have_hash_algo "SHA512"; then + test_one ":10:" "4DBFF86CC2CA1BAE1E16468A05CB9881C97F1753BCE3619034898FAA1AABE429955A1BF8EC483D7421FE3C1646613A59ED5441FB0F321389F77F48A879C7B1F1" +fi + +[ "$failed" != "" ] && error "$failed failed for a..z" + +exit 0 diff --git a/tests/openpgp/mkdemodirs b/tests/openpgp/mkdemodirs new file mode 100755 index 000000000..217908078 --- /dev/null +++ b/tests/openpgp/mkdemodirs @@ -0,0 +1,37 @@ +#!/bin/sh + +set -e + +GPG="../g10/gpg2 --batch --quiet --no-secmem-warning --allow-secret-key-import" +NAMES='Alpha Bravo Charlie Delta Echo Foxtrot Golf Hotel India + Juliet Kilo Lima Mike November Oscar Papa Quebec Romeo + Sierra Tango Uniform Victor Whisky XRay Yankee Zulu' + +if [ "$1" = "--clean" ]; then + (for i in $NAMES; do + [ -d $i ] && rm -r $i + done) || true + exit 0 +fi + +$GPG --dearmor -o secdemo.gpg --yes ../checks/secdemo.asc +$GPG --dearmor -o pubdemo.gpg --yes ../checks/pubdemo.asc +[ -f ./tdb.tmp ] && rm ./tdb.tmp +GPGDEMO="$GPG --homedir . --trustdb-name ./tdb.tmp --no-default-keyring + --keyring pubdemo.gpg --secret-keyring secdemo.gpg" +echo -n "Creating:" +for name in $NAMES; do + echo -n " $name" + [ -d $name ] && rm -r $name + mkdir $name + $GPGDEMO --export-secret-key -o - $name > $name/Secret.gpg + $GPG --homedir $name --import $name/Secret.gpg + $GPGDEMO --export -o - $name > $name/Public.gpg + $GPG --homedir $name --import $name/Public.gpg + [ -f $name/pubring.gpg~ ] && rm $name/pubring.gpg~ +done +echo "." +[ -f ./tdb.tmp ] && rm ./tdb.tmp +rm pubdemo.gpg secdemo.gpg + + diff --git a/tests/openpgp/multisig.test b/tests/openpgp/multisig.test new file mode 100755 index 000000000..ece6f22da --- /dev/null +++ b/tests/openpgp/multisig.test @@ -0,0 +1,145 @@ +#!/bin/sh +# Check that gpg verifies only signatures where there is no ambiguity +# in the order of packets. Needs the Demo Keys Lima and Mike. + +# Note: We do son't support multiple signaturess anymore thus thsi test is +# not really needed becuase verify could do the same. We keep it anyway. + +. $srcdir/defs.inc || exit 3 + +suspend_error + + + +sig_1ls1ls_valid=' +-----BEGIN PGP ARMORED FILE----- + +kA0DAAIRN8q1H7eRA/gBrCdiBXRleHQxOogq9EkgYW0gc29ycnksIEkgY2FuJ3Qg +ZG8gdGhhdAqIPwMFADqIKvQ3yrUft5ED+BEC2joAoJaSaXOZEtSZqQ780HIXG77e +8PB7AJ4wCprmaFTO0fBaTcXDuEOBdAWnOZANAwACETfKtR+3kQP4AawnYgV0ZXh0 +MTqIKvRJIGFtIHNvcnJ5LCBJIGNhbid0IGRvIHRoYXQKiD8DBQA6iCr0N8q1H7eR +A/gRAto6AKCWkmlzmRLUmakO/NByFxu+3vDwewCeMAqa5mhUztHwWk3Fw7hDgXQF +pzk= +=8jSC +-----END PGP ARMORED FILE----- +' +sig_ls_valid=' +-----BEGIN PGP ARMORED FILE----- + +rCdiBXRleHQxOogrS0kgYW0gc29ycnksIEkgY2FuJ3QgZG8gdGhhdAqIPwMFADqI +K0s3yrUft5ED+BECLQMAn2jZUNOpB4OuurSQkc2TRfg6ek02AJ9+oJS0frQ+yUsT +QDUFTH2PvZRxjw== +=J+lb +-----END PGP ARMORED FILE----- +' +sig_sl_valid=' +-----BEGIN PGP ARMORED FILE----- + +iD8DBQA6iCtLN8q1H7eRA/gRAi0DAJ9o2VDTqQeDrrq0kJHNk0X4OnpNNgCffqCU +tH60PslLE0A1BUx9j72UcY+sJ2IFdGV4dDE6iCtLSSBhbSBzb3JyeSwgSSBjYW4n +dCBkbyB0aGF0Cg== +=N9MP +-----END PGP ARMORED FILE----- +' +sig_11lss_valid_but_is_not=' +-----BEGIN PGP ARMORED FILE----- + +kA0DAAIRN8q1H7eRA/gAkA0DAAIRN8q1H7eRA/gBrCdiBXRleHQxOogyXUkgYW0g +c29ycnksIEkgY2FuJ3QgZG8gdGhhdAqIPwMFADqIMl03yrUft5ED+BECwQAAnRXT +mXjVd385oD38W80XuheWKTGcAJ9pZ6/flaKDfw+SLido7xaUHuhp5Yg/AwUAOogy +XTfKtR+3kQP4EQLBAACgnN0IP+NztE0aAc/DZ17yHWR9diwAniN0P01WmbgZJoZB +Q341WRXKS/at +=Ekrs +-----END PGP ARMORED FILE----- +' +sig_11lss11lss_valid_but_is_not=' +-----BEGIN PGP ARMORED FILE----- + +kA0DAAIRN8q1H7eRA/gAkA0DAAIRN8q1H7eRA/gBrCdiBXRleHQxOogyXUkgYW0g +c29ycnksIEkgY2FuJ3QgZG8gdGhhdAqIPwMFADqIMl03yrUft5ED+BECwQAAnRXT +mXjVd385oD38W80XuheWKTGcAJ9pZ6/flaKDfw+SLido7xaUHuhp5Yg/AwUAOogy +XTfKtR+3kQP4EQLBAACgnN0IP+NztE0aAc/DZ17yHWR9diwAniN0P01WmbgZJoZB +Q341WRXKS/atkA0DAAIRN8q1H7eRA/gAkA0DAAIRN8q1H7eRA/gBrCdiBXRleHQx +OogyXUkgYW0gc29ycnksIEkgY2FuJ3QgZG8gdGhhdAqIPwMFADqIMl03yrUft5ED ++BECwQAAnRXTmXjVd385oD38W80XuheWKTGcAJ9pZ6/flaKDfw+SLido7xaUHuhp +5Yg/AwUAOogyXTfKtR+3kQP4EQLBAACgnN0IP+NztE0aAc/DZ17yHWR9diwAniN0 +P01WmbgZJoZBQ341WRXKS/at +=P1Mu +-----END PGP ARMORED FILE----- +' +sig_ssl_valid_but_is_not=' +-----BEGIN PGP ARMORED FILE----- + +iD8DBQA6iCtLN8q1H7eRA/gRAi0DAJ9o2VDTqQeDrrq0kJHNk0X4OnpNNgCffqCU +tH60PslLE0A1BUx9j72UcY+IPwMFADqIK0s3yrUft5ED+BECLQMAn2jZUNOpB4Ou +urSQkc2TRfg6ek02AJ9+oJS0frQ+yUsTQDUFTH2PvZRxj6wnYgV0ZXh0MTqIK0tJ +IGFtIHNvcnJ5LCBJIGNhbid0IGRvIHRoYXQK +=Zven +-----END PGP ARMORED FILE----- +' +sig_1lsls_invalid=' +-----BEGIN PGP ARMORED FILE----- + +kA0DAAIRN8q1H7eRA/gBrCdiBXRleHQxOogq9EkgYW0gc29ycnksIEkgY2FuJ3Qg +ZG8gdGhhdAqIPwMFADqIKvQ3yrUft5ED+BEC2joAoJaSaXOZEtSZqQ780HIXG77e +8PB7AJ4wCprmaFTO0fBaTcXDuEOBdAWnOawnYgV0ZXh0MTqIK0tJIGFtIHNvcnJ5 +LCBJIGNhbid0IGRvIHRoYXQKiD8DBQA6iCtLN8q1H7eRA/gRAi0DAJ9o2VDTqQeD +rrq0kJHNk0X4OnpNNgCffqCUtH60PslLE0A1BUx9j72UcY8= +=nkeu +-----END PGP ARMORED FILE----- +' +sig_lsls_invalid=' +-----BEGIN PGP ARMORED FILE----- + +rCdiBXRleHQxOogrS0kgYW0gc29ycnksIEkgY2FuJ3QgZG8gdGhhdAqIPwMFADqI +K0s3yrUft5ED+BECLQMAn2jZUNOpB4OuurSQkc2TRfg6ek02AJ9+oJS0frQ+yUsT +QDUFTH2PvZRxj6wnYgV0ZXh0MTqIK0tJIGFtIHNvcnJ5LCBJIGNhbid0IGRvIHRo +YXQKiD8DBQA6iCtLN8q1H7eRA/gRAi0DAJ9o2VDTqQeDrrq0kJHNk0X4OnpNNgCf +fqCUtH60PslLE0A1BUx9j72UcY8= +=BlZH +-----END PGP ARMORED FILE----- +' +sig_lss_invalid=' +-----BEGIN PGP ARMORED FILE----- + +rCdiBXRleHQxOogrS0kgYW0gc29ycnksIEkgY2FuJ3QgZG8gdGhhdAqIPwMFADqI +K0s3yrUft5ED+BECLQMAn2jZUNOpB4OuurSQkc2TRfg6ek02AJ9+oJS0frQ+yUsT +QDUFTH2PvZRxj4g/AwUAOogrSzfKtR+3kQP4EQItAwCfaNlQ06kHg666tJCRzZNF ++Dp6TTYAn36glLR+tD7JSxNANQVMfY+9lHGP +=jmt6 +-----END PGP ARMORED FILE----- +' +sig_slsl_invalid=' +-----BEGIN PGP ARMORED FILE----- + +iD8DBQA6iCtLN8q1H7eRA/gRAi0DAJ9o2VDTqQeDrrq0kJHNk0X4OnpNNgCffqCU +tH60PslLE0A1BUx9j72UcY+sJ2IFdGV4dDE6iCtLSSBhbSBzb3JyeSwgSSBjYW4n +dCBkbyB0aGF0Cog/AwUAOogrSzfKtR+3kQP4EQItAwCfaNlQ06kHg666tJCRzZNF ++Dp6TTYAn36glLR+tD7JSxNANQVMfY+9lHGPrCdiBXRleHQxOogrS0kgYW0gc29y +cnksIEkgY2FuJ3QgZG8gdGhhdAo= +=phBF +-----END PGP ARMORED FILE----- +' + + +for i in sig_sl_valid ; do + eval "(IFS=; echo \"\$$i\")" | ./gpg_dearmor >x + $GPG --verify x 2>/dev/null || error "valid is invalid ($i)" + linefeed +done +#for i in "$sig_11lss_valid_but_is_not" "$sig_11lss11lss_valid_but_is_not" \ +# "$sig_ssl_valid_but_is_not"; do +# echo "$i" | $GPG --dearmor >x +# $GPG --verify <x 2>/dev/null || error "valid is invalid" +#done + +for i in sig_1ls1ls_valid sig_ls_valid \ + sig_1lsls_invalid sig_lsls_invalid \ + sig_lss_invalid sig_slsl_invalid ; do + eval "(IFS=; echo \"\$$i\")" | ./gpg_dearmor >x + $GPG --verify <x 2>/dev/null && error "invalid is valid ($i)" + linefeed +done + + +resume_error
\ No newline at end of file diff --git a/tests/openpgp/pgp263-test.pub.asc b/tests/openpgp/pgp263-test.pub.asc new file mode 100644 index 000000000..53310d778 --- /dev/null +++ b/tests/openpgp/pgp263-test.pub.asc @@ -0,0 +1,14 @@ +Type Bits/KeyID Date User ID +pub 888/A50283F1 2001/11/08 pgp2.6.3-test-key + +-----BEGIN PGP PUBLIC KEY BLOCK----- +Version: 2.6.3a + +mQB8AzvqRosAAAEDeNMKLJMJQeGC2RG5Nec6R2mzC12N1wGLiYYJCsmSQd1Y8mht +A2Sc+4k/q5+l6GHtfqUR/RTCIIudAZUzrQVIMhHDKF+5de9lsE5QxQS1u43QGVCb +/9IYrOLOizYQ2pkBtD9LCrf7W2DccMEkpQKD8QAFE7QRcGdwMi42LjMtdGVzdC1r +ZXmJAIQDBRA76kaL3HDBJKUCg/EBAZMoA3Yqqdix6B2RAzywi9bKSLqwAFVL+MMw +W+BnYeBXF9u+bPpQvtyxgi0vx8F9r84B3HAhZNEjBWODF6vctIQhXhAhXIniDTSj +HNzQ/+nbWnebQn18XUV2SdM1PzMOblD+nISte7+WUfWzlD7YUJPkFPw= +=b498 +-----END PGP PUBLIC KEY BLOCK----- diff --git a/tests/openpgp/pgp263-test.sec.asc b/tests/openpgp/pgp263-test.sec.asc new file mode 100644 index 000000000..78992e3b7 --- /dev/null +++ b/tests/openpgp/pgp263-test.sec.asc @@ -0,0 +1,18 @@ +Type Bits/KeyID Date User ID +sec 888/A50283F1 2001/11/08 pgp2.6.3-test-key + +-----BEGIN PGP SECRET KEY BLOCK----- +Version: 2.6.3a + +lQGdAzvqRosAAAEDeNMKLJMJQeGC2RG5Nec6R2mzC12N1wGLiYYJCsmSQd1Y8mht +A2Sc+4k/q5+l6GHtfqUR/RTCIIudAZUzrQVIMhHDKF+5de9lsE5QxQS1u43QGVCb +/9IYrOLOizYQ2pkBtD9LCrf7W2DccMEkpQKD8QAFEwADd0Kk5aeyFM3zbPgfikkE +7iFg9h2LG3nARmA4wAnCZaQ3CS5zRHCdXOf5KLkm6xFza1yMat4iWx6ULvuuNpIc +RmkHccyXYkRi3Hvacd5A9VCNw1UKtCdaCKgacsfplU0s1xYWGZd4J8Jg8boSfW5W +gwG8Dc9R20HHno8uD2vfr5rg8ElWvbFyJI/j4eCVAd+NYAGNvB8I3VP38IIYcavh +YYcGjrpxbGVRybsBvA9IJltpGaVulxwpeCp5NecCGgoAUsN4Ktf42Pg7HXDlQL6r +Xs/YggMztj4NzEgBHXAOLShdKKhDAbEByVSKXZD9A8J+RejXBl6VbuJmD/5qOvph +GAPKS3ahPDj8438HyD7yIDLYYVRKfxjWHLubc46Pgui0EXBncDIuNi4zLXRlc3Qt +a2V5 +=l/aV +-----END PGP SECRET KEY BLOCK----- diff --git a/tests/openpgp/plain-1-pgp.asc b/tests/openpgp/plain-1-pgp.asc new file mode 100644 index 000000000..9a83dcfa0 --- /dev/null +++ b/tests/openpgp/plain-1-pgp.asc @@ -0,0 +1,27 @@ +This is an encrypted version of plain-1 for the PGP test key +0xCB879DE9 using 3DES. + +-----BEGIN PGP MESSAGE----- +Version: GnuPG v1.3.5-cvs (GNU/Linux) + +hM4DW3oC8MuHnekQAv0U6qlDAA64QS/oZJErr1J77m5Dh7IFen3mAcwOxvL/POqS +HQWTFcuFT4LH9asSWgRe6DebJGfscMjMqNPAkhEJtKQQ2jEesn2Bon6SMwah7vkD +9Zap7WKHRlnB/Da1/xQC/ispXY7e5tuejnzoNSAOWFpBn354nvkKGaCfMRNuz3R2 +HljH+gXKRa00n2dPmvX9Mr8AI0Q+FoEI2/YW+6aUxmv8b0c2dP6HcL6HUu0Ro2Nl +RJNPfYXP20EL/Xrv8LN0Ksnp3YKTWrz5gQKNr3DH5pn1PjFqAKz4JD6rQBpnlh1c +03gLB1OAJWA6+/QNaEQV451GBZW3ul10R/6621/kk0Isdxn/htlD4Jl/jAvFdlQW +ULBu1HorZZ5X/IMuMRFwSQkx+H8i0zq+LGr8+rLFVTRuXBrgpeTLWs/f35DDblPp +jtPGSs1qql98PfOV1tAr16rGRLAAyNWEgi3yZWUGgq5dfFnRbJX1hrj9waQmq1g0 +mn1oB9Ig708xSZqcfFVFNpvIB7nmbFF/WaMnqfL3XmgTe8whKB/f/XYhg+W2d57h +EmTcAlC1N6IHY8/7YqtnjitavTIUsi0hPldX0tvrjsaZ7ppSma2epRJhx47jIFjw +wXOEByZE+K3pyTSN8KJxParDsqrTWFrL0t8az9W8lWG7YYsxUxk9cwRo5PyEko1M +kAKrbDMb+02Iw35yeuxFY33dl7KqpaWy43ksX/ROxX4S0InQywaQejXyt5A1cJN1 +t+G0aKdRp40MDKtOkZfFGlUSFZIhB0dxKVfSKJE/SIeYZzROTuyCNe/2wwufxgpa +uztUf5ipVnINupiztWGw5c5Wp40ptQ/0K4/35KrZhMoFGR9DtImAPpZocuiFdJDt +uqqapxGfJ876S4hFjRAkHSNRsAySul9zFLnIJ+Smk5xsvQZK4yjDwZfSs9b7WPKg +7NCxl5bF5dIbWRYdRBNjHQ4m3LyYmqKzQqALSYT54/9O35B7rb1fOB2SFIuME0QI +5XQq9QsH/f5rW8U6Ixzw1582B8fO1TMRhCqMyXozmsBJoWdCIQTQiVNyrbgLi+ss +wKiKq4AymLXFMSpI4TOCc+rKiAdMpLbNO8Ndox5hZEGz+mqg84cgC/rkJc/P03KR +uo0+rb5eSfJw9t+uzBXDmFHynayj0CB8wW9iwXknpdlHDo1z +=7Otr +-----END PGP MESSAGE----- diff --git a/tests/openpgp/plain-1.asc b/tests/openpgp/plain-1.asc new file mode 100644 index 000000000..f62fb15df --- /dev/null +++ b/tests/openpgp/plain-1.asc @@ -0,0 +1,26 @@ +-----BEGIN PGP MESSAGE----- +Version: GnuPG v1.3.5-cvs (GNU/Linux) + +hQEOA6urKKJHvid1EAQA0MchGc7vZsjUgxdII4lo/2jRDesMmLDN4U0uOgExvyhD +u1OtQBJF8iHgNdDEf8/R3GWhRE94IpVwLqzKTqfVmyKIFd80/Qe4h37TUPpEf8Ex +f7WaIBk/9OSDNKOkCwZ5OH9xGaorhBwYiTNJlEEGv5zcDte9ZoLO7WhWFfHp3b0E +AJYk/tf3oV4sJSn8AbUa8UC2tAdpNM1Lx+UEuCtxevYRpWeDVDok7/xuaa/wcb39 +lKyhUV+FBUH++k59K4GVqykOz02hmFl97O+4bAldgP6cVTm0Gh7jwMcJANzhLW/O +MR5birB+HPKOotMIfhggzxsAt6ESrviIlknkGqwKXWog0ukB/npOqQdu1GmvJqoC +k6ElA6xZPY5HTF/JLKlLXFfIIKLeuyckKwGDkVNFE7JYPW+dfxcGH9z1KXaNNllY +V4OKGQh3+gMaoJSY2X7PsmjC4fvi3g6rr360ATr5f82Mr8GPa3x21XLdIFZ04vTe +yE3kwdcarkiT1QQLnOXk/yRBxJwiA5loL9crVdC2WyOV3B3DG33/yas8krw4BYWw +DzAgxNtZR4MQXcj83WwoflMo43dYUq3Pk7ZnzKN04O8m9w0gxVxCpXu4ds9emMdJ +WS4eNTPUOnzeWttkfYcd3SarK6COi9iBosFT2QF80FwDSlH3XdEo7rD1j6WJ5GeX +RbHDvIm9g0xB23S7jmtfdqIHndvPKLmwW2B1VC1mbjcDUo6pyUb31GBd1zFVhT69 +ijhiEwBlr8uWxROdwJd/7IVIB/RYHLr5P3M8p08hdEdS1IMQbNEE4Y25fRdcc6g8 +fVEAExbG01K1EJhRLxoHzgnAkxDTV2HSwlqbFvKEzUfE+rMHApmSX2lfMvKgueYz +JpA7nxuf79Wk17bjNvuVQwokhXpzw7FyPPdD7h4Z30LW0ozvSVgs2tigWCAysIKB +3ZIolchqBoj0ddJgbPXrx09r1oCckEmdj1KtZsci9m+CFA8d22uxXBec0HkEHZpr +EHlqEZfNTmqowoDtJ8KT+S8VPsALEyDnrqm3s4i44OwgvsPiKOST1xwk6lIJ5isu +fO76RHTQ2jc8z7+sKyNffVugfjYVRj54/8Gj34QkrVo/42rlvg398tpbAbWuNq8w +PM//M6eVD4IRDYEGrGOk7prd9mgdbWnOWpasirhr41kePu2vsrIUkJWHmOgdMQDH +cSSzI8C5NpafROHAhMsUymcJ5dKksvPubh5IAdgtH+m6yDnNUJT8s6WV1f1RpSsQ +L/n3dhti76l0XtfZ7aST8j46B1JPNDx8+r6Xl9IUbSU= +=xK46 +-----END PGP MESSAGE----- diff --git a/tests/openpgp/plain-1o.asc b/tests/openpgp/plain-1o.asc new file mode 100644 index 000000000..973b29395 --- /dev/null +++ b/tests/openpgp/plain-1o.asc @@ -0,0 +1,28 @@ +-----BEGIN PGP ARMORED FILE----- +Version: GNUPG v0.3.4 (GNU/Linux) +Comment: Get GNUPG from ftp://ftp.guug.de/pub/gcrypt/ +Comment: Use "gpgm --dearmor" for unpacking + +PCEtLSBEaWVzIGlzdCBTZWl0ZSAzLCBkb3J0IGlzdCBrZWluZSBTZWl0ZW56YWhsIGFuZ2Vn +ZWJlbiwKICAgICBvYmVuIHJlY2h0cyBpc3Qgd2llZGVyIGRlciBTdGVtcGVsIHZvbiBtZWlu +ZW0gT3BhIHp1IGZpbmRlbiAtLT4KCjxzZWN0MT5OYW1lIDxxPkdyb98tQmFydGxvZmY8Lz4K +CjxwPgpEZXIgTmFtZSA8cS9CYXJ0bG9mZi8gaXN0IHNjaHdlciB6dSBkZXV0ZW4uIE1hbiBo +YXQgdmllbGUgTXV0bWHfdW5nZW4KYW5nZXN0ZWxsdCwgdm9uIGRlbmVuIG1hbiBhYmVyIGJp +c2xhbmcga2VpbmUgZWluemlnZSBhbHMgdW5iZWRpbmd0CnJpY2h0aWcgZXJrbORyZW4ga2Fu +bi4KPGZvbnRpbmZvIHJlbT0ibWl0IExlZXJ6ZWljaGVuIGdlc2NocmllYmVuIj5Vcmt1bmRs +aWNoPC8+IHdpcmQgZGFzCkRvcmYgYmlzIHp1ciBSZWZvcm1hdGlvbiBzdGV0cyA8cS9CYXJ0 +b3JmLyAoYW5ubyAxMjUzKSB1bmQKPHEvQmFyZG9yZi8gKDEzMDYsIDEzMTgsIDEzMjksIDE0 +MjkpIGdlbmFubnQgdW5kIGRhc18gc293b2hsIEtsZWluLQp3aWUgR3Jv32JhcnRsb2ZmLiBF +cnN0IDE1ODYgaW0gQmlzY2hvZnNzdGVpbmVyIEp1cmlzZGlrdGlvbmFsYnVjaApoZWnfdCB1 +bnNlciBEb3JmIDxxL0JhcnR0ZWxvZmYvIHVuZCBzbyBhdWNoIGluIGRlciDkbHRlc3RlbiBu +b2NoCnZvcmhhbmRlbmVuIEtpcmNoZW5yZWNobnVuZyB2b20gSmFocmUgMTY1MS4gTkFjaCBk +ZW0gSmFocmUgMTcwMCB3aXJkCmluIGRlbiBVcmt1bmRlbiBiZWdvbm5lbiwgZGVuIHZvbGxl +biBOYW1lbiA8cS9Hcm/fLUJhcnRsb2ZmLyB1bmQKPHEvS2xlaW4tQmFydGxvZmYvIHp1IHNj +aHJlaWJlbi4KLS0tLS0tLS0tLS0tLS0tLSBbd2VnZW4gZGFzaGVkIGVzY2FwZWQgdGV4dF0K +PHA+Ck5pbW10IG1hbiBhbiwgZGHfIGRpZSB1cmt1bmRsaWNoZSwg5Gx0ZXN0ZSBCZXplaWNo +bnVuZyBCYXJ0b3JmIGRpZQp1cnNwcvxuZ2xpY2hlIGlzdCB1bmQgbmljaHQgZGllIG11bmRh +cnRsaWNoZSBCYXJ0bG9mZiwgc28ga/ZubnRlIGRlcgpOYW1lIGd1dCBnZWRldXRldCB3ZXJk +ZW4gYWxzIERvcmYgYW4gZGVyIDxxL0JvcmRlLyBvZGVyIGFtIFJhbmRlCm9kZXIgYW4gZGVy +IEdyZW56ZSBlbnR3ZWRlciBkZXMgV2FsZGVzCg== +=m1k/ +-----END PGP ARMORED FILE----- diff --git a/tests/openpgp/plain-2.asc b/tests/openpgp/plain-2.asc new file mode 100644 index 000000000..5a774a634 --- /dev/null +++ b/tests/openpgp/plain-2.asc @@ -0,0 +1,31 @@ +-----BEGIN PGP MESSAGE----- +Version: GnuPG v1.3.5-cvs (GNU/Linux) + +hQEOA6urKKJHvid1EAP/aYXFOkxPzbBB0SWtyX+yyvZso8i1WJS3pzrHNXcXQSQx +xOAfmlCiuXYrjEzlyDAn7k7RLAhUB/ffI58HnbkQ7btWujrHig/V1tQ0j5igR85M +3y2/msWu2c2pyeZnx29LzeoJ2aMVTbMObszlG+TNOuhCNn4unvbShrkFjNK5fi8E +AIHiavE77ZPfcaUrXp6FJ6OuhbnJQ8y8CVpH++ddgU6xXK1vByMSsYqiOjfq08gV +MzqT1eMVvKhSjl3R6Ktl7j+ErYM4KuIofIZsKc8M3JnoTSrLqWSEBq+DEiaSI58i +SMJfzxfKA84bpJyLIjp4bjRIXveYoX8UjEnSNr3xuDIq0ukBoVe6Bx8lBActcwE+ +kE7EffSBHUmnm8cvwZan+Ms8t9p9aQEzBxV/LfEXZyk36lK35zCH188iJR+tt9zs +rNubkRuOjq9jAcBtrvgjTTO91Ru7z4RCYeMfnX9AauJZFShBNYN46GTIwqMWE9vq +B/IYFH9/L2nufcrDQ6u5WxJo0y2FoPqVS4RKEZ4FlKnlT2Op0X1k9w+1nWTtKwQx +fPsB+YRSKmVbZOXDeKAIVEyGHgR1Hj6pbo/IeHSJ2DJt5OFu6eLQYjxYjM7BPjPD +Gn+lTUvqw5ykYpCcnvpEx25+qHh5HI11Hi0sLKzvB92hhsQ7+lU2D+iAzsMJKdwE +u2bCnrZokzZwDBy6NISQ+hoc6NPPezQM4FLN0BB752fa9DYMQo5nEGfPUM7fv51A +nUdGOmaDVWY54GQxiYzl0JAT41sQSYlVHcWBCGNAm064y+tsHVjDYcf5uze/3Iuw +m/IbRGLBT7x+j2OqMX30yXoeHCg0/M/2c6vIzhdHEsJjTbTr+M4bMii/mB5kSo/7 +x5R14Lr0mwnPNDFHG2egqd5uL8985+5BENm7q0pQHKGM5NxkjVSWCpzRgKcSEq5A +x4Q2HbhEJNP6ZonnZkDmGM52Eq62eaR7t8+k9px35osfiTiClmVrjsTgl5Kvatk0 +oL1aYEwp8OtavoSwidUTk+Xb+cEE09P5bnCFs5Js0e5wdo+/izJ6iBuF+PndTh4i +4ppFmt8/GZ63MKBJu4CZE7QJMVAcmmCrsGRONP2JVgmyaBjrIl5xk9FPXQVY0AJx +gl3/jO/QFHYs+dlrQ3aqg8Mm0eZyLmZEYjoNibD8PW0keYiVfTF7EGl4jS2sAboc +AOzbuABa+30vIjJRWeW5UdTcLyNK7B2qWk6dqpRn9ps3cwCWUiTIcIRgot4PY+3M +8BL4smyZIP1Fmz/woL7gSVIaJHMExHjYPyRlfo+6Vfy3hh3zdiB9e5xA8QRFKgUb +Px5ShU5bBykfvFBJjgKU1XLBKqdklaudf3+v8F3LPIyuO6vTYzOIU9UKAHy9CrA2 +kAZ8kgHBTtAjmKuJjASBCZHPepq0G9SaRDQI5g4DXx0LXPX3y5xkwVI6kd0QmsMF +UU4ij/xjzIPN/AxBgQI8HKk56FnaX0JKoHm7mqWa+1TzbuvJjio4J/IN9XXzVqb1 +YL+mkx607hdW9oJltXLO5eio0pb12v/0YXAQlsrlJJNPCUW5hYFv/vH1rHzR98xx +nx4PXElm8VUuhKDxdVi9Ipo8fL9Amu3PwYonzOck3R2W4wwlmcopVQQ= +=Ng8B +-----END PGP MESSAGE----- diff --git a/tests/openpgp/plain-2o.asc b/tests/openpgp/plain-2o.asc new file mode 100644 index 000000000..562e5f06e --- /dev/null +++ b/tests/openpgp/plain-2o.asc @@ -0,0 +1,36 @@ +-----BEGIN PGP ARMORED FILE----- +Version: GNUPG v0.3.4 (GNU/Linux) +Comment: Get GNUPG from ftp://ftp.guug.de/pub/gcrypt/ +Comment: Use "gpgm --dearmor" for unpacking + +Cgo8c2VjdD5Wb3J3b3J0CjxwPgpEZXIgV2VydCBlaW5lciBPcnRzY2hyb25payBpc3Qgb2Zm +ZW5iYXIgdW5kIGJlZGFyZiBrZWluZXIgRXL2cnRlcnVuZy4KTWl0IEF1c2JydWNoIGRlcyBX +ZWx0a3JpZWdlc18sIGlubWl0dGVuIGRlciBnZXdhbHRpZ2VuIEdlc2NoZWhuaXNzZSwgZvxo +bHRlCmRlciBLbGVydXNfIHVuc2VyZXNfIEVpY2hzX2ZlbGRlc18gZGFzXyBtZWhyIHdpZSBm +cvxoZXIgdW5kIHNvCmVyc3Rhcmt0ZSBkYXNfIFN0cmViZW4sIGVpbmUgc29sY2hlIE9ydHNf +Z2VzY2hpY2h0ZSB6dSBzY2FoZmZlbiwgdW0KdW5zZXJlbiBOYWNoa29tbWVuIHp1IGJlcmlj +aHRlbiwgd2FzXyBhdWNoIGRpZSBrbGVpbnN0ZW4gRPZyZmVyIGluCmRlciBncm/fZW4gWmVp +dCBnZWxlaXN0ZXQsIGVybGVidCB1bmQgZXJsaXR0ZW4gaGFiZW4uCjxwPgpVbmQgc28gYmVn +YW5uIGF1Y2ggaWNoIGltIERlemVtYmVyIDE5MTQsIGRlbiA/Pz8/Pz8/Pz8KU3RvZmYsIHdv +IGltbWVyIGljaCBpaG4gYXVjaCBudXIgc28gc3DkcmxpY2ggZmluZGVuIGtvbm50ZSwgenUK +c2FtbWVsbiwgaWNoIGJlZnJhZ3RlIHp1buRjaHN0IGVtc2lnIGRpZSDkbHRlc3RlbiBMZXV0 +ZSwKZHVyY2hmb3JzY2h0ZSBzb2Rhbm4gZGFzIGdhbnplIFBmYXJyYXJjaGl2LCBkYXMgU2No +dWx6ZW5hcmNoaXYKYmVpZGVyIFBmYXJyZPZyZmVyLCBkYXMgS29tbWlzc2FyaWF0c19hcmNo +aXYgenUgSGVpbGlnZW5zdGFkdCwKZW5kbGljaCBhdWNoIDE5MTYgZGFzIFN0YWF0c19hcmNo +aXYgenUgTWFnZGVidXJnLiBTZWxic3R2ZXJzdORuZGxpY2gKYXJiZWl0ZXRlIGljaCBhdWNo +IGRpZSBlaW5zY2hs5GdpZ2UgTGl0ZXJhdHVyIGR1cmNoLiBHYXIgdmllbGUgWmVpdAp1bmQg +TfxoZSBoYXQgZXNfIGdla29zdGV0IHVtIG5hY2ggbWVociBhbHMgOCBKYWhyZW4gZGllIE9y +dHNjaHJvbmlrIHZvbgpHcm/fYmFydGxvZmYgdW5kIHZvbSBGaWxpYWxkb3JmIFdpbGJpY2gg +Z2Vzb25kZXJ0IHp1IHNjaGFmZmVuLgo8cCB2c3BhY2U9IjJleCI+CjxiZj5Hcm/fYmFydGxv +ZmYsPC8+IGRlbiAyMy4gTeRyeiAxOTIzLgo8cCB2c3BhY2U9IjNleCIgYWxpZ249cmlnaHQ+ +CjxiZi9OaWtvbGF1cyBH9nJpbmcsLyBQZmFycmVyLgo8L3A+Cgo8IS0tIEhpZXIgZm9sZ3Qg +ZWluIFN0ZW1wZWwgdm9uIG1laW5lbSBPcGE6CgkgIFJ1ZC4gS29jaAogICAgIEdyb99iYXJ0 +bG9mZi9FaWNoc2ZlbGQKCUFuZ2VyIDE2MQotLT4KPCEtLSBGSVhNRTogaGllciBrb21tdCBl +aW5lbiBaaWVybGluaWUgLS0+Cgo8cCB2c3BhY2U9ZmlsbD4gPCEtLSBEZXIgUmVzdCBrYW0g +YW0gRW5kZSBkZXIgU2VpdGUgLS0+CjxwIGFsaWduPWNlbnRlcj4gTGl0ZXJhdHVyOiA8L3A+ +CjEpIEpvaC4gV29sZjogUG9saXRpc2NoZSBHZXNjaGljaHRlIGRlcyBFaWNoc2YuIEf2dHQu +IDE3OTIgdW5kCkz2ZmZsZXIgMTkyMS4gMikgSy4gR2VzY2hpY2h0ZSwgV29sZiAxODE2IEf2 +dHQuICAzKSBLbmllYjogR2VzY2guCmRlciBSZWYuIHUuIEdlZ2VucmVmPz8/Cgo8IS0tIEZJ +WE1FOiBEZXIgUmVzdCBmZWhsdCBub2NoIC0tPgoKCgoKCgoKCjwvc2VjdD4K +=9nnj +-----END PGP ARMORED FILE----- diff --git a/tests/openpgp/plain-3.asc b/tests/openpgp/plain-3.asc new file mode 100644 index 000000000..b2206aee5 --- /dev/null +++ b/tests/openpgp/plain-3.asc @@ -0,0 +1,13 @@ +-----BEGIN PGP MESSAGE----- +Version: GnuPG v1.3.5-cvs (GNU/Linux) + +hQEOA6urKKJHvid1EAQAreXx68NPUPpiNhqRyM//Y97N8hX5iAWq3WxXTa8D6Hy9 +81Jy2wI4IeDhHIoWuXMIX2oVL//V1+LyLkrF/tutBVvqct0TUDUWqb4Ydpfk2l5j +FfSybWW1fS4D1e0KVB3Lfj2Y4cCoT/+zyq7jUKQE++qNefPBzeaRWY4qeI6xXF8E +AMj01HPe0ZwIBWqiIYv91Q7rGzEZm0ROPilgSQjUvCdsNQGhZpFGTl6uMSU0lmp8 +SD2EKv3xGeo2nMPy/Xp4JoYAMW+fjJh+wM6uT84nJgCVaeWyR7HAfF1U4rzqz7DF +amPozuwuZiyjoo/wB1irZSl90t5Oa69oMesZtGMvwBN10mMBM0TotT4gjgviv5uY +kLjD7DM79xy0drptNypmcVcjnDunM6bSEhTyq/fahdaULTYcwSOTXVMyesNpmLCb +ziayleyuSaXPxIqWTgSfkab/W2FGWZvbexYaSaWXmDqsyzs81o0= +=JDKF +-----END PGP MESSAGE----- diff --git a/tests/openpgp/plain-3o.asc b/tests/openpgp/plain-3o.asc new file mode 100644 index 000000000..409b9c2e4 --- /dev/null +++ b/tests/openpgp/plain-3o.asc @@ -0,0 +1,10 @@ +Stored by G10, because diff/patch have problems with +files not having a trailing LF - and this one has none. + +-----BEGIN PGP ARMORED FILE----- +Version: G10 v0.2.6a (Linux) +Comment: This is an alpha version! + +RGllcyBpc3QgZWluZSBlaW5mYWNoZSBaZWlsZSBvaG5lIExGIGFtIEVuZGUu +=ZQ6m +-----END PGP ARMORED FILE----- diff --git a/tests/openpgp/pubdemo.asc b/tests/openpgp/pubdemo.asc new file mode 100644 index 000000000..d550f1af7 --- /dev/null +++ b/tests/openpgp/pubdemo.asc @@ -0,0 +1,566 @@ +26 demo keys: + +pub 1024D/68697734 1999-03-08 Alpha Test (demo key) <alpha@example.net> +uid Alice (demo key) +uid Alfa Test (demo key) <alfa@example.net> +sub 1024g/46A871F8 1999-03-08 +pub 1024D/1AFDAB6C 1999-03-08 Charlie Test (demo key) <charlie@example.net> +sub 1024g/BC43DA60 1999-03-08 +pub 1024D/FAEF6D1B 1999-03-08 Echo Test (demo key) <echo@example.net> +uid Eve (demo key) +uid Echelon (demo key) +sub 1024g/7272144D 1999-03-08 +pub 1024D/8FC282E6 1999-03-08 Golf Test (demo key) <golf@example.net> +sub 1024g/9DCAD354 1999-03-08 +pub 1024D/04259677 1999-03-08 India Test (demo key) <india@example.net> +sub 1024g/61F76C73 1999-03-08 +pub 1024D/43C2D0C7 1999-03-08 Kilo Test (demo key) <kilo@example.net> +sub 1024g/9AF64D02 1999-03-08 +pub 1024D/A9E3B0B2 1999-03-08 Bravo Test (demo key) <bravo@example.net> +uid Bob (demo key) +sub 1024g/E29BA37F 1999-03-08 +pub 1024D/EB9DC9E6 1999-03-08 Delta Test (demo key) <delta@example.net> +sub 1024g/B0C45424 1999-03-08 +pub 1024D/7372E243 1999-03-08 Foxtrot Test (demo key) <foxtrot@example.net> +sub 1024g/EE45198E 1999-03-08 +pub 1024D/34C6E3F1 1999-03-08 Hotel Test (demo key) <hotel@example.net> +sub 1024g/D622AD0A 1999-03-08 +pub 1024D/D2699313 1999-03-08 Juliet Test (demo key) <juliet@example.net> +sub 1024g/35F8F136 1999-03-08 +pub 1024D/B79103F8 1999-03-08 Lima Test (demo key) <lima@example.net> +sub 1024g/FE56350C 1999-03-08 +pub 1024D/BE5CF886 1999-03-08 Mike Test (demo key) <mike@example.net> +uid Mallory (demo key) +sub 1024g/4F31EAE8 1999-03-08 +pub 1024D/30CEC684 1999-03-08 November Test (demo key) <november@example.net> +sub 1024g/8B70E472 1999-03-08 +pub 1024D/6D9732AC 1999-03-08 Oscar Test (demo key) <oscar@example.net> +sub 1024g/2681619F 1999-03-08 +pub 1024D/3FF13206 1999-03-08 Papa test (demo key) <papa@example.net> +sub 1024g/63330D9C 1999-03-08 +pub 1024D/3C661C84 1999-03-08 Quebec Test (demo key) <quebec@example.net> +sub 1024g/A029ACF4 1999-03-08 +pub 1024D/777FBED3 1999-03-08 Romeo Test (demo key) <romeo@example.net> +sub 1024g/11D102EA 1999-03-08 +pub 1024D/A3AE3EA1 1999-03-08 Sierra Test (demo key) <sierra@example.net> +sub 1024g/0F1B50B4 1999-03-08 +pub 1024D/85A81F38 1999-03-08 Tango Test (demo key) <tango@example.net> +sub 1024g/101C0402 1999-03-08 +pub 1024D/653244D6 1999-03-08 Uniform Test (demo key) <uniform@example.net> +sub 1024g/5522BDB9 1999-03-08 +pub 1024D/61F04784 1999-03-08 Victor Test (demo key) <victor@example.org> +sub 1024g/07287134 1999-03-08 +pub 1024D/EC67DBDE 1999-03-08 Whisky Test (demo key) <whisky@example.net> +sub 1024g/FD6E27F6 1999-03-08 +pub 1024D/567FB34A 1999-03-08 XRay Test (demo key) <xray@example.net> +sub 1024g/41E408BE 1999-03-08 +pub 1024D/4B11B25F 1999-03-08 Yankee Test (demo key) <yankee@example.net> +sub 1024g/F7B080AD 1999-03-08 +pub 1024D/54ACD246 1999-03-08 Zulu Test (demo key) <zulu@example.net> +sub 1024g/A172C881 1999-03-08 + +-----BEGIN PGP PUBLIC KEY BLOCK----- +Version: GnuPG v0.9.3 (GNU/Linux) +Comment: For info see http://www.gnupg.org + +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 +=1N8S +-----END PGP PUBLIC KEY BLOCK----- diff --git a/tests/openpgp/pubring.asc b/tests/openpgp/pubring.asc new file mode 100644 index 000000000..a091e0e63 --- /dev/null +++ b/tests/openpgp/pubring.asc @@ -0,0 +1,720 @@ +-----BEGIN PGP PUBLIC KEY BLOCK----- +Version: GnuPG v1.3.5-cvs (GNU/Linux) + +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 +wRjlQVX31vkPxZDR2UBoHjBYDg== +=XVtd +-----END PGP PUBLIC KEY BLOCK----- diff --git a/tests/openpgp/pubring.pkr.asc b/tests/openpgp/pubring.pkr.asc new file mode 100644 index 000000000..e8eaabb93 --- /dev/null +++ b/tests/openpgp/pubring.pkr.asc @@ -0,0 +1,28 @@ +This is a test pubring generated by pgp 5 beta + +Type Bits KeyID Created Expires Algorithm Use +sec+ 768 439F02CA 1998-03-17 ---------- DSS Sign and Encrypt +sub 768 CB879DE9 1998-03-17 ---------- Diffie-Hellman +uid pgp5 test <pgp5@dev.null> + + +-----BEGIN PGP ARMORED FILE----- +Version: GNUPG v0.2.13a (Linux) +Comment: This is an alpha version! +Comment: Use "gpgm --dearmor" for unpacking + +mQFCBDUOrE4RAwDbbxWAbWsheUJprK6VryMTpwDiYwMfL+92nrHqSfPqlpMWgDTia8qnpRSXbyEm +Sppp/6/Ygp+N3n32Kznq7PjHXiuWLlZGvZMtzmvaMA17y0GY6oLBxS7rhASXIKa9hEUAoP+KBFly +qNMdsK8j+ZO0A8rnImGrAwC1ddDme5iZFkTEWHhrtU97sEu2GDkSQB8HdX8CoRcrOz/B2WliF6qf +BKhcZPFVBIhKNzjTfY7SEYAZk2zcsCm8elnwSLaGEzxKFNFBqKDNXP+a35spcqsHSGzDVw4VuKMD +AJNnAP6skpHlhVAmecLZT9eRzVoOq1ivUIntK2Mh47qsL74q6BBwz2sviPU2Y3pDlbb6Ed0qJAXv +dCT24hlfoGoXzkoDInkPJTJeL0gCnwmQPjvXFFd71Cvg5LaL4lIQLbABh7QZcGdwNSB0ZXN0IDxw +Z3A1QGRldi5udWxsPrABA4kASwQQEQIACwUCNQ6sTgQLAwECAAoJENY0E25DnwLKxIoAoPSyM/Mw +BogpyMU5YY+Sj74k3UIfAJ0RopQa8ciickDVzoSVPrGysrnOkLABZ7kAzQQ1DqxWEAMA/wVrlNsP +qTxWZbUiMrUN8MjTFR2xUhuTw3cdvRgiVPUT/q1l1+I3CpopVBx/XuAkg5sHB80zc6pZg652YFV3 +dLoTceS7ridb5k23sHa2hZGCeTo6AdxIOy53giCPDP9FAAICAv9Oh5/OVxUqI+6hsp9ccOEhRA9N +8aJzYDPjvCQyhgej2P1kTsBZqWIx0/PiMvIt+qqhT2YfyD68mHIBztScAXZKTnjroUPKl0+bkX09 +NbdyqojAkzhaCRKUzwnaHEfhi2WwAYeJAD8DBRg1DqxW1jQTbkOfAsoRAnaPAJ0Z/k6Y2ypgDhXo +qBLeW7Lq/AKYEACeLTod6Nt117DkqDz9epmIqwWOE1ewAWc= +=6BrN +-----END PGP ARMORED FILE----- diff --git a/tests/openpgp/seat.test b/tests/openpgp/seat.test new file mode 100755 index 000000000..72ab27f41 --- /dev/null +++ b/tests/openpgp/seat.test @@ -0,0 +1,11 @@ +#!/bin/sh + +. $srcdir/defs.inc || exit 3 + +for i in $plain_files ; do + echo "$usrpass1" | $GPG --passphrase-fd 0 --always-trust -seat \ + -r two -o x --yes $i + $GPG -o y --yes x + cmp $i y || error "$i: mismatch" +done + diff --git a/tests/openpgp/secdemo.asc b/tests/openpgp/secdemo.asc new file mode 100644 index 000000000..343453c45 --- /dev/null +++ b/tests/openpgp/secdemo.asc @@ -0,0 +1,737 @@ +26 demo keys (passphrase is "abc"): + +sec 1024D/68697734 1999-03-08 Alpha Test (demo key) <alpha@example.net> +uid Alice (demo key) +uid Alfa Test (demo key) <alfa@example.net> +ssb 1024g/46A871F8 1999-03-08 +sec 1024D/1AFDAB6C 1999-03-08 Charlie Test (demo key) <charlie@example.net> +ssb 1024g/BC43DA60 1999-03-08 +sec 1024D/FAEF6D1B 1999-03-08 Echo Test (demo key) <echo@example.net> +uid Eve (demo key) +uid Echelon (demo key) +ssb 1024g/7272144D 1999-03-08 +sec 1024D/8FC282E6 1999-03-08 Golf Test (demo key) <golf@example.net> +ssb 1024g/9DCAD354 1999-03-08 +sec 1024D/04259677 1999-03-08 India Test (demo key) <india@example.net> +ssb 1024g/61F76C73 1999-03-08 +sec 1024D/43C2D0C7 1999-03-08 Kilo Test (demo key) <kilo@example.net> +ssb 1024g/9AF64D02 1999-03-08 +sec 1024D/A9E3B0B2 1999-03-08 Bravo Test (demo key) <bravo@example.net> +uid Bob (demo key) +ssb 1024g/E29BA37F 1999-03-08 +sec 1024D/EB9DC9E6 1999-03-08 Delta Test (demo key) <delta@example.net> +ssb 1024g/B0C45424 1999-03-08 +sec 1024D/7372E243 1999-03-08 Foxtrot Test (demo key) <foxtrot@example.net> +ssb 1024g/EE45198E 1999-03-08 +sec 1024D/34C6E3F1 1999-03-08 Hotel Test (demo key) <hotel@example.net> +ssb 1024g/D622AD0A 1999-03-08 +sec 1024D/D2699313 1999-03-08 Juliet Test (demo key) <juliet@example.net> +ssb 1024g/35F8F136 1999-03-08 +sec 1024D/B79103F8 1999-03-08 Lima Test (demo key) <lima@example.net> +ssb 1024g/FE56350C 1999-03-08 +sec 1024D/BE5CF886 1999-03-08 Mike Test (demo key) <mike@example.net> +uid Mallory (demo key) +ssb 1024g/4F31EAE8 1999-03-08 +sec 1024D/30CEC684 1999-03-08 November Test (demo key) <november@example.net> +ssb 1024g/8B70E472 1999-03-08 +sec 1024D/6D9732AC 1999-03-08 Oscar Test (demo key) <oscar@example.net> +ssb 1024g/2681619F 1999-03-08 +sec 1024D/3FF13206 1999-03-08 Papa test (demo key) <papa@example.net> +ssb 1024g/63330D9C 1999-03-08 +sec 1024D/3C661C84 1999-03-08 Quebec Test (demo key) <quebec@example.net> +ssb 1024g/A029ACF4 1999-03-08 +sec 1024D/777FBED3 1999-03-08 Romeo Test (demo key) <romeo@example.net> +ssb 1024g/11D102EA 1999-03-08 +sec 1024D/A3AE3EA1 1999-03-08 Sierra Test (demo key) <sierra@example.net> +ssb 1024g/0F1B50B4 1999-03-08 +sec 1024D/85A81F38 1999-03-08 Tango Test (demo key) <tango@example.net> +ssb 1024g/101C0402 1999-03-08 +sec 1024D/653244D6 1999-03-08 Uniform Test (demo key) <uniform@example.net> +ssb 1024g/5522BDB9 1999-03-08 +sec 1024D/61F04784 1999-03-08 Victor Test (demo key) <victor@example.org> +ssb 1024g/07287134 1999-03-08 +sec 1024D/EC67DBDE 1999-03-08 Whisky Test (demo key) <whisky@example.net> +ssb 1024g/FD6E27F6 1999-03-08 +sec 1024D/567FB34A 1999-03-08 XRay Test (demo key) <xray@example.net> +ssb 1024g/41E408BE 1999-03-08 +sec 1024D/4B11B25F 1999-03-08 Yankee Test (demo key) <yankee@example.net> +ssb 1024g/F7B080AD 1999-03-08 +sec 1024D/54ACD246 1999-03-08 Zulu Test (demo key) <zulu@example.net> +ssb 1024g/A172C881 1999-03-08 + +-----BEGIN PGP PRIVATE KEY BLOCK----- +Version: GnuPG v0.9.3 (GNU/Linux) +Comment: For info see http://www.gnupg.org + +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 +=P9+G +-----END PGP PRIVATE KEY BLOCK----- diff --git a/tests/openpgp/secring.asc b/tests/openpgp/secring.asc new file mode 100644 index 000000000..99e02ca6f --- /dev/null +++ b/tests/openpgp/secring.asc @@ -0,0 +1,73 @@ +This is a test secret keyring simply stored by GNUPG so that it is +easier to make diff files. + +sec 1024D/D74C5F22 2003-12-31 Test one (pp=def) <one@example.com> +ssb 1024g/47BE2775 2003-12-31 + +sec 1024D/C40FDECF 2003-12-31 Test two (no pp) <two@example.com> +ssb 1024g/B27907AA 2003-12-31 + +sec 1024R/ECABF51D 2003-12-31 Test three (no pp) <three@example.com> + +-----BEGIN PGP PRIVATE KEY BLOCK----- +Version: GnuPG v1.3.5-cvs (GNU/Linux) + +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 +IHWHiQ== +=52aT +-----END PGP PRIVATE KEY BLOCK----- diff --git a/tests/openpgp/secring.skr.asc b/tests/openpgp/secring.skr.asc new file mode 100644 index 000000000..0081b59c1 --- /dev/null +++ b/tests/openpgp/secring.skr.asc @@ -0,0 +1,27 @@ +This is a test secring generated by pgp 5 beta + +Type Bits KeyID Created Expires Algorithm Use +sec+ 768 439F02CA 1998-03-17 ---------- DSS Sign and Encrypt +sub 768 CB879DE9 1998-03-17 ---------- Diffie-Hellman +uid pgp5 test <pgp5@dev.null> + +There is no password on the key + +-----BEGIN PGP ARMORED FILE----- +Version: GNUPG v0.2.13a (Linux) +Comment: This is an alpha version! +Comment: Use "gpgm --dearmor" for unpacking + +lQFbBDUOrE4RAwDbbxWAbWsheUJprK6VryMTpwDiYwMfL+92nrHqSfPqlpMWgDTia8qnpRSXbyEm +Sppp/6/Ygp+N3n32Kznq7PjHXiuWLlZGvZMtzmvaMA17y0GY6oLBxS7rhASXIKa9hEUAoP+KBFly +qNMdsK8j+ZO0A8rnImGrAwC1ddDme5iZFkTEWHhrtU97sEu2GDkSQB8HdX8CoRcrOz/B2WliF6qf +BKhcZPFVBIhKNzjTfY7SEYAZk2zcsCm8elnwSLaGEzxKFNFBqKDNXP+a35spcqsHSGzDVw4VuKMD +AJNnAP6skpHlhVAmecLZT9eRzVoOq1ivUIntK2Mh47qsL74q6BBwz2sviPU2Y3pDlbb6Ed0qJAXv +dCT24hlfoGoXzkoDInkPJTJeL0gCnwmQPjvXFFd71Cvg5LaL4lIQLQAAn3GbgsWo+7E/hWakzstp +TXzI2kDIDIm0GXBncDUgdGVzdCA8cGdwNUBkZXYubnVsbD6dAO8ENQ6sVhADAP8Fa5TbD6k8VmW1 +IjK1DfDI0xUdsVIbk8N3Hb0YIlT1E/6tZdfiNwqaKVQcf17gJIObBwfNM3OqWYOudmBVd3S6E3Hk +u64nW+ZNt7B2toWRgnk6OgHcSDsud4Igjwz/RQACAgL/ToefzlcVKiPuobKfXHDhIUQPTfGic2Az +47wkMoYHo9j9ZE7AWaliMdPz4jLyLfqqoU9mH8g+vJhyAc7UnAF2Sk5466FDypdPm5F9PTW3cqqI +wJM4WgkSlM8J2hxH4YtlAADlG+pxFXNFuDPmcq6jL6dug2ikZ7hcHLAy7DddSS8OAA== +=1UWo +-----END PGP ARMORED FILE----- diff --git a/tests/openpgp/signdemokey b/tests/openpgp/signdemokey new file mode 100755 index 000000000..9a1257cc4 --- /dev/null +++ b/tests/openpgp/signdemokey @@ -0,0 +1,16 @@ +#!/bin/sh + +set -e + +if [ $# != 3 ]; then + echo "Usage: signdemokey name user_id user_id_no" + exit 1 +fi +name="$1" +user_id="$2" +user_id_no="$3" + +echo "abc" | ../g10/gpg2 --options ./gpg.conf --homedir $name \ + --sign-key --batch --yes --passphrase-fd 0 $user_id \ + $user_id_no sign save + diff --git a/tests/openpgp/signencrypt-dsa.test b/tests/openpgp/signencrypt-dsa.test new file mode 100755 index 000000000..41bf83164 --- /dev/null +++ b/tests/openpgp/signencrypt-dsa.test @@ -0,0 +1,22 @@ +#!/bin/sh + +. $srcdir/defs.inc || exit 3 + +#info Checking signing and encryption for DSA +for i in $plain_files $data_files ; do + $GPG $dsa_keyrings --always-trust -se -o x --yes \ + -u "$dsa_usrname1" -r "$dsa_usrname2" $i + $GPG $dsa_keyrings -o y --yes x + cmp $i y || error "$i: mismatch" +done + +for da in ripemd160 sha1; do + for i in $plain_files; do + $GPG $dsa_keyrings --always-trust -se -o x --yes --digest-algo $da \ + -u "$dsa_usrname1" -r "$dsa_usrname2" $i + $GPG $dsa_keyrings -o y --yes x + cmp $i y || error "$i: mismatch" + # process only the first one + break + done +done diff --git a/tests/openpgp/signencrypt.test b/tests/openpgp/signencrypt.test new file mode 100755 index 000000000..1d05990fc --- /dev/null +++ b/tests/openpgp/signencrypt.test @@ -0,0 +1,13 @@ +#!/bin/sh + +. $srcdir/defs.inc || exit 3 + + +#info Checking signing and encryption +for i in $plain_files $data_files ; do + echo "$usrpass1" | $GPG --passphrase-fd 0 --always-trust \ + -se -o x --yes -r "$usrname2" $i + $GPG -o y --yes x + cmp $i y || error "$i: mismatch" +done + diff --git a/tests/openpgp/sigs-dsa.test b/tests/openpgp/sigs-dsa.test new file mode 100755 index 000000000..2294cf55a --- /dev/null +++ b/tests/openpgp/sigs-dsa.test @@ -0,0 +1,22 @@ +#!/bin/sh + +. $srcdir/defs.inc || exit 3 + +#info Checking DSA signatures (default digest algo) +for i in $plain_files $data_files; do + $GPG $dsa_keyrings -s -o x --yes -u $dsa_usrname1 $i + $GPG $dsa_keyrings -o y --yes x + cmp $i y || error "$i: mismatch" +done + +for da in ripemd160 sha1; do + for i in $plain_files; do + $GPG $dsa_keyrings --digest-algo $da \ + -s -o x --yes -u $dsa_usrname1 $i + $GPG $dsa_keyrings -o y --yes x + cmp $i y || error "$i: mismatch" + # process only the first one + break + done +done + diff --git a/tests/openpgp/sigs.test b/tests/openpgp/sigs.test new file mode 100755 index 000000000..2c3be5cf5 --- /dev/null +++ b/tests/openpgp/sigs.test @@ -0,0 +1,52 @@ +#!/bin/sh + +. $srcdir/defs.inc || exit 3 + +#info Checking signatures +for i in $plain_files $data_files; do + echo "$usrpass1" | $GPG --passphrase-fd 0 -s -o x --yes $i + $GPG -o y --yes x + cmp $i y || error "$i: mismatch" +done + +# Using the DSA sig key - only 160 bit hashes +for da in ripemd160 sha1 ; do + for i in $plain_files; do + echo "$usrpass1" | $GPG --passphrase-fd 0 --digest-algo $da \ + -s -o x --yes $i + $GPG -o y --yes x + cmp $i y || error "$i: mismatch" + # process only the first one + break + done +done + +# TODO: add the new SHAs here once we allow them to be used in new +# documents. + +if have_pubkey_algo "RSA"; then + # Using the RSA sig key - all hashes + hash_algo_list="ripemd160 sha1 md5" + if have_hash_algo "SHA224"; then + hash_algo_list="$hash_algo_list sha224" + fi + if have_hash_algo "SHA256"; then + hash_algo_list="$hash_algo_list sha256" + fi + if have_hash_algo "SHA384"; then + hash_algo_list="$hash_algo_list sha384" + fi + if have_hash_algo "SHA512"; then + hash_algo_list="$hash_algo_list sha512" + fi + + for da in $hash_algo_list ; do + for i in $plain_files; do + $GPG -u $usrname3 --digest-algo $da -s -o x --yes $i + $GPG -o y --yes x + cmp $i y || error "$i: mismatch" + # process only the first one + break + done + done +fi diff --git a/tests/openpgp/verify.test b/tests/openpgp/verify.test new file mode 100755 index 000000000..e6a61fc1b --- /dev/null +++ b/tests/openpgp/verify.test @@ -0,0 +1,252 @@ +#!/bin/sh + +. $srcdir/defs.inc || exit 3 + +suspend_error + +# +# Two simple tests to check that verify fails for bad input data +# +info "checking bogus signature 1" +../../tools/mk-tdata --char 0x2d 64 >x +$GPG --verify x data-500 && error "no error code from verify" +info "checking bogus signature 2" +../../tools/mk-tdata --char 0xca 64 >x +$GPG --verify x data-500 && error "no error code from verify" + +linefeed + +# A variable to collect the test names +tests="" + +# A plain signed message created using +# echo abc | gpg --homedir . --passphrase-fd 0 -u Alpha -z0 -sa msg +tests="$tests msg_ols_asc" +msg_ols_asc='-----BEGIN PGP MESSAGE----- + +kA0DAAIRLXJ8x2hpdzQBrQEHYgNtc2dEDFJaSSB0aGluayB0aGF0IGFsbCByaWdo +dC10aGlua2luZyBwZW9wbGUgaW4gdGhpcyBjb3VudHJ5IGFyZSBzaWNrIGFuZAp0 +aXJlZCBvZiBiZWluZyB0b2xkIHRoYXQgb3JkaW5hcnkgZGVjZW50IHBlb3BsZSBh +cmUgZmVkIHVwIGluIHRoaXMKY291bnRyeSB3aXRoIGJlaW5nIHNpY2sgYW5kIHRp +cmVkLiAgSSdtIGNlcnRhaW5seSBub3QuICBCdXQgSSdtCnNpY2sgYW5kIHRpcmVk +IG9mIGJlaW5nIHRvbGQgdGhhdCBJIGFtLgotIE1vbnR5IFB5dGhvbgqIPwMFAEQM +UlotcnzHaGl3NBECR4IAoJlEGTY+bHjD2HYuCixLQCmk01pbAKCIjkzLOAmkZNm0 +D8luT78c/1x45Q== +=a29i +-----END PGP MESSAGE-----' + +# A plain signed message created using +# echo abc | gpg --homedir . --passphrase-fd 0 -u Alpha -sa msg +tests="$tests msg_cols_asc" +msg_cols_asc='-----BEGIN PGP MESSAGE----- + +owGbwMvMwCSoW1RzPCOz3IRxLSN7EnNucboLT6Cgp0JJRmZeNpBMLFFIzMlRKMpM +zyjRBQtm5qUrFKTmF+SkKmTmgdQVKyTnl+aVFFUqJBalKhRnJmcrJOalcJVkFqWm +KOSnKSSlgrSU5OekQMzLL0rJzEsEKk9JTU7NK4EZBtKcBtRRWgAzlwtmbnlmSQbU +GJjxCmDj9RQUPNVzFZJTi0oSM/NyKhXy8kuAYk6lJSBxLlTF2NziqZCYq8elq+Cb +n1dSqRBQWZKRn8fVYc/MygAKBljYCDIFiTDMT+9seu836Q+bevyHTJ0dzPNuvCjn +ZpgrwX38z58rJsfYDhwOSS4SkN/d6vUAAA== +=s6sY +-----END PGP MESSAGE-----' + +# A PGP 2 style message. +tests="$tests msg_sl_asc" +msg_sl_asc='-----BEGIN PGP MESSAGE----- + +iD8DBQBEDFJaLXJ8x2hpdzQRAkeCAKCZRBk2Pmx4w9h2LgosS0AppNNaWwCgiI5M +yzgJpGTZtA/Jbk+/HP9ceOWtAQdiA21zZ0QMUlpJIHRoaW5rIHRoYXQgYWxsIHJp +Z2h0LXRoaW5raW5nIHBlb3BsZSBpbiB0aGlzIGNvdW50cnkgYXJlIHNpY2sgYW5k +CnRpcmVkIG9mIGJlaW5nIHRvbGQgdGhhdCBvcmRpbmFyeSBkZWNlbnQgcGVvcGxl +IGFyZSBmZWQgdXAgaW4gdGhpcwpjb3VudHJ5IHdpdGggYmVpbmcgc2ljayBhbmQg +dGlyZWQuICBJJ20gY2VydGFpbmx5IG5vdC4gIEJ1dCBJJ20Kc2ljayBhbmQgdGly +ZWQgb2YgYmVpbmcgdG9sZCB0aGF0IEkgYW0uCi0gTW9udHkgUHl0aG9uCg== +=0ukK +-----END PGP MESSAGE-----' + +# An OpenPGP message lacking the onepass packet. We used to accept +# such messages but now consider them invalid. +tests="$tests bad_ls_asc" +bad_ls_asc='-----BEGIN PGP MESSAGE----- + +rQEHYgNtc2dEDFJaSSB0aGluayB0aGF0IGFsbCByaWdodC10aGlua2luZyBwZW9w +bGUgaW4gdGhpcyBjb3VudHJ5IGFyZSBzaWNrIGFuZAp0aXJlZCBvZiBiZWluZyB0 +b2xkIHRoYXQgb3JkaW5hcnkgZGVjZW50IHBlb3BsZSBhcmUgZmVkIHVwIGluIHRo +aXMKY291bnRyeSB3aXRoIGJlaW5nIHNpY2sgYW5kIHRpcmVkLiAgSSdtIGNlcnRh +aW5seSBub3QuICBCdXQgSSdtCnNpY2sgYW5kIHRpcmVkIG9mIGJlaW5nIHRvbGQg +dGhhdCBJIGFtLgotIE1vbnR5IFB5dGhvbgqIPwMFAEQMUlotcnzHaGl3NBECR4IA +oJlEGTY+bHjD2HYuCixLQCmk01pbAKCIjkzLOAmkZNm0D8luT78c/1x45Q== +=Mpiu +-----END PGP MESSAGE-----' + + +# A signed message prefixed with an unsigned literal packet. +# (fols = faked-literal-data, one-pass, literal-data, signature) +# This should throw an error because running gpg to extract the +# signed data will return both literal data packets +tests="$tests bad_fols_asc" +bad_fols_asc='-----BEGIN PGP MESSAGE----- + +rF1iDG1zZy51bnNpZ25lZEQMY0x0aW1lc2hhcmluZywgbjoKCUFuIGFjY2VzcyBt +ZXRob2Qgd2hlcmVieSBvbmUgY29tcHV0ZXIgYWJ1c2VzIG1hbnkgcGVvcGxlLgqQ +DQMAAhEtcnzHaGl3NAGtAQdiA21zZ0QMUlpJIHRoaW5rIHRoYXQgYWxsIHJpZ2h0 +LXRoaW5raW5nIHBlb3BsZSBpbiB0aGlzIGNvdW50cnkgYXJlIHNpY2sgYW5kCnRp +cmVkIG9mIGJlaW5nIHRvbGQgdGhhdCBvcmRpbmFyeSBkZWNlbnQgcGVvcGxlIGFy +ZSBmZWQgdXAgaW4gdGhpcwpjb3VudHJ5IHdpdGggYmVpbmcgc2ljayBhbmQgdGly +ZWQuICBJJ20gY2VydGFpbmx5IG5vdC4gIEJ1dCBJJ20Kc2ljayBhbmQgdGlyZWQg +b2YgYmVpbmcgdG9sZCB0aGF0IEkgYW0uCi0gTW9udHkgUHl0aG9uCog/AwUARAxS +Wi1yfMdoaXc0EQJHggCgmUQZNj5seMPYdi4KLEtAKaTTWlsAoIiOTMs4CaRk2bQP +yW5Pvxz/XHjl +=UNM4 +-----END PGP MESSAGE-----' + +# A signed message suffixed with an unsigned literal packet. +# (fols = faked-literal-data, one-pass, literal-data, signature) +# This should throw an error because running gpg to extract the +# signed data will return both literal data packets +tests="$tests bad_olsf_asc" +bad_olsf_asc='-----BEGIN PGP MESSAGE----- + +kA0DAAIRLXJ8x2hpdzQBrQEHYgNtc2dEDFJaSSB0aGluayB0aGF0IGFsbCByaWdo +dC10aGlua2luZyBwZW9wbGUgaW4gdGhpcyBjb3VudHJ5IGFyZSBzaWNrIGFuZAp0 +aXJlZCBvZiBiZWluZyB0b2xkIHRoYXQgb3JkaW5hcnkgZGVjZW50IHBlb3BsZSBh +cmUgZmVkIHVwIGluIHRoaXMKY291bnRyeSB3aXRoIGJlaW5nIHNpY2sgYW5kIHRp +cmVkLiAgSSdtIGNlcnRhaW5seSBub3QuICBCdXQgSSdtCnNpY2sgYW5kIHRpcmVk +IG9mIGJlaW5nIHRvbGQgdGhhdCBJIGFtLgotIE1vbnR5IFB5dGhvbgqIPwMFAEQM +UlotcnzHaGl3NBECR4IAoJlEGTY+bHjD2HYuCixLQCmk01pbAKCIjkzLOAmkZNm0 +D8luT78c/1x45axdYgxtc2cudW5zaWduZWREDGNMdGltZXNoYXJpbmcsIG46CglB +biBhY2Nlc3MgbWV0aG9kIHdoZXJlYnkgb25lIGNvbXB1dGVyIGFidXNlcyBtYW55 +IHBlb3BsZS4K +=3gnG +-----END PGP MESSAGE-----' + + +# Two standard signed messages in a row +tests="$tests msg_olsols_asc_multisig" +msg_olsols_asc_multisig='-----BEGIN PGP MESSAGE----- + +kA0DAAIRLXJ8x2hpdzQBrQEHYgNtc2dEDFJaSSB0aGluayB0aGF0IGFsbCByaWdo +dC10aGlua2luZyBwZW9wbGUgaW4gdGhpcyBjb3VudHJ5IGFyZSBzaWNrIGFuZAp0 +aXJlZCBvZiBiZWluZyB0b2xkIHRoYXQgb3JkaW5hcnkgZGVjZW50IHBlb3BsZSBh +cmUgZmVkIHVwIGluIHRoaXMKY291bnRyeSB3aXRoIGJlaW5nIHNpY2sgYW5kIHRp +cmVkLiAgSSdtIGNlcnRhaW5seSBub3QuICBCdXQgSSdtCnNpY2sgYW5kIHRpcmVk +IG9mIGJlaW5nIHRvbGQgdGhhdCBJIGFtLgotIE1vbnR5IFB5dGhvbgqIPwMFAEQM +UlotcnzHaGl3NBECR4IAoJlEGTY+bHjD2HYuCixLQCmk01pbAKCIjkzLOAmkZNm0 +D8luT78c/1x45ZANAwACES1yfMdoaXc0Aa0BB2IDbXNnRAxSWkkgdGhpbmsgdGhh +dCBhbGwgcmlnaHQtdGhpbmtpbmcgcGVvcGxlIGluIHRoaXMgY291bnRyeSBhcmUg +c2ljayBhbmQKdGlyZWQgb2YgYmVpbmcgdG9sZCB0aGF0IG9yZGluYXJ5IGRlY2Vu +dCBwZW9wbGUgYXJlIGZlZCB1cCBpbiB0aGlzCmNvdW50cnkgd2l0aCBiZWluZyBz +aWNrIGFuZCB0aXJlZC4gIEknbSBjZXJ0YWlubHkgbm90LiAgQnV0IEknbQpzaWNr +IGFuZCB0aXJlZCBvZiBiZWluZyB0b2xkIHRoYXQgSSBhbS4KLSBNb250eSBQeXRo +b24KiD8DBQBEDFJaLXJ8x2hpdzQRAkeCAKCZRBk2Pmx4w9h2LgosS0AppNNaWwCg +iI5MyzgJpGTZtA/Jbk+/HP9ceOU= +=8nLN +-----END PGP MESSAGE-----' + +# A standard message with two signatures (actually the same signature +# duplicated). +tests="$tests msg_oolss_asc" +msg_oolss_asc='-----BEGIN PGP MESSAGE----- + +kA0DAAIRLXJ8x2hpdzQBkA0DAAIRLXJ8x2hpdzQBrQEHYgNtc2dEDFJaSSB0aGlu +ayB0aGF0IGFsbCByaWdodC10aGlua2luZyBwZW9wbGUgaW4gdGhpcyBjb3VudHJ5 +IGFyZSBzaWNrIGFuZAp0aXJlZCBvZiBiZWluZyB0b2xkIHRoYXQgb3JkaW5hcnkg +ZGVjZW50IHBlb3BsZSBhcmUgZmVkIHVwIGluIHRoaXMKY291bnRyeSB3aXRoIGJl +aW5nIHNpY2sgYW5kIHRpcmVkLiAgSSdtIGNlcnRhaW5seSBub3QuICBCdXQgSSdt +CnNpY2sgYW5kIHRpcmVkIG9mIGJlaW5nIHRvbGQgdGhhdCBJIGFtLgotIE1vbnR5 +IFB5dGhvbgqIPwMFAEQMUlotcnzHaGl3NBECR4IAoJlEGTY+bHjD2HYuCixLQCmk +01pbAKCIjkzLOAmkZNm0D8luT78c/1x45Yg/AwUARAxSWi1yfMdoaXc0EQJHggCg +mUQZNj5seMPYdi4KLEtAKaTTWlsAoIiOTMs4CaRk2bQPyW5Pvxz/XHjl +=KVw5 +-----END PGP MESSAGE-----' + +# A standard message with two one-pass packet but only one signature +# packet +tests="$tests bad_ools_asc" +bad_ools_asc='-----BEGIN PGP MESSAGE----- + +kA0DAAIRLXJ8x2hpdzQBkA0DAAIRLXJ8x2hpdzQBrQEHYgNtc2dEDFJaSSB0aGlu +ayB0aGF0IGFsbCByaWdodC10aGlua2luZyBwZW9wbGUgaW4gdGhpcyBjb3VudHJ5 +IGFyZSBzaWNrIGFuZAp0aXJlZCBvZiBiZWluZyB0b2xkIHRoYXQgb3JkaW5hcnkg +ZGVjZW50IHBlb3BsZSBhcmUgZmVkIHVwIGluIHRoaXMKY291bnRyeSB3aXRoIGJl +aW5nIHNpY2sgYW5kIHRpcmVkLiAgSSdtIGNlcnRhaW5seSBub3QuICBCdXQgSSdt +CnNpY2sgYW5kIHRpcmVkIG9mIGJlaW5nIHRvbGQgdGhhdCBJIGFtLgotIE1vbnR5 +IFB5dGhvbgqIPwMFAEQMUlotcnzHaGl3NBECR4IAoJlEGTY+bHjD2HYuCixLQCmk +01pbAKCIjkzLOAmkZNm0D8luT78c/1x45Q== +=1/ix +-----END PGP MESSAGE-----' + +# Standard cleartext signature +tests="$tests msg_cls_asc" +msg_cls_asc=`cat <<EOF +-----BEGIN PGP SIGNED MESSAGE----- +Hash: SHA1 + +I think that all right-thinking people in this country are sick and +tired of being told that ordinary decent people are fed up in this +country with being sick and tired. I'm certainly not. But I'm +sick and tired of being told that I am. +- - Monty Python +-----BEGIN PGP SIGNATURE----- + +iD8DBQFEDVp1LXJ8x2hpdzQRAplUAKCMfpG3GPw/TLN52tosgXP5lNECkwCfQhAa +emmev7IuQjWYrGF9Lxj+zj8= +=qJsY +-----END PGP SIGNATURE----- +EOF +` + +# Cleartext signature with two signatures +tests="$tests msg_clss_asc" +msg_clss_asc=`cat <<EOF +-----BEGIN PGP SIGNED MESSAGE----- +Hash: SHA1 + +What is the difference between a Turing machine and the modern computer? +It's the same as that between Hillary's ascent of Everest and the +establishment of a Hilton on its peak. +-----BEGIN PGP SIGNATURE----- + +iD8DBQFEDVz6LXJ8x2hpdzQRAtkGAKCeMhNbHnh339fpjNj9owsYcC4zBwCfYO5l +2u+KEfXX0FKyk8SMzLjZ536IPwMFAUQNXPr+GAsdqeOwshEC2QYAoPOWAiQm0EF/ +FWIAQUplk7JWbyRKAJ92ZJyJpWfzb0yc1s7MY65r2qEHrg== +=1Xvv +-----END PGP SIGNATURE----- +EOF +` + +# Two clear text signatures in a row +tests="$tests msg_clsclss_asc" +msg_clsclss_asc="${msg_cls_asc} +${msg_clss_asc}" + + +# Fixme: We need more tests with manipulated cleartext signatures. + + +# +# Now run the tests. +# +for i in $tests ; do + info "checking: $i" + eval "(IFS=; echo \"\$$i\")" >x + case "$i" in + msg_*_asc) + $GPG --verify x || error "verify of $i failed" + ;; + msg_*_asc_multisig) + $GPG --verify --allow-multisig-verification x \ + || error "verify of $i failed" + $GPG --verify x && error "verify of $i succeeded but should not" + ;; + bad_*_asc) + $GPG --verify x && error "verify of $i succeeded but should not" + ;; + *) + error "No handler for test case $i" + ;; + esac + linefeed +done + + +resume_error diff --git a/tests/openpgp/version.test b/tests/openpgp/version.test new file mode 100755 index 000000000..f1fd7284f --- /dev/null +++ b/tests/openpgp/version.test @@ -0,0 +1,9 @@ +#!/bin/sh + +. $srcdir/defs.inc || exit 3 + +# print the GPG version +$GPG --version + +#fixme: check that the output is correct + diff --git a/tools/ChangeLog b/tools/ChangeLog index 25ffae5d2..af5925aa1 100644 --- a/tools/ChangeLog +++ b/tools/ChangeLog @@ -1,3 +1,9 @@ +2006-08-21 Werner Koch <wk@g10code.com> + + * gpgsplit.c: New. Taken from 1.4. Adjusted to GnuPG2. + + * Makefile.am (noinst_PROGRAMS): New. + 2006-06-09 Marcus Brinkmann <marcus@g10code.de> * Makefile.am (gpgconf_LDADD): Add $(GPG_ERROR_LIBS). diff --git a/tools/Makefile.am b/tools/Makefile.am index 6b4767a79..702bd5187 100644 --- a/tools/Makefile.am +++ b/tools/Makefile.am @@ -18,8 +18,11 @@ # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, # USA. -EXTRA_DIST = Manifest watchgnupg.c \ - addgnupghome gpgsm-gencert.sh +EXTRA_DIST = \ + Manifest watchgnupg.c \ + addgnupghome gpgsm-gencert.sh \ + lspgpot mail-signed-keys convert-from-106 + AM_CPPFLAGS = -I$(top_srcdir)/gl -I$(top_srcdir)/intl -I$(top_srcdir)/common include $(top_srcdir)/am/cmacros.am @@ -29,6 +32,9 @@ AM_CFLAGS = $(LIBGCRYPT_CFLAGS) $(GPG_ERROR_CFLAGS) $(LIBASSUAN_CFLAGS) sbin_SCRIPTS = addgnupghome bin_SCRIPTS = gpgsm-gencert.sh +if HAVE_USTAR +bin_SCRIPTS += gpg-zip +endif if BUILD_SYMCRYPTRUN symcryptrun = symcryptrun @@ -36,17 +42,24 @@ else symcryptrun = endif -bin_PROGRAMS = gpgconf gpg-connect-agent gpgkey2ssh ${symcryptrun} gpgparsemail +bin_PROGRAMS = gpgconf gpg-connect-agent gpgkey2ssh ${symcryptrun} \ + gpgparsemail gpgsplit if !HAVE_W32_SYSTEM bin_PROGRAMS += watchgnupg endif +noinst_PROGRAMS = clean-sat mk-tdata make-dns-cert + +common_libs = ../jnlib/libjnlib.a ../common/libcommon.a ../gl/libgnu.a + +gpgsplit_LDADD = $(common_libs) $(LIBGCRYPT_LIBS) $(GPG_ERROR_LIBS) $(ZLIBS) + gpgconf_SOURCES = gpgconf.c gpgconf.h gpgconf-comp.c no-libgcrypt.c # jnlib/common sucks in gpg-error, will they, nil they (some compilers # do not eliminate the supposed-to-be-unused-inline-functions). gpgconf_LDADD = ../jnlib/libjnlib.a ../common/libcommon.a \ - ../gl/libgnu.a @LIBINTL@ $(GPG_ERROR_LIBS) + ../gl/libgnu.a $(LIBINTL) $(GPG_ERROR_LIBS) gpgparsemail_SOURCES = gpgparsemail.c rfc822parse.c rfc822parse.h gpgparsemail_LDADD = @@ -71,3 +84,5 @@ gpgkey2ssh_CFLAGS = $(LIBGCRYPT_CFLAGS) $(GPG_ERROR_CFLAGS) # some compilers do not eliminate. gpgkey2ssh_LDADD = ../jnlib/libjnlib.a ../common/libcommon.a ../gl/libgnu.a \ $(LIBGCRYPT_LIBS) $(GPG_ERROR_LIBS) + + diff --git a/tools/clean-sat.c b/tools/clean-sat.c new file mode 100644 index 000000000..8b6bfd77a --- /dev/null +++ b/tools/clean-sat.c @@ -0,0 +1,34 @@ +/* clean-sat.c + * Copyright (C) 1998, 1999, 2000, 2001 Free Software Foundation, Inc. + * + * This file is free software; as a special exception the author gives + * unlimited permission to copy and/or distribute it, with or without + * modifications, as long as this notice is preserved. + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY, to the extent permitted by law; without even the + * implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + */ + +#include <stdio.h> + +int +main(int argc, char **argv) +{ + int c; + + if( argc > 1 ) { + fprintf(stderr, "no arguments, please\n"); + return 1; + } + + while( (c=getchar()) == '\n' ) + ; + while( c != EOF ) { + putchar(c); + c = getchar(); + } + + return 0; +} + diff --git a/tools/convert-from-106 b/tools/convert-from-106 new file mode 100755 index 000000000..634152b11 --- /dev/null +++ b/tools/convert-from-106 @@ -0,0 +1,57 @@ +#!/bin/sh +# Copyright (C) 2002, 2004 Free Software Foundation, Inc. +# +# This program is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2 of the License, or +# (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, but +# WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software +# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + +if ! gpg --version > /dev/null 2>&1 ; then + echo "GnuPG not available!" + exit 1 +fi + +gpg="gpg --no-greeting --no-secmem-warning" + +echo "This script converts your public keyring and trustdb from GnuPG" +echo "1.0.6 or earlier to the 1.0.7 and later format." + +echo "If you have already done this, there is no harm (but no point)" +echo "in doing it again." + +echo -n "Continue? (y/N)" + +read answer + +if test "x$answer" != "xy" ; then + exit 0 +fi + +echo +echo "Marking your keys as ultimately trusted" +for key in `$gpg --with-colons --list-secret-keys | grep sec: | cut -d: -f5` +do + $gpg --trusted-key $key --with-colons --list-keys $key > /dev/null 2>&1 + echo -n "." +done +echo + +echo +echo "Adding signature caches" +$gpg --rebuild-keydb-caches + +echo +echo "Checking trustdb" +$gpg --check-trustdb + +echo +echo "Done!" diff --git a/tools/crlf.c b/tools/crlf.c new file mode 100644 index 000000000..ecb6eecdb --- /dev/null +++ b/tools/crlf.c @@ -0,0 +1,52 @@ +/* crlf.c + * Copyright (C) 1999, 2000, 2001 Free Software Foundation, Inc. + * + * This file is free software; as a special exception the author gives + * unlimited permission to copy and/or distribute it, with or without + * modifications, as long as this notice is preserved. + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY, to the extent permitted by law; without even the + * implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + */ + +#include <stdio.h> + +int +main(int argc, char **argv) +{ + int c, lc; + int off=0; + + if( argc > 1 ) { + fprintf(stderr, "no arguments, please\n"); + return 1; + } + + lc = -1; + while( (c=getchar()) != EOF ) { +#if 0 + if( c == '\r' && lc == ' ' ) + fprintf(stderr,"SP,CR at %d\n", off ); + if( c == '\n' && lc == ' ' ) + fprintf(stderr,"SP,LF at %d\n", off ); +#endif + if( c == '\n' && lc == '\r' ) + putchar(c); + else if( c == '\n' ) { + putchar('\r'); + putchar(c); + } + else if( c != '\n' && lc == '\r' ) { + putchar('\n'); + putchar(c); + } + else + putchar(c); + + lc = c; + off++; + } + + return 0; +} diff --git a/tools/gpg-zip.in b/tools/gpg-zip.in new file mode 100644 index 000000000..8b4ccfb2b --- /dev/null +++ b/tools/gpg-zip.in @@ -0,0 +1,142 @@ +#!/bin/sh + +# gpg-archive - gpg-ized tar using the same format as PGP's PGP Zip. +# Copyright (C) 2005 Free Software Foundation, Inc. +# +# This file is part of GnuPG. +# +# GnuPG is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2 of the License, or +# (at your option) any later version. +# +# GnuPG is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software +# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA + +# Despite the name, PGP Zip format is actually an OpenPGP-wrapped tar +# file. To be compatible with PGP itself, this must be a USTAR format +# tar file. Unclear on whether there is a distinction here between +# the GNU or POSIX variant of USTAR. + +VERSION=@VERSION@ +TAR=@TAR@ +GPG=gpg + +usage="\ +Usage: gpg-zip [--help] [--version] [--encrypt] [--decrypt] [--symmetric] + [--list-archive] [--output FILE] [--gpg GPG] [--gpg-args ARGS] + [--tar TAR] [--tar-args ARGS] filename1 [filename2, ...] + directory1 [directory2, ...] + +Encrypt or sign files into an archive." + +while test $# -gt 0 ; do + case $1 in + -h | --help | --h*) + echo "$usage" + exit 0 + ;; + --list-archive) + list=yes + create=no + unpack=no + shift + ;; + --encrypt | -e) + gpg_args="$gpg_args --encrypt" + list=no + create=yes + unpack=no + shift + ;; + --decrypt | -d) + gpg_args="$gpg_args --decrypt" + list=no + create=no + unpack=yes + shift + ;; + --symmetric | -c) + gpg_args="$gpg_args --symmetric" + list=no + create=yes + unpack=no + shift + ;; + --sign | -s) + gpg_args="$gpg_args --sign" + list=no + create=yes + unpack=no + shift + ;; + --recipient | -r) + gpg_args="$gpg_args --recipient $2" + shift + shift + ;; + --local-user | -u) + gpg_args="$gpg_args --local-user $2" + shift + shift + ;; + --output | -o) + gpg_args="$gpg_args --output $2" + shift + shift + ;; + --version) + echo "gpg-zip (GnuPG) $VERSION" + exit 0 + ;; + --gpg) + GPG=$1 + shift + ;; + --gpg-args) + gpg_args="$gpg_args $2" + shift + shift + ;; + --tar) + TAR=$1 + shift + ;; + --tar-args) + tar_args="$tar_args $2" + shift + shift + ;; + --) + shift + break + ;; + -*) + echo "$usage" 1>&2 + exit 1 + ;; + *) + break + ;; + esac +done + +if test x$create = xyes ; then +# echo "$TAR -cf - "$@" | $GPG --set-filename x.tar $gpg_args" 1>&2 + $TAR -cf - "$@" | $GPG --set-filename x.tar $gpg_args +elif test x$list = xyes ; then +# echo "cat \"$1\" | $GPG $gpg_args | $TAR $tar_args -tf -" 1>&2 + cat "$1" | $GPG $gpg_args | $TAR $tar_args -tf - +elif test x$unpack = xyes ; then +# echo "cat \"$1\" | $GPG $gpg_args | $TAR $tar_args -xvf -" 1>&2 + cat "$1" | $GPG $gpg_args | $TAR $tar_args -xvf - +else + echo "$usage" 1>&2 + exit 1 +fi diff --git a/tools/gpgsplit.c b/tools/gpgsplit.c new file mode 100644 index 000000000..96760dab3 --- /dev/null +++ b/tools/gpgsplit.c @@ -0,0 +1,881 @@ +/* gpgsplit.c - An OpenPGP packet splitting tool + * Copyright (C) 2001, 2002, 2003 Free Software Foundation, Inc. + * + * This file is part of GnuPG. + * + * GnuPG is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * GnuPG is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, + * USA. + */ + +/* + * TODO: Add an option to uncompress packets. This should come quite handy. + */ + +#include <config.h> +#include <errno.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <ctype.h> +#include <unistd.h> +#include <assert.h> +#include <sys/types.h> +#ifdef HAVE_DOSISH_SYSTEM +# include <fcntl.h> /* for setmode() */ +#endif +#include <zlib.h> +#ifdef HAVE_BZIP2 +#include <bzlib.h> +#endif /* HAVE_BZIP2 */ +#if defined(__riscos__) && defined(USE_ZLIBRISCOS) +# include "zlib-riscos.h" +#endif + +#define INCLUDED_BY_MAIN_MODULE 1 +#include "util.h" +#include "openpgpdefs.h" + +static int opt_verbose; +static const char *opt_prefix = ""; +static int opt_uncompress; +static int opt_secret_to_public; +static int opt_no_split; + +static void g10_exit( int rc ); +static void split_packets (const char *fname); + + +enum cmd_and_opt_values { + aNull = 0, + oVerbose = 'v', + oPrefix = 'p', + oUncompress = 500, + oSecretToPublic, + oNoSplit, + + aTest +}; + + +static ARGPARSE_OPTS opts[] = { + + { 301, NULL, 0, "@Options:\n " }, + + { oVerbose, "verbose", 0, "verbose" }, + { oPrefix, "prefix", 2, "|STRING|Prepend filenames with STRING" }, + { oUncompress, "uncompress", 0, "uncompress a packet"}, + { oSecretToPublic, "secret-to-public", 0, "convert secret keys to public keys"}, + { oNoSplit, "no-split", 0, "write to stdout and don't actually split"}, +{0} }; + + +static const char * +my_strusage (int level) +{ + const char *p; + switch (level) + { + case 11: p = "gpgsplit (GnuPG)"; + break; + case 13: p = VERSION; break; + case 17: p = PRINTABLE_OS_NAME; break; + case 19: p = + "Please report bugs to <bug-gnupg@gnu.org>.\n"; + break; + case 1: + case 40: p = + "Usage: gpgsplit [options] [files] (-h for help)"; + break; + case 41: p = + "Syntax: gpgsplit [options] [files]\n" + "Split an OpenPGP message into packets\n"; + break; + + default: p = NULL; + } + return p; +} + + + +int +main (int argc, char **argv) +{ + ARGPARSE_ARGS pargs; + +#ifdef HAVE_DOSISH_SYSTEM + setmode( fileno(stdin), O_BINARY ); + setmode( fileno(stdout), O_BINARY ); +#endif + log_set_prefix ("gpgsplit", JNLIB_LOG_WITH_PREFIX); + set_strusage (my_strusage); + + pargs.argc = &argc; + pargs.argv = &argv; + pargs.flags= 1; /* do not remove the args */ + while (optfile_parse( NULL, NULL, NULL, &pargs, opts)) + { + switch (pargs.r_opt) + { + case oVerbose: opt_verbose = 1; break; + case oPrefix: opt_prefix = pargs.r.ret_str; break; + case oUncompress: opt_uncompress = 1; break; + case oSecretToPublic: opt_secret_to_public = 1; break; + case oNoSplit: opt_no_split = 1; break; + default : pargs.err = 2; break; + } + } + + if (log_get_errorcount(0)) + g10_exit (2); + + if (!argc) + split_packets (NULL); + else + { + for ( ;argc; argc--, argv++) + split_packets (*argv); + } + + g10_exit (0); + return 0; +} + + +static void +g10_exit (int rc) +{ + rc = rc? rc : log_get_errorcount(0)? 2 : 0; + exit(rc ); +} + +static const char * +pkttype_to_string (int pkttype) +{ + const char *s; + + switch (pkttype) + { + case PKT_PUBKEY_ENC : s = "pk_enc"; break; + case PKT_SIGNATURE : s = "sig"; break; + case PKT_SYMKEY_ENC : s = "sym_enc"; break; + case PKT_ONEPASS_SIG : s = "onepass_sig"; break; + case PKT_SECRET_KEY : s = "secret_key"; break; + case PKT_PUBLIC_KEY : s = "public_key"; break; + case PKT_SECRET_SUBKEY : s = "secret_subkey"; break; + case PKT_COMPRESSED : + s = opt_uncompress? "uncompressed":"compressed"; + break; + case PKT_ENCRYPTED : s = "encrypted"; break; + case PKT_MARKER : s = "marker"; break; + case PKT_PLAINTEXT : s = "plaintext"; break; + case PKT_RING_TRUST : s = "ring_trust"; break; + case PKT_USER_ID : s = "user_id"; break; + case PKT_PUBLIC_SUBKEY : s = "public_subkey"; break; + case PKT_OLD_COMMENT : s = "old_comment"; break; + case PKT_ATTRIBUTE : s = "attribute"; break; + case PKT_ENCRYPTED_MDC : s = "encrypted_mdc"; break; + case PKT_MDC : s = "mdc"; break; + case PKT_COMMENT : s = "comment"; break; + case PKT_GPG_CONTROL : s = "gpg_control"; break; + default: s = "unknown"; break; + } + return s; +} + + +/* + * Create a new filename and a return a pointer to a statically + * allocated buffer + */ +static char * +create_filename (int pkttype) +{ + static unsigned int partno = 0; + static char *name; + + if (!name) + name = xmalloc (strlen (opt_prefix) + 100 ); + + assert (pkttype < 1000 && pkttype >= 0 ); + partno++; + sprintf (name, "%s%06u-%03d" EXTSEP_S "%.40s", + opt_prefix, partno, pkttype, pkttype_to_string (pkttype)); + return name; +} + +static int +read_u16 (FILE *fp, size_t *rn) +{ + int c; + + if ( (c = getc (fp)) == EOF ) + return -1; + *rn = c << 8; + if ( (c = getc (fp)) == EOF ) + return -1; + *rn |= c; + return 0; +} + +static int +read_u32 (FILE *fp, unsigned long *rn) +{ + size_t tmp; + + if (read_u16 (fp, &tmp)) + return -1; + *rn = tmp << 16; + if (read_u16 (fp, &tmp)) + return -1; + *rn |= tmp; + return 0; +} + +static int +write_old_header (FILE *fp, int pkttype, unsigned int len) +{ + int ctb = (0x80 | ((pkttype & 15)<<2)); + + if (len < 256) + ; + else if (len < 65536) + ctb |= 1; + else + ctb |= 2; + + if ( putc ( ctb, fp) == EOF ) + return -1; + + if ( (ctb & 2) ) + { + if (putc ((len>>24), fp) == EOF) + return -1; + if (putc ((len>>16), fp) == EOF) + return -1; + } + if ( (ctb & 3) ) + { + if (putc ((len>>8), fp) == EOF) + return -1; + } + if (putc ((len&0xff), fp) == EOF) + return -1; + return 0; +} + +static int +write_new_header (FILE *fp, int pkttype, unsigned int len) +{ + if ( putc ((0xc0 | (pkttype & 0x3f)), fp) == EOF ) + return -1; + + if (len < 192) + { + if (putc (len, fp) == EOF) + return -1; + } + else if (len < 8384) + { + len -= 192; + if (putc ((len/256)+192, fp) == EOF) + return -1; + if (putc ((len%256), fp) == EOF) + return -1; + } + else + { + if (putc ( 0xff, fp) == EOF) + return -1; + if (putc ( (len >> 24), fp) == EOF) + return -1; + if (putc ( (len >> 16), fp) == EOF) + return -1; + if (putc ( (len >> 8), fp) == EOF) + return -1; + if (putc ( (len & 0xff), fp) == EOF) + return -1; + } + return 0; +} + +/* Return the length of the public key given BUF of BUFLEN with a + secret key. */ +static int +public_key_length (const unsigned char *buf, size_t buflen) +{ + const unsigned char *s; + int nmpis; + + /* byte version number (3 or 4) + u32 creation time + [u16 valid days (version 3 only)] + byte algorithm + n MPIs (n and e) */ + if (!buflen) + return 0; + if (buf[0] < 2 || buf[0] > 4) + return 0; /* wrong version number */ + if (buflen < (buf[0] == 4? 6:8)) + return 0; + s = buf + (buf[0] == 4? 6:8); + buflen -= (buf[0] == 4? 6:8); + switch (s[-1]) + { + case 1: + case 2: + case 3: + nmpis = 2; + break; + case 16: + case 20: + nmpis = 3; + break; + case 17: + nmpis = 4; + break; + default: + return 0; + } + + for (; nmpis; nmpis--) + { + unsigned int nbits, nbytes; + + if (buflen < 2) + return 0; + nbits = (s[0] << 8) | s[1]; + s += 2; buflen -= 2; + nbytes = (nbits+7) / 8; + if (buflen < nbytes) + return 0; + s += nbytes; buflen -= nbytes; + } + + return s - buf; +} + +static int +handle_zlib(int algo,FILE *fpin,FILE *fpout) +{ + z_stream zs; + byte *inbuf, *outbuf; + unsigned int inbufsize, outbufsize; + int c,zinit_done, zrc, nread, count; + size_t n; + + memset (&zs, 0, sizeof zs); + inbufsize = 2048; + inbuf = xmalloc (inbufsize); + outbufsize = 8192; + outbuf = xmalloc (outbufsize); + zs.avail_in = 0; + zinit_done = 0; + + do + { + if (zs.avail_in < inbufsize) + { + n = zs.avail_in; + if (!n) + zs.next_in = (Bytef *) inbuf; + count = inbufsize - n; + for (nread=0; + nread < count && (c=getc (fpin)) != EOF; + nread++) + inbuf[n+nread] = c; + + n += nread; + if (nread < count && algo == 1) + { + inbuf[n] = 0xFF; /* chew dummy byte */ + n++; + } + zs.avail_in = n; + } + zs.next_out = (Bytef *) outbuf; + zs.avail_out = outbufsize; + + if (!zinit_done) + { + zrc = (algo == 1? inflateInit2 ( &zs, -13) + : inflateInit ( &zs )); + if (zrc != Z_OK) + { + log_fatal ("zlib problem: %s\n", zs.msg? zs.msg : + zrc == Z_MEM_ERROR ? "out of core" : + zrc == Z_VERSION_ERROR ? + "invalid lib version" : + "unknown error" ); + } + zinit_done = 1; + } + else + { +#ifdef Z_SYNC_FLUSH + zrc = inflate (&zs, Z_SYNC_FLUSH); +#else + zrc = inflate (&zs, Z_PARTIAL_FLUSH); +#endif + if (zrc == Z_STREAM_END) + ; /* eof */ + else if (zrc != Z_OK && zrc != Z_BUF_ERROR) + { + if (zs.msg) + log_fatal ("zlib inflate problem: %s\n", zs.msg ); + else + log_fatal ("zlib inflate problem: rc=%d\n", zrc ); + } + for (n=0; n < outbufsize - zs.avail_out; n++) + { + if (putc (outbuf[n], fpout) == EOF ) + return 1; + } + } + } + while (zrc != Z_STREAM_END && zrc != Z_BUF_ERROR); + inflateEnd (&zs); + + return 0; +} + +#ifdef HAVE_BZIP2 +static int +handle_bzip2(int algo,FILE *fpin,FILE *fpout) +{ + bz_stream bzs; + byte *inbuf, *outbuf; + unsigned int inbufsize, outbufsize; + int c,zinit_done, zrc, nread, count; + size_t n; + + memset (&bzs, 0, sizeof bzs); + inbufsize = 2048; + inbuf = xmalloc (inbufsize); + outbufsize = 8192; + outbuf = xmalloc (outbufsize); + bzs.avail_in = 0; + zinit_done = 0; + + do + { + if (bzs.avail_in < inbufsize) + { + n = bzs.avail_in; + if (!n) + bzs.next_in = inbuf; + count = inbufsize - n; + for (nread=0; + nread < count && (c=getc (fpin)) != EOF; + nread++) + inbuf[n+nread] = c; + + n += nread; + if (nread < count && algo == 1) + { + inbuf[n] = 0xFF; /* chew dummy byte */ + n++; + } + bzs.avail_in = n; + } + bzs.next_out = outbuf; + bzs.avail_out = outbufsize; + + if (!zinit_done) + { + zrc = BZ2_bzDecompressInit(&bzs,0,0); + if (zrc != BZ_OK) + log_fatal ("bz2lib problem: %d\n",zrc); + zinit_done = 1; + } + else + { + zrc = BZ2_bzDecompress(&bzs); + if (zrc == BZ_STREAM_END) + ; /* eof */ + else if (zrc != BZ_OK && zrc != BZ_PARAM_ERROR) + log_fatal ("bz2lib inflate problem: %d\n", zrc ); + for (n=0; n < outbufsize - bzs.avail_out; n++) + { + if (putc (outbuf[n], fpout) == EOF ) + return 1; + } + } + } + while (zrc != BZ_STREAM_END && zrc != BZ_PARAM_ERROR); + BZ2_bzDecompressEnd(&bzs); + + return 0; +} +#endif /* HAVE_BZIP2 */ + +/* hdr must point to a buffer large enough to hold all header bytes */ +static int +write_part ( const char *fname, FILE *fpin, unsigned long pktlen, + int pkttype, int partial, unsigned char *hdr, size_t hdrlen) +{ + FILE *fpout; + int c, first; + unsigned char *p; + const char *outname = create_filename (pkttype); + +#if defined(__riscos__) && defined(USE_ZLIBRISCOS) + static int initialized = 0; + + if (!initialized) + initialized = riscos_load_module("ZLib", zlib_path, 1); +#endif + if (opt_no_split) + fpout = stdout; + else + { + if (opt_verbose) + log_info ("writing `%s'\n", outname); + fpout = fopen (outname, "wb"); + if (!fpout) + { + log_error ("error creating `%s': %s\n", outname, strerror(errno)); + /* stop right now, otherwise we would mess up the sequence + of the part numbers */ + g10_exit (1); + } + } + + if (opt_secret_to_public + && (pkttype == PKT_SECRET_KEY || pkttype == PKT_SECRET_SUBKEY)) + { + unsigned char *blob = xmalloc (pktlen); + int i, len; + + pkttype = pkttype == PKT_SECRET_KEY? PKT_PUBLIC_KEY:PKT_PUBLIC_SUBKEY; + + for (i=0; i < pktlen; i++) + { + c = getc (fpin); + if (c == EOF) + goto read_error; + blob[i] = c; + } + len = public_key_length (blob, pktlen); + if (!len) + { + log_error ("error calcualting public key length\n"); + g10_exit (1); + } + if ( (hdr[0] & 0x40) ) + { + if (write_new_header (fpout, pkttype, len)) + goto write_error; + } + else + { + if (write_old_header (fpout, pkttype, len)) + goto write_error; + } + + for (i=0; i < len; i++) + { + if ( putc (blob[i], fpout) == EOF ) + goto write_error; + } + + goto ready; + } + + + if (!opt_uncompress) + { + for (p=hdr; hdrlen; p++, hdrlen--) + { + if ( putc (*p, fpout) == EOF ) + goto write_error; + } + } + + first = 1; + while (partial) + { + size_t partlen; + + if (partial == 1) + { /* openpgp */ + if (first ) + { + c = pktlen; + assert( c >= 224 && c < 255 ); + first = 0; + } + else if ((c = getc (fpin)) == EOF ) + goto read_error; + else + hdr[hdrlen++] = c; + + if (c < 192) + { + pktlen = c; + partial = 0; /* (last segment may follow) */ + } + else if (c < 224 ) + { + pktlen = (c - 192) * 256; + if ((c = getc (fpin)) == EOF) + goto read_error; + hdr[hdrlen++] = c; + pktlen += c + 192; + partial = 0; + } + else if (c == 255) + { + if (read_u32 (fpin, &pktlen)) + goto read_error; + hdr[hdrlen++] = pktlen >> 24; + hdr[hdrlen++] = pktlen >> 16; + hdr[hdrlen++] = pktlen >> 8; + hdr[hdrlen++] = pktlen; + partial = 0; + } + else + { /* next partial body length */ + for (p=hdr; hdrlen; p++, hdrlen--) + { + if ( putc (*p, fpout) == EOF ) + goto write_error; + } + partlen = 1 << (c & 0x1f); + for (; partlen; partlen--) + { + if ((c = getc (fpin)) == EOF) + goto read_error; + if ( putc (c, fpout) == EOF ) + goto write_error; + } + } + } + else if (partial == 2) + { /* old gnupg */ + assert (!pktlen); + if ( read_u16 (fpin, &partlen) ) + goto read_error; + hdr[hdrlen++] = partlen >> 8; + hdr[hdrlen++] = partlen; + for (p=hdr; hdrlen; p++, hdrlen--) + { + if ( putc (*p, fpout) == EOF ) + goto write_error; + } + if (!partlen) + partial = 0; /* end of packet */ + for (; partlen; partlen--) + { + c = getc (fpin); + if (c == EOF) + goto read_error; + if ( putc (c, fpout) == EOF ) + goto write_error; + } + } + else + { /* compressed: read to end */ + pktlen = 0; + partial = 0; + hdrlen = 0; + if (opt_uncompress) + { + if ((c = getc (fpin)) == EOF) + goto read_error; + + if(c==1 || c==2) + { + if(handle_zlib(c,fpin,fpout)) + goto write_error; + } +#ifdef HAVE_BZIP2 + else if(c==3) + { + if(handle_bzip2(c,fpin,fpout)) + goto write_error; + } +#endif /* HAVE_BZIP2 */ + else + { + log_error("invalid compression algorithm (%d)\n",c); + goto read_error; + } + } + else + { + while ( (c=getc (fpin)) != EOF ) + { + if ( putc (c, fpout) == EOF ) + goto write_error; + } + } + if (!feof (fpin)) + goto read_error; + } + } + + for (p=hdr; hdrlen; p++, hdrlen--) + { + if ( putc (*p, fpout) == EOF ) + goto write_error; + } + + /* standard packet or last segment of partial length encoded packet */ + for (; pktlen; pktlen--) + { + c = getc (fpin); + if (c == EOF) + goto read_error; + if ( putc (c, fpout) == EOF ) + goto write_error; + } + + ready: + if ( !opt_no_split && fclose (fpout) ) + log_error ("error closing `%s': %s\n", outname, strerror (errno)); + return 0; + + write_error: + log_error ("error writing `%s': %s\n", outname, strerror (errno)); + if (!opt_no_split) + fclose (fpout); + return 2; + + read_error: + if (!opt_no_split) + { + int save = errno; + fclose (fpout); + errno = save; + } + return -1; +} + + + +static int +do_split (const char *fname, FILE *fp) +{ + int c, ctb, pkttype; + unsigned long pktlen = 0; + int partial = 0; + unsigned char header[20]; + int header_idx = 0; + + ctb = getc (fp); + if (ctb == EOF) + return 3; /* ready */ + header[header_idx++] = ctb; + + if (!(ctb & 0x80)) + { + log_error("invalid CTB %02x\n", ctb ); + return 1; + } + if ( (ctb & 0x40) ) + { /* new CTB */ + pkttype = (ctb & 0x3f); + if( (c = getc (fp)) == EOF ) + return -1; + header[header_idx++] = c; + + if ( c < 192 ) + pktlen = c; + else if ( c < 224 ) + { + pktlen = (c - 192) * 256; + if( (c = getc (fp)) == EOF ) + return -1; + header[header_idx++] = c; + pktlen += c + 192; + } + else if ( c == 255 ) + { + if (read_u32 (fp, &pktlen)) + return -1; + header[header_idx++] = pktlen >> 24; + header[header_idx++] = pktlen >> 16; + header[header_idx++] = pktlen >> 8; + header[header_idx++] = pktlen; + } + else + { /* partial body length */ + pktlen = c; + partial = 1; + } + } + else + { + int lenbytes; + + pkttype = (ctb>>2)&0xf; + lenbytes = ((ctb&3)==3)? 0 : (1<<(ctb & 3)); + if (!lenbytes ) + { + pktlen = 0; /* don't know the value */ + if( pkttype == PKT_COMPRESSED ) + partial = 3; + else + partial = 2; /* the old GnuPG partial length encoding */ + } + else + { + for ( ; lenbytes; lenbytes-- ) + { + pktlen <<= 8; + if( (c = getc (fp)) == EOF ) + return -1; + header[header_idx++] = c; + + pktlen |= c; + } + } + } + + return write_part (fname, fp, pktlen, pkttype, partial, + header, header_idx); +} + + +static void +split_packets (const char *fname) +{ + FILE *fp; + int rc; + + if (!fname || !strcmp (fname, "-")) + { + fp = stdin; + fname = "-"; + } + else if ( !(fp = fopen (fname,"rb")) ) + { + log_error ("can't open `%s': %s\n", fname, strerror (errno)); + return; + } + + while ( !(rc = do_split (fname, fp)) ) + ; + if ( rc > 0 ) + ; /* error already handled */ + else if ( ferror (fp) ) + log_error ("error reading `%s': %s\n", fname, strerror (errno)); + else + log_error ("premature EOF while reading `%s'\n", fname ); + + if ( fp != stdin ) + fclose (fp); +} diff --git a/tools/lspgpot b/tools/lspgpot new file mode 100755 index 000000000..f406392eb --- /dev/null +++ b/tools/lspgpot @@ -0,0 +1,27 @@ +#!/bin/sh +# lspgpot - script to extract the ownertrust values +# from PGP keyrings and list them in GnuPG ownertrust format. +# +# This file is free software; as a special exception the author gives +# unlimited permission to copy and/or distribute it, with or without +# modifications, as long as this notice is preserved. +# +# This program is distributed in the hope that it will be useful, but +# WITHOUT ANY WARRANTY, to the extent permitted by law; without even the +# implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + +if ! gpg --version > /dev/null 2>&1 ; then + echo "GnuPG not available!" + exit 1 +fi + +gpg --dry-run --with-fingerprint --with-colons $* | awk ' +BEGIN { FS=":" + printf "# Ownertrust listing generated by lspgpot\n" + printf "# This can be imported using the command:\n" + printf "# gpg --import-ownertrust\n\n" } +$1 == "fpr" { fpr = $10 } +$1 == "rtv" && $2 == 1 && $3 == 2 { printf "%s:3:\n", fpr; next } +$1 == "rtv" && $2 == 1 && $3 == 5 { printf "%s:4:\n", fpr; next } +$1 == "rtv" && $2 == 1 && $3 == 6 { printf "%s:5:\n", fpr; next } +' diff --git a/tools/mail-signed-keys b/tools/mail-signed-keys new file mode 100755 index 000000000..80fbb3481 --- /dev/null +++ b/tools/mail-signed-keys @@ -0,0 +1,114 @@ +#!/bin/sh +# Copyright (C) 2000, 2001 Free Software Foundation, Inc. +# +# This file is free software; as a special exception the author gives +# unlimited permission to copy and/or distribute it, with or without +# modifications, as long as this notice is preserved. +# +# This program is distributed in the hope that it will be useful, but +# WITHOUT ANY WARRANTY, to the extent permitted by law; without even the +# implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + +# FIXME: Add --dry-run, use only valid email addreses, extract only given keys + +dryrun=0 +if [ "$1" = "--dry-run" ]; then + dryrun=1 + shift +fi + +if [ -z "$1" -o -z "$2" -o -z "$3" ]; then + echo "usage: mail-signed-keys keyring signedby signame" >&2 + exit 1 +fi + +signame="$3" + +if [ ! -f $1 ]; then + echo "mail-signed-keys: '$1': no such file" >&2 + exit 1 +fi + +[ -f '.#tdb.tmp' ] && rm '.#tdb.tmp' +ro="--homedir . --no-options --trustdb-name=./.#tdb.tmp --dry-run --lock-never --no-default-keyring --keyring $1" + +signedby=`gpg $ro --list-keys --with-colons $2 \ + 2>/dev/null | awk -F: '$1=="pub" {print $5; exit 0}'` + +if [ -z "$signedby" ]; then + echo "mail-signed-keys: '$2': no such signator" >&2 + exit 1 +fi + +if [ "$dryrun" = "0" ]; then + echo "About to send the the keys signed by $signedby" >&2 + echo -n "to their owners. Do you really want to do this? (y/N)" >&2 + read + [ "$REPLY" != "y" -a "$REPLY" != "Y" ] && exit 0 +fi + +gpg $ro --check-sigs --with-colons 2>/dev/null \ + | awk -F: -v signedby="$signedby" -v gpgopt="$ro" \ + -v dryrun="$dryrun" -v signame="$signame" ' +BEGIN { sendmail="/usr/lib/sendmail -oi -t " } +$1 == "pub" { nextkid=$5; nextuid=$10 + if( uidcount > 0 ) { myflush() } + kid=nextkid; uid=nextuid; next + } +$1 == "uid" { uid=$10 ; next } +$1 == "sig" && $2 == "!" && $5 == signedby { uids[uidcount++] = uid; next } +END { if( uidcount > 0 ) { myflush() } } + +function myflush() +{ + if ( kid == signedby ) { uidcount=0; return } + print "sending key " substr(kid,9) " to" | "cat >&2" + for(i=0; i < 1; i++ ) { + print " " uids[i] | "cat >&2" + if( dryrun == 0 ) { + if( i == 0 ) { + printf "To: %s", uids[i] | sendmail + } + else { + printf ",\n %s", uids[i] | sendmail + } + } + } + if(dryrun == 0) { + printf "\n" | sendmail + print "Subject: I signed your key " substr(kid,9) | sendmail + print "" | sendmail + print "Hi," | sendmail + print "" | sendmail + print "Here you get back the signed key." | sendmail + print "Please send it yourself to a keyserver." | sendmail + print "" | sendmail + print "Peace," | sendmail + print " " signame | sendmail + print "" | sendmail + cmd = "gpg " gpgopt " --export -a " kid " 2>/dev/null" + while( (cmd | getline) > 0 ) { + print | sendmail + } + print "" | sendmail + close(cmd) + close( sendmail ) + } + uidcount=0 +} +' + + + + + + + + + + + + + + + diff --git a/tools/make-dns-cert.c b/tools/make-dns-cert.c new file mode 100644 index 000000000..496b63b0b --- /dev/null +++ b/tools/make-dns-cert.c @@ -0,0 +1,239 @@ +/* make-dns-cert.c - An OpenPGP-to-DNS CERT conversion tool + * Copyright (C) 2006 Free Software Foundation, Inc. + * + * This file is part of GnuPG. + * + * GnuPG is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * GnuPG is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, + * USA. + */ + +#include <config.h> +#include <unistd.h> +#ifdef HAVE_GETOPT_H +#include <getopt.h> +#endif +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <errno.h> +#include <sys/types.h> +#include <sys/stat.h> +#include <fcntl.h> + +/* We use TYPE37 instead of CERT since not all nameservers can handle + CERT yet... */ + +static int +cert_key(const char *name,const char *keyfile) +{ + int fd,ret=1,err,i; + struct stat statbuf; + + fd=open(keyfile,O_RDONLY); + if(fd==-1) + { + fprintf(stderr,"Cannot open key file %s: %s\n",keyfile,strerror(errno)); + return 1; + } + + err=fstat(fd,&statbuf); + if(err==-1) + { + fprintf(stderr,"Unable to stat key file %s: %s\n", + keyfile,strerror(errno)); + goto fail; + } + + if(statbuf.st_size>65536) + { + fprintf(stderr,"Key %s too large for CERT encoding\n",keyfile); + goto fail; + } + + if(statbuf.st_size>16384) + fprintf(stderr,"Warning: key file %s is larger than the default" + " GnuPG max-cert-size\n",keyfile); + + printf("%s\tTYPE37\t\\# %u 0003 0000 00 ", + name,(unsigned int)statbuf.st_size+5); + + err=1; + while(err!=0) + { + unsigned char buffer[1024]; + + err=read(fd,buffer,1024); + if(err==-1) + { + fprintf(stderr,"Unable to read key file %s: %s\n", + keyfile,strerror(errno)); + goto fail; + } + + for(i=0;i<err;i++) + printf("%02X",buffer[i]); + } + + printf("\n"); + + ret=0; + + fail: + close(fd); + + return ret; +} + +static int +url_key(const char *name,const char *fpr,const char *url) +{ + int len=6,fprlen=0; + + if(fpr) + { + const char *tmp = fpr; + while (*tmp) + { + if ((*tmp >= 'A' && *tmp <= 'F') || + (*tmp >= 'a' && *tmp <= 'f') || + (*tmp >= '0' && *tmp <= '9')) + { + fprlen++; + } + else if (*tmp != ' ' && *tmp != '\t') + { + fprintf(stderr,"Fingerprint must consist of only hex digits" + " and whitespace\n"); + return 1; + } + + tmp++; + } + + if(fprlen%2) + { + fprintf(stderr,"Fingerprint must be an even number of characters\n"); + return 1; + } + + fprlen/=2; + len+=fprlen; + } + + if(url) + len+=strlen(url); + + if(!fpr && !url) + { + fprintf(stderr, + "Cannot generate a CERT without either a fingerprint or URL\n"); + return 1; + } + + printf("%s\tTYPE37\t\\# %d 0006 0000 00 %02X",name,len,fprlen); + + if(fpr) + printf(" %s",fpr); + + if(url) + { + const char *c; + printf(" "); + for(c=url;*c;c++) + printf("%02X",*c); + } + + printf("\n"); + + return 0; +} + +static void +usage(FILE *stream) +{ + fprintf(stream,"make-dns-cert\n"); + fprintf(stream,"\t-f\tfingerprint\n"); + fprintf(stream,"\t-u\tURL\n"); + fprintf(stream,"\t-k\tkey file\n"); + fprintf(stream,"\t-n\tDNS name\n"); +} + +int +main(int argc,char *argv[]) +{ + int arg,err=1; + char *fpr=NULL,*url=NULL,*keyfile=NULL,*name=NULL; + + if(argc==1) + { + usage(stderr); + return 1; + } + else if(argc>1 && strcmp(argv[1],"--version")==0) + { + printf("make-dns-cert (GnuPG) " VERSION "\n"); + return 0; + } + else if(argc>1 && strcmp(argv[1],"--help")==0) + { + usage(stdout); + return 0; + } + + while((arg=getopt(argc,argv,"hf:u:k:n:"))!=-1) + switch(arg) + { + default: + case 'h': + usage(stdout); + exit(0); + + case 'f': + fpr=optarg; + break; + + case 'u': + url=optarg; + break; + + case 'k': + keyfile=optarg; + break; + + case 'n': + name=optarg; + break; + } + + if(!name) + { + fprintf(stderr,"No name provided\n"); + return 1; + } + + if(keyfile && (fpr || url)) + { + fprintf(stderr,"Cannot generate a CERT record with both a keyfile and" + " a fingerprint or URL\n"); + return 1; + } + + if(keyfile) + err=cert_key(name,keyfile); + else + err=url_key(name,fpr,url); + + return err; +} diff --git a/tools/mk-tdata.c b/tools/mk-tdata.c new file mode 100644 index 000000000..833875d28 --- /dev/null +++ b/tools/mk-tdata.c @@ -0,0 +1,67 @@ +/* mk-tdata.c - Create some simple random testdata + * Copyright (C) 1998, 1999, 2000, 2001, 2006 Free Software Foundation, Inc. + * + * This file is free software; as a special exception the author gives + * unlimited permission to copy and/or distribute it, with or without + * modifications, as long as this notice is preserved. + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY, to the extent permitted by law; without even the + * implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. + */ + +#include <config.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> + + +#ifndef RAND_MAX /* for SunOS */ +#define RAND_MAX 32767 +#endif + +int +main(int argc, char **argv) +{ + int i, c = 0; + int limit =0; + int char_mode = 0; + + if (argc) + { + argc--; + argv++; + } + + /* Check for option --char N */ + if (argc > 1 && !strcmp (argv[0], "--char")) + { + char_mode = 1; + c = strtol (argv[1], NULL, 0); + argc -= 2; + argv += 2; + } + + limit = argc ? atoi(argv[0]) : 0; + + srand(getpid()); + + for (i=0; !limit || i < limit; i++ ) + { + if (char_mode) + { + putchar (c); + } + else + { +#ifdef HAVE_RAND + c = ((unsigned)(1 + (int) (256.0*rand()/(RAND_MAX+1.0)))-1); +#else + c = ((unsigned)(1 + (int) (256.0*random()/(RAND_MAX+1.0)))-1); +#endif + putchar (c); + } + } + return 0; +} diff --git a/tools/pgpgroup-to-gpggroup b/tools/pgpgroup-to-gpggroup new file mode 100755 index 000000000..5ea9990b6 --- /dev/null +++ b/tools/pgpgroup-to-gpggroup @@ -0,0 +1,42 @@ +#!/usr/bin/perl -w + +# pgpgroup-to-gpggroup - convert PGP groups to GnuPG groups +# Copyright (C) 2004 Free Software Foundation, Inc. +# +# This program is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2 of the License, or +# (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, but +# WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software +# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + +# This program requires a PGP command line program that supports +# groups (note that the PGP 8 command line doesn't). + +$pgp="pgp -gvv 2>/dev/null"; + +open(PGP,"$pgp|") || die "Unable to call PGP: $!"; + +while(<PGP>) +{ + # If the line begins with a ">", then it is a new group. + + if(/^ > (\S+)/) + { + print "\ngroup $1 = "; + } + elsif(/\s+(0x\S+)/) + { + print "$1 "; + } +} + +print "\n"; +close(PGP); |