Merge remote-tracking branch 'upstream/master' into winui

This commit is contained in:
Frank Morgner 2017-10-16 15:16:34 +02:00
commit 498aedd165
43 changed files with 1755 additions and 657 deletions

View File

@ -82,7 +82,10 @@ build_script:
# build libeac.lib as a static library
xcopy C:\openpace C:\openpace-${env:OPENSSL_PF} /e /i /y /s
cd C:\openpace-${env:OPENSSL_PF}\src
cl /IC:\OpenSSL-${env:OPENSSL_PF}\include /I. /DX509DIR=\`"/\`" /DCVCDIR=\`"/\`" /W3 /D_CRT_SECURE_NO_DEPRECATE /DWIN32_LEAN_AND_MEAN /GS /MT /DHAVE_ASN1_STRING_GET0_DATA=1 /DHAVE_DECL_OPENSSL_ZALLOC=1 /DHAVE_DH_GET0_KEY=1 /DHAVE_DH_GET0_PQG=1 /DHAVE_DH_SET0_KEY=1 /DHAVE_DH_SET0_PQG=1 /DHAVE_ECDSA_SIG_GET0=1 /DHAVE_ECDSA_SIG_SET0=1 /DHAVE_EC_KEY_METHOD=1 /DHAVE_RSA_GET0_KEY=1 /DHAVE_RSA_SET0_KEY=1 /c ca_lib.c cv_cert.c cvc_lookup.c x509_lookup.c eac_asn1.c eac.c eac_ca.c eac_dh.c eac_ecdh.c eac_kdf.c eac_lib.c eac_print.c eac_util.c misc.c pace.c pace_lib.c pace_mappings.c ri.c ri_lib.c ta.c ta_lib.c objects.c ssl_compat.c
# OpenSSL 1.1.0
#cl /IC:\OpenSSL-${env:OPENSSL_PF}\include /I. /DX509DIR=\`"/\`" /DCVCDIR=\`"/\`" /W3 /D_CRT_SECURE_NO_DEPRECATE /DWIN32_LEAN_AND_MEAN /GS /MT /DHAVE_ASN1_STRING_GET0_DATA=1 /DHAVE_DECL_OPENSSL_ZALLOC=1 /DHAVE_DH_GET0_KEY=1 /DHAVE_DH_GET0_PQG=1 /DHAVE_DH_SET0_KEY=1 /DHAVE_DH_SET0_PQG=1 /DHAVE_ECDSA_SIG_GET0=1 /DHAVE_ECDSA_SIG_SET0=1 /DHAVE_EC_KEY_METHOD=1 /DHAVE_RSA_GET0_KEY=1 /DHAVE_RSA_SET0_KEY=1 /c ca_lib.c cv_cert.c cvc_lookup.c x509_lookup.c eac_asn1.c eac.c eac_ca.c eac_dh.c eac_ecdh.c eac_kdf.c eac_lib.c eac_print.c eac_util.c misc.c pace.c pace_lib.c pace_mappings.c ri.c ri_lib.c ta.c ta_lib.c objects.c ssl_compat.c
# OpenSSL 1.0.2
cl /IC:\OpenSSL-${env:OPENSSL_PF}\include /I. /DX509DIR=\`"/\`" /DCVCDIR=\`"/\`" /W3 /D_CRT_SECURE_NO_DEPRECATE /DWIN32_LEAN_AND_MEAN /GS /MT /c ca_lib.c cv_cert.c cvc_lookup.c x509_lookup.c eac_asn1.c eac.c eac_ca.c eac_dh.c eac_ecdh.c eac_kdf.c eac_lib.c eac_print.c eac_util.c misc.c pace.c pace_lib.c pace_mappings.c ri.c ri_lib.c ta.c ta_lib.c objects.c ssl_compat.c
lib /out:libeac.lib ca_lib.obj cv_cert.obj cvc_lookup.obj x509_lookup.obj eac_asn1.obj eac.obj eac_ca.obj eac_dh.obj eac_ecdh.obj eac_kdf.obj eac_lib.obj eac_print.obj eac_util.obj misc.obj pace.obj pace_lib.obj pace_mappings.obj ri.obj ri_lib.obj ta.obj ta_lib.obj objects.obj ssl_compat.obj
cd C:\projects\OpenSC
}

View File

@ -862,7 +862,11 @@ if test "${enable_sm}" = "yes"; then
fi
if test "${with_pkcs11_provider}" = "detect"; then
DEFAULT_PKCS11_PROVIDER="opensc-pkcs11${DYN_LIB_EXT}"
if test "${WIN32}" != "yes"; then
DEFAULT_PKCS11_PROVIDER="opensc-pkcs11${DYN_LIB_EXT}"
else
DEFAULT_PKCS11_PROVIDER="%PROGRAMFILES%\\\OpenSC Project\\\OpenSC\\\pkcs11\\\opensc-pkcs11.dll"
fi
else
DEFAULT_PKCS11_PROVIDER="${with_pkcs11_provider}"
fi

View File

@ -71,6 +71,14 @@
<listitem><para>Hash some data.</para></listitem>
</varlistentry>
<varlistentry>
<term>
<option>--hash-algorithm</option> <replaceable>mechanism</replaceable>
</term>
<listitem><para>Specify hash algorithm used with
RSA-PKCS-PSS signature. Default is SHA-1.</para></listitem>
</varlistentry>
<varlistentry>
<term>
<option>--id</option> <replaceable>id</replaceable>,
@ -116,7 +124,7 @@
<varlistentry>
<term>
<option>--key-type</option> <replacement>specification</replacement>
<option>--key-type</option> <replaceable>specification</replaceable>
</term>
<listitem><para>Specify the type and length of the key to create, for example rsa:1024 or EC:prime256v1.</para></listitem>
</varlistentry>
@ -212,6 +220,17 @@
of mechanisms supported by your token.</para></listitem>
</varlistentry>
<varlistentry>
<term>
<option>--mgf</option> <replaceable>function</replaceable>
</term>
<listitem><para>Use the specified Message Generation
Function (MGF) <replaceable>function</replaceable>
for RSA-PSS signatures. Supported arguments are MGF1-SHA1
to MGF1-SHA512 if supported by the driver.
The default is based on the hash selection.</para></listitem>
</varlistentry>
<varlistentry>
<term>
<option>--module</option> <replaceable>mod</replaceable>
@ -309,6 +328,17 @@
<listitem><para>Derive a secret key using another key and some data.</para></listitem>
</varlistentry>
<varlistentry>
<term>
<option>--salt-len</option> <replaceable>bytes</replaceable>
</term>
<listitem><para>Specify how many bytes of salt should
be used in RSA-PSS signatures. Accepts two special values:
"-1" means salt length equals to digest length,
"-2" means use maximum permissible length.
Default is digest length (-1).</para></listitem>
</varlistentry>
<varlistentry>
<term>
<option>--slot</option> <replaceable>id</replaceable>

View File

@ -1160,6 +1160,11 @@ app tokend {
# Default: 300
#
# score = 10;
# Tokend ignore to read PIN protected certificate that is set SC_PKCS15_CO_FLAG_PRIVATE flag.
# Default: true
#
# ignore_private_certificate = false;
}
}

View File

@ -390,9 +390,7 @@ static int cac_apdu_io(sc_card_t *card, int ins, int p1, int p2,
goto err;
}
if (apdu.sw1 == 0x61) {
r = sc_check_sw(card, apdu.sw1, apdu.sw2);
}
r = sc_check_sw(card, apdu.sw1, apdu.sw2);
if (r < 0) {
sc_debug(card->ctx, SC_LOG_DEBUG_NORMAL, "Card returned error ");
@ -606,9 +604,14 @@ static int cac_read_binary(sc_card_t *card, unsigned int idx,
/* SPICE smart card emulator only presents CAC-1 cards with the old CAC-1 interface as
* certs. If we are a cac 1 card, use the old interface */
r = cac_cac1_get_certificate(card, &val, &val_len);
if (r < 0)
if (r == SC_ERROR_INS_NOT_SUPPORTED) {
/* The CACv1 instruction is not recognized. Try with CACv2 */
card->type = SC_CARD_TYPE_CAC_II;
} else if (r < 0)
goto done;
}
if ((card->type == SC_CARD_TYPE_CAC_I) && (priv->object_type == CAC_OBJECT_TYPE_CERT)) {
r = cac_cac1_get_cert_tag(card, val_len, &tl, &tl_len);
if (r < 0)
goto done;
@ -1106,6 +1109,7 @@ static int cac_select_file_by_type(sc_card_t *card, const sc_path_t *in_path, sc
r = sc_check_sw(card, apdu.sw1, apdu.sw2);
if (apdu.sw1 == 0x6A && apdu.sw2 == 0x86) {
apdu.p2 = 0x00;
apdu.resplen = sizeof(buf);
if (sc_transmit_apdu(card, &apdu) == SC_SUCCESS)
r = sc_check_sw(card, apdu.sw1, apdu.sw2);
}

View File

@ -59,6 +59,7 @@ static struct sc_atr_table cardos_atrs[] = {
/* CardOS v5.0 */
{ "3b:d2:18:00:81:31:fe:58:c9:01:14", NULL, NULL, SC_CARD_TYPE_CARDOS_V5_0, 0, NULL},
/* CardOS v5.3 */
{ "3b:d2:18:00:81:31:fe:58:c9:02:17", NULL, NULL, SC_CARD_TYPE_CARDOS_V5_0, 0, NULL},
{ "3b:d2:18:00:81:31:fe:58:c9:03:16", NULL, NULL, SC_CARD_TYPE_CARDOS_V5_0, 0, NULL},
{ NULL, NULL, NULL, 0, 0, NULL }
};
@ -171,7 +172,7 @@ static int cardos_init(sc_card_t *card)
sc_apdu_t apdu;
u8 rbuf[2];
card->name = "CardOS M4";
card->name = "Atos CardOS";
card->cla = 0x00;
/* Set up algorithm info. */

View File

@ -98,6 +98,8 @@ typedef struct epass2003_exdata_st {
unsigned char sk_enc[16]; /* encrypt session key */
unsigned char sk_mac[16]; /* mac session key */
unsigned char icv_mac[16]; /* instruction counter vector(for sm) */
unsigned char currAlg; /* current Alg */
unsigned int ecAlgFlags; /* Ec Alg mechanism type*/
} epass2003_exdata;
#define REVERSE_ORDER4(x) ( \
@ -170,6 +172,7 @@ static const struct sc_card_error epass2003_errors[] = {
static int epass2003_transmit_apdu(struct sc_card *card, struct sc_apdu *apdu);
static int epass2003_select_file(struct sc_card *card, const sc_path_t * in_path, sc_file_t ** file_out);
int epass2003_refresh(struct sc_card *card);
static int hash_data(const unsigned char *data, size_t datalen, unsigned char *hash, unsigned int mechanismType);
static int
epass2003_check_sw(struct sc_card *card, unsigned int sw1, unsigned int sw2)
@ -403,6 +406,12 @@ sha1_digest(const unsigned char *input, size_t length, unsigned char *output)
return openssl_dig(EVP_sha1(), input, length, output);
}
static int
sha256_digest(const unsigned char *input, size_t length, unsigned char *output)
{
return openssl_dig(EVP_sha256(), input, length, output);
}
static int
gen_init_key(struct sc_card *card, unsigned char *key_enc, unsigned char *key_mac,
@ -1140,6 +1149,7 @@ static int
epass2003_init(struct sc_card *card)
{
unsigned int flags;
unsigned int ext_flags;
unsigned char data[SC_MAX_APDU_BUFFER_SIZE] = { 0 };
size_t datalen = SC_MAX_APDU_BUFFER_SIZE;
epass2003_exdata *exdata = NULL;
@ -1192,6 +1202,11 @@ epass2003_init(struct sc_card *card)
_sc_card_add_rsa_alg(card, 1024, flags, 0);
_sc_card_add_rsa_alg(card, 2048, flags, 0);
//set EC Alg Flags
flags = SC_ALGORITHM_ONBOARD_KEY_GEN|SC_ALGORITHM_ECDSA_HASH_SHA1|SC_ALGORITHM_ECDSA_HASH_SHA256|SC_ALGORITHM_ECDSA_HASH_NONE|SC_ALGORITHM_ECDSA_RAW;
ext_flags = 0;
_sc_card_add_ec_alg(card, 256, flags, ext_flags, NULL);
card->caps = SC_CARD_CAP_RNG | SC_CARD_CAP_APDU_EXT;
LOG_FUNC_RETURN(card->ctx, SC_SUCCESS);
@ -1561,6 +1576,13 @@ epass2003_set_security_env(struct sc_card *card, const sc_security_env_t * env,
u8 *p;
unsigned short fid = 0;
int r, locked = 0;
epass2003_exdata *exdata = NULL;
if (!card->drv_data)
return SC_ERROR_INVALID_ARGUMENTS;
exdata = (epass2003_exdata *)card->drv_data;
exdata->currAlg = SC_ALGORITHM_RSA; //default algorithm
sc_format_apdu(card, &apdu, SC_APDU_CASE_3_SHORT, 0x22, 0x41, 0);
switch (env->operation) {
@ -1590,6 +1612,28 @@ epass2003_set_security_env(struct sc_card *card, const sc_security_env_t * env,
apdu.lc = r;
apdu.datalen = r;
apdu.data = sbuf;
if (env->algorithm == SC_ALGORITHM_EC)
{
apdu.p2 = 0xB6;
exdata->currAlg = SC_ALGORITHM_EC;
if(env->algorithm_flags | SC_ALGORITHM_ECDSA_HASH_SHA1)
{
sbuf[2] = 0x91;
exdata->ecAlgFlags = SC_ALGORITHM_ECDSA_HASH_SHA1;
}
else if (env->algorithm_flags | SC_ALGORITHM_ECDSA_HASH_SHA256)
{
sbuf[2] = 0x92;
exdata->ecAlgFlags = SC_ALGORITHM_ECDSA_HASH_SHA256;
}
else
{
sc_log(card->ctx, "%0x Alg Not Support! ", env->algorithm_flags);
goto err;
}
}
if (se_num > 0) {
r = sc_lock(card);
LOG_TEST_RET(card->ctx, r, "sc_lock() failed");
@ -1640,7 +1684,55 @@ static int epass2003_decipher(struct sc_card *card, const u8 * data, size_t data
struct sc_apdu apdu;
u8 rbuf[SC_MAX_APDU_BUFFER_SIZE] = { 0 };
u8 sbuf[SC_MAX_APDU_BUFFER_SIZE] = { 0 };
epass2003_exdata *exdata = NULL;
LOG_FUNC_CALLED(card->ctx);
if (!card->drv_data)
return SC_ERROR_INVALID_ARGUMENTS;
exdata = (epass2003_exdata *)card->drv_data;
if(exdata->currAlg == SC_ALGORITHM_EC)
{
unsigned char hash[HASH_LEN] = { 0 };
if(exdata->ecAlgFlags | SC_ALGORITHM_ECDSA_HASH_SHA1)
{
hash_data(data, datalen, hash, SC_ALGORITHM_ECDSA_HASH_SHA1);
sc_format_apdu(card, &apdu, SC_APDU_CASE_3,0x2A, 0x9E, 0x9A);
memset(sbuf, 0, sizeof(sbuf));
memcpy(sbuf, hash, 0x14);
apdu.data = sbuf;
apdu.lc = 0x14;
apdu.datalen = 0x14;
}
else if (exdata->ecAlgFlags | SC_ALGORITHM_ECDSA_HASH_SHA256)
{
hash_data(data, datalen, hash, SC_ALGORITHM_ECDSA_HASH_SHA256);
sc_format_apdu(card, &apdu, SC_APDU_CASE_3,0x2A, 0x9E, 0x9A);
memset(sbuf, 0, sizeof(sbuf));
memcpy(sbuf, hash, 0x20);
apdu.data = sbuf;
apdu.lc = 0x20;
apdu.datalen = 0x20;
}
else
{
return SC_ERROR_NOT_SUPPORTED;
}
apdu.resp = rbuf;
apdu.resplen = sizeof(rbuf);
apdu.le = 0;
r = sc_transmit_apdu_t(card, &apdu);
LOG_TEST_RET(card->ctx, r, "APDU transmit failed");
if (apdu.sw1 == 0x90 && apdu.sw2 == 0x00) {
size_t len = apdu.resplen > outlen ? outlen : apdu.resplen;
memcpy(out, apdu.resp, len);
LOG_FUNC_RETURN(card->ctx, len);
}
LOG_FUNC_RETURN(card->ctx, sc_check_sw(card, apdu.sw1, apdu.sw2));
}
sc_format_apdu(card, &apdu, SC_APDU_CASE_4_EXT, 0x2A, 0x80, 0x86);
apdu.resp = rbuf;
apdu.resplen = sizeof(rbuf);
@ -1862,11 +1954,13 @@ epass2003_construct_fci(struct sc_card *card, const sc_file_t * file,
}
else if (file->type == SC_FILE_TYPE_INTERNAL_EF) {
if (file->ef_structure == SC_CARDCTL_OBERTHUR_KEY_RSA_CRT) {
if (file->ef_structure == SC_CARDCTL_OBERTHUR_KEY_RSA_CRT ||
file->ef_structure == SC_CARDCTL_OBERTHUR_KEY_EC_CRT) {
buf[0] = 0x11;
buf[1] = 0x00;
}
else if (file->ef_structure == SC_CARDCTL_OBERTHUR_KEY_RSA_PUBLIC) {
else if (file->ef_structure == SC_CARDCTL_OBERTHUR_KEY_RSA_PUBLIC ||
file->ef_structure == SC_CARDCTL_OBERTHUR_KEY_EC_PUBLIC) {
buf[0] = 0x12;
buf[1] = 0x00;
}
@ -1903,7 +1997,9 @@ epass2003_construct_fci(struct sc_card *card, const sc_file_t * file,
}
else if (file->type == SC_FILE_TYPE_INTERNAL_EF) {
if (file->ef_structure == SC_CARDCTL_OBERTHUR_KEY_RSA_CRT ||
file->ef_structure == SC_CARDCTL_OBERTHUR_KEY_RSA_PUBLIC) {
file->ef_structure == SC_CARDCTL_OBERTHUR_KEY_RSA_PUBLIC||
file->ef_structure == SC_CARDCTL_OBERTHUR_KEY_EC_CRT||
file->ef_structure == SC_CARDCTL_OBERTHUR_KEY_EC_PUBLIC) {
buf[0] = (file->size >> 8) & 0xFF;
buf[1] = file->size & 0xFF;
sc_asn1_put_tag(0x85, buf, 2, p, *outlen - (p - out), &p);
@ -1942,13 +2038,14 @@ epass2003_construct_fci(struct sc_card *card, const sc_file_t * file,
ops[3] = SC_AC_OP_DELETE;
}
else if (file->type == SC_FILE_TYPE_INTERNAL_EF) {
if (file->ef_structure ==
SC_CARDCTL_OBERTHUR_KEY_RSA_CRT) {
if (file->ef_structure == SC_CARDCTL_OBERTHUR_KEY_RSA_CRT ||
file->ef_structure == SC_CARDCTL_OBERTHUR_KEY_EC_CRT) {
ops[1] = SC_AC_OP_UPDATE;
ops[2] = SC_AC_OP_CRYPTO;
ops[3] = SC_AC_OP_DELETE;
}
else if (file->ef_structure == SC_CARDCTL_OBERTHUR_KEY_RSA_PUBLIC) {
else if (file->ef_structure == SC_CARDCTL_OBERTHUR_KEY_RSA_PUBLIC||
file->ef_structure == SC_CARDCTL_OBERTHUR_KEY_EC_PUBLIC) {
ops[0] = SC_AC_OP_READ;
ops[1] = SC_AC_OP_UPDATE;
ops[2] = SC_AC_OP_CRYPTO;
@ -1973,13 +2070,22 @@ epass2003_construct_fci(struct sc_card *card, const sc_file_t * file,
buf[ii] = rv;
}
sc_asn1_put_tag(0x86, buf, sizeof(ops), p, *outlen - (p - out), &p);
if(file->size == 256)
{
out[4]= 0x13;
}
}
/* VT ??? */
if (file->ef_structure == SC_CARDCTL_OBERTHUR_KEY_RSA_PUBLIC) {
if (file->ef_structure == SC_CARDCTL_OBERTHUR_KEY_RSA_PUBLIC||
file->ef_structure == SC_CARDCTL_OBERTHUR_KEY_EC_PUBLIC) {
unsigned char data[2] = {0x00, 0x66};
sc_asn1_put_tag(0x87, data, sizeof(data), p, *outlen - (p - out), &p);
if(file->size == 256)
{
out[4]= 0x14;
}
}
out[1] = p - out - 2;
@ -2129,19 +2235,36 @@ internal_write_rsa_key(struct sc_card *card, unsigned short fid, struct sc_pkcs1
static int
hash_data(unsigned char *data, size_t datalen, unsigned char *hash)
hash_data(const unsigned char *data, size_t datalen, unsigned char *hash, unsigned int mechanismType)
{
unsigned char data_hash[24] = { 0 };
size_t len = 0;
if ((NULL == data) || (NULL == hash))
return SC_ERROR_INVALID_ARGUMENTS;
sha1_digest(data, datalen, data_hash);
if(mechanismType | SC_ALGORITHM_ECDSA_HASH_SHA1)
{
unsigned char data_hash[24] = { 0 };
size_t len = 0;
len = REVERSE_ORDER4(datalen);
memcpy(&data_hash[20], &len, 4);
memcpy(hash, data_hash, 24);
sha1_digest(data, datalen, data_hash);
len = REVERSE_ORDER4(datalen);
memcpy(&data_hash[20], &len, 4);
memcpy(hash, data_hash, 24);
}
else if(mechanismType | SC_ALGORITHM_ECDSA_HASH_SHA256)
{
unsigned char data_hash[36] = { 0 };
size_t len = 0;
sha256_digest(data, datalen, data_hash);
len = REVERSE_ORDER4(datalen);
memcpy(&data_hash[32], &len, 4);
memcpy(hash, data_hash, 36);
}
else
{
return SC_ERROR_NOT_SUPPORTED;
}
return SC_SUCCESS;
}
@ -2214,7 +2337,7 @@ internal_install_pin(struct sc_card *card, sc_epass2003_wkey_data * pin)
int r;
unsigned char hash[HASH_LEN] = { 0 };
r = hash_data(pin->key_data.es_secret.key_val, pin->key_data.es_secret.key_len, hash);
r = hash_data(pin->key_data.es_secret.key_val, pin->key_data.es_secret.key_len, hash, SC_ALGORITHM_ECDSA_HASH_SHA1);
LOG_TEST_RET(card->ctx, r, "hash data failed");
r = install_secret_key(card, 0x04, pin->key_data.es_secret.kid,
@ -2265,7 +2388,14 @@ epass2003_gen_key(struct sc_card *card, sc_epass2003_gen_key_data * data)
LOG_FUNC_CALLED(card->ctx);
sbuf[0] = 0x01;
if(len == 256)
{
sbuf[0] = 0x02;
}
else
{
sbuf[0] = 0x01;
}
sbuf[1] = (u8) ((len >> 8) & 0xff);
sbuf[2] = (u8) (len & 0xff);
sbuf[3] = (u8) ((data->prkey_id >> 8) & 0xFF);
@ -2285,6 +2415,10 @@ epass2003_gen_key(struct sc_card *card, sc_epass2003_gen_key_data * data)
/* read public key */
sc_format_apdu(card, &apdu, SC_APDU_CASE_3_SHORT, 0xb4, 0x02, 0x00);
if(len == 256)
{
apdu.p1 = 0x00;
}
apdu.cla = 0x80;
apdu.lc = apdu.datalen = 2;
apdu.data = &sbuf[5];
@ -2349,6 +2483,7 @@ epass2003_card_ctl(struct sc_card *card, unsigned long cmd, void *ptr)
{
LOG_FUNC_CALLED(card->ctx);
sc_log(card->ctx, "cmd is %0lx", cmd);
switch (cmd) {
case SC_CARDCTL_ENTERSAFE_WRITE_KEY:
return epass2003_write_key(card, (sc_epass2003_wkey_data *) ptr);
@ -2474,7 +2609,7 @@ external_key_auth(struct sc_card *card, unsigned char kid,
r = sc_get_challenge(card, random, 8);
LOG_TEST_RET(card->ctx, r, "get challenge external_key_auth failed");
r = hash_data(data, datalen, hash);
r = hash_data(data, datalen, hash, SC_ALGORITHM_ECDSA_HASH_SHA1);
LOG_TEST_RET(card->ctx, r, "hash data failed");
des3_encrypt_cbc(hash, HASH_LEN, iv, random, 8, tmp_data);
@ -2501,7 +2636,7 @@ update_secret_key(struct sc_card *card, unsigned char ktype, unsigned char kid,
unsigned char tmp_data[256] = { 0 };
unsigned char maxtries = 0;
r = hash_data(data, datalen, hash);
r = hash_data(data, datalen, hash, SC_ALGORITHM_ECDSA_HASH_SHA1);
LOG_TEST_RET(card->ctx, r, "hash data failed");
r = get_external_key_maxtries(card, &maxtries);

View File

@ -1879,13 +1879,13 @@ static int gids_authenticate_admin(sc_card_t *card, u8* key) {
u8 apduSetRandomResponse[256];
u8* randomR2 = apduSetRandomResponse+4;
u8 apduSendReponse[40 + 4] = {0x7C,0x2A,0x82,0x28};
// according to the specification, the z size (z1||z2) should be 14 bytes
// but because the buffer must be a multiple of the 3DES block size (8 bytes), 7 isn't working
u8 z1[8];
u8 buffer[16+16+8];
u8* buffer2 = apduSendReponse + 4;
int buffer2size = 40;
u8 apduSendResponseResponse[256];
u8 buffer3[16+16+8];
int buffer3size = 40;
sc_apdu_t apdu;
const EVP_CIPHER *cipher;
@ -1923,8 +1923,10 @@ static int gids_authenticate_admin(sc_card_t *card, u8* key) {
SC_TEST_RET(card->ctx, SC_LOG_DEBUG_NORMAL, sc_check_sw(card, apdu.sw1, apdu.sw2), "invalid return");
// compute the half size of the mutual authentication secret
r = RAND_bytes(z1, sizeof(z1));
r = RAND_bytes(z1, 7);
SC_TEST_RET(card->ctx, SC_LOG_DEBUG_NORMAL, r, "unable to set computer random");
// set the padding
z1[7] = 0x80;
// Encrypt R2||R1||Z1
memcpy(buffer, randomR2, 16);
@ -1963,6 +1965,47 @@ static int gids_authenticate_admin(sc_card_t *card, u8* key) {
r = sc_transmit_apdu(card, &apdu);
SC_TEST_RET(card->ctx, SC_LOG_DEBUG_NORMAL, r, "APDU transmit failed");
SC_TEST_RET(card->ctx, SC_LOG_DEBUG_NORMAL, sc_check_sw(card, apdu.sw1, apdu.sw2), "invalid return");
if (apdu.resplen != 44)
{
sc_debug(card->ctx, SC_LOG_DEBUG_NORMAL, "Expecting a response len of 44 - found %d",(int) apdu.resplen);
SC_FUNC_RETURN(card->ctx, SC_LOG_DEBUG_NORMAL, SC_ERROR_INTERNAL);
}
// init crypto
ctx = EVP_CIPHER_CTX_new();
if (ctx == NULL) {
SC_FUNC_RETURN(card->ctx, SC_LOG_DEBUG_NORMAL, SC_ERROR_INTERNAL);
}
if (!EVP_DecryptInit(ctx, cipher, key, NULL)) {
EVP_CIPHER_CTX_free(ctx);
SC_FUNC_RETURN(card->ctx, SC_LOG_DEBUG_NORMAL, SC_ERROR_INTERNAL);
}
EVP_CIPHER_CTX_set_padding(ctx,0);
if (!EVP_DecryptUpdate(ctx, buffer3, &buffer3size, apdu.resp + 4, apdu.resplen - 4)) {
sc_debug(card->ctx, SC_LOG_DEBUG_NORMAL, "unable to decrypt data");
EVP_CIPHER_CTX_free(ctx);
SC_FUNC_RETURN(card->ctx, SC_LOG_DEBUG_NORMAL, SC_ERROR_PIN_CODE_INCORRECT);
}
if(!EVP_DecryptFinal(ctx, buffer3+buffer3size, &buffer3size)) {
sc_debug(card->ctx, SC_LOG_DEBUG_NORMAL, "unable to decrypt final data");
EVP_CIPHER_CTX_free(ctx);
SC_FUNC_RETURN(card->ctx, SC_LOG_DEBUG_NORMAL, SC_ERROR_PIN_CODE_INCORRECT);
}
sc_debug(card->ctx, SC_LOG_DEBUG_NORMAL, "data has been decrypted using the key");
if (memcmp(buffer3, randomR1, 16) != 0) {
sc_debug(card->ctx, SC_LOG_DEBUG_NORMAL, "R1 doesn't match");
SC_FUNC_RETURN(card->ctx, SC_LOG_DEBUG_NORMAL, SC_ERROR_PIN_CODE_INCORRECT);
}
if (memcmp(buffer3 + 16, randomR2, 16) != 0) {
sc_debug(card->ctx, SC_LOG_DEBUG_NORMAL, "R2 doesn't match");
SC_FUNC_RETURN(card->ctx, SC_LOG_DEBUG_NORMAL, SC_ERROR_PIN_CODE_INCORRECT);
}
if (buffer[39] != 0x80) {
sc_debug(card->ctx, SC_LOG_DEBUG_NORMAL, "Padding not found");
SC_FUNC_RETURN(card->ctx, SC_LOG_DEBUG_NORMAL, SC_ERROR_PIN_CODE_INCORRECT);
}
EVP_CIPHER_CTX_free(ctx);
ctx = NULL;
SC_FUNC_RETURN(card->ctx, SC_LOG_DEBUG_NORMAL, SC_SUCCESS);
#endif

View File

@ -264,6 +264,9 @@ iasecc_select_mf(struct sc_card *card, struct sc_file **file_out)
apdu.resplen = sizeof(apdu_resp);
apdu.resp = apdu_resp;
if (card->type == SC_CARD_TYPE_IASECC_MI2)
apdu.p2 = 0x04;
rv = sc_transmit_apdu(card, &apdu);
LOG_TEST_RET(card->ctx, rv, "APDU transmit failed");
rv = sc_check_sw(card, apdu.sw1, apdu.sw2);
@ -513,75 +516,21 @@ iasecc_init_oberthur(struct sc_card *card)
}
static int
iasecc_init_sagem(struct sc_card *card)
{
struct sc_context *ctx = card->ctx;
unsigned int flags;
int rv = 0;
LOG_FUNC_CALLED(ctx);
flags = IASECC_CARD_DEFAULT_FLAGS;
_sc_card_add_rsa_alg(card, 1024, flags, 0x10001);
_sc_card_add_rsa_alg(card, 2048, flags, 0x10001);
card->caps = SC_CARD_CAP_RNG;
card->caps |= SC_CARD_CAP_APDU_EXT;
card->caps |= SC_CARD_CAP_USE_FCI_AC;
rv = iasecc_parse_ef_atr(card);
if (rv == SC_ERROR_FILE_NOT_FOUND) {
rv = iasecc_select_mf(card, NULL);
LOG_TEST_RET(ctx, rv, "MF selection error");
rv = iasecc_parse_ef_atr(card);
}
LOG_TEST_RET(ctx, rv, "IASECC: ATR parse failed");
LOG_FUNC_RETURN(ctx, SC_SUCCESS);
}
static int
iasecc_init_amos(struct sc_card *card)
{
struct sc_context *ctx = card->ctx;
unsigned int flags;
int rv = 0;
LOG_FUNC_CALLED(ctx);
flags = IASECC_CARD_DEFAULT_FLAGS;
_sc_card_add_rsa_alg(card, 1024, flags, 0x10001);
_sc_card_add_rsa_alg(card, 2048, flags, 0x10001);
card->caps = SC_CARD_CAP_RNG;
card->caps |= SC_CARD_CAP_APDU_EXT;
card->caps |= SC_CARD_CAP_USE_FCI_AC;
rv = iasecc_parse_ef_atr(card);
if (rv == SC_ERROR_FILE_NOT_FOUND) {
rv = iasecc_select_mf(card, NULL);
LOG_TEST_RET(ctx, rv, "MF selection error");
rv = iasecc_parse_ef_atr(card);
}
LOG_TEST_RET(ctx, rv, "IASECC: ATR parse failed");
LOG_FUNC_RETURN(ctx, SC_SUCCESS);
}
static int
iasecc_mi_match(struct sc_card *card)
{
struct sc_context *ctx = card->ctx;
unsigned char resp[0x100];
size_t resp_len;
int rv = 0;
LOG_FUNC_CALLED(ctx);
if (!card->ef_atr)
resp_len = sizeof(resp);
rv = iasecc_select_aid(card, &MIIASECC_AID, resp, &resp_len);
LOG_TEST_RET(ctx, rv, "IASECC: failed to select MI IAS/ECC applet");
if (!card->ef_atr)
card->ef_atr = calloc(1, sizeof(struct sc_ef_atr));
if (!card->ef_atr)
LOG_FUNC_RETURN(ctx, SC_ERROR_OUT_OF_MEMORY);
@ -592,13 +541,12 @@ iasecc_mi_match(struct sc_card *card)
LOG_FUNC_RETURN(ctx, SC_SUCCESS);
}
static int
iasecc_init_mi(struct sc_card *card)
iasecc_init_amos_or_sagem(struct sc_card *card)
{
struct sc_context *ctx = card->ctx;
unsigned int flags;
unsigned char resp[0x100];
size_t resp_len;
int rv = 0;
LOG_FUNC_CALLED(ctx);
@ -612,16 +560,27 @@ iasecc_init_mi(struct sc_card *card)
card->caps |= SC_CARD_CAP_APDU_EXT;
card->caps |= SC_CARD_CAP_USE_FCI_AC;
resp_len = sizeof(resp);
rv = iasecc_select_aid(card, &MIIASECC_AID, resp, &resp_len);
LOG_TEST_RET(ctx, rv, "Could not select MI's AID");
if (card->type == SC_CARD_TYPE_IASECC_MI) {
rv = iasecc_mi_match(card);
if (rv)
card->type = SC_CARD_TYPE_IASECC_MI2;
else
LOG_FUNC_RETURN(ctx, SC_SUCCESS);
}
rv = iasecc_mi_match(card);
LOG_TEST_RET(ctx, rv, "Could not match MI's AID");
rv = iasecc_parse_ef_atr(card);
if (rv == SC_ERROR_FILE_NOT_FOUND) {
rv = iasecc_select_mf(card, NULL);
LOG_TEST_RET(ctx, rv, "MF selection error");
rv = iasecc_parse_ef_atr(card);
}
LOG_TEST_RET(ctx, rv, "IASECC: ATR parse failed");
LOG_FUNC_RETURN(ctx, SC_SUCCESS);
}
static int
iasecc_init(struct sc_card *card)
{
@ -642,11 +601,11 @@ iasecc_init(struct sc_card *card)
else if (card->type == SC_CARD_TYPE_IASECC_OBERTHUR)
rv = iasecc_init_oberthur(card);
else if (card->type == SC_CARD_TYPE_IASECC_SAGEM)
rv = iasecc_init_sagem(card);
rv = iasecc_init_amos_or_sagem(card);
else if (card->type == SC_CARD_TYPE_IASECC_AMOS)
rv = iasecc_init_amos(card);
rv = iasecc_init_amos_or_sagem(card);
else if (card->type == SC_CARD_TYPE_IASECC_MI)
rv = iasecc_init_mi(card);
rv = iasecc_init_amos_or_sagem(card);
else
LOG_FUNC_RETURN(ctx, SC_ERROR_NO_CARD_SUPPORT);
@ -950,7 +909,8 @@ iasecc_select_file(struct sc_card *card, const struct sc_path *path,
&& card->type != SC_CARD_TYPE_IASECC_OBERTHUR
&& card->type != SC_CARD_TYPE_IASECC_SAGEM
&& card->type != SC_CARD_TYPE_IASECC_AMOS
&& card->type != SC_CARD_TYPE_IASECC_MI)
&& card->type != SC_CARD_TYPE_IASECC_MI
&& card->type != SC_CARD_TYPE_IASECC_MI2)
LOG_TEST_RET(ctx, SC_ERROR_NOT_SUPPORTED, "Unsupported card");
if (lpath.type == SC_PATH_TYPE_FILE_ID) {
@ -963,6 +923,8 @@ iasecc_select_file(struct sc_card *card, const struct sc_path *path,
apdu.p2 = 0x04;
if (card->type == SC_CARD_TYPE_IASECC_MI)
apdu.p2 = 0x04;
if (card->type == SC_CARD_TYPE_IASECC_MI2)
apdu.p2 = 0x04;
}
else if (lpath.type == SC_PATH_TYPE_FROM_CURRENT) {
apdu.p1 = 0x09;
@ -972,6 +934,8 @@ iasecc_select_file(struct sc_card *card, const struct sc_path *path,
apdu.p2 = 0x04;
if (card->type == SC_CARD_TYPE_IASECC_MI)
apdu.p2 = 0x04;
if (card->type == SC_CARD_TYPE_IASECC_MI2)
apdu.p2 = 0x04;
}
else if (lpath.type == SC_PATH_TYPE_PARENT) {
apdu.p1 = 0x03;
@ -982,6 +946,8 @@ iasecc_select_file(struct sc_card *card, const struct sc_path *path,
apdu.p1 = 0x04;
if (card->type == SC_CARD_TYPE_IASECC_AMOS)
apdu.p2 = 0x04;
if (card->type == SC_CARD_TYPE_IASECC_MI2)
apdu.p2 = 0x04;
}
else {
sc_log(ctx, "Invalid PATH type: 0x%X", lpath.type);

View File

@ -68,62 +68,62 @@ static struct sc_atr_table sc_hsm_atrs[] = {
{
"3B:84:80:01:47:6f:49:44:00",
"FF:FF:FF:FF:FF:FF:FF:FF:00",
"GoID", SC_CARD_TYPE_SC_HSM_SOC, 0, NULL
"GoID", SC_CARD_TYPE_SC_HSM_GOID, 0, NULL
},
{
"3B:85:80:01:47:6f:49:44:00:00",
"FF:FF:FF:FF:FF:FF:FF:FF:00:00",
"GoID", SC_CARD_TYPE_SC_HSM_SOC, 0, NULL
"GoID", SC_CARD_TYPE_SC_HSM_GOID, 0, NULL
},
{
"3B:86:80:01:47:6f:49:44:00:00:00",
"FF:FF:FF:FF:FF:FF:FF:FF:00:00:00",
"GoID", SC_CARD_TYPE_SC_HSM_SOC, 0, NULL
"GoID", SC_CARD_TYPE_SC_HSM_GOID, 0, NULL
},
{
"3B:87:80:01:47:6f:49:44:00:00:00:00",
"FF:FF:FF:FF:FF:FF:FF:FF:00:00:00:00",
"GoID", SC_CARD_TYPE_SC_HSM_SOC, 0, NULL
"GoID", SC_CARD_TYPE_SC_HSM_GOID, 0, NULL
},
{
"3B:88:80:01:47:6f:49:44:00:00:00:00:00",
"FF:FF:FF:FF:FF:FF:FF:FF:00:00:00:00:00",
"GoID", SC_CARD_TYPE_SC_HSM_SOC, 0, NULL
"GoID", SC_CARD_TYPE_SC_HSM_GOID, 0, NULL
},
{
"3B:89:80:01:47:6f:49:44:00:00:00:00:00:00",
"FF:FF:FF:FF:FF:FF:FF:FF:00:00:00:00:00:00",
"GoID", SC_CARD_TYPE_SC_HSM_SOC, 0, NULL
"GoID", SC_CARD_TYPE_SC_HSM_GOID, 0, NULL
},
{
"3B:8a:80:01:47:6f:49:44:00:00:00:00:00:00:00",
"FF:FF:FF:FF:FF:FF:FF:FF:00:00:00:00:00:00:00",
"GoID", SC_CARD_TYPE_SC_HSM_SOC, 0, NULL
"GoID", SC_CARD_TYPE_SC_HSM_GOID, 0, NULL
},
{
"3B:8b:80:01:47:6f:49:44:00:00:00:00:00:00:00:00",
"FF:FF:FF:FF:FF:FF:FF:FF:00:00:00:00:00:00:00:00",
"GoID", SC_CARD_TYPE_SC_HSM_SOC, 0, NULL
"GoID", SC_CARD_TYPE_SC_HSM_GOID, 0, NULL
},
{
"3B:8c:80:01:47:6f:49:44:00:00:00:00:00:00:00:00:00",
"FF:FF:FF:FF:FF:FF:FF:FF:00:00:00:00:00:00:00:00:00",
"GoID", SC_CARD_TYPE_SC_HSM_SOC, 0, NULL
"GoID", SC_CARD_TYPE_SC_HSM_GOID, 0, NULL
},
{
"3B:8d:80:01:47:6f:49:44:00:00:00:00:00:00:00:00:00:00",
"FF:FF:FF:FF:FF:FF:FF:FF:00:00:00:00:00:00:00:00:00:00",
"GoID", SC_CARD_TYPE_SC_HSM_SOC, 0, NULL
"GoID", SC_CARD_TYPE_SC_HSM_GOID, 0, NULL
},
{
"3B:8e:80:01:47:6f:49:44:00:00:00:00:00:00:00:00:00:00:00",
"FF:FF:FF:FF:FF:FF:FF:FF:00:00:00:00:00:00:00:00:00:00:00",
"GoID", SC_CARD_TYPE_SC_HSM_SOC, 0, NULL
"GoID", SC_CARD_TYPE_SC_HSM_GOID, 0, NULL
},
{
"3B:8f:80:01:47:6f:49:44:00:00:00:00:00:00:00:00:00:00:00:00",
"FF:FF:FF:FF:FF:FF:FF:FF:00:00:00:00:00:00:00:00:00:00:00:00",
"GoID", SC_CARD_TYPE_SC_HSM_SOC, 0, NULL
"GoID", SC_CARD_TYPE_SC_HSM_GOID, 0, NULL
},
{NULL, NULL, NULL, 0, 0, NULL}
};
@ -305,30 +305,62 @@ static int sc_hsm_soc_change(sc_card_t *card, struct sc_pin_cmd_data *data,
sc_path_t path;
int r;
/* Select MinBioClient */
r = sc_hsm_soc_select_minbioclient(card);
LOG_TEST_RET(card->ctx, r, "Could not select MinBioClient application");
if (card->type == SC_CARD_TYPE_SC_HSM_SOC) {
/* Select MinBioClient */
r = sc_hsm_soc_select_minbioclient(card);
LOG_TEST_RET(card->ctx, r, "Could not select MinBioClient application");
/* verify PIN */
sc_format_apdu(card, &apdu, SC_APDU_CASE_1, 0x20, 0x00, 0x80);
r = sc_transmit_apdu(card, &apdu);
LOG_TEST_GOTO_ERR(card->ctx, r, "APDU transmit failed");
r = sc_check_sw(card, apdu.sw1, apdu.sw2);
LOG_TEST_GOTO_ERR(card->ctx, r, "Could not verify PIN");
/* verify PIN */
sc_format_apdu(card, &apdu, SC_APDU_CASE_1, 0x20, 0x00, 0x80);
r = sc_transmit_apdu(card, &apdu);
LOG_TEST_GOTO_ERR(card->ctx, r, "APDU transmit failed");
r = sc_check_sw(card, apdu.sw1, apdu.sw2);
LOG_TEST_GOTO_ERR(card->ctx, r, "Could not verify PIN");
/* change PIN */
sc_format_apdu(card, &apdu, SC_APDU_CASE_1, 0x24, 0x01, 0x80);
r = sc_transmit_apdu(card, &apdu);
LOG_TEST_GOTO_ERR(card->ctx, r, "APDU transmit failed");
r = sc_check_sw(card, apdu.sw1, apdu.sw2);
LOG_TEST_GOTO_ERR(card->ctx, r, "Could not change PIN");
/* change PIN */
sc_format_apdu(card, &apdu, SC_APDU_CASE_1, 0x24, 0x01, 0x80);
r = sc_transmit_apdu(card, &apdu);
LOG_TEST_GOTO_ERR(card->ctx, r, "APDU transmit failed");
r = sc_check_sw(card, apdu.sw1, apdu.sw2);
LOG_TEST_GOTO_ERR(card->ctx, r, "Could not change PIN");
} else {
#ifdef ENABLE_SM
unsigned sm_mode = card->sm_ctx.sm_mode;
#endif
/* verify PIN */
sc_format_apdu(card, &apdu, SC_APDU_CASE_1, 0x20, 0x00, 0x85);
apdu.cla = 0x80;
r = sc_transmit_apdu(card, &apdu);
LOG_TEST_GOTO_ERR(card->ctx, r, "APDU transmit failed");
#ifdef ENABLE_SM
/* temporary disable SM, change reference data does not reach the applet */
card->sm_ctx.sm_mode = SM_MODE_NONE;
#endif
/* change PIN */
sc_format_apdu(card, &apdu, SC_APDU_CASE_1, 0x24, 0x01, 0x85);
apdu.cla = 0x80;
r = sc_transmit_apdu(card, &apdu);
#ifdef ENABLE_SM
/* restore SM if possible */
card->sm_ctx.sm_mode = sm_mode;
#endif
LOG_TEST_GOTO_ERR(card->ctx, r, "APDU transmit failed");
r = sc_check_sw(card, apdu.sw1, apdu.sw2);
LOG_TEST_GOTO_ERR(card->ctx, r, "Could not change PIN");
}
err:
/* Select SC-HSM */
sc_path_set(&path, SC_PATH_TYPE_DF_NAME, sc_hsm_aid.value, sc_hsm_aid.len, 0, 0);
LOG_TEST_RET(card->ctx,
sc_hsm_select_file_ex(card, &path, 1, NULL),
"Could not select SmartCard-HSM application");
if (card->type == SC_CARD_TYPE_SC_HSM_SOC) {
/* Select SC-HSM */
sc_path_set(&path, SC_PATH_TYPE_DF_NAME,
sc_hsm_aid.value, sc_hsm_aid.len, 0, 0);
LOG_TEST_RET(card->ctx,
sc_hsm_select_file_ex(card, &path, 1, NULL),
"Could not select SmartCard-HSM application");
}
return r;
}
@ -340,6 +372,10 @@ static int sc_hsm_soc_unblock(sc_card_t *card, struct sc_pin_cmd_data *data,
sc_path_t path;
int r;
if (card->type == SC_CARD_TYPE_SC_HSM_GOID) {
return SC_ERROR_NOT_SUPPORTED;
}
/* Select MinBioClient */
r = sc_hsm_soc_select_minbioclient(card);
LOG_TEST_RET(card->ctx, r, "Could not select MinBioClient application");
@ -375,19 +411,24 @@ static int sc_hsm_soc_biomatch(sc_card_t *card, struct sc_pin_cmd_data *data,
u8 rbuf[SC_MAX_APDU_BUFFER_SIZE];
int r;
sc_format_apdu(card, &apdu, SC_APDU_CASE_3_SHORT, 0x20, 0x00, 0x85);
apdu.cla = 0x80;
apdu.data = (unsigned char*)"\x7F\x24\x00";
apdu.datalen = 3;
apdu.lc = 3;
apdu.resplen = 0;
if (card->type == SC_CARD_TYPE_SC_HSM_SOC) {
sc_format_apdu(card, &apdu, SC_APDU_CASE_3_SHORT, 0x20, 0x00, 0x85);
apdu.cla = 0x80;
apdu.data = (unsigned char*)"\x7F\x24\x00";
apdu.datalen = 3;
apdu.lc = 3;
apdu.resplen = 0;
r = sc_transmit_apdu(card, &apdu);
LOG_TEST_RET(card->ctx, r, "APDU transmit failed");
/* ignore the actual status bytes */
r = sc_transmit_apdu(card, &apdu);
LOG_TEST_RET(card->ctx, r, "APDU transmit failed");
/* ignore the actual status bytes */
}
/* JCOP's SM accelerator is incapable of using case 1 APDU in SM */
sc_format_apdu(card, &apdu, SC_APDU_CASE_2, 0x20, 0x00, 0x81);
if (card->type == SC_CARD_TYPE_SC_HSM_GOID) {
apdu.cla = 0x80;
}
apdu.resp = rbuf;
apdu.resplen = sizeof rbuf;
r = sc_transmit_apdu(card, &apdu);
@ -564,8 +605,9 @@ static int sc_hsm_pin_cmd(sc_card_t *card, struct sc_pin_cmd_data *data,
/* For contactless cards always establish a secure channel before PIN
* verification. Also, Session PIN generation requires SM. */
if ((card->type == SC_CARD_TYPE_SC_HSM_SOC || card->reader->uid.len
|| cmd == SC_PIN_CMD_GET_SESSION_PIN)
if ((card->type == SC_CARD_TYPE_SC_HSM_SOC
|| card->type == SC_CARD_TYPE_SC_HSM_GOID
|| card->reader->uid.len || cmd == SC_PIN_CMD_GET_SESSION_PIN)
&& (data->cmd != SC_PIN_CMD_GET_INFO)
#ifdef ENABLE_SM
&& card->sm_ctx.sm_mode != SM_MODE_TRANSMIT
@ -1501,7 +1543,7 @@ static int sc_hsm_card_ctl(sc_card_t *card, unsigned long cmd, void *ptr)
static int sc_hsm_init(struct sc_card *card)
{
#ifdef _WIN32
#if defined(ENABLE_OPENPACE) && defined(_WIN32)
char expanded_val[PATH_MAX];
size_t expanded_len = PATH_MAX;
#endif
@ -1575,7 +1617,8 @@ static int sc_hsm_init(struct sc_card *card)
}
card->max_send_size = 1431; // 1439 buffer size - 8 byte TLV because of odd ins in UPDATE BINARY
if (card->type == SC_CARD_TYPE_SC_HSM_SOC) {
if (card->type == SC_CARD_TYPE_SC_HSM_SOC
|| card->type == SC_CARD_TYPE_SC_HSM_GOID) {
card->max_recv_size = 0x0630; // SoC Proxy forces this limit
} else {
card->max_recv_size = 0; // Card supports sending with extended length APDU and without limit

View File

@ -490,7 +490,9 @@ enum SC_CARDCTL_OBERTHUR_KEY_TYPE {
SC_CARDCTL_OBERTHUR_KEY_RSA_SFM,
SC_CARDCTL_OBERTHUR_KEY_RSA_CRT,
SC_CARDCTL_OBERTHUR_KEY_DSA_PUBLIC,
SC_CARDCTL_OBERTHUR_KEY_DSA_PRIVATE
SC_CARDCTL_OBERTHUR_KEY_DSA_PRIVATE,
SC_CARDCTL_OBERTHUR_KEY_EC_CRT,
SC_CARDCTL_OBERTHUR_KEY_EC_PUBLIC
};
struct sc_cardctl_oberthur_genkey_info {

View File

@ -200,10 +200,12 @@ enum {
SC_CARD_TYPE_IASECC_SAGEM,
SC_CARD_TYPE_IASECC_AMOS,
SC_CARD_TYPE_IASECC_MI,
SC_CARD_TYPE_IASECC_MI2,
/* SmartCard-HSM */
SC_CARD_TYPE_SC_HSM = 26000,
SC_CARD_TYPE_SC_HSM_SOC = 26001,
SC_CARD_TYPE_SC_HSM_GOID = 26002,
/* Spanish DNIe card */
SC_CARD_TYPE_DNIE_BASE = 27000,

View File

@ -163,6 +163,7 @@ extern "C" {
struct sc_supported_algo_info {
unsigned int reference;
unsigned int mechanism;
struct sc_object_id *parameters; /* OID for ECC, NULL for RSA */
unsigned int operations;
struct sc_object_id algo_id;
unsigned int algo_ref;

View File

@ -139,7 +139,7 @@ cac_alg_flags_from_algorithm(int algorithm)
/* map a cert usage and algorithm to public and private key usages */
static int
cac_map_usage(unsigned long long cert_usage, int algorithm, unsigned int *pub_usage_ptr, unsigned int *pr_usage_ptr, int allow_nonrepudiation)
cac_map_usage(unsigned int cert_usage, int algorithm, unsigned int *pub_usage_ptr, unsigned int *pr_usage_ptr, int allow_nonrepudiation)
{
unsigned int pub_usage = 0, pr_usage = 0;
unsigned int alg_flags = cac_alg_flags_from_algorithm(algorithm);
@ -184,7 +184,7 @@ static int sc_pkcs15emu_cac_init(sc_pkcs15_card_t *p15card)
};
/* oid for key usage */
static const struct sc_object_id usage_type = {{ 2, 5, 29, 15, -1 }};
unsigned long long usage;
unsigned int usage;
/*
@ -323,8 +323,8 @@ static int sc_pkcs15emu_cac_init(sc_pkcs15_card_t *p15card)
prkey_info.path.len += 2;
}
pubkey_info.native = 1;
pubkey_info.key_reference = ((int)obj_info.id.value[0]) << 8 || obj_info.id.value[1];
prkey_info.key_reference = ((int)obj_info.id.value[0]) << 8 || obj_info.id.value[1];
pubkey_info.key_reference = ((int)obj_info.id.value[0]) << 8 | obj_info.id.value[1];
prkey_info.key_reference = ((int)obj_info.id.value[0]) << 8 | obj_info.id.value[1];
prkey_info.native = 1;
memcpy(cert_obj.label, obj_info.app_label, sizeof(obj_info.app_label));
@ -401,7 +401,7 @@ static int sc_pkcs15emu_cac_init(sc_pkcs15_card_t *p15card)
usage = 0xd9ULL; /* basic default usage */
}
cac_map_usage(usage, cert_out->key->algorithm, &pubkey_info.usage, &prkey_info.usage, 1);
sc_debug(card->ctx, SC_LOG_DEBUG_NORMAL, "cert %s: cert_usage=0x%llx, pub_usage=0x%x priv_usage=0x%x\n",
sc_debug(card->ctx, SC_LOG_DEBUG_NORMAL, "cert %s: cert_usage=0x%x, pub_usage=0x%x priv_usage=0x%x\n",
sc_dump_hex(cert_info.id.value, cert_info.id.len),
usage, pubkey_info.usage, prkey_info.usage);
if (cert_out->key->algorithm != SC_ALGORITHM_RSA) {

View File

@ -310,13 +310,13 @@ sc_pkcs15_get_extension(struct sc_context *ctx, struct sc_pkcs15_cert *cert,
int
sc_pkcs15_get_bitstring_extension(struct sc_context *ctx,
struct sc_pkcs15_cert *cert, const struct sc_object_id *type,
unsigned long long *value, int *is_critical)
unsigned int *value, int *is_critical)
{
int r;
u8 *bit_string = NULL;
size_t bit_string_len=0, val_len = sizeof(*value);
struct sc_asn1_entry asn1_bit_string[] = {
{ "bitString", SC_ASN1_BIT_STRING, SC_ASN1_TAG_BIT_STRING, 0, value, &val_len },
{ "bitString", SC_ASN1_BIT_FIELD, SC_ASN1_TAG_BIT_STRING, 0, value, &val_len },
{ NULL, 0, 0, 0, NULL, NULL }
};

View File

@ -104,7 +104,7 @@ typedef struct common_key_info_st {
int pubkey_from_file;
int key_alg;
unsigned int pubkey_len;
unsigned long long cert_keyUsage; /* x509 key usage as defined in certificate */
unsigned int cert_keyUsage; /* x509 key usage as defined in certificate */
int cert_keyUsage_present; /* 1 if keyUsage found in certificate */
int pub_usage;
int priv_usage;
@ -359,7 +359,7 @@ static int sc_pkcs15emu_piv_init(sc_pkcs15_card_t *p15card)
};
static const pindata pins[] = {
{ "01", "PIV Card Holder pin", "", 0x80,
{ "01", "PIN", "", 0x80,
/* label, flag and ref will change if using global pin */
SC_PKCS15_PIN_TYPE_ASCII_NUMERIC,
8, 4, 8,
@ -613,7 +613,7 @@ static int sc_pkcs15emu_piv_init(sc_pkcs15_card_t *p15card)
char buf[SC_MAX_SERIALNR * 2 + 1];
common_key_info ckis[PIV_NUM_CERTS_AND_KEYS];
int follows_nist_fascn = 0;
char *token_name = NULL;
SC_FUNC_CALLED(card->ctx, SC_LOG_DEBUG_VERBOSE);
@ -765,6 +765,28 @@ static int sc_pkcs15emu_piv_init(sc_pkcs15_card_t *p15card)
sc_pkcs15_free_certificate(cert_out);
continue;
}
/* set the token name to the name of the CN of the first certificate */
if (!token_name) {
u8 * cn_name = NULL;
size_t cn_len = 0;
static const struct sc_object_id cn_oid = {{ 2, 5, 4, 3, -1 }};
r = sc_pkcs15_get_name_from_dn(card->ctx, cert_out->subject,
cert_out->subject_len, &cn_oid, &cn_name, &cn_len);
if (r == SC_SUCCESS) {
token_name = malloc (cn_len+1);
if (!token_name) {
SC_FUNC_RETURN(card->ctx,
SC_ERROR_OUT_OF_MEMORY, r);
}
memcpy(token_name, cn_name, cn_len);
free(cn_name);
token_name[cn_len] = 0;
free(p15card->tokeninfo->label);
p15card->tokeninfo->label = token_name;
}
}
/*
* get keyUsage if present save in ckis[i]
* Will only use it if this in a non FED issued card
@ -773,13 +795,11 @@ static int sc_pkcs15emu_piv_init(sc_pkcs15_card_t *p15card)
if (follows_nist_fascn == 0) {
struct sc_object_id keyUsage_oid={{2,5,29,15,-1}};
unsigned long long *value;
int r = 0;
value = &ckis[i].cert_keyUsage;
r = sc_pkcs15_get_bitstring_extension(card->ctx, cert_out,
&keyUsage_oid,
value, NULL);
&ckis[i].cert_keyUsage, NULL);
if ( r >= 0)
ckis[i].cert_keyUsage_present = 1;
/* TODO if no key usage, we could set all uses */
@ -932,7 +952,7 @@ static int sc_pkcs15emu_piv_init(sc_pkcs15_card_t *p15card)
pin_info.attrs.pin.reference = pin_ref;
pin_info.attrs.pin.flags &= ~SC_PKCS15_PIN_FLAG_LOCAL;
label = "Global PIN";
}
}
sc_debug(card->ctx, SC_LOG_DEBUG_NORMAL, "DEE Adding pin %d label=%s",i, label);
strncpy(pin_obj.label, label, SC_PKCS15_MAX_LABEL_SIZE - 1);
pin_obj.flags = pins[i].obj_flags;

View File

@ -606,13 +606,13 @@ static int sc_pkcs15emu_sc_hsm_add_prkd(sc_pkcs15_card_t * p15card, u8 keyid) {
/* Try to select a related EF containing the PKCS#15 description of the key */
len = sizeof efbin;
r = read_file(p15card, fid, efbin, &len, 1);
LOG_TEST_RET(card->ctx, r, "Could not read EF.PRKD");
LOG_TEST_RET(card->ctx, r, "Skipping optional EF.PRKD");
ptr = efbin;
memset(&prkd, 0, sizeof(prkd));
r = sc_pkcs15_decode_prkdf_entry(p15card, &prkd, (const u8 **)&ptr, &len);
LOG_TEST_RET(card->ctx, r, "Could not decode EF.PRKD");
LOG_TEST_RET(card->ctx, r, "Skipping optional EF.PRKD");
/* All keys require user PIN authentication */
prkd.auth_id.len = 1;
@ -642,8 +642,6 @@ static int sc_pkcs15emu_sc_hsm_add_prkd(sc_pkcs15_card_t * p15card, u8 keyid) {
r = read_file(p15card, fid, efbin, &len, 0);
LOG_TEST_RET(card->ctx, r, "Could not read EF");
LOG_TEST_RET(card->ctx, r, "Could not read EF");
if (efbin[0] == 0x67) { /* Decode CSR and create public key object */
sc_pkcs15emu_sc_hsm_add_pubkey(p15card, efbin, len, key_info, prkd.label);
free(key_info);
@ -702,13 +700,13 @@ static int sc_pkcs15emu_sc_hsm_add_dcod(sc_pkcs15_card_t * p15card, u8 id) {
/* Try to select a related EF containing the PKCS#15 description of the data */
len = sizeof efbin;
r = read_file(p15card, fid, efbin, &len, 1);
LOG_TEST_RET(card->ctx, r, "Could not read EF.DCOD");
LOG_TEST_RET(card->ctx, r, "Skipping optional EF.DCOD");
ptr = efbin;
memset(&data_obj, 0, sizeof(data_obj));
r = sc_pkcs15_decode_dodf_entry(p15card, &data_obj, &ptr, &len);
LOG_TEST_RET(card->ctx, r, "Could not decode EF.DCOD");
LOG_TEST_RET(card->ctx, r, "Could not decode optional EF.DCOD");
data_info = (sc_pkcs15_data_info_t *)data_obj.data;
@ -741,13 +739,13 @@ static int sc_pkcs15emu_sc_hsm_add_cd(sc_pkcs15_card_t * p15card, u8 id) {
/* Try to select a related EF containing the PKCS#15 description of the data */
len = sizeof efbin;
r = read_file(p15card, fid, efbin, &len, 1);
LOG_TEST_RET(card->ctx, r, "Could not read EF.DCOD");
LOG_TEST_RET(card->ctx, r, "Skipping optional EF.DCOD");
ptr = efbin;
memset(&obj, 0, sizeof(obj));
r = sc_pkcs15_decode_cdf_entry(p15card, &obj, &ptr, &len);
LOG_TEST_RET(card->ctx, r, "Could not decode EF.CD");
LOG_TEST_RET(card->ctx, r, "Skipping optional EF.CDOD");
cert_info = (sc_pkcs15_cert_info_t *)obj.data;
@ -772,10 +770,10 @@ static int sc_pkcs15emu_sc_hsm_read_tokeninfo (sc_pkcs15_card_t * p15card)
/* Read token info */
len = sizeof efbin;
r = read_file(p15card, (u8 *) "\x2F\x03", efbin, &len, 1);
LOG_TEST_RET(card->ctx, r, "Could not read EF.TokenInfo");
LOG_TEST_RET(card->ctx, r, "Skipping optional EF.TokenInfo");
r = sc_pkcs15_parse_tokeninfo(card->ctx, p15card->tokeninfo, efbin, len);
LOG_TEST_RET(card->ctx, r, "Could not decode EF.TokenInfo");
LOG_TEST_RET(card->ctx, r, "Skipping optional EF.TokenInfo");
LOG_FUNC_RETURN(card->ctx, SC_SUCCESS);
}
@ -835,7 +833,7 @@ static int sc_pkcs15emu_sc_hsm_init (sc_pkcs15_card_t * p15card)
} else {
len = sizeof efbin;
r = read_file(p15card, (u8 *) "\x2F\x02", efbin, &len, 1);
LOG_TEST_RET(card->ctx, r, "Could not select EF.C_DevAut");
LOG_TEST_RET(card->ctx, r, "Skipping optional EF.C_DevAut");
/* save EF_C_DevAut for further use */
ptr = realloc(priv->EF_C_DevAut, len);
@ -941,7 +939,8 @@ static int sc_pkcs15emu_sc_hsm_init (sc_pkcs15_card_t * p15card)
LOG_FUNC_RETURN(card->ctx, r);
if (card->type == SC_CARD_TYPE_SC_HSM_SOC) {
if (card->type == SC_CARD_TYPE_SC_HSM_SOC
|| card->type == SC_CARD_TYPE_SC_HSM_GOID) {
/* SC-HSM of this type always has a PIN-Pad */
r = SC_SUCCESS;
} else {
@ -998,7 +997,8 @@ int sc_pkcs15emu_sc_hsm_init_ex(sc_pkcs15_card_t *p15card,
return sc_pkcs15emu_sc_hsm_init(p15card);
} else {
if (p15card->card->type != SC_CARD_TYPE_SC_HSM
&& p15card->card->type != SC_CARD_TYPE_SC_HSM_SOC) {
&& p15card->card->type != SC_CARD_TYPE_SC_HSM_SOC
&& p15card->card->type != SC_CARD_TYPE_SC_HSM_GOID) {
return SC_ERROR_WRONG_CARD;
}
return sc_pkcs15emu_sc_hsm_init(p15card);

View File

@ -50,13 +50,19 @@ static const struct sc_asn1_entry c_asn1_twlabel[] = {
static const struct sc_asn1_entry c_asn1_algorithm_info[7] = {
{ "reference", SC_ASN1_INTEGER, SC_ASN1_TAG_INTEGER, 0, NULL, NULL },
{ "algorithmPKCS#11", SC_ASN1_INTEGER, SC_ASN1_TAG_INTEGER, 0, NULL, NULL },
{ "parameters", SC_ASN1_NULL, SC_ASN1_TAG_NULL, 0, NULL, NULL },
{ "parameters", SC_ASN1_CHOICE, 0, 0, NULL, NULL },
{ "supportedOperations",SC_ASN1_BIT_FIELD, SC_ASN1_TAG_BIT_STRING, 0, NULL, NULL },
{ "objId", SC_ASN1_OBJECT, SC_ASN1_TAG_OBJECT, SC_ASN1_OPTIONAL, NULL, NULL },
{ "algRef", SC_ASN1_INTEGER, SC_ASN1_TAG_INTEGER, SC_ASN1_OPTIONAL, NULL, NULL },
{ NULL, 0, 0, 0, NULL, NULL }
};
static const struct sc_asn1_entry c_asn1_algorithm_info_parameters[3] = {
{ "PKCS15RSAParameters",SC_ASN1_NULL, SC_ASN1_TAG_NULL, 0, NULL, NULL },
{ "PKCS15ECParameters", SC_ASN1_OBJECT, SC_ASN1_TAG_OBJECT, 0, NULL, NULL },
{ NULL, 0, 0, 0, NULL, NULL }
};
/*
* in src/libopensc/types.h SC_MAX_SUPPORTED_ALGORITHMS defined as 8
*/
@ -134,9 +140,11 @@ int sc_pkcs15_parse_tokeninfo(sc_context_t *ctx,
u8 preferred_language[3];
size_t lang_length = sizeof(preferred_language);
struct sc_asn1_entry asn1_supported_algorithms[SC_MAX_SUPPORTED_ALGORITHMS + 1],
asn1_algo_infos[SC_MAX_SUPPORTED_ALGORITHMS][7];
asn1_algo_infos[SC_MAX_SUPPORTED_ALGORITHMS][7],
asn1_algo_infos_parameters[SC_MAX_SUPPORTED_ALGORITHMS][3];
size_t reference_len = sizeof(ti->supported_algos[0].reference);
size_t mechanism_len = sizeof(ti->supported_algos[0].mechanism);
size_t parameter_len = sizeof(ti->supported_algos[0].parameters);
size_t operations_len = sizeof(ti->supported_algos[0].operations);
size_t algo_ref_len = sizeof(ti->supported_algos[0].algo_ref);
@ -152,14 +160,22 @@ int sc_pkcs15_parse_tokeninfo(sc_context_t *ctx,
sc_format_asn1_entry(asn1_twlabel, label, &label_len, 0);
sc_copy_asn1_entry(c_asn1_profile_indication, asn1_profile_indication);
for (ii=0; ii<SC_MAX_SUPPORTED_ALGORITHMS; ii++)
for (ii=0; ii<SC_MAX_SUPPORTED_ALGORITHMS; ii++) {
sc_copy_asn1_entry(c_asn1_algorithm_info, asn1_algo_infos[ii]);
sc_copy_asn1_entry(c_asn1_algorithm_info_parameters,
asn1_algo_infos_parameters[ii]);
}
sc_copy_asn1_entry(c_asn1_supported_algorithms, asn1_supported_algorithms);
for (ii=0; ii<SC_MAX_SUPPORTED_ALGORITHMS; ii++) {
sc_format_asn1_entry(asn1_algo_infos[ii] + 0, &ti->supported_algos[ii].reference, &reference_len, 0);
sc_format_asn1_entry(asn1_algo_infos[ii] + 1, &ti->supported_algos[ii].mechanism, &mechanism_len, 0);
sc_format_asn1_entry(asn1_algo_infos[ii] + 2, NULL, NULL, 0);
sc_format_asn1_entry(asn1_algo_infos[ii] + 2,
asn1_algo_infos_parameters[ii], NULL, 0);
sc_format_asn1_entry(asn1_algo_infos_parameters[ii] + 0,
NULL, NULL, 0);
sc_format_asn1_entry(asn1_algo_infos_parameters[ii] + 1,
&ti->supported_algos[ii].parameters, &parameter_len, 0);
sc_format_asn1_entry(asn1_algo_infos[ii] + 3, &ti->supported_algos[ii].operations, &operations_len, 0);
sc_format_asn1_entry(asn1_algo_infos[ii] + 4, &ti->supported_algos[ii].algo_id, NULL, 1);
sc_format_asn1_entry(asn1_algo_infos[ii] + 5, &ti->supported_algos[ii].algo_ref, &algo_ref_len, 0);
@ -270,9 +286,11 @@ sc_pkcs15_encode_tokeninfo(sc_context_t *ctx, sc_pkcs15_tokeninfo_t *ti,
struct sc_asn1_entry asn1_toki_attrs[C_ASN1_TOKI_ATTRS_SIZE];
struct sc_asn1_entry asn1_tokeninfo[2];
struct sc_asn1_entry asn1_supported_algorithms[SC_MAX_SUPPORTED_ALGORITHMS + 1],
asn1_algo_infos[SC_MAX_SUPPORTED_ALGORITHMS][7];
asn1_algo_infos[SC_MAX_SUPPORTED_ALGORITHMS][7],
asn1_algo_infos_parameters[SC_MAX_SUPPORTED_ALGORITHMS][3];
size_t reference_len = sizeof(ti->supported_algos[0].reference);
size_t mechanism_len = sizeof(ti->supported_algos[0].mechanism);
size_t parameter_len = sizeof(ti->supported_algos[0].parameters);
size_t operations_len = sizeof(ti->supported_algos[0].operations);
size_t algo_ref_len = sizeof(ti->supported_algos[0].algo_ref);
struct sc_asn1_entry asn1_last_update[C_ASN1_LAST_UPDATE_SIZE];
@ -283,14 +301,22 @@ sc_pkcs15_encode_tokeninfo(sc_context_t *ctx, sc_pkcs15_tokeninfo_t *ti,
sc_copy_asn1_entry(c_asn1_last_update, asn1_last_update);
sc_copy_asn1_entry(c_asn1_profile_indication, asn1_profile_indication);
for (ii=0; ii<SC_MAX_SUPPORTED_ALGORITHMS && ti->supported_algos[ii].reference; ii++)
for (ii=0; ii<SC_MAX_SUPPORTED_ALGORITHMS && ti->supported_algos[ii].reference; ii++) {
sc_copy_asn1_entry(c_asn1_algorithm_info, asn1_algo_infos[ii]);
sc_copy_asn1_entry(c_asn1_algorithm_info_parameters,
asn1_algo_infos_parameters[ii]);
}
sc_copy_asn1_entry(c_asn1_supported_algorithms, asn1_supported_algorithms);
for (ii=0; ii<SC_MAX_SUPPORTED_ALGORITHMS && ti->supported_algos[ii].reference; ii++) {
sc_format_asn1_entry(asn1_algo_infos[ii] + 0, &ti->supported_algos[ii].reference, &reference_len, 1);
sc_format_asn1_entry(asn1_algo_infos[ii] + 1, &ti->supported_algos[ii].mechanism, &mechanism_len, 1);
sc_format_asn1_entry(asn1_algo_infos[ii] + 2, NULL, NULL, 0);
sc_format_asn1_entry(asn1_algo_infos[ii] + 2,
asn1_algo_infos_parameters[ii], NULL, 0);
sc_format_asn1_entry(asn1_algo_infos_parameters[ii] + 0,
NULL, NULL, 0);
sc_format_asn1_entry(asn1_algo_infos_parameters[ii] + 1,
&ti->supported_algos[ii].parameters, &parameter_len, 0);
sc_format_asn1_entry(asn1_algo_infos[ii] + 3, &ti->supported_algos[ii].operations, &operations_len, 1);
sc_format_asn1_entry(asn1_algo_infos[ii] + 4, &ti->supported_algos[ii].algo_id, NULL, 1);
sc_format_asn1_entry(asn1_algo_infos[ii] + 5, &ti->supported_algos[ii].algo_ref, &algo_ref_len, 1);
@ -1059,15 +1085,17 @@ sc_pkcs15_bind_internal(struct sc_pkcs15_card *p15card, struct sc_aid *aid)
}
if (err < 0) {
err = sc_read_binary(card, 0, buf, len, 0);
if (err < 0) {
sc_log(ctx, "read EF(ODF) file error: %s", sc_strerror(err));
goto end;
}
else if (err < 2) {
err = SC_ERROR_PKCS15_APP_NOT_FOUND;
sc_log(ctx, "Invalid content of EF(ODF): %s", sc_strerror(err));
if (err < 2) {
if (err < 0) {
sc_log(ctx, "read EF(ODF) file error: %s", sc_strerror(err));
} else {
err = SC_ERROR_PKCS15_APP_NOT_FOUND;
sc_log(ctx, "Invalid content of EF(ODF): %s", sc_strerror(err));
}
goto end;
}
/* sc_read_binary may return less than requested */
len = err;
if (p15card->opts.use_file_cache) {
sc_pkcs15_cache_file(p15card, &tmppath, buf, len);
@ -1125,20 +1153,21 @@ sc_pkcs15_bind_internal(struct sc_pkcs15_card *p15card, struct sc_aid *aid)
}
if (err < 0) {
err = sc_read_binary(card, 0, buf, len, 0);
if (err < 0) {
sc_log(ctx, "read EF(TokenInfo) file error: %s", sc_strerror(err));
goto end;
}
if (err <= 2) {
err = SC_ERROR_PKCS15_APP_NOT_FOUND;
sc_log(ctx, "Invalid content of EF(TokenInfo): %s", sc_strerror(err));
if (err < 0) {
sc_log(ctx, "read EF(TokenInfo) file error: %s", sc_strerror(err));
} else {
err = SC_ERROR_PKCS15_APP_NOT_FOUND;
sc_log(ctx, "Invalid content of EF(TokenInfo): %s", sc_strerror(err));
}
goto end;
}
/* sc_read_binary may return less than requested */
len = err;
if (p15card->opts.use_file_cache) {
sc_pkcs15_cache_file(p15card, &tmppath, buf, len);
}
err = len;
}
memset(&tokeninfo, 0, sizeof(tokeninfo));
@ -2392,7 +2421,7 @@ sc_pkcs15_read_file(struct sc_pkcs15_card *p15card, const struct sc_path *in_pat
sc_file_free(file);
if (p15card->opts.use_file_cache) {
if (len && p15card->opts.use_file_cache) {
sc_pkcs15_cache_file(p15card, in_path, data, len);
}
}

View File

@ -738,7 +738,7 @@ int sc_pkcs15_get_extension(struct sc_context *ctx,
int sc_pkcs15_get_bitstring_extension(struct sc_context *ctx,
struct sc_pkcs15_cert *cert,
const struct sc_object_id *type,
unsigned long long *value,
unsigned int *value,
int *is_critical);
/* sc_pkcs15_create_cdf: Creates a new certificate DF on a card pointed
* by <card>. Information about the file, such as the file ID, is read

View File

@ -31,6 +31,7 @@
#include "asn1.h"
#include "sm.h"
#ifdef ENABLE_SM
static const struct sc_asn1_entry c_asn1_sm_response[4] = {
{ "encryptedData", SC_ASN1_OCTET_STRING, SC_ASN1_CTX | 7, SC_ASN1_OPTIONAL, NULL, NULL },
{ "statusWord", SC_ASN1_OCTET_STRING, SC_ASN1_CTX | 0x19, 0, NULL, NULL },
@ -38,7 +39,6 @@ static const struct sc_asn1_entry c_asn1_sm_response[4] = {
{ NULL, 0, 0, 0, NULL, NULL }
};
#ifdef ENABLE_SM
int
sc_sm_parse_answer(struct sc_card *card, unsigned char *resp_data, size_t resp_len,
struct sm_card_response *out)
@ -157,7 +157,7 @@ sc_sm_single_transmit(struct sc_card *card, struct sc_apdu *apdu)
}
/* send APDU flagged as NO_SM */
sm_apdu->flags |= SC_APDU_FLAGS_NO_SM;
sm_apdu->flags |= SC_APDU_FLAGS_NO_SM | SC_APDU_FLAGS_NO_RETRY_WL;
rv = sc_transmit_apdu(card, sm_apdu);
if (rv < 0) {
card->sm_ctx.ops.free_sm_apdu(card, apdu, &sm_apdu);

View File

@ -7,9 +7,9 @@ if ENABLE_MINIDRIVER
lib_LTLIBRARIES = opensc-minidriver@LIBRARY_BITNESS@.la
# Do we need this on bin? Why can't we
# put it in dedicated directory
dist_sbin_SCRIPTS = opensc-minidriver.inf minidriver-westcos.reg minidriver-sc-hsm.reg minidriver-feitian.reg
dist_sbin_SCRIPTS = opensc-minidriver.inf
else
dist_noinst_DATA = opensc-minidriver.inf minidriver-westcos.reg minidriver-sc-hsm.reg minidriver-feitian.reg
dist_noinst_DATA = opensc-minidriver.inf
endif
AM_CFLAGS = $(OPTIONAL_OPENSSL_CFLAGS)

View File

@ -1,30 +0,0 @@
Windows Registry Editor Version 5.00
[HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Cryptography\Calais\SmartCards\ePass2003]
"ATR"=hex:3b,9f,95,81,31,fe,9f,00,66,46,53,05,01,00,11,71,df,00,00,03,6a,82,f8
"ATRMask"=hex,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff
"Crypto Provider"="Microsoft Base Smart Card Crypto Provider"
"Smart Card Key Storage Provider"="Microsoft Smart Card Key Storage Provider"
"80000001"="opensc-minidriver.dll"
[HKEY_LOCAL_MACHINE\SOFTWARE\Wow6432Node\Microsoft\Cryptography\Calais\SmartCards\ePass2003]
"ATR"=hex:3b,9f,95,81,31,fe,9f,00,66,46,53,05,01,00,11,71,df,00,00,03,6a,82,f8
"ATRMask"=hex:ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,00,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff
"Crypto Provider"="Microsoft Base Smart Card Crypto Provider"
"Smart Card Key Storage Provider"="Microsoft Smart Card Key Storage Provider"
"80000001"="opensc-minidriver.dll"
[HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Cryptography\Calais\SmartCards\FTCOS/PK-01C]
"ATR"=hex:3b,9f,95,81,31,fe,9f,00,65,46,53,05,00,06,71,df,00,00,00,00,00,00,00
"ATRMask"=hex:ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,00,ff,ff,ff,ff,ff,ff,00,00,00,00
"Crypto Provider"="Microsoft Base Smart Card Crypto Provider"
"Smart Card Key Storage Provider"="Microsoft Smart Card Key Storage Provider"
"80000001"="opensc-minidriver.dll"
[HKEY_LOCAL_MACHINE\SOFTWARE\Wow6432Node\Microsoft\Cryptography\Calais\SmartCards\FTCOS/PK-01C]
"ATR"=hex:3b,9f,95,81,31,fe,9f,00,65,46,53,05,00,06,71,df,00,00,00,00,00,00,00
"ATRMask"=hex:ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,00,ff,ff,ff,ff,ff,ff,00,00,00,00
"Crypto Provider"="Microsoft Base Smart Card Crypto Provider"
"Smart Card Key Storage Provider"="Microsoft Smart Card Key Storage Provider"
"80000001"="opensc-minidriver.dll"

View File

@ -1,33 +0,0 @@
Windows Registry Editor Version 5.00
[HKEY_LOCAL_MACHINE\SOFTWARE\Wow6432Node\Microsoft\Cryptography\Calais\SmartCards\CPS]
"Crypto Provider"="Microsoft Base Smart Card Crypto Provider"
"Smart Card Key Storage Provider"="Microsoft Smart Card Key Storage Provider"
"80000001"="opensc-minidriver.dll"
"ATR"=hex:3b,ff,18,00,ff,c1,0a,31,fe,55,00,6b,05,08,c8,0c,01,11,01,43,4e,53,10,\
31,80,05
"ATRMask"=hex:ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,\
ff,ff,ff,ff,ff
[HKEY_LOCAL_MACHINE\SOFTWARE\Wow6432Node\Microsoft\Cryptography\Calais\SmartCards\CPS-Athena]
"Crypto Provider"="Microsoft Base Smart Card Crypto Provider"
"Smart Card Key Storage Provider"="Microsoft Smart Card Key Storage Provider"
"80000001"="opensc-minidriver.dll"
"ATR"=hex:3b,df,18,00,81,31,fe,7d,00,6b,02,0c,01,82,01,11,01,43,4e,53,10,31,80,fc
"ATRMask"=hex:ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff
[HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Cryptography\Calais\SmartCards\CPS]
"Crypto Provider"="Microsoft Base Smart Card Crypto Provider"
"Smart Card Key Storage Provider"="Microsoft Smart Card Key Storage Provider"
"80000001"="opensc-minidriver.dll"
"ATR"=hex:3b,ff,18,00,ff,c1,0a,31,fe,55,00,6b,05,08,c8,0c,01,11,01,43,4e,53,10,\
31,80,05
"ATRMask"=hex:ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,\
ff,ff,ff,ff,ff
[HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Cryptography\Calais\SmartCards\CPS-Athena]
"Crypto Provider"="Microsoft Base Smart Card Crypto Provider"
"Smart Card Key Storage Provider"="Microsoft Smart Card Key Storage Provider"
"80000001"="opensc-minidriver.dll"
"ATR"=hex:3b,df,18,00,81,31,fe,7d,00,6b,02,0c,01,82,01,11,01,43,4e,53,10,31,80,fc
"ATRMask"=hex:ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff,ff

Binary file not shown.

View File

@ -1,7 +0,0 @@
Windows Registry Editor Version 5.00
[HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Cryptography\Calais\SmartCards\CEV WESTCOS]
"80000001"="opensc-minidriver.dll"
"ATR"=hex:3f,69,00,00,00,64,01,00,00,00,80,90,00
"ATRMask"=hex:ff,ff,ff,ff,ff,ff,ff,00,00,00,f0,ff,ff
"Crypto Provider"="Microsoft Base Smart Card Crypto Provider"

File diff suppressed because it is too large Load Diff

View File

@ -1043,6 +1043,7 @@ pkcs15_init_slot(struct sc_pkcs15_card *p15card, struct sc_pkcs11_slot *slot,
struct sc_pkcs15_auth_info *pin_info = NULL;
char label[64];
sc_log(context, "Called");
pkcs15_init_token_info(p15card, &slot->token_info);
slot->token_info.flags |= CKF_TOKEN_INITIALIZED;
if (auth != NULL)
@ -1067,9 +1068,10 @@ pkcs15_init_slot(struct sc_pkcs15_card *p15card, struct sc_pkcs11_slot *slot,
pin_info = NULL;
}
else {
if (auth->label[0])
if (auth->label[0] && strncmp(auth->label, "PIN", 4) != 0)
snprintf(label, sizeof(label), "%.*s (%s)", (int) sizeof auth->label, auth->label, p15card->tokeninfo->label);
else
/* The PIN label is empty or says just non-useful "PIN" */
snprintf(label, sizeof(label), "%s", p15card->tokeninfo->label);
slot->token_info.flags |= CKF_LOGIN_REQUIRED;
}
@ -1230,6 +1232,7 @@ _get_auth_object_by_name(struct sc_pkcs15_card *p15card, char *name)
struct sc_pkcs15_object *out = NULL;
int rv = SC_ERROR_OBJECT_NOT_FOUND;
/* please keep me in sync with md_get_pin_by_role() in minidriver */
if (!strcmp(name, "UserPIN")) {
/* Try to get 'global' PIN; if no, get the 'local' one */
rv = sc_pkcs15_find_pin_by_flags(p15card, SC_PKCS15_PIN_TYPE_FLAGS_PIN_GLOBAL,

View File

@ -521,6 +521,14 @@ static enum_specs ck_mec_s[] = {
{ CKM_VENDOR_DEFINED , "CKM_VENDOR_DEFINED " }
};
static enum_specs ck_mgf_s[] = {
{ CKG_MGF1_SHA1 , "CKG_MGF1_SHA1 " },
{ CKG_MGF1_SHA224, "CKG_MGF1_SHA224" },
{ CKG_MGF1_SHA256, "CKG_MGF1_SHA256" },
{ CKG_MGF1_SHA384, "CKG_MGF1_SHA384" },
{ CKG_MGF1_SHA512, "CKG_MGF1_SHA512" },
};
static enum_specs ck_err_s[] = {
{ CKR_OK, "CKR_OK" },
{ CKR_CANCEL, "CKR_CANCEL" },
@ -630,6 +638,7 @@ enum_spec ck_types[] = {
{ KEY_T, ck_key_s, sizeof(ck_key_s) / SZ_SPECS, "CK_KEY_TYPE" },
{ CRT_T, ck_crt_s, sizeof(ck_crt_s) / SZ_SPECS, "CK_CERTIFICATE_TYPE" },
{ MEC_T, ck_mec_s, sizeof(ck_mec_s) / SZ_SPECS, "CK_MECHANISM_TYPE" },
{ MGF_T, ck_mgf_s, sizeof(ck_mgf_s) / SZ_SPECS, "CK_RSA_PKCS_MGF_TYPE"},
{ USR_T, ck_usr_s, sizeof(ck_usr_s) / SZ_SPECS, "CK_USER_TYPE" },
{ STA_T, ck_sta_s, sizeof(ck_sta_s) / SZ_SPECS, "CK_STATE" },
{ RV_T, ck_err_s, sizeof(ck_err_s) / SZ_SPECS, "CK_RV" },

View File

@ -56,6 +56,7 @@ enum ck_type{
KEY_T,
CRT_T,
MEC_T,
MGF_T,
USR_T,
STA_T,
RV_T

View File

@ -264,7 +264,6 @@ CK_RV C_Initialize(CK_VOID_PTR pInitArgs)
list_attributes_seeker(&sessions, session_list_seeker);
/* List of slots */
list_init(&virtual_slots);
if (0 != list_init(&virtual_slots)) {
rv = CKR_HOST_MEMORY;
goto out;

View File

@ -2,13 +2,22 @@
#define PKCS11_OPENSC_H
/* OpenSC specific extensions */
/*
* define OpenSC specific Vendor Defined extensions
* to make unique OpenSC flags, attribures, mechanisms, etc.
*
* Netscape used NSSCK_VENDOR_NSS 0x4E534350 "NSCP"
*/
#define SC_VENDOR_DEFINED 0x4F534300 /* OSC */
/*
* In PKCS#11 there is no CKA_ attribute dedicated to the NON-REPUDIATION flag.
* We need this flag in PKCS#15/libopensc to make dinstinction between
* 'signature' and 'qualified signature' key slots.
*/
#define CKA_OPENSC_NON_REPUDIATION (CKA_VENDOR_DEFINED | 1UL)
#define CKA_OPENSC_NON_REPUDIATION (CKA_VENDOR_DEFINED | SC_VENDOR_DEFINED | 1UL)
#define CKA_SPKI (CKA_VENDOR_DEFINED | 2UL)
#define CKA_SPKI (CKA_VENDOR_DEFINED | SC_VENDOR_DEFINED | 2UL)
#endif

View File

@ -172,7 +172,7 @@ init_spy(void)
}
}
if( (rc == ERROR_SUCCESS) && (temp_len < PATH_MAX) )
if( (rc == ERROR_SUCCESS) && (temp_len < PATH_MAX) )
output = temp_path;
RegCloseKey( hKey );
}
@ -969,6 +969,24 @@ C_SignInit(CK_SESSION_HANDLE hSession, CK_MECHANISM_PTR pMechanism, CK_OBJECT_HA
enter("C_SignInit");
spy_dump_ulong_in("hSession", hSession);
fprintf(spy_output, "pMechanism->type=%s\n", lookup_enum(MEC_T, pMechanism->mechanism));
switch (pMechanism->mechanism) {
case CKM_RSA_PKCS_PSS:
case CKM_SHA1_RSA_PKCS_PSS:
case CKM_SHA256_RSA_PKCS_PSS:
case CKM_SHA384_RSA_PKCS_PSS:
case CKM_SHA512_RSA_PKCS_PSS:
if (pMechanism->pParameter != NULL) {
CK_RSA_PKCS_PSS_PARAMS *param =
(CK_RSA_PKCS_PSS_PARAMS *) pMechanism->pParameter;
fprintf(spy_output, "pMechanism->pParameter->hashAlg=%s\n",
lookup_enum(MEC_T, param->hashAlg));
fprintf(spy_output, "pMechanism->pParameter->mgf=%s\n",
lookup_enum(MGF_T, param->mgf));
fprintf(spy_output, "pMechanism->pParameter->sLen=%lu\n",
param->sLen);
}
break;
}
spy_dump_ulong_in("hKey", hKey);
rv = po->C_SignInit(hSession, pMechanism, hKey);
return retne(rv);

View File

@ -153,6 +153,8 @@ extern "C" {
#define ck_mechanism_type_t CK_MECHANISM_TYPE
#define ck_rsa_pkcs_mgf_type_t CK_RSA_PKCS_MGF_TYPE
#define ck_mechanism _CK_MECHANISM
#define parameter pParameter
#define parameter_len ulParameterLen
@ -478,6 +480,8 @@ struct ck_date
typedef unsigned long ck_mechanism_type_t;
typedef unsigned long int ck_rsa_pkcs_mgf_type_t;
#define CKM_RSA_PKCS_KEY_PAIR_GEN (0UL)
#define CKM_RSA_PKCS (1UL)
#define CKM_RSA_9796 (2UL)
@ -508,6 +512,8 @@ typedef unsigned long ck_mechanism_type_t;
#define CKM_SHA256_RSA_PKCS_PSS (0x43UL)
#define CKM_SHA384_RSA_PKCS_PSS (0x44UL)
#define CKM_SHA512_RSA_PKCS_PSS (0x45UL)
#define CKM_SHA224_RSA_PKCS (0x46UL)
#define CKM_SHA224_RSA_PKCS_PSS (0x47UL)
#define CKM_RC2_KEY_GEN (0x100UL)
#define CKM_RC2_ECB (0x101UL)
#define CKM_RC2_CBC (0x102UL)
@ -553,6 +559,9 @@ typedef unsigned long ck_mechanism_type_t;
#define CKM_SHA256 (0x250UL)
#define CKM_SHA256_HMAC (0x251UL)
#define CKM_SHA256_HMAC_GENERAL (0x252UL)
#define CKM_SHA224 (0x255UL)
#define CKM_SHA224_HMAC (0x256UL)
#define CKM_SHA224_HMAC_GENERAL (0x257UL)
#define CKM_SHA384 (0x260UL)
#define CKM_SHA384_HMAC (0x261UL)
#define CKM_SHA384_HMAC_GENERAL (0x262UL)
@ -755,6 +764,17 @@ typedef struct CK_ECDH1_DERIVE_PARAMS {
unsigned char * pPublicData;
} CK_ECDH1_DERIVE_PARAMS;
typedef struct CK_RSA_PKCS_PSS_PARAMS {
ck_mechanism_type_t hashAlg;
unsigned long mgf;
unsigned long sLen;
} CK_RSA_PKCS_PSS_PARAMS;
#define CKG_MGF1_SHA1 (0x00000001UL)
#define CKG_MGF1_SHA224 (0x00000005UL)
#define CKG_MGF1_SHA256 (0x00000002UL)
#define CKG_MGF1_SHA384 (0x00000003UL)
#define CKG_MGF1_SHA512 (0x00000004UL)
typedef unsigned long ck_rv_t;
@ -1292,6 +1312,8 @@ typedef struct ck_date *CK_DATE_PTR;
typedef ck_mechanism_type_t *CK_MECHANISM_TYPE_PTR;
typedef ck_rsa_pkcs_mgf_type_t *CK_RSA_PKCS_MGF_TYPE_PTR;
typedef struct ck_mechanism CK_MECHANISM;
typedef struct ck_mechanism *CK_MECHANISM_PTR;
@ -1362,6 +1384,8 @@ typedef struct ck_c_initialize_args *CK_C_INITIALIZE_ARGS_PTR;
#undef ck_mechanism_type_t
#undef ck_rsa_pkcs_mgf_type_t
#undef ck_mechanism
#undef parameter
#undef parameter_len

View File

@ -36,12 +36,6 @@
extern "C" {
#endif
#if defined(_WIN32) || defined(USE_CYGWIN)
#define PKCS11_DEFAULT_MODULE_NAME "opensc-pkcs11.dll"
#else
#define PKCS11_DEFAULT_MODULE_NAME "opensc-pkcs11.so"
#endif
#define SC_PKCS11_PIN_UNBLOCK_NOT_ALLOWED 0
#define SC_PKCS11_PIN_UNBLOCK_UNLOGGED_SETPIN 1
#define SC_PKCS11_PIN_UNBLOCK_SCONTEXT_SETPIN 2

View File

@ -312,6 +312,16 @@ cosm_new_file(struct sc_profile *profile, struct sc_card *card,
num);
while (1) {
switch (type) {
case SC_PKCS15_TYPE_PRKEY_EC:
desc = "RSA private key";
_template = "private-key";
structure = SC_CARDCTL_OBERTHUR_KEY_EC_CRT;
break;
case SC_PKCS15_TYPE_PUBKEY_EC:
desc = "RSA public key";
_template = "public-key";
structure = SC_CARDCTL_OBERTHUR_KEY_EC_PUBLIC;
break;
case SC_PKCS15_TYPE_PRKEY_RSA:
desc = "RSA private key";
_template = "private-key";
@ -497,11 +507,14 @@ static int epass2003_pkcs15_generate_key(struct sc_profile *profile,
SC_FUNC_CALLED(card->ctx, SC_LOG_DEBUG_VERBOSE);
if (obj->type != SC_PKCS15_TYPE_PRKEY_RSA)
if (obj->type != SC_PKCS15_TYPE_PRKEY_RSA && obj->type != SC_PKCS15_TYPE_PRKEY_EC)
return SC_ERROR_NOT_SUPPORTED;
if(obj->type == SC_PKCS15_TYPE_PRKEY_EC && keybits == 0)
keybits = 256; //EC key length is 256 ...
/* allocate key object */
r = cosm_new_file(profile, card, SC_PKCS15_TYPE_PRKEY_RSA, idx, &file);
r = cosm_new_file(profile, card, obj->type, idx, &file); //replace SC_PKCS15_TYPE_PRKEY_RSA with obj->type
SC_TEST_GOTO_ERR(card->ctx, SC_LOG_DEBUG_NORMAL, r,
"create key: failed to allocate new key object");
file->size = keybits;
@ -525,11 +538,18 @@ static int epass2003_pkcs15_generate_key(struct sc_profile *profile,
"index %"SC_FORMAT_LEN_SIZE_T"u; keybits %"SC_FORMAT_LEN_SIZE_T"u\n",
idx, keybits);
if (keybits < 1024 || keybits > 2048 || (keybits % 0x20)) {
sc_debug(card->ctx, SC_LOG_DEBUG_VERBOSE_TOOL,
"Unsupported key size %"SC_FORMAT_LEN_SIZE_T"u\n",
keybits);
r = SC_ERROR_INVALID_ARGUMENTS;
goto err;
if(obj->type == SC_PKCS15_TYPE_PRKEY_EC && keybits == 256)
{
sc_log(card->ctx, "current Alg is EC,Only support 256 ..\n");
}
else
{
sc_debug(card->ctx, SC_LOG_DEBUG_VERBOSE_TOOL,
"Unsupported key size %"SC_FORMAT_LEN_SIZE_T"u\n",
keybits);
r = SC_ERROR_INVALID_ARGUMENTS;
goto err;
}
}
path = key_info->path;
@ -549,12 +569,23 @@ static int epass2003_pkcs15_generate_key(struct sc_profile *profile,
SC_TEST_GOTO_ERR(card->ctx, SC_LOG_DEBUG_NORMAL, r,
"generate key: pkcs15init_authenticate(SC_AC_OP_CREATE) failed");
if ((r = cosm_new_file(profile, card, SC_PKCS15_TYPE_PUBKEY_RSA, idx,
&pukf)) < 0) {
if (obj->type != SC_PKCS15_TYPE_PRKEY_RSA )
{
r = cosm_new_file(profile, card, SC_PKCS15_TYPE_PUBKEY_EC, idx, &pukf);
}
else
{
r = cosm_new_file(profile, card, SC_PKCS15_TYPE_PUBKEY_RSA, idx, &pukf);
}
if (r < 0) {
sc_debug(card->ctx, SC_LOG_DEBUG_NORMAL,
"generate key: create temporary pukf failed\n");
goto err;
}
pukf->size = keybits;
pukf->id = pukf->path.value[pukf->path.len - 2] * 0x100
+ pukf->path.value[pukf->path.len - 1];

View File

@ -4211,7 +4211,7 @@ sc_pkcs15init_read_info(struct sc_card *card, struct sc_profile *profile)
}
if (r >= 0)
r = sc_pkcs15init_parse_info(card, mem, len, profile);
r = sc_pkcs15init_parse_info(card, mem, r, profile);
if (mem)
free(mem);

View File

@ -188,6 +188,9 @@ static int cardos_info(void)
printf(" (that's CardOS M4.4)\n");
} else if (apdu.resp[0] == 0xc9 && apdu.resp[1] == 0x01) {
printf(" (that's CardOS V5.0)\n");
} else if (apdu.resp[0] == 0xc9 &&
(apdu.resp[1] == 0x02 || apdu.resp[1] == 0x03)) {
printf(" (that's CardOS V5.3)\n");
} else {
printf(" (unknown Version)\n");
}

View File

@ -26,10 +26,11 @@
#include <stdlib.h>
#ifndef _WIN32
#include <unistd.h>
#include <sys/types.h>
#include <sys/wait.h>
#include <unistd.h>
#else
#include <windows.h>
#include <io.h>
#endif
@ -133,6 +134,7 @@ enum {
OPT_KEY_USAGE_DECRYPT,
OPT_KEY_USAGE_DERIVE,
OPT_PRIVATE,
OPT_SENSITIVE,
OPT_TEST_HOTPLUG,
OPT_UNLOCK_PIN,
OPT_PUK,
@ -145,6 +147,9 @@ enum {
OPT_TEST_FORK,
OPT_GENERATE_KEY,
OPT_GENERATE_RANDOM,
OPT_HASH_ALGORITHM,
OPT_MGF,
OPT_SALT,
};
static const struct option options[] = {
@ -161,6 +166,9 @@ static const struct option options[] = {
{ "derive", 0, NULL, OPT_DERIVE },
{ "derive-pass-der", 0, NULL, OPT_DERIVE_PASS_DER },
{ "mechanism", 1, NULL, 'm' },
{ "hash-algorithm", 1, NULL, OPT_HASH_ALGORITHM },
{ "mgf", 1, NULL, OPT_MGF },
{ "salt-len", 1, NULL, OPT_SALT },
{ "login", 0, NULL, 'l' },
{ "login-type", 1, NULL, OPT_LOGIN_TYPE },
@ -203,6 +211,7 @@ static const struct option options[] = {
{ "moz-cert", 1, NULL, 'z' },
{ "verbose", 0, NULL, 'v' },
{ "private", 0, NULL, OPT_PRIVATE },
{ "sensitive", 0, NULL, OPT_SENSITIVE },
{ "test-ec", 0, NULL, OPT_TEST_EC },
#ifndef _WIN32
{ "test-fork", 0, NULL, OPT_TEST_FORK },
@ -226,6 +235,9 @@ static const char *option_help[] = {
"Derive a secret key using another key and some data",
"Derive ECDHpass DER encoded pubkey for compatibility with some PKCS#11 implementations",
"Specify mechanism (use -M for a list of supported mechanisms)",
"Specify hash algorithm used with RSA-PKCS-PSS signature",
"Specify MGF (Message Generation Function) used for RSA-PSS signatures (possible values are MGF1-SHA1 to MGF1-SHA512)",
"Specify how many bytes should be used for salt in RSA-PSS signatures (default is digest size)",
"Log into the token first",
"Specify login type ('so', 'user', 'context-specific'; default:'user')",
@ -268,6 +280,7 @@ static const char *option_help[] = {
"Test Mozilla-like keypair gen and cert req, <arg>=certfile",
"Verbose operation. (Set OPENSC_DEBUG to enable OpenSC specific debugging)",
"Set the CKA_PRIVATE attribute (object is only viewable after a login)",
"Set the CKA_SENSITIVE attribute (object cannot be revealed in plaintext)",
"Test EC (best used with the --login or --pin option)",
#ifndef _WIN32
"Test forking and calling C_Initialize() in the child",
@ -307,6 +320,7 @@ static char * opt_subject = NULL;
static char * opt_key_type = NULL;
static char * opt_sig_format = NULL;
static int opt_is_private = 0;
static int opt_is_sensitive = 0;
static int opt_test_hotplug = 0;
static int opt_login_type = -1;
static int opt_key_usage_sign = 0;
@ -315,6 +329,10 @@ static int opt_key_usage_derive = 0;
static int opt_key_usage_default = 1; /* uses defaults if no opt_key_usage options */
static int opt_derive_pass_der = 0;
static unsigned long opt_random_bytes = 0;
static CK_MECHANISM_TYPE opt_hash_alg = 0;
static unsigned long opt_mgf = 0;
static long salt_len = 0;
static int salt_len_given = 0; /* 0 - not given, 1 - given with input parameters */
static void *module = NULL;
static CK_FUNCTION_LIST_PTR p11 = NULL;
@ -405,6 +423,8 @@ static const char * p11_utf8_to_local(CK_UTF8CHAR *, size_t);
static const char * p11_flag_names(struct flag_info *, CK_FLAGS);
static const char * p11_mechanism_to_name(CK_MECHANISM_TYPE);
static CK_MECHANISM_TYPE p11_name_to_mechanism(const char *);
static const char * p11_mgf_to_name(CK_RSA_PKCS_MGF_TYPE);
static CK_MECHANISM_TYPE p11_name_to_mgf(const char *);
static void p11_perror(const char *, CK_RV);
static const char * CKR2Str(CK_ULONG res);
static int p11_test(CK_SESSION_HANDLE session);
@ -537,6 +557,9 @@ int main(int argc, char * argv[])
CK_RV rv;
#ifdef _WIN32
char expanded_val[PATH_MAX];
DWORD expanded_len;
if(_setmode(_fileno(stdout), _O_BINARY ) == -1)
util_fatal("Cannot set FMODE to O_BINARY");
if(_setmode(_fileno(stdin), _O_BINARY ) == -1)
@ -669,6 +692,16 @@ int main(int argc, char * argv[])
opt_mechanism_used = 1;
opt_mechanism = p11_name_to_mechanism(optarg);
break;
case OPT_HASH_ALGORITHM:
opt_hash_alg = p11_name_to_mechanism(optarg);
break;
case OPT_MGF:
opt_mgf = p11_name_to_mgf(optarg);
break;
case OPT_SALT:
salt_len = (CK_ULONG) strtoul(optarg, NULL, 0);
salt_len_given = 1;
break;
case 'o':
opt_output = optarg;
break;
@ -804,6 +837,9 @@ int main(int argc, char * argv[])
case OPT_PRIVATE:
opt_is_private = 1;
break;
case OPT_SENSITIVE:
opt_is_sensitive = 1;
break;
case OPT_TEST_HOTPLUG:
opt_test_hotplug = 1;
action_count++;
@ -844,6 +880,13 @@ int main(int argc, char * argv[])
if (action_count == 0)
util_print_usage_and_die(app_name, options, option_help, NULL);
#ifdef _WIN32
expanded_len = PATH_MAX;
expanded_len = ExpandEnvironmentStringsA(opt_module, expanded_val, expanded_len);
if (0 < expanded_len && expanded_len < sizeof expanded_val)
opt_module = expanded_val;
#endif
module = C_LoadModule(opt_module, &p11);
if (module == NULL)
util_fatal("Failed to load pkcs11 module");
@ -1318,7 +1361,7 @@ static int login(CK_SESSION_HANDLE session, int login_type)
pin_flags=info.flags & (
CKF_SO_PIN_COUNT_LOW |
CKF_SO_PIN_FINAL_TRY |
CKF_SO_PIN_LOCKED |
CKF_SO_PIN_LOCKED |
CKF_SO_PIN_TO_BE_CHANGED);
if(pin_flags)
printf("WARNING: %s\n",p11_token_info_flags(pin_flags));
@ -1329,7 +1372,7 @@ static int login(CK_SESSION_HANDLE session, int login_type)
pin_flags=info.flags & (
CKF_USER_PIN_COUNT_LOW |
CKF_USER_PIN_FINAL_TRY |
CKF_USER_PIN_LOCKED |
CKF_USER_PIN_LOCKED |
CKF_USER_PIN_TO_BE_CHANGED);
if(pin_flags)
printf("WARNING: %s\n",p11_token_info_flags(pin_flags));
@ -1591,15 +1634,45 @@ static int unlock_pin(CK_SLOT_ID slot, CK_SESSION_HANDLE sess, int login_type)
return 0;
}
/* return digest length in bytes */
static unsigned long figure_pss_salt_length(const int hash) {
unsigned long sLen = 0;
switch (hash) {
case CKM_SHA_1:
sLen = 20;
break;
case CKM_SHA224:
sLen = 28;
break;
case CKM_SHA256:
sLen = 32;
break;
case CKM_SHA384:
sLen = 48;
break;
case CKM_SHA512:
sLen = 64;
break;
default:
util_fatal("Unknown hash algorithm '%s' for RSA-PSS signatures",
p11_mechanism_to_name(hash));
break;
}
return sLen;
}
static void sign_data(CK_SLOT_ID slot, CK_SESSION_HANDLE session,
CK_OBJECT_HANDLE key)
{
unsigned char in_buffer[1025], sig_buffer[512];
CK_MECHANISM mech;
CK_RSA_PKCS_PSS_PARAMS pss_params;
CK_RV rv;
CK_ULONG sig_len;
int fd, r;
unsigned long hashlen = 0, modlen = 0;
if (!opt_mechanism_used)
if (!find_mechanism(slot, CKF_SIGN|CKF_HW, NULL, 0, &opt_mechanism))
util_fatal("Sign mechanism not supported");
@ -1607,6 +1680,93 @@ static void sign_data(CK_SLOT_ID slot, CK_SESSION_HANDLE session,
fprintf(stderr, "Using signature algorithm %s\n", p11_mechanism_to_name(opt_mechanism));
memset(&mech, 0, sizeof(mech));
mech.mechanism = opt_mechanism;
pss_params.hashAlg = 0;
if (opt_hash_alg != 0 && opt_mechanism != CKM_RSA_PKCS_PSS)
util_fatal("The hash-algorithm is applicable only to "
"RSA-PKCS-PSS mechanism");
/* set "default" MGF and hash algorithms. We can overwrite MGF later */
switch (opt_mechanism) {
case CKM_RSA_PKCS_PSS:
pss_params.hashAlg = opt_hash_alg;
switch (opt_hash_alg) {
case CKM_SHA256:
pss_params.mgf = CKG_MGF1_SHA256;
break;
case CKM_SHA384:
pss_params.mgf = CKG_MGF1_SHA384;
break;
case CKM_SHA512:
pss_params.mgf = CKG_MGF1_SHA512;
break;
default:
/* the PSS should use SHA-1 if not specified */
pss_params.hashAlg = CKM_SHA_1;
/* fallthrough */
case CKM_SHA_1:
pss_params.mgf = CKG_MGF1_SHA1;
}
break;
case CKM_SHA1_RSA_PKCS_PSS:
pss_params.hashAlg = CKM_SHA_1;
pss_params.mgf = CKG_MGF1_SHA1;
break;
case CKM_SHA256_RSA_PKCS_PSS:
pss_params.hashAlg = CKM_SHA256;
pss_params.mgf = CKG_MGF1_SHA256;
break;
case CKM_SHA384_RSA_PKCS_PSS:
pss_params.hashAlg = CKM_SHA384;
pss_params.mgf = CKG_MGF1_SHA384;
break;
case CKM_SHA512_RSA_PKCS_PSS:
pss_params.hashAlg = CKM_SHA512;
pss_params.mgf = CKG_MGF1_SHA512;
break;
}
/* One of RSA-PSS mechanisms above: They need parameters */
if (pss_params.hashAlg) {
if (opt_mgf != 0)
pss_params.mgf = opt_mgf;
hashlen = figure_pss_salt_length(pss_params.hashAlg);
if (salt_len_given == 1) { /* salt size explicitly given */
if (salt_len < 0 && salt_len != -1 && salt_len != -2)
util_fatal("Salt length must be greater or equal \
to zero, or equal to -1 (meaning: use digest size) or to -2 \
(meaning: use maximum permissible size");
modlen = (get_private_key_length(session, key) + 7) / 8;
switch(salt_len) {
case -1: /* salt size equals to digest size */
pss_params.sLen = hashlen;
break;
case -2: /* maximum permissible salt len */
pss_params.sLen = modlen - hashlen -2;
break;
default: /* use given size but its value must be >= 0 */
pss_params.sLen = salt_len;
break;
} /* end switch (salt_len_given) */
} else { /* use default: salt len of digest size */
pss_params.sLen = hashlen;
}
mech.pParameter = &pss_params;
mech.ulParameterLen = sizeof(pss_params);
fprintf(stderr, "PSS parameters: hashAlg=%s, mgf=%s, salt=%lu B\n",
p11_mechanism_to_name(pss_params.hashAlg),
p11_mgf_to_name(pss_params.mgf),
pss_params.sLen);
}
if (opt_input == NULL)
fd = 0;
@ -1659,7 +1819,7 @@ static void sign_data(CK_SLOT_ID slot, CK_SESSION_HANDLE session,
util_fatal("failed to open %s: %m", opt_output);
}
if (opt_mechanism == CKM_ECDSA || opt_mechanism == CKM_ECDSA_SHA1) {
if (opt_mechanism == CKM_ECDSA || opt_mechanism == CKM_ECDSA_SHA1 || opt_mechanism == CKM_ECDSA_SHA256 || opt_mechanism == CKM_ECDSA_SHA384 || opt_mechanism == CKM_ECDSA_SHA512) {
if (opt_sig_format && (!strcmp(opt_sig_format, "openssl") || !strcmp(opt_sig_format, "sequence"))) {
unsigned char *seq;
size_t seqlen;
@ -2028,6 +2188,7 @@ gen_key(CK_SLOT_ID slot, CK_SESSION_HANDLE session, CK_OBJECT_HANDLE *hSecretKey
CK_MECHANISM mechanism = {CKM_AES_KEY_GEN, NULL_PTR, 0};
CK_OBJECT_CLASS secret_key_class = CKO_SECRET_KEY;
CK_BBOOL _true = TRUE;
CK_BBOOL _false = FALSE;
CK_KEY_TYPE key_type = CKK_AES;
CK_ULONG key_length;
CK_ATTRIBUTE keyTemplate[20] = {
@ -2102,6 +2263,15 @@ gen_key(CK_SLOT_ID slot, CK_SESSION_HANDLE session, CK_OBJECT_HANDLE *hSecretKey
util_fatal("Unknown key type %s", type);
}
if (opt_is_sensitive != 0) {
FILL_ATTR(keyTemplate[n_attr], CKA_SENSITIVE, &_true, sizeof(_true));
n_attr++;
}
else {
FILL_ATTR(keyTemplate[n_attr], CKA_SENSITIVE, &_false, sizeof(_false));
n_attr++;
}
FILL_ATTR(keyTemplate[n_attr], CKA_ENCRYPT, &_true, sizeof(_true));
n_attr++;
FILL_ATTR(keyTemplate[n_attr], CKA_DECRYPT, &_true, sizeof(_true));
@ -4310,14 +4480,14 @@ static int test_signature(CK_SESSION_HANDLE sess)
break;
case CKM_RSA_X_509:
dataLen = modLenBytes;
pseudo_randomize(data, dataLen);
break;
default:
dataLen = sizeof(data); /* let's hope it's OK */
pseudo_randomize(data, dataLen);
break;
}
pseudo_randomize(data, dataLen);
if (firstMechType == CKM_RSA_X_509) {
/* make sure our data is smaller than the modulus */
data[0] = 0x00;
@ -4836,7 +5006,7 @@ static int encrypt_decrypt(CK_SESSION_HANDLE session,
return 0;
if (EVP_PKEY_size(pkey) > (int)sizeof(encrypted)) {
fprintf(stderr, "Ciphertext buffer too small\n");
printf("Ciphertext buffer too small\n");
EVP_PKEY_free(pkey);
return 0;
}
@ -4847,14 +5017,14 @@ static int encrypt_decrypt(CK_SESSION_HANDLE session,
#endif
EVP_PKEY_free(pkey);
if (((int) encrypted_len) <= 0) {
fprintf(stderr, "Encryption failed, returning\n");
printf("Encryption failed, returning\n");
return 0;
}
mech.mechanism = mech_type;
rv = p11->C_DecryptInit(session, &mech, privKeyObject);
if (rv == CKR_MECHANISM_INVALID) {
fprintf(stderr, "Mechanism not supported\n");
if (rv == CKR_MECHANISM_INVALID || rv == CKR_MECHANISM_PARAM_INVALID) {
printf("Mechanism not supported\n");
return 0;
}
if (rv != CKR_OK)
@ -5621,10 +5791,10 @@ static struct mech_info p11_mechanisms[] = {
{ CKM_RSA_X9_31, "RSA-X9-31", NULL },
{ CKM_SHA1_RSA_X9_31, "SHA1-RSA-X9-31", NULL },
{ CKM_RSA_PKCS_PSS, "RSA-PKCS-PSS", NULL },
{ CKM_SHA1_RSA_PKCS_PSS, "SHA1-RSA-PKCS-PSS", NULL },
{ CKM_SHA256_RSA_PKCS, "SHA256-RSA-PKCS-PSS", NULL },
{ CKM_SHA384_RSA_PKCS, "SHA384-RSA-PKCS-PSS", NULL },
{ CKM_SHA512_RSA_PKCS, "SHA512-RSA-PKCS-PSS", NULL },
{ CKM_SHA1_RSA_PKCS_PSS, "SHA1-RSA-PKCS-PSS", "rsa-pss-sha1" },
{ CKM_SHA256_RSA_PKCS_PSS,"SHA256-RSA-PKCS-PSS", "rsa-pss-sha256" },
{ CKM_SHA384_RSA_PKCS_PSS,"SHA384-RSA-PKCS-PSS", "rsa-pss-sha384" },
{ CKM_SHA512_RSA_PKCS_PSS,"SHA512-RSA-PKCS-PSS", "rsa-pss-sha512" },
{ CKM_DSA_KEY_PAIR_GEN, "DSA-KEY-PAIR-GEN", NULL },
{ CKM_DSA, "DSA", NULL },
{ CKM_DSA_SHA1, "DSA-SHA1", NULL },
@ -5671,8 +5841,11 @@ static struct mech_info p11_mechanisms[] = {
{ CKM_SHA_1_HMAC, "SHA-1-HMAC", NULL },
{ CKM_SHA_1_HMAC_GENERAL, "SHA-1-HMAC-GENERAL", NULL },
{ CKM_SHA256, "SHA256", NULL },
{ CKM_SHA256_HMAC, "SHA256-HMAC", NULL },
{ CKM_SHA384, "SHA384", NULL },
{ CKM_SHA384_HMAC, "SHA384-HMAC", NULL },
{ CKM_SHA512, "SHA512", NULL },
{ CKM_SHA512_HMAC, "SHA512-HMAC", NULL },
{ CKM_RIPEMD128, "RIPEMD128", NULL },
{ CKM_RIPEMD128_HMAC, "RIPEMD128-HMAC", NULL },
{ CKM_RIPEMD128_HMAC_GENERAL,"RIPEMD128-HMAC-GENERAL", NULL },
@ -5770,7 +5943,7 @@ static struct mech_info p11_mechanisms[] = {
{ CKM_ECDSA_SHA1, "ECDSA-SHA1", NULL },
{ CKM_ECDSA_SHA224, "ECDSA-SHA224", NULL },
{ CKM_ECDSA_SHA256, "ECDSA-SHA256", NULL },
{ CKM_ECDSA_SHA384, "ECDSA-SHA348", NULL },
{ CKM_ECDSA_SHA384, "ECDSA-SHA384", NULL },
{ CKM_ECDSA_SHA512, "ECDSA-SHA512", NULL },
{ CKM_ECDH1_DERIVE, "ECDH1-DERIVE", NULL },
{ CKM_ECDH1_COFACTOR_DERIVE,"ECDH1-COFACTOR-DERIVE", NULL },
@ -5798,6 +5971,15 @@ static struct mech_info p11_mechanisms[] = {
{ 0, NULL, NULL }
};
static struct mech_info p11_mgf[] = {
{ CKG_MGF1_SHA1, "MGF1-SHA1", NULL },
{ CKG_MGF1_SHA224, "MGF1-SHA224", NULL },
{ CKG_MGF1_SHA256, "MGF1-SHA256", NULL },
{ CKG_MGF1_SHA384, "MGF1-SHA384", NULL },
{ CKG_MGF1_SHA512, "MGF1-SHA512", NULL },
{ 0, NULL, NULL }
};
static const char *p11_mechanism_to_name(CK_MECHANISM_TYPE mech)
{
static char temp[64];
@ -5824,6 +6006,30 @@ static CK_MECHANISM_TYPE p11_name_to_mechanism(const char *name)
return 0; /* gcc food */
}
static CK_RSA_PKCS_MGF_TYPE p11_name_to_mgf(const char *name)
{
struct mech_info *mi;
for (mi = p11_mgf; mi->name; mi++) {
if (!strcasecmp(mi->name, name))
return mi->mech;
}
util_fatal("Unknown PKCS11 MGF \"%s\"", name);
}
static const char *p11_mgf_to_name(CK_RSA_PKCS_MGF_TYPE mgf)
{
static char temp[64];
struct mech_info *mi;
for (mi = p11_mgf; mi->name; mi++) {
if (mi->mech == mgf)
return mi->name;
}
snprintf(temp, sizeof(temp), "mgf-0x%lX", (unsigned long) mgf);
return temp;
}
static const char * CKR2Str(CK_ULONG res)
{
switch (res) {

View File

@ -232,7 +232,8 @@ void util_hex_dump_asc(FILE *f, const u8 *in, size_t count, int addr)
}
}
void util_print_usage_and_die(const char *app_name, const struct option options[],
NORETURN void
util_print_usage_and_die(const char *app_name, const struct option options[],
const char *option_help[], const char *args)
{
int i;
@ -343,7 +344,7 @@ const char * util_acl_to_str(const sc_acl_entry_t *e)
return line;
}
void
NORETURN void
util_fatal(const char *fmt, ...)
{
va_list ap;

View File

@ -23,15 +23,28 @@
extern "C" {
#endif
#if _MSC_VER >= 1310
/* MS Visual Studio 2003/.NET Framework 1.1 or newer */
# define NORETURN _declspec( noreturn)
#elif __GNUC__ > 2 || (__GNUC__ == 2 && (__GNUC_MINOR__ >= 5)) || (defined __clang__)
# define NORETURN __attribute__ ((noreturn))
#elif __cplusplus >= 201103L
# define NORETURN [[noreturn]]
#elif __STDC_VERSION__ >= 201112L
# define NORETURN _Noreturn
#else
# define NORETURN
#endif
void util_print_binary(FILE *f, const u8 *buf, int count);
void util_hex_dump(FILE *f, const u8 *in, int len, const char *sep);
void util_hex_dump_asc(FILE *f, const u8 *in, size_t count, int addr);
void util_print_usage_and_die(const char *app_name, const struct option options[],
NORETURN void util_print_usage_and_die(const char *app_name, const struct option options[],
const char *option_help[], const char *args);
const char * util_acl_to_str(const struct sc_acl_entry *e);
void util_warn(const char *fmt, ...);
void util_error(const char *fmt, ...);
void util_fatal(const char *fmt, ...);
NORETURN void util_fatal(const char *fmt, ...);
/* All singing all dancing card connect routine */
int util_connect_card_ex(struct sc_context *, struct sc_card **, const char *reader_id, int do_wait, int do_lock, int verbose);
int util_connect_card(struct sc_context *, struct sc_card **, const char *reader_id, int do_wait, int verbose);

View File

@ -45,15 +45,27 @@ OPENSSL_STATIC_DIR = static
!IF "$(DEBUG_DEF)" == "/DDEBUG"
!IF "$(PLATFORM)" == "x86"
OPENSSL_LIB = $(OPENSSL_DIR)\lib\VC\$(OPENSSL_STATIC_DIR)\libcrypto32MTd.lib user32.lib advapi32.lib crypt32.lib ws2_32.lib
# OpenSSL 1.0.2
OPENSSL_LIB = $(OPENSSL_DIR)\lib\VC\$(OPENSSL_STATIC_DIR)\libeay32MTd.lib user32.lib advapi32.lib crypt32.lib ws2_32.lib
# OpenSSL 1.1.0
#OPENSSL_LIB = $(OPENSSL_DIR)\lib\VC\$(OPENSSL_STATIC_DIR)\libcrypto32MTd.lib user32.lib advapi32.lib crypt32.lib ws2_32.lib
!ELSE
OPENSSL_LIB = $(OPENSSL_DIR)\lib\VC\$(OPENSSL_STATIC_DIR)\libcrypto64MTd.lib user32.lib advapi32.lib crypt32.lib ws2_32.lib
# OpenSSL 1.0.2
OPENSSL_LIB = $(OPENSSL_DIR)\lib\VC\$(OPENSSL_STATIC_DIR)\libeay32MTd.lib user32.lib advapi32.lib crypt32.lib ws2_32.lib
# OpenSSL 1.1.0
#OPENSSL_LIB = $(OPENSSL_DIR)\lib\VC\$(OPENSSL_STATIC_DIR)\libcrypto64MTd.lib user32.lib advapi32.lib crypt32.lib ws2_32.lib
!ENDIF
!ELSE
!IF "$(PLATFORM)" == "x86"
OPENSSL_LIB = $(OPENSSL_DIR)\lib\VC\$(OPENSSL_STATIC_DIR)\libcrypto32MT.lib user32.lib advapi32.lib crypt32.lib ws2_32.lib
# OpenSSL 1.0.2
OPENSSL_LIB = $(OPENSSL_DIR)\lib\VC\$(OPENSSL_STATIC_DIR)\libeay32MT.lib user32.lib advapi32.lib crypt32.lib ws2_32.lib
# OpenSSL 1.1.0
#OPENSSL_LIB = $(OPENSSL_DIR)\lib\VC\$(OPENSSL_STATIC_DIR)\libcrypto32MT.lib user32.lib advapi32.lib crypt32.lib ws2_32.lib
!ELSE
OPENSSL_LIB = $(OPENSSL_DIR)\lib\VC\$(OPENSSL_STATIC_DIR)\libcrypto64MT.lib user32.lib advapi32.lib crypt32.lib ws2_32.lib
# OpenSSL 1.0.2
OPENSSL_LIB = $(OPENSSL_DIR)\lib\VC\$(OPENSSL_STATIC_DIR)\libeay32MT.lib user32.lib advapi32.lib crypt32.lib ws2_32.lib
# OpenSSL 1.1.0
#OPENSSL_LIB = $(OPENSSL_DIR)\lib\VC\$(OPENSSL_STATIC_DIR)\libcrypto64MT.lib user32.lib advapi32.lib crypt32.lib ws2_32.lib
!ENDIF
!ENDIF

View File

@ -7,7 +7,6 @@
<?endif ?>
<?define Win64YesNo="yes" ?>
<?define PlatformProgramFilesFolder = "ProgramFiles64Folder" ?>
<?define PlatformSystemFolder = "System64Folder" ?>
<?define PlatformUpgradeCode = "{9A449570-69A2-11E0-9CC6-955B4824019B}" ?>
<?else ?>
<?ifndef OpenSSL ?>
@ -17,7 +16,6 @@
<?endif ?>
<?define Win64YesNo="no" ?>
<?define PlatformProgramFilesFolder = "ProgramFilesFolder" ?>
<?define PlatformSystemFolder = "SystemFolder" ?>
<?define PlatformUpgradeCode = "{69428F65-B96D-458D-BB87-DBB5FDB35DCE}" ?>
<?endif ?>
@ -59,56 +57,10 @@
<MajorUpgrade DowngradeErrorMessage="Can't downgrade." AllowSameVersionUpgrades="yes"/>
<Directory Id="TARGETDIR" Name="SourceDir">
<!-- Install critical DLL-s to system folder. NB! Id-s can not contain "-" characters! -->
<Directory Id="$(var.PlatformSystemFolder)" Name=".">
<Component Id="opensc_pkcs11.dll" Guid="*" Win64="$(var.Win64YesNo)">
<File Source="$(var.SOURCE_DIR)\src\pkcs11\opensc-pkcs11.dll" Vital="yes"/>
</Component>
<Component Id="onepin_opensc_pkcs11.dll" Guid="*" Win64="$(var.Win64YesNo)">
<File Source="$(var.SOURCE_DIR)\src\pkcs11\onepin-opensc-pkcs11.dll" Vital="yes"/>
</Component>
<Component Id="opensc_minidriver.dll" Guid="*" Win64="$(var.Win64YesNo)">
<File Source="$(var.SOURCE_DIR)\src\minidriver\opensc-minidriver.dll" Vital="yes"/>
</Component>
<!-- install an alias for the Base smart card CSP. Using a different CSP in minidriver installation deactivate the plug and play feature
but not all other components like the pin change screen available after ctrl+alt+del.
It is because the "80000001" entry is still returning the minidriver dll.-->
<Component Id="openscBaseCSP" Guid="*" Win64="$(var.Win64YesNo)">
<RegistryKey Root="HKLM" Key="SOFTWARE\Microsoft\Cryptography\Defaults\Provider\OpenSC CSP">
<RegistryValue Type="string" Name="Image Path" Value="basecsp.dll" KeyPath="yes"/>
<RegistryValue Type="integer" Name="Type" Value="1"/>
</RegistryKey>
<!-- when the x64 installer will install x86 components on x64 plateform too
<?if $(var.Platform) = x64 ?>
<RegistryKey Root="HKLM" Key="SOFTWARE\Wow6432Node\Microsoft\Cryptography\Defaults\Provider\OpenSC CSP">
<RegistryValue Type="string" Name="Image Path" Value="basecsp.dll"/>
<RegistryValue Type="integer" Name="Type" Value="1"/>
</RegistryKey>
<?endif?>
-->
</Component>
<Component Id="CertPropSvc" Guid="*" Win64="$(var.Win64YesNo)" Permanent="yes">
<!-- CertPropSvc loads the minidriver and propagates the smart card's
certificates to the user's certificate store, see https://technet.microsoft.com/en-us/itpro/windows/keep-secure/smart-card-certificate-propagation-service -->
<ServiceControl Id="ControlCertPropSvcStart" Name="CertPropSvc" Start="install" Wait="no" />
<ServiceControl Id="ControlCertPropSvcStop" Name="CertPropSvc" Stop="uninstall" Wait="yes" />
<RegistryKey Root="HKLM" Key="SYSTEM\CurrentControlSet\Services\CertPropSvc">
<RegistryValue Type="integer" Name="Start" Value="2" KeyPath="yes"/>
</RegistryKey>
</Component>
</Directory>
<!-- Install tools and profiles to Program Files -->
<Directory Id="$(var.PlatformProgramFilesFolder)" Name="PFiles">
<Directory Id="OpenSC_Project_Dir" Name="OpenSC Project">
<!-- Most of the stuff goes to the Program Files folder -->
<Directory Id="PKCS11SPYINSTALLDIR" Name="PKCS11-Spy">
<Component Id="pkcs11_spy.dll" Guid="*" Win64="$(var.Win64YesNo)">
<File Source="$(var.SOURCE_DIR)\src\pkcs11\pkcs11-spy.dll"/>
<RegistryKey Id="Pkcs11SpyRegs" Root="HKLM" Key="Software\[Manufacturer]\PKCS11-Spy" Action="createAndRemoveOnUninstall">
<RegistryValue Type="string" Name="Module" Value="%SystemRoot%\system32\opensc-pkcs11.dll"/>
<RegistryValue Type="string" Name="Output" Value="%TEMP%\pkcs11-spy.log"/>
</RegistryKey>
</Component>
</Directory>
<Directory Id="INSTALLDIR" Name="OpenSC">
<!-- opensc.conf sample goes to installation directory -->
<Component Id="opensc.conf" Guid="*" Win64="$(var.Win64YesNo)">
@ -122,6 +74,47 @@
</RegistryKey>
</Component>
<Directory Id="INSTALLDIR_MINIDRIVER" Name="minidriver">
<Component Id="opensc_minidriver.dll" Guid="*" Win64="$(var.Win64YesNo)">
<File Source="$(var.SOURCE_DIR)\src\minidriver\opensc-minidriver.dll" Vital="yes"/>
</Component>
<!-- install an alias for the Base smart card CSP. Using a different CSP in minidriver installation deactivate the plug and play feature
but not all other components like the pin change screen available after ctrl+alt+del.
It is because the "80000001" entry is still returning the minidriver dll.-->
<Component Id="openscBaseCSP" Guid="*" Win64="$(var.Win64YesNo)">
<RegistryKey Root="HKLM" Key="SOFTWARE\Microsoft\Cryptography\Defaults\Provider\OpenSC CSP">
<RegistryValue Type="string" Name="Image Path" Value="basecsp.dll" KeyPath="yes"/>
<RegistryValue Type="integer" Name="Type" Value="1"/>
</RegistryKey>
<!-- when the x64 installer will install x86 components on x64 plateform too
<?if $(var.Platform) = x64 ?>
<RegistryKey Root="HKLM" Key="SOFTWARE\Wow6432Node\Microsoft\Cryptography\Defaults\Provider\OpenSC CSP">
<RegistryValue Type="string" Name="Image Path" Value="basecsp.dll"/>
<RegistryValue Type="integer" Name="Type" Value="1"/>
</RegistryKey>
<?endif?>
-->
</Component>
<Component Id="CertPropSvc" Guid="*" Win64="$(var.Win64YesNo)" Permanent="yes">
<!-- CertPropSvc loads the minidriver and propagates the smart card's
certificates to the user's certificate store, see https://technet.microsoft.com/en-us/itpro/windows/keep-secure/smart-card-certificate-propagation-service -->
<ServiceControl Id="ControlCertPropSvcStart" Name="CertPropSvc" Start="install" Wait="no" />
<ServiceControl Id="ControlCertPropSvcStop" Name="CertPropSvc" Stop="uninstall" Wait="yes" />
<RegistryKey Root="HKLM" Key="SYSTEM\CurrentControlSet\Services\CertPropSvc">
<RegistryValue Type="integer" Name="Start" Value="2" KeyPath="yes"/>
</RegistryKey>
</Component>
</Directory>
<Directory Id="INSTALLDIR_PKCS11" Name="pkcs11">
<Component Id="opensc_pkcs11.dll" Guid="*" Win64="$(var.Win64YesNo)">
<File Source="$(var.SOURCE_DIR)\src\pkcs11\opensc-pkcs11.dll" Vital="yes"/>
</Component>
<Component Id="onepin_opensc_pkcs11.dll" Guid="*" Win64="$(var.Win64YesNo)">
<File Source="$(var.SOURCE_DIR)\src\pkcs11\onepin-opensc-pkcs11.dll" Vital="yes"/>
</Component>
</Directory>
<!-- Tools have their own folder -->
<Directory Id="INSTALLDIR_TOOLS" Name="tools">
<?ifdef zlib ?>
@ -300,6 +293,15 @@
</Directory>
<?endif ?>
</Directory>
<Directory Id="PKCS11SPYINSTALLDIR" Name="PKCS11-Spy">
<Component Id="pkcs11_spy.dll" Guid="*" Win64="$(var.Win64YesNo)">
<File Source="$(var.SOURCE_DIR)\src\pkcs11\pkcs11-spy.dll"/>
<RegistryKey Id="Pkcs11SpyRegs" Root="HKLM" Key="Software\[Manufacturer]\PKCS11-Spy" Action="createAndRemoveOnUninstall">
<RegistryValue Type="string" Name="Module" Value="[INSTALLDIR_MINIDRIVER]opensc-pkcs11.dll"/>
<RegistryValue Type="string" Name="Output" Value="%TEMP%\pkcs11-spy.log"/>
</RegistryKey>
</Component>
</Directory>
</Directory>
</Directory>
<Directory Id="ProgramMenuFolder" Name="Programs">

View File

@ -64,12 +64,10 @@ typedef struct _MD_REGISTRATION
For example, do not uninstall the minidriver for a card if a middleware is already installed */
MD_REGISTRATION minidriver_registration[] = {
/* from minidriver-feitian.reg */
{TEXT("ePass2003"), {0x3b,0x9f,0x95,0x81,0x31,0xfe,0x9f,0x00,0x66,0x46,0x53,0x05,0x01,0x00,0x11,0x71,0xdf,0x00,0x00,0x03,0x6a,0x82,0xf8},
23, {0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff}},
{TEXT("FTCOS/PK-01C"), {0x3b,0x9f,0x95,0x81,0x31,0xfe,0x9f,0x00,0x65,0x46,0x53,0x05,0x00,0x06,0x71,0xdf,0x00,0x00,0x00,0x00,0x00,0x00,0x00},
23, {0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0x00,0xff,0xff,0xff,0xff,0xff,0xff,0x00,0x00,0x00,0x00}},
/* from minidriver-sc-hsm.reg */
{TEXT("SmartCard-HSM"), {0x3b,0xfe,0x18,0x00,0x00,0x81,0x31,0xfe,0x45,0x80,0x31,0x81,0x54,0x48,0x53,0x4d,0x31,0x73,0x80,0x21,0x40,0x81,0x07,0xfa},
24, {0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff}},
{TEXT("SmartCard-HSM-CL"), {0x3B,0x8E,0x80,0x01,0x80,0x31,0x81,0x54,0x48,0x53,0x4D,0x31,0x73,0x80,0x21,0x40,0x81,0x07,0x18},
@ -100,7 +98,6 @@ MD_REGISTRATION minidriver_registration[] = {
19, {0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}},
{TEXT("GoID (11)"), {0x3B,0x8f,0x80,0x01,0x47,0x6f,0x49,0x44,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00},
20, {0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00}},
/* from minidriver-westcos.reg */
{TEXT("CEV WESTCOS"), {0x3f,0x69,0x00,0x00,0x00,0x64,0x01,0x00,0x00,0x00,0x80,0x90,0x00},
13, {0xff,0xff,0xff,0xff,0xff,0xff,0xff,0x00,0x00,0x00,0xf0,0xff,0xff}},
/* from card-openpgp.c */
@ -120,12 +117,14 @@ MD_REGISTRATION minidriver_registration[] = {
/* from card-cardos.c */
{TEXT("CardOS 4.0"), {0x3b,0xe2,0x00,0xff,0xc1,0x10,0x31,0xfe,0x55,0xc8,0x02,0x9c},
12, {0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff}},
{TEXT("Italian eID card, postecert"), {0x3b,0xe9,0x00,0xff,0xc1,0x10,0x31,0xfe,0x55,0x00,0x64,0x05,0x00,0xc8,0x02,0x31,0x80,0x00,0x47},
{TEXT("Italian CNS (a)"), {0x3b,0xe9,0x00,0xff,0xc1,0x10,0x31,0xfe,0x55,0x00,0x64,0x05,0x00,0xc8,0x02,0x31,0x80,0x00,0x47},
19, {0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff}},
{TEXT("Italian eID card, infocamere"), {0x3b,0xfb,0x98,0x00,0xff,0xc1,0x10,0x31,0xfe,0x55,0x00,0x64,0x05,0x20,0x47,0x03,0x31,0x80,0x00,0x90,0x00,0xf3},
{TEXT("Italian CNS (b)"), {0x3b,0xfb,0x98,0x00,0xff,0xc1,0x10,0x31,0xfe,0x55,0x00,0x64,0x05,0x20,0x47,0x03,0x31,0x80,0x00,0x90,0x00,0xf3},
22, {0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff}},
{TEXT("Italian InfocamereCard"), {0x3b,0xfc,0x98,0x00,0xff,0xc1,0x10,0x31,0xfe,0x55,0xc8,0x03,0x49,0x6e,0x66,0x6f,0x63,0x61,0x6d,0x65,0x72,0x65,0x28},
{TEXT("Italian CNS (c)"), {0x3b,0xfc,0x98,0x00,0xff,0xc1,0x10,0x31,0xfe,0x55,0xc8,0x03,0x49,0x6e,0x66,0x6f,0x63,0x61,0x6d,0x65,0x72,0x65,0x28},
23, {0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff}},
{TEXT("Italian CNS (d)"), {0x3b,0xff,0x18,0x00,0xff,0x81,0x31,0xfe,0x55,0x00,0x6b,0x02,0x09,0x03,0x03,0x01,0x01,0x01,0x43,0x4e,0x53,0x10,0x31,0x80,0x9d},
25, {0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff}},
{TEXT("CardOS 4.0 a"), {0x3b,0xf4,0x98,0x00,0xff,0xc1,0x10,0x31,0xfe,0x55,0x4d,0x34,0x63,0x76,0xb4},
15, {0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff,0xff}},
{TEXT("Cardos M4"), {0x3b,0xf2,0x18,0x00,0x02,0xc1,0x0a,0x31,0xfe,0x58,0xc8,0x08,0x74},
@ -254,8 +253,18 @@ void RegisterCardWithKey(PTSTR szKey, PTSTR szCard, PTSTR szPath, PBYTE pbATR, D
VOID RegisterSmartCard(PMD_REGISTRATION registration)
{
RegisterCardWithKey(SC_DATABASE, registration->szName, TEXT("opensc-minidriver.dll"),registration->pbAtr, registration->dwAtrSize, registration->pbAtrMask );
DWORD expanded_len = PATH_MAX;
TCHAR expanded_val[PATH_MAX];
PTSTR szPath = TEXT("C:\\Program Files\\OpenSC Project\\OpenSC\\minidriver\\opensc-minidriver.dll");
/* cope with x86 installation on x64 */
expanded_len = ExpandEnvironmentStrings(
TEXT("%ProgramFiles%\\OpenSC Project\\OpenSC\\minidriver\\opensc-minidriver.dll"),
expanded_val, expanded_len);
if (0 < expanded_len && expanded_len < sizeof expanded_val)
szPath = expanded_val;
RegisterCardWithKey(SC_DATABASE, registration->szName, szPath, registration->pbAtr, registration->dwAtrSize, registration->pbAtrMask );
}
UINT WINAPI AddSmartCardConfiguration(MSIHANDLE hInstall)