From 97e9cc209153fcffaca7805f7bf272800fbe7963 Mon Sep 17 00:00:00 2001 From: frankmorgner Date: Sat, 19 Jun 2010 16:19:51 +0000 Subject: [PATCH] - added patch to distribution package - changed debug_sc_result to be a define. this now gets the line of code correct - added checking for input length to functions that parse the bulkin buffer - fixed segfault for GetReadersPACECapabilities when no card is inserted - added length checking of input for EstablishPACEChannel - ccid-test: fixed pbSendBufferEstablish - pcsclite_trunk.patch: - fixed parsing of lengthCertificateDescription - fixed wrong bPINOperation for pace capabilities and execute pace git-svn-id: https://vsmartcard.svn.sourceforge.net/svnroot/vsmartcard@156 96b47cad-a561-4643-ad3b-153ac7d7599c --- ccid/Makefile.am | 1 + ccid/pcsclite_trunk.patch | 8 +-- ccid/src/ccid-test.c | 3 +- ccid/src/ccid.c | 101 +++++++++++++++++++++++++++++--------- ccid/src/ccid.h | 2 +- ccid/src/pace-tool.c | 3 +- ccid/src/pace.c | 47 +++++++++++++++--- ccid/src/pace.h | 4 +- ccid/src/usb.c | 2 +- 9 files changed, 131 insertions(+), 40 deletions(-) diff --git a/ccid/Makefile.am b/ccid/Makefile.am index 38f289b..6f31f59 100644 --- a/ccid/Makefile.am +++ b/ccid/Makefile.am @@ -1,2 +1,3 @@ +EXTRA_DIST = pcsclite_trunk.patch ACLOCAL_AMFLAGS = -I m4 SUBDIRS = src m4 diff --git a/ccid/pcsclite_trunk.patch b/ccid/pcsclite_trunk.patch index 2ccb455..542173e 100644 --- a/ccid/pcsclite_trunk.patch +++ b/ccid/pcsclite_trunk.patch @@ -135,10 +135,10 @@ Index: Drivers/ccid/src/commands.c + lengthCertificateDescription = *((uint16_t *) + (TxBuffer + 1 + lengthCHAT + lengthPIN)); + -+ if (TxLength != 4+lengthCHAT+lengthPIN+lengthCertificateDescription) { ++ if (TxLength != 5+lengthCHAT+lengthPIN+lengthCertificateDescription) { + DEBUG_CRITICAL3("Buffer too small or too big to contain only " + "CHAT, PIN and certificate description (expected %u, got %u)", -+ 4+lengthCHAT+lengthPIN+lengthCertificateDescription, TxLength); ++ 5+lengthCHAT+lengthPIN+lengthCertificateDescription, TxLength); + return_value = IFD_COMMUNICATION_ERROR; + goto err; + } @@ -147,7 +147,7 @@ Index: Drivers/ccid/src/commands.c + + /* bPINOperation: PIN PACE Capabilities */ + return_value = SecurePINPACE(reader_index, TxBuffer, TxLength, RxBuffer, -+ RxLength, CCID_CLASS_PIN_PACE_CAPABILITIES); ++ RxLength, CCID_CLASS_PIN_PACE_EXECUTE); + +err: + ccid_descriptor -> readTimeout = old_read_timeout; @@ -160,7 +160,7 @@ Index: Drivers/ccid/src/commands.c +{ + /* bPINOperation: PIN PACE Capabilities */ + return SecurePINPACE(reader_index, TxBuffer, TxLength, RxBuffer, -+ RxLength, CCID_CLASS_PIN_PACE_EXECUTE); ++ RxLength, CCID_CLASS_PIN_PACE_CAPABILITIES); +} + +static RESPONSECODE SecurePINPACE(unsigned int reader_index, diff --git a/ccid/src/ccid-test.c b/ccid/src/ccid-test.c index 62782da..7720f6f 100644 --- a/ccid/src/ccid-test.c +++ b/ccid/src/ccid-test.c @@ -46,13 +46,14 @@ main(int argc, char *argv[]) 0x00, /* lengthInputData */ 0x03, /* PACE with PIN */ 0x00, /* length CHAT */ + 0x00, /* length PIN */ 0x00, /* length certificate description */ 0x00, /* length certificate description */ }; BYTE pbRecvBuffer[1024]; DWORD dwActiveProtocol, dwRecvLength, dwReaders; - uint16_t lengthInputData = 4; + uint16_t lengthInputData = 5; memcpy(pbSendBufferEstablish + 1, &lengthInputData, 2); if (argc > 1) { diff --git a/ccid/src/ccid.c b/ccid/src/ccid.c index 232197c..d70d28e 100644 --- a/ccid/src/ccid.c +++ b/ccid/src/ccid.c @@ -83,10 +83,12 @@ ccid_desc = { .bMaxCCIDBusySlots = 0x01, }; -static void -debug_sc_result(int sc_result) -{ - sc_debug(ctx, sc_strerror(sc_result)); +#define debug_sc_result(sc_result) \ +{ \ + if (sc_result < 0) \ + sc_error(ctx, sc_strerror(sc_result)); \ + else \ + sc_debug(ctx, sc_strerror(sc_result)); \ } static int @@ -329,13 +331,16 @@ get_RDR_to_PC_DataBlock(__u8 bSlot, __u8 bSeq, int sc_result, RDR_to_PC_DataBloc } static int -perform_PC_to_RDR_GetSlotStatus(const __u8 *in, __u8 **out, size_t *outlen) +perform_PC_to_RDR_GetSlotStatus(const __u8 *in, size_t inlen, __u8 **out, size_t *outlen) { const PC_to_RDR_GetSlotStatus_t *request = (PC_to_RDR_GetSlotStatus_t *) in; if (!out || !outlen || !in) SC_FUNC_RETURN(ctx, SC_LOG_TYPE_ERROR, SC_ERROR_INVALID_ARGUMENTS); + if (inlen < sizeof *request) + SC_FUNC_RETURN(ctx, SC_LOG_TYPE_ERROR, SC_ERROR_INVALID_DATA); + *outlen = sizeof(RDR_to_PC_SlotStatus_t); if ( request->bMessageType != 0x65 || @@ -350,7 +355,7 @@ perform_PC_to_RDR_GetSlotStatus(const __u8 *in, __u8 **out, size_t *outlen) } static int -perform_PC_to_RDR_IccPowerOn(const __u8 *in, __u8 **out, size_t *outlen) +perform_PC_to_RDR_IccPowerOn(const __u8 *in, size_t inlen, __u8 **out, size_t *outlen) { const PC_to_RDR_IccPowerOn_t *request = (PC_to_RDR_IccPowerOn_t *) in; int sc_result; @@ -359,6 +364,9 @@ perform_PC_to_RDR_IccPowerOn(const __u8 *in, __u8 **out, size_t *outlen) if (!out || !outlen || !in) SC_FUNC_RETURN(ctx, SC_LOG_TYPE_ERROR, SC_ERROR_INVALID_ARGUMENTS); + if (inlen < sizeof *request) + SC_FUNC_RETURN(ctx, SC_LOG_TYPE_ERROR, SC_ERROR_INVALID_DATA); + if ( request->bMessageType != 0x62 || request->dwLength != __constant_cpu_to_le32(0) || !( request->bPowerSelect == 0 || @@ -408,7 +416,7 @@ perform_PC_to_RDR_IccPowerOn(const __u8 *in, __u8 **out, size_t *outlen) } static int -perform_PC_to_RDR_IccPowerOff(const __u8 *in, __u8 **out, size_t *outlen) +perform_PC_to_RDR_IccPowerOff(const __u8 *in, size_t inlen, __u8 **out, size_t *outlen) { const PC_to_RDR_IccPowerOff_t *request = (PC_to_RDR_IccPowerOff_t *) in; int sc_result; @@ -416,6 +424,9 @@ perform_PC_to_RDR_IccPowerOff(const __u8 *in, __u8 **out, size_t *outlen) if (!in || !out || !outlen) SC_FUNC_RETURN(ctx, SC_LOG_TYPE_ERROR, SC_ERROR_INVALID_ARGUMENTS); + if (inlen < sizeof *request) + SC_FUNC_RETURN(ctx, SC_LOG_TYPE_ERROR, SC_ERROR_INVALID_DATA); + if ( request->bMessageType != 0x63 || request->dwLength != __constant_cpu_to_le32(0) || request->abRFU1 != 0 || @@ -438,7 +449,7 @@ perform_PC_to_RDR_IccPowerOff(const __u8 *in, __u8 **out, size_t *outlen) } static int -perform_PC_to_RDR_XfrBlock(const u8 *in, __u8** out, size_t *outlen) +perform_PC_to_RDR_XfrBlock(const u8 *in, size_t inlen, __u8** out, size_t *outlen) { const PC_to_RDR_XfrBlock_t *request = (PC_to_RDR_XfrBlock_t *) in; const __u8 *abDataIn = in + sizeof *request; @@ -451,6 +462,9 @@ perform_PC_to_RDR_XfrBlock(const u8 *in, __u8** out, size_t *outlen) if (!in || !out || !outlen) SC_FUNC_RETURN(ctx, SC_LOG_TYPE_ERROR, SC_ERROR_INVALID_ARGUMENTS); + if (inlen < sizeof *request) + SC_FUNC_RETURN(ctx, SC_LOG_TYPE_ERROR, SC_ERROR_INVALID_DATA); + if ( request->bMessageType != 0x6F || request->bBWI != 0) sc_debug(ctx, "malformed PC_to_RDR_XfrBlock, will continue anyway"); @@ -497,7 +511,7 @@ perform_PC_to_RDR_XfrBlock(const u8 *in, __u8** out, size_t *outlen) } static int -perform_PC_to_RDR_GetParamters(const __u8 *in, __u8** out, size_t *outlen) +perform_PC_to_RDR_GetParamters(const __u8 *in, size_t inlen, __u8** out, size_t *outlen) { const PC_to_RDR_GetParameters_t *request = (PC_to_RDR_GetParameters_t *) in; RDR_to_PC_Parameters_t *result; @@ -508,6 +522,9 @@ perform_PC_to_RDR_GetParamters(const __u8 *in, __u8** out, size_t *outlen) if (!in || !out || !outlen) SC_FUNC_RETURN(ctx, SC_LOG_TYPE_ERROR, SC_ERROR_INVALID_ARGUMENTS); + if (inlen < sizeof *request) + SC_FUNC_RETURN(ctx, SC_LOG_TYPE_ERROR, SC_ERROR_INVALID_DATA); + if ( request->bMessageType != 0x6C || request->dwLength != __constant_cpu_to_le32(0)) sc_debug(ctx, "warning: malformed PC_to_RDR_GetParamters"); @@ -751,7 +768,7 @@ write_pin(sc_apdu_t *apdu, struct sc_pin_cmd_pin *pin, uint8_t blocksize, } static int -perform_PC_to_RDR_Secure(const __u8 *in, __u8** out, size_t *outlen) +perform_PC_to_RDR_Secure(const __u8 *in, size_t inlen, __u8** out, size_t *outlen) { int sc_result, r; struct sc_pin_cmd_pin curr_pin, new_pin; @@ -759,6 +776,7 @@ perform_PC_to_RDR_Secure(const __u8 *in, __u8** out, size_t *outlen) sc_ui_hints_t hints; const PC_to_RDR_Secure_t *request = (PC_to_RDR_Secure_t *) in; const __u8* abData = in + sizeof *request; + size_t abDatalen = inlen - sizeof *request; u8 *abDataOut = NULL; size_t resplen = 0; RDR_to_PC_DataBlock_t *result; @@ -766,6 +784,9 @@ perform_PC_to_RDR_Secure(const __u8 *in, __u8** out, size_t *outlen) if (!in || !out || !outlen) SC_FUNC_RETURN(ctx, SC_LOG_TYPE_ERROR, SC_ERROR_INVALID_ARGUMENTS); + if (inlen < sizeof *request + 1) + SC_FUNC_RETURN(ctx, SC_LOG_TYPE_ERROR, SC_ERROR_INVALID_DATA); + if (request->bMessageType != 0x69) sc_debug(ctx, "warning: malformed PC_to_RDR_Secure"); @@ -793,6 +814,12 @@ perform_PC_to_RDR_Secure(const __u8 *in, __u8** out, size_t *outlen) // PIN Verification verify = (abPINDataStucture_Verification_t *) (abData + sizeof(__u8)); + + if (abDatalen < sizeof *verify) { + sc_result = SC_ERROR_INVALID_DATA; + goto err; + } + wPINMaxExtraDigit = verify->wPINMaxExtraDigit; bmPINLengthFormat = verify->bmPINLengthFormat; bmPINBlockString = verify->bmPINBlockString; @@ -805,6 +832,13 @@ perform_PC_to_RDR_Secure(const __u8 *in, __u8** out, size_t *outlen) // PIN Modification modify = (abPINDataStucture_Modification_t *) (abData + sizeof(__u8)); + + if (abDatalen < sizeof *modify) { + sc_error(ctx, "Not enough data for abPINDataStucture_Modification_t"); + sc_result = SC_ERROR_INVALID_DATA; + goto err; + } + wPINMaxExtraDigit = modify->wPINMaxExtraDigit; bmPINLengthFormat = modify->bmPINLengthFormat; bmPINBlockString = modify->bmPINBlockString; @@ -815,21 +849,37 @@ perform_PC_to_RDR_Secure(const __u8 *in, __u8** out, size_t *outlen) break; #ifdef WITH_PACE case 0x10: + + if (abDatalen < 1) { + sc_error(ctx, "Not enough data for input of GetReadersPACECapabilities"); + sc_result = SC_ERROR_INVALID_DATA; + goto err; + } + sc_result = GetReadersPACECapabilities(card_in_slot[request->bSlot], - abData + 1, &abDataOut, &resplen); + abData + 1, abDatalen-1, &abDataOut, &resplen); goto err; break; case 0x20: + + if (abDatalen < 1) { + sc_error(ctx, "Not enough data for input of EstablishPACEChannel"); + sc_result = SC_ERROR_INVALID_DATA; + goto err; + } + sc_result = EstablishPACEChannel(&sctx, - card_in_slot[request->bSlot], abData + 1, &abDataOut, - &resplen, &sctx); + card_in_slot[request->bSlot], abData + 1, abDatalen-1, + &abDataOut, &resplen, &sctx); goto err; break; #endif case 0x04: // Cancel PIN function default: + sc_error(ctx, "PIN operation not supported (bPINOperation=%02x).", + *abData); sc_result = SC_ERROR_NOT_SUPPORTED; goto err; } @@ -1039,7 +1089,7 @@ get_RDR_to_PC_NotifySlotChange(RDR_to_PC_NotifySlotChange_t **out) } static int -perform_unknown(const __u8 *in, __u8 **out, size_t *outlen) +perform_unknown(const __u8 *in, size_t inlen, __u8 **out, size_t *outlen) { const PC_to_RDR_GetSlotStatus_t *request = (PC_to_RDR_GetSlotStatus_t *) in; RDR_to_PC_SlotStatus_t *result; @@ -1047,6 +1097,9 @@ perform_unknown(const __u8 *in, __u8 **out, size_t *outlen) if (!in || !out || !outlen) SC_FUNC_RETURN(ctx, SC_LOG_TYPE_ERROR, SC_ERROR_INVALID_ARGUMENTS); + if (inlen < sizeof *request) + SC_FUNC_RETURN(ctx, SC_LOG_TYPE_ERROR, SC_ERROR_INVALID_DATA); + result = realloc(*out, sizeof *result); if (!result) SC_FUNC_RETURN(ctx, SC_LOG_TYPE_ERROR, SC_ERROR_OUT_OF_MEMORY); @@ -1096,7 +1149,7 @@ perform_unknown(const __u8 *in, __u8 **out, size_t *outlen) SC_FUNC_RETURN(ctx, SC_LOG_TYPE_ERROR, SC_SUCCESS); } -int ccid_parse_bulkin(const __u8* inbuf, __u8** outbuf) +int ccid_parse_bulkin(const __u8* inbuf, size_t inlen, __u8** outbuf) { int sc_result; size_t outlen; @@ -1107,38 +1160,38 @@ int ccid_parse_bulkin(const __u8* inbuf, __u8** outbuf) switch (*inbuf) { case 0x62: sc_debug(ctx, "PC_to_RDR_IccPowerOn"); - sc_result = perform_PC_to_RDR_IccPowerOn(inbuf, outbuf, &outlen); + sc_result = perform_PC_to_RDR_IccPowerOn(inbuf, inlen, outbuf, &outlen); break; case 0x63: sc_debug(ctx, "PC_to_RDR_IccPowerOff"); - sc_result = perform_PC_to_RDR_IccPowerOff(inbuf, outbuf, &outlen); + sc_result = perform_PC_to_RDR_IccPowerOff(inbuf, inlen, outbuf, &outlen); break; case 0x65: sc_debug(ctx, "PC_to_RDR_GetSlotStatus"); - sc_result = perform_PC_to_RDR_GetSlotStatus(inbuf, outbuf, &outlen); + sc_result = perform_PC_to_RDR_GetSlotStatus(inbuf, inlen, outbuf, &outlen); break; case 0x6F: sc_debug(ctx, "PC_to_RDR_XfrBlock"); - sc_result = perform_PC_to_RDR_XfrBlock(inbuf, outbuf, &outlen); + sc_result = perform_PC_to_RDR_XfrBlock(inbuf, inlen, outbuf, &outlen); break; case 0x6C: sc_debug(ctx, "PC_to_RDR_GetParameters"); - sc_result = perform_PC_to_RDR_GetParamters(inbuf, outbuf, &outlen); + sc_result = perform_PC_to_RDR_GetParamters(inbuf, inlen, outbuf, &outlen); break; case 0x69: sc_debug(ctx, "PC_to_RDR_Secure"); - sc_result = perform_PC_to_RDR_Secure(inbuf, outbuf, &outlen); + sc_result = perform_PC_to_RDR_Secure(inbuf, inlen, outbuf, &outlen); break; default: - sc_debug(ctx, "Unknown ccid bulk-in message. " - "Starting default handler."); - sc_result = perform_unknown(inbuf, outbuf, &outlen); + sc_error(ctx, "Unknown ccid bulk-in message. " + "Starting default handler..."); + sc_result = perform_unknown(inbuf, inlen, outbuf, &outlen); } if (sc_result < 0) { diff --git a/ccid/src/ccid.h b/ccid/src/ccid.h index 1a91d3f..e645f7d 100644 --- a/ccid/src/ccid.h +++ b/ccid/src/ccid.h @@ -268,7 +268,7 @@ struct hid_class_descriptor { int ccid_initialize(int reader_id, const char *cdriver, int verbose); void ccid_shutdown(); -int ccid_parse_bulkin(const __u8* inbuf, __u8** outbuf); +int ccid_parse_bulkin(const __u8* inbuf, size_t inlen, __u8** outbuf); int ccid_parse_control(struct usb_ctrlrequest *setup, __u8 **outbuf); int ccid_state_changed(RDR_to_PC_NotifySlotChange_t **slotchange, int timeout); diff --git a/ccid/src/pace-tool.c b/ccid/src/pace-tool.c index d3e8ab4..ad45583 100644 --- a/ccid/src/pace-tool.c +++ b/ccid/src/pace-tool.c @@ -155,7 +155,8 @@ int pace_get_channel(struct sm_ctx *oldpacectx, sc_card_t *card, memcpy(&buf[3 + chatlen + pinlen + sizeof word], desc, desclen); - return EstablishPACEChannel(oldpacectx, card, buf, out, outlen, sctx); + return EstablishPACEChannel(oldpacectx, card, buf, + 1+pinlen+1+chatlen+2+desclen, out, outlen, sctx); } int pace_translate_apdus(struct sm_ctx *sctx, sc_card_t *card) diff --git a/ccid/src/pace.c b/ccid/src/pace.c index fe63db6..52c89b0 100644 --- a/ccid/src/pace.c +++ b/ccid/src/pace.c @@ -161,13 +161,17 @@ IMPLEMENT_ASN1_FUNCTIONS(PACE_GEN_AUTH_R) const size_t maxresp = SC_MAX_APDU_BUFFER_SIZE - 2; int GetReadersPACECapabilities(sc_card_t *card, - const __u8 *in, __u8 **out, size_t *outlen) { + const __u8 *in, size_t inlen, __u8 **out, size_t *outlen) { if (!out || !outlen) SC_FUNC_RETURN(card->ctx, SC_LOG_TYPE_DEBUG, SC_ERROR_INVALID_ARGUMENTS); __u8 *result = realloc(*out, 2); - if (!result) - SC_FUNC_RETURN(card->ctx, SC_LOG_TYPE_DEBUG, SC_ERROR_OUT_OF_MEMORY); + if (!result) { + if (card) + SC_FUNC_RETURN(card->ctx, SC_LOG_TYPE_DEBUG, SC_ERROR_OUT_OF_MEMORY); + else + return SC_ERROR_OUT_OF_MEMORY; + } *out = result; *outlen = 2; @@ -177,7 +181,10 @@ int GetReadersPACECapabilities(sc_card_t *card, /* BitMap */ *result = PACE_BITMAP_PACE|PACE_BITMAP_EID; - SC_FUNC_RETURN(card->ctx, SC_LOG_TYPE_DEBUG, SC_SUCCESS); + if (card) + SC_FUNC_RETURN(card->ctx, SC_LOG_TYPE_DEBUG, SC_SUCCESS); + else + return SC_SUCCESS; } /** select and read EF.CardAccess */ @@ -675,7 +682,7 @@ void debug_ossl(sc_context_t *ctx) { } int EstablishPACEChannel(const struct sm_ctx *oldpacectx, sc_card_t *card, - const __u8 *in, __u8 **out, size_t *outlen, struct sm_ctx *sctx) + const __u8 *in, size_t inlen, __u8 **out, size_t *outlen, struct sm_ctx *sctx) { __u8 pin_id; size_t length_chat, length_pin, length_cert_desc, length_ef_cardaccess; @@ -692,15 +699,27 @@ int EstablishPACEChannel(const struct sm_ctx *oldpacectx, sc_card_t *card, int r, second_execution; if (!card) - return SC_ERROR_INVALID_ARGUMENTS; + return SC_ERROR_CARD_NOT_PRESENT; if (!in || !out || !outlen) SC_FUNC_RETURN(card->ctx, SC_LOG_TYPE_DEBUG, SC_ERROR_INVALID_ARGUMENTS); + if (inlen < 1) { + sc_error(card->ctx, "Buffer too small, could not get PinID"); + SC_FUNC_RETURN(card->ctx, SC_LOG_TYPE_DEBUG, SC_ERROR_INVALID_DATA); + } pin_id = *in; in++; + if (inlen < 1+1) { + sc_error(card->ctx, "Buffer too small, could not get lengthCHAT"); + SC_FUNC_RETURN(card->ctx, SC_LOG_TYPE_DEBUG, SC_ERROR_INVALID_DATA); + } length_chat = *in; in++; + if (inlen < 1+1+length_chat) { + sc_error(card->ctx, "Buffer too small, could not get CHAT"); + SC_FUNC_RETURN(card->ctx, SC_LOG_TYPE_DEBUG, SC_ERROR_INVALID_DATA); + } chat = in; in += length_chat; /* XXX make this human readable */ @@ -708,14 +727,30 @@ int EstablishPACEChannel(const struct sm_ctx *oldpacectx, sc_card_t *card, bin_log(card->ctx, "Card holder authorization template", chat, length_chat); + if (inlen < 1+1+length_chat+1) { + sc_error(card->ctx, "Buffer too small, could not get lengthPIN"); + SC_FUNC_RETURN(card->ctx, SC_LOG_TYPE_DEBUG, SC_ERROR_INVALID_DATA); + } length_pin = *in; in++; + if (inlen < 1+1+length_chat+1+length_pin) { + sc_error(card->ctx, "Buffer too small, could not get PIN"); + SC_FUNC_RETURN(card->ctx, SC_LOG_TYPE_DEBUG, SC_ERROR_INVALID_DATA); + } pin = in; in += length_pin; + if (inlen < 1+1+length_chat+1+length_pin+sizeof(word)) { + sc_error(card->ctx, "Buffer too small, could not get lengthCertificateDescription %d %d",1+1+length_chat+1+length_pin+sizeof(word), inlen); + SC_FUNC_RETURN(card->ctx, SC_LOG_TYPE_DEBUG, SC_ERROR_INVALID_DATA); + } memcpy(&word, in, sizeof word); length_cert_desc = __le16_to_cpu(word); in += sizeof word; + if (inlen < 1+1+length_chat+1+length_pin+sizeof(word)+length_cert_desc) { + sc_error(card->ctx, "Buffer too small, could not get CertificateDescription"); + SC_FUNC_RETURN(card->ctx, SC_LOG_TYPE_DEBUG, SC_ERROR_INVALID_DATA); + } certificate_description = in; /* XXX make this human readable */ if (length_cert_desc) diff --git a/ccid/src/pace.h b/ccid/src/pace.h index 58dd456..09c644c 100644 --- a/ccid/src/pace.h +++ b/ccid/src/pace.h @@ -64,9 +64,9 @@ int pace_sm_post_transmit(sc_card_t *card, const struct sm_ctx *ctx, sc_apdu_t *sm_apdu); int GetReadersPACECapabilities(sc_card_t *card, const unsigned char *in, - unsigned char **out, size_t *outlen); + size_t inlen, unsigned char **out, size_t *outlen); int EstablishPACEChannel(const struct sm_ctx *oldpacectx, sc_card_t *card, - const unsigned char *in, unsigned char **out, size_t *outlen, struct sm_ctx *sctx); + const unsigned char *in, size_t inlen, unsigned char **out, size_t *outlen, struct sm_ctx *sctx); int pace_reset_retry_counter(struct sm_ctx *ctx, sc_card_t *card, enum s_type pin_id, int ask_for_secret, diff --git a/ccid/src/usb.c b/ccid/src/usb.c index b06507e..63e1ae2 100644 --- a/ccid/src/usb.c +++ b/ccid/src/usb.c @@ -1056,7 +1056,7 @@ static void *ccid (void *param) fprintf(stderr, "got %d, done.\n", result); if (!result) break; - result = ccid_parse_bulkin(inbuf, &outbuf); + result = ccid_parse_bulkin(inbuf, result, &outbuf); if (result < 0) break; if (verbose > 1)