diff options
author | Werner Koch <wk@gnupg.org> | 2002-08-16 12:33:31 +0200 |
---|---|---|
committer | Werner Koch <wk@gnupg.org> | 2002-08-16 12:33:31 +0200 |
commit | fd2f1c8aa3190d55cb16fd6d2aab994447ab3bf8 (patch) | |
tree | d88d5f3480e5c6856a8a8c1947de91b4a9d06176 /scd/card-p15.c | |
parent | Removed a leftover conflict indicator. (diff) | |
download | gnupg2-fd2f1c8aa3190d55cb16fd6d2aab994447ab3bf8.tar.xz gnupg2-fd2f1c8aa3190d55cb16fd6d2aab994447ab3bf8.zip |
* card-common.h (struct p15_private_s): Forward declaration. Add
it to card_ctx_s.
* card.c (card_close): Make sure private data is released.
* card-p15.c (p15_release_private_data): New.
(init_private_data): New to work around an OpenSC weirdness.
(p15_enum_keypairs): Do an OpenSC get_objects only once.
Diffstat (limited to 'scd/card-p15.c')
-rw-r--r-- | scd/card-p15.c | 73 |
1 files changed, 63 insertions, 10 deletions
diff --git a/scd/card-p15.c b/scd/card-p15.c index 6248ddfe2..c0758161f 100644 --- a/scd/card-p15.c +++ b/scd/card-p15.c @@ -32,6 +32,61 @@ #include "card-common.h" +struct p15private_s { + int n_prkey_rsa_objs; + struct sc_pkcs15_object *prkey_rsa_objs[32]; +}; + + +/* Allocate private data. */ +static int +init_private_data (CARD card) +{ + struct p15private_s *priv; + int rc; + + if (card->p15priv) + return 0; /* already done. */ + + priv = xtrycalloc (1, sizeof *priv); + if (!priv) + return GNUPG_Out_Of_Core; + + /* OpenSC (0.7.0) is a bit strange in that the get_objects functions + tries to be a bit too clever and implicitly does an enumeration + which eventually leads to the fact that every call to this + fucntion returns one more macthing object. The old code in + p15_enum_keypairs assume that it would alwyas return the same + numer of objects and used this to figure out what the last object + enumerated is. We now do an enum_objects just once and keep it + in the private data. */ + rc = sc_pkcs15_get_objects (card->p15card, SC_PKCS15_TYPE_PRKEY_RSA, + priv->prkey_rsa_objs, + DIM (priv->prkey_rsa_objs)); + if (rc < 0) + { + log_error ("private keys enumeration failed: %s\n", sc_strerror (rc)); + xfree (priv); + return GNUPG_Card_Error; + } + priv->n_prkey_rsa_objs = rc; + card->p15priv = priv; + return 0; +} + + +/* Release private data used in this module. */ +void +p15_release_private_data (CARD card) +{ + if (!card->p15priv) + return; + xfree (card->p15priv); + card->p15priv = NULL; +} + + + /* See card.c for interface description */ static int p15_enum_keypairs (CARD card, int idx, @@ -39,25 +94,23 @@ p15_enum_keypairs (CARD card, int idx, { int rc; KsbaError krc; - struct sc_pkcs15_object *objs[32], *tmpobj; + struct p15private_s *priv; + struct sc_pkcs15_object *tmpobj; int nobjs; struct sc_pkcs15_prkey_info *pinfo; struct sc_pkcs15_cert_info *certinfo; struct sc_pkcs15_cert *certder; KsbaCert cert; - rc = sc_pkcs15_get_objects (card->p15card, SC_PKCS15_TYPE_PRKEY_RSA, - objs, DIM (objs)); - if (rc < 0) - { - log_error ("private keys enumeration failed: %s\n", sc_strerror (rc)); - return GNUPG_Card_Error; - } - nobjs = rc; + rc = init_private_data (card); + if (rc) + return rc; + priv = card->p15priv; + nobjs = priv->n_prkey_rsa_objs; rc = 0; if (idx >= nobjs) return -1; - pinfo = objs[idx]->data; + pinfo = priv->prkey_rsa_objs[idx]->data; /* now we need to read the certificate so that we can calculate the keygrip */ |