pkcs15: use general 'AuthenticationObject' instead of 'PinObject'
now the attributes of the previous 'pin-info' data type are included as the sub-type attributes of the general 'auth-info' data . It will allow to include support of the 'biometricTemplate' and 'authKey' authentication types. http://www.opensc-project.org/pipermail/opensc-devel/2011-May/016655.html git-svn-id: https://www.opensc-project.org/svnp/opensc/trunk@5550 c6295689-39f2-0310-b995-f0e70906c6a9
This commit is contained in:
parent
32d035a9ad
commit
d888b3fd55
@ -180,7 +180,7 @@ sc_pkcs15_free_data_info
|
||||
sc_pkcs15_free_data_object
|
||||
sc_pkcs15_free_key_params
|
||||
sc_pkcs15_free_object
|
||||
sc_pkcs15_free_pin_info
|
||||
sc_pkcs15_free_auth_info
|
||||
sc_pkcs15_free_prkey
|
||||
sc_pkcs15_free_prkey_info
|
||||
sc_pkcs15_free_pubkey
|
||||
|
@ -277,20 +277,23 @@ int sc_pkcs15emu_initialize_pins(sc_pkcs15_card_t *p15card, p15data_items* items
|
||||
const pindata* pins = items->pins;
|
||||
if(!pins) return SC_SUCCESS;
|
||||
for (i = 0; pins[i].label; i++) {
|
||||
struct sc_pkcs15_pin_info pin_info;
|
||||
struct sc_pkcs15_auth_info pin_info;
|
||||
struct sc_pkcs15_object pin_obj;
|
||||
|
||||
memset(&pin_info, 0, sizeof(pin_info));
|
||||
memset(&pin_obj, 0, sizeof(pin_obj));
|
||||
|
||||
pin_info.auth_type = SC_PKCS15_PIN_AUTH_TYPE_PIN;
|
||||
sc_pkcs15_format_id(pins[i].id, &pin_info.auth_id);
|
||||
pin_info.reference = pins[i].ref;
|
||||
pin_info.flags = pins[i].flags;
|
||||
pin_info.type = pins[i].type;
|
||||
pin_info.min_length = pins[i].minlen;
|
||||
pin_info.stored_length = pins[i].storedlen;
|
||||
pin_info.max_length = pins[i].maxlen;
|
||||
pin_info.pad_char = pins[i].pad_char;
|
||||
|
||||
pin_info.attrs.pin.reference = pins[i].ref;
|
||||
pin_info.attrs.pin.flags = pins[i].flags;
|
||||
pin_info.attrs.pin.type = pins[i].type;
|
||||
pin_info.attrs.pin.min_length = pins[i].minlen;
|
||||
pin_info.attrs.pin.stored_length = pins[i].storedlen;
|
||||
pin_info.attrs.pin.max_length = pins[i].maxlen;
|
||||
pin_info.attrs.pin.pad_char = pins[i].pad_char;
|
||||
|
||||
sc_format_path(pins[i].path, &pin_info.path);
|
||||
pin_info.tries_left = -1;
|
||||
|
||||
|
@ -77,27 +77,27 @@ static int sc_pkcs15emu_add_pin(sc_pkcs15_card_t *p15card,
|
||||
unsigned int max_length,
|
||||
int flags, int tries_left, const char pad_char, int obj_flags)
|
||||
{
|
||||
sc_pkcs15_pin_info_t info;
|
||||
sc_pkcs15_auth_info_t info;
|
||||
sc_pkcs15_object_t obj;
|
||||
|
||||
memset(&info, 0, sizeof(info));
|
||||
memset(&obj, 0, sizeof(obj));
|
||||
|
||||
info.auth_id = *id;
|
||||
info.min_length = min_length;
|
||||
info.max_length = max_length;
|
||||
info.stored_length = max_length;
|
||||
info.type = type;
|
||||
info.reference = ref;
|
||||
info.flags = flags;
|
||||
info.auth_type = SC_PKCS15_PIN_AUTH_TYPE_PIN;
|
||||
info.attrs.pin.min_length = min_length;
|
||||
info.attrs.pin.max_length = max_length;
|
||||
info.attrs.pin.stored_length = max_length;
|
||||
info.attrs.pin.type = type;
|
||||
info.attrs.pin.reference = ref;
|
||||
info.attrs.pin.flags = flags;
|
||||
info.attrs.pin.pad_char = pad_char;
|
||||
info.tries_left = tries_left;
|
||||
info.magic = SC_PKCS15_PIN_MAGIC;
|
||||
info.pad_char = pad_char;
|
||||
|
||||
if (path)
|
||||
info.path = *path;
|
||||
if (type == SC_PKCS15_PIN_TYPE_BCD)
|
||||
info.stored_length /= 2;
|
||||
info.attrs.pin.stored_length /= 2;
|
||||
|
||||
strlcpy(obj.label, label, sizeof(obj.label));
|
||||
obj.flags = obj_flags;
|
||||
|
@ -220,20 +220,21 @@ static int sc_pkcs15emu_atrust_acos_init(sc_pkcs15_card_t *p15card)
|
||||
}
|
||||
/* set pins */
|
||||
for (i = 0; pins[i].label; i++) {
|
||||
struct sc_pkcs15_pin_info pin_info;
|
||||
struct sc_pkcs15_auth_info pin_info;
|
||||
struct sc_pkcs15_object pin_obj;
|
||||
|
||||
memset(&pin_info, 0, sizeof(pin_info));
|
||||
memset(&pin_obj, 0, sizeof(pin_obj));
|
||||
|
||||
sc_pkcs15_format_id(pins[i].id, &pin_info.auth_id);
|
||||
pin_info.reference = pins[i].ref;
|
||||
pin_info.flags = pins[i].flags;
|
||||
pin_info.type = pins[i].type;
|
||||
pin_info.min_length = pins[i].minlen;
|
||||
pin_info.stored_length = pins[i].storedlen;
|
||||
pin_info.max_length = pins[i].maxlen;
|
||||
pin_info.pad_char = pins[i].pad_char;
|
||||
pin_info.auth_type = SC_PKCS15_PIN_AUTH_TYPE_PIN;
|
||||
pin_info.attrs.pin.reference = pins[i].ref;
|
||||
pin_info.attrs.pin.flags = pins[i].flags;
|
||||
pin_info.attrs.pin.type = pins[i].type;
|
||||
pin_info.attrs.pin.min_length = pins[i].minlen;
|
||||
pin_info.attrs.pin.stored_length = pins[i].storedlen;
|
||||
pin_info.attrs.pin.max_length = pins[i].maxlen;
|
||||
pin_info.attrs.pin.pad_char = pins[i].pad_char;
|
||||
sc_format_path(pins[i].path, &pin_info.path);
|
||||
pin_info.tries_left = -1;
|
||||
|
||||
|
@ -173,7 +173,7 @@ sc_pkcs15emu_esteid_init (sc_pkcs15_card_t * p15card)
|
||||
static const int esteid_pin_authid[3] = {1, 2, 3};
|
||||
static const int esteid_pin_flags[3] = {0, 0, SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN};
|
||||
|
||||
struct sc_pkcs15_pin_info pin_info;
|
||||
struct sc_pkcs15_auth_info pin_info;
|
||||
struct sc_pkcs15_object pin_obj;
|
||||
|
||||
memset(&pin_info, 0, sizeof(pin_info));
|
||||
@ -187,13 +187,14 @@ sc_pkcs15emu_esteid_init (sc_pkcs15_card_t * p15card)
|
||||
|
||||
pin_info.auth_id.len = 1;
|
||||
pin_info.auth_id.value[0] = esteid_pin_authid[i];
|
||||
pin_info.reference = esteid_pin_ref[i];
|
||||
pin_info.flags = esteid_pin_flags[i];
|
||||
pin_info.type = SC_PKCS15_PIN_TYPE_ASCII_NUMERIC;
|
||||
pin_info.min_length = esteid_pin_min[i];
|
||||
pin_info.stored_length = 12;
|
||||
pin_info.max_length = 12;
|
||||
pin_info.pad_char = '\0';
|
||||
pin_info.auth_type = SC_PKCS15_PIN_AUTH_TYPE_PIN;
|
||||
pin_info.attrs.pin.reference = esteid_pin_ref[i];
|
||||
pin_info.attrs.pin.flags = esteid_pin_flags[i];
|
||||
pin_info.attrs.pin.type = SC_PKCS15_PIN_TYPE_ASCII_NUMERIC;
|
||||
pin_info.attrs.pin.min_length = esteid_pin_min[i];
|
||||
pin_info.attrs.pin.stored_length = 12;
|
||||
pin_info.attrs.pin.max_length = 12;
|
||||
pin_info.attrs.pin.pad_char = '\0';
|
||||
pin_info.tries_left = (int)tries_left;
|
||||
pin_info.max_tries = 3;
|
||||
|
||||
|
@ -430,20 +430,21 @@ static int sc_pkcs15emu_gemsafeGPK_init(sc_pkcs15_card_t *p15card)
|
||||
card->ops->pin_cmd = my_pin_cmd;
|
||||
|
||||
for (i = 0; pins[i].label; i++) {
|
||||
struct sc_pkcs15_pin_info pin_info;
|
||||
struct sc_pkcs15_auth_info pin_info;
|
||||
struct sc_pkcs15_object pin_obj;
|
||||
|
||||
memset(&pin_info, 0, sizeof(pin_info));
|
||||
memset(&pin_obj, 0, sizeof(pin_obj));
|
||||
|
||||
sc_pkcs15_format_id(pins[i].id, &pin_info.auth_id);
|
||||
pin_info.reference = pins[i].ref;
|
||||
pin_info.flags = pins[i].flags;
|
||||
pin_info.type = pins[i].type;
|
||||
pin_info.min_length = pins[i].minlen;
|
||||
pin_info.stored_length = pins[i].storedlen;
|
||||
pin_info.max_length = pins[i].maxlen;
|
||||
pin_info.pad_char = pins[i].pad_char;
|
||||
pin_info.auth_type = SC_PKCS15_PIN_AUTH_TYPE_PIN;
|
||||
pin_info.attrs.pin.reference = pins[i].ref;
|
||||
pin_info.attrs.pin.flags = pins[i].flags;
|
||||
pin_info.attrs.pin.type = pins[i].type;
|
||||
pin_info.attrs.pin.min_length = pins[i].minlen;
|
||||
pin_info.attrs.pin.stored_length = pins[i].storedlen;
|
||||
pin_info.attrs.pin.max_length = pins[i].maxlen;
|
||||
pin_info.attrs.pin.pad_char = pins[i].pad_char;
|
||||
sc_format_path(pins[i].path, &pin_info.path);
|
||||
pin_info.path.value[2] = dfpath >> 8;
|
||||
pin_info.path.value[3] = dfpath & 0xff;
|
||||
|
@ -432,19 +432,19 @@ sc_pkcs15emu_add_pin(sc_pkcs15_card_t *p15card,
|
||||
unsigned int max_length,
|
||||
int flags, int tries_left, const char pad_char, int obj_flags)
|
||||
{
|
||||
sc_pkcs15_pin_info_t *info;
|
||||
sc_pkcs15_auth_info_t *info;
|
||||
|
||||
info = calloc(1, sizeof(*info));
|
||||
info->auth_type = SC_PKCS15_PIN_AUTH_TYPE_PIN;
|
||||
info->auth_id = *id;
|
||||
info->min_length = min_length;
|
||||
info->max_length = max_length;
|
||||
info->stored_length = max_length;
|
||||
info->type = type;
|
||||
info->reference = ref;
|
||||
info->flags = flags;
|
||||
info->attrs.pin.min_length = min_length;
|
||||
info->attrs.pin.max_length = max_length;
|
||||
info->attrs.pin.stored_length = max_length;
|
||||
info->attrs.pin.type = type;
|
||||
info->attrs.pin.reference = ref;
|
||||
info->attrs.pin.flags = flags;
|
||||
info->attrs.pin.pad_char = pad_char;
|
||||
info->tries_left = tries_left;
|
||||
info->magic = SC_PKCS15_PIN_MAGIC;
|
||||
info->pad_char = pad_char;
|
||||
|
||||
if (path)
|
||||
info->path = *path;
|
||||
|
@ -72,27 +72,27 @@ static int sc_pkcs15emu_add_pin(sc_pkcs15_card_t *p15card,
|
||||
unsigned int max_length,
|
||||
int flags, int tries_left, const char pad_char, int obj_flags)
|
||||
{
|
||||
sc_pkcs15_pin_info_t info;
|
||||
sc_pkcs15_auth_info_t info;
|
||||
sc_pkcs15_object_t obj;
|
||||
|
||||
memset(&info, 0, sizeof(info));
|
||||
memset(&obj, 0, sizeof(obj));
|
||||
|
||||
info.auth_type = SC_PKCS15_PIN_AUTH_TYPE_PIN;
|
||||
info.auth_id = *id;
|
||||
info.min_length = min_length;
|
||||
info.max_length = max_length;
|
||||
info.stored_length = max_length;
|
||||
info.type = type;
|
||||
info.reference = ref;
|
||||
info.flags = flags;
|
||||
info.attrs.pin.min_length = min_length;
|
||||
info.attrs.pin.max_length = max_length;
|
||||
info.attrs.pin.stored_length = max_length;
|
||||
info.attrs.pin.type = type;
|
||||
info.attrs.pin.reference = ref;
|
||||
info.attrs.pin.flags = flags;
|
||||
info.attrs.pin.pad_char = pad_char;
|
||||
info.tries_left = tries_left;
|
||||
info.magic = SC_PKCS15_PIN_MAGIC;
|
||||
info.pad_char = pad_char;
|
||||
|
||||
if (path)
|
||||
info.path = *path;
|
||||
if (type == SC_PKCS15_PIN_TYPE_BCD)
|
||||
info.stored_length /= 2;
|
||||
info.attrs.pin.stored_length /= 2;
|
||||
|
||||
strlcpy(obj.label, label, sizeof(obj.label));
|
||||
obj.flags = obj_flags;
|
||||
|
@ -344,21 +344,22 @@ static int itacns_add_pin(sc_pkcs15_card_t *p15card,
|
||||
sc_path_t *path,
|
||||
int flags)
|
||||
{
|
||||
struct sc_pkcs15_pin_info pin_info;
|
||||
struct sc_pkcs15_auth_info pin_info;
|
||||
struct sc_pkcs15_object pin_obj;
|
||||
|
||||
SC_FUNC_CALLED(p15card->card->ctx, 1);
|
||||
|
||||
memset(&pin_info, 0, sizeof(pin_info));
|
||||
pin_info.auth_type = SC_PKCS15_PIN_AUTH_TYPE_PIN;
|
||||
pin_info.auth_id.len = 1;
|
||||
pin_info.auth_id.value[0] = id;
|
||||
pin_info.reference = reference;
|
||||
pin_info.flags = flags;
|
||||
pin_info.type = SC_PKCS15_PIN_TYPE_ASCII_NUMERIC;
|
||||
pin_info.min_length = 5;
|
||||
pin_info.stored_length = 8;
|
||||
pin_info.max_length = 8;
|
||||
pin_info.pad_char = 0xff;
|
||||
pin_info.attrs.pin.reference = reference;
|
||||
pin_info.attrs.pin.flags = flags;
|
||||
pin_info.attrs.pin.type = SC_PKCS15_PIN_TYPE_ASCII_NUMERIC;
|
||||
pin_info.attrs.pin.min_length = 5;
|
||||
pin_info.attrs.pin.stored_length = 8;
|
||||
pin_info.attrs.pin.max_length = 8;
|
||||
pin_info.attrs.pin.pad_char = 0xff;
|
||||
if(path)
|
||||
pin_info.path = *path;
|
||||
|
||||
|
@ -294,17 +294,16 @@ sc_oberthur_read_file(struct sc_pkcs15_card *p15card, const char *in_path,
|
||||
if (verify_pin && rv == SC_ERROR_SECURITY_STATUS_NOT_SATISFIED) {
|
||||
struct sc_pkcs15_object *objs[0x10], *pin_obj = NULL;
|
||||
const struct sc_acl_entry *acl = sc_file_get_acl_entry(file, SC_AC_OP_READ);
|
||||
struct sc_pkcs15_pin_info *pinfo = NULL;
|
||||
int ii;
|
||||
|
||||
rv = sc_pkcs15_get_objects(p15card, SC_PKCS15_TYPE_AUTH_PIN, objs, 0x10);
|
||||
SC_TEST_RET(card->ctx, SC_LOG_DEBUG_NORMAL, rv, "Cannot read oberthur file: get AUTH objects error");
|
||||
|
||||
for (ii=0; ii<rv; ii++) {
|
||||
pinfo = (struct sc_pkcs15_pin_info *) objs[ii]->data;
|
||||
struct sc_pkcs15_auth_info *auth_info = (struct sc_pkcs15_auth_info *) objs[ii]->data;
|
||||
sc_debug(ctx, SC_LOG_DEBUG_NORMAL, "compare PIN/ACL refs:%i/%i, method:%i/%i",
|
||||
pinfo->reference, acl->key_ref, pinfo->auth_method, acl->method);
|
||||
if (pinfo->reference == (int)acl->key_ref && pinfo->auth_method == (unsigned)acl->method) {
|
||||
auth_info->attrs.pin.reference, acl->key_ref, auth_info->auth_method, acl->method);
|
||||
if (auth_info->attrs.pin.reference == (int)acl->key_ref && auth_info->auth_method == (unsigned)acl->method) {
|
||||
pin_obj = objs[ii];
|
||||
break;
|
||||
}
|
||||
@ -911,7 +910,7 @@ static int
|
||||
sc_pkcs15emu_oberthur_init(struct sc_pkcs15_card * p15card)
|
||||
{
|
||||
struct sc_context *ctx = p15card->card->ctx;
|
||||
struct sc_pkcs15_pin_info info;
|
||||
struct sc_pkcs15_auth_info auth_info;
|
||||
struct sc_pkcs15_object obj;
|
||||
struct sc_card *card = p15card->card;
|
||||
struct sc_path path;
|
||||
@ -942,67 +941,66 @@ sc_pkcs15emu_oberthur_init(struct sc_pkcs15_card * p15card)
|
||||
SC_TEST_RET(ctx, SC_LOG_DEBUG_NORMAL, rv, "Invalid state of SO-PIN");
|
||||
|
||||
/* add PIN */
|
||||
memset(&info, 0, sizeof(info));
|
||||
memset(&auth_info, 0, sizeof(auth_info));
|
||||
memset(&obj, 0, sizeof(obj));
|
||||
|
||||
info.auth_id.len = 1;
|
||||
info.auth_id.value[0] = 0xFF;
|
||||
info.min_length = 4;
|
||||
info.max_length = 64;
|
||||
info.stored_length = 64;
|
||||
info.type = SC_PKCS15_PIN_TYPE_ASCII_NUMERIC;
|
||||
info.reference = sopin_reference;
|
||||
info.tries_left = tries_left;
|
||||
info.auth_method = SC_AC_CHV;
|
||||
info.magic = SC_PKCS15_PIN_MAGIC;
|
||||
info.pad_char = 0xFF;
|
||||
info.flags = SC_PKCS15_PIN_FLAG_CASE_SENSITIVE
|
||||
|
||||
auth_info.auth_type = SC_PKCS15_PIN_AUTH_TYPE_PIN;
|
||||
auth_info.auth_method = SC_AC_CHV;
|
||||
auth_info.auth_id.len = 1;
|
||||
auth_info.auth_id.value[0] = 0xFF;
|
||||
auth_info.attrs.pin.min_length = 4;
|
||||
auth_info.attrs.pin.max_length = 64;
|
||||
auth_info.attrs.pin.stored_length = 64;
|
||||
auth_info.attrs.pin.type = SC_PKCS15_PIN_TYPE_ASCII_NUMERIC;
|
||||
auth_info.attrs.pin.reference = sopin_reference;
|
||||
auth_info.attrs.pin.pad_char = 0xFF;
|
||||
auth_info.attrs.pin.flags = SC_PKCS15_PIN_FLAG_CASE_SENSITIVE
|
||||
| SC_PKCS15_PIN_FLAG_INITIALIZED
|
||||
| SC_PKCS15_PIN_FLAG_NEEDS_PADDING
|
||||
| SC_PKCS15_PIN_FLAG_SO_PIN;
|
||||
auth_info.tries_left = tries_left;
|
||||
|
||||
strncpy(obj.label, "SO PIN", SC_PKCS15_MAX_LABEL_SIZE-1);
|
||||
obj.flags = SC_PKCS15_CO_FLAG_MODIFIABLE | SC_PKCS15_CO_FLAG_PRIVATE;
|
||||
|
||||
sc_debug(ctx, SC_LOG_DEBUG_NORMAL, "Add PIN(%s,auth_id:%s,reference:%i)", obj.label,
|
||||
sc_pkcs15_print_id(&info.auth_id), info.reference);
|
||||
rv = sc_pkcs15emu_add_pin_obj(p15card, &obj, &info);
|
||||
sc_pkcs15_print_id(&auth_info.auth_id), auth_info.attrs.pin.reference);
|
||||
rv = sc_pkcs15emu_add_pin_obj(p15card, &obj, &auth_info);
|
||||
SC_TEST_RET(ctx, SC_LOG_DEBUG_NORMAL, rv, "Oberthur init failed: cannot add PIN object");
|
||||
|
||||
tries_left = -1;
|
||||
rv = sc_verify(card, SC_AC_CHV, 0x81, (unsigned char *)"", 0, &tries_left);
|
||||
if (rv == SC_ERROR_PIN_CODE_INCORRECT) {
|
||||
/* add PIN */
|
||||
memset(&info, 0, sizeof(info));
|
||||
memset(&auth_info, 0, sizeof(auth_info));
|
||||
memset(&obj, 0, sizeof(obj));
|
||||
|
||||
info.auth_id.len = sizeof(PinDomainID) > sizeof(info.auth_id.value)
|
||||
? sizeof(info.auth_id.value) : sizeof(PinDomainID);
|
||||
memcpy(info.auth_id.value, PinDomainID, info.auth_id.len);
|
||||
auth_info.auth_id.len = sizeof(PinDomainID) > sizeof(auth_info.auth_id.value)
|
||||
? sizeof(auth_info.auth_id.value) : sizeof(PinDomainID);
|
||||
memcpy(auth_info.auth_id.value, PinDomainID, auth_info.auth_id.len);
|
||||
auth_info.auth_method = SC_AC_CHV;
|
||||
|
||||
info.min_length = 4;
|
||||
info.max_length = 64;
|
||||
info.stored_length = 64;
|
||||
info.type = SC_PKCS15_PIN_TYPE_ASCII_NUMERIC;
|
||||
info.reference = 0x81;
|
||||
info.auth_method = SC_AC_CHV;
|
||||
info.tries_left = tries_left;
|
||||
info.magic = SC_PKCS15_PIN_MAGIC;
|
||||
info.pad_char = 0xFF;
|
||||
info.flags = SC_PKCS15_PIN_FLAG_CASE_SENSITIVE
|
||||
auth_info.attrs.pin.min_length = 4;
|
||||
auth_info.attrs.pin.max_length = 64;
|
||||
auth_info.attrs.pin.stored_length = 64;
|
||||
auth_info.attrs.pin.type = SC_PKCS15_PIN_TYPE_ASCII_NUMERIC;
|
||||
auth_info.attrs.pin.reference = 0x81;
|
||||
auth_info.attrs.pin.pad_char = 0xFF;
|
||||
auth_info.attrs.pin.flags = SC_PKCS15_PIN_FLAG_CASE_SENSITIVE
|
||||
| SC_PKCS15_PIN_FLAG_INITIALIZED
|
||||
| SC_PKCS15_PIN_FLAG_NEEDS_PADDING
|
||||
| SC_PKCS15_PIN_FLAG_LOCAL;
|
||||
auth_info.tries_left = tries_left;
|
||||
|
||||
strncpy(obj.label, PIN_DOMAIN_LABEL, SC_PKCS15_MAX_LABEL_SIZE-1);
|
||||
obj.flags = SC_PKCS15_CO_FLAG_MODIFIABLE | SC_PKCS15_CO_FLAG_PRIVATE;
|
||||
|
||||
sc_format_path(AWP_PIN_DF, &info.path);
|
||||
info.path.type = SC_PATH_TYPE_PATH;
|
||||
sc_format_path(AWP_PIN_DF, &auth_info.path);
|
||||
auth_info.path.type = SC_PATH_TYPE_PATH;
|
||||
|
||||
sc_debug(ctx, SC_LOG_DEBUG_NORMAL, "Add PIN(%s,auth_id:%s,reference:%i)", obj.label,
|
||||
sc_pkcs15_print_id(&info.auth_id), info.reference);
|
||||
rv = sc_pkcs15emu_add_pin_obj(p15card, &obj, &info);
|
||||
sc_pkcs15_print_id(&auth_info.auth_id), auth_info.attrs.pin.reference);
|
||||
rv = sc_pkcs15emu_add_pin_obj(p15card, &obj, &auth_info);
|
||||
SC_TEST_RET(ctx, SC_LOG_DEBUG_NORMAL, rv, "Oberthur init failed: cannot add PIN object");
|
||||
}
|
||||
else if (rv != SC_ERROR_DATA_OBJECT_NOT_FOUND) {
|
||||
|
@ -126,7 +126,7 @@ sc_pkcs15emu_openpgp_init(sc_pkcs15_card_t *p15card)
|
||||
for (i = 0; i < 3; i++) {
|
||||
unsigned int flags;
|
||||
|
||||
struct sc_pkcs15_pin_info pin_info;
|
||||
struct sc_pkcs15_auth_info pin_info;
|
||||
struct sc_pkcs15_object pin_obj;
|
||||
|
||||
memset(&pin_info, 0, sizeof(pin_info));
|
||||
@ -140,15 +140,16 @@ sc_pkcs15emu_openpgp_init(sc_pkcs15_card_t *p15card)
|
||||
SC_PKCS15_PIN_FLAG_SO_PIN;
|
||||
}
|
||||
|
||||
pin_info.auth_type = SC_PKCS15_PIN_AUTH_TYPE_PIN;
|
||||
pin_info.auth_id.len = 1;
|
||||
pin_info.auth_id.value[0] = i + 1;
|
||||
pin_info.reference = i + 1;
|
||||
pin_info.flags = flags;
|
||||
pin_info.type = SC_PKCS15_PIN_TYPE_ASCII_NUMERIC;
|
||||
pin_info.min_length = 0;
|
||||
pin_info.stored_length = buffer[1+i];
|
||||
pin_info.max_length = buffer[1+i];
|
||||
pin_info.pad_char = '\0';
|
||||
pin_info.attrs.pin.reference = i + 1;
|
||||
pin_info.attrs.pin.flags = flags;
|
||||
pin_info.attrs.pin.type = SC_PKCS15_PIN_TYPE_ASCII_NUMERIC;
|
||||
pin_info.attrs.pin.min_length = 0;
|
||||
pin_info.attrs.pin.stored_length = buffer[1+i];
|
||||
pin_info.attrs.pin.max_length = buffer[1+i];
|
||||
pin_info.attrs.pin.pad_char = '\0';
|
||||
sc_format_path("3F00", &pin_info.path);
|
||||
pin_info.tries_left = buffer[4+i];
|
||||
|
||||
|
@ -59,9 +59,9 @@ int sc_pkcs15_decode_aodf_entry(struct sc_pkcs15_card *p15card,
|
||||
const u8 ** buf, size_t *buflen)
|
||||
{
|
||||
sc_context_t *ctx = p15card->card->ctx;
|
||||
struct sc_pkcs15_pin_info info;
|
||||
struct sc_pkcs15_auth_info info;
|
||||
int r;
|
||||
size_t flags_len = sizeof(info.flags);
|
||||
size_t flags_len = sizeof(info.attrs.pin.flags);
|
||||
size_t padchar_len = 1;
|
||||
struct sc_asn1_entry asn1_com_ao_attr[2], asn1_pin_attr[10], asn1_type_pin_attr[2];
|
||||
struct sc_asn1_entry asn1_pin[2];
|
||||
@ -77,13 +77,13 @@ int sc_pkcs15_decode_aodf_entry(struct sc_pkcs15_card *p15card,
|
||||
|
||||
sc_format_asn1_entry(asn1_type_pin_attr + 0, asn1_pin_attr, NULL, 0);
|
||||
|
||||
sc_format_asn1_entry(asn1_pin_attr + 0, &info.flags, &flags_len, 0);
|
||||
sc_format_asn1_entry(asn1_pin_attr + 1, &info.type, NULL, 0);
|
||||
sc_format_asn1_entry(asn1_pin_attr + 2, &info.min_length, NULL, 0);
|
||||
sc_format_asn1_entry(asn1_pin_attr + 3, &info.stored_length, NULL, 0);
|
||||
sc_format_asn1_entry(asn1_pin_attr + 4, &info.max_length, NULL, 0);
|
||||
sc_format_asn1_entry(asn1_pin_attr + 5, &info.reference, NULL, 0);
|
||||
sc_format_asn1_entry(asn1_pin_attr + 6, &info.pad_char, &padchar_len, 0);
|
||||
sc_format_asn1_entry(asn1_pin_attr + 0, &info.attrs.pin.flags, &flags_len, 0);
|
||||
sc_format_asn1_entry(asn1_pin_attr + 1, &info.attrs.pin.type, NULL, 0);
|
||||
sc_format_asn1_entry(asn1_pin_attr + 2, &info.attrs.pin.min_length, NULL, 0);
|
||||
sc_format_asn1_entry(asn1_pin_attr + 3, &info.attrs.pin.stored_length, NULL, 0);
|
||||
sc_format_asn1_entry(asn1_pin_attr + 4, &info.attrs.pin.max_length, NULL, 0);
|
||||
sc_format_asn1_entry(asn1_pin_attr + 5, &info.attrs.pin.reference, NULL, 0);
|
||||
sc_format_asn1_entry(asn1_pin_attr + 6, &info.attrs.pin.pad_char, &padchar_len, 0);
|
||||
/* We don't support lastPinChange yet. */
|
||||
sc_format_asn1_entry(asn1_pin_attr + 8, &info.path, NULL, 0);
|
||||
|
||||
@ -91,26 +91,27 @@ int sc_pkcs15_decode_aodf_entry(struct sc_pkcs15_card *p15card,
|
||||
|
||||
/* Fill in defaults */
|
||||
memset(&info, 0, sizeof(info));
|
||||
info.reference = 0;
|
||||
info.auth_type = SC_PKCS15_PIN_AUTH_TYPE_PIN;
|
||||
info.tries_left = -1;
|
||||
|
||||
r = sc_asn1_decode(ctx, asn1_pin, *buf, *buflen, buf, buflen);
|
||||
if (r == SC_ERROR_ASN1_END_OF_CONTENTS)
|
||||
return r;
|
||||
SC_TEST_RET(ctx, SC_LOG_DEBUG_NORMAL, r, "ASN.1 decoding failed");
|
||||
info.magic = SC_PKCS15_PIN_MAGIC;
|
||||
|
||||
obj->type = SC_PKCS15_TYPE_AUTH_PIN;
|
||||
obj->data = malloc(sizeof(info));
|
||||
if (obj->data == NULL)
|
||||
SC_FUNC_RETURN(ctx, SC_LOG_DEBUG_NORMAL, SC_ERROR_OUT_OF_MEMORY);
|
||||
if (info.max_length == 0) {
|
||||
|
||||
if (info.attrs.pin.max_length == 0) {
|
||||
if (p15card->card->max_pin_len != 0)
|
||||
info.max_length = p15card->card->max_pin_len;
|
||||
else if (info.stored_length != 0)
|
||||
info.max_length = info.type != SC_PKCS15_PIN_TYPE_BCD ?
|
||||
info.stored_length : 2 * info.stored_length;
|
||||
info.attrs.pin.max_length = p15card->card->max_pin_len;
|
||||
else if (info.attrs.pin.stored_length != 0)
|
||||
info.attrs.pin.max_length = info.attrs.pin.type != SC_PKCS15_PIN_TYPE_BCD ?
|
||||
info.attrs.pin.stored_length : 2 * info.attrs.pin.stored_length;
|
||||
else
|
||||
info.max_length = 8; /* shouldn't happen */
|
||||
info.attrs.pin.max_length = 8; /* shouldn't happen */
|
||||
}
|
||||
|
||||
/* OpenSC 0.11.4 and older encoded "pinReference" as a negative
|
||||
@ -118,12 +119,12 @@ int sc_pkcs15_decode_aodf_entry(struct sc_pkcs15_card *p15card,
|
||||
continue to work.
|
||||
The same invalid encoding has some models of the proprietary PKCS#15 cards.
|
||||
*/
|
||||
if (info.reference < 0)
|
||||
info.reference += 256;
|
||||
if (info.attrs.pin.reference < 0)
|
||||
info.attrs.pin.reference += 256;
|
||||
|
||||
info.auth_method = SC_AC_CHV;
|
||||
|
||||
if (info.flags & SC_PKCS15_PIN_FLAG_LOCAL) {
|
||||
if (info.attrs.pin.flags & SC_PKCS15_PIN_FLAG_LOCAL) {
|
||||
/* In OpenSC pkcs#15 framework 'path' is mandatory for the 'Local' PINs.
|
||||
* If 'path' do not present in PinAttributes,
|
||||
* derive it from the PKCS#15 context. */
|
||||
@ -135,7 +136,7 @@ int sc_pkcs15_decode_aodf_entry(struct sc_pkcs15_card *p15card,
|
||||
info.path = p15card->file_app->path;
|
||||
}
|
||||
}
|
||||
sc_debug(ctx, SC_LOG_DEBUG_ASN1, "decoded PIN(ref:%X,path:%s)", info.reference, sc_print_path(&info.path));
|
||||
sc_debug(ctx, SC_LOG_DEBUG_ASN1, "decoded PIN(ref:%X,path:%s)", info.attrs.pin.reference, sc_print_path(&info.path));
|
||||
|
||||
memcpy(obj->data, &info, sizeof(info));
|
||||
SC_FUNC_RETURN(ctx, SC_LOG_DEBUG_ASN1, SC_SUCCESS);
|
||||
@ -147,14 +148,16 @@ int sc_pkcs15_encode_aodf_entry(sc_context_t *ctx,
|
||||
{
|
||||
struct sc_asn1_entry asn1_com_ao_attr[2], asn1_pin_attr[10], asn1_type_pin_attr[2];
|
||||
struct sc_asn1_entry asn1_pin[2];
|
||||
struct sc_pkcs15_pin_info *pin =
|
||||
(struct sc_pkcs15_pin_info *) obj->data;
|
||||
struct sc_pkcs15_auth_info *info = (struct sc_pkcs15_auth_info *) obj->data;
|
||||
struct sc_asn1_pkcs15_object pin_obj = { (struct sc_pkcs15_object *) obj,
|
||||
asn1_com_ao_attr, NULL, asn1_type_pin_attr };
|
||||
int r;
|
||||
size_t flags_len;
|
||||
size_t padchar_len = 1;
|
||||
|
||||
if (info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_NOT_SUPPORTED;
|
||||
|
||||
sc_copy_asn1_entry(c_asn1_pin, asn1_pin);
|
||||
sc_copy_asn1_entry(c_asn1_type_pin_attr, asn1_type_pin_attr);
|
||||
sc_copy_asn1_entry(c_asn1_pin_attr, asn1_pin_attr);
|
||||
@ -164,39 +167,39 @@ int sc_pkcs15_encode_aodf_entry(sc_context_t *ctx,
|
||||
|
||||
sc_format_asn1_entry(asn1_type_pin_attr + 0, asn1_pin_attr, NULL, 1);
|
||||
|
||||
flags_len = sizeof(pin->flags);
|
||||
sc_format_asn1_entry(asn1_pin_attr + 0, &pin->flags, &flags_len, 1);
|
||||
sc_format_asn1_entry(asn1_pin_attr + 1, &pin->type, NULL, 1);
|
||||
sc_format_asn1_entry(asn1_pin_attr + 2, &pin->min_length, NULL, 1);
|
||||
sc_format_asn1_entry(asn1_pin_attr + 3, &pin->stored_length, NULL, 1);
|
||||
if (pin->max_length > 0)
|
||||
sc_format_asn1_entry(asn1_pin_attr + 4, &pin->max_length, NULL, 1);
|
||||
if (pin->reference >= 0)
|
||||
sc_format_asn1_entry(asn1_pin_attr + 5, &pin->reference, NULL, 1);
|
||||
flags_len = sizeof(info->attrs.pin.flags);
|
||||
sc_format_asn1_entry(asn1_pin_attr + 0, &info->attrs.pin.flags, &flags_len, 1);
|
||||
sc_format_asn1_entry(asn1_pin_attr + 1, &info->attrs.pin.type, NULL, 1);
|
||||
sc_format_asn1_entry(asn1_pin_attr + 2, &info->attrs.pin.min_length, NULL, 1);
|
||||
sc_format_asn1_entry(asn1_pin_attr + 3, &info->attrs.pin.stored_length, NULL, 1);
|
||||
if (info->attrs.pin.max_length > 0)
|
||||
sc_format_asn1_entry(asn1_pin_attr + 4, &info->attrs.pin.max_length, NULL, 1);
|
||||
if (info->attrs.pin.reference >= 0)
|
||||
sc_format_asn1_entry(asn1_pin_attr + 5, &info->attrs.pin.reference, NULL, 1);
|
||||
/* FIXME: check if pad_char present */
|
||||
sc_format_asn1_entry(asn1_pin_attr + 6, &pin->pad_char, &padchar_len, 1);
|
||||
sc_format_asn1_entry(asn1_pin_attr + 8, &pin->path, NULL, pin->path.len ? 1 : 0);
|
||||
sc_format_asn1_entry(asn1_pin_attr + 6, &info->attrs.pin.pad_char, &padchar_len, 1);
|
||||
sc_format_asn1_entry(asn1_pin_attr + 8, &info->path, NULL, info->path.len ? 1 : 0);
|
||||
|
||||
sc_format_asn1_entry(asn1_com_ao_attr + 0, &pin->auth_id, NULL, 1);
|
||||
sc_format_asn1_entry(asn1_com_ao_attr + 0, &info->auth_id, NULL, 1);
|
||||
|
||||
assert(pin->magic == SC_PKCS15_PIN_MAGIC);
|
||||
r = sc_asn1_encode(ctx, asn1_pin, buf, buflen);
|
||||
|
||||
return r;
|
||||
}
|
||||
|
||||
static int _validate_pin(struct sc_pkcs15_card *p15card,
|
||||
struct sc_pkcs15_pin_info *pin,
|
||||
struct sc_pkcs15_auth_info *auth_info,
|
||||
size_t pinlen)
|
||||
{
|
||||
size_t max_length;
|
||||
assert(p15card != NULL);
|
||||
|
||||
if (pin->magic != SC_PKCS15_PIN_MAGIC)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
/* Ignore validation of the non-PIN authentication objects */
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_SUCCESS;
|
||||
|
||||
/* prevent buffer overflow from hostile card */
|
||||
if (pin->stored_length > SC_MAX_PIN_SIZE)
|
||||
if (auth_info->attrs.pin.stored_length > SC_MAX_PIN_SIZE)
|
||||
return SC_ERROR_BUFFER_TOO_SMALL;
|
||||
|
||||
/* if we use pinpad, no more checks are needed */
|
||||
@ -204,8 +207,8 @@ static int _validate_pin(struct sc_pkcs15_card *p15card,
|
||||
return SC_SUCCESS;
|
||||
|
||||
/* If pin is given, make sure it is within limits */
|
||||
max_length = pin->max_length != 0 ? pin->max_length : SC_MAX_PIN_SIZE;
|
||||
if (pinlen > max_length || pinlen < pin->min_length)
|
||||
max_length = auth_info->attrs.pin.max_length != 0 ? auth_info->attrs.pin.max_length : SC_MAX_PIN_SIZE;
|
||||
if (pinlen > max_length || pinlen < auth_info->attrs.pin.min_length)
|
||||
return SC_ERROR_INVALID_PIN_LENGTH;
|
||||
|
||||
return SC_SUCCESS;
|
||||
@ -223,7 +226,7 @@ int sc_pkcs15_verify_pin(struct sc_pkcs15_card *p15card,
|
||||
const unsigned char *pincode, size_t pinlen)
|
||||
{
|
||||
struct sc_context *ctx = p15card->card->ctx;
|
||||
struct sc_pkcs15_pin_info *pin_info = (struct sc_pkcs15_pin_info *)pin_obj->data;
|
||||
struct sc_pkcs15_auth_info *auth_info = (struct sc_pkcs15_auth_info *)pin_obj->data;
|
||||
int r;
|
||||
sc_card_t *card;
|
||||
struct sc_pin_cmd_data data;
|
||||
@ -231,7 +234,11 @@ int sc_pkcs15_verify_pin(struct sc_pkcs15_card *p15card,
|
||||
SC_FUNC_CALLED(ctx, SC_LOG_DEBUG_NORMAL);
|
||||
sc_debug(ctx, SC_LOG_DEBUG_NORMAL, "PIN(%p;len:%i)", pincode, pinlen);
|
||||
|
||||
r = _validate_pin(p15card, pin_info, pinlen);
|
||||
/* TODO: verify other authentication objects */
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_NOT_SUPPORTED;
|
||||
|
||||
r = _validate_pin(p15card, auth_info, pinlen);
|
||||
SC_TEST_RET(ctx, SC_LOG_DEBUG_NORMAL, r, "PIN value do not conforms the PIN policy");
|
||||
|
||||
card = p15card->card;
|
||||
@ -239,8 +246,8 @@ int sc_pkcs15_verify_pin(struct sc_pkcs15_card *p15card,
|
||||
r = sc_lock(card);
|
||||
SC_TEST_RET(ctx, SC_LOG_DEBUG_NORMAL, r, "sc_lock() failed");
|
||||
/* the path in the pin object is optional */
|
||||
if (pin_info->path.len > 0) {
|
||||
r = sc_select_file(card, &pin_info->path, NULL);
|
||||
if (auth_info->path.len > 0) {
|
||||
r = sc_select_file(card, &auth_info->path, NULL);
|
||||
if (r)
|
||||
goto out;
|
||||
}
|
||||
@ -248,19 +255,19 @@ int sc_pkcs15_verify_pin(struct sc_pkcs15_card *p15card,
|
||||
/* Initialize arguments */
|
||||
memset(&data, 0, sizeof(data));
|
||||
data.cmd = SC_PIN_CMD_VERIFY;
|
||||
data.pin_type = pin_info->auth_method;
|
||||
data.pin_reference = pin_info->reference;
|
||||
data.pin1.min_length = pin_info->min_length;
|
||||
data.pin1.max_length = pin_info->max_length;
|
||||
data.pin1.pad_length = pin_info->stored_length;
|
||||
data.pin1.pad_char = pin_info->pad_char;
|
||||
data.pin_type = auth_info->auth_method;
|
||||
data.pin_reference = auth_info->attrs.pin.reference;
|
||||
data.pin1.min_length = auth_info->attrs.pin.min_length;
|
||||
data.pin1.max_length = auth_info->attrs.pin.max_length;
|
||||
data.pin1.pad_length = auth_info->attrs.pin.stored_length;
|
||||
data.pin1.pad_char = auth_info->attrs.pin.pad_char;
|
||||
data.pin1.data = pincode;
|
||||
data.pin1.len = pinlen;
|
||||
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_NEEDS_PADDING)
|
||||
if (auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_NEEDS_PADDING)
|
||||
data.flags |= SC_PIN_CMD_NEED_PADDING;
|
||||
|
||||
switch (pin_info->type) {
|
||||
switch (auth_info->attrs.pin.type) {
|
||||
case SC_PKCS15_PIN_TYPE_BCD:
|
||||
data.pin1.encoding = SC_PIN_ENCODING_BCD;
|
||||
break;
|
||||
@ -275,13 +282,13 @@ int sc_pkcs15_verify_pin(struct sc_pkcs15_card *p15card,
|
||||
if(p15card->card->reader->capabilities & SC_READER_CAP_PIN_PAD) {
|
||||
if (!pincode && !pinlen)
|
||||
data.flags |= SC_PIN_CMD_USE_PINPAD;
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
if (auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
data.pin1.prompt = "Please enter SO PIN";
|
||||
else
|
||||
data.pin1.prompt = "Please enter PIN";
|
||||
}
|
||||
|
||||
r = sc_pin_cmd(card, &data, &pin_info->tries_left);
|
||||
r = sc_pin_cmd(card, &data, &auth_info->tries_left);
|
||||
if (r == SC_SUCCESS)
|
||||
sc_pkcs15_pincache_add(p15card, pin_obj, pincode, pinlen);
|
||||
out:
|
||||
@ -300,20 +307,23 @@ int sc_pkcs15_change_pin(struct sc_pkcs15_card *p15card,
|
||||
int r;
|
||||
sc_card_t *card;
|
||||
struct sc_pin_cmd_data data;
|
||||
struct sc_pkcs15_pin_info *pin_info = (struct sc_pkcs15_pin_info *)pin_obj->data;
|
||||
struct sc_pkcs15_auth_info *auth_info = (struct sc_pkcs15_auth_info *)pin_obj->data;
|
||||
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_NOT_SUPPORTED;
|
||||
|
||||
/* make sure the pins are in valid range */
|
||||
if ((r = _validate_pin(p15card, pin_info, oldpinlen)) != SC_SUCCESS)
|
||||
if ((r = _validate_pin(p15card, auth_info, oldpinlen)) != SC_SUCCESS)
|
||||
return r;
|
||||
if ((r = _validate_pin(p15card, pin_info, newpinlen)) != SC_SUCCESS)
|
||||
if ((r = _validate_pin(p15card, auth_info, newpinlen)) != SC_SUCCESS)
|
||||
return r;
|
||||
|
||||
card = p15card->card;
|
||||
r = sc_lock(card);
|
||||
SC_TEST_RET(card->ctx, SC_LOG_DEBUG_NORMAL, r, "sc_lock() failed");
|
||||
/* the path in the pin object is optional */
|
||||
if (pin_info->path.len > 0) {
|
||||
r = sc_select_file(card, &pin_info->path, NULL);
|
||||
if (auth_info->path.len > 0) {
|
||||
r = sc_select_file(card, &auth_info->path, NULL);
|
||||
if (r)
|
||||
goto out;
|
||||
}
|
||||
@ -322,24 +332,24 @@ int sc_pkcs15_change_pin(struct sc_pkcs15_card *p15card,
|
||||
memset(&data, 0, sizeof(data));
|
||||
data.cmd = SC_PIN_CMD_CHANGE;
|
||||
data.pin_type = SC_AC_CHV;
|
||||
data.pin_reference = pin_info->reference;
|
||||
data.pin_reference = auth_info->attrs.pin.reference;
|
||||
data.pin1.data = oldpin;
|
||||
data.pin1.len = oldpinlen;
|
||||
data.pin1.pad_char = pin_info->pad_char;
|
||||
data.pin1.min_length = pin_info->min_length;
|
||||
data.pin1.max_length = pin_info->max_length;
|
||||
data.pin1.pad_length = pin_info->stored_length;
|
||||
data.pin1.pad_char = auth_info->attrs.pin.pad_char;
|
||||
data.pin1.min_length = auth_info->attrs.pin.min_length;
|
||||
data.pin1.max_length = auth_info->attrs.pin.max_length;
|
||||
data.pin1.pad_length = auth_info->attrs.pin.stored_length;
|
||||
data.pin2.data = newpin;
|
||||
data.pin2.len = newpinlen;
|
||||
data.pin2.pad_char = pin_info->pad_char;
|
||||
data.pin2.min_length = pin_info->min_length;
|
||||
data.pin2.max_length = pin_info->max_length;
|
||||
data.pin2.pad_length = pin_info->stored_length;
|
||||
data.pin2.pad_char = auth_info->attrs.pin.pad_char;
|
||||
data.pin2.min_length = auth_info->attrs.pin.min_length;
|
||||
data.pin2.max_length = auth_info->attrs.pin.max_length;
|
||||
data.pin2.pad_length = auth_info->attrs.pin.stored_length;
|
||||
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_NEEDS_PADDING)
|
||||
if (auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_NEEDS_PADDING)
|
||||
data.flags |= SC_PIN_CMD_NEED_PADDING;
|
||||
|
||||
switch (pin_info->type) {
|
||||
switch (auth_info->attrs.pin.type) {
|
||||
case SC_PKCS15_PIN_TYPE_BCD:
|
||||
data.pin1.encoding = SC_PIN_ENCODING_BCD;
|
||||
data.pin2.encoding = SC_PIN_ENCODING_BCD;
|
||||
@ -353,7 +363,7 @@ int sc_pkcs15_change_pin(struct sc_pkcs15_card *p15card,
|
||||
if((!oldpin || !newpin)
|
||||
&& p15card->card->reader->capabilities & SC_READER_CAP_PIN_PAD) {
|
||||
data.flags |= SC_PIN_CMD_USE_PINPAD;
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
if (auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
data.pin1.prompt = "Please enter SO PIN";
|
||||
data.pin2.prompt = "Please enter new SO PIN";
|
||||
} else {
|
||||
@ -362,7 +372,7 @@ int sc_pkcs15_change_pin(struct sc_pkcs15_card *p15card,
|
||||
}
|
||||
}
|
||||
|
||||
r = sc_pin_cmd(card, &data, &pin_info->tries_left);
|
||||
r = sc_pin_cmd(card, &data, &auth_info->tries_left);
|
||||
if (r == SC_SUCCESS)
|
||||
sc_pkcs15_pincache_add(p15card, pin_obj, newpin, newpinlen);
|
||||
|
||||
@ -383,11 +393,14 @@ int sc_pkcs15_unblock_pin(struct sc_pkcs15_card *p15card,
|
||||
sc_card_t *card;
|
||||
struct sc_pin_cmd_data data;
|
||||
struct sc_pkcs15_object *puk_obj;
|
||||
struct sc_pkcs15_pin_info *puk_info = NULL;
|
||||
struct sc_pkcs15_pin_info *pin_info = (struct sc_pkcs15_pin_info *)pin_obj->data;
|
||||
struct sc_pkcs15_auth_info *puk_info = NULL;
|
||||
struct sc_pkcs15_auth_info *auth_info = (struct sc_pkcs15_auth_info *)pin_obj->data;
|
||||
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_NOT_SUPPORTED;
|
||||
|
||||
/* make sure the pins are in valid range */
|
||||
if ((r = _validate_pin(p15card, pin_info, newpinlen)) != SC_SUCCESS)
|
||||
if ((r = _validate_pin(p15card, auth_info, newpinlen)) != SC_SUCCESS)
|
||||
return r;
|
||||
|
||||
card = p15card->card;
|
||||
@ -399,11 +412,11 @@ int sc_pkcs15_unblock_pin(struct sc_pkcs15_card *p15card,
|
||||
r = sc_pkcs15_find_pin_by_auth_id(p15card, &pin_obj->auth_id, &puk_obj);
|
||||
if (r >= 0 && puk_obj) {
|
||||
/* second step: get the pkcs15 info object of the puk */
|
||||
puk_info = (struct sc_pkcs15_pin_info *)puk_obj->data;
|
||||
puk_info = (struct sc_pkcs15_auth_info *)puk_obj->data;
|
||||
}
|
||||
if (!puk_info) {
|
||||
sc_debug(card->ctx, SC_LOG_DEBUG_NORMAL, "Unable to get puk object, using pin object instead!");
|
||||
puk_info = pin_info;
|
||||
puk_info = auth_info;
|
||||
}
|
||||
|
||||
/* make sure the puk is in valid range */
|
||||
@ -413,8 +426,8 @@ int sc_pkcs15_unblock_pin(struct sc_pkcs15_card *p15card,
|
||||
r = sc_lock(card);
|
||||
SC_TEST_RET(card->ctx, SC_LOG_DEBUG_NORMAL, r, "sc_lock() failed");
|
||||
/* the path in the pin object is optional */
|
||||
if (pin_info->path.len > 0) {
|
||||
r = sc_select_file(card, &pin_info->path, NULL);
|
||||
if (auth_info->path.len > 0) {
|
||||
r = sc_select_file(card, &auth_info->path, NULL);
|
||||
if (r)
|
||||
goto out;
|
||||
}
|
||||
@ -423,24 +436,24 @@ int sc_pkcs15_unblock_pin(struct sc_pkcs15_card *p15card,
|
||||
memset(&data, 0, sizeof(data));
|
||||
data.cmd = SC_PIN_CMD_UNBLOCK;
|
||||
data.pin_type = SC_AC_CHV;
|
||||
data.pin_reference = pin_info->reference;
|
||||
data.pin_reference = auth_info->attrs.pin.reference;
|
||||
data.pin1.data = puk;
|
||||
data.pin1.len = puklen;
|
||||
data.pin1.pad_char = pin_info->pad_char;
|
||||
data.pin1.min_length = pin_info->min_length;
|
||||
data.pin1.max_length = pin_info->max_length;
|
||||
data.pin1.pad_length = pin_info->stored_length;
|
||||
data.pin1.pad_char = auth_info->attrs.pin.pad_char;
|
||||
data.pin1.min_length = auth_info->attrs.pin.min_length;
|
||||
data.pin1.max_length = auth_info->attrs.pin.max_length;
|
||||
data.pin1.pad_length = auth_info->attrs.pin.stored_length;
|
||||
data.pin2.data = newpin;
|
||||
data.pin2.len = newpinlen;
|
||||
data.pin2.pad_char = puk_info->pad_char;
|
||||
data.pin2.min_length = puk_info->min_length;
|
||||
data.pin2.max_length = puk_info->max_length;
|
||||
data.pin2.pad_length = puk_info->stored_length;
|
||||
data.pin2.pad_char = puk_info->attrs.pin.pad_char;
|
||||
data.pin2.min_length = puk_info->attrs.pin.min_length;
|
||||
data.pin2.max_length = puk_info->attrs.pin.max_length;
|
||||
data.pin2.pad_length = puk_info->attrs.pin.stored_length;
|
||||
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_NEEDS_PADDING)
|
||||
if (auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_NEEDS_PADDING)
|
||||
data.flags |= SC_PIN_CMD_NEED_PADDING;
|
||||
|
||||
switch (pin_info->type) {
|
||||
switch (auth_info->attrs.pin.type) {
|
||||
case SC_PKCS15_PIN_TYPE_BCD:
|
||||
data.pin1.encoding = SC_PIN_ENCODING_BCD;
|
||||
break;
|
||||
@ -449,7 +462,7 @@ int sc_pkcs15_unblock_pin(struct sc_pkcs15_card *p15card,
|
||||
break;
|
||||
}
|
||||
|
||||
switch (puk_info->type) {
|
||||
switch (puk_info->attrs.pin.type) {
|
||||
case SC_PKCS15_PIN_TYPE_BCD:
|
||||
data.pin2.encoding = SC_PIN_ENCODING_BCD;
|
||||
break;
|
||||
@ -460,7 +473,7 @@ int sc_pkcs15_unblock_pin(struct sc_pkcs15_card *p15card,
|
||||
|
||||
if(p15card->card->reader->capabilities & SC_READER_CAP_PIN_PAD) {
|
||||
data.flags |= SC_PIN_CMD_USE_PINPAD;
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
if (auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
data.pin1.prompt = "Please enter PUK";
|
||||
data.pin2.prompt = "Please enter new SO PIN";
|
||||
} else {
|
||||
@ -469,7 +482,7 @@ int sc_pkcs15_unblock_pin(struct sc_pkcs15_card *p15card,
|
||||
}
|
||||
}
|
||||
|
||||
r = sc_pin_cmd(card, &data, &pin_info->tries_left);
|
||||
r = sc_pin_cmd(card, &data, &auth_info->tries_left);
|
||||
if (r == SC_SUCCESS)
|
||||
sc_pkcs15_pincache_add(p15card, pin_obj, newpin, newpinlen);
|
||||
|
||||
@ -478,9 +491,9 @@ out:
|
||||
return r;
|
||||
}
|
||||
|
||||
void sc_pkcs15_free_pin_info(sc_pkcs15_pin_info_t *pin)
|
||||
void sc_pkcs15_free_auth_info(sc_pkcs15_auth_info_t *auth_info)
|
||||
{
|
||||
free(pin);
|
||||
free(auth_info);
|
||||
}
|
||||
|
||||
|
||||
@ -489,7 +502,7 @@ void sc_pkcs15_pincache_add(struct sc_pkcs15_card *p15card, struct sc_pkcs15_obj
|
||||
const u8 *pin, size_t pinlen)
|
||||
{
|
||||
struct sc_context *ctx = p15card->card->ctx;
|
||||
struct sc_pkcs15_pin_info *pin_info = (struct sc_pkcs15_pin_info *)pin_obj->data;
|
||||
struct sc_pkcs15_auth_info *auth_info = (struct sc_pkcs15_auth_info *)pin_obj->data;
|
||||
struct sc_pkcs15_object *obj = NULL;
|
||||
int r;
|
||||
|
||||
@ -509,7 +522,7 @@ void sc_pkcs15_pincache_add(struct sc_pkcs15_card *p15card, struct sc_pkcs15_obj
|
||||
* "6.1.16 CommonAuthenticationObjectAttributes" with the exception that
|
||||
* "CommonObjectAttributes.accessControlRules" are not taken into account. */
|
||||
|
||||
if (sc_pkcs15_compare_id(&obj->auth_id, &pin_info->auth_id)) {
|
||||
if (sc_pkcs15_compare_id(&obj->auth_id, &auth_info->auth_id)) {
|
||||
/* Caching is refused, if the protected object requires user consent */
|
||||
if (obj->user_consent > 0) {
|
||||
sc_debug(ctx, SC_LOG_DEBUG_NORMAL, "caching refused (user consent)");
|
||||
|
@ -763,7 +763,7 @@ static int sc_pkcs15emu_piv_init(sc_pkcs15_card_t *p15card)
|
||||
/* set pins */
|
||||
sc_debug(card->ctx, SC_LOG_DEBUG_NORMAL, "PIV-II adding pins...");
|
||||
for (i = 0; pins[i].label; i++) {
|
||||
struct sc_pkcs15_pin_info pin_info;
|
||||
struct sc_pkcs15_auth_info pin_info;
|
||||
struct sc_pkcs15_object pin_obj;
|
||||
const char * label;
|
||||
int pin_ref;
|
||||
@ -771,14 +771,15 @@ static int sc_pkcs15emu_piv_init(sc_pkcs15_card_t *p15card)
|
||||
memset(&pin_info, 0, sizeof(pin_info));
|
||||
memset(&pin_obj, 0, sizeof(pin_obj));
|
||||
|
||||
pin_info.auth_type = SC_PKCS15_PIN_AUTH_TYPE_PIN;
|
||||
sc_pkcs15_format_id(pins[i].id, &pin_info.auth_id);
|
||||
pin_info.reference = pins[i].ref;
|
||||
pin_info.flags = pins[i].flags;
|
||||
pin_info.type = pins[i].type;
|
||||
pin_info.min_length = pins[i].minlen;
|
||||
pin_info.stored_length = pins[i].storedlen;
|
||||
pin_info.max_length = pins[i].maxlen;
|
||||
pin_info.pad_char = pins[i].pad_char;
|
||||
pin_info.attrs.pin.reference = pins[i].ref;
|
||||
pin_info.attrs.pin.flags = pins[i].flags;
|
||||
pin_info.attrs.pin.type = pins[i].type;
|
||||
pin_info.attrs.pin.min_length = pins[i].minlen;
|
||||
pin_info.attrs.pin.stored_length = pins[i].storedlen;
|
||||
pin_info.attrs.pin.max_length = pins[i].maxlen;
|
||||
pin_info.attrs.pin.pad_char = pins[i].pad_char;
|
||||
sc_format_path(pins[i].path, &pin_info.path);
|
||||
pin_info.tries_left = -1;
|
||||
|
||||
@ -787,7 +788,7 @@ static int sc_pkcs15emu_piv_init(sc_pkcs15_card_t *p15card)
|
||||
(card->ops->card_ctl)(card, SC_CARDCTL_PIV_PIN_PREFERENCE,
|
||||
&pin_ref) == 0 &&
|
||||
pin_ref == 0x00) { /* must be 80 for PIV pin, or 00 for Global PIN */
|
||||
pin_info.reference = pin_ref;
|
||||
pin_info.attrs.pin.reference = pin_ref;
|
||||
label = "Global PIN";
|
||||
}
|
||||
sc_debug(card->ctx, SC_LOG_DEBUG_NORMAL, "DEE Adding pin %d label=%s",i, label);
|
||||
|
@ -67,27 +67,27 @@ static int sc_pkcs15emu_add_pin(sc_pkcs15_card_t *p15card,
|
||||
unsigned int max_length,
|
||||
int flags, int tries_left, const char pad_char, int obj_flags)
|
||||
{
|
||||
sc_pkcs15_pin_info_t info;
|
||||
sc_pkcs15_auth_info_t info;
|
||||
sc_pkcs15_object_t obj;
|
||||
|
||||
memset(&info, 0, sizeof(info));
|
||||
memset(&obj, 0, sizeof(obj));
|
||||
|
||||
info.auth_id = *id;
|
||||
info.min_length = min_length;
|
||||
info.max_length = max_length;
|
||||
info.stored_length = max_length;
|
||||
info.type = type;
|
||||
info.reference = ref;
|
||||
info.flags = flags;
|
||||
info.auth_type = SC_PKCS15_PIN_AUTH_TYPE_PIN;
|
||||
info.attrs.pin.min_length = min_length;
|
||||
info.attrs.pin.max_length = max_length;
|
||||
info.attrs.pin.stored_length = max_length;
|
||||
info.attrs.pin.type = type;
|
||||
info.attrs.pin.reference = ref;
|
||||
info.attrs.pin.flags = flags;
|
||||
info.attrs.pin.pad_char = pad_char;
|
||||
info.tries_left = tries_left;
|
||||
info.magic = SC_PKCS15_PIN_MAGIC;
|
||||
info.pad_char = pad_char;
|
||||
|
||||
if (path)
|
||||
info.path = *path;
|
||||
if (type == SC_PKCS15_PIN_TYPE_BCD)
|
||||
info.stored_length /= 2;
|
||||
info.attrs.pin.stored_length /= 2;
|
||||
|
||||
strlcpy(obj.label, label, sizeof(obj.label));
|
||||
obj.flags = obj_flags;
|
||||
|
@ -151,23 +151,24 @@ static int sc_pkcs15emu_pteid_init(sc_pkcs15_card_t * p15card)
|
||||
/* PIN Paths */
|
||||
static const char *pteid_pin_paths[2][3] = { {NULL, "3f005f00", NULL},
|
||||
{NULL, NULL, NULL} };
|
||||
struct sc_pkcs15_pin_info pin_info;
|
||||
struct sc_pkcs15_auth_info pin_info;
|
||||
struct sc_pkcs15_object pin_obj;
|
||||
|
||||
memset(&pin_info, 0, sizeof(pin_info));
|
||||
memset(&pin_obj, 0, sizeof(pin_obj));
|
||||
|
||||
pin_info.auth_type = SC_PKCS15_PIN_AUTH_TYPE_PIN;
|
||||
pin_info.auth_id.len = 1;
|
||||
pin_info.auth_id.value[0] = pteid_pin_authid[i];
|
||||
pin_info.reference = pteid_pin_ref[type][i];
|
||||
pin_info.flags = SC_PKCS15_PIN_FLAG_NEEDS_PADDING
|
||||
pin_info.attrs.pin.reference = pteid_pin_ref[type][i];
|
||||
pin_info.attrs.pin.flags = SC_PKCS15_PIN_FLAG_NEEDS_PADDING
|
||||
| SC_PKCS15_PIN_FLAG_INITIALIZED
|
||||
| SC_PKCS15_PIN_FLAG_CASE_SENSITIVE;
|
||||
pin_info.type = SC_PKCS15_PIN_TYPE_ASCII_NUMERIC;
|
||||
pin_info.min_length = 4;
|
||||
pin_info.stored_length = 8;
|
||||
pin_info.max_length = 8;
|
||||
pin_info.pad_char = type == IAS_CARD ? 0x2F : 0xFF;
|
||||
pin_info.attrs.pin.type = SC_PKCS15_PIN_TYPE_ASCII_NUMERIC;
|
||||
pin_info.attrs.pin.min_length = 4;
|
||||
pin_info.attrs.pin.stored_length = 8;
|
||||
pin_info.attrs.pin.max_length = 8;
|
||||
pin_info.attrs.pin.pad_char = type == IAS_CARD ? 0x2F : 0xFF;
|
||||
pin_info.tries_left = -1;
|
||||
if (pteid_pin_paths[type][i] != NULL)
|
||||
sc_format_path(pteid_pin_paths[type][i], &pin_info.path);
|
||||
|
@ -203,20 +203,22 @@ static int sc_pkcs15emu_starcert_init(sc_pkcs15_card_t *p15card)
|
||||
}
|
||||
/* set pins */
|
||||
for (i = 0; pins[i].label; i++) {
|
||||
struct sc_pkcs15_pin_info pin_info;
|
||||
struct sc_pkcs15_auth_info pin_info;
|
||||
struct sc_pkcs15_object pin_obj;
|
||||
|
||||
memset(&pin_info, 0, sizeof(pin_info));
|
||||
memset(&pin_obj, 0, sizeof(pin_obj));
|
||||
|
||||
|
||||
sc_pkcs15_format_id(pins[i].id, &pin_info.auth_id);
|
||||
pin_info.reference = pins[i].ref;
|
||||
pin_info.flags = pins[i].flags;
|
||||
pin_info.type = pins[i].type;
|
||||
pin_info.min_length = pins[i].minlen;
|
||||
pin_info.stored_length = pins[i].storedlen;
|
||||
pin_info.max_length = pins[i].maxlen;
|
||||
pin_info.pad_char = pins[i].pad_char;
|
||||
pin_info.auth_type = SC_PKCS15_PIN_AUTH_TYPE_PIN;
|
||||
pin_info.attrs.pin.reference = pins[i].ref;
|
||||
pin_info.attrs.pin.flags = pins[i].flags;
|
||||
pin_info.attrs.pin.type = pins[i].type;
|
||||
pin_info.attrs.pin.min_length = pins[i].minlen;
|
||||
pin_info.attrs.pin.stored_length = pins[i].storedlen;
|
||||
pin_info.attrs.pin.max_length = pins[i].maxlen;
|
||||
pin_info.attrs.pin.pad_char = pins[i].pad_char;
|
||||
sc_format_path(pins[i].path, &pin_info.path);
|
||||
pin_info.tries_left = -1;
|
||||
|
||||
|
@ -324,11 +324,11 @@ static sc_pkcs15_df_t * sc_pkcs15emu_get_df(sc_pkcs15_card_t *p15card,
|
||||
}
|
||||
|
||||
int sc_pkcs15emu_add_pin_obj(sc_pkcs15_card_t *p15card,
|
||||
const sc_pkcs15_object_t *obj, const sc_pkcs15_pin_info_t *in_pin)
|
||||
const sc_pkcs15_object_t *obj, const sc_pkcs15_auth_info_t *in_pin)
|
||||
{
|
||||
sc_pkcs15_pin_info_t pin = *in_pin;
|
||||
sc_pkcs15_auth_info_t pin = *in_pin;
|
||||
|
||||
pin.magic = SC_PKCS15_PIN_MAGIC;
|
||||
pin.auth_type = SC_PKCS15_PIN_AUTH_TYPE_PIN;
|
||||
if(!pin.auth_method) /* or SC_AC_NONE */
|
||||
pin.auth_method = SC_AC_CHV;
|
||||
|
||||
@ -412,7 +412,7 @@ int sc_pkcs15emu_object_add(sc_pkcs15_card_t *p15card, unsigned int type,
|
||||
switch (type & SC_PKCS15_TYPE_CLASS_MASK) {
|
||||
case SC_PKCS15_TYPE_AUTH:
|
||||
df_type = SC_PKCS15_AODF;
|
||||
data_len = sizeof(struct sc_pkcs15_pin_info);
|
||||
data_len = sizeof(struct sc_pkcs15_auth_info);
|
||||
break;
|
||||
case SC_PKCS15_TYPE_PRKEY:
|
||||
df_type = SC_PKCS15_PRKDF;
|
||||
|
@ -166,7 +166,7 @@ static int create_pin_obj(sc_pkcs15_card_t *p15card, int cert,
|
||||
int key_descr, unsigned int pinId)
|
||||
{
|
||||
sc_pkcs15_object_t p15obj;
|
||||
sc_pkcs15_pin_info_t ainfo;
|
||||
sc_pkcs15_auth_info_t ainfo;
|
||||
|
||||
/* init data objects */
|
||||
memset(&p15obj, 0, sizeof(p15obj));
|
||||
@ -174,15 +174,16 @@ static int create_pin_obj(sc_pkcs15_card_t *p15card, int cert,
|
||||
/* the authentication object attributes */
|
||||
ainfo.auth_id.value[0] = (u8)pinId;
|
||||
ainfo.auth_id.len = 1;
|
||||
ainfo.reference = (u8)pinId;
|
||||
ainfo.flags = SC_PKCS15_PIN_FLAG_EXCHANGE_REF_DATA;
|
||||
ainfo.auth_type = SC_PKCS15_PIN_AUTH_TYPE_PIN;
|
||||
ainfo.attrs.pin.reference = (u8)pinId;
|
||||
ainfo.attrs.pin.flags = SC_PKCS15_PIN_FLAG_EXCHANGE_REF_DATA;
|
||||
if ((key_descr & TC_CARDOS_PIN_MASK) == TC_CARDOS_LOCALPIN)
|
||||
ainfo.flags |= SC_PKCS15_PIN_FLAG_LOCAL;
|
||||
ainfo.type = SC_PKCS15_PIN_TYPE_BCD; /* XXX */
|
||||
ainfo.min_length = 6; /* XXX */
|
||||
ainfo.stored_length = 8; /* XXX */
|
||||
ainfo.max_length = 8;
|
||||
ainfo.pad_char = 0;
|
||||
ainfo.attrs.pin.flags |= SC_PKCS15_PIN_FLAG_LOCAL;
|
||||
ainfo.attrs.pin.type = SC_PKCS15_PIN_TYPE_BCD; /* XXX */
|
||||
ainfo.attrs.pin.min_length = 6; /* XXX */
|
||||
ainfo.attrs.pin.stored_length = 8; /* XXX */
|
||||
ainfo.attrs.pin.max_length = 8;
|
||||
ainfo.attrs.pin.pad_char = 0;
|
||||
ainfo.tries_left = 3; /* XXX */
|
||||
sc_format_path(TC_CARDOS_APP_DF, &ainfo.path);
|
||||
ainfo.path.index = 0;
|
||||
|
@ -189,20 +189,21 @@ static int insert_pin(
|
||||
sc_card_t *card=p15card->card;
|
||||
sc_context_t *ctx=p15card->card->ctx;
|
||||
sc_file_t *f;
|
||||
struct sc_pkcs15_pin_info pin_info;
|
||||
struct sc_pkcs15_auth_info pin_info;
|
||||
struct sc_pkcs15_object pin_obj;
|
||||
int r;
|
||||
|
||||
memset(&pin_info, 0, sizeof(pin_info));
|
||||
pin_info.auth_id.len = 1;
|
||||
pin_info.auth_id.value[0] = id;
|
||||
pin_info.reference = pin_reference;
|
||||
pin_info.flags = pin_flags;
|
||||
pin_info.type = SC_PKCS15_PIN_TYPE_ASCII_NUMERIC;
|
||||
pin_info.min_length = min_length;
|
||||
pin_info.stored_length = 16;
|
||||
pin_info.max_length = 16;
|
||||
pin_info.pad_char = '\0';
|
||||
pin_info.auth_type = SC_PKCS15_PIN_AUTH_TYPE_PIN;
|
||||
pin_info.attrs.pin.reference = pin_reference;
|
||||
pin_info.attrs.pin.flags = pin_flags;
|
||||
pin_info.attrs.pin.type = SC_PKCS15_PIN_TYPE_ASCII_NUMERIC;
|
||||
pin_info.attrs.pin.min_length = min_length;
|
||||
pin_info.attrs.pin.stored_length = 16;
|
||||
pin_info.attrs.pin.max_length = 16;
|
||||
pin_info.attrs.pin.pad_char = '\0';
|
||||
sc_format_path(path, &pin_info.path);
|
||||
|
||||
memset(&pin_obj, 0, sizeof(pin_obj));
|
||||
|
@ -72,7 +72,7 @@ static int sc_pkcs15emu_westcos_init(sc_pkcs15_card_t * p15card)
|
||||
{
|
||||
for (i = 0; i < 1; i++) {
|
||||
unsigned int flags;
|
||||
struct sc_pkcs15_pin_info pin_info;
|
||||
struct sc_pkcs15_auth_info pin_info;
|
||||
struct sc_pkcs15_object pin_obj;
|
||||
memset(&pin_info, 0, sizeof(pin_info));
|
||||
memset(&pin_obj, 0, sizeof(pin_obj));
|
||||
@ -82,15 +82,16 @@ static int sc_pkcs15emu_westcos_init(sc_pkcs15_card_t * p15card)
|
||||
SC_PKCS15_PIN_FLAG_UNBLOCK_DISABLED |
|
||||
SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN;
|
||||
}
|
||||
pin_info.auth_type = SC_PKCS15_PIN_AUTH_TYPE_PIN;
|
||||
pin_info.auth_id.len = 1;
|
||||
pin_info.auth_id.value[0] = i + 1;
|
||||
pin_info.reference = i;
|
||||
pin_info.flags = flags;
|
||||
pin_info.type = SC_PKCS15_PIN_TYPE_BCD;
|
||||
pin_info.min_length = 4;
|
||||
pin_info.stored_length = 8;
|
||||
pin_info.max_length = 8;
|
||||
pin_info.pad_char = 0xff;
|
||||
pin_info.attrs.pin.reference = i;
|
||||
pin_info.attrs.pin.flags = flags;
|
||||
pin_info.attrs.pin.type = SC_PKCS15_PIN_TYPE_BCD;
|
||||
pin_info.attrs.pin.min_length = 4;
|
||||
pin_info.attrs.pin.stored_length = 8;
|
||||
pin_info.attrs.pin.max_length = 8;
|
||||
pin_info.attrs.pin.pad_char = 0xff;
|
||||
pin_info.path = path;
|
||||
pin_info.tries_left = -1;
|
||||
if (i == 1)
|
||||
|
@ -1072,7 +1072,7 @@ static int compare_obj_id(struct sc_pkcs15_object *obj, const sc_pkcs15_id_t *id
|
||||
case SC_PKCS15_TYPE_PUBKEY_EC:
|
||||
return sc_pkcs15_compare_id(&((struct sc_pkcs15_pubkey_info *) data)->id, id);
|
||||
case SC_PKCS15_TYPE_AUTH_PIN:
|
||||
return sc_pkcs15_compare_id(&((struct sc_pkcs15_pin_info *) data)->auth_id, id);
|
||||
return sc_pkcs15_compare_id(&((struct sc_pkcs15_auth_info *) data)->auth_id, id);
|
||||
case SC_PKCS15_TYPE_DATA_OBJECT:
|
||||
return sc_pkcs15_compare_id(&((struct sc_pkcs15_data_info *) data)->id, id);
|
||||
}
|
||||
@ -1113,11 +1113,15 @@ static int compare_obj_usage(sc_pkcs15_object_t *obj, unsigned int mask, unsigne
|
||||
static int compare_obj_flags(sc_pkcs15_object_t *obj, unsigned int mask, unsigned int value)
|
||||
{
|
||||
void *data = obj->data;
|
||||
struct sc_pkcs15_auth_info *auth_info;
|
||||
unsigned int flags;
|
||||
|
||||
switch (obj->type) {
|
||||
case SC_PKCS15_TYPE_AUTH_PIN:
|
||||
flags = ((struct sc_pkcs15_pin_info *) data)->flags;
|
||||
auth_info = (struct sc_pkcs15_auth_info *) obj->data;
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return 0;
|
||||
flags = auth_info->attrs.pin.flags;
|
||||
break;
|
||||
default:
|
||||
return 0;
|
||||
@ -1127,12 +1131,16 @@ static int compare_obj_flags(sc_pkcs15_object_t *obj, unsigned int mask, unsigne
|
||||
|
||||
static int compare_obj_reference(sc_pkcs15_object_t *obj, int value)
|
||||
{
|
||||
struct sc_pkcs15_auth_info *auth_info;
|
||||
void *data = obj->data;
|
||||
int reference;
|
||||
|
||||
switch (obj->type) {
|
||||
case SC_PKCS15_TYPE_AUTH_PIN:
|
||||
reference = ((struct sc_pkcs15_pin_info *) data)->reference;
|
||||
auth_info = (struct sc_pkcs15_auth_info *) obj->data;
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return 0;
|
||||
reference = auth_info->attrs.pin.reference;
|
||||
break;
|
||||
case SC_PKCS15_TYPE_PRKEY_RSA:
|
||||
case SC_PKCS15_TYPE_PRKEY_DSA:
|
||||
@ -1164,7 +1172,7 @@ static int compare_obj_path(sc_pkcs15_object_t *obj, const sc_path_t *path)
|
||||
case SC_PKCS15_TYPE_PUBKEY_EC:
|
||||
return sc_compare_path(&((struct sc_pkcs15_pubkey_info *) data)->path, path);
|
||||
case SC_PKCS15_TYPE_AUTH_PIN:
|
||||
return sc_compare_path(&((struct sc_pkcs15_pin_info *) data)->path, path);
|
||||
return sc_compare_path(&((struct sc_pkcs15_auth_info *) data)->path, path);
|
||||
case SC_PKCS15_TYPE_DATA_OBJECT:
|
||||
return sc_compare_path(&((struct sc_pkcs15_data_info *) data)->path, path);
|
||||
}
|
||||
@ -1317,14 +1325,15 @@ int sc_pkcs15_find_pin_by_type_and_reference(struct sc_pkcs15_card *p15card,
|
||||
nn_objs = r;
|
||||
|
||||
for (ii=0; ii<nn_objs; ii++) {
|
||||
struct sc_pkcs15_pin_info *pin_info = (struct sc_pkcs15_pin_info *)auth_objs[ii]->data;
|
||||
struct sc_pkcs15_auth_info *auth_info = (struct sc_pkcs15_auth_info *)auth_objs[ii]->data;
|
||||
|
||||
if (pin_info->auth_method != auth_method)
|
||||
continue;
|
||||
if (pin_info->reference != reference)
|
||||
if (auth_info->auth_method != auth_method)
|
||||
continue;
|
||||
if (auth_info->auth_type == SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
if (auth_info->attrs.pin.reference != reference)
|
||||
continue;
|
||||
|
||||
if (path && !sc_compare_path(&pin_info->path, path))
|
||||
if (path && !sc_compare_path(&auth_info->path, path))
|
||||
continue;
|
||||
|
||||
if (out)
|
||||
@ -1473,7 +1482,7 @@ void sc_pkcs15_free_object(struct sc_pkcs15_object *obj)
|
||||
sc_pkcs15_free_data_info((sc_pkcs15_data_info_t *)obj->data);
|
||||
break;
|
||||
case SC_PKCS15_TYPE_AUTH:
|
||||
sc_pkcs15_free_pin_info((sc_pkcs15_pin_info_t *)obj->data);
|
||||
sc_pkcs15_free_auth_info((sc_pkcs15_auth_info_t *)obj->data);
|
||||
break;
|
||||
default:
|
||||
free(obj->data);
|
||||
@ -2136,7 +2145,7 @@ sc_pkcs15_get_object_id(const struct sc_pkcs15_object *obj, struct sc_pkcs15_id
|
||||
*out = ((struct sc_pkcs15_pubkey_info *) obj->data)->id;
|
||||
break;
|
||||
case SC_PKCS15_TYPE_AUTH_PIN:
|
||||
*out = ((struct sc_pkcs15_pin_info *) obj->data)->auth_id;
|
||||
*out = ((struct sc_pkcs15_auth_info *) obj->data)->auth_id;
|
||||
break;
|
||||
case SC_PKCS15_TYPE_DATA_OBJECT:
|
||||
*out = ((struct sc_pkcs15_data_info *) obj->data)->id;
|
||||
|
@ -73,20 +73,31 @@ typedef struct sc_pkcs15_id sc_pkcs15_id_t;
|
||||
#define SC_PKCS15_PIN_AUTH_TYPE_AUTH_KEY 1
|
||||
#define SC_PKCS15_PIN_AUTH_TYPE_SM_KEY 2
|
||||
|
||||
struct sc_pkcs15_pin_info {
|
||||
struct sc_pkcs15_id auth_id;
|
||||
int reference;
|
||||
unsigned int flags, type;
|
||||
unsigned int auth_method;
|
||||
size_t min_length, stored_length, max_length;
|
||||
u8 pad_char;
|
||||
struct sc_path path;
|
||||
int tries_left;
|
||||
int max_tries;
|
||||
|
||||
unsigned int magic;
|
||||
};
|
||||
typedef struct sc_pkcs15_pin_info sc_pkcs15_pin_info_t;
|
||||
struct sc_pkcs15_pin_attributes {
|
||||
unsigned int flags, type;
|
||||
size_t min_length, stored_length, max_length;
|
||||
int reference;
|
||||
u8 pad_char;
|
||||
};
|
||||
struct sc_pkcs15_authkey_attributes {
|
||||
int derived;
|
||||
struct sc_pkcs15_id skey_id;
|
||||
};
|
||||
struct sc_pkcs15_biometric_attributes {
|
||||
};
|
||||
struct sc_pkcs15_auth_info {
|
||||
struct sc_pkcs15_id auth_id;
|
||||
struct sc_path path;
|
||||
unsigned auth_type;
|
||||
union {
|
||||
struct sc_pkcs15_pin_attributes pin;
|
||||
struct sc_pkcs15_biometric_attributes bio;
|
||||
struct sc_pkcs15_authkey_attributes authkey;
|
||||
} attrs;
|
||||
unsigned int auth_method;
|
||||
int tries_left, max_tries;
|
||||
};
|
||||
typedef struct sc_pkcs15_auth_info sc_pkcs15_auth_info_t;
|
||||
|
||||
#define SC_PKCS15_ALGO_OP_COMPUTE_CHECKSUM 0x01
|
||||
#define SC_PKCS15_ALGO_OP_COMPUTE_SIGNATURE 0x02
|
||||
@ -752,7 +763,7 @@ void sc_pkcs15_free_prkey_info(sc_pkcs15_prkey_info_t *key);
|
||||
void sc_pkcs15_free_pubkey_info(sc_pkcs15_pubkey_info_t *key);
|
||||
void sc_pkcs15_free_cert_info(sc_pkcs15_cert_info_t *cert);
|
||||
void sc_pkcs15_free_data_info(sc_pkcs15_data_info_t *data);
|
||||
void sc_pkcs15_free_pin_info(sc_pkcs15_pin_info_t *pin);
|
||||
void sc_pkcs15_free_auth_info(sc_pkcs15_auth_info_t *auth_info);
|
||||
void sc_pkcs15_free_object(sc_pkcs15_object_t *obj);
|
||||
|
||||
/* Generic file i/o */
|
||||
@ -834,7 +845,7 @@ int sc_pkcs15emu_object_add(sc_pkcs15_card_t *, unsigned int,
|
||||
const sc_pkcs15_object_t *, const void *);
|
||||
/* some wrapper functions for sc_pkcs15emu_object_add */
|
||||
int sc_pkcs15emu_add_pin_obj(sc_pkcs15_card_t *,
|
||||
const sc_pkcs15_object_t *, const sc_pkcs15_pin_info_t *);
|
||||
const sc_pkcs15_object_t *, const sc_pkcs15_auth_info_t *);
|
||||
int sc_pkcs15emu_add_rsa_prkey(sc_pkcs15_card_t *,
|
||||
const sc_pkcs15_object_t *, const sc_pkcs15_prkey_info_t *);
|
||||
int sc_pkcs15emu_add_rsa_pubkey(sc_pkcs15_card_t *,
|
||||
|
@ -36,8 +36,8 @@ struct pkcs15_slot_data {
|
||||
};
|
||||
#define slot_data(p) ((struct pkcs15_slot_data *) (p))
|
||||
#define slot_data_auth(p) (((p) && slot_data(p)) ? slot_data(p)->auth_obj : NULL)
|
||||
#define slot_data_pin_info(p) (((p) && slot_data_auth(p))? \
|
||||
(struct sc_pkcs15_pin_info *) slot_data_auth(p)->data : NULL)
|
||||
#define slot_data_auth_info(p) (((p) && slot_data_auth(p))? \
|
||||
(struct sc_pkcs15_auth_info *) slot_data_auth(p)->data : NULL)
|
||||
|
||||
#define check_attribute_buffer(attr,size) \
|
||||
if (attr->pValue == NULL_PTR) { \
|
||||
@ -317,7 +317,7 @@ CK_RV C_GetTokenInfo(CK_SLOT_ID slotID, CK_TOKEN_INFO_PTR pInfo)
|
||||
{
|
||||
struct sc_pkcs11_slot *slot;
|
||||
struct sc_pkcs15_object *auth;
|
||||
struct sc_pkcs15_pin_info *pin_info;
|
||||
struct sc_pkcs15_auth_info *pin_info;
|
||||
struct sc_pin_cmd_data data;
|
||||
int r;
|
||||
CK_RV rv;
|
||||
@ -339,13 +339,18 @@ CK_RV C_GetTokenInfo(CK_SLOT_ID slotID, CK_TOKEN_INFO_PTR pInfo)
|
||||
slot->token_info.flags &= ~(CKF_USER_PIN_COUNT_LOW|CKF_USER_PIN_FINAL_TRY|CKF_USER_PIN_LOCKED);
|
||||
auth = slot_data_auth(slot->fw_data);
|
||||
if (auth) {
|
||||
pin_info = (struct sc_pkcs15_pin_info*) auth->data;
|
||||
pin_info = (struct sc_pkcs15_auth_info*) auth->data;
|
||||
|
||||
if (pin_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN) {
|
||||
rv = CKR_FUNCTION_REJECTED;
|
||||
goto out;
|
||||
}
|
||||
|
||||
/* Try to update PIN info from card */
|
||||
memset(&data, 0, sizeof(data));
|
||||
data.cmd = SC_PIN_CMD_GET_INFO;
|
||||
data.pin_type = SC_AC_CHV;
|
||||
data.pin_reference = pin_info->reference;
|
||||
data.pin_reference = pin_info->attrs.pin.reference;
|
||||
|
||||
r = sc_pin_cmd(slot->card->card, &data, NULL);
|
||||
if (r == SC_SUCCESS) {
|
||||
@ -791,7 +796,7 @@ static void pkcs15_init_slot(struct sc_pkcs15_card *p15card,
|
||||
struct sc_pkcs15_object *auth)
|
||||
{
|
||||
struct pkcs15_slot_data *fw_data;
|
||||
struct sc_pkcs15_pin_info *pin_info = NULL;
|
||||
struct sc_pkcs15_auth_info *pin_info = NULL;
|
||||
char tmp[64];
|
||||
|
||||
pkcs15_init_token_info(p15card, &slot->token_info);
|
||||
@ -809,22 +814,25 @@ static void pkcs15_init_slot(struct sc_pkcs15_card *p15card,
|
||||
fw_data->auth_obj = auth;
|
||||
|
||||
if (auth != NULL) {
|
||||
pin_info = (struct sc_pkcs15_pin_info*) auth->data;
|
||||
pin_info = (struct sc_pkcs15_auth_info*) auth->data;
|
||||
|
||||
if (auth->label[0]) {
|
||||
snprintf(tmp, sizeof(tmp), "%s (%s)",
|
||||
p15card->tokeninfo->label, auth->label);
|
||||
} else {
|
||||
snprintf(tmp, sizeof(tmp), "%s", p15card->tokeninfo->label);
|
||||
if (pin_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN) {
|
||||
pin_info = NULL;
|
||||
}
|
||||
else {
|
||||
if (auth->label[0])
|
||||
snprintf(tmp, sizeof(tmp), "%s (%s)", p15card->tokeninfo->label, auth->label);
|
||||
else
|
||||
snprintf(tmp, sizeof(tmp), "%s", p15card->tokeninfo->label);
|
||||
slot->token_info.flags |= CKF_LOGIN_REQUIRED;
|
||||
}
|
||||
slot->token_info.flags |= CKF_LOGIN_REQUIRED;
|
||||
} else
|
||||
snprintf(tmp, sizeof(tmp), "%s", p15card->tokeninfo->label);
|
||||
strcpy_bp(slot->token_info.label, tmp, 32);
|
||||
|
||||
if (pin_info && pin_info->magic == SC_PKCS15_PIN_MAGIC) {
|
||||
slot->token_info.ulMaxPinLen = pin_info->max_length;
|
||||
slot->token_info.ulMinPinLen = pin_info->min_length;
|
||||
if (pin_info) {
|
||||
slot->token_info.ulMaxPinLen = pin_info->attrs.pin.max_length;
|
||||
slot->token_info.ulMinPinLen = pin_info->attrs.pin.min_length;
|
||||
} else {
|
||||
/* choose reasonable defaults */
|
||||
slot->token_info.ulMaxPinLen = 8;
|
||||
@ -941,21 +949,25 @@ static CK_RV pkcs15_create_tokens(struct sc_pkcs11_card *p11card)
|
||||
auth_count = 1;
|
||||
|
||||
for (i = 0; i < auth_count; i++) {
|
||||
struct sc_pkcs15_pin_info *pin_info = NULL;
|
||||
struct sc_pkcs15_auth_info *pin_info = NULL;
|
||||
|
||||
pin_info = (struct sc_pkcs15_pin_info*) auths[i]->data;
|
||||
pin_info = (struct sc_pkcs15_auth_info*) auths[i]->data;
|
||||
|
||||
/* Ignore all but PIN authentication objects */
|
||||
if (pin_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
continue;
|
||||
|
||||
/* Ignore any non-authentication PINs */
|
||||
if ((pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN) != 0)
|
||||
if ((pin_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN) != 0)
|
||||
continue;
|
||||
|
||||
/* Ignore unblocking pins for hacked module */
|
||||
if (hack_enabled && (pin_info->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN) != 0)
|
||||
if (hack_enabled && (pin_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN) != 0)
|
||||
continue;
|
||||
|
||||
/* Ignore unblocking pins */
|
||||
if (!sc_pkcs11_conf.create_puk_slot)
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN)
|
||||
if (pin_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN)
|
||||
continue;
|
||||
|
||||
found_auth_count++;
|
||||
@ -1052,7 +1064,7 @@ static CK_RV pkcs15_login(struct sc_pkcs11_slot *slot,
|
||||
struct pkcs15_fw_data *fw_data = (struct pkcs15_fw_data *) p11card->fw_data;
|
||||
struct sc_pkcs15_card *p15card = fw_data->p15_card;
|
||||
struct sc_pkcs15_object *auth_object;
|
||||
struct sc_pkcs15_pin_info *pin_info;
|
||||
struct sc_pkcs15_auth_info *pin_info;
|
||||
|
||||
switch (userType) {
|
||||
case CKU_USER:
|
||||
@ -1125,7 +1137,9 @@ static CK_RV pkcs15_login(struct sc_pkcs11_slot *slot,
|
||||
default:
|
||||
return CKR_USER_TYPE_INVALID;
|
||||
}
|
||||
pin_info = (struct sc_pkcs15_pin_info *) auth_object->data;
|
||||
pin_info = (struct sc_pkcs15_auth_info *) auth_object->data;
|
||||
if (pin_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return CKR_FUNCTION_REJECTED;
|
||||
|
||||
if (p11card->card->reader->capabilities & SC_READER_CAP_PIN_PAD) {
|
||||
/* pPin should be NULL in case of a pin pad reader, but
|
||||
@ -1146,8 +1160,8 @@ static CK_RV pkcs15_login(struct sc_pkcs11_slot *slot,
|
||||
* If PIN is out of range,
|
||||
* it cannot be correct.
|
||||
*/
|
||||
if (ulPinLen < pin_info->min_length ||
|
||||
ulPinLen > pin_info->max_length)
|
||||
if (ulPinLen < pin_info->attrs.pin.min_length ||
|
||||
ulPinLen > pin_info->attrs.pin.max_length)
|
||||
return CKR_PIN_INCORRECT;
|
||||
}
|
||||
|
||||
@ -1259,17 +1273,17 @@ static CK_RV pkcs15_change_pin(struct sc_pkcs11_card *p11card,
|
||||
{
|
||||
int rc;
|
||||
struct pkcs15_fw_data *fw_data = (struct pkcs15_fw_data *) p11card->fw_data;
|
||||
struct sc_pkcs15_pin_info *pin_info;
|
||||
struct sc_pkcs15_auth_info *auth_info;
|
||||
struct sc_pkcs15_object *pin_obj;
|
||||
|
||||
if (!(pin_obj = slot_data_auth(fw_token)))
|
||||
return CKR_USER_PIN_NOT_INITIALIZED;
|
||||
|
||||
if (!(pin_info = slot_data_pin_info(fw_token)))
|
||||
if (!(auth_info = slot_data_auth_info(fw_token)))
|
||||
return CKR_USER_PIN_NOT_INITIALIZED;
|
||||
|
||||
sc_debug(context, SC_LOG_DEBUG_NORMAL, "Change '%s', reference %i; login type %i",
|
||||
pin_obj->label, pin_info->reference, login_user);
|
||||
pin_obj->label, auth_info->attrs.pin.reference, login_user);
|
||||
if (p11card->card->reader->capabilities & SC_READER_CAP_PIN_PAD) {
|
||||
/* pPin should be NULL in case of a pin pad reader, but
|
||||
* some apps (e.g. older Netscapes) don't know about it.
|
||||
@ -1280,7 +1294,7 @@ static CK_RV pkcs15_change_pin(struct sc_pkcs11_card *p11card,
|
||||
pOldPin = pNewPin = NULL;
|
||||
ulOldLen = ulNewLen = 0;
|
||||
}
|
||||
else if (ulNewLen < pin_info->min_length || ulNewLen > pin_info->max_length) {
|
||||
else if (ulNewLen < auth_info->attrs.pin.min_length || ulNewLen > auth_info->attrs.pin.max_length) {
|
||||
return CKR_PIN_LEN_RANGE;
|
||||
}
|
||||
|
||||
@ -1310,8 +1324,8 @@ static CK_RV pkcs15_change_pin(struct sc_pkcs11_card *p11card,
|
||||
return sc_to_cryptoki_error(rc, "C_SetPIN");
|
||||
auth_count = rc;
|
||||
for (i = 0; i < auth_count; i++) {
|
||||
pin_info = (struct sc_pkcs15_pin_info*) auths[i]->data;
|
||||
if ((pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN))
|
||||
auth_info = (struct sc_pkcs15_auth_info*) auths[i]->data;
|
||||
if ((auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN))
|
||||
break;
|
||||
}
|
||||
if (i == auth_count) {
|
||||
@ -1339,14 +1353,14 @@ static CK_RV pkcs15_init_pin(struct sc_pkcs11_card *p11card,
|
||||
struct sc_pkcs15init_pinargs args;
|
||||
struct sc_profile *profile;
|
||||
struct sc_pkcs15_object *auth_obj;
|
||||
struct sc_pkcs15_pin_info *pin_info;
|
||||
struct sc_pkcs15_auth_info *auth_info;
|
||||
int rc;
|
||||
|
||||
sc_debug(context, SC_LOG_DEBUG_NORMAL, "pkcs15 init PIN: pin %p:%d; unblock style %i",
|
||||
pPin, ulPinLen, sc_pkcs11_conf.pin_unblock_style);
|
||||
|
||||
pin_info = slot_data_pin_info(slot->fw_data);
|
||||
if (pin_info && sc_pkcs11_conf.pin_unblock_style == SC_PKCS11_PIN_UNBLOCK_SO_LOGGED_INITPIN) {
|
||||
auth_info = slot_data_auth_info(slot->fw_data);
|
||||
if (auth_info && sc_pkcs11_conf.pin_unblock_style == SC_PKCS11_PIN_UNBLOCK_SO_LOGGED_INITPIN) {
|
||||
/* C_InitPIN is used to unblock User PIN or set it in the SO session .*/
|
||||
auth_obj = slot_data_auth(slot->fw_data);
|
||||
if (fw_data->user_puk_len) {
|
||||
@ -1357,7 +1371,7 @@ static CK_RV pkcs15_init_pin(struct sc_pkcs11_card *p11card,
|
||||
/* FIXME (VT): Actually sc_pkcs15_unblock_pin() do not accepts zero length PUK.
|
||||
* Something like sc_pkcs15_set_pin() should be introduced.
|
||||
* For a while, use the 'libopensc' API to set PIN. */
|
||||
rc = sc_reset_retry_counter(fw_data->p15_card->card, SC_AC_CHV, pin_info->reference,
|
||||
rc = sc_reset_retry_counter(fw_data->p15_card->card, SC_AC_CHV, auth_info->attrs.pin.reference,
|
||||
NULL, 0, pPin, ulPinLen);
|
||||
}
|
||||
|
||||
@ -1393,7 +1407,7 @@ static CK_RV pkcs15_init_pin(struct sc_pkcs11_card *p11card,
|
||||
free(slot->fw_data);
|
||||
pkcs15_init_slot(fw_data->p15_card, slot, auth_obj);
|
||||
|
||||
pin_info = (sc_pkcs15_pin_info_t *) auth_obj->data;
|
||||
auth_info = (sc_pkcs15_auth_info_t *) auth_obj->data;
|
||||
return CKR_OK;
|
||||
}
|
||||
|
||||
@ -1407,7 +1421,7 @@ static CK_RV pkcs15_create_private_key(struct sc_pkcs11_card *p11card,
|
||||
struct sc_pkcs15init_prkeyargs args;
|
||||
struct pkcs15_any_object *key_any_obj;
|
||||
struct sc_pkcs15_object *key_obj;
|
||||
struct sc_pkcs15_pin_info *pin;
|
||||
struct sc_pkcs15_auth_info *pin;
|
||||
CK_KEY_TYPE key_type;
|
||||
struct sc_pkcs15_prkey_rsa *rsa;
|
||||
struct sc_pkcs15_prkey_ec *ec;
|
||||
@ -1419,7 +1433,7 @@ static CK_RV pkcs15_create_private_key(struct sc_pkcs11_card *p11card,
|
||||
|
||||
/* See if the "slot" is pin protected. If so, get the
|
||||
* PIN id */
|
||||
if ((pin = slot_data_pin_info(slot->fw_data)) != NULL)
|
||||
if ((pin = slot_data_auth_info(slot->fw_data)) != NULL)
|
||||
args.auth_id = pin->auth_id;
|
||||
|
||||
/* Get the key type */
|
||||
@ -1539,7 +1553,7 @@ static CK_RV pkcs15_create_public_key(struct sc_pkcs11_card *p11card,
|
||||
struct sc_pkcs15init_pubkeyargs args;
|
||||
struct pkcs15_any_object *key_any_obj;
|
||||
struct sc_pkcs15_object *key_obj;
|
||||
struct sc_pkcs15_pin_info *pin;
|
||||
struct sc_pkcs15_auth_info *pin;
|
||||
CK_KEY_TYPE key_type;
|
||||
struct sc_pkcs15_pubkey_rsa *rsa;
|
||||
int rc, rv;
|
||||
@ -1549,7 +1563,7 @@ static CK_RV pkcs15_create_public_key(struct sc_pkcs11_card *p11card,
|
||||
|
||||
/* See if the "slot" is pin protected. If so, get the
|
||||
* PIN id */
|
||||
if ((pin = slot_data_pin_info(slot->fw_data)) != NULL)
|
||||
if ((pin = slot_data_auth_info(slot->fw_data)) != NULL)
|
||||
args.auth_id = pin->auth_id;
|
||||
|
||||
/* Get the key type */
|
||||
@ -1714,7 +1728,7 @@ static CK_RV pkcs15_create_data(struct sc_pkcs11_card *p11card,
|
||||
struct sc_pkcs15init_dataargs args;
|
||||
struct pkcs15_any_object *data_any_obj;
|
||||
struct sc_pkcs15_object *data_obj;
|
||||
struct sc_pkcs15_pin_info *pin;
|
||||
struct sc_pkcs15_auth_info *pin;
|
||||
CK_BBOOL bValue;
|
||||
int rc, rv;
|
||||
char label[SC_PKCS15_MAX_LABEL_SIZE];
|
||||
@ -1733,7 +1747,7 @@ static CK_RV pkcs15_create_data(struct sc_pkcs11_card *p11card,
|
||||
case CKA_PRIVATE:
|
||||
rv = attr_extract(attr, &bValue, NULL);
|
||||
if (bValue) {
|
||||
pin = slot_data_pin_info(slot->fw_data);
|
||||
pin = slot_data_auth_info(slot->fw_data);
|
||||
if (pin == NULL) {
|
||||
rv = CKR_TEMPLATE_INCOMPLETE;
|
||||
goto out;
|
||||
@ -1935,7 +1949,7 @@ static CK_RV pkcs15_gen_keypair(struct sc_pkcs11_card *p11card,
|
||||
CK_OBJECT_HANDLE_PTR phPubKey, CK_OBJECT_HANDLE_PTR phPrivKey) /* gets priv. key handle */
|
||||
{
|
||||
struct sc_profile *profile = NULL;
|
||||
struct sc_pkcs15_pin_info *pin;
|
||||
struct sc_pkcs15_auth_info *pin;
|
||||
struct pkcs15_fw_data *fw_data = (struct pkcs15_fw_data *) p11card->fw_data;
|
||||
struct sc_pkcs15init_keygen_args keygen_args;
|
||||
struct sc_pkcs15init_pubkeyargs pub_args;
|
||||
@ -1973,7 +1987,7 @@ static CK_RV pkcs15_gen_keypair(struct sc_pkcs11_card *p11card,
|
||||
|
||||
/* 1. Convert the pkcs11 attributes to pkcs15init args */
|
||||
|
||||
if ((pin = slot_data_pin_info(slot->fw_data)) != NULL)
|
||||
if ((pin = slot_data_auth_info(slot->fw_data)) != NULL)
|
||||
keygen_args.prkey_args.auth_id = pub_args.auth_id = pin->auth_id;
|
||||
|
||||
rv = attr_find2(pPubTpl, ulPubCnt, pPrivTpl, ulPrivCnt, CKA_KEY_TYPE,
|
||||
|
@ -168,17 +168,17 @@ static int asepcos_create_dir(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
* determine the next best file id of the PIN file.
|
||||
*/
|
||||
static int asepcos_select_pin_reference(sc_profile_t *profile,
|
||||
sc_pkcs15_card_t *p15card, sc_pkcs15_pin_info_t *pinfo)
|
||||
sc_pkcs15_card_t *p15card, sc_pkcs15_auth_info_t *auth_info)
|
||||
{
|
||||
if (pinfo->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
if (auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
return SC_SUCCESS;
|
||||
if (pinfo->reference <= 0)
|
||||
pinfo->reference = 1;
|
||||
if (auth_info->attrs.pin.reference <= 0)
|
||||
auth_info->attrs.pin.reference = 1;
|
||||
/* as we want to use <fileid of PIN> + 1 for the PUK we need to
|
||||
* ensure that all references are odd => if the reference is
|
||||
* even add one */
|
||||
if ((pinfo->reference & 1) == 0)
|
||||
pinfo->reference++;
|
||||
if ((auth_info->attrs.pin.reference & 1) == 0)
|
||||
auth_info->attrs.pin.reference++;
|
||||
return SC_SUCCESS;
|
||||
}
|
||||
|
||||
@ -216,13 +216,16 @@ static int asepcos_pinid_to_akn(sc_card_t *card, int fileid, int *akn)
|
||||
}
|
||||
|
||||
static int asepcos_do_store_pin(sc_profile_t *profile, sc_card_t *card,
|
||||
sc_pkcs15_pin_info_t *pinfo, const u8* pin, size_t pinlen,
|
||||
sc_pkcs15_auth_info_t *auth_info, const u8* pin, size_t pinlen,
|
||||
int puk, int pinid)
|
||||
{
|
||||
sc_file_t *nfile = NULL;
|
||||
u8 buf[64], sbuf[64], *p = buf, *q = sbuf;
|
||||
int r, akn;
|
||||
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
/* outter tag */
|
||||
*p++ = 0x85;
|
||||
p++;
|
||||
@ -237,7 +240,7 @@ static int asepcos_do_store_pin(sc_profile_t *profile, sc_card_t *card,
|
||||
*p++ = 0x00;
|
||||
*p++ = pinlen & 0xff;
|
||||
/* max tries */
|
||||
*p++ = pinfo->tries_left & 0xff;
|
||||
*p++ = auth_info->tries_left & 0xff;
|
||||
/* algorithm id and key key usage and padding bytes */
|
||||
*p++ = 0x00;
|
||||
*p++ = 0x00;
|
||||
@ -305,11 +308,11 @@ static int asepcos_do_store_pin(sc_profile_t *profile, sc_card_t *card,
|
||||
if (r != SC_SUCCESS)
|
||||
return r;
|
||||
/* use the AKN as reference */
|
||||
pinfo->reference = akn;
|
||||
auth_info->attrs.pin.reference = akn;
|
||||
/* set the correct PIN length */
|
||||
pinfo->min_length = 4;
|
||||
pinfo->stored_length = pinlen;
|
||||
pinfo->max_length = 16;
|
||||
auth_info->attrs.pin.min_length = 4;
|
||||
auth_info->attrs.pin.stored_length = pinlen;
|
||||
auth_info->attrs.pin.max_length = 16;
|
||||
|
||||
return r;
|
||||
}
|
||||
@ -319,9 +322,11 @@ static int asepcos_do_store_pin(sc_profile_t *profile, sc_card_t *card,
|
||||
*/
|
||||
static int have_onepin(sc_profile_t *profile)
|
||||
{
|
||||
sc_pkcs15_pin_info_t sopin;
|
||||
sc_pkcs15_auth_info_t sopin;
|
||||
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_SO_PIN, &sopin);
|
||||
if (!(sopin.flags & SC_PKCS15_PIN_FLAG_SO_PIN))
|
||||
|
||||
if (!(sopin.attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN))
|
||||
return 1;
|
||||
else
|
||||
return 0;
|
||||
@ -342,7 +347,7 @@ static int asepcos_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
sc_file_t *df, sc_pkcs15_object_t *pin_obj,
|
||||
const u8 *pin, size_t pin_len, const u8 *puk, size_t puk_len)
|
||||
{
|
||||
sc_pkcs15_pin_info_t *pinfo = (sc_pkcs15_pin_info_t *) pin_obj->data;
|
||||
sc_pkcs15_auth_info_t *auth_info = (sc_pkcs15_auth_info_t *) pin_obj->data;
|
||||
struct sc_card *card = p15card->card;
|
||||
int r, pid, puk_id;
|
||||
sc_path_t tpath = df->path;
|
||||
@ -353,7 +358,10 @@ static int asepcos_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
if (!pin || !pin_len)
|
||||
return SC_ERROR_INVALID_ARGUMENTS;
|
||||
|
||||
pid = (pinfo->reference & 0xff) | (((tpath.len >> 1) - 1) << 16);
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
pid = (auth_info->attrs.pin.reference & 0xff) | (((tpath.len >> 1) - 1) << 16);
|
||||
|
||||
/* get the ACL of the application DF */
|
||||
r = sc_select_file(card, &df->path, &tfile);
|
||||
@ -389,29 +397,29 @@ static int asepcos_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
/* Create PUK (if specified). Note: we need to create the PUK
|
||||
* the PIN as the PUK fileid is used in the PIN acl.
|
||||
*/
|
||||
struct sc_pkcs15_pin_info puk_info;
|
||||
struct sc_pkcs15_auth_info puk_ainfo;
|
||||
|
||||
if (pinfo->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_SO_PUK, &puk_info);
|
||||
if (auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_SO_PUK, &puk_ainfo);
|
||||
else
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_USER_PUK, &puk_info);
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_USER_PUK, &puk_ainfo);
|
||||
|
||||
/* If a PUK we use "file id of the PIN" + 1 as the file id
|
||||
* of the PUK.
|
||||
*/
|
||||
puk_id = pid + 1;
|
||||
r = asepcos_do_store_pin(profile, card, &puk_info, puk, puk_len, 0, puk_id);
|
||||
r = asepcos_do_store_pin(profile, card, &puk_ainfo, puk, puk_len, 0, puk_id);
|
||||
if (r != SC_SUCCESS)
|
||||
SC_FUNC_RETURN(ctx, SC_LOG_DEBUG_VERBOSE, r);
|
||||
} else
|
||||
puk_id = 0;
|
||||
|
||||
r = asepcos_do_store_pin(profile, card, pinfo, pin, pin_len, puk_id, pid);
|
||||
r = asepcos_do_store_pin(profile, card, auth_info, pin, pin_len, puk_id, pid);
|
||||
if (r != SC_SUCCESS)
|
||||
SC_FUNC_RETURN(ctx, SC_LOG_DEBUG_VERBOSE, r);
|
||||
|
||||
#if 1
|
||||
if (pinfo->flags & SC_PKCS15_PIN_FLAG_SO_PIN ||
|
||||
if (auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN ||
|
||||
(have_onepin(profile) && pid == 0x010001)) {
|
||||
sc_cardctl_asepcos_activate_file_t st;
|
||||
/* Once the SO PIN or ,in case of the "onepin" profile", the
|
||||
@ -454,7 +462,7 @@ static int asepcos_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
r = sc_append_file_id(&tpath, pid & 0xff);
|
||||
if (r != SC_SUCCESS)
|
||||
return r;
|
||||
pinfo->path = tpath;
|
||||
auth_info->path = tpath;
|
||||
#endif
|
||||
SC_FUNC_RETURN(ctx, SC_LOG_DEBUG_VERBOSE, r);
|
||||
}
|
||||
|
@ -50,7 +50,7 @@ struct tlv {
|
||||
* Local functions
|
||||
*/
|
||||
static int cardos_store_pin(sc_profile_t *profile, sc_card_t *card,
|
||||
sc_pkcs15_pin_info_t *pin_info, int puk_id,
|
||||
sc_pkcs15_auth_info_t *auth_info, int puk_id,
|
||||
const u8 *pin, size_t pin_len);
|
||||
static int cardos_create_sec_env(sc_profile_t *, sc_card_t *,
|
||||
unsigned int, unsigned int);
|
||||
@ -152,14 +152,17 @@ cardos_create_dir(sc_profile_t *profile, sc_pkcs15_card_t *p15card, sc_file_t *d
|
||||
*/
|
||||
static int
|
||||
cardos_select_pin_reference(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
sc_pkcs15_pin_info_t *pin_info)
|
||||
sc_pkcs15_auth_info_t *auth_info)
|
||||
{
|
||||
int preferred, current;
|
||||
|
||||
if ((current = pin_info->reference) < 0)
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
if ((current = auth_info->attrs.pin.reference) < 0)
|
||||
current = CARDOS_PIN_ID_MIN;
|
||||
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
if (auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
preferred = 1;
|
||||
} else {
|
||||
preferred = current;
|
||||
@ -172,7 +175,7 @@ cardos_select_pin_reference(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
|
||||
if (current > preferred || preferred > CARDOS_PIN_ID_MAX)
|
||||
return SC_ERROR_TOO_MANY_OBJECTS;
|
||||
pin_info->reference = preferred;
|
||||
auth_info->attrs.pin.reference = preferred;
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -185,7 +188,7 @@ cardos_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card, sc_file_t *d
|
||||
const u8 *pin, size_t pin_len,
|
||||
const u8 *puk, size_t puk_len)
|
||||
{
|
||||
sc_pkcs15_pin_info_t *pin_info = (sc_pkcs15_pin_info_t *) pin_obj->data;
|
||||
sc_pkcs15_auth_info_t *auth_info = (sc_pkcs15_auth_info_t *) pin_obj->data;
|
||||
struct sc_card *card = p15card->card;
|
||||
unsigned int puk_id = CARDOS_AC_NEVER;
|
||||
int r;
|
||||
@ -193,24 +196,27 @@ cardos_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card, sc_file_t *d
|
||||
if (!pin || !pin_len)
|
||||
return SC_ERROR_INVALID_ARGUMENTS;
|
||||
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
r = sc_select_file(card, &df->path, NULL);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
if (puk && puk_len) {
|
||||
struct sc_pkcs15_pin_info puk_info;
|
||||
struct sc_pkcs15_auth_info puk_ainfo;
|
||||
|
||||
sc_profile_get_pin_info(profile,
|
||||
SC_PKCS15INIT_USER_PUK, &puk_info);
|
||||
puk_info.reference = puk_id = pin_info->reference + 1;
|
||||
SC_PKCS15INIT_USER_PUK, &puk_ainfo);
|
||||
puk_ainfo.attrs.pin.reference = puk_id = auth_info->attrs.pin.reference + 1;
|
||||
r = cardos_store_pin(profile, card,
|
||||
&puk_info, CARDOS_AC_NEVER,
|
||||
&puk_ainfo, CARDOS_AC_NEVER,
|
||||
puk, puk_len);
|
||||
}
|
||||
|
||||
if (r >= 0) {
|
||||
r = cardos_store_pin(profile, card,
|
||||
pin_info, puk_id, pin, pin_len);
|
||||
auth_info, puk_id, pin, pin_len);
|
||||
}
|
||||
|
||||
return r;
|
||||
@ -399,7 +405,7 @@ out:
|
||||
*/
|
||||
static int
|
||||
cardos_store_pin(sc_profile_t *profile, sc_card_t *card,
|
||||
sc_pkcs15_pin_info_t *pin_info, int puk_id,
|
||||
sc_pkcs15_auth_info_t *auth_info, int puk_id,
|
||||
const u8 *pin, size_t pin_len)
|
||||
{
|
||||
struct sc_cardctl_cardos_obj_info args;
|
||||
@ -409,6 +415,9 @@ cardos_store_pin(sc_profile_t *profile, sc_card_t *card,
|
||||
unsigned int attempts, minlen, maxlen;
|
||||
int r;
|
||||
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
/* We need to do padding because pkcs15-lib.c does it.
|
||||
* Would be nice to have a flag in the profile that says
|
||||
* "no padding required". */
|
||||
@ -423,15 +432,15 @@ cardos_store_pin(sc_profile_t *profile, sc_card_t *card,
|
||||
pinpadded[pin_len++] = profile->pin_pad_char;
|
||||
pin = pinpadded;
|
||||
|
||||
attempts = pin_info->tries_left;
|
||||
minlen = pin_info->min_length;
|
||||
attempts = auth_info->tries_left;
|
||||
minlen = auth_info->attrs.pin.min_length;
|
||||
|
||||
tlv_init(&tlv, buffer, sizeof(buffer));
|
||||
|
||||
/* object address: class, id */
|
||||
tlv_next(&tlv, 0x83);
|
||||
tlv_add(&tlv, 0x00); /* class byte: usage TEST, k=0 */
|
||||
tlv_add(&tlv, pin_info->reference);
|
||||
tlv_add(&tlv, auth_info->attrs.pin.reference);
|
||||
|
||||
/* parameters */
|
||||
tlv_next(&tlv, 0x85);
|
||||
@ -461,7 +470,7 @@ cardos_store_pin(sc_profile_t *profile, sc_card_t *card,
|
||||
/* AC conditions */
|
||||
tlv_next(&tlv, 0x86);
|
||||
tlv_add(&tlv, 0x00); /* use: always */
|
||||
tlv_add(&tlv, pin_info->reference); /* change: PIN */
|
||||
tlv_add(&tlv, auth_info->attrs.pin.reference); /* change: PIN */
|
||||
tlv_add(&tlv, puk_id); /* unblock: PUK */
|
||||
|
||||
/* data: PIN */
|
||||
|
@ -185,21 +185,24 @@ cflex_create_domain(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
*/
|
||||
static int
|
||||
cflex_select_pin_reference(sc_profile_t *profike, sc_pkcs15_card_t *p15card,
|
||||
sc_pkcs15_pin_info_t *pin_info)
|
||||
sc_pkcs15_auth_info_t *auth_info)
|
||||
{
|
||||
int preferred;
|
||||
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
if (auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
preferred = 2;
|
||||
} else {
|
||||
preferred = 1;
|
||||
}
|
||||
if (pin_info->reference <= preferred) {
|
||||
pin_info->reference = preferred;
|
||||
if (auth_info->attrs.pin.reference <= preferred) {
|
||||
auth_info->attrs.pin.reference = preferred;
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (pin_info->reference > 2)
|
||||
if (auth_info->attrs.pin.reference > 2)
|
||||
return SC_ERROR_INVALID_ARGUMENTS;
|
||||
|
||||
/* Caller, please select a different PIN reference */
|
||||
@ -217,34 +220,39 @@ cflex_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card, sc_file_t *df
|
||||
const u8 *puk, size_t puk_len)
|
||||
{
|
||||
struct sc_context *ctx = p15card->card->ctx;
|
||||
sc_pkcs15_pin_info_t *pin_info = (sc_pkcs15_pin_info_t *) pin_obj->data;
|
||||
sc_pkcs15_auth_info_t *auth_info = (sc_pkcs15_auth_info_t *) pin_obj->data;
|
||||
struct sc_pkcs15_pin_attributes *pin_attrs = &auth_info->attrs.pin;
|
||||
sc_file_t *dummies[2];
|
||||
int ndummies, pin_type, puk_type, r;
|
||||
sc_file_t *file;
|
||||
|
||||
SC_FUNC_CALLED(ctx, SC_LOG_DEBUG_NORMAL);
|
||||
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
/* If the profile doesn't specify a reference for this PIN, guess */
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
if (pin_attrs->flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
pin_type = SC_PKCS15INIT_SO_PIN;
|
||||
puk_type = SC_PKCS15INIT_SO_PUK;
|
||||
if (pin_info->reference != 2)
|
||||
if (pin_attrs->reference != 2)
|
||||
return SC_ERROR_INVALID_ARGUMENTS;
|
||||
} else {
|
||||
pin_type = SC_PKCS15INIT_USER_PIN;
|
||||
puk_type = SC_PKCS15INIT_USER_PUK;
|
||||
if (pin_info->reference != 1)
|
||||
if (pin_attrs->reference != 1)
|
||||
return SC_ERROR_INVALID_ARGUMENTS;
|
||||
}
|
||||
|
||||
/* Get file definition from the profile */
|
||||
if (sc_profile_get_file(profile, (pin_info->reference == 1)? "CHV1" : "CHV2", &file) < 0
|
||||
if (sc_profile_get_file(profile, (pin_attrs->reference == 1)? "CHV1" : "CHV2", &file) < 0
|
||||
&& sc_profile_get_file(profile, "CHV", &file) < 0)
|
||||
SC_TEST_RET(ctx, SC_LOG_DEBUG_NORMAL, SC_ERROR_FILE_NOT_FOUND, "profile does not define pin file ACLs");
|
||||
|
||||
ndummies = cflex_create_dummy_chvs(profile, p15card, file, SC_AC_OP_CREATE, dummies);
|
||||
SC_TEST_RET(ctx, SC_LOG_DEBUG_NORMAL, ndummies, "Unable to create dummy CHV file");
|
||||
|
||||
r = cflex_create_pin_file(profile, p15card, &df->path, pin_info->reference,
|
||||
r = cflex_create_pin_file(profile, p15card, &df->path, pin_attrs->reference,
|
||||
pin, pin_len, sc_profile_get_pin_retries(profile, pin_type),
|
||||
puk, puk_len, sc_profile_get_pin_retries(profile, puk_type),
|
||||
NULL, 0);
|
||||
|
@ -246,14 +246,18 @@ static int entersafe_create_dir(sc_profile_t *profile, sc_pkcs15_card_t *p15card
|
||||
}
|
||||
|
||||
static int entersafe_pin_reference(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
sc_pkcs15_pin_info_t *pin_info)
|
||||
sc_pkcs15_auth_info_t *auth_info)
|
||||
{
|
||||
SC_FUNC_CALLED(p15card->card->ctx, SC_LOG_DEBUG_VERBOSE);
|
||||
|
||||
if (pin_info->reference < ENTERSAFE_USER_PIN_ID)
|
||||
pin_info->reference = ENTERSAFE_USER_PIN_ID;
|
||||
if(pin_info->reference>ENTERSAFE_USER_PIN_ID)
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
if (auth_info->attrs.pin.reference < ENTERSAFE_USER_PIN_ID)
|
||||
auth_info->attrs.pin.reference = ENTERSAFE_USER_PIN_ID;
|
||||
if (auth_info->attrs.pin.reference > ENTERSAFE_USER_PIN_ID)
|
||||
return SC_ERROR_TOO_MANY_OBJECTS;
|
||||
|
||||
SC_FUNC_RETURN(p15card->card->ctx, SC_LOG_DEBUG_VERBOSE,SC_SUCCESS);
|
||||
}
|
||||
|
||||
@ -264,17 +268,20 @@ static int entersafe_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card
|
||||
{
|
||||
struct sc_card *card = p15card->card;
|
||||
int r;
|
||||
sc_pkcs15_pin_info_t *pin_info = (sc_pkcs15_pin_info_t *) pin_obj->data;
|
||||
sc_pkcs15_auth_info_t *auth_info = (sc_pkcs15_auth_info_t *) pin_obj->data;
|
||||
|
||||
SC_FUNC_CALLED(card->ctx, SC_LOG_DEBUG_VERBOSE);
|
||||
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
{/*pin*/
|
||||
sc_entersafe_wkey_data data;
|
||||
|
||||
if (!pin || !pin_len || pin_len > 16)
|
||||
return SC_ERROR_INVALID_ARGUMENTS;
|
||||
|
||||
data.key_id=pin_info->reference;
|
||||
data.key_id = auth_info->attrs.pin.reference;
|
||||
data.usage=0x0B;
|
||||
data.key_data.symmetric.EC=0x33;
|
||||
data.key_data.symmetric.ver=0x00;
|
||||
@ -296,7 +303,7 @@ static int entersafe_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card
|
||||
if (!puk || !puk_len || puk_len > 16)
|
||||
return SC_ERROR_INVALID_ARGUMENTS;
|
||||
|
||||
data.key_id=pin_info->reference+1;
|
||||
data.key_id = auth_info->attrs.pin.reference+1;
|
||||
data.usage=0x0B;
|
||||
data.key_data.symmetric.EC=0x33;
|
||||
data.key_data.symmetric.ver=0x00;
|
||||
@ -427,7 +434,7 @@ static int entersafe_generate_key(sc_profile_t *profile, sc_pkcs15_card_t *p15ca
|
||||
static int entersafe_sanity_check(sc_profile_t *profile, sc_pkcs15_card_t *p15card)
|
||||
{
|
||||
struct sc_context *ctx = p15card->card->ctx;
|
||||
struct sc_pkcs15_pin_info profile_pin;
|
||||
struct sc_pkcs15_auth_info profile_auth;
|
||||
struct sc_pkcs15_object *objs[32];
|
||||
int rv, nn, ii, update_df = 0;
|
||||
|
||||
@ -438,17 +445,22 @@ static int entersafe_sanity_check(sc_profile_t *profile, sc_pkcs15_card_t *p15ca
|
||||
SC_TEST_RET(ctx, SC_LOG_DEBUG_NORMAL, rv, "Failed to get PINs");
|
||||
nn = rv;
|
||||
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_USER_PIN, &profile_pin);
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_USER_PIN, &profile_auth);
|
||||
SC_TEST_RET(ctx, SC_LOG_DEBUG_NORMAL, rv, "Failed to get PIN info");
|
||||
|
||||
for (ii=0; ii<nn; ii++) {
|
||||
struct sc_pkcs15_pin_info *pinfo = (struct sc_pkcs15_pin_info *) objs[ii]->data;
|
||||
struct sc_pkcs15_auth_info *ainfo = (struct sc_pkcs15_auth_info *) objs[ii]->data;
|
||||
struct sc_pkcs15_pin_attributes *pin_attrs = &ainfo->attrs.pin;
|
||||
|
||||
if (pinfo->reference == profile_pin.reference && pinfo->flags != profile_pin.flags) {
|
||||
if (ainfo->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
continue;
|
||||
|
||||
if (pin_attrs->reference == profile_auth.attrs.pin.reference
|
||||
&& pin_attrs->flags != profile_auth.attrs.pin.flags) {
|
||||
sc_debug(ctx, SC_LOG_DEBUG_NORMAL, "Set flags of '%s'(flags:%X,ref:%i,id:%s) to %X", objs[ii]->label,
|
||||
pinfo->flags, pinfo->reference, sc_pkcs15_print_id(&pinfo->auth_id),
|
||||
profile_pin.flags);
|
||||
pinfo->flags = profile_pin.flags;
|
||||
pin_attrs->flags, pin_attrs->reference, sc_pkcs15_print_id(&ainfo->auth_id),
|
||||
profile_auth.attrs.pin.flags);
|
||||
pin_attrs->flags = profile_auth.attrs.pin.flags;
|
||||
update_df = 1;
|
||||
}
|
||||
}
|
||||
|
@ -162,15 +162,19 @@ gpk_create_dir(sc_profile_t *profile, sc_pkcs15_card_t *p15card, sc_file_t *df)
|
||||
*/
|
||||
static int
|
||||
gpk_select_pin_reference(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
sc_pkcs15_pin_info_t *pin_info)
|
||||
sc_pkcs15_auth_info_t *auth_info)
|
||||
{
|
||||
int preferred, current;
|
||||
|
||||
SC_FUNC_CALLED(p15card->card->ctx, SC_LOG_DEBUG_VERBOSE);
|
||||
if ((current = pin_info->reference) < 0)
|
||||
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
if ((current = auth_info->attrs.pin.reference) < 0)
|
||||
current = 0;
|
||||
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
if (auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
preferred = GPK_PIN_SCOPE | 0;
|
||||
} else {
|
||||
preferred = current | GPK_PIN_SCOPE;
|
||||
@ -185,7 +189,7 @@ gpk_select_pin_reference(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
|
||||
if (current > preferred)
|
||||
return SC_ERROR_TOO_MANY_OBJECTS;
|
||||
pin_info->reference = preferred;
|
||||
auth_info->attrs.pin.reference = preferred;
|
||||
SC_FUNC_RETURN(p15card->card->ctx, SC_LOG_DEBUG_NORMAL, 0);
|
||||
}
|
||||
|
||||
@ -198,14 +202,19 @@ gpk_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card, sc_file_t *df,
|
||||
const u8 *pin, size_t pin_len,
|
||||
const u8 *puk, size_t puk_len)
|
||||
{
|
||||
sc_pkcs15_pin_info_t *pin_info = (sc_pkcs15_pin_info_t *) pin_obj->data;
|
||||
sc_pkcs15_auth_info_t *auth_info = (sc_pkcs15_auth_info_t *) pin_obj->data;
|
||||
struct sc_pkcs15_pin_attributes *pin_attrs = &auth_info->attrs.pin;
|
||||
u8 nulpin[8];
|
||||
int r;
|
||||
|
||||
SC_FUNC_CALLED(p15card->card->ctx, SC_LOG_DEBUG_VERBOSE);
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
if (pin_attrs->flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
/* SO PIN reference must be 0 */
|
||||
if (pin_info->reference != (GPK_PIN_SCOPE | 0))
|
||||
if (pin_attrs->reference != (GPK_PIN_SCOPE | 0))
|
||||
return SC_ERROR_INVALID_ARGUMENTS;
|
||||
} else {
|
||||
/* PIN references must be even numbers
|
||||
@ -214,9 +223,9 @@ gpk_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card, sc_file_t *df,
|
||||
* Returning SC_ERROR_INVALID_PIN_REFERENCE will
|
||||
* tell the caller to pick a different value.
|
||||
*/
|
||||
if ((pin_info->reference & 1) || !(pin_info->reference & GPK_PIN_SCOPE))
|
||||
if ((pin_attrs->reference & 1) || !(pin_attrs->reference & GPK_PIN_SCOPE))
|
||||
return SC_ERROR_INVALID_PIN_REFERENCE;
|
||||
if (pin_info->reference >= (GPK_PIN_SCOPE + GPK_MAX_PINS))
|
||||
if (pin_attrs->reference >= (GPK_PIN_SCOPE + GPK_MAX_PINS))
|
||||
return SC_ERROR_TOO_MANY_OBJECTS;
|
||||
}
|
||||
|
||||
@ -238,7 +247,7 @@ gpk_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card, sc_file_t *df,
|
||||
/* Current PIN is 00:00:00:00:00:00:00:00 */
|
||||
memset(nulpin, 0, sizeof(nulpin));
|
||||
r = sc_change_reference_data(p15card->card, SC_AC_CHV,
|
||||
pin_info->reference,
|
||||
pin_attrs->reference,
|
||||
nulpin, sizeof(nulpin),
|
||||
pin, pin_len, NULL);
|
||||
sc_debug(p15card->card->ctx, SC_LOG_DEBUG_NORMAL, "change CHV %i", r);
|
||||
@ -247,7 +256,7 @@ gpk_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card, sc_file_t *df,
|
||||
|
||||
/* Current PUK is 00:00:00:00:00:00:00:00 */
|
||||
r = sc_change_reference_data(p15card->card, SC_AC_CHV,
|
||||
pin_info->reference + 1,
|
||||
pin_attrs->reference + 1,
|
||||
nulpin, sizeof(nulpin),
|
||||
puk, puk_len, NULL);
|
||||
sc_debug(p15card->card->ctx, SC_LOG_DEBUG_NORMAL, "change CHV+1 %i", r);
|
||||
|
@ -648,12 +648,14 @@ iasecc_pkcs15_get_auth_id_from_se(struct sc_pkcs15_card *p15card, unsigned char
|
||||
LOG_TEST_RET(ctx, rv, "Card CTL error: cannot get CHV reference from SE");
|
||||
pin_ref = rv;
|
||||
for (ii=0; ii<nn_pins; ii++) {
|
||||
const struct sc_pkcs15_pin_info *pin_info = (const struct sc_pkcs15_pin_info *) pin_objs[ii]->data;
|
||||
const struct sc_pkcs15_auth_info *auth_info = (const struct sc_pkcs15_auth_info *) pin_objs[ii]->data;
|
||||
|
||||
/* FIXME: make pin reference 'unsigned' */
|
||||
sc_log(ctx, "PIN refs %i/%i", pin_ref, pin_info->reference);
|
||||
if (pin_ref == ((pin_info->reference + 0x100) % 0x100)) {
|
||||
*auth_id = pin_info->auth_id;
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
continue;
|
||||
|
||||
sc_log(ctx, "PIN refs %i/%i", pin_ref, auth_info->attrs.pin.reference);
|
||||
if (pin_ref == ((auth_info->attrs.pin.reference + 0x100) % 0x100)) {
|
||||
*auth_id = auth_info->auth_id;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
@ -56,7 +56,7 @@ struct rsakey {
|
||||
* Local functions
|
||||
*/
|
||||
static int incrypto34_store_pin(sc_profile_t *profile, sc_card_t *card,
|
||||
sc_pkcs15_pin_info_t *pin_info, int puk_id,
|
||||
sc_pkcs15_auth_info_t *auth_info, int puk_id,
|
||||
const u8 *pin, size_t pin_len);
|
||||
static int incrypto34_create_sec_env(sc_profile_t *, sc_card_t *,
|
||||
unsigned int, unsigned int);
|
||||
@ -172,14 +172,17 @@ incrypto34_create_dir(sc_profile_t *profile, sc_pkcs15_card_t *p15card, sc_file_
|
||||
*/
|
||||
static int
|
||||
incrypto34_select_pin_reference(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
sc_pkcs15_pin_info_t *pin_info)
|
||||
sc_pkcs15_auth_info_t *auth_info)
|
||||
{
|
||||
int preferred, current;
|
||||
|
||||
if ((current = pin_info->reference) < 0)
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
if ((current = auth_info->attrs.pin.reference) < 0)
|
||||
current = INCRYPTO34_PIN_ID_MIN;
|
||||
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
if (auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
preferred = 1;
|
||||
} else {
|
||||
preferred = current;
|
||||
@ -192,7 +195,7 @@ incrypto34_select_pin_reference(sc_profile_t *profile, sc_pkcs15_card_t *p15card
|
||||
|
||||
if (current > preferred || preferred > INCRYPTO34_PIN_ID_MAX)
|
||||
return SC_ERROR_TOO_MANY_OBJECTS;
|
||||
pin_info->reference = preferred;
|
||||
auth_info->attrs.pin.reference = preferred;
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -205,31 +208,34 @@ incrypto34_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
const u8 *pin, size_t pin_len,
|
||||
const u8 *puk, size_t puk_len)
|
||||
{
|
||||
sc_pkcs15_pin_info_t *pin_info = (sc_pkcs15_pin_info_t *) pin_obj->data;
|
||||
sc_pkcs15_auth_info_t *auth_info = (sc_pkcs15_auth_info_t *) pin_obj->data;
|
||||
unsigned int puk_id = INCRYPTO34_AC_NEVER;
|
||||
int r;
|
||||
|
||||
if (!pin || !pin_len)
|
||||
return SC_ERROR_INVALID_ARGUMENTS;
|
||||
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
r = sc_select_file(p15card->card, &df->path, NULL);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
if (puk && puk_len) {
|
||||
struct sc_pkcs15_pin_info puk_info;
|
||||
struct sc_pkcs15_auth_info puk_ainfo;
|
||||
|
||||
sc_profile_get_pin_info(profile,
|
||||
SC_PKCS15INIT_USER_PUK, &puk_info);
|
||||
puk_info.reference = puk_id = pin_info->reference + 1;
|
||||
SC_PKCS15INIT_USER_PUK, &puk_ainfo);
|
||||
puk_ainfo.attrs.pin.reference = puk_id = auth_info->attrs.pin.reference + 1;
|
||||
r = incrypto34_store_pin(profile, p15card->card,
|
||||
&puk_info, INCRYPTO34_AC_NEVER,
|
||||
&puk_ainfo, INCRYPTO34_AC_NEVER,
|
||||
puk, puk_len);
|
||||
}
|
||||
|
||||
if (r >= 0) {
|
||||
r = incrypto34_store_pin(profile, p15card->card,
|
||||
pin_info, puk_id,
|
||||
auth_info, puk_id,
|
||||
pin, pin_len);
|
||||
}
|
||||
|
||||
@ -383,7 +389,7 @@ out: if (delete_it) {
|
||||
*/
|
||||
static int
|
||||
incrypto34_store_pin(sc_profile_t *profile, sc_card_t *card,
|
||||
sc_pkcs15_pin_info_t *pin_info, int puk_id,
|
||||
sc_pkcs15_auth_info_t *auth_info, int puk_id,
|
||||
const u8 *pin, size_t pin_len)
|
||||
{
|
||||
struct sc_cardctl_incrypto34_obj_info args;
|
||||
@ -392,6 +398,9 @@ incrypto34_store_pin(sc_profile_t *profile, sc_card_t *card,
|
||||
struct tlv tlv;
|
||||
unsigned int attempts, minlen, maxlen;
|
||||
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
/* We need to do padding because pkcs15-lib.c does it.
|
||||
* Would be nice to have a flag in the profile that says
|
||||
* "no padding required". */
|
||||
@ -403,15 +412,15 @@ incrypto34_store_pin(sc_profile_t *profile, sc_card_t *card,
|
||||
pinpadded[pin_len++] = profile->pin_pad_char;
|
||||
pin = pinpadded;
|
||||
|
||||
attempts = pin_info->tries_left;
|
||||
minlen = pin_info->min_length;
|
||||
attempts = auth_info->tries_left;
|
||||
minlen = auth_info->attrs.pin.min_length;
|
||||
|
||||
tlv_init(&tlv, buffer, sizeof(buffer));
|
||||
|
||||
/* object address: class, id */
|
||||
tlv_next(&tlv, 0x83);
|
||||
tlv_add(&tlv, 0x00); /* class byte: usage TEST, k=0 */
|
||||
tlv_add(&tlv, pin_info->reference);
|
||||
tlv_add(&tlv, auth_info->attrs.pin.reference);
|
||||
|
||||
/* parameters */
|
||||
tlv_next(&tlv, 0x85);
|
||||
@ -439,7 +448,7 @@ incrypto34_store_pin(sc_profile_t *profile, sc_card_t *card,
|
||||
/* AC conditions */
|
||||
tlv_next(&tlv, 0x86);
|
||||
tlv_add(&tlv, 0x00); /* use: always */
|
||||
tlv_add(&tlv, pin_info->reference); /* change: PIN */
|
||||
tlv_add(&tlv, auth_info->attrs.pin.reference); /* change: PIN */
|
||||
tlv_add(&tlv, puk_id); /* unblock: PUK */
|
||||
tlv_add(&tlv, 0xFF); /*RFU*/
|
||||
tlv_add(&tlv, 0xFF); /*RFU*/
|
||||
|
@ -57,7 +57,7 @@ struct sc_pkcs15init_operations {
|
||||
* Select a PIN reference
|
||||
*/
|
||||
int (*select_pin_reference)(struct sc_profile *, struct sc_pkcs15_card *,
|
||||
struct sc_pkcs15_pin_info *);
|
||||
struct sc_pkcs15_auth_info *);
|
||||
|
||||
/*
|
||||
* Create a PIN object within the given DF.
|
||||
@ -160,7 +160,7 @@ struct sc_pkcs15init_callbacks {
|
||||
* Get a PIN from the front-end. The first argument is
|
||||
* one of the SC_PKCS15INIT_XXX_PIN/PUK macros.
|
||||
*/
|
||||
int (*get_pin)(struct sc_profile *, int, const struct sc_pkcs15_pin_info *,
|
||||
int (*get_pin)(struct sc_profile *, int, const struct sc_pkcs15_auth_info *,
|
||||
const char *, unsigned char *, size_t *);
|
||||
|
||||
/*
|
||||
@ -340,7 +340,7 @@ extern int sc_pkcs15init_authenticate(struct sc_profile *, struct sc_pkcs15_card
|
||||
struct sc_file *, int);
|
||||
extern int sc_pkcs15init_fixup_file(struct sc_profile *, struct sc_pkcs15_card *,
|
||||
struct sc_file *);
|
||||
extern int sc_pkcs15init_get_pin_info(struct sc_profile *, int, struct sc_pkcs15_pin_info *);
|
||||
extern int sc_pkcs15init_get_pin_info(struct sc_profile *, int, struct sc_pkcs15_auth_info *);
|
||||
extern int sc_profile_get_pin_retries(struct sc_profile *, int);
|
||||
extern int sc_pkcs15init_get_manufacturer(struct sc_profile *,
|
||||
const char **);
|
||||
|
@ -73,13 +73,16 @@ jcop_create_dir(sc_profile_t *profile, sc_pkcs15_card_t *p15card, sc_file_t *fil
|
||||
*/
|
||||
static int
|
||||
jcop_select_pin_reference(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
sc_pkcs15_pin_info_t *pin_info) {
|
||||
sc_pkcs15_auth_info_t *auth_info) {
|
||||
int preferred, current;
|
||||
|
||||
if ((current = pin_info->reference) < 0)
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
if ((current = auth_info->attrs.pin.reference) < 0)
|
||||
current = 0;
|
||||
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
if (auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
preferred = 3;
|
||||
} else {
|
||||
preferred = current;
|
||||
@ -90,7 +93,7 @@ jcop_select_pin_reference(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
}
|
||||
if (current > preferred)
|
||||
return SC_ERROR_TOO_MANY_OBJECTS;
|
||||
pin_info->reference = preferred;
|
||||
auth_info->attrs.pin.reference = preferred;
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -103,17 +106,21 @@ jcop_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card, sc_file_t *df,
|
||||
const unsigned char *pin, size_t pin_len,
|
||||
const unsigned char *puk, size_t puk_len)
|
||||
{
|
||||
sc_pkcs15_pin_info_t *pin_info = (sc_pkcs15_pin_info_t *) pin_obj->data;
|
||||
sc_pkcs15_auth_info_t *auth_info = (sc_pkcs15_auth_info_t *) pin_obj->data;
|
||||
struct sc_pkcs15_pin_attributes *pin_attrs = &auth_info->attrs.pin;
|
||||
unsigned char nulpin[16];
|
||||
unsigned char padpin[16];
|
||||
int r;
|
||||
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
if (pin_attrs->flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
/* SO PIN reference must be 0 */
|
||||
if (pin_info->reference != 3)
|
||||
if (pin_attrs->reference != 3)
|
||||
return SC_ERROR_INVALID_ARGUMENTS;
|
||||
} else {
|
||||
if (pin_info->reference >= 3)
|
||||
if (pin_attrs->reference >= 3)
|
||||
return SC_ERROR_TOO_MANY_OBJECTS;
|
||||
}
|
||||
if (puk != NULL && puk_len > 0) {
|
||||
@ -128,13 +135,13 @@ jcop_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card, sc_file_t *df,
|
||||
memset(padpin, 0, sizeof(padpin));
|
||||
memcpy(padpin, pin, pin_len);
|
||||
r = sc_change_reference_data(p15card->card, SC_AC_CHV,
|
||||
pin_info->reference,
|
||||
pin_attrs->reference,
|
||||
nulpin, sizeof(nulpin),
|
||||
padpin, sizeof(padpin), NULL);
|
||||
if (r < 0)
|
||||
return r;
|
||||
|
||||
pin_info->flags &= ~SC_PKCS15_PIN_FLAG_LOCAL;
|
||||
pin_attrs->flags &= ~SC_PKCS15_PIN_FLAG_LOCAL;
|
||||
return r;
|
||||
}
|
||||
|
||||
|
@ -119,7 +119,7 @@ static int select_object_path(struct sc_pkcs15_card *, struct sc_profile *,
|
||||
static int sc_pkcs15init_get_pin_path(struct sc_pkcs15_card *,
|
||||
struct sc_pkcs15_id *, struct sc_path *);
|
||||
static int sc_pkcs15init_qualify_pin(struct sc_card *, const char *,
|
||||
unsigned int, struct sc_pkcs15_pin_info *);
|
||||
unsigned int, struct sc_pkcs15_auth_info *);
|
||||
static struct sc_pkcs15_df * find_df_by_type(struct sc_pkcs15_card *,
|
||||
unsigned int);
|
||||
static int sc_pkcs15init_read_info(struct sc_card *card, struct sc_profile *);
|
||||
@ -410,19 +410,20 @@ sc_pkcs15init_set_p15card(struct sc_profile *profile,
|
||||
* for every present local User PIN, add to the profile EF list the named PIN path. */
|
||||
nn_objs = sc_pkcs15_get_objects(p15card, SC_PKCS15_TYPE_AUTH_PIN, p15objects, 10);
|
||||
for (i = 0; i < nn_objs; i++) {
|
||||
struct sc_pkcs15_pin_info *pininfo = (struct sc_pkcs15_pin_info *) p15objects[i]->data;
|
||||
struct sc_pkcs15_auth_info *auth_info = (struct sc_pkcs15_auth_info *) p15objects[i]->data;
|
||||
struct sc_pkcs15_pin_attributes *pin_attrs = &auth_info->attrs.pin;
|
||||
struct sc_file *file = NULL;
|
||||
|
||||
if (pininfo->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
if (pin_attrs->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
continue;
|
||||
if (pininfo->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN)
|
||||
if (pin_attrs->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN)
|
||||
continue;
|
||||
if (!pininfo->path.len)
|
||||
if (!auth_info->path.len)
|
||||
continue;
|
||||
|
||||
r = sc_profile_get_file_by_path(profile, &pininfo->path, &file);
|
||||
r = sc_profile_get_file_by_path(profile, &auth_info->path, &file);
|
||||
if (r == SC_ERROR_FILE_NOT_FOUND) {
|
||||
if (!sc_select_file(p15card->card, &pininfo->path, &file)) {
|
||||
if (!sc_select_file(p15card->card, &auth_info->path, &file)) {
|
||||
char pin_name[16];
|
||||
|
||||
sprintf(pin_name, "pin-dir-%02X%02X",
|
||||
@ -695,7 +696,8 @@ sc_pkcs15init_add_app(struct sc_card *card, struct sc_profile *profile,
|
||||
{
|
||||
struct sc_context *ctx = card->ctx;
|
||||
struct sc_pkcs15_card *p15card = profile->p15_spec;
|
||||
struct sc_pkcs15_pin_info pin_info, puk_info;
|
||||
struct sc_pkcs15_auth_info pin_ainfo, puk_ainfo;
|
||||
struct sc_pkcs15_pin_attributes *pin_attrs = &pin_ainfo.attrs.pin;
|
||||
struct sc_pkcs15_object *pin_obj = NULL;
|
||||
struct sc_app_info *app;
|
||||
struct sc_file *df = profile->df_info->file;
|
||||
@ -717,36 +719,35 @@ sc_pkcs15init_add_app(struct sc_card *card, struct sc_profile *profile,
|
||||
if (args->so_pin_len) {
|
||||
const char *pin_label;
|
||||
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_SO_PIN, &pin_info);
|
||||
r = sc_pkcs15init_qualify_pin(card, "SO PIN", args->so_pin_len, &pin_info);
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_SO_PIN, &pin_ainfo);
|
||||
r = sc_pkcs15init_qualify_pin(card, "SO PIN", args->so_pin_len, &pin_ainfo);
|
||||
LOG_TEST_RET(ctx, r, "Failed to qualify SO PIN");
|
||||
|
||||
/* Path encoded only for local SO PIN */
|
||||
if (pin_info.flags & SC_PKCS15_PIN_FLAG_LOCAL)
|
||||
pin_info.path = df->path;
|
||||
if (pin_attrs->flags & SC_PKCS15_PIN_FLAG_LOCAL)
|
||||
pin_ainfo.path = df->path;
|
||||
|
||||
/* Select the PIN reference */
|
||||
if (profile->ops->select_pin_reference) {
|
||||
r = profile->ops->select_pin_reference(profile, p15card, &pin_info);
|
||||
r = profile->ops->select_pin_reference(profile, p15card, &pin_ainfo);
|
||||
LOG_TEST_RET(ctx, r, "Failed to select card specific PIN reference");
|
||||
}
|
||||
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_SO_PUK, &puk_info);
|
||||
r = sc_pkcs15init_qualify_pin(card, "SO PUK", args->so_puk_len, &puk_info);
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_SO_PUK, &puk_ainfo);
|
||||
r = sc_pkcs15init_qualify_pin(card, "SO PUK", args->so_puk_len, &puk_ainfo);
|
||||
LOG_TEST_RET(ctx, r, "Failed to qulify SO PUK");
|
||||
|
||||
if (!(pin_label = args->so_pin_label)) {
|
||||
if (pin_info.flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
if (pin_attrs->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
pin_label = "Security Officer PIN";
|
||||
else
|
||||
pin_label = "User PIN";
|
||||
}
|
||||
|
||||
if (args->so_puk_len == 0)
|
||||
pin_info.flags |= SC_PKCS15_PIN_FLAG_UNBLOCK_DISABLED;
|
||||
pin_attrs->flags |= SC_PKCS15_PIN_FLAG_UNBLOCK_DISABLED;
|
||||
|
||||
pin_obj = sc_pkcs15init_new_object(SC_PKCS15_TYPE_AUTH_PIN,
|
||||
pin_label, NULL, &pin_info);
|
||||
pin_obj = sc_pkcs15init_new_object(SC_PKCS15_TYPE_AUTH_PIN, pin_label, NULL, &pin_ainfo);
|
||||
|
||||
if (pin_obj) {
|
||||
/* When composing ACLs to create 'DIR' DF,
|
||||
@ -754,9 +755,8 @@ sc_pkcs15init_add_app(struct sc_card *card, struct sc_profile *profile,
|
||||
* For this, create a 'virtual' AUTH object 'SO PIN', accessible by the card specific part,
|
||||
* but not yet written into the on-card PKCS#15.
|
||||
*/
|
||||
sc_log(ctx, "Add virtual SO_PIN('%s',flags:%X,reference:%i,path:'%s')",
|
||||
pin_obj->label, pin_info.flags, pin_info.reference,
|
||||
sc_print_path(&pin_info.path));
|
||||
sc_log(ctx, "Add virtual SO_PIN('%s',flags:%X,reference:%i,path:'%s')", pin_obj->label,
|
||||
pin_attrs->flags, pin_attrs->reference, sc_print_path(&pin_ainfo.path));
|
||||
r = sc_pkcs15_add_object(p15card, pin_obj);
|
||||
LOG_TEST_RET(ctx, r, "Failed to add 'SOPIN' AUTH object");
|
||||
}
|
||||
@ -860,7 +860,7 @@ sc_pkcs15init_store_puk(struct sc_pkcs15_card *p15card,
|
||||
{
|
||||
struct sc_context *ctx = p15card->card->ctx;
|
||||
struct sc_pkcs15_object *pin_obj;
|
||||
struct sc_pkcs15_pin_info *pin_info;
|
||||
struct sc_pkcs15_auth_info *auth_info;
|
||||
int r;
|
||||
char puk_label[0x30];
|
||||
|
||||
@ -891,10 +891,10 @@ sc_pkcs15init_store_puk(struct sc_pkcs15_card *p15card,
|
||||
if (pin_obj == NULL)
|
||||
LOG_TEST_RET(ctx, SC_ERROR_OUT_OF_MEMORY, "Cannot allocate PIN object");
|
||||
|
||||
pin_info = (struct sc_pkcs15_pin_info *) pin_obj->data;
|
||||
auth_info = (struct sc_pkcs15_auth_info *) pin_obj->data;
|
||||
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_USER_PUK, pin_info);
|
||||
pin_info->auth_id = args->puk_id;
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_USER_PUK, auth_info);
|
||||
auth_info->auth_id = args->puk_id;
|
||||
|
||||
/* Now store the PINs */
|
||||
if (profile->ops->create_pin)
|
||||
@ -914,13 +914,12 @@ sc_pkcs15init_store_puk(struct sc_pkcs15_card *p15card,
|
||||
|
||||
|
||||
int
|
||||
sc_pkcs15init_store_pin(struct sc_pkcs15_card *p15card,
|
||||
struct sc_profile *profile,
|
||||
sc_pkcs15init_store_pin(struct sc_pkcs15_card *p15card, struct sc_profile *profile,
|
||||
struct sc_pkcs15init_pinargs *args)
|
||||
{
|
||||
struct sc_context *ctx = p15card->card->ctx;
|
||||
struct sc_pkcs15_object *pin_obj;
|
||||
struct sc_pkcs15_pin_info *pin_info;
|
||||
struct sc_pkcs15_auth_info *auth_info;
|
||||
int r;
|
||||
|
||||
LOG_FUNC_CALLED(ctx);
|
||||
@ -949,13 +948,13 @@ sc_pkcs15init_store_pin(struct sc_pkcs15_card *p15card,
|
||||
if (pin_obj == NULL)
|
||||
LOG_TEST_RET(ctx, SC_ERROR_OUT_OF_MEMORY, "Cannot allocate PIN object");
|
||||
|
||||
pin_info = (struct sc_pkcs15_pin_info *) pin_obj->data;
|
||||
auth_info = (struct sc_pkcs15_auth_info *) pin_obj->data;
|
||||
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_USER_PIN, pin_info);
|
||||
pin_info->auth_id = args->auth_id;
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_USER_PIN, auth_info);
|
||||
auth_info->auth_id = args->auth_id;
|
||||
|
||||
/* Now store the PINs */
|
||||
sc_log(ctx, "Store PIN(%s,authID:%s)", pin_obj->label, sc_pkcs15_print_id(&pin_info->auth_id));
|
||||
sc_log(ctx, "Store PIN(%s,authID:%s)", pin_obj->label, sc_pkcs15_print_id(&auth_info->auth_id));
|
||||
r = sc_pkcs15init_create_pin(p15card, profile, pin_obj, args);
|
||||
if (r < 0)
|
||||
sc_pkcs15_free_object(pin_obj);
|
||||
@ -982,7 +981,8 @@ sc_pkcs15init_create_pin(struct sc_pkcs15_card *p15card,
|
||||
struct sc_pkcs15init_pinargs *args)
|
||||
{
|
||||
struct sc_context *ctx = p15card->card->ctx;
|
||||
struct sc_pkcs15_pin_info *pin_info = (struct sc_pkcs15_pin_info *) pin_obj->data;
|
||||
struct sc_pkcs15_auth_info *auth_info = (struct sc_pkcs15_auth_info *) pin_obj->data;
|
||||
struct sc_pkcs15_pin_attributes *pin_attrs = &auth_info->attrs.pin;
|
||||
struct sc_file *df = profile->df_info->file;
|
||||
int r, retry = 0;
|
||||
|
||||
@ -995,27 +995,26 @@ sc_pkcs15init_create_pin(struct sc_pkcs15_card *p15card,
|
||||
if (!profile->ops->create_domain)
|
||||
LOG_TEST_RET(ctx, SC_ERROR_NOT_SUPPORTED, "PIN domains not supported.");
|
||||
|
||||
r = profile->ops->create_domain(profile, p15card, &pin_info->auth_id, &df);
|
||||
r = profile->ops->create_domain(profile, p15card, &auth_info->auth_id, &df);
|
||||
LOG_TEST_RET(ctx, r, "Card specific create domain failed");
|
||||
}
|
||||
|
||||
/* Path encoded only for local PINs */
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_LOCAL)
|
||||
pin_info->path = df->path;
|
||||
if (pin_attrs->flags & SC_PKCS15_PIN_FLAG_LOCAL)
|
||||
auth_info->path = df->path;
|
||||
|
||||
/* pin_info->reference = 0; */
|
||||
|
||||
/* Loop until we come up with an acceptable pin reference */
|
||||
while (1) {
|
||||
if (profile->ops->select_pin_reference) {
|
||||
r = profile->ops->select_pin_reference(profile, p15card, pin_info);
|
||||
r = profile->ops->select_pin_reference(profile, p15card, auth_info);
|
||||
LOG_TEST_RET(ctx, r, "Card specific select PIN reference failed");
|
||||
|
||||
retry = 1;
|
||||
}
|
||||
|
||||
r = sc_pkcs15_find_pin_by_reference(p15card, &pin_info->path,
|
||||
pin_info->reference, NULL);
|
||||
r = sc_pkcs15_find_pin_by_reference(p15card, &auth_info->path, pin_attrs->reference, NULL);
|
||||
if (r == SC_ERROR_OBJECT_NOT_FOUND)
|
||||
break;
|
||||
|
||||
@ -1023,14 +1022,14 @@ sc_pkcs15init_create_pin(struct sc_pkcs15_card *p15card,
|
||||
/* Other error trying to retrieve pin obj */
|
||||
LOG_TEST_RET(ctx, SC_ERROR_TOO_MANY_OBJECTS, "Failed to allocate PIN reference.");
|
||||
|
||||
pin_info->reference++;
|
||||
pin_attrs->reference++;
|
||||
}
|
||||
|
||||
if (args->puk_len == 0)
|
||||
pin_info->flags |= SC_PKCS15_PIN_FLAG_UNBLOCK_DISABLED;
|
||||
pin_attrs->flags |= SC_PKCS15_PIN_FLAG_UNBLOCK_DISABLED;
|
||||
|
||||
sc_log(ctx, "create PIN with reference:%X, flags:%X, path:%s",
|
||||
pin_info->reference, pin_info->flags, sc_print_path(&pin_info->path));
|
||||
pin_attrs->reference, pin_attrs->flags, sc_print_path(&auth_info->path));
|
||||
r = profile->ops->create_pin(profile, p15card,
|
||||
df, pin_obj,
|
||||
args->pin, args->pin_len,
|
||||
@ -1634,7 +1633,7 @@ sc_pkcs15init_get_pin_reference(struct sc_pkcs15_card *p15card,
|
||||
struct sc_profile *profile, unsigned auth_method, int reference)
|
||||
{
|
||||
struct sc_context *ctx = p15card->card->ctx;
|
||||
struct sc_pkcs15_pin_info pinfo;
|
||||
struct sc_pkcs15_auth_info auth_info;
|
||||
struct sc_pkcs15_object *auth_objs[0x10];
|
||||
int r, ii, nn_objs;
|
||||
|
||||
@ -1650,14 +1649,15 @@ sc_pkcs15init_get_pin_reference(struct sc_pkcs15_card *p15card,
|
||||
sc_log(ctx, "found %i auth objects; looking for AUTH object(auth_method:%i,reference:%i)",
|
||||
nn_objs, auth_method, reference);
|
||||
for (ii=0; ii<nn_objs; ii++) {
|
||||
struct sc_pkcs15_pin_info *pin_info = (struct sc_pkcs15_pin_info *)auth_objs[ii]->data;
|
||||
struct sc_pkcs15_auth_info *auth_info = (struct sc_pkcs15_auth_info *)auth_objs[ii]->data;
|
||||
struct sc_pkcs15_pin_attributes *pin_attrs = &auth_info->attrs.pin;
|
||||
|
||||
sc_log(ctx, "check PIN(%s,auth_method:%i,type:%i,reference:%i,flags:%X)",
|
||||
auth_objs[ii]->label, pin_info->auth_method, pin_info->type,
|
||||
pin_info->reference, pin_info->flags);
|
||||
auth_objs[ii]->label, auth_info->auth_method, pin_attrs->type,
|
||||
pin_attrs->reference, pin_attrs->flags);
|
||||
/* Find out if there is AUTH pkcs15 object with given 'type' and 'reference' */
|
||||
if (pin_info->auth_method == auth_method && pin_info->reference == reference)
|
||||
LOG_FUNC_RETURN(ctx, pin_info->reference);
|
||||
if (auth_info->auth_method == auth_method && pin_attrs->reference == reference)
|
||||
LOG_FUNC_RETURN(ctx, pin_attrs->reference);
|
||||
|
||||
if (auth_method != SC_AC_SYMBOLIC)
|
||||
continue;
|
||||
@ -1666,44 +1666,44 @@ sc_pkcs15init_get_pin_reference(struct sc_pkcs15_card *p15card,
|
||||
* and check for the existing pkcs15 PIN object with these flags. */
|
||||
switch (reference) {
|
||||
case SC_PKCS15INIT_USER_PIN:
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
if (pin_attrs->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
continue;
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN)
|
||||
if (pin_attrs->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN)
|
||||
continue;
|
||||
break;
|
||||
case SC_PKCS15INIT_SO_PIN:
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN)
|
||||
if (pin_attrs->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN)
|
||||
continue;
|
||||
if (!(pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN))
|
||||
if (!(pin_attrs->flags & SC_PKCS15_PIN_FLAG_SO_PIN))
|
||||
continue;
|
||||
break;
|
||||
case SC_PKCS15INIT_USER_PUK:
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
if (pin_attrs->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
continue;
|
||||
if (!(pin_info->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN))
|
||||
if (!(pin_attrs->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN))
|
||||
continue;
|
||||
break;
|
||||
case SC_PKCS15INIT_SO_PUK:
|
||||
if (!(pin_info->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN))
|
||||
if (!(pin_attrs->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN))
|
||||
continue;
|
||||
if (!(pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN))
|
||||
if (!(pin_attrs->flags & SC_PKCS15_PIN_FLAG_SO_PIN))
|
||||
continue;
|
||||
break;
|
||||
default:
|
||||
LOG_TEST_RET(ctx, SC_ERROR_INVALID_ARGUMENTS, "Invalid Symbolic PIN reference");
|
||||
}
|
||||
|
||||
LOG_FUNC_RETURN(ctx, pin_info->reference);
|
||||
LOG_FUNC_RETURN(ctx, pin_attrs->reference);
|
||||
|
||||
}
|
||||
|
||||
/* 2. No existing pkcs15 PIN object
|
||||
* -- check if profile defines some PIN with 'reference' as PIN reference. */
|
||||
r = sc_profile_get_pin_id_by_reference(profile, auth_method, reference, &pinfo);
|
||||
r = sc_profile_get_pin_id_by_reference(profile, auth_method, reference, &auth_info);
|
||||
if (r < 0)
|
||||
LOG_TEST_RET(ctx, SC_ERROR_OBJECT_NOT_FOUND, "PIN template not found");
|
||||
|
||||
LOG_FUNC_RETURN(ctx, pinfo.reference);
|
||||
LOG_FUNC_RETURN(ctx, auth_info.attrs.pin.reference);
|
||||
}
|
||||
|
||||
|
||||
@ -2251,7 +2251,7 @@ get_object_path_from_object (struct sc_pkcs15_object *obj,
|
||||
*ret_path = ((struct sc_pkcs15_data_info *)obj->data)->path;
|
||||
return SC_SUCCESS;
|
||||
case SC_PKCS15_TYPE_AUTH:
|
||||
*ret_path = ((struct sc_pkcs15_pin_info *)obj->data)->path;
|
||||
*ret_path = ((struct sc_pkcs15_auth_info *)obj->data)->path;
|
||||
return SC_SUCCESS;
|
||||
}
|
||||
return SC_ERROR_NOT_SUPPORTED;
|
||||
@ -2608,7 +2608,7 @@ sc_pkcs15init_new_object(int type, const char *label, struct sc_pkcs15_id *auth_
|
||||
switch (type & SC_PKCS15_TYPE_CLASS_MASK) {
|
||||
case SC_PKCS15_TYPE_AUTH:
|
||||
object->flags = DEFAULT_PIN_FLAGS;
|
||||
data_size = sizeof(struct sc_pkcs15_pin_info);
|
||||
data_size = sizeof(struct sc_pkcs15_auth_info);
|
||||
break;
|
||||
case SC_PKCS15_TYPE_PRKEY:
|
||||
object->flags = DEFAULT_PRKEY_FLAGS;
|
||||
@ -2949,7 +2949,7 @@ sc_pkcs15init_get_transport_key(struct sc_profile *profile, struct sc_pkcs15_car
|
||||
{
|
||||
struct sc_context *ctx = p15card->card->ctx;
|
||||
struct sc_pkcs15_object *pin_obj = NULL;
|
||||
struct sc_pkcs15_pin_info pin_info;
|
||||
struct sc_pkcs15_auth_info auth_info;
|
||||
struct sc_cardctl_default_key data;
|
||||
size_t defsize = 0;
|
||||
unsigned char defbuf[0x100];
|
||||
@ -2976,15 +2976,15 @@ sc_pkcs15init_get_transport_key(struct sc_profile *profile, struct sc_pkcs15_car
|
||||
*pinsize = data.len;
|
||||
}
|
||||
|
||||
memset(&pin_info, 0, sizeof(pin_info));
|
||||
pin_info.auth_method = type;
|
||||
pin_info.reference = reference;
|
||||
pin_info.stored_length = *pinsize;
|
||||
pin_info.max_length = *pinsize;
|
||||
pin_info.min_length = *pinsize;
|
||||
pin_info.magic = SC_PKCS15_PIN_MAGIC;
|
||||
memset(&auth_info, 0, sizeof(auth_info));
|
||||
auth_info.auth_type = SC_PKCS15_PIN_AUTH_TYPE_PIN;
|
||||
auth_info.auth_method = type;
|
||||
auth_info.attrs.pin.reference = reference;
|
||||
auth_info.attrs.pin.stored_length = *pinsize;
|
||||
auth_info.attrs.pin.max_length = *pinsize;
|
||||
auth_info.attrs.pin.min_length = *pinsize;
|
||||
|
||||
pin_obj = sc_pkcs15init_new_object(SC_PKCS15_TYPE_AUTH_PIN, "Default transport key", NULL, &pin_info);
|
||||
pin_obj = sc_pkcs15init_new_object(SC_PKCS15_TYPE_AUTH_PIN, "Default transport key", NULL, &auth_info);
|
||||
if (!pin_obj)
|
||||
LOG_TEST_RET(ctx, SC_ERROR_OUT_OF_MEMORY, "Cannot allocate AUTH object");
|
||||
|
||||
@ -3006,7 +3006,7 @@ sc_pkcs15init_verify_secret(struct sc_profile *profile, struct sc_pkcs15_card *p
|
||||
{
|
||||
struct sc_context *ctx = p15card->card->ctx;
|
||||
struct sc_pkcs15_object *pin_obj = NULL;
|
||||
struct sc_pkcs15_pin_info pin_info;
|
||||
struct sc_pkcs15_auth_info auth_info;
|
||||
struct sc_path *path;
|
||||
int r, use_pinpad = 0, pin_id = -1;
|
||||
const char *ident, *label = NULL;
|
||||
@ -3032,9 +3032,10 @@ sc_pkcs15init_verify_secret(struct sc_profile *profile, struct sc_pkcs15_card *p
|
||||
LOG_TEST_RET(ctx, r, "Card CTL error: cannot get CHV reference");
|
||||
}
|
||||
|
||||
memset(&pin_info, 0, sizeof(pin_info));
|
||||
pin_info.auth_method = type;
|
||||
pin_info.reference = reference;
|
||||
memset(&auth_info, 0, sizeof(auth_info));
|
||||
auth_info.auth_type = SC_PKCS15_PIN_AUTH_TYPE_PIN;
|
||||
auth_info.auth_method = type;
|
||||
auth_info.attrs.pin.reference = reference;
|
||||
|
||||
pin_id = sc_pkcs15init_get_pin_reference(p15card, profile, type, reference);
|
||||
sc_log(ctx, "found PIN reference %i", pin_id);
|
||||
@ -3062,7 +3063,7 @@ sc_pkcs15init_verify_secret(struct sc_profile *profile, struct sc_pkcs15_card *p
|
||||
}
|
||||
|
||||
if (!r && pin_obj) {
|
||||
memcpy(&pin_info, pin_obj->data, sizeof(pin_info));
|
||||
memcpy(&auth_info, pin_obj->data, sizeof(auth_info));
|
||||
sc_log(ctx, "found PIN object '%s'", pin_obj->label);
|
||||
}
|
||||
}
|
||||
@ -3085,7 +3086,7 @@ sc_pkcs15init_verify_secret(struct sc_profile *profile, struct sc_pkcs15_card *p
|
||||
switch (type) {
|
||||
case SC_AC_CHV:
|
||||
if (callbacks.get_pin) {
|
||||
r = callbacks.get_pin(profile, pin_id, &pin_info, label, pinbuf, &pinsize);
|
||||
r = callbacks.get_pin(profile, pin_id, &auth_info, label, pinbuf, &pinsize);
|
||||
sc_log(ctx, "'get_pin' callback returned %i; pinsize:%i", r, pinsize);
|
||||
}
|
||||
break;
|
||||
@ -3467,14 +3468,13 @@ sc_pkcs15init_get_pin_path(struct sc_pkcs15_card *p15card,
|
||||
r = sc_pkcs15_find_pin_by_auth_id(p15card, auth_id, &obj);
|
||||
if (r < 0)
|
||||
return r;
|
||||
*path = ((struct sc_pkcs15_pin_info *) obj->data)->path;
|
||||
*path = ((struct sc_pkcs15_auth_info *) obj->data)->path;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
int
|
||||
sc_pkcs15init_get_pin_info(struct sc_profile *profile,
|
||||
int id, struct sc_pkcs15_pin_info *pin)
|
||||
sc_pkcs15init_get_pin_info(struct sc_profile *profile, int id, struct sc_pkcs15_auth_info *pin)
|
||||
{
|
||||
sc_profile_get_pin_info(profile, id, pin);
|
||||
return 0;
|
||||
@ -3526,16 +3526,22 @@ sc_pkcs15init_sanity_check(struct sc_pkcs15_card *p15card, struct sc_profile *pr
|
||||
|
||||
static int
|
||||
sc_pkcs15init_qualify_pin(struct sc_card *card, const char *pin_name,
|
||||
unsigned int pin_len, struct sc_pkcs15_pin_info *pin_info)
|
||||
unsigned int pin_len, struct sc_pkcs15_auth_info *auth_info)
|
||||
{
|
||||
if (pin_len == 0)
|
||||
struct sc_context *ctx = card->ctx;
|
||||
struct sc_pkcs15_pin_attributes *pin_attrs;
|
||||
|
||||
if (pin_len == 0 || auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return 0;
|
||||
if (pin_len < pin_info->min_length) {
|
||||
sc_log(card->ctx, "%s too short (min length %u)", pin_name, pin_info->min_length);
|
||||
|
||||
pin_attrs = &auth_info->attrs.pin;
|
||||
|
||||
if (pin_len < pin_attrs->min_length) {
|
||||
sc_log(ctx, "%s too short (min length %u)", pin_name, pin_attrs->min_length);
|
||||
return SC_ERROR_WRONG_LENGTH;
|
||||
}
|
||||
if (pin_len > pin_info->max_length) {
|
||||
sc_log(card->ctx, "%s too long (max length %u)", pin_name, pin_info->max_length);
|
||||
if (pin_len > pin_attrs->max_length) {
|
||||
sc_log(ctx, "%s too long (max length %u)", pin_name, pin_attrs->max_length);
|
||||
return SC_ERROR_WRONG_LENGTH;
|
||||
}
|
||||
|
||||
@ -3704,7 +3710,7 @@ sc_pkcs15init_write_info(struct sc_pkcs15_card *p15card,
|
||||
|
||||
if (pin_obj != NULL) {
|
||||
method = SC_AC_CHV;
|
||||
key_ref = ((struct sc_pkcs15_pin_info *) pin_obj->data)->reference;
|
||||
key_ref = ((struct sc_pkcs15_auth_info *) pin_obj->data)->attrs.pin.reference;
|
||||
}
|
||||
else {
|
||||
method = SC_AC_NONE; /* Unprotected */
|
||||
|
@ -136,11 +136,13 @@ miocos_create_dir(struct sc_profile *profile, sc_pkcs15_card_t *p15card,
|
||||
*/
|
||||
static int
|
||||
miocos_select_pin_reference(struct sc_profile *profile, sc_pkcs15_card_t *p15card,
|
||||
struct sc_pkcs15_pin_info *pin_info)
|
||||
struct sc_pkcs15_auth_info *auth_info)
|
||||
{
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
if (pin_info->reference < MIOCOS_PIN_ID_MIN)
|
||||
pin_info->reference = MIOCOS_PIN_ID_MIN;
|
||||
if (auth_info->attrs.pin.reference < MIOCOS_PIN_ID_MIN)
|
||||
auth_info->attrs.pin.reference = MIOCOS_PIN_ID_MIN;
|
||||
|
||||
return SC_SUCCESS;
|
||||
}
|
||||
@ -155,22 +157,23 @@ miocos_create_pin(struct sc_profile *profile, sc_pkcs15_card_t *p15card, struct
|
||||
const u8 *puk, size_t puk_len)
|
||||
{
|
||||
struct sc_context *ctx = p15card->card->ctx;
|
||||
struct sc_pkcs15_pin_info *pin_info = (struct sc_pkcs15_pin_info *)pin_obj->data;
|
||||
struct sc_pkcs15_pin_info tmpinfo;
|
||||
struct sc_pkcs15_auth_info *auth_info = (struct sc_pkcs15_auth_info *)pin_obj->data;
|
||||
struct sc_pkcs15_pin_attributes *pin_attrs = &auth_info->attrs.pin;
|
||||
struct sc_pkcs15_auth_info tmpinfo;
|
||||
struct sc_cardctl_miocos_ac_info ac_info;
|
||||
int r;
|
||||
|
||||
SC_FUNC_CALLED(ctx, SC_LOG_DEBUG_VERBOSE);
|
||||
/* Ignore SOPIN */
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
if (pin_attrs->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
return SC_SUCCESS;
|
||||
|
||||
pin_info->path = profile->df_info->file->path;
|
||||
r = sc_select_file(p15card->card, &pin_info->path, NULL);
|
||||
auth_info->path = profile->df_info->file->path;
|
||||
r = sc_select_file(p15card->card, &auth_info->path, NULL);
|
||||
if (r)
|
||||
return r;
|
||||
memset(&ac_info, 0, sizeof(ac_info));
|
||||
ac_info.ref = pin_info->reference;
|
||||
ac_info.ref = pin_attrs->reference;
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_USER_PIN, &tmpinfo);
|
||||
ac_info.max_tries = tmpinfo.tries_left;
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_USER_PUK, &tmpinfo);
|
||||
|
@ -92,33 +92,38 @@ muscle_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
const unsigned char *puk, size_t puk_len)
|
||||
{
|
||||
sc_file_t *file;
|
||||
sc_pkcs15_pin_info_t *pin_info = (sc_pkcs15_pin_info_t *) pin_obj->data;
|
||||
sc_pkcs15_auth_info_t *auth_info = (sc_pkcs15_auth_info_t *) pin_obj->data;
|
||||
int r;
|
||||
|
||||
if ((r = sc_select_file(p15card->card, &df->path, &file)) < 0)
|
||||
return r;
|
||||
if ((r = sc_pkcs15init_authenticate(profile, p15card, file, SC_AC_OP_WRITE)) < 0)
|
||||
return r;
|
||||
pin_info->flags &= ~SC_PKCS15_PIN_FLAG_LOCAL;
|
||||
|
||||
auth_info->attrs.pin.flags &= ~SC_PKCS15_PIN_FLAG_LOCAL;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int
|
||||
muscle_select_pin_reference(sc_profile_t *profike, sc_pkcs15_card_t *p15card,
|
||||
sc_pkcs15_pin_info_t *pin_info)
|
||||
sc_pkcs15_auth_info_t *auth_info)
|
||||
{
|
||||
int preferred;
|
||||
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
if (auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
preferred = 0;
|
||||
} else {
|
||||
preferred = 1;
|
||||
}
|
||||
if (pin_info->reference <= preferred) {
|
||||
pin_info->reference = preferred;
|
||||
if (auth_info->attrs.pin.reference <= preferred) {
|
||||
auth_info->attrs.pin.reference = preferred;
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (pin_info->reference > 2)
|
||||
if (auth_info->attrs.pin.reference > 2)
|
||||
return SC_ERROR_INVALID_ARGUMENTS;
|
||||
|
||||
/* Caller, please select a different PIN reference */
|
||||
|
@ -246,25 +246,29 @@ myeid_create_dir(sc_profile_t *profile, sc_pkcs15_card_t *p15card, sc_file_t *df
|
||||
*/
|
||||
static int
|
||||
myeid_select_pin_reference(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
sc_pkcs15_pin_info_t *pin_info)
|
||||
sc_pkcs15_auth_info_t *auth_info)
|
||||
{
|
||||
SC_FUNC_CALLED(p15card->card->ctx, SC_LOG_DEBUG_VERBOSE);
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
if (auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
{
|
||||
sc_debug(p15card->card->ctx, SC_LOG_DEBUG_NORMAL,
|
||||
"PIN_FLAG_SO_PIN, ref (%d), tries_left (%d)",
|
||||
pin_info->reference,pin_info->tries_left);
|
||||
auth_info->attrs.pin.reference, auth_info->tries_left);
|
||||
}
|
||||
else
|
||||
{
|
||||
sc_debug(p15card->card->ctx, SC_LOG_DEBUG_NORMAL,
|
||||
"PIN_FLAG_PIN, ref (%d), tries_left (%d)",
|
||||
pin_info->reference, pin_info->tries_left);
|
||||
auth_info->attrs.pin.reference, auth_info->tries_left);
|
||||
|
||||
}
|
||||
|
||||
if (pin_info->reference <= 0 || pin_info->reference > MYEID_MAX_PINS)
|
||||
pin_info->reference = 1;
|
||||
if (auth_info->attrs.pin.reference <= 0 || auth_info->attrs.pin.reference > MYEID_MAX_PINS)
|
||||
auth_info->attrs.pin.reference = 1;
|
||||
|
||||
SC_FUNC_RETURN(p15card->card->ctx, SC_LOG_DEBUG_NORMAL, 0);
|
||||
}
|
||||
@ -281,41 +285,43 @@ myeid_create_pin(struct sc_profile *profile, struct sc_pkcs15_card *p15card,
|
||||
struct sc_context *ctx = p15card->card->ctx;
|
||||
unsigned char data[20];
|
||||
struct sc_cardctl_myeid_data_obj data_obj;
|
||||
struct sc_pkcs15_pin_info *pin_info = (struct sc_pkcs15_pin_info *)pin_obj->data;
|
||||
struct sc_pkcs15_pin_info puk_info;
|
||||
struct sc_pkcs15_auth_info *auth_info = (struct sc_pkcs15_auth_info *)pin_obj->data;
|
||||
struct sc_pkcs15_auth_info puk_ainfo;
|
||||
int r;
|
||||
|
||||
SC_FUNC_CALLED(ctx, SC_LOG_DEBUG_VERBOSE);
|
||||
sc_debug(ctx, SC_LOG_DEBUG_NORMAL, "PIN('%s',ref:%i,flags:0x%X,pin_len:%d,puk_len:%d)\n",
|
||||
pin_obj->label, pin_info->reference, pin_info->flags, pin_len, puk_len);
|
||||
pin_obj->label, auth_info->attrs.pin.reference, auth_info->attrs.pin.flags, pin_len, puk_len);
|
||||
|
||||
if (pin_info->reference >= MYEID_MAX_PINS)
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
if (auth_info->attrs.pin.reference >= MYEID_MAX_PINS)
|
||||
return SC_ERROR_INVALID_ARGUMENTS;
|
||||
if (pin == NULL || puk == NULL || pin_len < 4 || puk_len < 4)
|
||||
return SC_ERROR_INVALID_PIN_LENGTH;
|
||||
|
||||
sc_profile_get_pin_info(profile, (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
sc_profile_get_pin_info(profile, (auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
? SC_PKCS15INIT_SO_PUK : SC_PKCS15INIT_USER_PUK,
|
||||
&puk_info);
|
||||
&puk_ainfo);
|
||||
|
||||
memset(data, 0, sizeof(data));
|
||||
/* Make command to add a pin-record */
|
||||
data_obj.P1 = 0x01;
|
||||
data_obj.P2 = pin_info->reference; /* myeid pin number */
|
||||
data_obj.P2 = auth_info->attrs.pin.reference; /* myeid pin number */
|
||||
|
||||
memset(data, pin_info->pad_char, 8);
|
||||
memset(data, auth_info->attrs.pin.pad_char, 8);
|
||||
memcpy(&data[0], (u8 *)pin, pin_len); /* copy pin */
|
||||
|
||||
memset(&data[8], puk_info.pad_char, 8);
|
||||
memset(&data[8], puk_ainfo.attrs.pin.pad_char, 8);
|
||||
memcpy(&data[8], (u8 *)puk, puk_len); /* copy puk */
|
||||
|
||||
if(pin_info->tries_left > 0 && pin_info->tries_left < 15)
|
||||
data[16] = pin_info->tries_left;
|
||||
if(auth_info->tries_left > 0 && auth_info->tries_left < 15)
|
||||
data[16] = auth_info->tries_left;
|
||||
else
|
||||
data[16] = 5; /* default value */
|
||||
|
||||
if(puk_info.tries_left > 0 && puk_info.tries_left < 15)
|
||||
data[17] = puk_info.tries_left;
|
||||
if(puk_ainfo.tries_left > 0 && puk_ainfo.tries_left < 15)
|
||||
data[17] = puk_ainfo.tries_left;
|
||||
else
|
||||
data[17] = 5; /* default value */
|
||||
|
||||
|
@ -53,10 +53,10 @@
|
||||
#define COSM_TOKEN_FLAG_TOKEN_INITIALIZED 0x0400
|
||||
|
||||
static int cosm_create_reference_data(struct sc_profile *, struct sc_pkcs15_card *,
|
||||
struct sc_pkcs15_pin_info *, const unsigned char *, size_t,
|
||||
struct sc_pkcs15_auth_info *, const unsigned char *, size_t,
|
||||
const unsigned char *, size_t);
|
||||
static int cosm_update_pin(struct sc_profile *, struct sc_pkcs15_card *,
|
||||
struct sc_pkcs15_pin_info *, const unsigned char *, size_t,
|
||||
struct sc_pkcs15_auth_info *, const unsigned char *, size_t,
|
||||
const unsigned char *, size_t);
|
||||
|
||||
static int
|
||||
@ -269,14 +269,13 @@ cosm_create_dir(struct sc_profile *profile, struct sc_pkcs15_card *p15card,
|
||||
|
||||
static int
|
||||
cosm_create_reference_data(struct sc_profile *profile, struct sc_pkcs15_card *p15card,
|
||||
struct sc_pkcs15_pin_info *pinfo,
|
||||
struct sc_pkcs15_auth_info *ainfo,
|
||||
const unsigned char *pin, size_t pin_len,
|
||||
const unsigned char *puk, size_t puk_len )
|
||||
{
|
||||
struct sc_context *ctx = p15card->card->ctx;
|
||||
struct sc_card *card = p15card->card;
|
||||
struct sc_pkcs15_pin_info profile_pin;
|
||||
struct sc_pkcs15_pin_info profile_puk;
|
||||
struct sc_pkcs15_auth_info profile_auth_pin, profile_auth_puk;
|
||||
struct sc_cardctl_oberthur_createpin_info args;
|
||||
unsigned char *puk_buff = NULL;
|
||||
int rv;
|
||||
@ -291,35 +290,38 @@ cosm_create_reference_data(struct sc_profile *profile, struct sc_pkcs15_card *p1
|
||||
return SC_ERROR_INVALID_ARGUMENTS;
|
||||
if (puk && !puk_len)
|
||||
return SC_ERROR_INVALID_ARGUMENTS;
|
||||
if (ainfo->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
rv = sc_select_file(card, &pinfo->path, NULL);
|
||||
rv = sc_select_file(card, &ainfo->path, NULL);
|
||||
SC_TEST_RET(ctx, SC_LOG_DEBUG_NORMAL, rv, "Cannot select file");
|
||||
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_USER_PIN, &profile_pin);
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_USER_PUK, &profile_puk);
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_USER_PIN, &profile_auth_pin);
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_USER_PUK, &profile_auth_puk);
|
||||
|
||||
memset(&args, 0, sizeof(args));
|
||||
args.type = SC_AC_CHV;
|
||||
args.ref = pinfo->reference;
|
||||
args.ref = ainfo->attrs.pin.reference;
|
||||
args.pin = pin;
|
||||
args.pin_len = pin_len;
|
||||
|
||||
if (!(pinfo->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN)) {
|
||||
args.pin_tries = profile_pin.tries_left;
|
||||
if (profile_puk.tries_left > 0) {
|
||||
if (!(ainfo->attrs.pin.flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN)) {
|
||||
args.pin_tries = profile_auth_pin.tries_left;
|
||||
if (profile_auth_puk.tries_left > 0) {
|
||||
args.puk = oberthur_puk;
|
||||
args.puk_len = sizeof(oberthur_puk);
|
||||
args.puk_tries = 5;
|
||||
}
|
||||
}
|
||||
else {
|
||||
args.pin_tries = profile_puk.tries_left;
|
||||
args.pin_tries = profile_auth_puk.tries_left;
|
||||
}
|
||||
|
||||
rv = sc_card_ctl(card, SC_CARDCTL_OBERTHUR_CREATE_PIN, &args);
|
||||
SC_TEST_RET(ctx, SC_LOG_DEBUG_NORMAL, rv, "'CREATE_PIN' card specific command failed");
|
||||
|
||||
if (!(pinfo->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN) && (profile_puk.tries_left > 0)) {
|
||||
if (!(ainfo->attrs.pin.flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN)
|
||||
&& (profile_auth_puk.tries_left > 0)) {
|
||||
struct sc_file *file = NULL;
|
||||
|
||||
if (sc_profile_get_file(profile, COSM_TITLE"-puk-file", &file))
|
||||
@ -344,24 +346,26 @@ cosm_create_reference_data(struct sc_profile *profile, struct sc_pkcs15_card *p1
|
||||
*/
|
||||
static int
|
||||
cosm_update_pin(struct sc_profile *profile, struct sc_pkcs15_card *p15card,
|
||||
struct sc_pkcs15_pin_info *pinfo, const unsigned char *pin, size_t pin_len,
|
||||
struct sc_pkcs15_auth_info *ainfo, const unsigned char *pin, size_t pin_len,
|
||||
const unsigned char *puk, size_t puk_len )
|
||||
{
|
||||
struct sc_context *ctx = p15card->card->ctx;
|
||||
int rv;
|
||||
|
||||
SC_FUNC_CALLED(ctx, SC_LOG_DEBUG_VERBOSE);
|
||||
sc_debug(ctx, SC_LOG_DEBUG_NORMAL, "ref %i; flags 0x%X", pinfo->reference, pinfo->flags);
|
||||
if (ainfo->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
if (pinfo->flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
if (pinfo->reference != 4)
|
||||
sc_debug(ctx, SC_LOG_DEBUG_NORMAL, "ref %i; flags 0x%X", ainfo->attrs.pin.reference, ainfo->attrs.pin.flags);
|
||||
|
||||
if (ainfo->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
if (ainfo->attrs.pin.reference != 4)
|
||||
SC_TEST_RET(ctx, SC_LOG_DEBUG_NORMAL, SC_ERROR_INVALID_PIN_REFERENCE, "cosm_update_pin() invalid SOPIN reference");
|
||||
sc_debug(ctx, SC_LOG_DEBUG_NORMAL, "Update SOPIN ignored");
|
||||
rv = SC_SUCCESS;
|
||||
}
|
||||
else {
|
||||
rv = cosm_create_reference_data(profile, p15card, pinfo,
|
||||
pin, pin_len, puk, puk_len);
|
||||
rv = cosm_create_reference_data(profile, p15card, ainfo, pin, pin_len, puk, puk_len);
|
||||
SC_TEST_RET(ctx, SC_LOG_DEBUG_NORMAL, rv, "cosm_update_pin() failed to change PIN");
|
||||
|
||||
rv = cosm_write_tokeninfo(p15card, profile, NULL,
|
||||
@ -378,33 +382,39 @@ cosm_update_pin(struct sc_profile *profile, struct sc_pkcs15_card *p15card,
|
||||
|
||||
static int
|
||||
cosm_select_pin_reference(struct sc_profile *profile, struct sc_pkcs15_card *p15card,
|
||||
struct sc_pkcs15_pin_info *pin_info)
|
||||
struct sc_pkcs15_auth_info *auth_info)
|
||||
{
|
||||
struct sc_context *ctx = p15card->card->ctx;
|
||||
struct sc_pkcs15_pin_attributes *pin_attrs;
|
||||
struct sc_file *pinfile;
|
||||
|
||||
SC_FUNC_CALLED(ctx, SC_LOG_DEBUG_VERBOSE);
|
||||
sc_debug(ctx, SC_LOG_DEBUG_NORMAL, "ref %i; flags %X", pin_info->reference, pin_info->flags);
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
pin_attrs = &auth_info->attrs.pin;
|
||||
|
||||
sc_debug(ctx, SC_LOG_DEBUG_NORMAL, "ref %i; flags %X", pin_attrs->reference, pin_attrs->flags);
|
||||
if (sc_profile_get_file(profile, COSM_TITLE "-AppDF", &pinfile) < 0) {
|
||||
sc_debug(ctx, SC_LOG_DEBUG_NORMAL, "Profile doesn't define \"%s\"", COSM_TITLE "-AppDF");
|
||||
return SC_ERROR_INCONSISTENT_PROFILE;
|
||||
}
|
||||
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_LOCAL)
|
||||
pin_info->path = pinfile->path;
|
||||
if (pin_attrs->flags & SC_PKCS15_PIN_FLAG_LOCAL)
|
||||
auth_info->path = pinfile->path;
|
||||
|
||||
sc_file_free(pinfile);
|
||||
|
||||
if (pin_info->reference <= 0) {
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
pin_info->reference = 4;
|
||||
else if (pin_info->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN)
|
||||
pin_info->reference = 4;
|
||||
if (pin_attrs->reference <= 0) {
|
||||
if (pin_attrs->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
pin_attrs->reference = 4;
|
||||
else if (pin_attrs->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN)
|
||||
pin_attrs->reference = 4;
|
||||
else
|
||||
pin_info->reference = 1;
|
||||
pin_attrs->reference = 1;
|
||||
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_LOCAL)
|
||||
pin_info->reference |= 0x80;
|
||||
if (pin_attrs->flags & SC_PKCS15_PIN_FLAG_LOCAL)
|
||||
pin_attrs->reference |= 0x80;
|
||||
}
|
||||
|
||||
SC_FUNC_RETURN(ctx, SC_LOG_DEBUG_NORMAL, SC_SUCCESS);
|
||||
@ -421,42 +431,48 @@ cosm_create_pin(struct sc_profile *profile, struct sc_pkcs15_card *p15card,
|
||||
const unsigned char *puk, size_t puk_len)
|
||||
{
|
||||
struct sc_context *ctx = p15card->card->ctx;
|
||||
struct sc_pkcs15_pin_info *pin_info = (struct sc_pkcs15_pin_info *) pin_obj->data;
|
||||
struct sc_pkcs15_auth_info *auth_info = (struct sc_pkcs15_auth_info *) pin_obj->data;
|
||||
struct sc_pkcs15_pin_attributes *pin_attrs;
|
||||
struct sc_file *pin_file;
|
||||
int rv = 0;
|
||||
|
||||
SC_FUNC_CALLED(ctx, SC_LOG_DEBUG_VERBOSE);
|
||||
sc_debug(ctx, SC_LOG_DEBUG_NORMAL, "create '%s'; ref 0x%X; flags %X", pin_obj->label, pin_info->reference, pin_info->flags);
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
pin_attrs = &auth_info->attrs.pin;
|
||||
|
||||
sc_debug(ctx, SC_LOG_DEBUG_NORMAL, "create '%s'; ref 0x%X; flags %X", pin_obj->label, pin_attrs->reference, pin_attrs->flags);
|
||||
if (sc_profile_get_file(profile, COSM_TITLE "-AppDF", &pin_file) < 0)
|
||||
SC_TEST_RET(ctx, SC_LOG_DEBUG_NORMAL, SC_ERROR_INCONSISTENT_PROFILE, "\""COSM_TITLE"-AppDF\" not defined");
|
||||
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_LOCAL)
|
||||
pin_info->path = pin_file->path;
|
||||
if (pin_attrs->flags & SC_PKCS15_PIN_FLAG_LOCAL)
|
||||
auth_info->path = pin_file->path;
|
||||
|
||||
sc_file_free(pin_file);
|
||||
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN) {
|
||||
if (pin_attrs->flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
if (pin_attrs->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN) {
|
||||
SC_TEST_RET(ctx, SC_LOG_DEBUG_NORMAL, SC_ERROR_NOT_SUPPORTED, "SOPIN unblocking is not supported");
|
||||
}
|
||||
else {
|
||||
if (pin_info->reference != 4)
|
||||
if (pin_attrs->reference != 4)
|
||||
SC_TEST_RET(ctx, SC_LOG_DEBUG_NORMAL, SC_ERROR_INVALID_PIN_REFERENCE, "Invalid SOPIN reference");
|
||||
}
|
||||
}
|
||||
else {
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN) {
|
||||
if (pin_info->reference != 0x84)
|
||||
if (pin_attrs->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN) {
|
||||
if (pin_attrs->reference != 0x84)
|
||||
SC_TEST_RET(ctx, SC_LOG_DEBUG_NORMAL, SC_ERROR_INVALID_PIN_REFERENCE, "Invalid User PUK reference");
|
||||
}
|
||||
else {
|
||||
if (pin_info->reference != 0x81)
|
||||
if (pin_attrs->reference != 0x81)
|
||||
SC_TEST_RET(ctx, SC_LOG_DEBUG_NORMAL, SC_ERROR_INVALID_PIN_REFERENCE, "Invalid User PIN reference");
|
||||
}
|
||||
}
|
||||
|
||||
if (pin && pin_len) {
|
||||
rv = cosm_update_pin(profile, p15card, pin_info, pin, pin_len, puk, puk_len);
|
||||
rv = cosm_update_pin(profile, p15card, auth_info, pin, pin_len, puk, puk_len);
|
||||
SC_TEST_RET(ctx, SC_LOG_DEBUG_NORMAL, rv, "Update PIN failed");
|
||||
}
|
||||
|
||||
|
@ -141,18 +141,21 @@ static int rtecp_create_dir(sc_profile_t *profile, sc_pkcs15_card_t *p15card, sc
|
||||
* Select a PIN reference
|
||||
*/
|
||||
static int rtecp_select_pin_reference(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
sc_pkcs15_pin_info_t *pin_info)
|
||||
sc_pkcs15_auth_info_t *auth_info)
|
||||
{
|
||||
int pin_ref;
|
||||
|
||||
if (!profile || !p15card || !p15card->card || !p15card->card->ctx || !pin_info)
|
||||
if (!profile || !p15card || !p15card->card || !p15card->card->ctx || !auth_info)
|
||||
return SC_ERROR_INVALID_ARGUMENTS;
|
||||
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
if (auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
pin_ref = RTECP_SO_PIN_REF;
|
||||
else
|
||||
pin_ref = RTECP_USER_PIN_REF;
|
||||
if (pin_info->reference != pin_ref)
|
||||
if (auth_info->attrs.pin.reference != pin_ref)
|
||||
SC_FUNC_RETURN(p15card->card->ctx, SC_LOG_DEBUG_NORMAL, SC_ERROR_NOT_SUPPORTED);
|
||||
|
||||
return SC_SUCCESS;
|
||||
@ -167,7 +170,7 @@ static int rtecp_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
const unsigned char *puk, size_t puk_len)
|
||||
{
|
||||
sc_context_t *ctx;
|
||||
sc_pkcs15_pin_info_t *pin_info;
|
||||
sc_pkcs15_auth_info_t *auth_info;
|
||||
sc_file_t *file = NULL;
|
||||
/* GCHV min-length Flags Attempts Reserve */
|
||||
unsigned char prop[] = { 0x01, '?', 0x01, '?', 0, 0 };
|
||||
@ -190,17 +193,21 @@ static int rtecp_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
sc_strerror(SC_ERROR_NOT_SUPPORTED));
|
||||
return SC_ERROR_NOT_SUPPORTED;
|
||||
}
|
||||
pin_info = (sc_pkcs15_pin_info_t *)pin_obj->data;
|
||||
if (pin_info->reference != RTECP_SO_PIN_REF
|
||||
&& pin_info->reference != RTECP_USER_PIN_REF)
|
||||
|
||||
auth_info = (sc_pkcs15_auth_info_t *)pin_obj->data;
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
if (auth_info->attrs.pin.reference != RTECP_SO_PIN_REF
|
||||
&& auth_info->attrs.pin.reference != RTECP_USER_PIN_REF)
|
||||
{
|
||||
sc_debug(ctx, SC_LOG_DEBUG_NORMAL, "PIN reference %i not found in standard"
|
||||
" (Rutoken ECP) PINs\n", pin_info->reference);
|
||||
" (Rutoken ECP) PINs\n", auth_info->attrs.pin.reference);
|
||||
return SC_ERROR_NOT_SUPPORTED;
|
||||
}
|
||||
|
||||
snprintf(pin_sname, sizeof(pin_sname), "CHV%i", pin_info->reference);
|
||||
if (pin_info->reference == RTECP_USER_PIN_REF) {
|
||||
snprintf(pin_sname, sizeof(pin_sname), "CHV%i", auth_info->attrs.pin.reference);
|
||||
if (auth_info->attrs.pin.reference == RTECP_USER_PIN_REF) {
|
||||
r = sc_profile_get_file(profile, pin_sname, &file);
|
||||
if (!r) {
|
||||
const struct sc_acl_entry *acl = NULL;
|
||||
@ -220,17 +227,17 @@ static int rtecp_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
file = sc_file_new();
|
||||
if (!file)
|
||||
SC_FUNC_RETURN(ctx, SC_LOG_DEBUG_NORMAL, SC_ERROR_OUT_OF_MEMORY);
|
||||
file->id = pin_info->reference;
|
||||
file->id = auth_info->attrs.pin.reference;
|
||||
file->size = pin_len;
|
||||
assert(sizeof(sec)/sizeof(sec[0]) > 2);
|
||||
sec[1] = (pin_info->reference == RTECP_SO_PIN_REF) ? 0xFF : RTECP_SO_PIN_REF;
|
||||
sec[2] = (unsigned char)pin_info->reference | (reset_by_sopin ? RTECP_SO_PIN_REF : 0);
|
||||
sec[1] = (auth_info->attrs.pin.reference == RTECP_SO_PIN_REF) ? 0xFF : RTECP_SO_PIN_REF;
|
||||
sec[2] = (unsigned char)auth_info->attrs.pin.reference | (reset_by_sopin ? RTECP_SO_PIN_REF : 0);
|
||||
r = sc_file_set_sec_attr(file, sec, sizeof(sec));
|
||||
if (r == SC_SUCCESS)
|
||||
{
|
||||
assert(sizeof(prop)/sizeof(prop[0]) > 3);
|
||||
prop[1] = (unsigned char)pin_info->min_length;
|
||||
prop[3] = 0x11 * (unsigned char)(pin_info->tries_left & 0x0F);
|
||||
prop[1] = (unsigned char)auth_info->attrs.pin.min_length;
|
||||
prop[3] = 0x11 * (unsigned char)(auth_info->tries_left & 0x0F);
|
||||
r = sc_file_set_prop_attr(file, prop, sizeof(prop));
|
||||
}
|
||||
if (r == SC_SUCCESS)
|
||||
@ -241,7 +248,7 @@ static int rtecp_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
|
||||
if (r == SC_SUCCESS)
|
||||
r = sc_change_reference_data(p15card->card, SC_AC_CHV,
|
||||
pin_info->reference, NULL, 0, pin, pin_len, NULL);
|
||||
auth_info->attrs.pin.reference, NULL, 0, pin, pin_len, NULL);
|
||||
SC_FUNC_RETURN(ctx, SC_LOG_DEBUG_NORMAL, r);
|
||||
}
|
||||
|
||||
|
@ -94,18 +94,21 @@ rutoken_create_dir(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
*/
|
||||
static int
|
||||
rutoken_select_pin_reference(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
sc_pkcs15_pin_info_t *pin_info)
|
||||
sc_pkcs15_auth_info_t *auth_info)
|
||||
{
|
||||
int pin_ref;
|
||||
unsigned int so_pin_flag;
|
||||
|
||||
if (!profile || !p15card || !p15card->card || !p15card->card->ctx || !pin_info)
|
||||
if (!profile || !p15card || !p15card->card || !p15card->card->ctx || !auth_info)
|
||||
return SC_ERROR_INVALID_ARGUMENTS;
|
||||
|
||||
SC_FUNC_CALLED(p15card->card->ctx, SC_LOG_DEBUG_VERBOSE);
|
||||
|
||||
pin_ref = pin_info->reference;
|
||||
so_pin_flag = pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN;
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
pin_ref = auth_info->attrs.pin.reference;
|
||||
so_pin_flag = auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN;
|
||||
|
||||
sc_debug(p15card->card->ctx, SC_LOG_DEBUG_NORMAL, "PIN reference %i%s\n",
|
||||
pin_ref, so_pin_flag ? " SO PIN flag" : "");
|
||||
@ -128,7 +131,7 @@ rutoken_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
const unsigned char *puk, size_t puk_len)
|
||||
{
|
||||
sc_context_t *ctx;
|
||||
sc_pkcs15_pin_info_t *pin_info;
|
||||
sc_pkcs15_auth_info_t *auth_info;
|
||||
size_t i;
|
||||
|
||||
(void)puk; /* no warning */
|
||||
@ -146,9 +149,13 @@ rutoken_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
sc_strerror(SC_ERROR_NOT_SUPPORTED));
|
||||
return SC_ERROR_NOT_SUPPORTED;
|
||||
}
|
||||
pin_info = (sc_pkcs15_pin_info_t *)pin_obj->data;
|
||||
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
auth_info = (sc_pkcs15_auth_info_t *)pin_obj->data;
|
||||
for (i = 0; i < sizeof(do_pins)/sizeof(do_pins[0]); ++i)
|
||||
if (pin_info->reference == do_pins[i].id)
|
||||
if (auth_info->attrs.pin.reference == do_pins[i].id)
|
||||
{
|
||||
if (pin_len == sizeof(do_pins[i].pass)
|
||||
&& memcmp(do_pins[i].pass, pin, pin_len) == 0
|
||||
@ -162,7 +169,7 @@ rutoken_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
}
|
||||
sc_debug(ctx, SC_LOG_DEBUG_NORMAL,
|
||||
"PIN reference %i not found in standard (Rutoken) PINs\n",
|
||||
pin_info->reference);
|
||||
auth_info->attrs.pin.reference);
|
||||
return SC_ERROR_NOT_SUPPORTED;
|
||||
}
|
||||
|
||||
|
@ -36,25 +36,26 @@ static unsigned char SETCOS_DEFAULT_PUBKEY[] = {0x01, 0x00, 0x01};
|
||||
#define SETCOS_DEFAULT_PUBKEY_LEN sizeof(SETCOS_DEFAULT_PUBKEY)
|
||||
|
||||
static int setcos_create_pin_internal(sc_profile_t *, sc_pkcs15_card_t *,
|
||||
int, sc_pkcs15_pin_info_t *, const u8 *, size_t, const u8 *, size_t);
|
||||
int, sc_pkcs15_auth_info_t *, const u8 *, size_t, const u8 *, size_t);
|
||||
|
||||
|
||||
static int
|
||||
setcos_puk_retries(sc_profile_t *profile, int pin_ref)
|
||||
{
|
||||
sc_pkcs15_pin_info_t pin_info;
|
||||
sc_pkcs15_auth_info_t auth_info;
|
||||
|
||||
pin_info.reference = 1; /* Default SO PIN ref. */
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_SO_PIN, &pin_info);
|
||||
auth_info.auth_type = SC_PKCS15_PIN_AUTH_TYPE_PIN;
|
||||
auth_info.attrs.pin.reference = 1; /* Default SO PIN ref. */
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_SO_PIN, &auth_info);
|
||||
|
||||
/* If pin_ref is the SO PIN, get the SO PUK info, otherwise the User PUK info */
|
||||
sc_profile_get_pin_info(profile,
|
||||
pin_ref == pin_info.reference ? SC_PKCS15INIT_SO_PUK : SC_PKCS15INIT_USER_PUK,
|
||||
&pin_info);
|
||||
pin_ref == auth_info.attrs.pin.reference ? SC_PKCS15INIT_SO_PUK : SC_PKCS15INIT_USER_PUK,
|
||||
&auth_info);
|
||||
|
||||
if ((pin_info.tries_left < 0) || (pin_info.tries_left > 15))
|
||||
if ((auth_info.tries_left < 0) || (auth_info.tries_left > 15))
|
||||
return 3; /* Little extra safety */
|
||||
return pin_info.tries_left;
|
||||
return auth_info.tries_left;
|
||||
}
|
||||
|
||||
|
||||
@ -162,21 +163,22 @@ setcos_create_dir(sc_profile_t *profile, sc_pkcs15_card_t *p15card, sc_file_t *d
|
||||
*/
|
||||
static int
|
||||
setcos_select_pin_reference(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
sc_pkcs15_pin_info_t *pin_info)
|
||||
sc_pkcs15_auth_info_t *auth_info)
|
||||
{
|
||||
sc_pkcs15_pin_info_t pin_info_prof;
|
||||
sc_pkcs15_auth_info_t auth_info_prof;
|
||||
|
||||
pin_info_prof.reference = 1; /* Default SO PIN ref. */
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_SO_PIN, &pin_info_prof);
|
||||
auth_info_prof.attrs.pin.reference = 1; /* Default SO PIN ref. */
|
||||
auth_info_prof.auth_type = SC_PKCS15_PIN_AUTH_TYPE_PIN;
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_SO_PIN, &auth_info_prof);
|
||||
|
||||
/* For the SO pin, we take the first available pin reference = 1 */
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
pin_info->reference = pin_info_prof.reference;
|
||||
if (auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
auth_info->attrs.pin.reference = auth_info_prof.attrs.pin.reference;
|
||||
/* sc_pkcs15init_create_pin() starts checking if -1 is an acceptable
|
||||
* pin reference, which isn't for the SetCOS cards. And since the
|
||||
* value 1 has been assigned to the SO pin, we'll jump to 2. */
|
||||
else if (pin_info->reference <= 0)
|
||||
pin_info->reference = pin_info_prof.reference + 1;
|
||||
else if (auth_info->attrs.pin.reference <= 0)
|
||||
auth_info->attrs.pin.reference = auth_info_prof.attrs.pin.reference + 1;
|
||||
|
||||
return 0;
|
||||
}
|
||||
@ -192,12 +194,15 @@ setcos_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
const u8 *puk, size_t puk_len)
|
||||
{
|
||||
struct sc_context *ctx = p15card->card->ctx;
|
||||
sc_pkcs15_pin_info_t *pin_info = (sc_pkcs15_pin_info_t *) pin_obj->data;
|
||||
sc_pkcs15_auth_info_t *auth_info = (sc_pkcs15_auth_info_t *) pin_obj->data;
|
||||
sc_file_t *pinfile = NULL;
|
||||
int r, ignore_ac = 0;
|
||||
|
||||
SC_FUNC_CALLED(ctx, SC_LOG_DEBUG_VERBOSE);
|
||||
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
/* Create the global pin file if it doesn't exist yet */
|
||||
r = sc_profile_get_file(profile, "pinfile", &pinfile);
|
||||
SC_TEST_RET(ctx, SC_LOG_DEBUG_NORMAL, r, "No 'pinfile' template in profile");
|
||||
@ -207,18 +212,18 @@ setcos_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
|
||||
sc_debug(ctx, SC_LOG_DEBUG_NORMAL, "pinfile->status:%X", pinfile->status);
|
||||
sc_debug(ctx, SC_LOG_DEBUG_NORMAL, "create PIN with reference:%X, flags:%X, path:%s",
|
||||
pin_info->reference, pin_info->flags, sc_print_path(&pin_info->path));
|
||||
auth_info->attrs.pin.reference, auth_info->attrs.pin.flags, sc_print_path(&auth_info->path));
|
||||
|
||||
if (pinfile->status == SC_FILE_STATUS_CREATION)
|
||||
ignore_ac = 1;
|
||||
|
||||
r = setcos_create_pin_internal(profile, p15card, ignore_ac, pin_info,
|
||||
r = setcos_create_pin_internal(profile, p15card, ignore_ac, auth_info,
|
||||
pin, pin_len, puk, puk_len);
|
||||
|
||||
/* If pinfile is in 'Creation' state and SOPIN has been created,
|
||||
* change status of MF and 'pinfile' to 'Operational:Activated'
|
||||
*/
|
||||
if (ignore_ac && (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN)) {
|
||||
if (ignore_ac && (auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN)) {
|
||||
sc_file_t *mf = profile->mf_info->file;
|
||||
|
||||
r = sc_card_ctl(p15card->card, SC_CARDCTL_SETCOS_ACTIVATE_FILE, NULL);
|
||||
@ -496,7 +501,7 @@ setcos_generate_key(struct sc_profile *profile, struct sc_pkcs15_card *p15card,
|
||||
*/
|
||||
static int
|
||||
setcos_create_pin_internal(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
int ignore_ac, sc_pkcs15_pin_info_t *pin_info,
|
||||
int ignore_ac, sc_pkcs15_auth_info_t *auth_info,
|
||||
const u8 *pin, size_t pin_len,
|
||||
const u8 *puk, size_t puk_len)
|
||||
{
|
||||
@ -507,7 +512,10 @@ setcos_create_pin_internal(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
sc_file_t *pinfile = NULL;
|
||||
|
||||
SC_FUNC_CALLED(ctx, SC_LOG_DEBUG_VERBOSE);
|
||||
if (pin_info->reference >= SETCOS_MAX_PINS)
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
if (auth_info->attrs.pin.reference >= SETCOS_MAX_PINS)
|
||||
return SC_ERROR_INVALID_ARGUMENTS;
|
||||
if (pin == NULL || puk == NULL || pin_len < 4 || puk_len < 4)
|
||||
return SC_ERROR_INVALID_PIN_LENGTH;
|
||||
@ -529,26 +537,26 @@ setcos_create_pin_internal(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
data_obj.P2 = 01;
|
||||
|
||||
/* setcos pin number */
|
||||
data[0] = pin_info->reference;
|
||||
data[0] = auth_info->attrs.pin.reference;
|
||||
|
||||
memset(&data[1], pin_info->pad_char, 16); /* padding */
|
||||
memset(&data[1], auth_info->attrs.pin.pad_char, 16); /* padding */
|
||||
memcpy(&data[1], (u8 *)pin, pin_len); /* copy pin*/
|
||||
memcpy(&data[9], (u8 *)puk, puk_len); /* copy puk */
|
||||
|
||||
data[17] = pin_info->tries_left & 0x0F;
|
||||
data[18] = pin_info->tries_left & 0x0F;
|
||||
data[17] = auth_info->tries_left & 0x0F;
|
||||
data[18] = auth_info->tries_left & 0x0F;
|
||||
/* 0xF0: unlimited unblock tries */
|
||||
data[19] = 0xF0 | setcos_puk_retries(profile, pin_info->reference);
|
||||
data[19] = 0xF0 | setcos_puk_retries(profile, auth_info->attrs.pin.reference);
|
||||
|
||||
/* Allow an unlimited number of signatures after a pin verification.
|
||||
* If set to 1 or so, we would have a UserConsent PIN. */
|
||||
data[20] = 0x00;
|
||||
|
||||
if (pin_info->type == 0)
|
||||
if (auth_info->attrs.pin.type == 0)
|
||||
data[21] = 0x01; /* BCD */
|
||||
else
|
||||
data[21] = 0x00; /* ASCII */
|
||||
if ((pin_info->flags & 0x010) == 0) /* test for initial pin */
|
||||
if ((auth_info->attrs.pin.flags & 0x010) == 0) /* test for initial pin */
|
||||
data[21] |= 0x80;
|
||||
|
||||
data[22] = 0x00; /* not used */
|
||||
|
@ -49,13 +49,13 @@ static int starcos_erase_card(struct sc_profile *pro, sc_pkcs15_card_t *p15card)
|
||||
}
|
||||
|
||||
static u8 get_so_ac(const sc_file_t *file, unsigned int op,
|
||||
const sc_pkcs15_pin_info_t *pin, unsigned int def,
|
||||
const sc_pkcs15_auth_info_t *auth, unsigned int def,
|
||||
unsigned int need_global)
|
||||
{
|
||||
int is_global = 1;
|
||||
const sc_acl_entry_t *acl;
|
||||
|
||||
if (pin->flags & SC_PKCS15_PIN_FLAG_LOCAL)
|
||||
if (auth->attrs.pin.flags & SC_PKCS15_PIN_FLAG_LOCAL)
|
||||
is_global = 0;
|
||||
if (!is_global && need_global)
|
||||
return def & 0xff;
|
||||
@ -83,7 +83,7 @@ static int starcos_init_card(sc_profile_t *profile, sc_pkcs15_card_t *p15card)
|
||||
sc_file_t *mf_file, *isf_file, *ipf_file;
|
||||
sc_path_t tpath;
|
||||
u8 *p = mf_data.data.mf.header, tmp = 0;
|
||||
sc_pkcs15_pin_info_t sopin;
|
||||
sc_pkcs15_auth_info_t sopin;
|
||||
|
||||
/* test if we already have a MF */
|
||||
memset(&tpath, 0, sizeof(sc_path_t));
|
||||
@ -180,7 +180,7 @@ static int starcos_create_dir(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
sc_starcos_create_data df_data, ipf_data;
|
||||
sc_file_t *isf_file, *ipf_file;
|
||||
u8 *p = df_data.data.df.header, tmp = 0;
|
||||
sc_pkcs15_pin_info_t sopin;
|
||||
sc_pkcs15_auth_info_t sopin;
|
||||
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_SO_PIN, &sopin);
|
||||
|
||||
@ -255,10 +255,11 @@ static int starcos_create_dir(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
|
||||
static int have_onepin(sc_profile_t *profile)
|
||||
{
|
||||
sc_pkcs15_pin_info_t sopin;
|
||||
sc_pkcs15_auth_info_t sopin;
|
||||
|
||||
sc_profile_get_pin_info(profile, SC_PKCS15INIT_SO_PIN, &sopin);
|
||||
if (!(sopin.flags & SC_PKCS15_PIN_FLAG_SO_PIN))
|
||||
|
||||
if (!(sopin.attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN))
|
||||
return 1;
|
||||
else
|
||||
return 0;
|
||||
@ -272,20 +273,25 @@ static int have_onepin(sc_profile_t *profile)
|
||||
#define STARCOS_MIN_GPIN_ID 0x03
|
||||
#define STARCOS_MAX_GPIN_ID 0x0f
|
||||
static int starcos_pin_reference(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
sc_pkcs15_pin_info_t *pin_info)
|
||||
sc_pkcs15_auth_info_t *auth_info)
|
||||
{
|
||||
int tmp = pin_info->reference;
|
||||
int tmp;
|
||||
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
tmp = auth_info->attrs.pin.reference;
|
||||
|
||||
if (have_onepin(profile)) {
|
||||
/* we have the onepin profile */
|
||||
pin_info->reference = STARCOS_SOPIN_GID;
|
||||
auth_info->attrs.pin.reference = STARCOS_SOPIN_GID;
|
||||
return SC_SUCCESS;
|
||||
}
|
||||
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_LOCAL) {
|
||||
if (auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_LOCAL) {
|
||||
/* use local KID */
|
||||
/* SO-pin */
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
if (auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
tmp = STARCOS_SOPIN_LID;
|
||||
else {
|
||||
if (tmp < STARCOS_MIN_LPIN_ID)
|
||||
@ -299,7 +305,7 @@ static int starcos_pin_reference(sc_profile_t *profile, sc_pkcs15_card_t *p15car
|
||||
} else {
|
||||
/* use global KID */
|
||||
/* SO-pin */
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
if (auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
tmp = STARCOS_SOPIN_GID;
|
||||
else {
|
||||
if (tmp < STARCOS_MIN_GPIN_ID)
|
||||
@ -311,7 +317,7 @@ static int starcos_pin_reference(sc_profile_t *profile, sc_pkcs15_card_t *p15car
|
||||
return SC_ERROR_TOO_MANY_OBJECTS;
|
||||
}
|
||||
}
|
||||
pin_info->reference = tmp;
|
||||
auth_info->attrs.pin.reference = tmp;
|
||||
|
||||
return SC_SUCCESS;
|
||||
}
|
||||
@ -349,14 +355,17 @@ static int starcos_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
size_t akd;
|
||||
sc_file_t *tfile;
|
||||
const sc_acl_entry_t *acl_entry;
|
||||
sc_pkcs15_pin_info_t *pin_info = (sc_pkcs15_pin_info_t *) pin_obj->data;
|
||||
sc_pkcs15_auth_info_t *auth_info = (sc_pkcs15_auth_info_t *) pin_obj->data;
|
||||
sc_starcos_wkey_data pin_d, puk_d;
|
||||
u8 tpin[8];
|
||||
|
||||
if (!pin || !pin_len || pin_len > 8)
|
||||
return SC_ERROR_INVALID_ARGUMENTS;
|
||||
|
||||
is_local = 0x80 & pin_info->reference;
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
is_local = 0x80 & auth_info->attrs.pin.reference;
|
||||
if (is_local)
|
||||
r = sc_select_file(card, &df->path, NULL);
|
||||
else
|
||||
@ -369,7 +378,7 @@ static int starcos_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
return r;
|
||||
acl_entry = sc_file_get_acl_entry(tfile, SC_AC_OP_WRITE);
|
||||
if (acl_entry->method != SC_AC_NONE) {
|
||||
if ((pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN) || have_onepin(profile))
|
||||
if ((auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN) || have_onepin(profile))
|
||||
need_finalize = 1;
|
||||
else
|
||||
r = sc_pkcs15init_authenticate(profile, p15card, tfile, SC_AC_OP_WRITE);
|
||||
@ -383,8 +392,8 @@ static int starcos_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
memcpy(tpin, pin, pin_len);
|
||||
|
||||
/* write PIN */
|
||||
tmp = pin_info->tries_left;
|
||||
pin_id = pin_info->reference;
|
||||
tmp = auth_info->tries_left;
|
||||
pin_id = auth_info->attrs.pin.reference;
|
||||
|
||||
pin_d.mode = 0; /* install */
|
||||
pin_d.kid = (u8) pin_id;
|
||||
@ -394,7 +403,7 @@ static int starcos_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
pin_d.key_header[1] = 0;
|
||||
pin_d.key_header[2] = 8;
|
||||
pin_d.key_header[3] = STARCOS_AC_ALWAYS;
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
if (auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
pin_d.key_header[4] = STARCOS_SOPIN_STATE;
|
||||
else
|
||||
pin_d.key_header[4] = STARCOS_PINID2STATE(pin_id);
|
||||
@ -402,7 +411,7 @@ static int starcos_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
pin_d.key_header[6] = ((0x0f & tmp) << 4) | (0x0f & tmp);
|
||||
pin_d.key_header[7] = 0x00;
|
||||
pin_d.key_header[8] = 0x00;
|
||||
akd = pin_info->min_length;
|
||||
akd = auth_info->attrs.pin.min_length;
|
||||
if (akd < 4)
|
||||
akd = 4;
|
||||
if (akd > 8)
|
||||
@ -419,7 +428,7 @@ static int starcos_create_pin(sc_profile_t *profile, sc_pkcs15_card_t *p15card,
|
||||
return r;
|
||||
|
||||
if (puk && puk_len) {
|
||||
sc_pkcs15_pin_info_t puk_info;
|
||||
sc_pkcs15_auth_info_t puk_info;
|
||||
|
||||
if (puk_len > 8)
|
||||
return SC_ERROR_INVALID_ARGUMENTS;
|
||||
|
@ -71,13 +71,16 @@ static int westcos_pkcs15init_create_dir(sc_profile_t *profile,
|
||||
*/
|
||||
static int westcos_pkcs15_select_pin_reference(sc_profile_t *profile,
|
||||
sc_pkcs15_card_t *p15card,
|
||||
sc_pkcs15_pin_info_t *pin_info)
|
||||
sc_pkcs15_auth_info_t *auth_info)
|
||||
{
|
||||
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
pin_info->reference = 1;
|
||||
if (auth_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_OBJECT_NOT_VALID;
|
||||
|
||||
if (auth_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
auth_info->attrs.pin.reference = 1;
|
||||
} else {
|
||||
pin_info->reference = 0;
|
||||
auth_info->attrs.pin.reference = 0;
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
@ -488,7 +488,7 @@ sc_profile_free(struct sc_profile *profile)
|
||||
|
||||
void
|
||||
sc_profile_get_pin_info(struct sc_profile *profile,
|
||||
int id, struct sc_pkcs15_pin_info *info)
|
||||
int id, struct sc_pkcs15_auth_info *info)
|
||||
{
|
||||
struct pin_info *pi;
|
||||
|
||||
@ -516,7 +516,9 @@ sc_profile_get_pin_id(struct sc_profile *profile,
|
||||
struct pin_info *pi;
|
||||
|
||||
for (pi = profile->pin_list; pi; pi = pi->next) {
|
||||
if (pi->pin.reference == (int)reference) {
|
||||
if (pi->pin.auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
continue;
|
||||
if (pi->pin.attrs.pin.reference == (int)reference) {
|
||||
*id = pi->id;
|
||||
return 0;
|
||||
}
|
||||
@ -778,7 +780,7 @@ sc_profile_instantiate_file(sc_profile_t *profile, struct file_info *ft,
|
||||
int
|
||||
sc_profile_get_pin_id_by_reference(struct sc_profile *profile,
|
||||
unsigned auth_method, int reference,
|
||||
struct sc_pkcs15_pin_info *pin_info)
|
||||
struct sc_pkcs15_auth_info *auth_info)
|
||||
{
|
||||
struct pin_info *pinfo;
|
||||
|
||||
@ -788,14 +790,16 @@ sc_profile_get_pin_id_by_reference(struct sc_profile *profile,
|
||||
continue;
|
||||
}
|
||||
else {
|
||||
if (pinfo->pin.auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
continue;
|
||||
if (pinfo->pin.auth_method != auth_method)
|
||||
continue;
|
||||
if (pinfo->pin.reference != reference)
|
||||
if (pinfo->pin.attrs.pin.reference != reference)
|
||||
continue;
|
||||
}
|
||||
|
||||
if (pin_info)
|
||||
*pin_info = pinfo->pin;
|
||||
if (auth_info)
|
||||
*auth_info = pinfo->pin;
|
||||
return pinfo->id;
|
||||
}
|
||||
|
||||
@ -1490,15 +1494,15 @@ new_pin(struct sc_profile *profile, int id)
|
||||
if (pi == NULL)
|
||||
return NULL;
|
||||
pi->id = id;
|
||||
pi->pin.auth_type = SC_PKCS15_PIN_AUTH_TYPE_PIN;
|
||||
pi->pin.auth_method = SC_AC_CHV;
|
||||
pi->pin.type = (unsigned int)-1;
|
||||
pi->pin.flags = 0x32;
|
||||
pi->pin.max_length = 0;
|
||||
pi->pin.min_length = 0;
|
||||
pi->pin.stored_length = 0;
|
||||
pi->pin.pad_char = 0xA5;
|
||||
pi->pin.magic = SC_PKCS15_PIN_MAGIC;
|
||||
pi->pin.reference = -1;
|
||||
pi->pin.attrs.pin.type = (unsigned int)-1;
|
||||
pi->pin.attrs.pin.flags = 0x32;
|
||||
pi->pin.attrs.pin.max_length = 0;
|
||||
pi->pin.attrs.pin.min_length = 0;
|
||||
pi->pin.attrs.pin.stored_length = 0;
|
||||
pi->pin.attrs.pin.pad_char = 0xA5;
|
||||
pi->pin.attrs.pin.reference = -1;
|
||||
pi->pin.tries_left = 3;
|
||||
|
||||
*tail = pi;
|
||||
@ -1507,22 +1511,25 @@ new_pin(struct sc_profile *profile, int id)
|
||||
|
||||
static void set_pin_defaults(struct sc_profile *profile, struct pin_info *pi)
|
||||
{
|
||||
struct sc_pkcs15_pin_info *info = &pi->pin;
|
||||
struct sc_pkcs15_auth_info *info = &pi->pin;
|
||||
struct sc_pkcs15_pin_attributes *pin_attrs = &info->attrs.pin;
|
||||
|
||||
if (info->type == (unsigned int) -1)
|
||||
info->type = profile->pin_encoding;
|
||||
if (info->max_length == 0)
|
||||
info->max_length = profile->pin_maxlen;
|
||||
if (info->min_length == 0)
|
||||
info->min_length = profile->pin_minlen;
|
||||
if (info->stored_length == 0) {
|
||||
info->stored_length = profile->pin_maxlen;
|
||||
info->auth_type = SC_PKCS15_PIN_AUTH_TYPE_PIN;
|
||||
|
||||
if (pin_attrs->type == (unsigned int) -1)
|
||||
pin_attrs->type = profile->pin_encoding;
|
||||
if (pin_attrs->max_length == 0)
|
||||
pin_attrs->max_length = profile->pin_maxlen;
|
||||
if (pin_attrs->min_length == 0)
|
||||
pin_attrs->min_length = profile->pin_minlen;
|
||||
if (pin_attrs->stored_length == 0) {
|
||||
pin_attrs->stored_length = profile->pin_maxlen;
|
||||
/* BCD encoded PIN takes half the space */
|
||||
if (info->type == SC_PKCS15_PIN_TYPE_BCD)
|
||||
info->stored_length = (info->stored_length + 1) / 2;
|
||||
if (pin_attrs->type == SC_PKCS15_PIN_TYPE_BCD)
|
||||
pin_attrs->stored_length = (pin_attrs->stored_length + 1) / 2;
|
||||
}
|
||||
if (info->pad_char == 0xA5)
|
||||
info->pad_char = profile->pin_pad_char;
|
||||
if (pin_attrs->pad_char == 0xA5)
|
||||
pin_attrs->pad_char = profile->pin_pad_char;
|
||||
}
|
||||
|
||||
static int
|
||||
@ -1557,7 +1564,9 @@ do_pin_type(struct state *cur, int argc, char **argv)
|
||||
|
||||
if (map_str2int(cur, argv[0], &type, pinTypeNames))
|
||||
return 1;
|
||||
cur->pin->pin.type = type;
|
||||
if (cur->pin->pin.auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return 1;
|
||||
cur->pin->pin.attrs.pin.type = type;
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -1568,7 +1577,9 @@ do_pin_reference(struct state *cur, int argc, char **argv)
|
||||
|
||||
if (get_uint(cur, argv[0], &reference))
|
||||
return 1;
|
||||
cur->pin->pin.reference = reference;
|
||||
if (cur->pin->pin.auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return 1;
|
||||
cur->pin->pin.attrs.pin.reference = reference;
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -1586,7 +1597,9 @@ do_pin_minlength(struct state *cur, int argc, char **argv)
|
||||
|
||||
if (get_uint(cur, argv[0], &len))
|
||||
return 1;
|
||||
cur->pin->pin.min_length = len;
|
||||
if (cur->pin->pin.auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return 1;
|
||||
cur->pin->pin.attrs.pin.min_length = len;
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -1597,7 +1610,9 @@ do_pin_maxlength(struct state *cur, int argc, char **argv)
|
||||
|
||||
if (get_uint(cur, argv[0], &len))
|
||||
return 1;
|
||||
cur->pin->pin.max_length = len;
|
||||
if (cur->pin->pin.auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return 1;
|
||||
cur->pin->pin.attrs.pin.max_length = len;
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -1608,7 +1623,9 @@ do_pin_storedlength(struct state *cur, int argc, char **argv)
|
||||
|
||||
if (get_uint(cur, argv[0], &len))
|
||||
return 1;
|
||||
cur->pin->pin.stored_length = len;
|
||||
if (cur->pin->pin.auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return 1;
|
||||
cur->pin->pin.attrs.pin.stored_length = len;
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -1618,11 +1635,14 @@ do_pin_flags(struct state *cur, int argc, char **argv)
|
||||
unsigned int flags;
|
||||
int i, r;
|
||||
|
||||
cur->pin->pin.flags = 0;
|
||||
if (cur->pin->pin.auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return -1;
|
||||
|
||||
cur->pin->pin.attrs.pin.flags = 0;
|
||||
for (i = 0; i < argc; i++) {
|
||||
if ((r = map_str2int(cur, argv[i], &flags, pinFlagNames)) < 0)
|
||||
return r;
|
||||
cur->pin->pin.flags |= flags;
|
||||
cur->pin->pin.attrs.pin.flags |= flags;
|
||||
}
|
||||
|
||||
return 0;
|
||||
|
@ -55,7 +55,7 @@ struct pin_info {
|
||||
unsigned int file_offset; /* obsolete */
|
||||
struct file_info * file; /* obsolete */
|
||||
|
||||
sc_pkcs15_pin_info_t pin;
|
||||
struct sc_pkcs15_auth_info pin;
|
||||
};
|
||||
|
||||
typedef struct sc_macro {
|
||||
@ -131,7 +131,7 @@ int sc_profile_load(struct sc_profile *, const char *);
|
||||
int sc_profile_finish(struct sc_profile *, const struct sc_app_info *);
|
||||
void sc_profile_free(struct sc_profile *);
|
||||
int sc_profile_build_pkcs15(struct sc_profile *);
|
||||
void sc_profile_get_pin_info(struct sc_profile *, int, struct sc_pkcs15_pin_info *);
|
||||
void sc_profile_get_pin_info(struct sc_profile *, int, struct sc_pkcs15_auth_info *);
|
||||
int sc_profile_get_pin_id(struct sc_profile *, unsigned int, int *);
|
||||
int sc_profile_get_file(struct sc_profile *, const char *, struct sc_file **);
|
||||
int sc_profile_get_file_by_path(struct sc_profile *, const struct sc_path *, struct sc_file **);
|
||||
@ -142,7 +142,7 @@ int sc_profile_instantiate_template(struct sc_profile *, const char *, const sc_
|
||||
int sc_profile_add_file(struct sc_profile *, const char *, sc_file_t *);
|
||||
int sc_profile_get_file_instance(struct sc_profile *, const char *, int, sc_file_t **);
|
||||
int sc_profile_get_pin_id_by_reference(struct sc_profile *, unsigned, int,
|
||||
struct sc_pkcs15_pin_info *);
|
||||
struct sc_pkcs15_auth_info *);
|
||||
int sc_profile_get_parent(struct sc_profile *profile, const char *, sc_file_t **);
|
||||
|
||||
#ifdef __cplusplus
|
||||
|
@ -46,12 +46,12 @@ static int enum_pins(struct sc_pkcs15_object ***ret)
|
||||
|
||||
static int ask_and_verify_pin(struct sc_pkcs15_object *pin_obj)
|
||||
{
|
||||
struct sc_pkcs15_pin_info *pin_info = (struct sc_pkcs15_pin_info *) pin_obj->data;
|
||||
struct sc_pkcs15_auth_info *pin_info = (struct sc_pkcs15_auth_info *) pin_obj->data;
|
||||
int i = 0;
|
||||
char prompt[80];
|
||||
u8 *pass;
|
||||
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN) {
|
||||
if (pin_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN) {
|
||||
printf("Skipping unblocking pin [%s]\n", pin_obj->label);
|
||||
return 0;
|
||||
}
|
||||
|
@ -53,38 +53,40 @@ static void print_pin(const struct sc_pkcs15_object *obj)
|
||||
"integrity-protected", "confidentiality-protected",
|
||||
"exchangeRefData"
|
||||
};
|
||||
struct sc_pkcs15_pin_info *pin;
|
||||
struct sc_pkcs15_auth_info *pin;
|
||||
const int pf_count = sizeof(pin_flags) / sizeof(pin_flags[0]);
|
||||
int i;
|
||||
|
||||
pin = (struct sc_pkcs15_pin_info *) obj->data;
|
||||
pin = (struct sc_pkcs15_auth_info *) obj->data;
|
||||
printf("\tAuth ID : %s\n", sc_pkcs15_print_id(&pin->auth_id));
|
||||
printf("\tFlags : [0x%02X]", pin->flags);
|
||||
for (i = 0; i < pf_count; i++)
|
||||
if (pin->flags & (1 << i)) {
|
||||
printf(", %s", pin_flags[i]);
|
||||
if (pin->auth_type == SC_PKCS15_PIN_AUTH_TYPE_PIN) {
|
||||
printf("\tFlags : [0x%02X]", pin->attrs.pin.flags);
|
||||
for (i = 0; i < pf_count; i++)
|
||||
if (pin->attrs.pin.flags & (1 << i)) {
|
||||
printf(", %s", pin_flags[i]);
|
||||
}
|
||||
printf("\n");
|
||||
printf("\tLength : min_len:%lu, max_len:%lu, stored_len:%lu\n",
|
||||
(unsigned long) pin->attrs.pin.min_length,
|
||||
(unsigned long) pin->attrs.pin.max_length,
|
||||
(unsigned long) pin->attrs.pin.stored_length);
|
||||
printf("\tPad char : 0x%02X\n", pin->attrs.pin.pad_char);
|
||||
printf("\tReference : %d\n", pin->attrs.pin.reference);
|
||||
printf("\tEncoding : ");
|
||||
switch (pin->attrs.pin.type) {
|
||||
case SC_PKCS15_PIN_TYPE_BCD:
|
||||
printf("BCD\n"); break;
|
||||
case SC_PKCS15_PIN_TYPE_ASCII_NUMERIC:
|
||||
printf("ASCII-numeric\n"); break;
|
||||
case SC_PKCS15_PIN_TYPE_UTF8:
|
||||
printf("UTF8\n"); break;
|
||||
case SC_PKCS15_PIN_TYPE_HALFNIBBLE_BCD:
|
||||
printf("half-nibble BCD\n"); break;
|
||||
case SC_PKCS15_PIN_TYPE_ISO9564_1:
|
||||
printf("ISO 9564-1\n"); break;
|
||||
default:
|
||||
printf("[encoding %d]\n", pin->attrs.pin.type);
|
||||
}
|
||||
printf("\n");
|
||||
printf("\tLength : min_len:%lu, max_len:%lu, stored_len:%lu\n",
|
||||
(unsigned long) pin->min_length,
|
||||
(unsigned long) pin->max_length,
|
||||
(unsigned long) pin->stored_length);
|
||||
printf("\tPad char : 0x%02X\n", pin->pad_char);
|
||||
printf("\tReference : %d\n", pin->reference);
|
||||
printf("\tEncoding : ");
|
||||
switch (pin->type) {
|
||||
case SC_PKCS15_PIN_TYPE_BCD:
|
||||
printf("BCD\n"); break;
|
||||
case SC_PKCS15_PIN_TYPE_ASCII_NUMERIC:
|
||||
printf("ASCII-numeric\n"); break;
|
||||
case SC_PKCS15_PIN_TYPE_UTF8:
|
||||
printf("UTF8\n"); break;
|
||||
case SC_PKCS15_PIN_TYPE_HALFNIBBLE_BCD:
|
||||
printf("half-nibble BCD\n"); break;
|
||||
case SC_PKCS15_PIN_TYPE_ISO9564_1:
|
||||
printf("ISO 9564-1\n"); break;
|
||||
default:
|
||||
printf("[encoding %d]\n", pin->type);
|
||||
}
|
||||
if (pin->path.len)
|
||||
printf("\tPath : %s\n", sc_print_path(&pin->path));
|
||||
|
@ -124,8 +124,11 @@ static char * get_pin(struct sc_pkcs15_object *obj)
|
||||
{
|
||||
char buf[80];
|
||||
char *pincode;
|
||||
struct sc_pkcs15_pin_info *pinfo = (struct sc_pkcs15_pin_info *) obj->data;
|
||||
|
||||
struct sc_pkcs15_auth_info *pinfo = (struct sc_pkcs15_auth_info *) obj->data;
|
||||
|
||||
if (pinfo->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return NULL;
|
||||
|
||||
if (opt_pincode != NULL) {
|
||||
if (strcmp(opt_pincode, "-") == 0)
|
||||
return readpin_stdin();
|
||||
@ -138,8 +141,8 @@ static char * get_pin(struct sc_pkcs15_object *obj)
|
||||
pincode = getpass(buf);
|
||||
if (strlen(pincode) == 0)
|
||||
return NULL;
|
||||
if (strlen(pincode) < pinfo->min_length ||
|
||||
strlen(pincode) > pinfo->max_length)
|
||||
if (strlen(pincode) < pinfo->attrs.pin.min_length ||
|
||||
strlen(pincode) > pinfo->attrs.pin.max_length)
|
||||
continue;
|
||||
return strdup(pincode);
|
||||
}
|
||||
|
@ -100,7 +100,7 @@ static int do_sanity_check(struct sc_profile *profile);
|
||||
static int init_keyargs(struct sc_pkcs15init_prkeyargs *);
|
||||
static void init_gost_params(struct sc_pkcs15init_keyarg_gost_params *, EVP_PKEY *);
|
||||
static int get_pin_callback(struct sc_profile *profile,
|
||||
int id, const struct sc_pkcs15_pin_info *info,
|
||||
int id, const struct sc_pkcs15_auth_info *info,
|
||||
const char *label,
|
||||
u8 *pinbuf, size_t *pinsize);
|
||||
static int get_key_callback(struct sc_profile *,
|
||||
@ -388,7 +388,7 @@ typedef struct sc_ui_hints {
|
||||
* look like. */
|
||||
const char * obj_label; /* O: object (PIN) label */
|
||||
union {
|
||||
struct sc_pkcs15_pin_info *pin;
|
||||
struct sc_pkcs15_auth_info *pin;
|
||||
} info;
|
||||
} sc_ui_hints_t;
|
||||
|
||||
@ -683,12 +683,13 @@ static int
|
||||
do_init_app(struct sc_profile *profile)
|
||||
{
|
||||
struct sc_pkcs15init_initargs args;
|
||||
sc_pkcs15_pin_info_t info;
|
||||
sc_pkcs15_auth_info_t info;
|
||||
sc_ui_hints_t hints;
|
||||
const char *role = "so";
|
||||
int r, so_puk_disabled = 0;
|
||||
|
||||
memset(&hints, 0, sizeof(hints));
|
||||
memset(&info, 0, sizeof(info));
|
||||
hints.usage = SC_UI_USAGE_NEW_PIN;
|
||||
hints.flags = SC_UI_PIN_RETYPE
|
||||
| SC_UI_PIN_CHECK_LENGTH
|
||||
@ -709,14 +710,14 @@ do_init_app(struct sc_profile *profile)
|
||||
|
||||
sc_pkcs15init_get_pin_info(profile, SC_PKCS15INIT_SO_PIN, &info);
|
||||
|
||||
if (!(info.flags & SC_PKCS15_PIN_FLAG_SO_PIN))
|
||||
if (!(info.attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN))
|
||||
role = "user";
|
||||
else
|
||||
hints.flags |= SC_UI_PIN_OPTIONAL; /* SO PIN is always optional */
|
||||
|
||||
|
||||
if ((info.flags & SC_PKCS15_PIN_FLAG_UNBLOCK_DISABLED)
|
||||
&& (info.flags & SC_PKCS15_PIN_FLAG_SO_PIN))
|
||||
if ((info.attrs.pin.flags & SC_PKCS15_PIN_FLAG_UNBLOCK_DISABLED)
|
||||
&& (info.attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN))
|
||||
so_puk_disabled = 1;
|
||||
|
||||
|
||||
@ -729,7 +730,7 @@ do_init_app(struct sc_profile *profile)
|
||||
if (!so_puk_disabled && opt_pins[2] && !opt_pins[3] && !opt_no_prompt) {
|
||||
sc_pkcs15init_get_pin_info(profile, SC_PKCS15INIT_SO_PUK, &info);
|
||||
|
||||
if (!(info.flags & SC_PKCS15_PIN_FLAG_SO_PIN))
|
||||
if (!(info.attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN))
|
||||
role = "user";
|
||||
|
||||
hints.flags |= SC_UI_PIN_OPTIONAL;
|
||||
@ -764,7 +765,7 @@ static int
|
||||
do_store_pin(struct sc_profile *profile)
|
||||
{
|
||||
struct sc_pkcs15init_pinargs args;
|
||||
sc_pkcs15_pin_info_t info;
|
||||
sc_pkcs15_auth_info_t info;
|
||||
sc_ui_hints_t hints;
|
||||
int r;
|
||||
const char *pin_id;
|
||||
@ -801,7 +802,7 @@ do_store_pin(struct sc_profile *profile)
|
||||
args.pin_len = strlen(opt_pins[0]);
|
||||
args.label = opt_label;
|
||||
|
||||
if (!(info.flags & SC_PKCS15_PIN_FLAG_UNBLOCK_DISABLED)
|
||||
if (!(info.attrs.pin.flags & SC_PKCS15_PIN_FLAG_UNBLOCK_DISABLED)
|
||||
&& opt_pins[1] == NULL) {
|
||||
sc_pkcs15init_get_pin_info(profile, SC_PKCS15INIT_USER_PUK, &info);
|
||||
|
||||
@ -1626,7 +1627,7 @@ static int get_new_pin(sc_ui_hints_t *hints,
|
||||
*/
|
||||
static int
|
||||
get_pin_callback(struct sc_profile *profile,
|
||||
int id, const struct sc_pkcs15_pin_info *info,
|
||||
int id, const struct sc_pkcs15_auth_info *info,
|
||||
const char *label,
|
||||
u8 *pinbuf, size_t *pinsize)
|
||||
{
|
||||
@ -1636,13 +1637,13 @@ get_pin_callback(struct sc_profile *profile,
|
||||
size_t len = 0;
|
||||
int allocated = 0;
|
||||
|
||||
if (label) {
|
||||
if (info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_NOT_SUPPORTED;
|
||||
|
||||
if (label)
|
||||
snprintf(namebuf, sizeof(namebuf), "PIN [%s]", label);
|
||||
} else {
|
||||
snprintf(namebuf, sizeof(namebuf),
|
||||
"Unspecified PIN [reference %u]",
|
||||
info->reference);
|
||||
}
|
||||
else
|
||||
snprintf(namebuf, sizeof(namebuf), "Unspecified PIN [reference %u]", info->attrs.pin.reference);
|
||||
|
||||
if (!ignore_cmdline_pins) {
|
||||
if (info->auth_method == SC_AC_SYMBOLIC) {
|
||||
@ -1666,23 +1667,23 @@ get_pin_callback(struct sc_profile *profile,
|
||||
}
|
||||
}
|
||||
else if (info->auth_method == SC_AC_CHV) {
|
||||
if (!(info->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
&& !(info->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN)) {
|
||||
if (!(info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
&& !(info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN)) {
|
||||
name = "User PIN";
|
||||
secret = opt_pins[OPT_PIN1 & 3];
|
||||
}
|
||||
else if (!(info->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
&& (info->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN)) {
|
||||
else if (!(info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
&& (info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN)) {
|
||||
name = "User PUK";
|
||||
secret = opt_pins[OPT_PUK1 & 3];
|
||||
}
|
||||
else if ((info->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
&& !(info->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN)) {
|
||||
else if ((info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
&& !(info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN)) {
|
||||
name = "Security officer PIN";
|
||||
secret = opt_pins[OPT_PIN2 & 3];
|
||||
}
|
||||
else if ((info->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
&& (info->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN)) {
|
||||
else if ((info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
&& (info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN)) {
|
||||
name = "Security officer PIN unlock key";
|
||||
secret = opt_pins[OPT_PUK2 & 3];
|
||||
}
|
||||
@ -2717,15 +2718,18 @@ ossl_print_errors(void)
|
||||
*/
|
||||
int get_pin(sc_ui_hints_t *hints, char **out)
|
||||
{
|
||||
sc_pkcs15_pin_info_t *pin_info;
|
||||
sc_pkcs15_auth_info_t *pin_info;
|
||||
const char *label;
|
||||
int flags = hints->flags;
|
||||
|
||||
pin_info = hints->info.pin;
|
||||
if (pin_info && pin_info->auth_type == SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return SC_ERROR_NOT_SUPPORTED;
|
||||
|
||||
if (!(label = hints->obj_label)) {
|
||||
if (pin_info == NULL) {
|
||||
label = "PIN";
|
||||
} else if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
} else if (pin_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN) {
|
||||
label = "Security Officer PIN";
|
||||
} else {
|
||||
label = "User PIN";
|
||||
@ -2758,17 +2762,17 @@ int get_pin(sc_ui_hints_t *hints, char **out)
|
||||
return 0;
|
||||
|
||||
if (pin_info && (flags & SC_UI_PIN_CHECK_LENGTH)) {
|
||||
if (strlen(pin) < pin_info->min_length) {
|
||||
if (strlen(pin) < pin_info->attrs.pin.min_length) {
|
||||
fprintf(stderr,
|
||||
"PIN too short (min %lu characters)\n",
|
||||
(unsigned long) pin_info->min_length);
|
||||
(unsigned long) pin_info->attrs.pin.min_length);
|
||||
continue;
|
||||
}
|
||||
if (pin_info->max_length
|
||||
&& strlen(pin) > pin_info->max_length) {
|
||||
if (pin_info->attrs.pin.max_length
|
||||
&& strlen(pin) > pin_info->attrs.pin.max_length) {
|
||||
fprintf(stderr,
|
||||
"PIN too long (max %lu characters)\n",
|
||||
(unsigned long) pin_info->max_length);
|
||||
(unsigned long) pin_info->attrs.pin.max_length);
|
||||
continue;
|
||||
}
|
||||
}
|
||||
@ -2827,11 +2831,13 @@ static int verify_pin(struct sc_pkcs15_card *p15card, char *auth_id_str)
|
||||
}
|
||||
|
||||
for (ii=0;ii<r;ii++) {
|
||||
struct sc_pkcs15_pin_info *pin_info = (struct sc_pkcs15_pin_info *) objs[ii]->data;
|
||||
struct sc_pkcs15_auth_info *pin_info = (struct sc_pkcs15_auth_info *) objs[ii]->data;
|
||||
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
if (pin_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
continue;
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN)
|
||||
if (pin_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
continue;
|
||||
if (pin_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN)
|
||||
continue;
|
||||
|
||||
pin_obj = objs[ii];
|
||||
|
@ -962,23 +962,26 @@ get_pin_info(void)
|
||||
|
||||
static u8 * get_pin(const char *prompt, sc_pkcs15_object_t *pin_obj)
|
||||
{
|
||||
sc_pkcs15_pin_info_t *pinfo = (sc_pkcs15_pin_info_t *) pin_obj->data;
|
||||
sc_pkcs15_auth_info_t *pinfo = (sc_pkcs15_auth_info_t *) pin_obj->data;
|
||||
char *pincode = NULL;
|
||||
size_t len = 0;
|
||||
int r;
|
||||
|
||||
printf("%s [%s]: ", prompt, pin_obj->label);
|
||||
if (pinfo->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return NULL;
|
||||
|
||||
while (1) {
|
||||
r = util_getpass(&pincode, &len, stdin);
|
||||
if (r < 0)
|
||||
return NULL;
|
||||
if (!pincode || strlen(pincode) == 0)
|
||||
return NULL;
|
||||
if (strlen(pincode) < pinfo->min_length) {
|
||||
if (strlen(pincode) < pinfo->attrs.pin.min_length) {
|
||||
printf("PIN code too short, try again.\n");
|
||||
continue;
|
||||
}
|
||||
if (strlen(pincode) > pinfo->max_length) {
|
||||
if (strlen(pincode) > pinfo->attrs.pin.max_length) {
|
||||
printf("PIN code too long, try again.\n");
|
||||
continue;
|
||||
}
|
||||
@ -1003,11 +1006,13 @@ static int verify_pin(void)
|
||||
}
|
||||
|
||||
for (ii=0;ii<r;ii++) {
|
||||
struct sc_pkcs15_pin_info *pin_info = (struct sc_pkcs15_pin_info *) objs[ii]->data;
|
||||
struct sc_pkcs15_auth_info *pin_info = (struct sc_pkcs15_auth_info *) objs[ii]->data;
|
||||
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
if (pin_info->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
continue;
|
||||
if (pin_info->flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN)
|
||||
if (pin_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_SO_PIN)
|
||||
continue;
|
||||
if (pin_info->attrs.pin.flags & SC_PKCS15_PIN_FLAG_UNBLOCKING_PIN)
|
||||
continue;
|
||||
|
||||
pin_obj = objs[ii];
|
||||
@ -1068,7 +1073,7 @@ static void print_pin_info(const struct sc_pkcs15_object *obj)
|
||||
};
|
||||
const char *pin_types[] = {"bcd", "ascii-numeric", "UTF-8",
|
||||
"halfnibble bcd", "iso 9664-1"};
|
||||
const struct sc_pkcs15_pin_info *pin = (const struct sc_pkcs15_pin_info *) obj->data;
|
||||
const struct sc_pkcs15_auth_info *pin = (const struct sc_pkcs15_auth_info *) obj->data;
|
||||
const size_t pf_count = NELEMENTS(pin_flags);
|
||||
size_t i;
|
||||
|
||||
@ -1077,21 +1082,23 @@ static void print_pin_info(const struct sc_pkcs15_object *obj)
|
||||
if (obj->auth_id.len)
|
||||
printf("\tAuth ID : %s\n", sc_pkcs15_print_id(&obj->auth_id));
|
||||
printf("\tID : %s\n", sc_pkcs15_print_id(&pin->auth_id));
|
||||
printf("\tFlags : [0x%02X]", pin->flags);
|
||||
for (i = 0; i < pf_count; i++)
|
||||
if (pin->flags & (1 << i)) {
|
||||
printf(", %s", pin_flags[i]);
|
||||
}
|
||||
printf("\n");
|
||||
printf("\tLength : min_len:%lu, max_len:%lu, stored_len:%lu\n",
|
||||
(unsigned long)pin->min_length, (unsigned long)pin->max_length,
|
||||
(unsigned long)pin->stored_length);
|
||||
printf("\tPad char : 0x%02X\n", pin->pad_char);
|
||||
printf("\tReference : %d\n", pin->reference);
|
||||
if (pin->type < NELEMENTS(pin_types))
|
||||
printf("\tType : %s\n", pin_types[pin->type]);
|
||||
else
|
||||
printf("\tType : [encoding %d]\n", pin->type);
|
||||
if (pin->auth_type == SC_PKCS15_PIN_AUTH_TYPE_PIN) {
|
||||
printf("\tFlags : [0x%02X]", pin->attrs.pin.flags);
|
||||
for (i = 0; i < pf_count; i++)
|
||||
if (pin->attrs.pin.flags & (1 << i)) {
|
||||
printf(", %s", pin_flags[i]);
|
||||
}
|
||||
printf("\n");
|
||||
printf("\tLength : min_len:%lu, max_len:%lu, stored_len:%lu\n",
|
||||
(unsigned long)pin->attrs.pin.min_length, (unsigned long)pin->attrs.pin.max_length,
|
||||
(unsigned long)pin->attrs.pin.stored_length);
|
||||
printf("\tPad char : 0x%02X\n", pin->attrs.pin.pad_char);
|
||||
printf("\tReference : %d\n", pin->attrs.pin.reference);
|
||||
if (pin->attrs.pin.type < NELEMENTS(pin_types))
|
||||
printf("\tType : %s\n", pin_types[pin->attrs.pin.type]);
|
||||
else
|
||||
printf("\tType : [encoding %d]\n", pin->attrs.pin.type);
|
||||
}
|
||||
if (pin->path.len || pin->path.aid.len)
|
||||
printf("\tPath : %s\n", sc_print_path(&pin->path));
|
||||
if (pin->tries_left >= 0)
|
||||
@ -1184,7 +1191,7 @@ static int dump(void)
|
||||
|
||||
static int unblock_pin(void)
|
||||
{
|
||||
struct sc_pkcs15_pin_info *pinfo = NULL;
|
||||
struct sc_pkcs15_auth_info *pinfo = NULL;
|
||||
sc_pkcs15_object_t *pin_obj;
|
||||
u8 *pin, *puk;
|
||||
int r, pinpad_present = 0;
|
||||
@ -1193,7 +1200,10 @@ static int unblock_pin(void)
|
||||
|
||||
if (!(pin_obj = get_pin_info()))
|
||||
return 2;
|
||||
pinfo = (sc_pkcs15_pin_info_t *) pin_obj->data;
|
||||
pinfo = (sc_pkcs15_auth_info_t *) pin_obj->data;
|
||||
|
||||
if (pinfo->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return 1;
|
||||
|
||||
puk = opt_puk;
|
||||
if (puk == NULL) {
|
||||
@ -1248,7 +1258,7 @@ static int unblock_pin(void)
|
||||
static int change_pin(void)
|
||||
{
|
||||
sc_pkcs15_object_t *pin_obj;
|
||||
sc_pkcs15_pin_info_t *pinfo = NULL;
|
||||
sc_pkcs15_auth_info_t *pinfo = NULL;
|
||||
u8 *pincode, *newpin;
|
||||
int r, pinpad_present = 0;
|
||||
|
||||
@ -1256,7 +1266,10 @@ static int change_pin(void)
|
||||
|
||||
if (!(pin_obj = get_pin_info()))
|
||||
return 2;
|
||||
pinfo = (sc_pkcs15_pin_info_t *) pin_obj->data;
|
||||
|
||||
pinfo = (sc_pkcs15_auth_info_t *) pin_obj->data;
|
||||
if (pinfo->auth_type != SC_PKCS15_PIN_AUTH_TYPE_PIN)
|
||||
return 1;
|
||||
|
||||
if (pinfo->tries_left != -1) {
|
||||
if (pinfo->tries_left != pinfo->max_tries) {
|
||||
|
Loading…
Reference in New Issue
Block a user