pcsc-lite  2.2.3
ifdwrapper.c
Go to the documentation of this file.
1 /*
2  * MUSCLE SmartCard Development ( https://pcsclite.apdu.fr/ )
3  *
4  * Copyright (C) 1999-2004
5  * David Corcoran <corcoran@musclecard.com>
6  * Copyright (C) 2003-2004
7  * Damien Sauveron <damien.sauveron@labri.fr>
8  * Copyright (C) 2002-2023
9  * Ludovic Rousseau <ludovic.rousseau@free.fr>
10  *
11 Redistribution and use in source and binary forms, with or without
12 modification, are permitted provided that the following conditions
13 are met:
14 
15 1. Redistributions of source code must retain the above copyright
16  notice, this list of conditions and the following disclaimer.
17 2. Redistributions in binary form must reproduce the above copyright
18  notice, this list of conditions and the following disclaimer in the
19  documentation and/or other materials provided with the distribution.
20 3. The name of the author may not be used to endorse or promote products
21  derived from this software without specific prior written permission.
22 
23 THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
24 IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
25 OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
26 IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
27 INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
28 NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
29 DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
30 THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
31 (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
32 THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
33  */
34 
40 #include <errno.h>
41 #include <unistd.h>
42 #include <pthread.h>
43 
44 #include "config.h"
45 #include "misc.h"
46 #include "pcscd.h"
47 #include "debuglog.h"
48 #include "readerfactory.h"
49 #include "ifdwrapper.h"
50 #include "atrhandler.h"
51 #include "dyn_generic.h"
52 #include "sys_generic.h"
53 #include "utils.h"
54 
55 #ifdef PCSCLITE_STATIC_DRIVER
56 /* check that either IFDHANDLERv2 or IFDHANDLERv3 is
57  * defined */
58  #if ! (defined(IFDHANDLERv2) || defined(IFDHANDLERv3))
59  #error IFDHANDLER version not defined
60  #endif
61 #endif
62 
67 RESPONSECODE IFDSetPTS(READER_CONTEXT * rContext, DWORD dwProtocol,
68  UCHAR ucFlags, UCHAR ucPTS1, UCHAR ucPTS2, UCHAR ucPTS3)
69 {
70  RESPONSECODE rv;
71 
72 #ifndef PCSCLITE_STATIC_DRIVER
73  RESPONSECODE(*IFDH_set_protocol_parameters) (DWORD, DWORD, UCHAR,
74  UCHAR, UCHAR, UCHAR) = NULL;
75 
76  IFDH_set_protocol_parameters = (RESPONSECODE(*)(DWORD, DWORD, UCHAR,
77  UCHAR, UCHAR, UCHAR))
78  rContext->psFunctions.psFunctions_v2.pvfSetProtocolParameters;
79 
80  if (NULL == IFDH_set_protocol_parameters)
82 #endif
83 
84  /*
85  * Locking is done in winscard.c SCardConnect() and SCardReconnect()
86  *
87  * This avoids to renegotiate the protocol and confuse the card
88  * Error returned by CCID driver is: CCID_Receive Procedure byte conflict
89  */
90 
91 #ifndef PCSCLITE_STATIC_DRIVER
92  rv = (*IFDH_set_protocol_parameters) (rContext->slot,
93  dwProtocol, ucFlags, ucPTS1, ucPTS2, ucPTS3);
94 #else
95  rv = IFDHSetProtocolParameters(rContext->slot, dwProtocol, ucFlags,
96  ucPTS1, ucPTS2, ucPTS3);
97 #endif
98 
99  return rv;
100 }
101 
105 RESPONSECODE IFDOpenIFD(READER_CONTEXT * rContext)
106 {
107  RESPONSECODE rv = IFD_SUCCESS;
108 
109 #ifndef PCSCLITE_STATIC_DRIVER
110  RESPONSECODE(*IFDH_create_channel) (DWORD, DWORD) = NULL;
111  RESPONSECODE(*IFDH_create_channel_by_name) (DWORD, LPSTR) = NULL;
112 
113  if (rContext->version == IFD_HVERSION_2_0)
114  IFDH_create_channel =
115  rContext->psFunctions.psFunctions_v2.pvfCreateChannel;
116  else
117  {
118  IFDH_create_channel =
119  rContext->psFunctions.psFunctions_v3.pvfCreateChannel;
120  IFDH_create_channel_by_name =
121  rContext->psFunctions.psFunctions_v3.pvfCreateChannelByName;
122  }
123 #endif
124 
125  /* LOCK THIS CODE REGION */
126  (void)pthread_mutex_lock(rContext->mMutex);
127 
128 #ifndef PCSCLITE_STATIC_DRIVER
129  if (rContext->version == IFD_HVERSION_2_0)
130  {
131  rv = (*IFDH_create_channel) (rContext->slot, rContext->port);
132  } else
133  {
134  /* use device name only if defined */
135  if (rContext->device[0] != '\0')
136  rv = (*IFDH_create_channel_by_name) (rContext->slot, rContext->device);
137  else
138  rv = (*IFDH_create_channel) (rContext->slot, rContext->port);
139  }
140 #else
141 #if defined(IFDHANDLERv2)
142  rv = IFDHCreateChannel(rContext->slot, rContext->port);
143 #else
144  {
145  /* Use device name only if defined */
146  if (rContext->device[0] != '\0')
147  rv = IFDHCreateChannelByName(rContext->slot, rContext->device);
148  else
149  rv = IFDHCreateChannel(rContext->slot, rContext->port);
150  }
151 #endif
152 #endif
153 
154  /* END OF LOCKED REGION */
155  (void)pthread_mutex_unlock(rContext->mMutex);
156 
157  return rv;
158 }
159 
163 RESPONSECODE IFDCloseIFD(READER_CONTEXT * rContext)
164 {
165  RESPONSECODE rv;
166  int repeat;
167  bool do_unlock = true;
168 
169 #ifndef PCSCLITE_STATIC_DRIVER
170  RESPONSECODE(*IFDH_close_channel) (DWORD) = NULL;
171 
172  IFDH_close_channel = rContext->psFunctions.psFunctions_v2.pvfCloseChannel;
173 #endif
174 
175  /* TRY TO LOCK THIS CODE REGION */
176  repeat = 5;
177 again:
178  rv = pthread_mutex_trylock(rContext->mMutex);
179  if (EBUSY == rv)
180  {
181  Log1(PCSC_LOG_ERROR, "Locking failed");
182  repeat--;
183  if (repeat)
184  {
185  (void)SYS_USleep(100*1000); /* 100 ms */
186  goto again;
187  }
188  else
189  /* locking failed but we need to close the IFD */
190  do_unlock = false;
191  }
192 
193 #ifndef PCSCLITE_STATIC_DRIVER
194  rv = (*IFDH_close_channel) (rContext->slot);
195 #else
196  rv = IFDHCloseChannel(rContext->slot);
197 #endif
198 
199  /* END OF LOCKED REGION */
200  if (do_unlock)
201  (void)pthread_mutex_unlock(rContext->mMutex);
202 
203  return rv;
204 }
205 
209 RESPONSECODE IFDSetCapabilities(READER_CONTEXT * rContext, DWORD dwTag,
210  DWORD dwLength, PUCHAR pucValue)
211 {
212  RESPONSECODE rv;
213 
214 #ifndef PCSCLITE_STATIC_DRIVER
215  RESPONSECODE(*IFDH_set_capabilities) (DWORD, DWORD, DWORD, PUCHAR) = NULL;
216 
217  IFDH_set_capabilities = rContext->psFunctions.psFunctions_v2.pvfSetCapabilities;
218 #endif
219 
220  /*
221  * Let the calling function lock this otherwise a deadlock will
222  * result
223  */
224 
225 #ifndef PCSCLITE_STATIC_DRIVER
226  rv = (*IFDH_set_capabilities) (rContext->slot, dwTag,
227  dwLength, pucValue);
228 #else
229  rv = IFDHSetCapabilities(rContext->slot, dwTag, dwLength, pucValue);
230 #endif
231 
232  return rv;
233 }
234 
240 RESPONSECODE IFDGetCapabilities(READER_CONTEXT * rContext, DWORD dwTag,
241  PDWORD pdwLength, PUCHAR pucValue)
242 {
243  RESPONSECODE rv;
244 
245 #ifndef PCSCLITE_STATIC_DRIVER
246  RESPONSECODE(*IFDH_get_capabilities) (DWORD, DWORD, PDWORD, /*@out@*/ PUCHAR) = NULL;
247 
248  IFDH_get_capabilities =
249  rContext->psFunctions.psFunctions_v2.pvfGetCapabilities;
250 #endif
251 
252  /* LOCK THIS CODE REGION */
253  (void)pthread_mutex_lock(rContext->mMutex);
254 
255 #ifndef PCSCLITE_STATIC_DRIVER
256  rv = (*IFDH_get_capabilities) (rContext->slot, dwTag, pdwLength, pucValue);
257 #else
258  rv = IFDHGetCapabilities(rContext->slot, dwTag, pdwLength, pucValue);
259 #endif
260 
261  /* END OF LOCKED REGION */
262  (void)pthread_mutex_unlock(rContext->mMutex);
263 
264  return rv;
265 }
266 
270 RESPONSECODE IFDPowerICC(READER_CONTEXT * rContext, DWORD dwAction,
271  PUCHAR pucAtr, PDWORD pdwAtrLen)
272 {
273  RESPONSECODE rv;
274  DWORD dwStatus;
275  UCHAR dummyAtr[MAX_ATR_SIZE];
276  DWORD dummyAtrLen = sizeof(dummyAtr);
277 
278 #ifndef PCSCLITE_STATIC_DRIVER
279  RESPONSECODE(*IFDH_power_icc) (DWORD, DWORD, PUCHAR, PDWORD) = NULL;
280 #endif
281 
282  /*
283  * Zero out everything
284  */
285  dwStatus = 0;
286 
287  if (NULL == pucAtr)
288  pucAtr = dummyAtr;
289  if (NULL == pdwAtrLen)
290  pdwAtrLen = &dummyAtrLen;
291 
292  /*
293  * Check that the card is inserted first
294  */
295  rv = IFDStatusICC(rContext, &dwStatus);
296  if (rv != SCARD_S_SUCCESS)
297  return rv;
298 
299  if (dwStatus & SCARD_ABSENT)
300  return SCARD_W_REMOVED_CARD;
301 #ifndef PCSCLITE_STATIC_DRIVER
302  IFDH_power_icc = rContext->psFunctions.psFunctions_v2.pvfPowerICC;
303 #endif
304 
305  /* LOCK THIS CODE REGION */
306  (void)pthread_mutex_lock(rContext->mMutex);
307 
308 #ifndef PCSCLITE_STATIC_DRIVER
309  rv = (*IFDH_power_icc) (rContext->slot, dwAction, pucAtr, pdwAtrLen);
310 #else
311  rv = IFDHPowerICC(rContext->slot, dwAction, pucAtr, pdwAtrLen);
312 #endif
313 
314  /* END OF LOCKED REGION */
315  (void)pthread_mutex_unlock(rContext->mMutex);
316 
317  /* use clean values in case of error */
318  if (rv != IFD_SUCCESS)
319  {
320  *pdwAtrLen = 0;
321  pucAtr[0] = '\0';
322 
323  if (rv == IFD_NO_SUCH_DEVICE)
324  {
325  (void)SendHotplugSignal();
327  }
328 
329  return SCARD_E_NOT_TRANSACTED;
330  }
331 
332  return rv;
333 }
334 
339 LONG IFDStatusICC(READER_CONTEXT * rContext, PDWORD pdwStatus)
340 {
341  RESPONSECODE rv;
342  DWORD dwCardStatus = 0;
343 
344 #ifndef PCSCLITE_STATIC_DRIVER
345  RESPONSECODE(*IFDH_icc_presence) (DWORD) = NULL;
346 
347  IFDH_icc_presence = rContext->psFunctions.psFunctions_v2.pvfICCPresence;
348 #endif
349 
350  /* LOCK THIS CODE REGION */
351  (void)pthread_mutex_lock(rContext->mMutex);
352 
353 #ifndef PCSCLITE_STATIC_DRIVER
354  rv = (*IFDH_icc_presence) (rContext->slot);
355 #else
356  rv = IFDHICCPresence(rContext->slot);
357 #endif
358 
359  /* END OF LOCKED REGION */
360  (void)pthread_mutex_unlock(rContext->mMutex);
361 
362  if (rv == IFD_SUCCESS || rv == IFD_ICC_PRESENT)
363  dwCardStatus |= SCARD_PRESENT;
364  else
365  if (rv == IFD_ICC_NOT_PRESENT)
366  dwCardStatus |= SCARD_ABSENT;
367  else
368  {
369  Log2(PCSC_LOG_ERROR, "Card not transacted: %ld", rv);
370  *pdwStatus = SCARD_UNKNOWN;
371 
372  if (rv == IFD_NO_SUCH_DEVICE)
373  {
374  (void)SendHotplugSignal();
376  }
377 
378  return SCARD_E_NOT_TRANSACTED;
379  }
380 
381  *pdwStatus = dwCardStatus;
382 
383  return SCARD_S_SUCCESS;
384 }
385 
386 /*
387  * Function: IFDControl Purpose : This function provides a means for
388  * toggling a specific action on the reader such as swallow, eject,
389  * biometric.
390  */
391 
392 /*
393  * Valid only for IFDHandler version 2.0
394  */
395 
396 LONG IFDControl_v2(READER_CONTEXT * rContext, PUCHAR TxBuffer,
397  DWORD TxLength, PUCHAR RxBuffer, PDWORD RxLength)
398 {
399  RESPONSECODE rv = IFD_SUCCESS;
400 
401 #ifndef PCSCLITE_STATIC_DRIVER
402  RESPONSECODE(*IFDH_control_v2) (DWORD, PUCHAR, DWORD, /*@out@*/ PUCHAR,
403  PDWORD);
404 #endif
405 
406  if (rContext->version != IFD_HVERSION_2_0)
408 
409 #ifndef PCSCLITE_STATIC_DRIVER
410  IFDH_control_v2 = rContext->psFunctions.psFunctions_v2.pvfControl;
411 #endif
412 
413  /* LOCK THIS CODE REGION */
414  (void)pthread_mutex_lock(rContext->mMutex);
415 
416 #ifndef PCSCLITE_STATIC_DRIVER
417  rv = (*IFDH_control_v2) (rContext->slot, TxBuffer, TxLength,
418  RxBuffer, RxLength);
419 #elif defined(IFDHANDLERv2)
420  rv = IFDHControl(rContext->slot, TxBuffer, TxLength,
421  RxBuffer, RxLength);
422 #endif
423 
424  /* END OF LOCKED REGION */
425  (void)pthread_mutex_unlock(rContext->mMutex);
426 
427  if (rv == IFD_SUCCESS)
428  return SCARD_S_SUCCESS;
429  else
430  {
431  Log2(PCSC_LOG_ERROR, "Card not transacted: %ld", rv);
432  LogXxd(PCSC_LOG_DEBUG, "TxBuffer ", TxBuffer, TxLength);
433  LogXxd(PCSC_LOG_DEBUG, "RxBuffer ", RxBuffer, *RxLength);
434  return SCARD_E_NOT_TRANSACTED;
435  }
436 }
437 
443 /*
444  * Valid only for IFDHandler version 3.0 and up
445  */
446 
447 LONG IFDControl(READER_CONTEXT * rContext, DWORD ControlCode,
448  LPCVOID TxBuffer, DWORD TxLength, LPVOID RxBuffer, DWORD RxLength,
449  LPDWORD BytesReturned)
450 {
451  RESPONSECODE rv = IFD_SUCCESS;
452 
453 #ifndef PCSCLITE_STATIC_DRIVER
454  RESPONSECODE(*IFDH_control) (DWORD, DWORD, LPCVOID, DWORD, LPVOID, DWORD, LPDWORD);
455 #endif
456 
457  if (rContext->version < IFD_HVERSION_3_0)
459 
460 #ifndef PCSCLITE_STATIC_DRIVER
461  IFDH_control = rContext->psFunctions.psFunctions_v3.pvfControl;
462 #endif
463 
464  /* LOCK THIS CODE REGION */
465  (void)pthread_mutex_lock(rContext->mMutex);
466 
467 #ifndef PCSCLITE_STATIC_DRIVER
468  rv = (*IFDH_control) (rContext->slot, ControlCode, TxBuffer,
469  TxLength, RxBuffer, RxLength, BytesReturned);
470 #elif defined(IFDHANDLERv3)
471  rv = IFDHControl(rContext->slot, ControlCode, TxBuffer,
472  TxLength, RxBuffer, RxLength, BytesReturned);
473 #endif
474 
475  /* END OF LOCKED REGION */
476  (void)pthread_mutex_unlock(rContext->mMutex);
477 
478  if (rv == IFD_SUCCESS)
479  return SCARD_S_SUCCESS;
480  else
481  {
482  Log2(PCSC_LOG_ERROR, "Card not transacted: %ld", rv);
483  Log3(PCSC_LOG_DEBUG, "ControlCode: 0x%.8lX BytesReturned: %ld",
484  ControlCode, *BytesReturned);
485  LogXxd(PCSC_LOG_DEBUG, "TxBuffer ", TxBuffer, TxLength);
486  LogXxd(PCSC_LOG_DEBUG, "RxBuffer ", RxBuffer, *BytesReturned);
487 
488  if (rv == IFD_NO_SUCH_DEVICE)
489  {
490  (void)SendHotplugSignal();
492  }
493 
494  if ((IFD_ERROR_NOT_SUPPORTED == rv) || (IFD_NOT_SUPPORTED == rv))
496 
499 
500  return SCARD_E_NOT_TRANSACTED;
501  }
502 }
503 
507 LONG IFDTransmit(READER_CONTEXT * rContext, SCARD_IO_HEADER pioTxPci,
508  PUCHAR pucTxBuffer, DWORD dwTxLength, PUCHAR pucRxBuffer,
509  PDWORD pdwRxLength, PSCARD_IO_HEADER pioRxPci)
510 {
511  RESPONSECODE rv;
512 
513 #ifndef PCSCLITE_STATIC_DRIVER
514  RESPONSECODE(*IFDH_transmit_to_icc) (DWORD, SCARD_IO_HEADER, PUCHAR,
515  DWORD, /*@out@*/ PUCHAR, PDWORD, PSCARD_IO_HEADER) = NULL;
516 #endif
517 
518  /* log the APDU */
519  DebugLogCategory(DEBUG_CATEGORY_APDU, pucTxBuffer, dwTxLength);
520 
521 #ifndef PCSCLITE_STATIC_DRIVER
522  IFDH_transmit_to_icc =
523  rContext->psFunctions.psFunctions_v2.pvfTransmitToICC;
524 #endif
525 
526  /* LOCK THIS CODE REGION */
527  (void)pthread_mutex_lock(rContext->mMutex);
528 
529 #ifndef PCSCLITE_STATIC_DRIVER
530  rv = (*IFDH_transmit_to_icc) (rContext->slot, pioTxPci, (LPBYTE)
531  pucTxBuffer, dwTxLength, pucRxBuffer, pdwRxLength, pioRxPci);
532 #else
533  rv = IFDHTransmitToICC(rContext->slot, pioTxPci,
534  (LPBYTE) pucTxBuffer, dwTxLength,
535  pucRxBuffer, pdwRxLength, pioRxPci);
536 #endif
537 
538  /* END OF LOCKED REGION */
539  (void)pthread_mutex_unlock(rContext->mMutex);
540 
541  /* log the returned status word */
542  DebugLogCategory(DEBUG_CATEGORY_SW, pucRxBuffer, *pdwRxLength);
543 
544  if (rv == IFD_SUCCESS)
545  return SCARD_S_SUCCESS;
546  else
547  {
548  Log2(PCSC_LOG_ERROR, "Card not transacted: %ld", rv);
549 
550  if (rv == IFD_NO_SUCH_DEVICE)
551  {
552  (void)SendHotplugSignal();
554  }
555 
556  if (rv == IFD_ICC_NOT_PRESENT)
557  return SCARD_E_NO_SMARTCARD;
558 
559  return SCARD_E_NOT_TRANSACTED;
560  }
561 }
562 
atrhandler.h
This keeps track of smart card protocols, timing issues and Answer to Reset ATR handling.
IFDStatusICC
LONG IFDStatusICC(READER_CONTEXT *rContext, PDWORD pdwStatus)
Provide statistical information about the IFD and ICC including insertions, atr, powering status/etc.
Definition: ifdwrapper.c:339
ReaderContext::psFunctions
union ReaderContext::@3 psFunctions
driver functions
debuglog.h
This handles debugging.
ReaderContext::slot
int slot
Current Reader Slot.
Definition: readerfactory.h:125
ReaderContext::device
char * device
Device Name.
Definition: readerfactory.h:109
dyn_generic.h
This abstracts dynamic library loading functions.
IFDHICCPresence
RESPONSECODE IFDHICCPresence(DWORD Lun)
This function returns the status of the card inserted in the reader/slot specified by Lun.
IFDHControl
RESPONSECODE IFDHControl(DWORD Lun, DWORD dwControlCode, PUCHAR TxBuffer, DWORD TxLength, PUCHAR RxBuffer, DWORD RxLength, LPDWORD pdwBytesReturned)
This function performs a data exchange with the reader (not the card) specified by Lun.
IFD_ICC_NOT_PRESENT
#define IFD_ICC_NOT_PRESENT
card is absent
Definition: ifdhandler.h:366
SCARD_S_SUCCESS
#define SCARD_S_SUCCESS
No error was encountered.
Definition: pcsclite.h:107
ReaderContext::port
int port
Port ID.
Definition: readerfactory.h:124
IFDHSetProtocolParameters
RESPONSECODE IFDHSetProtocolParameters(DWORD Lun, DWORD Protocol, UCHAR Flags, UCHAR PTS1, UCHAR PTS2, UCHAR PTS3)
This function should set the Protocol Type Selection (PTS) of a particular card/slot using the three ...
SCARD_W_REMOVED_CARD
#define SCARD_W_REMOVED_CARD
The smart card has been removed, so further communication is not possible.
Definition: pcsclite.h:219
IFDHCloseChannel
RESPONSECODE IFDHCloseChannel(DWORD Lun)
This function should close the reader communication channel for the particular reader.
IFD_NOT_SUPPORTED
#define IFD_NOT_SUPPORTED
request is not supported
Definition: ifdhandler.h:364
SYS_USleep
int SYS_USleep(int)
Makes the current process sleep for some microseconds.
Definition: sys_unix.c:80
IFDHGetCapabilities
RESPONSECODE IFDHGetCapabilities(DWORD Lun, DWORD Tag, PDWORD Length, PUCHAR Value)
This function should get the slot/card capabilities for a particular slot/card specified by Lun.
IFD_ERROR_INSUFFICIENT_BUFFER
#define IFD_ERROR_INSUFFICIENT_BUFFER
buffer is too small
Definition: ifdhandler.h:373
SCARD_ABSENT
#define SCARD_ABSENT
Card is absent.
Definition: pcsclite.h:259
IFDGetCapabilities
RESPONSECODE IFDGetCapabilities(READER_CONTEXT *rContext, DWORD dwTag, PDWORD pdwLength, PUCHAR pucValue)
Gets capabilities in the reader.
Definition: ifdwrapper.c:240
sys_generic.h
This handles abstract system level calls.
IFDHCreateChannel
RESPONSECODE IFDHCreateChannel(DWORD Lun, DWORD Channel)
This function is required to open a communications channel to the port listed by Channel.
SCARD_UNKNOWN
#define SCARD_UNKNOWN
Unknown state.
Definition: pcsclite.h:258
readerfactory.h
This keeps track of a list of currently available reader structures.
IFDOpenIFD
RESPONSECODE IFDOpenIFD(READER_CONTEXT *rContext)
Open a communication channel to the IFD.
Definition: ifdwrapper.c:105
SCARD_E_READER_UNAVAILABLE
#define SCARD_E_READER_UNAVAILABLE
The specified reader is not currently available for use.
Definition: pcsclite.h:153
ReaderContext::mMutex
pthread_mutex_t * mMutex
Mutex for this connection.
Definition: readerfactory.h:112
SCARD_E_INSUFFICIENT_BUFFER
#define SCARD_E_INSUFFICIENT_BUFFER
The data buffer to receive returned data is too small for the returned data.
Definition: pcsclite.h:123
ReaderContext
Definition: readerfactory.h:107
IFDControl
LONG IFDControl(READER_CONTEXT *rContext, DWORD ControlCode, LPCVOID TxBuffer, DWORD TxLength, LPVOID RxBuffer, DWORD RxLength, LPDWORD BytesReturned)
Provide a means for toggling a specific action on the reader such as swallow, eject,...
Definition: ifdwrapper.c:447
SCARD_IO_HEADER
struct _SCARD_IO_HEADER SCARD_IO_HEADER
Use by SCardTransmit()
MAX_ATR_SIZE
#define MAX_ATR_SIZE
Maximum ATR size.
Definition: pcsclite.h:59
IFD_SUCCESS
#define IFD_SUCCESS
no error
Definition: ifdhandler.h:351
IFDHCreateChannelByName
RESPONSECODE IFDHCreateChannelByName(DWORD Lun, LPSTR DeviceName)
This function is required to open a communications channel to the port listed by DeviceName.
IFDSetPTS
RESPONSECODE IFDSetPTS(READER_CONTEXT *rContext, DWORD dwProtocol, UCHAR ucFlags, UCHAR ucPTS1, UCHAR ucPTS2, UCHAR ucPTS3)
Set the protocol type selection (PTS).
Definition: ifdwrapper.c:67
SCARD_E_NO_SMARTCARD
#define SCARD_E_NO_SMARTCARD
The operation requires a Smart Card, but no Smart Card is currently in the device.
Definition: pcsclite.h:131
ReaderContext::psFunctions_v2
FCT_MAP_V2 psFunctions_v2
API V2.0.
Definition: readerfactory.h:118
IFDPowerICC
RESPONSECODE IFDPowerICC(READER_CONTEXT *rContext, DWORD dwAction, PUCHAR pucAtr, PDWORD pdwAtrLen)
Power up/down or reset's an ICC located in the IFD.
Definition: ifdwrapper.c:270
ReaderContext::version
int version
IFD Handler version number.
Definition: readerfactory.h:123
IFDHPowerICC
RESPONSECODE IFDHPowerICC(DWORD Lun, DWORD Action, PUCHAR Atr, PDWORD AtrLength)
This function controls the power and reset signals of the smart card reader at the particular reader/...
IFDHSetCapabilities
RESPONSECODE IFDHSetCapabilities(DWORD Lun, DWORD Tag, DWORD Length, PUCHAR Value)
This function should set the slot/card capabilities for a particular slot/card specified by Lun.
IFDHTransmitToICC
RESPONSECODE IFDHTransmitToICC(DWORD Lun, SCARD_IO_HEADER SendPci, PUCHAR TxBuffer, DWORD TxLength, PUCHAR RxBuffer, PDWORD RxLength, PSCARD_IO_HEADER RecvPci)
This function performs an APDU exchange with the card/slot specified by Lun.
IFDTransmit
LONG IFDTransmit(READER_CONTEXT *rContext, SCARD_IO_HEADER pioTxPci, PUCHAR pucTxBuffer, DWORD dwTxLength, PUCHAR pucRxBuffer, PDWORD pdwRxLength, PSCARD_IO_HEADER pioRxPci)
Transmit an APDU to the ICC.
Definition: ifdwrapper.c:507
IFD_NO_SUCH_DEVICE
#define IFD_NO_SUCH_DEVICE
The IFD_NO_SUCH_DEVICE error must be returned by the driver when it detects the reader is no more pre...
Definition: ifdhandler.h:372
_SCARD_IO_HEADER
Use by SCardTransmit()
Definition: ifdhandler.h:311
ifdwrapper.h
This wraps the dynamic ifdhandler functions.
IFD_ICC_PRESENT
#define IFD_ICC_PRESENT
card is present
Definition: ifdhandler.h:365
IFDSetCapabilities
RESPONSECODE IFDSetCapabilities(READER_CONTEXT *rContext, DWORD dwTag, DWORD dwLength, PUCHAR pucValue)
Set capabilities in the reader.
Definition: ifdwrapper.c:209
SCARD_PRESENT
#define SCARD_PRESENT
Card is present.
Definition: pcsclite.h:260
IFDCloseIFD
RESPONSECODE IFDCloseIFD(READER_CONTEXT *rContext)
Close a communication channel to the IFD.
Definition: ifdwrapper.c:163
ReaderContext::psFunctions_v3
FCT_MAP_V3 psFunctions_v3
API V3.0.
Definition: readerfactory.h:119
SCARD_E_UNSUPPORTED_FEATURE
#define SCARD_E_UNSUPPORTED_FEATURE
This smart card does not support the requested feature.
Definition: pcsclite.h:171
SCARD_E_NOT_TRANSACTED
#define SCARD_E_NOT_TRANSACTED
An attempt was made to end a non-existent transaction.
Definition: pcsclite.h:151