[svn] GnuPG - r5312 - trunk/g10
svn author wk
cvs at cvs.gnupg.org
Tue Apr 20 19:57:51 CEST 2010
Author: wk
Date: 2010-04-20 19:57:50 +0200 (Tue, 20 Apr 2010)
New Revision: 5312
Modified:
trunk/g10/ChangeLog
trunk/g10/call-agent.c
trunk/g10/call-agent.h
trunk/g10/card-util.c
trunk/g10/export.c
trunk/g10/getkey.c
trunk/g10/gpg.h
trunk/g10/gpgv.c
trunk/g10/keydb.h
trunk/g10/keyedit.c
trunk/g10/keygen.c
trunk/g10/keyid.c
trunk/g10/keylist.c
trunk/g10/main.h
trunk/g10/packet.h
trunk/g10/pkglue.c
trunk/g10/pkglue.h
trunk/g10/pubkey-enc.c
trunk/g10/revoke.c
trunk/g10/seckey-cert.c
trunk/g10/seskey.c
trunk/g10/sig-check.c
trunk/g10/sign.c
Log:
Generating an OpenPGP key cia gpg-agent basically works.
[The diff below has been truncated]
Modified: trunk/g10/ChangeLog
===================================================================
--- trunk/g10/ChangeLog 2010-04-20 13:47:12 UTC (rev 5311)
+++ trunk/g10/ChangeLog 2010-04-20 17:57:50 UTC (rev 5312)
@@ -1,3 +1,38 @@
+2010-04-20 Werner Koch <wk at g10code.com>
+
+ * keylist.c (list_keyblock_colon): Print the keygrip.
+
+ * sign.c (do_sign): Call the agent to create the signature.
+ (mpi_from_sexp): New.
+ * keyid.c (keygrip_from_pk, hexkeygrip_from_pk): New.
+ * call-agent.c (agent_pksign): New.
+ * pkglue.c (pk_sign): Remove.
+
+ * keygen.c (generate_keypair): Do not ask for a passphrase.
+
+2010-04-15 Werner Koch <wk at g10code.com>
+
+ * keygen.c (gen_dsa, gen_elg, gen_rsa): Remove args SEC_ROOT, DEK,
+ S2K and RET_SK. Change to use the gpg-agent based key generation.
+ Factor common code out to ...
+ (common_gen): New.
+ (do_create): Remove args SEC_ROOT, DEK, S2K and RET_SK.
+ (do_generate_keypair, write_selfsigs, write_direct_sig)
+ (write_keybinding, make_backsig): Adjust for above changes.
+ (generate_subkeypair): Remove arg SEC_KEYBLOCK.
+ (genhelp_protect, genhelp_factors): Remove.
+ (get_parameter_dek, get_parameter_s2k): Remove.
+
+ * call-agent.c (start_agent): Add dummy arg CTRL.
+ (agent_havekey, keyinfo_status_cb, agent_get_keyinfo)
+ (agent_genkey): New.
+
+ * seckey-cert.c (check_secret_key): Remove
+ (is_secret_key_protected): Take a public key as arg.
+ (protect_secret_key): Remove.
+
+ * seskey.c (encode_md_value): Remove SK arg.
+
2010-04-14 Werner Koch <wk at g10code.com>
* cpr.c (myread) [W32CE]: Do not use raise.
Modified: trunk/g10/call-agent.c
===================================================================
--- trunk/g10/call-agent.c 2010-04-20 13:47:12 UTC (rev 5311)
+++ trunk/g10/call-agent.c 2010-04-20 17:57:50 UTC (rev 5312)
@@ -1,6 +1,6 @@
/* call-agent.c - Divert GPG operations to the agent.
- * Copyright (C) 2001, 2002, 2003, 2006, 2007,
- * 2008, 2009 Free Software Foundation, Inc.
+ * Copyright (C) 2001, 2002, 2003, 2006, 2007, 2008, 2009,
+ * 2010 Free Software Foundation, Inc.
*
* This file is part of GnuPG.
*
@@ -69,14 +69,15 @@
size_t keydatalen;
};
-struct genkey_parm_s
+struct genkey_parm_s
{
+ ctrl_t ctrl;
assuan_context_t ctx;
- const char *sexp;
- size_t sexplen;
+ const char *keyparms;
};
+
static gpg_error_t learn_status_cb (void *opaque, const char *line);
@@ -107,10 +108,12 @@
/* Try to connect to the agent via socket or fork it off and work by
pipes. Handle the server's initial greeting */
static int
-start_agent (int for_card)
+start_agent (ctrl_t ctrl, int for_card)
{
int rc;
+ (void)ctrl; /* Not yet used. */
+
/* Fixme: We need a context for each thread or serialize the access
to the agent. */
if (agent_ctx)
@@ -486,7 +489,7 @@
{
int rc;
- rc = start_agent (1);
+ rc = start_agent (NULL, 1);
if (rc)
return rc;
@@ -531,7 +534,7 @@
return gpg_error (GPG_ERR_TOO_LARGE);
stpcpy (stpcpy (line, "SCD GETATTR "), name);
- rc = start_agent (1);
+ rc = start_agent (NULL, 1);
if (rc)
return rc;
@@ -581,7 +584,7 @@
}
*p = 0;
- rc = start_agent (1);
+ rc = start_agent (NULL, 1);
if (!rc)
{
rc = assuan_transact (agent_ctx, line, NULL, NULL,
@@ -623,7 +626,7 @@
char line[ASSUAN_LINELENGTH];
struct writecert_parm_s parms;
- rc = start_agent (1);
+ rc = start_agent (NULL, 1);
if (rc)
return rc;
@@ -673,7 +676,7 @@
(void)serialno;
- rc = start_agent (1);
+ rc = start_agent (NULL, 1);
if (rc)
return rc;
@@ -762,7 +765,7 @@
(void)serialno;
- rc = start_agent (1);
+ rc = start_agent (NULL, 1);
if (rc)
return rc;
@@ -909,7 +912,7 @@
*r_buf = NULL;
*r_buflen = 0;
- rc = start_agent (1);
+ rc = start_agent (NULL, 1);
if (gpg_err_code (rc) == GPG_ERR_CARD_NOT_PRESENT
|| gpg_err_code (rc) == GPG_ERR_NOT_SUPPORTED)
rc = 0; /* We check later. */
@@ -972,7 +975,7 @@
size_t len;
*r_buf = NULL;
- rc = start_agent (1);
+ rc = start_agent (NULL, 1);
if (gpg_err_code (rc) == GPG_ERR_CARD_NOT_PRESENT
|| gpg_err_code (rc) == GPG_ERR_NOT_SUPPORTED)
rc = 0; /* We check later. */
@@ -1029,7 +1032,7 @@
size_t len;
*r_buf = NULL;
- rc = start_agent (1);
+ rc = start_agent (NULL, 1);
if (rc)
return rc;
@@ -1077,7 +1080,7 @@
reset = "--reset";
chvno %= 100;
- rc = start_agent (1);
+ rc = start_agent (NULL, 1);
if (rc)
return rc;
@@ -1099,7 +1102,7 @@
int rc;
char line[ASSUAN_LINELENGTH];
- rc = start_agent (1);
+ rc = start_agent (NULL, 1);
if (rc)
return rc;
@@ -1146,7 +1149,7 @@
*r_passphrase = NULL;
- rc = start_agent (0);
+ rc = start_agent (NULL, 0);
if (rc)
return rc;
@@ -1217,7 +1220,7 @@
if (!cache_id || !*cache_id)
return 0;
- rc = start_agent (0);
+ rc = start_agent (NULL, 0);
if (rc)
return rc;
@@ -1237,7 +1240,7 @@
char *tmp;
char line[ASSUAN_LINELENGTH];
- rc = start_agent (0);
+ rc = start_agent (NULL, 0);
if (rc)
return rc;
@@ -1264,7 +1267,7 @@
*r_count = 0;
- err = start_agent (0);
+ err = start_agent (NULL, 0);
if (err)
return err;
@@ -1289,3 +1292,291 @@
return err;
}
+
+
+/* Ask the agent whether a secret key with the given keygrip is
+ known. */
+gpg_error_t
+agent_havekey (ctrl_t ctrl, const char *hexkeygrip)
+{
+ gpg_error_t err;
+ char line[ASSUAN_LINELENGTH];
+
+ err = start_agent (ctrl, 0);
+ if (err)
+ return err;
+
+ if (!hexkeygrip || strlen (hexkeygrip) != 40)
+ return gpg_error (GPG_ERR_INV_VALUE);
+
+ snprintf (line, DIM(line)-1, "HAVEKEY %s", hexkeygrip);
+ line[DIM(line)-1] = 0;
+
+ err = assuan_transact (agent_ctx, line, NULL, NULL, NULL, NULL, NULL, NULL);
+ return err;
+}
+
+
+
+static gpg_error_t
+keyinfo_status_cb (void *opaque, const char *line)
+{
+ char **serialno = opaque;
+ const char *s, *s2;
+
+ if (!strncmp (line, "KEYINFO ", 8) && !*serialno)
+ {
+ s = strchr (line+8, ' ');
+ if (s && s[1] == 'T' && s[2] == ' ' && s[3])
+ {
+ s += 3;
+ s2 = strchr (s, ' ');
+ if ( s2 > s )
+ {
+ *serialno = xtrymalloc ((s2 - s)+1);
+ if (*serialno)
+ {
+ memcpy (*serialno, s, s2 - s);
+ (*serialno)[s2 - s] = 0;
+ }
+ }
+ }
+ }
+ return 0;
+}
+
+
+/* Return the serial number for a secret key. If the returned serial
+ number is NULL, the key is not stored on a smartcard. Caller needs
+ to free R_SERIALNO. */
+gpg_error_t
+agent_get_keyinfo (ctrl_t ctrl, const char *hexkeygrip, char **r_serialno)
+{
+ gpg_error_t err;
+ char line[ASSUAN_LINELENGTH];
+ char *serialno = NULL;
+
+ *r_serialno = NULL;
+
+ err = start_agent (ctrl, 0);
+ if (err)
+ return err;
+
+ if (!hexkeygrip || strlen (hexkeygrip) != 40)
+ return gpg_error (GPG_ERR_INV_VALUE);
+
+ snprintf (line, DIM(line)-1, "KEYINFO %s", hexkeygrip);
+ line[DIM(line)-1] = 0;
+
+ err = assuan_transact (agent_ctx, line, NULL, NULL, NULL, NULL,
+ keyinfo_status_cb, &serialno);
+ if (!err && serialno)
+ {
+ /* Sanity check for bad characters. */
+ if (strpbrk (serialno, ":\n\r"))
+ err = GPG_ERR_INV_VALUE;
+ }
+ if (err)
+ xfree (serialno);
+ else
+ *r_serialno = serialno;
+ return err;
+}
+
+
+
+/* Handle a KEYPARMS inquiry. Note, we only send the data,
+ assuan_transact takes care of flushing and writing the end */
+static gpg_error_t
+inq_genkey_parms (void *opaque, const char *line)
+{
+ struct genkey_parm_s *parm = opaque;
+ gpg_error_t err;
+
+ if (!strncmp (line, "KEYPARAM", 8) && (line[8]==' '||!line[8]))
+ {
+ err = assuan_send_data (parm->ctx,
+ parm->keyparms, strlen (parm->keyparms));
+ }
+ else
+ err = default_inq_cb (parm->ctrl, line);
+
+ return err;
+}
+
+
+/* Call the agent to generate a new key. KEYPARMS is the usual
+ S-expression giving the parameters of the key. gpg-agent passes it
+ gcry_pk_genkey. */
+gpg_error_t
+agent_genkey (ctrl_t ctrl, const char *keyparms, gcry_sexp_t *r_pubkey)
+{
+ gpg_error_t err;
+ struct genkey_parm_s gk_parm;
+ membuf_t data;
+ size_t len;
+ unsigned char *buf;
+
+ *r_pubkey = NULL;
+ err = start_agent (ctrl, 0);
+ if (err)
+ return err;
+
+ err = assuan_transact (agent_ctx, "RESET",
+ NULL, NULL, NULL, NULL, NULL, NULL);
+ if (err)
+ return err;
+
+ init_membuf (&data, 1024);
+ gk_parm.ctrl = ctrl;
+ gk_parm.ctx = agent_ctx;
+ gk_parm.keyparms = keyparms;
+ err = assuan_transact (agent_ctx, "GENKEY",
+ membuf_data_cb, &data,
+ inq_genkey_parms, &gk_parm, NULL, NULL);
+ if (err)
+ {
+ xfree (get_membuf (&data, &len));
+ return err;
+ }
+
+ buf = get_membuf (&data, &len);
+ if (!buf)
+ err = gpg_error_from_syserror ();
+ else
+ {
+ err = gcry_sexp_sscan (r_pubkey, NULL, buf, len);
+ xfree (buf);
+ }
+ return err;
+}
+
+
+
+
+/* FIXME: Call the agent to read the public key part for a given keygrip. If
+ FROMCARD is true, the key is directly read from the current
+ smartcard. In this case HEXKEYGRIP should be the keyID
+ (e.g. OPENPGP.3). */
+/* int */
+/* agent_readkey (ctrl_t ctrl, int fromcard, const char *hexkeygrip, */
+/* ksba_sexp_t *r_pubkey) */
+/* { */
+/* int rc; */
+/* membuf_t data; */
+/* size_t len; */
+/* unsigned char *buf; */
+/* char line[ASSUAN_LINELENGTH]; */
+
+/* *r_pubkey = NULL; */
+/* rc = start_agent (ctrl); */
+/* if (rc) */
+/* return rc; */
+
+/* rc = assuan_transact (agent_ctx, "RESET",NULL, NULL, NULL, NULL, NULL, NULL); */
+/* if (rc) */
+/* return rc; */
+
+/* snprintf (line, DIM(line)-1, "%sREADKEY %s", */
+/* fromcard? "SCD ":"", hexkeygrip); */
+/* line[DIM(line)-1] = 0; */
+
+/* init_membuf (&data, 1024); */
+/* rc = assuan_transact (agent_ctx, line, */
+/* membuf_data_cb, &data, */
+/* default_inq_cb, ctrl, NULL, NULL); */
+/* if (rc) */
+/* { */
+/* xfree (get_membuf (&data, &len)); */
+/* return rc; */
+/* } */
+/* buf = get_membuf (&data, &len); */
+/* if (!buf) */
+/* return gpg_error (GPG_ERR_ENOMEM); */
+/* if (!gcry_sexp_canon_len (buf, len, NULL, NULL)) */
+/* { */
+/* xfree (buf); */
+/* return gpg_error (GPG_ERR_INV_SEXP); */
+/* } */
+/* *r_pubkey = buf; */
+/* return 0; */
+/* } */
+
+
+
+/* Call the agent to do a sign operation using the key identified by
+ the hex string KEYGRIP. DESC is a description of the key to be
+ displayed if the agent needs to ask for the PIN. DIGEST and
+ DIGESTLEN is the hash value to sign and DIGESTALGO the algorithm id
+ used to compute the digest. */
+gpg_error_t
+agent_pksign (ctrl_t ctrl, const char *keygrip, const char *desc,
+ unsigned char *digest, size_t digestlen, int digestalgo,
+ gcry_sexp_t *r_sigval)
+{
+ gpg_error_t err;
+ int i;
+ char *p, line[ASSUAN_LINELENGTH];
+ membuf_t data;
+
+ *r_sigval = NULL;
+ err = start_agent (ctrl, 0);
+ if (err)
+ return err;
+
+ if (digestlen*2 + 50 > DIM(line))
+ return gpg_error (GPG_ERR_GENERAL);
+
+ err = assuan_transact (agent_ctx, "RESET",
+ NULL, NULL, NULL, NULL, NULL, NULL);
+ if (err)
+ return err;
+
+ snprintf (line, DIM(line)-1, "SIGKEY %s", keygrip);
+ line[DIM(line)-1] = 0;
+ err = assuan_transact (agent_ctx, line, NULL, NULL, NULL, NULL, NULL, NULL);
+ if (err)
+ return err;
+
+ if (desc)
+ {
+ snprintf (line, DIM(line)-1, "SETKEYDESC %s", desc);
+ line[DIM(line)-1] = 0;
+ err = assuan_transact (agent_ctx, line,
+ NULL, NULL, NULL, NULL, NULL, NULL);
+ if (err)
+ return err;
+ }
+
+ snprintf (line, sizeof line, "SETHASH %d ", digestalgo);
+ p = line + strlen (line);
+ for (i=0; i < digestlen ; i++, p += 2 )
+ sprintf (p, "%02X", digest[i]);
+ err = assuan_transact (agent_ctx, line, NULL, NULL, NULL, NULL, NULL, NULL);
+ if (err)
+ return err;
+
+ init_membuf (&data, 1024);
+ err = assuan_transact (agent_ctx, "PKSIGN",
+ membuf_data_cb, &data, default_inq_cb, ctrl,
+ NULL, NULL);
+ if (err)
+ xfree (get_membuf (&data, NULL));
+ else
+ {
+ unsigned char *buf;
+ size_t len;
+
+ buf = get_membuf (&data, &len);
+ if (!buf)
+ err = gpg_error_from_syserror ();
+ else
+ {
+ err = gcry_sexp_sscan (r_sigval, NULL, buf, len);
+ xfree (buf);
+ }
+ }
+ return err;
+}
+
+
Modified: trunk/g10/call-agent.h
===================================================================
--- trunk/g10/call-agent.h 2010-04-20 13:47:12 UTC (rev 5311)
+++ trunk/g10/call-agent.h 2010-04-20 17:57:50 UTC (rev 5312)
@@ -140,6 +140,24 @@
/* Return the S2K iteration count as computed by gpg-agent. */
gpg_error_t agent_get_s2k_count (unsigned long *r_count);
+/* Check whether a secret key with HEXKEYGRIP is available. */
+gpg_error_t agent_havekey (ctrl_t ctrl, const char *hexkeygrip);
+/* Return infos about the secret key with HEXKEYGRIP. */
+gpg_error_t agent_get_keyinfo (ctrl_t ctrl, const char *hexkeygrip,
+ char **r_serialno);
+
+/* Generate a new key. */
+gpg_error_t agent_genkey (ctrl_t ctrl, const char *keyparms,
+ gcry_sexp_t *r_pubkey);
+
+/* Create a sigtnature. */
+gpg_error_t agent_pksign (ctrl_t ctrl, const char *keygrip, const char *desc,
+ unsigned char *digest, size_t digestlen,
+ int digestalgo,
+ gcry_sexp_t *r_sigval);
+
+
+
#endif /*GNUPG_G10_CALL_AGENT_H*/
Modified: trunk/g10/card-util.c
===================================================================
--- trunk/g10/card-util.c 2010-04-20 13:47:12 UTC (rev 5311)
+++ trunk/g10/card-util.c 2010-04-20 17:57:50 UTC (rev 5312)
@@ -1495,8 +1495,8 @@
the serialnumber and thus it won't harm. */
}
- okay = generate_card_subkeypair (pub_keyblock, sec_keyblock,
- keyno, info.serialno);
+ /* xxx = generate_card_subkeypair (pub_keyblock, sec_keyblock, */
+ /* keyno, info.serialno); */
leave:
agent_release_card_info (&info);
@@ -1612,17 +1612,18 @@
}
/* We better copy the key before we unprotect it. */
copied_sk = sk = copy_secret_key (NULL, sk);
- rc = check_secret_key (sk, 0);
+ rc = 0/*check_secret_key (sk, 0)*/;
if (rc)
goto leave;
}
- rc = save_unprotected_key_to_card (sk, keyno);
- if (rc)
- {
- log_error (_("error writing key to card: %s\n"), gpg_strerror (rc));
- goto leave;
- }
+#warning code save_unprotected_key_to_card
+ /* rc = save_unprotected_key_to_card (sk, keyno); */
+ /* if (rc) */
+ /* { */
+ /* log_error (_("error writing key to card: %s\n"), gpg_strerror (rc)); */
+ /* goto leave; */
+ /* } */
/* Get back to the maybe protected original secret key. */
if (copied_sk)
Modified: trunk/g10/export.c
===================================================================
--- trunk/g10/export.c 2010-04-20 13:47:12 UTC (rev 5311)
+++ trunk/g10/export.c 2010-04-20 17:57:50 UTC (rev 5312)
@@ -550,7 +550,7 @@
; /* Card key stub. */
else
{
- rc = check_secret_key( sk, 0 );
+ /* rc = check_secret_key( sk, 0 ); */
}
break;
}
Modified: trunk/g10/getkey.c
===================================================================
--- trunk/g10/getkey.c 2010-04-20 13:47:12 UTC (rev 5311)
+++ trunk/g10/getkey.c 2010-04-20 17:57:50 UTC (rev 5312)
@@ -526,7 +526,7 @@
{
/* Check the secret key (this may prompt for a passprase to
* unlock the secret key. */
- rc = check_secret_key (sk, 0);
+ /* rc = check_secret_key (sk, 0); */
}
return rc;
@@ -1111,8 +1111,8 @@
free_strlist (namelist);
- if (!rc && unprotect)
- rc = check_secret_key (sk, 0);
+ /* if (!rc && unprotect) */
+ /* rc = check_secret_key (sk, 0); */
return rc;
}
Modified: trunk/g10/gpg.h
===================================================================
--- trunk/g10/gpg.h 2010-04-20 13:47:12 UTC (rev 5311)
+++ trunk/g10/gpg.h 2010-04-20 17:57:50 UTC (rev 5312)
@@ -108,7 +108,7 @@
#define G10ERR_RENAME_FILE GPG_ERR_RENAME_FILE
#define G10ERR_RESOURCE_LIMIT GPG_ERR_RESOURCE_LIMIT
#define G10ERR_SIG_CLASS GPG_ERR_SIG_CLASS
-#define G10ERR_TIME_CONFLICT GPG_ERR_TIME_CONFLICT
+#define G10ERR_TIME_CONFLICT GPG_ERR_TIME_CONFLICT
#define G10ERR_TRUSTDB GPG_ERR_TRUSTDB
#define G10ERR_UNEXPECTED GPG_ERR_UNEXPECTED
#define G10ERR_UNKNOWN_PACKET GPG_ERR_UNKNOWN_PACKET
Modified: trunk/g10/gpgv.c
===================================================================
--- trunk/g10/gpgv.c 2010-04-20 13:47:12 UTC (rev 5311)
+++ trunk/g10/gpgv.c 2010-04-20 17:57:50 UTC (rev 5312)
@@ -399,9 +399,9 @@
* We don't use secret keys, but getkey.c links to this
*/
int
-check_secret_key (PKT_secret_key *sk, int n)
+check_secret_key (PKT_public_key *pk, int n)
{
- (void)sk;
+ (void)pk;
(void)n;
return G10ERR_GENERAL;
}
Modified: trunk/g10/keydb.h
===================================================================
--- trunk/g10/keydb.h 2010-04-20 13:47:12 UTC (rev 5311)
+++ trunk/g10/keydb.h 2010-04-20 17:57:50 UTC (rev 5312)
@@ -286,7 +286,10 @@
byte *fingerprint_from_pk( PKT_public_key *pk, byte *buf, size_t *ret_len );
char *serialno_and_fpr_from_sk (const unsigned char *sn, size_t snlen,
PKT_secret_key *sk);
+gpg_error_t keygrip_from_pk (PKT_public_key *pk, unsigned char *array);
+gpg_error_t hexkeygrip_from_pk (PKT_public_key *pk, char **r_grip);
+
/*-- kbnode.c --*/
KBNODE new_kbnode( PACKET *pkt );
KBNODE clone_kbnode( KBNODE node );
Modified: trunk/g10/keyedit.c
===================================================================
--- trunk/g10/keyedit.c 2010-04-20 13:47:12 UTC (rev 5311)
+++ trunk/g10/keyedit.c 2010-04-20 17:57:50 UTC (rev 5312)
@@ -1164,9 +1164,9 @@
keyid_from_sk (sk, keyid);
passphrase_clear_cache (keyid, NULL, 0);
- rc = check_secret_key( sk, 0 );
- if( !rc )
- passphrase = get_last_passphrase();
+ /* rc = check_secret_key( sk, 0 ); */
+ /* if( !rc ) */
+ /* passphrase = get_last_passphrase(); */
}
break;
}
@@ -1179,9 +1179,9 @@
&& (subsk->protect.s2k.mode == 1001
|| subsk->protect.s2k.mode == 1002))) {
set_next_passphrase( passphrase );
- rc = check_secret_key( subsk, 0 );
- if( !rc && !passphrase )
- passphrase = get_last_passphrase();
+ /* rc = check_secret_key( subsk, 0 ); */
+ /* if( !rc && !passphrase ) */
+ /* passphrase = get_last_passphrase(); */
}
}
}
@@ -1227,7 +1227,9 @@
if( !no_primary_secrets ) {
sk->protect.algo = dek->algo;
sk->protect.s2k = *s2k;
- rc = protect_secret_key( sk, dek );
+#warning fixme
+ rc = 0;
+ /* rc = protect_secret_key( sk, dek ); */
}
for(node=keyblock; !rc && node; node = node->next ) {
if( node->pkt->pkttype == PKT_SECRET_SUBKEY ) {
@@ -1237,7 +1239,9 @@
|| subsk->protect.s2k.mode == 1002))) {
subsk->protect.algo = dek->algo;
subsk->protect.s2k = *s2k;
- rc = protect_secret_key( subsk, dek );
+#warning fixme
+ rc = 0;
+ /* rc = protect_secret_key( subsk, dek ); */
}
}
}
@@ -1892,12 +1896,13 @@
break;
case cmdADDKEY:
- if( generate_subkeypair( keyblock, sec_keyblock ) ) {
+ if (!generate_subkeypair (keyblock))
+ {
redisplay = 1;
sec_modified = modified = 1;
merge_keys_and_selfsig( sec_keyblock );
merge_keys_and_selfsig( keyblock );
- }
+ }
break;
#ifdef ENABLE_CARD_SUPPORT
@@ -2018,8 +2023,8 @@
if (sk->protect.s2k.mode == 1002)
tty_printf (_("Secret parts of key"
" are stored on-card.\n"));
- else
- check_secret_key (sk, 0);
+ /* else */
+ /* check_secret_key (sk, 0); */
}
}
else /* Store it. */
Modified: trunk/g10/keygen.c
===================================================================
--- trunk/g10/keygen.c 2010-04-20 13:47:12 UTC (rev 5311)
+++ trunk/g10/keygen.c 2010-04-20 17:57:50 UTC (rev 5312)
@@ -132,15 +132,12 @@
static void do_generate_keypair( struct para_data_s *para,
struct output_control_s *outctrl, int card );
-static int write_keyblock( IOBUF out, KBNODE node );
-static int gen_card_key (int algo, int keyno, int is_primary,
- KBNODE pub_root, KBNODE sec_root,
- PKT_secret_key **ret_sk,
- u32 *timestamp,
- u32 expireval, struct para_data_s *para);
+static int write_keyblock (iobuf_t out, kbnode_t node);
+static int gen_card_key (int algo, int keyno, int is_primary, kbnode_t pub_root,
+ u32 *timestamp, u32 expireval,
+ struct para_data_s *para);
static int gen_card_key_with_backup (int algo, int keyno, int is_primary,
- KBNODE pub_root, KBNODE sec_root,
- u32 timestamp,
+ kbnode_t pub_root, u32 timestamp,
u32 expireval, struct para_data_s *para,
const char *backup_dir);
@@ -227,43 +224,46 @@
int
-keygen_add_key_expire( PKT_signature *sig, void *opaque )
+keygen_add_key_expire (PKT_signature *sig, void *opaque)
{
- PKT_public_key *pk = opaque;
- byte buf[8];
- u32 u;
-
- if( pk->expiredate ) {
- if(pk->expiredate > pk->timestamp)
- u= pk->expiredate - pk->timestamp;
- else
- u= 1;
-
- buf[0] = (u >> 24) & 0xff;
- buf[1] = (u >> 16) & 0xff;
- buf[2] = (u >> 8) & 0xff;
- buf[3] = u & 0xff;
- build_sig_subpkt( sig, SIGSUBPKT_KEY_EXPIRE, buf, 4 );
+ PKT_public_key *pk = opaque;
+ byte buf[8];
+ u32 u;
+
+ if (pk->expiredate)
+ {
+ if (pk->expiredate > pk->timestamp)
+ u = pk->expiredate - pk->timestamp;
+ else
+ u = 1;
+
+ buf[0] = (u >> 24) & 0xff;
+ buf[1] = (u >> 16) & 0xff;
+ buf[2] = (u >> 8) & 0xff;
+ buf[3] = u & 0xff;
+ build_sig_subpkt (sig, SIGSUBPKT_KEY_EXPIRE, buf, 4);
}
- else
- {
- /* Make sure we don't leave a key expiration subpacket lying
- around */
- delete_sig_subpkt (sig->hashed, SIGSUBPKT_KEY_EXPIRE);
- }
+ else
+ {
+ /* Make sure we don't leave a key expiration subpacket lying
+ around */
+ delete_sig_subpkt (sig->hashed, SIGSUBPKT_KEY_EXPIRE);
+ }
- return 0;
+ return 0;
}
+
static int
keygen_add_key_flags_and_expire (PKT_signature *sig, void *opaque)
{
- struct opaque_data_usage_and_pk *oduap = opaque;
-
- do_add_key_flags (sig, oduap->usage);
- return keygen_add_key_expire (sig, oduap->pk);
+ struct opaque_data_usage_and_pk *oduap = opaque;
+
+ do_add_key_flags (sig, oduap->usage);
+ return keygen_add_key_expire (sig, oduap->pk);
}
+
static int
set_one_pref (int val, int type, const char *item, byte *buf, int *nbuf)
{
@@ -697,19 +697,18 @@
/****************
* Add preference to the self signature packet.
* This is only called for packets with version > 3.
-
*/
int
-keygen_add_std_prefs( PKT_signature *sig, void *opaque )
+keygen_add_std_prefs (PKT_signature *sig, void *opaque)
{
- PKT_public_key *pk = opaque;
-
- do_add_key_flags (sig, pk->pubkey_usage);
- keygen_add_key_expire( sig, opaque );
- keygen_upd_std_prefs (sig, opaque);
- keygen_add_keyserver_url(sig,NULL);
-
- return 0;
+ PKT_public_key *pk = opaque;
+
+ do_add_key_flags (sig, pk->pubkey_usage);
+ keygen_add_key_expire (sig, opaque );
+ keygen_upd_std_prefs (sig, opaque);
+ keygen_add_keyserver_url (sig,NULL);
+
+ return 0;
}
int
@@ -778,23 +777,23 @@
}
int
-keygen_add_revkey(PKT_signature *sig, void *opaque)
+keygen_add_revkey (PKT_signature *sig, void *opaque)
{
- struct revocation_key *revkey=opaque;
+ struct revocation_key *revkey = opaque;
byte buf[2+MAX_FINGERPRINT_LEN];
- buf[0]=revkey->class;
- buf[1]=revkey->algid;
- memcpy(&buf[2],revkey->fpr,MAX_FINGERPRINT_LEN);
+ buf[0] = revkey->class;
+ buf[1] = revkey->algid;
+ memcpy (&buf[2], revkey->fpr, MAX_FINGERPRINT_LEN);
- build_sig_subpkt(sig,SIGSUBPKT_REV_KEY,buf,2+MAX_FINGERPRINT_LEN);
+ build_sig_subpkt (sig, SIGSUBPKT_REV_KEY, buf, 2+MAX_FINGERPRINT_LEN);
- /* All sigs with revocation keys set are nonrevocable */
- sig->flags.revocable=0;
+ /* All sigs with revocation keys set are nonrevocable. */
+ sig->flags.revocable = 0;
buf[0] = 0;
- build_sig_subpkt( sig, SIGSUBPKT_REVOCABLE, buf, 1 );
+ build_sig_subpkt (sig, SIGSUBPKT_REVOCABLE, buf, 1);
- parse_revkeys(sig);
+ parse_revkeys (sig);
return 0;
}
@@ -803,115 +802,118 @@
/* Create a back-signature. If TIMESTAMP is not NULL, use it for the
signature creation time. */
-int
-make_backsig (PKT_signature *sig,PKT_public_key *pk,
- PKT_public_key *sub_pk,PKT_secret_key *sub_sk,
+gpg_error_t
+make_backsig (PKT_signature *sig, PKT_public_key *pk,
+ PKT_public_key *sub_pk, PKT_public_key *sub_psk,
u32 timestamp)
{
+ gpg_error_t err;
PKT_signature *backsig;
- int rc;
- cache_public_key(sub_pk);
+ cache_public_key (sub_pk);
- rc = make_keysig_packet (&backsig, pk, NULL, sub_pk, sub_sk, 0x19,
- 0, 0, timestamp, 0, NULL, NULL);
- if(rc)
- log_error("make_keysig_packet failed for backsig: %s\n",g10_errstr(rc));
+ err = make_keysig_packet (&backsig, pk, NULL, sub_pk, sub_psk, 0x19,
+ 0, 0, timestamp, 0, NULL, NULL);
+ if (err)
+ log_error ("make_keysig_packet failed for backsig: %s\n", g10_errstr(err));
else
{
/* Get it into a binary packed form. */
- IOBUF backsig_out=iobuf_temp();
+ IOBUF backsig_out = iobuf_temp();
PACKET backsig_pkt;
- init_packet(&backsig_pkt);
- backsig_pkt.pkttype=PKT_SIGNATURE;
- backsig_pkt.pkt.signature=backsig;
- rc=build_packet(backsig_out,&backsig_pkt);
- free_packet(&backsig_pkt);
- if(rc)
- log_error("build_packet failed for backsig: %s\n",g10_errstr(rc));
+ init_packet (&backsig_pkt);
+ backsig_pkt.pkttype = PKT_SIGNATURE;
+ backsig_pkt.pkt.signature = backsig;
+ err = build_packet (backsig_out, &backsig_pkt);
+ free_packet (&backsig_pkt);
+ if (err)
+ log_error ("build_packet failed for backsig: %s\n", g10_errstr(err));
else
{
- size_t pktlen=0;
- byte *buf=iobuf_get_temp_buffer(backsig_out);
+ size_t pktlen = 0;
+ byte *buf = iobuf_get_temp_buffer (backsig_out);
- /* Remove the packet header */
+ /* Remove the packet header. */
if(buf[0]&0x40)
{
- if(buf[1]<192)
+ if (buf[1] < 192)
{
- pktlen=buf[1];
- buf+=2;
- }
- else if(buf[1]<224)
+ pktlen = buf[1];
+ buf += 2;
+ }
+ else if(buf[1] < 224)
{
- pktlen=(buf[1]-192)*256;
- pktlen+=buf[2]+192;
- buf+=3;
+ pktlen = (buf[1]-192)*256;
+ pktlen += buf[2]+192;
+ buf += 3;
}
- else if(buf[1]==255)
+ else if (buf[1] == 255)
{
- pktlen =buf[2] << 24;
- pktlen|=buf[3] << 16;
- pktlen|=buf[4] << 8;
- pktlen|=buf[5];
- buf+=6;
+ pktlen = buf[2] << 24;
+ pktlen |= buf[3] << 16;
+ pktlen |= buf[4] << 8;
+ pktlen |= buf[5];
+ buf += 6;
}
else
- BUG();
+ BUG ();
}
else
{
- int mark=1;
+ int mark = 1;
- switch(buf[0]&3)
+ switch (buf[0]&3)
{
case 3:
- BUG();
+ BUG ();
break;
case 2:
- pktlen =buf[mark++] << 24;
- pktlen|=buf[mark++] << 16;
+ pktlen = buf[mark++] << 24;
+ pktlen |= buf[mark++] << 16;
case 1:
- pktlen|=buf[mark++] << 8;
+ pktlen |= buf[mark++] << 8;
case 0:
- pktlen|=buf[mark++];
+ pktlen |= buf[mark++];
}
- buf+=mark;
+ buf += mark;
}
/* Now make the binary blob into a subpacket. */
- build_sig_subpkt(sig,SIGSUBPKT_SIGNATURE,buf,pktlen);
+ build_sig_subpkt (sig, SIGSUBPKT_SIGNATURE, buf, pktlen);
- iobuf_close(backsig_out);
+ iobuf_close (backsig_out);
}
}
-
- return rc;
+
+ return err;
}
-static int
-write_direct_sig (KBNODE root, KBNODE pub_root, PKT_secret_key *sk,
- struct revocation_key *revkey, u32 timestamp)
+/* Write a direct key signature to the first key in ROOT using the key
+ PSK. REVKEY is describes the direct key signature and TIMESTAMP is
+ the timestamp to set on the signature. */
+static gpg_error_t
+write_direct_sig (KBNODE root, PKT_public_key *psk,
+ struct revocation_key *revkey, u32 timestamp)
{
+ gpg_error_t err;
PACKET *pkt;
PKT_signature *sig;
- int rc=0;
KBNODE node;
PKT_public_key *pk;
- if( opt.verbose )
- log_info(_("writing direct signature\n"));
+ if (opt.verbose)
+ log_info (_("writing direct signature\n"));
/* Get the pk packet from the pub_tree. */
- node = find_kbnode( pub_root, PKT_PUBLIC_KEY );
- if( !node )
- BUG();
+ node = find_kbnode (root, PKT_PUBLIC_KEY);
+ if (!node)
+ BUG ();
pk = node->pkt->pkt.public_key;
/* We have to cache the key, so that the verification of the
@@ -919,48 +921,54 @@
cache_public_key (pk);
/* Make the signature. */
- rc = make_keysig_packet (&sig,pk,NULL,NULL,sk,0x1F,
- 0, 0, timestamp, 0,
- keygen_add_revkey, revkey);
- if( rc )
+ err = make_keysig_packet (&sig, pk, NULL,NULL, psk, 0x1F,
+ 0, 0, timestamp, 0,
+ keygen_add_revkey, revkey);
+ if (err)
{
- log_error("make_keysig_packet failed: %s\n", g10_errstr(rc) );
- return rc;
+ log_error ("make_keysig_packet failed: %s\n", g10_errstr (err) );
+ return err;
}
- pkt = xmalloc_clear( sizeof *pkt );
+ pkt = xmalloc_clear (sizeof *pkt);
pkt->pkttype = PKT_SIGNATURE;
pkt->pkt.signature = sig;
- add_kbnode( root, new_kbnode( pkt ) );
- return rc;
+ add_kbnode (root, new_kbnode (pkt));
+ return err;
}
-static int
-write_selfsigs( KBNODE sec_root, KBNODE pub_root, PKT_secret_key *sk,
- unsigned int use, u32 timestamp )
+
+/* Write a self-signature to the first user id in ROOT using the key
+ PSK. USE and TIMESTAMP give the extra data we need for the
+ signature. */
+static gpg_error_t
+write_selfsigs (KBNODE root, PKT_public_key *psk,
+ unsigned int use, u32 timestamp)
{
+ gpg_error_t err;
PACKET *pkt;
PKT_signature *sig;
PKT_user_id *uid;
- int rc=0;
KBNODE node;
PKT_public_key *pk;
- if( opt.verbose )
- log_info(_("writing self signature\n"));
+ if (opt.verbose)
+ log_info (_("writing self signature\n"));
/* Get the uid packet from the list. */
- node = find_kbnode( pub_root, PKT_USER_ID );
- if( !node )
+ node = find_kbnode (root, PKT_USER_ID);
+ if (!node)
BUG(); /* No user id packet in tree. */
uid = node->pkt->pkt.user_id;
/* Get the pk packet from the pub_tree. */
- node = find_kbnode( pub_root, PKT_PUBLIC_KEY );
- if( !node )
+ node = find_kbnode (root, PKT_PUBLIC_KEY);
+ if (!node)
BUG();
pk = node->pkt->pkt.public_key;
+
+ /* The usage has not yet been set - do it now. */
pk->pubkey_usage = use;
/* We have to cache the key, so that the verification of the
@@ -968,48 +976,45 @@
cache_public_key (pk);
/* Make the signature. */
- rc = make_keysig_packet (&sig, pk, uid, NULL, sk, 0x13,
- 0, 0, timestamp, 0,
- keygen_add_std_prefs, pk);
- if( rc )
+ err = make_keysig_packet (&sig, pk, uid, NULL, psk, 0x13,
+ 0, 0, timestamp, 0,
+ keygen_add_std_prefs, pk);
+ if (err)
{
- log_error("make_keysig_packet failed: %s\n", g10_errstr(rc) );
- return rc;
+ log_error ("make_keysig_packet failed: %s\n", g10_errstr (err));
+ return err;
}
- pkt = xmalloc_clear( sizeof *pkt );
+ pkt = xmalloc_clear (sizeof *pkt);
pkt->pkttype = PKT_SIGNATURE;
pkt->pkt.signature = sig;
- add_kbnode( sec_root, new_kbnode( pkt ) );
+ add_kbnode (root, new_kbnode (pkt));
- pkt = xmalloc_clear( sizeof *pkt );
- pkt->pkttype = PKT_SIGNATURE;
- pkt->pkt.signature = copy_signature(NULL,sig);
- add_kbnode( pub_root, new_kbnode( pkt ) );
- return rc;
+ return err;
}
/* Write the key binding signature. If TIMESTAMP is not NULL use the
- signature creation times. */
+ signature creation time. PRI_PSK is the key use for signing.
+ SUB_PSK is a key used to create a back-signature; that one is only
+ used if USE has the PUBKEY_USAGE_SIG capability. */
static int
-write_keybinding (KBNODE root, KBNODE pub_root,
- PKT_secret_key *pri_sk, PKT_secret_key *sub_sk,
+write_keybinding (KBNODE root, PKT_public_key *pri_psk, PKT_public_key *sub_psk,
unsigned int use, u32 timestamp)
{
+ gpg_error_t err;
PACKET *pkt;
PKT_signature *sig;
- int rc=0;
KBNODE node;
PKT_public_key *pri_pk, *sub_pk;
struct opaque_data_usage_and_pk oduap;
- if ( opt.verbose )
+ if (opt.verbose)
log_info(_("writing key binding signature\n"));
- /* Get the pk packet from the pub_tree. */
- node = find_kbnode ( pub_root, PKT_PUBLIC_KEY );
- if ( !node )
+ /* Get the primary pk packet from the tree. */
+ node = find_kbnode (root, PKT_PUBLIC_KEY);
+ if (!node)
BUG();
pri_pk = node->pkt->pkt.public_key;
@@ -1019,9 +1024,9 @@
/* Find the last subkey. */
sub_pk = NULL;
- for (node=pub_root; node; node = node->next )
+ for (node = root; node; node = node->next )
{
- if ( node->pkt->pkttype == PKT_PUBLIC_SUBKEY )
+ if (node->pkt->pkttype == PKT_PUBLIC_SUBKEY)
sub_pk = node->pkt->pkt.public_key;
}
if (!sub_pk)
@@ -1030,28 +1035,28 @@
/* Make the signature. */
oduap.usage = use;
oduap.pk = sub_pk;
- rc = make_keysig_packet (&sig, pri_pk, NULL, sub_pk, pri_sk, 0x18,
- 0, 0, timestamp, 0,
- keygen_add_key_flags_and_expire, &oduap );
- if (rc)
+ err = make_keysig_packet (&sig, pri_pk, NULL, sub_pk, pri_psk, 0x18,
+ 0, 0, timestamp, 0,
+ keygen_add_key_flags_and_expire, &oduap);
+ if (err)
{
- log_error ("make_keysig_packet failed: %s\n", g10_errstr(rc) );
- return rc;
+ log_error ("make_keysig_packet failed: %s\n", g10_errstr (err));
+ return err;
}
/* Make a backsig. */
- if (use&PUBKEY_USAGE_SIG)
+ if (use & PUBKEY_USAGE_SIG)
{
- rc = make_backsig (sig, pri_pk, sub_pk, sub_sk, timestamp);
- if (rc)
- return rc;
+ err = make_backsig (sig, pri_pk, sub_pk, sub_psk, timestamp);
+ if (err)
+ return err;
}
pkt = xmalloc_clear ( sizeof *pkt );
pkt->pkttype = PKT_SIGNATURE;
pkt->pkt.signature = sig;
add_kbnode (root, new_kbnode (pkt) );
- return rc;
+ return err;
}
@@ -1106,71 +1111,76 @@
}
+
+/* Common code for the key generation fucntion gen_xxx. */
static int
-genhelp_protect (DEK *dek, STRING2KEY *s2k, PKT_secret_key *sk)
+common_gen (const char *keyparms, int algo, const char *algoelem,
+ kbnode_t pub_root, u32 timestamp, u32 expireval, int is_subkey)
{
- int rc = 0;
-
- if (dek)
+ int err;
+ PACKET *pkt;
+ PKT_public_key *pk;
+ gcry_sexp_t s_key;
+
+ err = agent_genkey (NULL, keyparms, &s_key);
+ if (err)
{
- sk->protect.algo = dek->algo;
- sk->protect.s2k = *s2k;
- rc = protect_secret_key (sk, dek);
- if (rc)
- log_error ("protect_secret_key failed: %s\n", gpg_strerror (rc) );
+ log_error ("agent_genkey failed: %s\n", gpg_strerror (err) );
+ return err;
}
+
+ pk = xtrycalloc (1, sizeof *pk);
+ if (!pk)
+ {
+ err = gpg_error_from_syserror ();
+ gcry_sexp_release (s_key);
+ return err;
+ }
- return rc;
-}
+ pk->timestamp = timestamp;
+ pk->version = 4;
+ if (expireval)
+ pk->expiredate = pk->timestamp + expireval;
+ pk->pubkey_algo = algo;
-static void
-genhelp_factors (gcry_sexp_t misc_key_info, KBNODE sec_root)
-{
- (void)misc_key_info;
- (void)sec_root;
-#if 0 /* Not used anymore */
- size_t n;
- char *buf;
+ err = key_from_sexp (pk->pkey, s_key, "public-key", algoelem);
+ if (err)
+ {
+ log_error ("key_from_sexp failed: %s\n", gpg_strerror (err) );
+ gcry_sexp_release (s_key);
+ free_public_key (pk);
+ return err;
+ }
+ gcry_sexp_release (s_key);
- if (misc_key_info)
+ pkt = xtrycalloc (1, sizeof *pkt);
+ if (!pkt)
{
- /* DSA: don't know whether it makes sense to have the factors, so for now
- we store them in the secret keyring (but they are not secret)
- p = 2 * q * f1 * f2 * ... * fn
- We store only f1 to f_n-1; fn can be calculated because p and q
- are known. */
- n = gcry_sexp_sprint (misc_key_info, 0, NULL, 0);
- buf = xmalloc (n+4);
- strcpy (buf, "#::");
- n = gcry_sexp_sprint (misc_key_info, 0, buf+3, n);
- if (n)
- {
- n += 3;
- add_kbnode (sec_root, make_comment_node_from_buffer (buf, n));
- }
- xfree (buf);
- gcry_sexp_release (misc_key_info);
+ err = gpg_error_from_syserror ();
+ free_public_key (pk);
+ return err;
}
-#endif
+
+ pkt->pkttype = is_subkey ? PKT_PUBLIC_SUBKEY : PKT_PUBLIC_KEY;
+ pkt->pkt.public_key = pk;
+ add_kbnode (pub_root, new_kbnode (pkt));
+
+ return 0;
}
-/* Generate an Elgamal encryption key pair. TIMESTAMP is the creatuion
- time to be put into the key structure. */
+/*
+ * Generate an Elgamal key.
+ */
static int
-gen_elg (int algo, unsigned int nbits,
- KBNODE pub_root, KBNODE sec_root, DEK *dek,
- STRING2KEY *s2k, PKT_secret_key **ret_sk,
+gen_elg (int algo, unsigned int nbits, KBNODE pub_root,
u32 timestamp, u32 expireval, int is_subkey)
{
- int rc;
- PACKET *pkt;
- PKT_secret_key *sk;
- PKT_public_key *pk;
- gcry_sexp_t s_parms, s_key;
- gcry_sexp_t misc_key_info;
+ int err;
+ char *keyparms;
+ char nbitsstr[35];
- assert( is_ELGAMAL(algo) );
+ assert (is_ELGAMAL (algo));
if (nbits < 512)
{
@@ -1184,104 +1194,36 @@
log_info (_("keysize rounded up to %u bits\n"), nbits );
}
-
- rc = gcry_sexp_build ( &s_parms, NULL,
- "(genkey(%s(nbits %d)))",
- algo == GCRY_PK_ELG_E ? "openpgp-elg" :
- algo == GCRY_PK_ELG ? "elg" : "x-oops" ,
- (int)nbits);
- if (rc)
- log_bug ("gcry_sexp_build failed: %s\n", gpg_strerror (rc));
-
- rc = gcry_pk_genkey (&s_key, s_parms);
- gcry_sexp_release (s_parms);
- if (rc)
+ snprintf (nbitsstr, sizeof nbitsstr, "%u", nbits);
+ keyparms = xtryasprintf ("(genkey(%s(nbits %zu:%s)))",
+ algo == GCRY_PK_ELG_E ? "openpgp-elg" :
+ algo == GCRY_PK_ELG ? "elg" : "x-oops" ,
+ strlen (nbitsstr), nbitsstr);
+ if (!keyparms)
+ err = gpg_error_from_syserror ();
+ else
{
- log_error ("gcry_pk_genkey failed: %s\n", gpg_strerror (rc) );
- return rc;
+ err = common_gen (keyparms, algo, "pgy",
+ pub_root, timestamp, expireval, is_subkey);
+ xfree (keyparms);
}
-
- sk = xmalloc_clear( sizeof *sk );
- pk = xmalloc_clear( sizeof *pk );
- sk->timestamp = pk->timestamp = timestamp;
- sk->version = pk->version = 4;
- if (expireval)
- {
- sk->expiredate = pk->expiredate = sk->timestamp + expireval;
- }
- sk->pubkey_algo = pk->pubkey_algo = algo;
- rc = key_from_sexp (pk->pkey, s_key, "public-key", "pgy");
- if (rc)
- {
- log_error ("key_from_sexp failed: %s\n", gpg_strerror (rc) );
- gcry_sexp_release (s_key);
- free_secret_key (sk);
- free_public_key (pk);
- return rc;
- }
- rc = key_from_sexp (sk->skey, s_key, "private-key", "pgyx");
- if (rc)
- {
- log_error("key_from_sexp failed: %s\n", gpg_strerror (rc) );
- gcry_sexp_release (s_key);
- free_secret_key (sk);
- free_public_key (pk);
- return rc;
- }
- misc_key_info = gcry_sexp_find_token (s_key, "misc-key-info", 0);
- gcry_sexp_release (s_key);
-
- sk->is_protected = 0;
- sk->protect.algo = 0;
-
- sk->csum = checksum_mpi (sk->skey[3]);
- if (ret_sk) /* Return an unprotected version of the sk. */
- *ret_sk = copy_secret_key ( NULL, sk );
-
- rc = genhelp_protect (dek, s2k, sk);
- if (rc)
- {
- free_public_key (pk);
- free_secret_key (sk);
- gcry_sexp_release (misc_key_info);
- return rc;
- }
-
- pkt = xmalloc_clear (sizeof *pkt);
- pkt->pkttype = is_subkey ? PKT_PUBLIC_SUBKEY : PKT_PUBLIC_KEY;
- pkt->pkt.public_key = pk;
- add_kbnode (pub_root, new_kbnode( pkt ));
-
- /* Don't know whether it makes sense to have access to the factors,
- so for now we store them in the secret keyring (but they are not
- secret). */
- pkt = xmalloc_clear (sizeof *pkt);
- pkt->pkttype = is_subkey ? PKT_SECRET_SUBKEY : PKT_SECRET_KEY;
- pkt->pkt.secret_key = sk;
- add_kbnode (sec_root, new_kbnode( pkt ));
-
- genhelp_factors (misc_key_info, sec_root);
-
- return 0;
+ return err;
}
-/****************
- * Generate a DSA key
+/*
+ * Generate an DSA key
*/
-static int
-gen_dsa (unsigned int nbits, KBNODE pub_root, KBNODE sec_root, DEK *dek,
- STRING2KEY *s2k, PKT_secret_key **ret_sk,
+static gpg_error_t
+gen_dsa (unsigned int nbits, KBNODE pub_root,
u32 timestamp, u32 expireval, int is_subkey)
{
- int rc;
- PACKET *pkt;
- PKT_secret_key *sk;
- PKT_public_key *pk;
- gcry_sexp_t s_parms, s_key;
- gcry_sexp_t misc_key_info;
+ int err;
unsigned int qbits;
+ char *keyparms;
+ char nbitsstr[35];
+ char qbitsstr[35];
if ( nbits < 512)
{
@@ -1334,84 +1276,21 @@
log_info (_("WARNING: some OpenPGP programs can't"
" handle a DSA key with this digest size\n"));
- rc = gcry_sexp_build (&s_parms, NULL,
- "(genkey(dsa(nbits %d)(qbits %d)))",
- (int)nbits, (int)qbits);
More information about the Gnupg-commits
mailing list