Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

sc-hsm-tool: Add options for public key authentication #1711

Closed
wants to merge 23 commits into from
Closed
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
sc-hsm-tool: Add option --public-key-auth-status
  • Loading branch information
Frank Braun committed Oct 29, 2019
commit 9e5058c9d367d10a7aa39119ca71b52b736701d3
67 changes: 42 additions & 25 deletions src/libopensc/card-sc-hsm.c
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
* Driver for the SmartCard-HSM, a light-weight hardware security module
*
* Copyright (C) 2012 Andreas Schwier, CardContact, Minden, Germany, and others
* Copyright (C) 2018 GSMK - Gesellschaft für Sichere Mobile Kommunikation mbH
* Copyright (C) 2018-2019 GSMK - Gesellschaft für Sichere Mobile Kommunikation mbH
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
Expand Down Expand Up @@ -1541,6 +1541,16 @@ static int verify_certificate(sc_card_t *card, const u8 *cert, size_t cert_len,



static void print_public_key_auth_status(u8 *recvbuf)
{
printf("Number of public keys: %d\n", recvbuf[0]);
printf("Missing public keys: %d\n", recvbuf[1]);
printf("Required pubkeys for auth: %d\n", recvbuf[2]);
printf("Authenticated public keys: %d\n", recvbuf[3]);
}



static int sc_hsm_register_public_key(sc_card_t *card, sc_cardctl_sc_hsm_public_key_t *params)
{
u8 tag = SC_ASN1_TAG_CONTEXT | SC_ASN1_TAG_BIT_STRING; /* 0x83 */
Expand All @@ -1555,26 +1565,6 @@ static int sc_hsm_register_public_key(sc_card_t *card, sc_cardctl_sc_hsm_public_

LOG_FUNC_CALLED(card->ctx);

/* get status */
#if 1
sc_format_apdu(card, &apdu, SC_APDU_CASE_2_EXT, 0x54, 0x00, 0x00);
apdu.cla = 0x80;
apdu.resp = recvbuf;
apdu.resplen = sizeof(recvbuf);
apdu.le = 4;

r = sc_transmit_apdu(card, &apdu);
LOG_TEST_RET(ctx, r, "APDU transmit failed");

r = sc_check_sw(card, apdu.sw1, apdu.sw2);
LOG_TEST_RET(ctx, r, "Check SW error");

printf("numberOfPublicKeys=%d\n", recvbuf[0]);
printf("missingPublicKeys=%d\n", recvbuf[1]);
printf("requiredPublicKeysForAuthentication=%d\n", recvbuf[2]);
printf("authenticatedPublicKeys=%d\n", recvbuf[3]);
#endif

/* verify dicacert */
r = verify_certificate(card, params->dicacert, params->dicacert_length, params->dicacert_chr, params->dicacert_chr_length);
LOG_TEST_RET(ctx, r, "device issuer certificate verification failed");
Expand Down Expand Up @@ -1620,16 +1610,41 @@ static int sc_hsm_register_public_key(sc_card_t *card, sc_cardctl_sc_hsm_public_
r = sc_check_sw(card, apdu.sw1, apdu.sw2);
LOG_TEST_RET(ctx, r, "Check SW error");

printf("numberOfPublicKeys=%d\n", recvbuf[0]);
printf("missingPublicKeys=%d\n", recvbuf[1]);
printf("requiredPublicKeysForAuthentication=%d\n", recvbuf[2]);
printf("authenticatedPublicKeys=%d\n", recvbuf[3]);
print_public_key_auth_status(recvbuf);

LOG_FUNC_RETURN(card->ctx, SC_SUCCESS);
}



static int sc_hsm_public_key_auth_status(sc_card_t *card)
{
u8 recvbuf[MAX_EXT_APDU_LENGTH];
sc_context_t *ctx = card->ctx;
sc_apdu_t apdu;
int r;

LOG_FUNC_CALLED(card->ctx);

/* get status */
sc_format_apdu(card, &apdu, SC_APDU_CASE_2_EXT, 0x54, 0x00, 0x00);
apdu.cla = 0x80;
apdu.resp = recvbuf;
apdu.resplen = sizeof(recvbuf);
apdu.le = 4;
frankbraun marked this conversation as resolved.
Show resolved Hide resolved

r = sc_transmit_apdu(card, &apdu);
LOG_TEST_RET(ctx, r, "APDU transmit failed");

r = sc_check_sw(card, apdu.sw1, apdu.sw2);
LOG_TEST_RET(ctx, r, "Check SW error");

print_public_key_auth_status(recvbuf);

LOG_FUNC_RETURN(card->ctx, SC_SUCCESS);
}


static int sc_hsm_init_token(sc_card_t *card, sc_cardctl_pkcs11_init_token_t *params)
{
sc_context_t *ctx = card->ctx;
Expand Down Expand Up @@ -1796,6 +1811,8 @@ static int sc_hsm_card_ctl(sc_card_t *card, unsigned long cmd, void *ptr)
return sc_hsm_unwrap_key(card, (sc_cardctl_sc_hsm_wrapped_key_t *)ptr);
case SC_CARDCTL_SC_HSM_REGISTER_PUBLIC_KEY:
return sc_hsm_register_public_key(card, (sc_cardctl_sc_hsm_public_key_t *)ptr);
case SC_CARDCTL_SC_HSM_PUBLIC_KEY_AUTH_STATUS:
return sc_hsm_public_key_auth_status(card);
}
return SC_ERROR_NOT_SUPPORTED;
}
Expand Down
3 changes: 2 additions & 1 deletion src/libopensc/cardctl.h
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
* cardctl.h: card_ctl command numbers
*
* Copyright (C) 2003 Olaf Kirch <[email protected]>
* Copyright (C) 2018 GSMK - Gesellschaft für Sichere Mobile Kommunikation mbH
* Copyright (C) 2018-2019 GSMK - Gesellschaft für Sichere Mobile Kommunikation mbH
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
Expand Down Expand Up @@ -274,6 +274,7 @@ enum {
SC_CARDCTL_SC_HSM_WRAP_KEY,
SC_CARDCTL_SC_HSM_UNWRAP_KEY,
SC_CARDCTL_SC_HSM_REGISTER_PUBLIC_KEY,
SC_CARDCTL_SC_HSM_PUBLIC_KEY_AUTH_STATUS,

/*
* DNIe specific calls
Expand Down
51 changes: 49 additions & 2 deletions src/tools/sc-hsm-tool.c
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
*
* Copyright (C) 2001 Juha Yrjölä <[email protected]>
* Copyright (C) 2012 www.CardContact.de, Andreas Schwier, Minden, Germany
* Copyright (C) 2018 GSMK - Gesellschaft für Sichere Mobile Kommunikation mbH
* Copyright (C) 2018-2019 GSMK - Gesellschaft für Sichere Mobile Kommunikation mbH
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
Expand Down Expand Up @@ -93,6 +93,7 @@ static const struct option options[] = {
{ "required-pub-keys", 1, NULL, 'n' },
{ "export-for-pub-key-auth",1, NULL, 'e' },
{ "register-public-key", 1, NULL, 'g' },
{ "public-key-auth-status", 0, NULL, 'S' },
{ "dkek-shares", 1, NULL, 's' },
{ "so-pin", 1, NULL, OPT_SO_PIN },
{ "pin", 1, NULL, OPT_PIN },
Expand Down Expand Up @@ -124,6 +125,7 @@ static const char *option_help[] = {
"Number of public keys required for authentication [1]",
"Export key for public key authentication",
"Register public key for public key authentication (PKA file)",
"Show status of public key authentication",
"Number of DKEK shares [No DKEK]",
"Define security officer PIN (SO-PIN)",
"Define user PIN",
Expand Down Expand Up @@ -1872,6 +1874,7 @@ static int register_public_key_with_card(sc_context_t *ctx, sc_card_t *card, con
fprintf(stderr, "sc_card_ctl(*, SC_CARDCTL_SC_HSM_REGISTER_PUBLIC_KEY, *) failed with %s\n", sc_strerror(r));
return -1;
}
fprintf(stderr, "Done.\n");
return 0;
}

Expand Down Expand Up @@ -1967,6 +1970,22 @@ static int register_public_key(sc_context_t *ctx, sc_card_t *card, const char *i



static int public_key_auth_status(sc_context_t *ctx, sc_card_t *card)
{
int r;
r = sc_card_ctl(card, SC_CARDCTL_SC_HSM_PUBLIC_KEY_AUTH_STATUS, NULL);
if (r == SC_ERROR_INS_NOT_SUPPORTED) { /* Not supported or not initialized for public key registration */
fprintf(stderr, "Card not initialized for public key registration\n");
return -1;
}
if (r < 0) {
fprintf(stderr, "sc_card_ctl(*, SC_CARDCTL_SC_HSM_PUBLIC_KEY_AUTH_STATUS, *) failed with %s\n", sc_strerror(r));
return -1;
}
return 0;
}


int main(int argc, char *argv[])
{
int err = 0, r, c, long_optind = 0;
Expand All @@ -1979,6 +1998,7 @@ int main(int argc, char *argv[])
int do_unwrap_key = 0;
int do_export_key = 0;
int do_register_public_key = 0;
int do_public_key_auth_status = 0;
sc_path_t path;
sc_file_t *file = NULL;
const char *opt_so_pin = NULL;
Expand All @@ -2001,7 +2021,7 @@ int main(int argc, char *argv[])
sc_card_t *card = NULL;

while (1) {
c = getopt_long(argc, argv, "XC:I:P:W:U:K:n:e:g:s:i:fr:wv", options, &long_optind);
c = getopt_long(argc, argv, "XC:I:P:W:U:K:n:e:g:Ss:i:fr:wv", options, &long_optind);
if (c == -1)
break;
if (c == '?')
Expand Down Expand Up @@ -2052,6 +2072,10 @@ int main(int argc, char *argv[])
opt_filename = optarg;
action_count++;
break;
case 'S':
do_public_key_auth_status = 1;
action_count++;
break;
case OPT_PASSWORD:
util_get_pin(optarg, &opt_password);
break;
Expand Down Expand Up @@ -2140,6 +2164,26 @@ int main(int argc, char *argv[])
fprintf(stderr, "Option -g (--register-public-key) excludes option -e\n");
exit(1);
}
if (do_initialize && do_public_key_auth_status) {
fprintf(stderr, "Option -S (--public-key-auth-status) excludes option -X\n");
exit(1);
}
if (do_wrap_key && do_public_key_auth_status) {
fprintf(stderr, "Option -S (--public-key-auth-status) excludes option -W\n");
exit(1);
}
if (do_unwrap_key && do_public_key_auth_status) {
fprintf(stderr, "Option -S (--public-key-auth-status) excludes option -U\n");
exit(1);
}
if (do_export_key && do_public_key_auth_status) {
fprintf(stderr, "Option -S (--public-key-auth-status) excludes option -e\n");
exit(1);
}
if (do_register_public_key && do_public_key_auth_status) {
fprintf(stderr, "Option -S (--public-key-auth-status) excludes option -g\n");
exit(1);
}

#if OPENSSL_VERSION_NUMBER >= 0x10100000L || (defined(LIBRESSL_VERSION_NUMBER) && LIBRESSL_VERSION_NUMBER >= 0x20700000L)
OPENSSL_init_crypto(OPENSSL_INIT_LOAD_CRYPTO_STRINGS
Expand Down Expand Up @@ -2201,6 +2245,9 @@ int main(int argc, char *argv[])
if (do_register_public_key && register_public_key(ctx, card, opt_filename))
goto fail;

if (do_public_key_auth_status && public_key_auth_status(ctx, card))
goto fail;

if (action_count == 0) {
print_info(card, file);
}
Expand Down