From d91b45c47aea989bfbdaca76ab8904c986def54b Mon Sep 17 00:00:00 2001 From: frankmorgner Date: Fri, 5 Mar 2010 09:53:44 +0000 Subject: [PATCH] - pace-testing is not done in threads anymore, program exits when test is finished - bugfix in debug_ossl - more generic aproach to select EF.CardAccess - EF.CardAccess is read sequencially, to get a correct send sequence counter git-svn-id: https://vsmartcard.svn.sourceforge.net/svnroot/vsmartcard@42 96b47cad-a561-4643-ad3b-153ac7d7599c --- ccid/ccid.c | 16 ++++++++++++++-- ccid/ccid.h | 2 +- ccid/pace.c | 46 +++++++++++++++++++++++++++++----------------- ccid/pace.h | 4 +++- ccid/usb.c | 11 +++++------ 5 files changed, 52 insertions(+), 27 deletions(-) diff --git a/ccid/ccid.c b/ccid/ccid.c index 5118d7e..949a8b7 100644 --- a/ccid/ccid.c +++ b/ccid/ccid.c @@ -1279,7 +1279,19 @@ int ccid_state_changed(RDR_to_PC_NotifySlotChange_t **slotchange, int timeout) return 0; } -void ccid_testpace() +int ccid_testpace() { - pace_test(ctx, card_in_slot[0]); + int i; + for (i = 0; i < sizeof *card_in_slot; i++) { + if (!card_in_slot[i] + && (sc_detect_card_presence(reader, 0) & SC_SLOT_CARD_PRESENT)) { + sc_connect_card(reader, i, &card_in_slot[i]); + } + + if (sc_card_valid(card_in_slot[i])) { + return pace_test(ctx, card_in_slot[i]); + } + } + + return SC_ERROR_SLOT_NOT_FOUND; } diff --git a/ccid/ccid.h b/ccid/ccid.h index b0cc28e..104d03e 100644 --- a/ccid/ccid.h +++ b/ccid/ccid.h @@ -270,7 +270,7 @@ void ccid_shutdown(); int ccid_parse_bulkin(const __u8* inbuf, __u8** outbuf); int ccid_parse_control(struct usb_ctrlrequest *setup, __u8 **outbuf); int ccid_state_changed(RDR_to_PC_NotifySlotChange_t **slotchange, int timeout); -void ccid_testpace(); +int ccid_testpace(); #ifdef __cplusplus } diff --git a/ccid/pace.c b/ccid/pace.c index a6387e7..c250711 100644 --- a/ccid/pace.c +++ b/ccid/pace.c @@ -171,28 +171,37 @@ int get_ef_card_access(sc_context_t *ctx, sc_card_t *card, __u8 **ef_cardaccess, size_t *length_ef_cardaccess) { int r; - char buf[9]; sc_path_t path; sc_file_t *file; + __u8 *p; + size_t maxresp = SC_MAX_APDU_BUFFER_SIZE - 2; - snprintf(buf, sizeof buf, "3f00%04x", FID_EF_CARDACCESS); - sc_format_path(buf, &path); + memset(&path, 0, sizeof path); + SC_TEST_RET(ctx, sc_append_file_id(&path, FID_EF_CARDACCESS), + "Could not create path object."); + SC_TEST_RET(ctx, sc_concatenate_path(&path, sc_get_mf_path(), &path), + "Could not create path object."); - //printf("%s:%d\n", __FILE__, __LINE__); + memset(&file, 0, sizeof file); SC_TEST_RET(ctx, sc_select_file(card, &path, &file), "Could not select EF.CardAccess."); - //printf("%s:%d\n", __FILE__, __LINE__); ssc++; - *length_ef_cardaccess = file->size; - *ef_cardaccess = malloc(*length_ef_cardaccess); - if (!*ef_cardaccess) - SC_FUNC_RETURN(ctx, SC_LOG_TYPE_DEBUG, SC_ERROR_OUT_OF_MEMORY); + for (*length_ef_cardaccess = 0; ; *length_ef_cardaccess += r, ssc++) { + p = realloc(*ef_cardaccess, *length_ef_cardaccess + maxresp); + if (!p) + SC_FUNC_RETURN(ctx, SC_LOG_TYPE_DEBUG, SC_ERROR_OUT_OF_MEMORY); + *ef_cardaccess = p; - r = sc_read_binary(card, 0, *ef_cardaccess, *length_ef_cardaccess, 0); - ssc++; - SC_TEST_RET(ctx, r, "Could not read EF.CardAccess."); - *length_ef_cardaccess = r; + r = sc_read_binary(card, *length_ef_cardaccess, + *ef_cardaccess + *length_ef_cardaccess, maxresp, 0); + SC_TEST_RET(ctx, r, "Could not read EF.CardAccess."); + } + + /* test cards only return an empty FCI template, + * so we can't determine any file proberties */ + if (*length_ef_cardaccess < file->size) + SC_FUNC_RETURN(ctx, SC_LOG_TYPE_DEBUG, SC_ERROR_FILE_TOO_SMALL); SC_FUNC_RETURN(ctx, SC_LOG_TYPE_DEBUG, SC_SUCCESS); } @@ -500,8 +509,8 @@ get_psec(sc_card_t *card, const char *pin, size_t length_pin, u8 pin_id) } void debug_ossl(sc_context_t *ctx) { - unsigned long r = ERR_get_error(); - while (r) { + unsigned long r; + for (r = ERR_get_error(); r; r = ERR_get_error()) { sc_error(ctx, ERR_error_string(r, NULL)); } } @@ -552,12 +561,15 @@ int EstablishPACEChannel(sc_context_t *ctx, sc_card_t *card, if (r < 0) { goto err; } + //printf("%s:%d\n", __FILE__, __LINE__); if (!parse_ef_card_access(ef_cardaccess, length_ef_cardaccess, &info, &static_dp)) { r = SC_ERROR_INTERNAL; debug_ossl(ctx); goto err; } + //printf("%s:%d\n", __FILE__, __LINE__); + //return 0; r = pace_mse_set_at(ctx, card, info->protocol, pin_id, 1); if (r < 0) { goto err; @@ -689,7 +701,7 @@ err: SC_FUNC_RETURN(ctx, SC_LOG_TYPE_DEBUG, r); } -void pace_test(sc_context_t *ctx, sc_card_t *card) +int pace_test(sc_context_t *ctx, sc_card_t *card) { __u8 in[16]; __u8 *out = NULL; @@ -707,7 +719,7 @@ void pace_test(sc_context_t *ctx, sc_card_t *card) in[9] = 0; // length_cert_desc in[10]= 0; // length_cert_desc - EstablishPACEChannel(ctx, card, in, &out, &outlen); + return EstablishPACEChannel(ctx, card, in, &out, &outlen); } #endif diff --git a/ccid/pace.h b/ccid/pace.h index 21dfd52..4dc2b15 100644 --- a/ccid/pace.h +++ b/ccid/pace.h @@ -38,11 +38,13 @@ extern "C" { #define FID_EF_CARDACCESS 0x011C +#define MAX_EF_CARDACCESS 2048 + int GetReadersPACECapabilities(sc_context_t *ctx, sc_card_t *card, const __u8 *in, __u8 **out, size_t *outlen); int EstablishPACEChannel(sc_context_t *ctx, sc_card_t *card, const __u8 *in, __u8 **out, size_t *outlen); -void pace_test(sc_context_t *ctx, sc_card_t *card); +int pace_test(sc_context_t *ctx, sc_card_t *card); #ifdef __cplusplus } diff --git a/ccid/usb.c b/ccid/usb.c index 3117158..a8b079b 100644 --- a/ccid/usb.c +++ b/ccid/usb.c @@ -58,7 +58,7 @@ static int debug = 0; static int dohid = 0; static int doint = 0; static int dotest = 0; -int usb_reader_num = 0; +static int usb_reader_num = -1; static const struct option options[] = { /*{ "hid", no_argument, &dohid, 1 },*/ @@ -1031,11 +1031,6 @@ static void *ccid (void *param) goto error; } - if (dotest) { - sleep(2); - ccid_testpace(); - } - do { /* original LinuxThreads cancelation didn't work right @@ -1802,6 +1797,10 @@ main (int argc, char **argv) return 1; } + if (dotest) { + return ccid_testpace(); + } + fd = init_device (); if (fd < 0) return 1;