- Checkpoint commit, add support for the next generation FinEID

cards with ISO/IEC 7816-15 layout.


git-svn-id: https://www.opensc-project.org/svnp/opensc/trunk@2161 c6295689-39f2-0310-b995-f0e70906c6a9
This commit is contained in:
aet 2005-02-09 11:37:25 +00:00
parent ece96aff98
commit 91fb274b1a
1 changed files with 74 additions and 14 deletions

View File

@ -2,6 +2,7 @@
* card-setcos.c: Support for PKI cards by Setec
*
* Copyright (C) 2001, 2002 Juha Yrjölä <juha.yrjola@iki.fi>
* Copyright (C) 2005 Antti Tapaninen <aet@cc.hut.fi>
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
@ -24,14 +25,26 @@
#define TYPE_GENERIC 0
#define TYPE_PKI 1
#define TYPE_FINEID 2
static struct sc_atr_table setcos_atrs[] = {
/* this is from a Nokia branded SC */
{ "3B:1F:11:00:67:80:42:46:49:53:45:10:52:66:FF:81:90:00", NULL, TYPE_GENERIC },
/* some Nokia branded SC */
{ "3B:1F:11:00:67:80:42:46:49:53:45:10:52:66:FF:81:90:00", NULL, NULL, TYPE_GENERIC },
/* RSA SecurID 3100 */
{ "3B:9F:94:40:1E:00:67:16:43:46:49:53:45:10:52:66:FF:81:90:00", NULL, TYPE_PKI },
/* FinEID card */
{ "3B:9F:94:40:1E:00:67:11:43:46:49:53:45:10:52:66:FF:81:90:00", NULL, TYPE_PKI },
{ "3B:9F:94:40:1E:00:67:16:43:46:49:53:45:10:52:66:FF:81:90:00", NULL, NULL, TYPE_PKI },
/* FINEID 1016 (SetCOS 4.3.1B3/PKCS#15, VRK) */
{ "3b:9f:94:40:1e:00:67:00:43:46:49:53:45:10:52:66:ff:81:90:00", "ff:ff:ff:ff:ff:ff:ff:00:ff:ff:ff:ff:ff:ff:ff:ff:ff:ff:ff:ff", NULL, TYPE_FINEID },
/* FINEID 2032 (EIDApplet/7816-15, test) */
{ "3b:6b:00:ff:80:62:00:a2:56:46:69:6e:45:49:44", "ff:ff:00:ff:ff:ff:00:ff:ff:ff:ff:ff:ff:ff:ff", NULL, TYPE_FINEID },
/* FINEID 2132 (EIDApplet/7816-15, OPK/EMV test) */
{ "3b:64:00:ff:80:62:00:a2", "ff:ff:00:ff:ff:ff:00:ff", NULL, TYPE_FINEID },
/* FINEID 2064 (EIDApplet/7816-15, VRK) */
{ "3b:7b:00:00:00:80:62:00:51:56:46:69:6e:45:49:44", "ff:ff:00:ff:ff:ff:ff:f0:ff:ff:ff:ff:ff:ff:ff:ff", NULL, TYPE_FINEID },
/* FINEID 2164 (EIDApplet/7816-15, OPK/EMV) */
{ "3b:64:00:00:80:62:00:51", "ff:ff:ff:ff:ff:ff:f0:ff", NULL, TYPE_FINEID },
/* FINEID 2264 (EIDApplet/7816-15, OPK/EMV/AVANT) */
{ "3b:6e:00:00:00:62:00:00:57:41:56:41:4e:54:10:81:90:00", "ff:ff:ff:ff:ff:ff:ff:ff:ff:ff:ff:ff:ff:ff:ff:ff:ff:ff", NULL, TYPE_FINEID },
{ NULL }
};
@ -47,32 +60,79 @@ static int setcos_finish(struct sc_card *card)
return 0;
}
static int match_hist_bytes(struct sc_card *card, const char *str, size_t len)
{
const char *src = (const char *) card->slot->atr_info.hist_bytes;
size_t srclen = card->slot->atr_info.hist_bytes_len;
size_t offset = 0;
if (len == 0)
len = strlen(str);
if (srclen < len)
return 0;
while (srclen - offset > len) {
if (memcmp(src + offset, str, len) == 0) {
return 1;
}
offset++;
}
return 0;
}
static int setcos_match_card(struct sc_card *card)
{
int i;
i = _sc_match_atr(card, setcos_atrs, &card->type);
if (i < 0) {
const u8 *hist_bytes = card->slot->atr_info.hist_bytes;
if (card->slot->atr_info.hist_bytes_len < 8)
return 0;
if (memcmp(hist_bytes + 4, "FISE", 4) == 0)
/* Unknown card, but has the FinEID application for sure */
if (match_hist_bytes(card, "FinEID", 0)) {
card->type = TYPE_FINEID;
return 1;
}
if (match_hist_bytes(card, "FISE", 0)) {
card->type = TYPE_GENERIC;
return 1;
}
return 0;
}
return 1;
}
static int select_fineid_app(sc_card_t * card)
{
sc_path_t app;
int r;
/* Regular PKCS#15 AID */
sc_format_path ("A000000063504B43532D3135", &app);
app.type = SC_PATH_TYPE_DF_NAME;
card->ctx->suppress_errors++;
r = sc_select_file (card, &app, NULL);
card->ctx->suppress_errors--;
return r;
}
static int setcos_init(struct sc_card *card)
{
card->name = "SetCOS";
card->cla = 0x80;
if (card->type < 0)
card->type = TYPE_GENERIC;
if (card->type == TYPE_PKI) {
/* Handle unknown or forced cards */
if (card->type < 0) {
#if 1
/* Hmm. For now, assume it's a bank card with FinEID application */
if (match_hist_bytes(card, "AVANT", 0)) {
card->type = TYPE_FINEID;
} else
#endif
card->type = TYPE_GENERIC;
}
if (card->type == TYPE_FINEID) {
card->cla = 0x00;
select_fineid_app(card);
}
if (card->type == TYPE_PKI || card->type == TYPE_FINEID) {
unsigned long flags;
flags = SC_ALGORITHM_RSA_RAW | SC_ALGORITHM_RSA_PAD_PKCS1;