Set PIN-PUK association for cards that don't have it set

sc_pkcs15_unblock_pin() in libopensc/pkcs15-pin.c wants to associate PIN
to be unblocked with its PUK to check, for example, whether provided PUK
conforms to its policy.

When this function is not able to find a relevant PUK is uses policy for
PIN to be unblocked instead to check provided PUK which causes problems if
PIN and PUK policies differ.

Set PIN-PUK association for cards where it was unset and where this
association was either obvious, described in code or specs or provided
by the community.

Signed-off-by: Maciej S. Szmigiero <mail@maciej.szmigiero.name>
This commit is contained in:
Maciej S. Szmigiero 2016-08-14 00:55:13 +02:00 committed by Frank Morgner
parent 2031735fb1
commit 1168ca00f3
6 changed files with 44 additions and 10 deletions

View File

@ -118,6 +118,7 @@ static int sc_pkcs15emu_gids_init (sc_pkcs15_card_t * p15card)
struct sc_pkcs15_object pin_obj;
struct sc_pin_cmd_data pin_cmd_data;
size_t recordsnum;
int has_puk;
r = sc_card_ctl(card, SC_CARDCTL_GIDS_GET_ALL_CONTAINERS, &recordsnum);
SC_TEST_RET(card->ctx, SC_LOG_DEBUG_NORMAL, r, "unable to get the containers. Uninitialized card ?");
@ -183,21 +184,28 @@ static int sc_pkcs15emu_gids_init (sc_pkcs15_card_t * p15card)
strlcpy(pin_obj.label, "UserPIN", sizeof(pin_obj.label));
pin_obj.flags = SC_PKCS15_CO_FLAG_PRIVATE|SC_PKCS15_CO_FLAG_MODIFIABLE;
/*
* check whether PUK is available on this card and then optionally
* link PIN with PUK.
*/
pin_cmd_data.pin_reference = 0x81;
has_puk = sc_pin_cmd(card, &pin_cmd_data, NULL) == SC_SUCCESS;
if (has_puk) {
pin_obj.auth_id.len = 1;
pin_obj.auth_id.value[0] = 0x81;
}
r = sc_pkcs15emu_add_pin_obj(p15card, &pin_obj, &pin_info);
SC_TEST_RET(card->ctx, SC_LOG_DEBUG_NORMAL, r, "unable to sc_pkcs15emu_add_pin_obj");
// add the PUK if it is available on the card. Not all card have a PUK
pin_info.attrs.pin.reference = 0x81;
pin_info.auth_id.value[0] = 0x81;
pin_info.attrs.pin.flags = SC_PKCS15_PIN_FLAG_LOCAL|SC_PKCS15_PIN_FLAG_INITIALIZED | SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN;
pin_info.attrs.pin.reference = 0x81;
pin_cmd_data.pin_reference = pin_info.attrs.pin.reference;
r = sc_pin_cmd(card, &pin_cmd_data, NULL);
if (r == SC_SUCCESS) {
if (has_puk) {
pin_info.auth_id.value[0] = 0x81;
pin_info.attrs.pin.flags = SC_PKCS15_PIN_FLAG_LOCAL|SC_PKCS15_PIN_FLAG_INITIALIZED | SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN;
pin_info.attrs.pin.reference = 0x81;
pin_info.max_tries = pin_cmd_data.pin1.max_tries;
pin_info.tries_left = pin_cmd_data.pin1.tries_left;
strlcpy(pin_obj.label, "PUK", sizeof(pin_obj.label));
pin_obj.auth_id.len = 0;
r = sc_pkcs15emu_add_pin_obj(p15card, &pin_obj, &pin_info);
SC_TEST_RET(card->ctx, SC_LOG_DEBUG_NORMAL, r, "unable to sc_pkcs15emu_add_pin_obj with PUK");
}

View File

@ -991,6 +991,15 @@ sc_pkcs15emu_oberthur_init(struct sc_pkcs15_card * p15card)
strncpy(obj.label, PIN_DOMAIN_LABEL, SC_PKCS15_MAX_LABEL_SIZE-1);
obj.flags = SC_PKCS15_CO_FLAG_MODIFIABLE | SC_PKCS15_CO_FLAG_PRIVATE;
if (sopin_reference == 0x84) {
/*
* auth_pin_reset_oberthur_style() in card-oberthur.c
* always uses PUK with reference 0x84 for
* unblocking of User PIN
*/
obj.auth_id.len = 1;
obj.auth_id.value[0] = 0xFF;
}
sc_format_path(AWP_PIN_DF, &auth_info.path);
auth_info.path.type = SC_PATH_TYPE_PATH;

View File

@ -231,6 +231,10 @@ sc_pkcs15emu_openpgp_init(sc_pkcs15_card_t *p15card)
strlcpy(pin_obj.label, pin_cfg[i].label, sizeof(pin_obj.label));
pin_obj.flags = SC_PKCS15_CO_FLAG_MODIFIABLE | SC_PKCS15_CO_FLAG_PRIVATE;
if (i < 2) {
pin_obj.auth_id.len = 1;
pin_obj.auth_id.value[0] = 3;
}
r = sc_pkcs15emu_add_pin_obj(p15card, &pin_obj, &pin_info);
if (r < 0)

View File

@ -934,6 +934,14 @@ static int sc_pkcs15emu_piv_init(sc_pkcs15_card_t *p15card)
sc_debug(card->ctx, SC_LOG_DEBUG_NORMAL, "DEE Adding pin %d label=%s",i, label);
strncpy(pin_obj.label, label, SC_PKCS15_MAX_LABEL_SIZE - 1);
pin_obj.flags = pins[i].obj_flags;
if (i == 0 && pin_info.attrs.pin.reference == 0x80) {
/*
* according to description of "RESET RETRY COUNTER"
* command in specs PUK can only unblock PIV PIN
*/
pin_obj.auth_id.len = 1;
pin_obj.auth_id.value[0] = 2;
}
r = sc_pkcs15emu_add_pin_obj(p15card, &pin_obj, &pin_info);
if (r < 0)

View File

@ -876,6 +876,8 @@ static int sc_pkcs15emu_sc_hsm_init (sc_pkcs15_card_t * p15card)
pin_info.tries_left = 3;
pin_info.max_tries = 3;
pin_obj.auth_id.len = 1;
pin_obj.auth_id.value[0] = 2;
strlcpy(pin_obj.label, "UserPIN", sizeof(pin_obj.label));
pin_obj.flags = SC_PKCS15_CO_FLAG_PRIVATE|SC_PKCS15_CO_FLAG_MODIFIABLE;

View File

@ -97,9 +97,12 @@ static int sc_pkcs15emu_westcos_init(sc_pkcs15_card_t * p15card)
strlcpy(pin_obj.label, "Unblock",
sizeof(pin_obj.label));
else
else {
strlcpy(pin_obj.label, "User",
sizeof(pin_obj.label));
pin_obj.auth_id.len = 1;
pin_obj.auth_id.value[0] = 2;
}
pin_obj.flags =
SC_PKCS15_CO_FLAG_MODIFIABLE |
SC_PKCS15_CO_FLAG_PRIVATE;