3 Copyright (C) 2003-2010 Ludovic Rousseau
5 This library is free software; you can redistribute it and/or
6 modify it under the terms of the GNU Lesser General Public
7 License as published by the Free Software Foundation; either
8 version 2.1 of the License, or (at your option) any later version.
10 This library is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 Lesser General Public License for more details.
15 You should have received a copy of the GNU Lesser General Public License
16 along with this library; if not, write to the Free Software Foundation,
17 Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
34 #ifdef HAVE_ARPA_INET_H
35 #include <arpa/inet.h>
40 #include <ifdhandler.h>
45 #include "ccid_ifdhandler.h"
49 #include "towitoko/atr.h"
50 #include "towitoko/pps.h"
52 #include "strlcpycat.h"
58 /* Array of structures to hold the ATR and other state value of each slot */
59 static CcidDesc CcidSlots[CCID_DRIVER_MAX_READERS];
63 static pthread_mutex_t ifdh_context_mutex = PTHREAD_MUTEX_INITIALIZER;
66 int LogLevel = DEBUG_LEVEL_CRITICAL | DEBUG_LEVEL_INFO;
67 int DriverOptions = 0;
68 int PowerOnVoltage = -1;
69 static int DebugInitialized = FALSE;
72 static void init_driver(void);
73 static char find_baud_rate(unsigned int baudrate, unsigned int *list);
74 static unsigned int T0_card_timeout(double f, double d, int TC1, int TC2,
76 static unsigned int T1_card_timeout(double f, double d, int TC1, int BWI,
77 int CWI, int clock_frequency);
78 static int get_IFSC(ATR_t *atr, int *i);
80 static void FreeChannel(int reader_index)
83 (void)pthread_mutex_lock(&ifdh_context_mutex);
86 (void)ClosePort(reader_index);
88 free(CcidSlots[reader_index].readerName);
89 memset(&CcidSlots[reader_index], 0, sizeof(CcidSlots[reader_index]));
91 ReleaseReaderIndex(reader_index);
94 (void)pthread_mutex_unlock(&ifdh_context_mutex);
98 static RESPONSECODE CreateChannelByNameOrChannel(DWORD Lun,
99 LPSTR lpcDevice, DWORD Channel)
101 RESPONSECODE return_value = IFD_SUCCESS;
105 if (! DebugInitialized)
110 DEBUG_INFO3("Lun: " DWORD_X ", device: %s", Lun, lpcDevice);
114 DEBUG_INFO3("Lun: " DWORD_X ", Channel: " DWORD_X, Lun, Channel);
118 (void)pthread_mutex_lock(&ifdh_context_mutex);
121 reader_index = GetNewReaderIndex(Lun);
124 (void)pthread_mutex_unlock(&ifdh_context_mutex);
127 if (-1 == reader_index)
128 return IFD_COMMUNICATION_ERROR;
130 /* Reset ATR buffer */
131 CcidSlots[reader_index].nATRLength = 0;
132 *CcidSlots[reader_index].pcATRBuffer = '\0';
134 /* Reset PowerFlags */
135 CcidSlots[reader_index].bPowerFlags = POWERFLAGS_RAZ;
139 CcidSlots[reader_index].readerName = strdup(lpcDevice);
141 CcidSlots[reader_index].readerName = strdup("no name");
144 ret = OpenPortByName(reader_index, lpcDevice);
146 ret = OpenPort(reader_index, Channel);
148 if (ret != STATUS_SUCCESS)
150 DEBUG_CRITICAL("failed");
151 if (STATUS_NO_SUCH_DEVICE == ret)
152 return_value = IFD_NO_SUCH_DEVICE;
154 return_value = IFD_COMMUNICATION_ERROR;
160 unsigned char pcbuffer[SIZE_GET_SLOT_STATUS];
161 unsigned int oldReadTimeout;
162 RESPONSECODE cmd_ret;
163 _ccid_descriptor *ccid_descriptor = get_ccid_descriptor(reader_index);
165 /* Maybe we have a special treatment for this reader */
166 (void)ccid_open_hack_pre(reader_index);
168 /* Try to access the reader */
169 /* This "warm up" sequence is sometimes needed when pcscd is
170 * restarted with the reader already connected. We get some
171 * "usb_bulk_read: Resource temporarily unavailable" on the first
172 * few tries. It is an empirical hack */
174 /* The reader may have to start here so give it some time */
175 cmd_ret = CmdGetSlotStatus(reader_index, pcbuffer);
176 if (IFD_NO_SUCH_DEVICE == cmd_ret)
178 return_value = cmd_ret;
182 /* save the current read timeout computed from card capabilities */
183 oldReadTimeout = ccid_descriptor->readTimeout;
185 /* 100 ms just to resync the USB toggle bits */
186 /* Do not use a fixed 100 ms value but compute it from the
187 * default timeout. It is now possible to use a different value
188 * by changing readTimeout in ccid_open_hack_pre() */
189 ccid_descriptor->readTimeout = ccid_descriptor->readTimeout * 100.0 / DEFAULT_COM_READ_TIMEOUT;
191 if ((IFD_COMMUNICATION_ERROR == CmdGetSlotStatus(reader_index, pcbuffer))
192 && (IFD_COMMUNICATION_ERROR == CmdGetSlotStatus(reader_index, pcbuffer)))
194 DEBUG_CRITICAL("failed");
195 return_value = IFD_COMMUNICATION_ERROR;
199 /* Maybe we have a special treatment for this reader */
200 return_value = ccid_open_hack_post(reader_index);
201 if (return_value != IFD_SUCCESS)
203 DEBUG_CRITICAL("failed");
207 /* set back the old timeout */
208 ccid_descriptor->readTimeout = oldReadTimeout;
212 if (return_value != IFD_SUCCESS)
214 /* release the allocated resources */
215 FreeChannel(reader_index);
219 } /* CreateChannelByNameOrChannel */
222 EXTERNAL RESPONSECODE IFDHCreateChannelByName(DWORD Lun, LPSTR lpcDevice)
224 return CreateChannelByNameOrChannel(Lun, lpcDevice, -1);
227 EXTERNAL RESPONSECODE IFDHCreateChannel(DWORD Lun, DWORD Channel)
230 * Lun - Logical Unit Number, use this for multiple card slots or
231 * multiple readers. 0xXXXXYYYY - XXXX multiple readers, YYYY multiple
232 * slots. The resource manager will set these automatically. By
233 * default the resource manager loads a new instance of the driver so
234 * if your reader does not have more than one smartcard slot then
235 * ignore the Lun in all the functions. Future versions of PC/SC might
236 * support loading multiple readers through one instance of the driver
237 * in which XXXX would be important to implement if you want this.
241 * Channel - Channel ID. This is denoted by the following: 0x000001 -
242 * /dev/pcsc/1 0x000002 - /dev/pcsc/2 0x000003 - /dev/pcsc/3
244 * USB readers may choose to ignore this parameter and query the bus
245 * for the particular reader.
249 * This function is required to open a communications channel to the
250 * port listed by Channel. For example, the first serial reader on
251 * COM1 would link to /dev/pcsc/1 which would be a sym link to
252 * /dev/ttyS0 on some machines This is used to help with intermachine
255 * Once the channel is opened the reader must be in a state in which
256 * it is possible to query IFDHICCPresence() for card status.
260 * IFD_SUCCESS IFD_COMMUNICATION_ERROR
262 return CreateChannelByNameOrChannel(Lun, NULL, Channel);
263 } /* IFDHCreateChannel */
266 EXTERNAL RESPONSECODE IFDHCloseChannel(DWORD Lun)
269 * This function should close the reader communication channel for the
270 * particular reader. Prior to closing the communication channel the
271 * reader should make sure the card is powered down and the terminal
272 * is also powered down.
276 * IFD_SUCCESS IFD_COMMUNICATION_ERROR
280 if (-1 == (reader_index = LunToReaderIndex(Lun)))
281 return IFD_COMMUNICATION_ERROR;
283 DEBUG_INFO3("%s (lun: " DWORD_X ")", CcidSlots[reader_index].readerName,
286 /* Restore the default timeout
287 * No need to wait too long if the reader disapeared */
288 get_ccid_descriptor(reader_index)->readTimeout = DEFAULT_COM_READ_TIMEOUT;
290 (void)CmdPowerOff(reader_index);
291 /* No reader status check, if it failed, what can you do ? :) */
293 FreeChannel(reader_index);
296 } /* IFDHCloseChannel */
299 #if !defined(TWIN_SERIAL)
300 static RESPONSECODE IFDHPolling(DWORD Lun, int timeout)
304 if (-1 == (reader_index = LunToReaderIndex(Lun)))
305 return IFD_COMMUNICATION_ERROR;
307 /* log only if DEBUG_LEVEL_PERIODIC is set */
308 if (LogLevel & DEBUG_LEVEL_PERIODIC)
309 DEBUG_INFO4("%s (lun: " DWORD_X ") %d ms",
310 CcidSlots[reader_index].readerName, Lun, timeout);
312 return InterruptRead(reader_index, timeout);
315 /* on an ICCD device the card is always inserted
316 * so no card movement will ever happen: just do nothing */
317 static RESPONSECODE IFDHSleep(DWORD Lun, int timeout)
321 if (-1 == (reader_index = LunToReaderIndex(Lun)))
322 return IFD_COMMUNICATION_ERROR;
324 DEBUG_INFO4("%s (lun: " DWORD_X ") %d ms",
325 CcidSlots[reader_index].readerName, Lun, timeout);
327 /* just sleep for 5 seconds since the polling thread is NOT killable
328 * so pcscd event thread must loop to exit cleanly
330 * Once the driver (libusb in fact) will support
331 * TAG_IFD_POLLING_THREAD_KILLABLE then we could use a much longer delay
332 * and be killed before pcscd exits
334 (void)usleep(timeout * 1000);
338 static RESPONSECODE IFDHStopPolling(DWORD Lun)
342 if (-1 == (reader_index = LunToReaderIndex(Lun)))
343 return IFD_COMMUNICATION_ERROR;
345 DEBUG_INFO3("%s (lun: " DWORD_X ")",
346 CcidSlots[reader_index].readerName, Lun);
348 (void)InterruptStop(reader_index);
354 EXTERNAL RESPONSECODE IFDHGetCapabilities(DWORD Lun, DWORD Tag,
355 PDWORD Length, PUCHAR Value)
358 * This function should get the slot/card capabilities for a
359 * particular slot/card specified by Lun. Again, if you have only 1
360 * card slot and don't mind loading a new driver for each reader then
363 * Tag - the tag for the information requested example: TAG_IFD_ATR -
364 * return the Atr and its size (required). these tags are defined in
367 * Length - the length of the returned data Value - the value of the
372 * IFD_SUCCESS IFD_ERROR_TAG
375 RESPONSECODE return_value = IFD_SUCCESS;
377 if (-1 == (reader_index = LunToReaderIndex(Lun)))
378 return IFD_COMMUNICATION_ERROR;
380 DEBUG_INFO4("tag: 0x" DWORD_X ", %s (lun: " DWORD_X ")", Tag,
381 CcidSlots[reader_index].readerName, Lun);
386 case SCARD_ATTR_ATR_STRING:
387 /* If Length is not zero, powerICC has been performed.
388 * Otherwise, return NULL pointer
389 * Buffer size is stored in *Length */
390 if ((int)*Length >= CcidSlots[reader_index].nATRLength)
392 *Length = CcidSlots[reader_index].nATRLength;
394 memcpy(Value, CcidSlots[reader_index].pcATRBuffer, *Length);
397 return_value = IFD_ERROR_INSUFFICIENT_BUFFER;
400 case SCARD_ATTR_ICC_INTERFACE_STATUS:
402 if (IFD_ICC_PRESENT == IFDHICCPresence(Lun))
403 /* nonzero if contact is active */
406 /* smart card electrical contact is not active */
410 case SCARD_ATTR_ICC_PRESENCE:
412 /* Single byte indicating smart card presence:
414 * 1 = card present but not swallowed (applies only if
415 * reader supports smart card swallowing)
416 * 2 = card present (and swallowed if reader supports smart
418 * 4 = card confiscated. */
419 if (IFD_ICC_PRESENT == IFDHICCPresence(Lun))
428 case TAG_IFD_SIMULTANEOUS_ACCESS:
432 *Value = CCID_DRIVER_MAX_READERS;
435 return_value = IFD_ERROR_INSUFFICIENT_BUFFER;
438 case TAG_IFD_THREAD_SAFE:
443 *Value = 0; /* Apple pcscd is bogus (rdar://problem/5697388) */
445 *Value = 1; /* Can talk to multiple readers at the same time */
449 return_value = IFD_ERROR_INSUFFICIENT_BUFFER;
453 case TAG_IFD_SLOTS_NUMBER:
457 *Value = 1 + get_ccid_descriptor(reader_index) -> bMaxSlotIndex;
458 #ifdef USE_COMPOSITE_AS_MULTISLOT
460 /* On MacOS X or Linux+libusb we can simulate a
461 * composite device with 2 CCID interfaces by a
462 * multi-slot reader */
463 int readerID = get_ccid_descriptor(reader_index) -> readerID;
465 /* 2 CCID interfaces */
466 if ((GEMALTOPROXDU == readerID)
467 || (GEMALTOPROXSU == readerID)
468 || (HID_OMNIKEY_5422 == readerID))
471 /* 3 CCID interfaces */
472 if (FEITIANR502DUAL == readerID)
476 DEBUG_INFO2("Reader supports %d slot(s)", *Value);
479 return_value = IFD_ERROR_INSUFFICIENT_BUFFER;
482 case TAG_IFD_SLOT_THREAD_SAFE:
486 *Value = 0; /* Can NOT talk to multiple slots at the same time */
489 return_value = IFD_ERROR_INSUFFICIENT_BUFFER;
492 case SCARD_ATTR_VENDOR_IFD_VERSION:
494 int IFD_bcdDevice = get_ccid_descriptor(reader_index)->IFD_bcdDevice;
496 /* Vendor-supplied interface device version (DWORD in the form
497 * 0xMMmmbbbb where MM = major version, mm = minor version, and
498 * bbbb = build number). */
501 *(uint32_t *)Value = IFD_bcdDevice << 16;
505 case SCARD_ATTR_VENDOR_NAME:
507 const char *sIFD_iManufacturer = get_ccid_descriptor(reader_index) -> sIFD_iManufacturer;
509 if (sIFD_iManufacturer)
511 strlcpy((char *)Value, sIFD_iManufacturer, *Length);
512 *Length = strlen((char *)Value) +1;
522 case SCARD_ATTR_MAXINPUT:
523 *Length = sizeof(uint32_t);
525 *(uint32_t *)Value = get_ccid_descriptor(reader_index) -> dwMaxCCIDMessageLength -10;
528 #if !defined(TWIN_SERIAL)
529 case TAG_IFD_POLLING_THREAD_WITH_TIMEOUT:
531 _ccid_descriptor *ccid_desc;
533 /* default value: not supported */
536 ccid_desc = get_ccid_descriptor(reader_index);
538 /* CCID and not ICCD */
539 if ((PROTOCOL_CCID == ccid_desc -> bInterfaceProtocol)
541 && (3 == ccid_desc -> bNumEndpoints))
543 *Length = sizeof(void *);
545 *(void **)Value = IFDHPolling;
548 if ((PROTOCOL_ICCD_A == ccid_desc->bInterfaceProtocol)
549 || (PROTOCOL_ICCD_B == ccid_desc->bInterfaceProtocol))
551 *Length = sizeof(void *);
553 *(void **)Value = IFDHSleep;
558 case TAG_IFD_POLLING_THREAD_KILLABLE:
560 _ccid_descriptor *ccid_desc;
562 /* default value: not supported */
565 ccid_desc = get_ccid_descriptor(reader_index);
566 if ((PROTOCOL_ICCD_A == ccid_desc->bInterfaceProtocol)
567 || (PROTOCOL_ICCD_B == ccid_desc->bInterfaceProtocol))
569 *Length = 1; /* 1 char */
571 *Value = 1; /* TRUE */
576 case TAG_IFD_STOP_POLLING_THREAD:
578 _ccid_descriptor *ccid_desc;
580 /* default value: not supported */
583 ccid_desc = get_ccid_descriptor(reader_index);
584 /* CCID and not ICCD */
585 if ((PROTOCOL_CCID == ccid_desc -> bInterfaceProtocol)
587 && (3 == ccid_desc -> bNumEndpoints))
589 *Length = sizeof(void *);
591 *(void **)Value = IFDHStopPolling;
597 case SCARD_ATTR_VENDOR_IFD_SERIAL_NO:
599 _ccid_descriptor *ccid_desc;
601 ccid_desc = get_ccid_descriptor(reader_index);
602 if (ccid_desc->sIFD_serial_number)
604 strlcpy((char *)Value, ccid_desc->sIFD_serial_number, *Length);
605 *Length = strlen((char *)Value)+1;
615 #if !defined(TWIN_SERIAL)
616 case SCARD_ATTR_CHANNEL_ID:
618 *Length = sizeof(uint32_t);
620 uint32_t bus = get_ccid_usb_bus_number(reader_index);
621 uint32_t addr = get_ccid_usb_device_address(reader_index);
622 *(uint32_t *)Value = ((uint32_t)0x0020 << 16) | bus << 8 | addr;
629 return_value = IFD_ERROR_TAG;
633 } /* IFDHGetCapabilities */
636 EXTERNAL RESPONSECODE IFDHSetCapabilities(DWORD Lun, DWORD Tag,
637 /*@unused@*/ DWORD Length, /*@unused@*/ PUCHAR Value)
640 * This function should set the slot/card capabilities for a
641 * particular slot/card specified by Lun. Again, if you have only 1
642 * card slot and don't mind loading a new driver for each reader then
645 * Tag - the tag for the information needing set
647 * Length - the length of the returned data Value - the value of the
652 * IFD_SUCCESS IFD_ERROR_TAG IFD_ERROR_SET_FAILURE
653 * IFD_ERROR_VALUE_READ_ONLY
661 if (-1 == (reader_index = LunToReaderIndex(Lun)))
662 return IFD_COMMUNICATION_ERROR;
664 DEBUG_INFO4("tag: 0x" DWORD_X ", %s (lun: " DWORD_X ")", Tag,
665 CcidSlots[reader_index].readerName, Lun);
667 return IFD_NOT_SUPPORTED;
668 } /* IFDHSetCapabilities */
671 EXTERNAL RESPONSECODE IFDHSetProtocolParameters(DWORD Lun, DWORD Protocol,
672 UCHAR Flags, UCHAR PTS1, UCHAR PTS2, UCHAR PTS3)
675 * This function should set the PTS of a particular card/slot using
676 * the three PTS parameters sent
678 * Protocol - SCARD_PROTOCOL_T0 or SCARD_PROTOCOL_T1
679 * Flags - Logical OR of possible values:
683 * to determine which PTS values to negotiate.
684 * PTS1,PTS2,PTS3 - PTS Values.
688 * IFD_ERROR_PTS_FAILURE
689 * IFD_COMMUNICATION_ERROR
690 * IFD_PROTOCOL_NOT_SUPPORTED
693 BYTE pps[PPS_MAX_LENGTH];
700 /* Set ccid desc params */
702 _ccid_descriptor *ccid_desc;
704 if (-1 == (reader_index = LunToReaderIndex(Lun)))
705 return IFD_COMMUNICATION_ERROR;
707 DEBUG_INFO4("protocol T=" DWORD_D ", %s (lun: " DWORD_X ")",
708 Protocol-SCARD_PROTOCOL_T0, CcidSlots[reader_index].readerName, Lun);
710 /* Set to zero buffer */
711 memset(pps, 0, sizeof(pps));
712 memset(&atr, 0, sizeof(atr));
714 /* Get ccid params */
715 ccid_slot = get_ccid_slot(reader_index);
716 ccid_desc = get_ccid_descriptor(reader_index);
718 /* Do not send CCID command SetParameters or PPS to the CCID
719 * The CCID will do this himself */
720 if (ccid_desc->dwFeatures & CCID_CLASS_AUTO_PPS_PROP)
722 DEBUG_COMM2("Timeout: %d ms", ccid_desc->readTimeout);
726 /* Get ATR of the card */
727 atr_ret = ATR_InitFromArray(&atr, ccid_slot->pcATRBuffer,
728 ccid_slot->nATRLength);
729 if (ATR_MALFORMED == atr_ret)
730 return IFD_PROTOCOL_NOT_SUPPORTED;
732 if (SCARD_PROTOCOL_T0 == Protocol)
733 pps[1] |= ATR_PROTOCOL_TYPE_T0;
735 if (SCARD_PROTOCOL_T1 == Protocol)
736 pps[1] |= ATR_PROTOCOL_TYPE_T1;
738 return IFD_PROTOCOL_NOT_SUPPORTED;
740 /* TA2 present -> specific mode */
741 if (atr.ib[1][ATR_INTERFACE_BYTE_TA].present)
743 if (pps[1] != (atr.ib[1][ATR_INTERFACE_BYTE_TA].value & 0x0F))
746 DEBUG_COMM3("Specific mode in T=%d and T=%d requested",
747 atr.ib[1][ATR_INTERFACE_BYTE_TA].value & 0x0F, pps[1]);
749 return IFD_PROTOCOL_NOT_SUPPORTED;
753 /* TCi (i>2) indicates CRC instead of LRC */
754 if (SCARD_PROTOCOL_T1 == Protocol)
756 t1_state_t *t1 = &(ccid_slot -> t1);
759 /* TCi (i>2) present? */
760 for (i=2; i<ATR_MAX_PROTOCOLS; i++)
761 if (atr.ib[i][ATR_INTERFACE_BYTE_TC].present)
763 if (0 == atr.ib[i][ATR_INTERFACE_BYTE_TC].value)
765 DEBUG_COMM("Use LRC");
766 (void)t1_set_param(t1, IFD_PROTOCOL_T1_CHECKSUM_LRC, 0);
769 if (1 == atr.ib[i][ATR_INTERFACE_BYTE_TC].value)
771 DEBUG_COMM("Use CRC");
772 (void)t1_set_param(t1, IFD_PROTOCOL_T1_CHECKSUM_CRC, 0);
775 DEBUG_COMM2("Wrong value for TCi: %d",
776 atr.ib[i][ATR_INTERFACE_BYTE_TC].value);
778 /* only the first TCi (i>2) must be used */
784 if (Flags & IFD_NEGOTIATE_PTS1)
786 /* just use the value passed in argument */
787 pps[1] |= 0x10; /* PTS1 presence */
793 if (atr.ib[0][ATR_INTERFACE_BYTE_TA].present)
795 unsigned int card_baudrate;
796 unsigned int default_baudrate;
799 (void)ATR_GetParameter(&atr, ATR_PARAMETER_D, &d);
800 (void)ATR_GetParameter(&atr, ATR_PARAMETER_F, &f);
802 /* may happen with non ISO cards */
803 if ((0 == f) || (0 == d))
805 /* values for TA1=11 */
810 /* Baudrate = f x D/F */
811 card_baudrate = (unsigned int) (1000 * ccid_desc->dwDefaultClock
814 default_baudrate = (unsigned int) (1000 * ccid_desc->dwDefaultClock
815 * ATR_DEFAULT_D / ATR_DEFAULT_F);
817 /* if the card does not try to lower the default speed */
818 if ((card_baudrate > default_baudrate)
819 /* and the reader is fast enough */
820 && (card_baudrate <= ccid_desc->dwMaxDataRate))
822 /* the reader has no baud rates table */
823 if ((NULL == ccid_desc->arrayOfSupportedDataRates)
824 /* or explicitely support it */
825 || find_baud_rate(card_baudrate,
826 ccid_desc->arrayOfSupportedDataRates))
828 pps[1] |= 0x10; /* PTS1 presence */
829 pps[2] = atr.ib[0][ATR_INTERFACE_BYTE_TA].value;
831 DEBUG_COMM2("Set speed to %d bauds", card_baudrate);
835 DEBUG_COMM2("Reader does not support %d bauds",
838 /* TA2 present -> specific mode: the card is supporting
839 * only the baud rate specified in TA1 but reader does not
840 * support this value. Reject the card. */
841 if (atr.ib[1][ATR_INTERFACE_BYTE_TA].present)
842 return IFD_COMMUNICATION_ERROR;
847 /* the card is too fast for the reader */
848 if ((card_baudrate > ccid_desc->dwMaxDataRate +2)
850 && (atr.ib[0][ATR_INTERFACE_BYTE_TA].value <= 0x97))
852 unsigned char old_TA1;
854 old_TA1 = atr.ib[0][ATR_INTERFACE_BYTE_TA].value;
855 while (atr.ib[0][ATR_INTERFACE_BYTE_TA].value > 0x94)
857 /* use a lower TA1 */
858 atr.ib[0][ATR_INTERFACE_BYTE_TA].value--;
860 (void)ATR_GetParameter(&atr, ATR_PARAMETER_D, &d);
861 (void)ATR_GetParameter(&atr, ATR_PARAMETER_F, &f);
863 /* Baudrate = f x D/F */
864 card_baudrate = (unsigned int) (1000 *
865 ccid_desc->dwDefaultClock * d / f);
867 /* the reader has a baud rate table */
868 if ((ccid_desc->arrayOfSupportedDataRates
869 /* and the baud rate is supported */
870 && find_baud_rate(card_baudrate,
871 ccid_desc->arrayOfSupportedDataRates))
872 /* or the reader has NO baud rate table */
873 || ((NULL == ccid_desc->arrayOfSupportedDataRates)
874 /* and the baud rate is bellow the limit */
875 && (card_baudrate <= ccid_desc->dwMaxDataRate)))
877 pps[1] |= 0x10; /* PTS1 presence */
878 pps[2] = atr.ib[0][ATR_INTERFACE_BYTE_TA].value;
880 DEBUG_COMM2("Set adapted speed to %d bauds",
887 /* restore original TA1 value */
888 atr.ib[0][ATR_INTERFACE_BYTE_TA].value = old_TA1;
895 if (Flags & IFD_NEGOTIATE_PTS2)
897 pps[1] |= 0x20; /* PTS2 presence */
902 if (Flags & IFD_NEGOTIATE_PTS3)
904 pps[1] |= 0x40; /* PTS3 presence */
911 /* Automatic PPS made by the ICC? */
912 if ((! (ccid_desc->dwFeatures & CCID_CLASS_AUTO_PPS_CUR))
913 /* TA2 absent: negociable mode */
914 && (! atr.ib[1][ATR_INTERFACE_BYTE_TA].present))
916 int default_protocol;
918 ATR_GetDefaultProtocol(&atr, &default_protocol, NULL);
920 /* if the requested protocol is not the default one
921 * or a TA1/PPS1 is present */
922 if (((pps[1] & 0x0F) != default_protocol) || (PPS_HAS_PPS1(pps)))
924 #ifdef O2MICRO_OZ776_PATCH
925 if ((OZ776 == ccid_desc->readerID)
926 || (OZ776_7772 == ccid_desc->readerID))
928 /* convert from ATR_PROTOCOL_TYPE_T? to SCARD_PROTOCOL_T? */
929 Protocol = default_protocol +
930 (SCARD_PROTOCOL_T0 - ATR_PROTOCOL_TYPE_T0);
931 DEBUG_INFO2("PPS not supported on O2Micro readers. Using T=" DWORD_D,
932 Protocol - SCARD_PROTOCOL_T0);
936 if (PPS_Exchange(reader_index, pps, &len, &pps[2]) != PPS_OK)
938 DEBUG_INFO1("PPS_Exchange Failed");
940 return IFD_ERROR_PTS_FAILURE;
945 /* Now we must set the reader parameters */
946 (void)ATR_GetConvention(&atr, &convention);
948 /* specific mode and implicit parameters? (b5 of TA2) */
949 if (atr.ib[1][ATR_INTERFACE_BYTE_TA].present
950 && (atr.ib[1][ATR_INTERFACE_BYTE_TA].value & 0x10))
951 return IFD_COMMUNICATION_ERROR;
954 if (SCARD_PROTOCOL_T1 == Protocol)
959 0x00, /* GuardTime */
961 0x00, /* ClockStop */
966 t1_state_t *t1 = &(ccid_slot -> t1);
971 /* TA1 is not default */
972 if (PPS_HAS_PPS1(pps))
976 if (2 == t1->rc_bytes)
979 /* the CCID should ignore this bit */
980 if (ATR_CONVENTION_INVERSE == convention)
983 /* get TC1 Extra guard time */
984 if (atr.ib[0][ATR_INTERFACE_BYTE_TC].present)
985 param[2] = atr.ib[0][ATR_INTERFACE_BYTE_TC].value;
987 /* TBi (i>2) present? BWI/CWI */
988 for (i=2; i<ATR_MAX_PROTOCOLS; i++)
989 if (atr.ib[i][ATR_INTERFACE_BYTE_TB].present)
991 DEBUG_COMM3("BWI/CWI (TB%d) present: 0x%02X", i+1,
992 atr.ib[i][ATR_INTERFACE_BYTE_TB].value);
993 param[3] = atr.ib[i][ATR_INTERFACE_BYTE_TB].value;
996 /* Hack for OpenPGP card */
997 unsigned char openpgp_atr[] = { 0x3B, 0xFA, 0x13,
998 0x00, 0xFF, 0x81, 0x31, 0x80, 0x45, 0x00, 0x31,
999 0xC1, 0x73, 0xC0, 0x01, 0x00, 0x00, 0x90, 0x00, 0xB1 };
1001 if (0 == memcmp(ccid_slot->pcATRBuffer, openpgp_atr,
1002 ccid_slot->nATRLength))
1003 /* change BWI from 4 to 7 to increase BWT from
1004 * 1.4s to 11s and avoid a timeout during on
1005 * board key generation (bogus card) */
1008 DEBUG_COMM2("OpenPGP hack, using 0x%02X", param[3]);
1012 /* only the first TBi (i>2) must be used */
1016 /* compute communication timeout */
1017 (void)ATR_GetParameter(&atr, ATR_PARAMETER_F, &f);
1018 (void)ATR_GetParameter(&atr, ATR_PARAMETER_D, &d);
1019 ccid_desc->readTimeout = T1_card_timeout(f, d, param[2],
1020 (param[3] & 0xF0) >> 4 /* BWI */, param[3] & 0x0F /* CWI */,
1021 ccid_desc->dwDefaultClock);
1023 ifsc = get_IFSC(&atr, &i);
1026 DEBUG_COMM3("IFSC (TA%d) present: %d", i, ifsc);
1030 DEBUG_COMM2("Timeout: %d ms", ccid_desc->readTimeout);
1032 ret = SetParameters(reader_index, 1, sizeof(param), param);
1033 if (IFD_SUCCESS != ret)
1042 0x00, /* GuardTime */
1043 0x0A, /* WaitingInteger */
1044 0x00 /* ClockStop */
1049 /* TA1 is not default */
1050 if (PPS_HAS_PPS1(pps))
1053 if (ATR_CONVENTION_INVERSE == convention)
1056 /* get TC1 Extra guard time */
1057 if (atr.ib[0][ATR_INTERFACE_BYTE_TC].present)
1058 param[2] = atr.ib[0][ATR_INTERFACE_BYTE_TC].value;
1061 if (atr.ib[1][ATR_INTERFACE_BYTE_TC].present)
1062 param[3] = atr.ib[1][ATR_INTERFACE_BYTE_TC].value;
1064 /* compute communication timeout */
1065 (void)ATR_GetParameter(&atr, ATR_PARAMETER_F, &f);
1066 (void)ATR_GetParameter(&atr, ATR_PARAMETER_D, &d);
1068 ccid_desc->readTimeout = T0_card_timeout(f, d, param[2] /* TC1 */,
1069 param[3] /* TC2 */, ccid_desc->dwDefaultClock);
1071 DEBUG_COMM2("Communication timeout: %d ms", ccid_desc->readTimeout);
1073 ret = SetParameters(reader_index, 0, sizeof(param), param);
1074 if (IFD_SUCCESS != ret)
1078 /* set IFSC & IFSD in T=1 */
1079 if (SCARD_PROTOCOL_T1 == Protocol)
1081 t1_state_t *t1 = &(ccid_slot -> t1);
1084 ifsc = get_IFSC(&atr, &i);
1087 DEBUG_COMM3("IFSC (TA%d) present: %d", i, ifsc);
1088 (void)t1_set_param(t1, IFD_PROTOCOL_T1_IFSC, ifsc);
1091 /* IFSD not negociated by the reader? */
1092 if (! (ccid_desc->dwFeatures & CCID_CLASS_AUTO_IFSD))
1094 DEBUG_COMM2("Negotiate IFSD at %d", ccid_desc -> dwMaxIFSD);
1095 if (t1_negotiate_ifsd(t1, 0, ccid_desc -> dwMaxIFSD) < 0)
1096 return IFD_COMMUNICATION_ERROR;
1098 (void)t1_set_param(t1, IFD_PROTOCOL_T1_IFSD, ccid_desc -> dwMaxIFSD);
1100 DEBUG_COMM3("T=1: IFSC=%d, IFSD=%d", t1->ifsc, t1->ifsd);
1104 /* store used protocol for use by the secure commands (verify/change PIN) */
1105 ccid_desc->cardProtocol = Protocol;
1108 } /* IFDHSetProtocolParameters */
1111 EXTERNAL RESPONSECODE IFDHPowerICC(DWORD Lun, DWORD Action,
1112 PUCHAR Atr, PDWORD AtrLength)
1115 * This function controls the power and reset signals of the smartcard
1116 * reader at the particular reader/slot specified by Lun.
1118 * Action - Action to be taken on the card.
1120 * IFD_POWER_UP - Power and reset the card if not done so (store the
1121 * ATR and return it and its length).
1123 * IFD_POWER_DOWN - Power down the card if not done already
1124 * (Atr/AtrLength should be zero'd)
1126 * IFD_RESET - Perform a quick reset on the card. If the card is not
1127 * powered power up the card. (Store and return the Atr/Length)
1129 * Atr - Answer to Reset of the card. The driver is responsible for
1130 * caching this value in case IFDHGetCapabilities is called requesting
1131 * the ATR and its length. This should not exceed MAX_ATR_SIZE.
1133 * AtrLength - Length of the Atr. This should not exceed
1138 * Memory cards without an ATR should return IFD_SUCCESS on reset but
1139 * the Atr should be zero'd and the length should be zero
1141 * Reset errors should return zero for the AtrLength and return
1142 * IFD_ERROR_POWER_ACTION.
1146 * IFD_SUCCESS IFD_ERROR_POWER_ACTION IFD_COMMUNICATION_ERROR
1150 unsigned int nlength;
1151 RESPONSECODE return_value = IFD_SUCCESS;
1152 unsigned char pcbuffer[10+MAX_ATR_SIZE];
1155 const char *actions[] = { "PowerUp", "PowerDown", "Reset" };
1157 unsigned int oldReadTimeout;
1158 _ccid_descriptor *ccid_descriptor;
1160 /* By default, assume it won't work :) */
1163 if (-1 == (reader_index = LunToReaderIndex(Lun)))
1164 return IFD_COMMUNICATION_ERROR;
1166 DEBUG_INFO4("action: %s, %s (lun: " DWORD_X ")",
1167 actions[Action-IFD_POWER_UP], CcidSlots[reader_index].readerName, Lun);
1171 case IFD_POWER_DOWN:
1172 /* Clear ATR buffer */
1173 CcidSlots[reader_index].nATRLength = 0;
1174 *CcidSlots[reader_index].pcATRBuffer = '\0';
1176 /* Memorise the request */
1177 CcidSlots[reader_index].bPowerFlags |= MASK_POWERFLAGS_PDWN;
1179 /* send the command */
1180 if (IFD_SUCCESS != CmdPowerOff(reader_index))
1182 DEBUG_CRITICAL("PowerDown failed");
1183 return_value = IFD_ERROR_POWER_ACTION;
1187 /* clear T=1 context */
1188 t1_release(&(get_ccid_slot(reader_index) -> t1));
1193 /* save the current read timeout computed from card capabilities */
1194 ccid_descriptor = get_ccid_descriptor(reader_index);
1195 oldReadTimeout = ccid_descriptor->readTimeout;
1197 /* The German eID card is bogus and need to be powered off
1198 * before a power on */
1199 if (KOBIL_IDTOKEN == ccid_descriptor -> readerID)
1201 /* send the command */
1202 if (IFD_SUCCESS != CmdPowerOff(reader_index))
1204 DEBUG_CRITICAL("PowerDown failed");
1205 return_value = IFD_ERROR_POWER_ACTION;
1210 /* use a very long timeout since the card can use up to
1211 * (9600+12)*33 ETU in total
1213 * 9600 ETU max between each byte
1214 * 33 bytes max for ATR
1215 * 1 ETU = 372 cycles during ATR
1216 * with a 4 MHz clock => 29 seconds
1218 ccid_descriptor->readTimeout = 60*1000;
1220 nlength = sizeof(pcbuffer);
1221 return_value = CmdPowerOn(reader_index, &nlength, pcbuffer,
1224 /* set back the old timeout */
1225 ccid_descriptor->readTimeout = oldReadTimeout;
1227 if (return_value != IFD_SUCCESS)
1229 /* used by GemCore SIM PRO: no card is present */
1230 if (GEMCORESIMPRO == ccid_descriptor -> readerID)
1231 get_ccid_descriptor(reader_index)->dwSlotStatus
1232 = IFD_ICC_NOT_PRESENT;
1234 DEBUG_CRITICAL("PowerUp failed");
1235 return_value = IFD_ERROR_POWER_ACTION;
1239 /* Power up successful, set state variable to memorise it */
1240 CcidSlots[reader_index].bPowerFlags |= MASK_POWERFLAGS_PUP;
1241 CcidSlots[reader_index].bPowerFlags &= ~MASK_POWERFLAGS_PDWN;
1243 /* Reset is returned, even if TCK is wrong */
1244 CcidSlots[reader_index].nATRLength = *AtrLength =
1245 (nlength < MAX_ATR_SIZE) ? nlength : MAX_ATR_SIZE;
1246 memcpy(Atr, pcbuffer, *AtrLength);
1247 memcpy(CcidSlots[reader_index].pcATRBuffer, pcbuffer, *AtrLength);
1249 /* initialise T=1 context */
1250 (void)t1_init(&(get_ccid_slot(reader_index) -> t1), reader_index);
1254 DEBUG_CRITICAL("Action not supported");
1255 return_value = IFD_NOT_SUPPORTED;
1259 return return_value;
1260 } /* IFDHPowerICC */
1263 EXTERNAL RESPONSECODE IFDHTransmitToICC(DWORD Lun, SCARD_IO_HEADER SendPci,
1264 PUCHAR TxBuffer, DWORD TxLength,
1265 PUCHAR RxBuffer, PDWORD RxLength, /*@unused@*/ PSCARD_IO_HEADER RecvPci)
1268 * This function performs an APDU exchange with the card/slot
1269 * specified by Lun. The driver is responsible for performing any
1270 * protocol specific exchanges such as T=0/1 ... differences. Calling
1271 * this function will abstract all protocol differences.
1273 * SendPci Protocol - 0, 1, .... 14 Length - Not used.
1275 * TxBuffer - Transmit APDU example (0x00 0xA4 0x00 0x00 0x02 0x3F
1276 * 0x00) TxLength - Length of this buffer. RxBuffer - Receive APDU
1277 * example (0x61 0x14) RxLength - Length of the received APDU. This
1278 * function will be passed the size of the buffer of RxBuffer and this
1279 * function is responsible for setting this to the length of the
1280 * received APDU. This should be ZERO on all errors. The resource
1281 * manager will take responsibility of zeroing out any temporary APDU
1282 * buffers for security reasons.
1284 * RecvPci Protocol - 0, 1, .... 14 Length - Not used.
1286 * Notes: The driver is responsible for knowing what type of card it
1287 * has. If the current slot/card contains a memory card then this
1288 * command should ignore the Protocol and use the MCT style commands
1289 * for support for these style cards and transmit them appropriately.
1290 * If your reader does not support memory cards or you don't want to
1293 * RxLength should be set to zero on error.
1297 * IFD_SUCCESS IFD_COMMUNICATION_ERROR IFD_RESPONSE_TIMEOUT
1298 * IFD_ICC_NOT_PRESENT IFD_PROTOCOL_NOT_SUPPORTED
1301 RESPONSECODE return_value;
1302 unsigned int rx_length;
1304 int old_read_timeout;
1305 int restore_timeout = FALSE;
1306 _ccid_descriptor *ccid_descriptor;
1310 if (-1 == (reader_index = LunToReaderIndex(Lun)))
1311 return IFD_COMMUNICATION_ERROR;
1313 ccid_descriptor = get_ccid_descriptor(reader_index);
1315 DEBUG_INFO3("%s (lun: " DWORD_X ")", CcidSlots[reader_index].readerName,
1318 /* special APDU for the Kobil IDToken (CLASS = 0xFF) */
1319 if (KOBIL_IDTOKEN == ccid_descriptor -> readerID)
1321 char manufacturer[] = {0xFF, 0x9A, 0x01, 0x01, 0x00};
1322 char product_name[] = {0xFF, 0x9A, 0x01, 0x03, 0x00};
1323 char firmware_version[] = {0xFF, 0x9A, 0x01, 0x06, 0x00};
1324 char driver_version[] = {0xFF, 0x9A, 0x01, 0x07, 0x00};
1326 if ((sizeof manufacturer == TxLength)
1327 && (memcmp(TxBuffer, manufacturer, sizeof manufacturer) == 0))
1329 DEBUG_INFO1("IDToken: Manufacturer command");
1330 memcpy(RxBuffer, "KOBIL systems\220\0", 15);
1335 if ((sizeof product_name == TxLength)
1336 && (memcmp(TxBuffer, product_name, sizeof product_name) == 0))
1338 DEBUG_INFO1("IDToken: Product name command");
1339 memcpy(RxBuffer, "IDToken\220\0", 9);
1344 if ((sizeof firmware_version == TxLength)
1345 && (memcmp(TxBuffer, firmware_version, sizeof firmware_version) == 0))
1347 int IFD_bcdDevice = ccid_descriptor -> IFD_bcdDevice;
1349 DEBUG_INFO1("IDToken: Firmware version command");
1350 *RxLength = sprintf((char *)RxBuffer, "%X.%02X",
1351 IFD_bcdDevice >> 8, IFD_bcdDevice & 0xFF);
1352 RxBuffer[(*RxLength)++] = 0x90;
1353 RxBuffer[(*RxLength)++] = 0x00;
1357 if ((sizeof driver_version == TxLength)
1358 && (memcmp(TxBuffer, driver_version, sizeof driver_version) == 0))
1360 DEBUG_INFO1("IDToken: Driver version command");
1361 #define DRIVER_VERSION "2012.2.7\220\0"
1362 memcpy(RxBuffer, DRIVER_VERSION, sizeof DRIVER_VERSION -1);
1363 *RxLength = sizeof DRIVER_VERSION -1;
1369 /* Pseudo-APDU as defined in PC/SC v2 part 10 supplement document
1370 * CLA=0xFF, INS=0xC2, P1=0x01 */
1371 if (0 == memcmp(TxBuffer, "\xFF\xC2\x01", 3))
1373 /* Yes, use the same timeout as for SCardControl() */
1374 restore_timeout = TRUE;
1375 old_read_timeout = ccid_descriptor -> readTimeout;
1376 ccid_descriptor -> readTimeout = 90 * 1000; /* 90 seconds */
1379 rx_length = *RxLength;
1380 return_value = CmdXfrBlock(reader_index, TxLength, TxBuffer, &rx_length,
1381 RxBuffer, SendPci.Protocol);
1382 if (IFD_SUCCESS == return_value)
1383 *RxLength = rx_length;
1387 /* restore timeout */
1388 if (restore_timeout)
1389 ccid_descriptor -> readTimeout = old_read_timeout;
1391 return return_value;
1392 } /* IFDHTransmitToICC */
1395 EXTERNAL RESPONSECODE IFDHControl(DWORD Lun, DWORD dwControlCode,
1396 PUCHAR TxBuffer, DWORD TxLength, PUCHAR RxBuffer, DWORD RxLength,
1397 PDWORD pdwBytesReturned)
1400 * This function performs a data exchange with the reader (not the
1401 * card) specified by Lun. Here XXXX will only be used. It is
1402 * responsible for abstracting functionality such as PIN pads,
1403 * biometrics, LCD panels, etc. You should follow the MCT, CTBCS
1404 * specifications for a list of accepted commands to implement.
1406 * TxBuffer - Transmit data TxLength - Length of this buffer. RxBuffer
1407 * - Receive data RxLength - Length of the received data. This
1408 * function will be passed the length of the buffer RxBuffer and it
1409 * must set this to the length of the received data.
1411 * Notes: RxLength should be zero on error.
1413 RESPONSECODE return_value = IFD_ERROR_NOT_SUPPORTED;
1415 _ccid_descriptor *ccid_descriptor;
1417 reader_index = LunToReaderIndex(Lun);
1418 if ((-1 == reader_index) || (NULL == pdwBytesReturned))
1419 return IFD_COMMUNICATION_ERROR;
1421 ccid_descriptor = get_ccid_descriptor(reader_index);
1423 DEBUG_INFO4("ControlCode: 0x" DWORD_X ", %s (lun: " DWORD_X ")",
1424 dwControlCode, CcidSlots[reader_index].readerName, Lun);
1425 DEBUG_INFO_XXD("Control TxBuffer: ", TxBuffer, TxLength);
1427 /* Set the return length to 0 to avoid problems */
1428 *pdwBytesReturned = 0;
1430 if (IOCTL_SMARTCARD_VENDOR_IFD_EXCHANGE == dwControlCode)
1432 int allowed = (DriverOptions & DRIVER_OPTION_CCID_EXCHANGE_AUTHORIZED);
1433 int readerID = ccid_descriptor -> readerID;
1435 if (VENDOR_GEMALTO == GET_VENDOR(readerID))
1437 unsigned char switch_interface[] = { 0x52, 0xF8, 0x04, 0x01, 0x00 };
1439 /* get firmware version escape command */
1440 if ((1 == TxLength) && (0x02 == TxBuffer[0]))
1443 /* switch interface escape command on the GemProx DU
1444 * the next byte in the command is the interface:
1445 * 0x01 switch to contactless interface
1446 * 0x02 switch to contact interface
1448 if ((GEMALTOPROXDU == readerID)
1450 && (0 == memcmp(TxBuffer, switch_interface, sizeof(switch_interface))))
1456 DEBUG_INFO1("ifd exchange (Escape command) not allowed");
1457 return_value = IFD_COMMUNICATION_ERROR;
1461 unsigned int iBytesReturned;
1463 iBytesReturned = RxLength;
1464 /* 30 seconds timeout for long commands */
1465 return_value = CmdEscape(reader_index, TxBuffer, TxLength,
1466 RxBuffer, &iBytesReturned, 30*1000);
1467 *pdwBytesReturned = iBytesReturned;
1471 /* Implement the PC/SC v2.02.07 Part 10 IOCTL mechanism */
1473 /* Query for features */
1474 /* 0x313520 is the Windows value for SCARD_CTL_CODE(3400)
1475 * This hack is needed for RDP applications */
1476 if ((CM_IOCTL_GET_FEATURE_REQUEST == dwControlCode)
1477 || (0x313520 == dwControlCode))
1479 unsigned int iBytesReturned = 0;
1480 PCSC_TLV_STRUCTURE *pcsc_tlv = (PCSC_TLV_STRUCTURE *)RxBuffer;
1481 int readerID = ccid_descriptor -> readerID;
1483 /* we need room for up to six records */
1484 if (RxLength < 6 * sizeof(PCSC_TLV_STRUCTURE))
1485 return IFD_ERROR_INSUFFICIENT_BUFFER;
1487 /* We can only support direct verify and/or modify currently */
1488 if (ccid_descriptor -> bPINSupport & CCID_CLASS_PIN_VERIFY)
1490 pcsc_tlv -> tag = FEATURE_VERIFY_PIN_DIRECT;
1491 pcsc_tlv -> length = 0x04; /* always 0x04 */
1492 set_U32(&pcsc_tlv -> value,
1493 htonl(IOCTL_FEATURE_VERIFY_PIN_DIRECT));
1496 iBytesReturned += sizeof(PCSC_TLV_STRUCTURE);
1499 if (ccid_descriptor -> bPINSupport & CCID_CLASS_PIN_MODIFY)
1501 pcsc_tlv -> tag = FEATURE_MODIFY_PIN_DIRECT;
1502 pcsc_tlv -> length = 0x04; /* always 0x04 */
1503 set_U32(&pcsc_tlv -> value,
1504 htonl(IOCTL_FEATURE_MODIFY_PIN_DIRECT));
1507 iBytesReturned += sizeof(PCSC_TLV_STRUCTURE);
1510 /* Provide IFD_PIN_PROPERTIES only for pinpad readers */
1511 if (ccid_descriptor -> bPINSupport)
1513 pcsc_tlv -> tag = FEATURE_IFD_PIN_PROPERTIES;
1514 pcsc_tlv -> length = 0x04; /* always 0x04 */
1515 set_U32(&pcsc_tlv -> value,
1516 htonl(IOCTL_FEATURE_IFD_PIN_PROPERTIES));
1519 iBytesReturned += sizeof(PCSC_TLV_STRUCTURE);
1522 if ((KOBIL_TRIBANK == readerID)
1523 || (KOBIL_MIDENTITY_VISUAL == readerID))
1525 pcsc_tlv -> tag = FEATURE_MCT_READER_DIRECT;
1526 pcsc_tlv -> length = 0x04; /* always 0x04 */
1527 set_U32(&pcsc_tlv -> value,
1528 htonl(IOCTL_FEATURE_MCT_READER_DIRECT));
1531 iBytesReturned += sizeof(PCSC_TLV_STRUCTURE);
1534 pcsc_tlv -> tag = FEATURE_GET_TLV_PROPERTIES;
1535 pcsc_tlv -> length = 0x04; /* always 0x04 */
1536 set_U32(&pcsc_tlv -> value,
1537 htonl(IOCTL_FEATURE_GET_TLV_PROPERTIES));
1539 iBytesReturned += sizeof(PCSC_TLV_STRUCTURE);
1541 /* IOCTL_SMARTCARD_VENDOR_IFD_EXCHANGE */
1542 if (DriverOptions & DRIVER_OPTION_CCID_EXCHANGE_AUTHORIZED)
1544 pcsc_tlv -> tag = FEATURE_CCID_ESC_COMMAND;
1545 pcsc_tlv -> length = 0x04; /* always 0x04 */
1546 set_U32(&pcsc_tlv -> value,
1547 htonl(IOCTL_SMARTCARD_VENDOR_IFD_EXCHANGE));
1550 iBytesReturned += sizeof(PCSC_TLV_STRUCTURE);
1553 *pdwBytesReturned = iBytesReturned;
1554 return_value = IFD_SUCCESS;
1557 /* Get PIN handling capabilities */
1558 if (IOCTL_FEATURE_IFD_PIN_PROPERTIES == dwControlCode)
1560 PIN_PROPERTIES_STRUCTURE *caps = (PIN_PROPERTIES_STRUCTURE *)RxBuffer;
1563 if (RxLength < sizeof(PIN_PROPERTIES_STRUCTURE))
1564 return IFD_ERROR_INSUFFICIENT_BUFFER;
1566 /* Only give the LCD size for now */
1567 set_U16(&caps -> wLcdLayout, ccid_descriptor -> wLcdLayout);
1569 /* Hardcoded special reader cases */
1570 switch (ccid_descriptor->readerID)
1575 validation = 0x02; /* Validation key pressed */
1578 validation = 0x07; /* Default */
1581 /* Gemalto readers providing firmware features */
1582 if (ccid_descriptor -> gemalto_firmware_features)
1583 validation = ccid_descriptor -> gemalto_firmware_features -> bEntryValidationCondition;
1585 caps -> bEntryValidationCondition = validation;
1586 caps -> bTimeOut2 = 0x00; /* We do not distinguish bTimeOut from TimeOut2 */
1588 *pdwBytesReturned = sizeof(*caps);
1589 return_value = IFD_SUCCESS;
1592 /* Reader features */
1593 if (IOCTL_FEATURE_GET_TLV_PROPERTIES == dwControlCode)
1599 RxBuffer[p++] = PCSCv2_PART10_PROPERTY_wLcdLayout; /* tag */
1600 RxBuffer[p++] = 2; /* length */
1601 tmp = ccid_descriptor -> wLcdLayout;
1602 RxBuffer[p++] = tmp & 0xFF; /* value in little endian order */
1603 RxBuffer[p++] = (tmp >> 8) & 0xFF;
1605 /* only if the reader has a display */
1606 if (ccid_descriptor -> wLcdLayout)
1608 /* wLcdMaxCharacters */
1609 RxBuffer[p++] = PCSCv2_PART10_PROPERTY_wLcdMaxCharacters; /* tag */
1610 RxBuffer[p++] = 2; /* length */
1611 tmp = ccid_descriptor -> wLcdLayout & 0xFF;
1612 RxBuffer[p++] = tmp & 0xFF; /* value in little endian order */
1613 RxBuffer[p++] = (tmp >> 8) & 0xFF;
1616 RxBuffer[p++] = PCSCv2_PART10_PROPERTY_wLcdMaxLines; /* tag */
1617 RxBuffer[p++] = 2; /* length */
1618 tmp = ccid_descriptor -> wLcdLayout >> 8;
1619 RxBuffer[p++] = tmp & 0xFF; /* value in little endian order */
1620 RxBuffer[p++] = (tmp >> 8) & 0xFF;
1624 RxBuffer[p++] = PCSCv2_PART10_PROPERTY_bTimeOut2;
1625 RxBuffer[p++] = 1; /* length */
1626 /* IFD does not distinguish bTimeOut from bTimeOut2 */
1627 RxBuffer[p++] = 0x00;
1630 if (VENDOR_GEMALTO == GET_VENDOR(ccid_descriptor -> readerID))
1632 unsigned char firmware[256];
1633 const unsigned char cmd[] = { 0x02 };
1637 len = sizeof(firmware);
1638 ret = CmdEscape(reader_index, cmd, sizeof(cmd), firmware, &len, 0);
1640 if (IFD_SUCCESS == ret)
1642 RxBuffer[p++] = PCSCv2_PART10_PROPERTY_sFirmwareID;
1643 RxBuffer[p++] = len;
1644 memcpy(&RxBuffer[p], firmware, len);
1649 /* Gemalto PC Pinpad V1 */
1650 if (((GEMPCPINPAD == ccid_descriptor -> readerID)
1651 && (0x0100 == ccid_descriptor -> IFD_bcdDevice))
1652 /* Covadis Véga-Alpha */
1653 || (VEGAALPHA == ccid_descriptor->readerID))
1656 RxBuffer[p++] = PCSCv2_PART10_PROPERTY_bMinPINSize;
1657 RxBuffer[p++] = 1; /* length */
1658 RxBuffer[p++] = 4; /* min PIN size */
1661 RxBuffer[p++] = PCSCv2_PART10_PROPERTY_bMaxPINSize;
1662 RxBuffer[p++] = 1; /* length */
1663 RxBuffer[p++] = 8; /* max PIN size */
1665 /* bEntryValidationCondition */
1666 RxBuffer[p++] = PCSCv2_PART10_PROPERTY_bEntryValidationCondition;
1667 RxBuffer[p++] = 1; /* length */
1668 RxBuffer[p++] = 0x02; /* validation key pressed */
1671 /* Cherry GmbH SmartTerminal ST-2xxx */
1672 if (CHERRYST2000 == ccid_descriptor -> readerID)
1675 RxBuffer[p++] = PCSCv2_PART10_PROPERTY_bMinPINSize;
1676 RxBuffer[p++] = 1; /* length */
1677 RxBuffer[p++] = 0; /* min PIN size */
1680 RxBuffer[p++] = PCSCv2_PART10_PROPERTY_bMaxPINSize;
1681 RxBuffer[p++] = 1; /* length */
1682 RxBuffer[p++] = 25; /* max PIN size */
1684 /* bEntryValidationCondition */
1685 RxBuffer[p++] = PCSCv2_PART10_PROPERTY_bEntryValidationCondition;
1686 RxBuffer[p++] = 1; /* length */
1687 RxBuffer[p++] = 0x02; /* validation key pressed */
1690 /* Cherry KC 1000 SC */
1691 if (CHERRY_KC1000SC == ccid_descriptor -> readerID)
1694 RxBuffer[p++] = PCSCv2_PART10_PROPERTY_bMinPINSize;
1695 RxBuffer[p++] = 1; /* length */
1696 RxBuffer[p++] = 0; /* min PIN size */
1699 RxBuffer[p++] = PCSCv2_PART10_PROPERTY_bMaxPINSize;
1700 RxBuffer[p++] = 1; /* length */
1701 RxBuffer[p++] = 32; /* max PIN size */
1705 if (HID_OMNIKEY_3821 == ccid_descriptor -> readerID)
1708 RxBuffer[p++] = PCSCv2_PART10_PROPERTY_bMinPINSize;
1709 RxBuffer[p++] = 1; /* length */
1710 RxBuffer[p++] = 1; /* min PIN size */
1713 RxBuffer[p++] = PCSCv2_PART10_PROPERTY_bMaxPINSize;
1714 RxBuffer[p++] = 1; /* length */
1715 RxBuffer[p++] = 31; /* max PIN size */
1718 /* Gemalto readers providing firmware features */
1719 if (ccid_descriptor -> gemalto_firmware_features)
1721 struct GEMALTO_FIRMWARE_FEATURES *features = ccid_descriptor -> gemalto_firmware_features;
1724 RxBuffer[p++] = PCSCv2_PART10_PROPERTY_bMinPINSize;
1725 RxBuffer[p++] = 1; /* length */
1726 RxBuffer[p++] = features -> MinimumPINSize; /* min PIN size */
1729 RxBuffer[p++] = PCSCv2_PART10_PROPERTY_bMaxPINSize;
1730 RxBuffer[p++] = 1; /* length */
1731 RxBuffer[p++] = features -> MaximumPINSize; /* max PIN size */
1733 /* bEntryValidationCondition */
1734 RxBuffer[p++] = PCSCv2_PART10_PROPERTY_bEntryValidationCondition;
1735 RxBuffer[p++] = 1; /* length */
1736 RxBuffer[p++] = features -> bEntryValidationCondition; /* validation key pressed */
1740 RxBuffer[p++] = PCSCv2_PART10_PROPERTY_bPPDUSupport;
1741 RxBuffer[p++] = 1; /* length */
1743 (DriverOptions & DRIVER_OPTION_CCID_EXCHANGE_AUTHORIZED) ? 1 : 0;
1744 /* bit0: PPDU is supported over SCardControl using
1745 * FEATURE_CCID_ESC_COMMAND */
1749 int idVendor = ccid_descriptor -> readerID >> 16;
1750 RxBuffer[p++] = PCSCv2_PART10_PROPERTY_wIdVendor;
1751 RxBuffer[p++] = 2; /* length */
1752 RxBuffer[p++] = idVendor & 0xFF;
1753 RxBuffer[p++] = idVendor >> 8;
1758 int idProduct = ccid_descriptor -> readerID & 0xFFFF;
1759 RxBuffer[p++] = PCSCv2_PART10_PROPERTY_wIdProduct;
1760 RxBuffer[p++] = 2; /* length */
1761 RxBuffer[p++] = idProduct & 0xFF;
1762 RxBuffer[p++] = idProduct >> 8;
1765 /* dwMaxAPDUDataSize */
1767 int MaxAPDUDataSize = 0; /* short APDU only by default */
1769 /* reader is TPDU or extended APDU */
1770 if ((ccid_descriptor -> dwFeatures & CCID_CLASS_EXTENDED_APDU)
1771 || (ccid_descriptor -> dwFeatures & CCID_CLASS_TPDU))
1772 MaxAPDUDataSize = 0x10000;
1774 RxBuffer[p++] = PCSCv2_PART10_PROPERTY_dwMaxAPDUDataSize;
1775 RxBuffer[p++] = 4; /* length */
1776 RxBuffer[p++] = MaxAPDUDataSize & 0xFF;
1777 RxBuffer[p++] = (MaxAPDUDataSize >> 8) & 0xFF;
1778 RxBuffer[p++] = (MaxAPDUDataSize >> 16) & 0xFF;
1779 RxBuffer[p++] = (MaxAPDUDataSize >> 24) & 0xFF;
1782 *pdwBytesReturned = p;
1783 return_value = IFD_SUCCESS;
1786 /* Verify a PIN, plain CCID */
1787 if (IOCTL_FEATURE_VERIFY_PIN_DIRECT == dwControlCode)
1789 unsigned int iBytesReturned;
1791 iBytesReturned = RxLength;
1792 return_value = SecurePINVerify(reader_index, TxBuffer, TxLength,
1793 RxBuffer, &iBytesReturned);
1794 *pdwBytesReturned = iBytesReturned;
1797 /* Modify a PIN, plain CCID */
1798 if (IOCTL_FEATURE_MODIFY_PIN_DIRECT == dwControlCode)
1800 unsigned int iBytesReturned;
1802 iBytesReturned = RxLength;
1803 return_value = SecurePINModify(reader_index, TxBuffer, TxLength,
1804 RxBuffer, &iBytesReturned);
1805 *pdwBytesReturned = iBytesReturned;
1808 /* MCT: Multifunctional Card Terminal */
1809 if (IOCTL_FEATURE_MCT_READER_DIRECT == dwControlCode)
1811 if ( (TxBuffer[0] != 0x20) /* CLA */
1812 || ((TxBuffer[1] & 0xF0) != 0x70) /* INS */
1814 * 0x70: SECODER INFO
1815 * 0x71: SECODER SELECT APPLICATION
1816 * 0x72: SECODER APPLICATION ACTIVE
1817 * 0x73: SECODER DATA CONFIRMATION
1818 * 0x74: SECODER PROCESS AUTHENTICATION TOKEN */
1819 || ((TxBuffer[1] & 0x0F) > 4)
1820 || (TxBuffer[2] != 0x00) /* P1 */
1821 || (TxBuffer[3] != 0x00) /* P2 */
1822 || (TxBuffer[4] != 0x00) /* Lind */
1825 DEBUG_INFO1("MCT Command refused by driver");
1826 return_value = IFD_COMMUNICATION_ERROR;
1830 unsigned int iBytesReturned;
1832 /* we just transmit the buffer as a CCID Escape command */
1833 iBytesReturned = RxLength;
1834 return_value = CmdEscape(reader_index, TxBuffer, TxLength,
1835 RxBuffer, &iBytesReturned, 0);
1836 *pdwBytesReturned = iBytesReturned;
1840 if (IFD_SUCCESS != return_value)
1841 *pdwBytesReturned = 0;
1843 DEBUG_INFO_XXD("Control RxBuffer: ", RxBuffer, *pdwBytesReturned);
1844 return return_value;
1848 EXTERNAL RESPONSECODE IFDHICCPresence(DWORD Lun)
1851 * This function returns the status of the card inserted in the
1852 * reader/slot specified by Lun. It will return either:
1854 * returns: IFD_ICC_PRESENT IFD_ICC_NOT_PRESENT
1855 * IFD_COMMUNICATION_ERROR
1858 unsigned char pcbuffer[SIZE_GET_SLOT_STATUS];
1859 RESPONSECODE return_value = IFD_COMMUNICATION_ERROR;
1862 _ccid_descriptor *ccid_descriptor;
1863 unsigned int oldReadTimeout;
1865 if (-1 == (reader_index = LunToReaderIndex(Lun)))
1866 return IFD_COMMUNICATION_ERROR;
1868 DEBUG_PERIODIC3("%s (lun: " DWORD_X ")", CcidSlots[reader_index].readerName, Lun);
1870 ccid_descriptor = get_ccid_descriptor(reader_index);
1872 if ((GEMCORESIMPRO == ccid_descriptor->readerID)
1873 && (ccid_descriptor->IFD_bcdDevice < 0x0200))
1875 /* GemCore SIM Pro firmware 2.00 and up features
1876 * a full independant second slot */
1877 return_value = ccid_descriptor->dwSlotStatus;
1881 /* save the current read timeout computed from card capabilities */
1882 oldReadTimeout = ccid_descriptor->readTimeout;
1884 /* use default timeout since the reader may not be present anymore */
1885 ccid_descriptor->readTimeout = DEFAULT_COM_READ_TIMEOUT;
1887 /* if DEBUG_LEVEL_PERIODIC is not set we remove DEBUG_LEVEL_COMM */
1888 oldLogLevel = LogLevel;
1889 if (! (LogLevel & DEBUG_LEVEL_PERIODIC))
1890 LogLevel &= ~DEBUG_LEVEL_COMM;
1892 return_value = CmdGetSlotStatus(reader_index, pcbuffer);
1894 /* set back the old timeout */
1895 ccid_descriptor->readTimeout = oldReadTimeout;
1897 /* set back the old LogLevel */
1898 LogLevel = oldLogLevel;
1900 if (return_value != IFD_SUCCESS)
1901 return return_value;
1903 return_value = IFD_COMMUNICATION_ERROR;
1904 switch (pcbuffer[7] & CCID_ICC_STATUS_MASK) /* bStatus */
1906 case CCID_ICC_PRESENT_ACTIVE:
1907 return_value = IFD_ICC_PRESENT;
1908 /* use default slot */
1911 case CCID_ICC_PRESENT_INACTIVE:
1912 if ((CcidSlots[reader_index].bPowerFlags == POWERFLAGS_RAZ)
1913 || (CcidSlots[reader_index].bPowerFlags & MASK_POWERFLAGS_PDWN))
1914 /* the card was previously absent */
1915 return_value = IFD_ICC_PRESENT;
1918 /* the card was previously present but has been
1919 * removed and inserted between two consecutive
1920 * IFDHICCPresence() calls */
1921 CcidSlots[reader_index].bPowerFlags = POWERFLAGS_RAZ;
1922 return_value = IFD_ICC_NOT_PRESENT;
1926 case CCID_ICC_ABSENT:
1927 /* Reset ATR buffer */
1928 CcidSlots[reader_index].nATRLength = 0;
1929 *CcidSlots[reader_index].pcATRBuffer = '\0';
1931 /* Reset PowerFlags */
1932 CcidSlots[reader_index].bPowerFlags = POWERFLAGS_RAZ;
1934 return_value = IFD_ICC_NOT_PRESENT;
1939 /* SCR331-DI contactless reader */
1940 if (((SCR331DI == ccid_descriptor->readerID)
1941 || (SDI010 == ccid_descriptor->readerID)
1942 || (SCR331DINTTCOM == ccid_descriptor->readerID))
1943 && (ccid_descriptor->bCurrentSlotIndex > 0))
1945 unsigned char cmd[] = { 0x11 };
1947 * response: 00 11 01 ?? no card
1948 * 01 04 00 ?? card present */
1950 unsigned char res[10];
1951 unsigned int length_res = sizeof(res);
1954 /* if DEBUG_LEVEL_PERIODIC is not set we remove DEBUG_LEVEL_COMM */
1955 oldLogLevel = LogLevel;
1956 if (! (LogLevel & DEBUG_LEVEL_PERIODIC))
1957 LogLevel &= ~DEBUG_LEVEL_COMM;
1959 ret = CmdEscape(reader_index, cmd, sizeof(cmd), res, &length_res, 0);
1961 /* set back the old LogLevel */
1962 LogLevel = oldLogLevel;
1964 if (ret != IFD_SUCCESS)
1966 DEBUG_INFO1("CmdEscape failed");
1967 /* simulate a card absent */
1972 return_value = IFD_ICC_PRESENT;
1975 /* Reset ATR buffer */
1976 CcidSlots[reader_index].nATRLength = 0;
1977 *CcidSlots[reader_index].pcATRBuffer = '\0';
1979 /* Reset PowerFlags */
1980 CcidSlots[reader_index].bPowerFlags = POWERFLAGS_RAZ;
1982 return_value = IFD_ICC_NOT_PRESENT;
1988 DEBUG_PERIODIC2("Card %s",
1989 IFD_ICC_PRESENT == return_value ? "present" : "absent");
1991 return return_value;
1992 } /* IFDHICCPresence */
1995 CcidDesc *get_ccid_slot(unsigned int reader_index)
1997 return &CcidSlots[reader_index];
1998 } /* get_ccid_slot */
2001 void init_driver(void)
2003 char infofile[FILENAME_MAX];
2006 list_t plist, *values;
2008 DEBUG_INFO1("Driver version: " VERSION);
2010 /* Info.plist full patch filename */
2011 (void)snprintf(infofile, sizeof(infofile), "%s/%s/Contents/Info.plist",
2012 PCSCLITE_HP_DROPDIR, BUNDLE);
2014 rv = bundleParse(infofile, &plist);
2018 rv = LTPBundleFindValueWithKey(&plist, "ifdLogLevel", &values);
2021 /* convert from hex or dec or octal */
2022 LogLevel = strtoul(list_get_at(values, 0), NULL, 0);
2024 /* print the log level used */
2025 DEBUG_INFO2("LogLevel: 0x%.4X", LogLevel);
2028 /* Driver options */
2029 rv = LTPBundleFindValueWithKey(&plist, "ifdDriverOptions", &values);
2032 /* convert from hex or dec or octal */
2033 DriverOptions = strtoul(list_get_at(values, 0), NULL, 0);
2035 /* print the log level used */
2036 DEBUG_INFO2("DriverOptions: 0x%.4X", DriverOptions);
2039 bundleRelease(&plist);
2042 e = getenv("LIBCCID_ifdLogLevel");
2045 /* convert from hex or dec or octal */
2046 LogLevel = strtoul(e, NULL, 0);
2048 /* print the log level used */
2049 DEBUG_INFO2("LogLevel from LIBCCID_ifdLogLevel: 0x%.4X", LogLevel);
2052 /* get the voltage parameter */
2053 switch ((DriverOptions >> 4) & 0x03)
2056 PowerOnVoltage = VOLTAGE_5V;
2060 PowerOnVoltage = VOLTAGE_3V;
2064 PowerOnVoltage = VOLTAGE_1_8V;
2068 PowerOnVoltage = VOLTAGE_AUTO;
2072 /* initialise the Lun to reader_index mapping */
2075 DebugInitialized = TRUE;
2079 static char find_baud_rate(unsigned int baudrate, unsigned int *list)
2083 DEBUG_COMM2("Card baud rate: %d", baudrate);
2085 /* Does the reader support the announced smart card data speed? */
2088 /* end of array marker */
2092 DEBUG_COMM2("Reader can do: %d", list[i]);
2094 /* We must take into account that the card_baudrate integral value
2095 * is an approximative result, computed from the d/f float result.
2097 if ((baudrate < list[i] + 2) && (baudrate > list[i] - 2))
2102 } /* find_baud_rate */
2105 static unsigned int T0_card_timeout(double f, double d, int TC1, int TC2,
2106 int clock_frequency)
2108 unsigned int timeout = DEFAULT_COM_READ_TIMEOUT;
2112 /* Timeout applied on ISO_IN or ISO_OUT card exchange
2113 * we choose the maximum computed value.
2115 * ISO_IN timeout is the sum of:
2116 * Terminal: Smart card:
2117 * 5 bytes header cmd ->
2121 * = 261 EGT + 3 WWT + 3 WWT
2123 * ISO_OUT Timeout is the sum of:
2124 * Terminal: Smart card:
2125 * 5 bytes header cmd ->
2126 * <- Procedure byte + 256 data bytes + SW1-SW2
2127 * = 5 EGT + 1 WWT + 259 WWT
2130 /* clock_frequency is in kHz so the times are in milliseconds and not
2133 /* may happen with non ISO cards */
2134 if ((0 == f) || (0 == d) || (0 == clock_frequency))
2135 return 60 * 1000; /* 60 seconds */
2138 /* see ch. 6.5.3 Extra Guard Time, page 12 of ISO 7816-3 */
2139 EGT = 12 * f / d / clock_frequency + (f / d) * TC1 / clock_frequency;
2142 /* see ch. 8.2 Character level, page 15 of ISO 7816-3 */
2143 WWT = 960 * TC2 * f / clock_frequency;
2146 t = 261 * EGT + (3 + 3) * WWT;
2151 t = 5 * EGT + (1 + 259) * WWT;
2156 } /* T0_card_timeout */
2159 static unsigned int T1_card_timeout(double f, double d, int TC1,
2160 int BWI, int CWI, int clock_frequency)
2162 double EGT, BWT, CWT, etu;
2163 unsigned int timeout;
2165 /* Timeout applied on ISO in + ISO out card exchange
2167 * Timeout is the sum of:
2168 * - ISO in delay between leading edge of the first character sent by the
2169 * interface device and the last one (NAD PCB LN APDU CKS) = 260 EGT,
2170 * - delay between ISO in and ISO out = BWT,
2171 * - ISO out delay between leading edge of the first character sent by the
2172 * card and the last one (NAD PCB LN DATAS CKS) = 260 CWT.
2175 /* clock_frequency is in kHz so the times are in milliseconds and not
2178 /* may happen with non ISO cards */
2179 if ((0 == f) || (0 == d) || (0 == clock_frequency))
2180 return 60 * 1000; /* 60 seconds */
2182 /* see ch. 6.5.2 Transmission factors F and D, page 12 of ISO 7816-3 */
2183 etu = f / d / clock_frequency;
2186 /* see ch. 6.5.3 Extra Guard Time, page 12 of ISO 7816-3 */
2187 EGT = 12 * etu + (f / d) * TC1 / clock_frequency;
2190 /* see ch. 9.5.3.2 Block Waiting Time, page 20 of ISO 7816-3 */
2191 BWT = 11 * etu + (1<<BWI) * 960 * 372 / clock_frequency;
2194 /* see ch. 9.5.3.1 Caracter Waiting Time, page 20 of ISO 7816-3 */
2195 CWT = (11 + (1<<CWI)) * etu;
2197 timeout = 260*EGT + BWT + 260*CWT;
2199 /* This is the card/reader timeout. Add 1 second for the libusb
2200 * timeout so we get the error from the reader. */
2204 } /* T1_card_timeout */
2207 static int get_IFSC(ATR_t *atr, int *idx)
2209 int i, ifsc, protocol = -1;
2211 /* default return values */
2215 for (i=0; i<ATR_MAX_PROTOCOLS; i++)
2217 /* TAi (i>2) present and protocol=1 => IFSC */
2218 if (i >= 2 && protocol == 1
2219 && atr->ib[i][ATR_INTERFACE_BYTE_TA].present)
2221 ifsc = atr->ib[i][ATR_INTERFACE_BYTE_TA].value;
2223 /* only the first TAi (i>2) must be used */
2228 if (atr->ib[i][ATR_INTERFACE_BYTE_TD].present)
2229 protocol = atr->ib[i][ATR_INTERFACE_BYTE_TD].value & 0x0F;
2234 /* 0xFF is not a valid value for IFSC */
2235 DEBUG_INFO2("Non ISO IFSC: 0x%X", ifsc);