OpenPGP: implement pgp_find_blob()

Replace the "one-trick-pony" pgp_do_iswritable() with a more generic
function returning the blob matching the passed tag.

This way we can get rid of the one-line function pgp_blob_iswritable() too.
comparisons like these can be done in the caller.
This commit is contained in:
Peter Marschall 2012-06-02 08:51:09 +02:00 committed by Viktor Tarasov
parent f5dc252aa9
commit 9e04ae46bb
1 changed files with 23 additions and 32 deletions

View File

@ -829,6 +829,27 @@ pgp_seek_blob(sc_card_t *card, struct blob *root, unsigned int id,
return SC_ERROR_FILE_NOT_FOUND;
}
/* internal: find a blob by tag - pgp_seek_blob with optimizations */
static struct blob *
pgp_find_blob(sc_card_t *card, unsigned int tag)
{
struct pgp_priv_data *priv = DRVDATA(card);
struct blob *blob = NULL;
int r;
/* Check if current selected blob is which we want to test*/
if (priv->current->id == tag) {
return priv->current;
}
/* Look for the blob representing the DO */
r = pgp_seek_blob(card, priv->mf, tag, &blob);
if (r < 0) {
sc_log(card->ctx, "Failed to seek the blob representing the tag %04X. Error %d.", tag, r);
return NULL;
}
return blob;
}
/**
* Strip out the parts of PKCS15 file layout in the path. Get the reduced version
* which is understood by the OpenPGP card driver.
@ -1065,37 +1086,6 @@ pgp_get_data(sc_card_t *card, unsigned int tag, u8 *buf, size_t buf_len)
LOG_FUNC_RETURN(card->ctx, apdu.resplen);
}
/* Internal: Check if a blob is writable */
static u8
pgp_blob_iswritable(sc_card_t *card, struct blob *tested_blob)
{
return ((tested_blob->info->access & WRITE_MASK) != WRITE_NEVER);
}
/**
* Internal: Check if a DO is writable
* @param[out] ref_blob Pointer to the blob corresponding to the DO.
**/
static u8
pgp_do_iswritable(sc_card_t *card, unsigned int tag, struct blob **ref_blob)
{
struct pgp_priv_data *priv = DRVDATA(card);
int r;
/* Check if current selected blob is which we want to test*/
if (priv->current->id == tag) {
*ref_blob = priv->current;
return pgp_blob_iswritable(card, priv->current);
}
/* Look for the blob representing the DO */
r = pgp_seek_blob(card, priv->mf, tag, ref_blob);
if (r < 0) {
sc_log(card->ctx, "Failed to seek the blob representing the tag %04X. Error %d.", tag, r);
return 0;
}
return pgp_blob_iswritable(card, *ref_blob);
}
/* ABI: PUT DATA */
static int
pgp_put_data(sc_card_t *card, unsigned int tag, const u8 *buf, size_t buf_len)
@ -1111,7 +1101,8 @@ pgp_put_data(sc_card_t *card, unsigned int tag, const u8 *buf, size_t buf_len)
LOG_FUNC_CALLED(card->ctx);
/* Check if the tag is writable */
if (!pgp_do_iswritable(card, tag, &affected_blob)) {
affected_blob = pgp_find_blob(card, tag);
if (affected_blob == NULL || (affected_blob->info->access & WRITE_MASK) == WRITE_NEVER) {
sc_log(card->ctx, "The %04X DO is not writable.", tag);
return SC_ERROR_NOT_ALLOWED;
}