mirror of
git://git.gnupg.org/gnupg.git
synced 2025-01-03 12:11:33 +01:00
2004-09-25 Moritz Schulte <moritz@g10code.com>
* agent.h: Declare: agent_pksign_do. (struct server_control_s): New member: raw_value. * pksign.c (do_encode_md): New argument: raw_value; support generation of raw (non-pkcs1) data objects; adjust callers. (agent_pksign_do): New function, based on code ripped out from agent_pksign. (agent_pksign): Use agent_pksign_do. * command.c (start_command_handler): Set ctrl.digest.raw_value.
This commit is contained in:
parent
f100401478
commit
1db08a412c
@ -1,3 +1,16 @@
|
||||
2004-09-25 Moritz Schulte <moritz@g10code.com>
|
||||
|
||||
* agent.h: Declare: agent_pksign_do.
|
||||
(struct server_control_s): New member: raw_value.
|
||||
|
||||
* pksign.c (do_encode_md): New argument: raw_value; support
|
||||
generation of raw (non-pkcs1) data objects; adjust callers.
|
||||
(agent_pksign_do): New function, based on code ripped
|
||||
out from agent_pksign.
|
||||
(agent_pksign): Use agent_pksign_do.
|
||||
|
||||
* command.c (start_command_handler): Set ctrl.digest.raw_value.
|
||||
|
||||
2004-09-09 Werner Koch <wk@g10code.de>
|
||||
|
||||
* gpg-agent.c (check_for_running_agent): New.
|
||||
|
@ -95,6 +95,7 @@ struct server_control_s {
|
||||
int algo;
|
||||
unsigned char value[MAX_DIGEST_LEN];
|
||||
int valuelen;
|
||||
int raw_value: 1;
|
||||
} digest;
|
||||
char keygrip[20];
|
||||
int have_keygrip;
|
||||
@ -159,6 +160,8 @@ void agent_unlock_cache_entry (void **cache_id);
|
||||
|
||||
|
||||
/*-- pksign.c --*/
|
||||
int agent_pksign_do (CTRL ctrl, const char *desc_text,
|
||||
gcry_sexp_t *signature_sexp, int ignore_cache);
|
||||
int agent_pksign (ctrl_t ctrl, const char *desc_text,
|
||||
FILE *outfp, int ignore_cache);
|
||||
|
||||
|
@ -854,6 +854,7 @@ start_command_handler (int listen_fd, int fd)
|
||||
ctrl.server_local->assuan_ctx = ctx;
|
||||
ctrl.server_local->message_fd = -1;
|
||||
ctrl.server_local->use_cache_for_signing = 1;
|
||||
ctrl.digest.raw_value = 0;
|
||||
|
||||
if (DBG_ASSUAN)
|
||||
assuan_set_log_stream (ctx, log_get_stream ());
|
||||
|
136
agent/pksign.c
136
agent/pksign.c
@ -32,41 +32,61 @@
|
||||
|
||||
|
||||
static int
|
||||
do_encode_md (const byte * md, size_t mdlen, int algo, gcry_sexp_t * r_hash)
|
||||
do_encode_md (const byte * md, size_t mdlen, int algo, gcry_sexp_t * r_hash,
|
||||
int raw_value)
|
||||
{
|
||||
gcry_sexp_t hash;
|
||||
const char *s;
|
||||
char tmp[16+1];
|
||||
int i, rc;
|
||||
int rc;
|
||||
|
||||
s = gcry_md_algo_name (algo);
|
||||
if (s && strlen (s) < 16)
|
||||
if (! raw_value)
|
||||
{
|
||||
for (i=0; i < strlen (s); i++)
|
||||
tmp[i] = tolower (s[i]);
|
||||
tmp[i] = '\0';
|
||||
const char *s;
|
||||
char tmp[16+1];
|
||||
int i;
|
||||
|
||||
s = gcry_md_algo_name (algo);
|
||||
if (s && strlen (s) < 16)
|
||||
{
|
||||
for (i=0; i < strlen (s); i++)
|
||||
tmp[i] = tolower (s[i]);
|
||||
tmp[i] = '\0';
|
||||
}
|
||||
|
||||
rc = gcry_sexp_build (&hash, NULL,
|
||||
"(data (flags pkcs1) (hash %s %b))",
|
||||
tmp, mdlen, md);
|
||||
}
|
||||
rc = gcry_sexp_build (&hash, NULL,
|
||||
"(data (flags pkcs1) (hash %s %b))",
|
||||
tmp,
|
||||
mdlen, md);
|
||||
else
|
||||
{
|
||||
gcry_mpi_t mpi;
|
||||
|
||||
rc = gcry_mpi_scan (&mpi, GCRYMPI_FMT_USG, md, mdlen, NULL);
|
||||
if (! rc)
|
||||
{
|
||||
rc = gcry_sexp_build (&hash, NULL,
|
||||
"(data (flags raw) (value %m))",
|
||||
mpi);
|
||||
gcry_mpi_release (mpi);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
*r_hash = hash;
|
||||
return rc;
|
||||
}
|
||||
|
||||
|
||||
/* SIGN whatever information we have accumulated in CTRL and write it
|
||||
back to OUTFP. */
|
||||
/* SIGN whatever information we have accumulated in CTRL and return
|
||||
the signature S-Expression. */
|
||||
int
|
||||
agent_pksign (CTRL ctrl, const char *desc_text, FILE *outfp, int ignore_cache)
|
||||
agent_pksign_do (CTRL ctrl, const char *desc_text,
|
||||
gcry_sexp_t *signature_sexp, int ignore_cache)
|
||||
{
|
||||
gcry_sexp_t s_skey = NULL, s_hash = NULL, s_sig = NULL;
|
||||
gcry_sexp_t s_skey = NULL, s_sig = NULL;
|
||||
unsigned char *shadow_info = NULL;
|
||||
int rc;
|
||||
char *buf = NULL;
|
||||
size_t len;
|
||||
unsigned int rc = 0; /* FIXME: gpg-error? */
|
||||
|
||||
if (!ctrl->have_keygrip)
|
||||
if (! ctrl->have_keygrip)
|
||||
return gpg_error (GPG_ERR_NO_SECKEY);
|
||||
|
||||
rc = agent_key_from_file (ctrl, desc_text, ctrl->keygrip,
|
||||
@ -77,32 +97,47 @@ agent_pksign (CTRL ctrl, const char *desc_text, FILE *outfp, int ignore_cache)
|
||||
goto leave;
|
||||
}
|
||||
|
||||
if (!s_skey)
|
||||
{ /* divert operation to the smartcard */
|
||||
unsigned char *sigbuf;
|
||||
if (! s_skey)
|
||||
{
|
||||
/* divert operation to the smartcard */
|
||||
|
||||
unsigned char *buf = NULL;
|
||||
size_t len = 0;
|
||||
|
||||
rc = divert_pksign (ctrl,
|
||||
ctrl->digest.value,
|
||||
ctrl->digest.valuelen,
|
||||
ctrl->digest.algo,
|
||||
shadow_info, &sigbuf);
|
||||
shadow_info, &buf);
|
||||
if (rc)
|
||||
{
|
||||
log_error ("smartcard signing failed: %s\n", gpg_strerror (rc));
|
||||
goto leave;
|
||||
}
|
||||
len = gcry_sexp_canon_len (sigbuf, 0, NULL, NULL);
|
||||
len = gcry_sexp_canon_len (buf, 0, NULL, NULL);
|
||||
assert (len);
|
||||
buf = sigbuf;
|
||||
|
||||
rc = gcry_sexp_sscan (&s_sig, NULL, buf, len);
|
||||
xfree (buf);
|
||||
if (rc)
|
||||
{
|
||||
log_error ("failed to convert sigbuf returned by divert_pksign "
|
||||
"into S-Exp: %s", gpg_strerror (rc));
|
||||
goto leave;
|
||||
}
|
||||
}
|
||||
else
|
||||
{ /* no smartcard, but a private key */
|
||||
{
|
||||
/* no smartcard, but a private key */
|
||||
|
||||
gcry_sexp_t s_hash = NULL;
|
||||
|
||||
/* put the hash into a sexp */
|
||||
rc = do_encode_md (ctrl->digest.value,
|
||||
ctrl->digest.valuelen,
|
||||
ctrl->digest.algo,
|
||||
&s_hash);
|
||||
&s_hash,
|
||||
ctrl->digest.raw_value);
|
||||
if (rc)
|
||||
goto leave;
|
||||
|
||||
@ -114,6 +149,7 @@ agent_pksign (CTRL ctrl, const char *desc_text, FILE *outfp, int ignore_cache)
|
||||
|
||||
/* sign */
|
||||
rc = gcry_pk_sign (&s_sig, s_hash, s_skey);
|
||||
gcry_sexp_release (s_hash);
|
||||
if (rc)
|
||||
{
|
||||
log_error ("signing failed: %s\n", gpg_strerror (rc));
|
||||
@ -125,26 +161,46 @@ agent_pksign (CTRL ctrl, const char *desc_text, FILE *outfp, int ignore_cache)
|
||||
log_debug ("result: ");
|
||||
gcry_sexp_dump (s_sig);
|
||||
}
|
||||
|
||||
len = gcry_sexp_sprint (s_sig, GCRYSEXP_FMT_CANON, NULL, 0);
|
||||
assert (len);
|
||||
buf = xmalloc (len);
|
||||
len = gcry_sexp_sprint (s_sig, GCRYSEXP_FMT_CANON, buf, len);
|
||||
assert (len);
|
||||
}
|
||||
|
||||
leave:
|
||||
|
||||
*signature_sexp = s_sig;
|
||||
|
||||
gcry_sexp_release (s_skey);
|
||||
xfree (shadow_info);
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
/* SIGN whatever information we have accumulated in CTRL and write it
|
||||
back to OUTFP. */
|
||||
int
|
||||
agent_pksign (CTRL ctrl, const char *desc_text, FILE *outfp, int ignore_cache)
|
||||
{
|
||||
gcry_sexp_t s_sig = NULL;
|
||||
char *buf = NULL;
|
||||
size_t len = 0;
|
||||
int rc = 0;
|
||||
|
||||
rc = agent_pksign_do (ctrl, desc_text, &s_sig, ignore_cache);
|
||||
if (rc)
|
||||
goto leave;
|
||||
|
||||
len = gcry_sexp_sprint (s_sig, GCRYSEXP_FMT_CANON, NULL, 0);
|
||||
assert (len);
|
||||
buf = xmalloc (len);
|
||||
len = gcry_sexp_sprint (s_sig, GCRYSEXP_FMT_CANON, buf, len);
|
||||
assert (len);
|
||||
|
||||
/* FIXME: we must make sure that no buffering takes place or we are
|
||||
in full control of the buffer memory (easy to do) - should go
|
||||
into assuan. */
|
||||
fwrite (buf, 1, len, outfp);
|
||||
|
||||
leave:
|
||||
gcry_sexp_release (s_skey);
|
||||
gcry_sexp_release (s_hash);
|
||||
gcry_sexp_release (s_sig);
|
||||
xfree (buf);
|
||||
xfree (shadow_info);
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user