00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00017 #include "config.h"
00018 #include "misc.h"
00019 #include "pcscd.h"
00020 #include "ifdhandler.h"
00021 #include "debuglog.h"
00022 #include "readerfactory.h"
00023 #include "ifdwrapper.h"
00024 #include "atrhandler.h"
00025 #include "dyn_generic.h"
00026 #include "sys_generic.h"
00027 #include "hotplug.h"
00028
00029 #undef PCSCLITE_STATIC_DRIVER
00030
00031
00032
00033
00034
00035
00036 LONG IFDSetPTS(PREADER_CONTEXT rContext, DWORD dwProtocol, UCHAR ucFlags,
00037 UCHAR ucPTS1, UCHAR ucPTS2, UCHAR ucPTS3)
00038 {
00039 RESPONSECODE rv = IFD_SUCCESS;
00040 UCHAR ucValue[1];
00041
00042 #ifndef PCSCLITE_STATIC_DRIVER
00043 RESPONSECODE(*IFD_set_protocol_parameters) (DWORD, UCHAR, UCHAR,
00044 UCHAR, UCHAR) = NULL;
00045 RESPONSECODE(*IFDH_set_protocol_parameters) (DWORD, DWORD, UCHAR,
00046 UCHAR, UCHAR, UCHAR) = NULL;
00047
00048 if (rContext->dwVersion == IFD_HVERSION_1_0)
00049 {
00050 IFD_set_protocol_parameters = (RESPONSECODE(*)(DWORD, UCHAR, UCHAR,
00051 UCHAR, UCHAR)) rContext->psFunctions.psFunctions_v1.pvfSetProtocolParameters;
00052
00053 if (NULL == IFD_set_protocol_parameters)
00054 return SCARD_E_UNSUPPORTED_FEATURE;
00055 }
00056 else
00057 {
00058 IFDH_set_protocol_parameters = (RESPONSECODE(*)(DWORD, DWORD, UCHAR,
00059 UCHAR, UCHAR, UCHAR))
00060 rContext->psFunctions.psFunctions_v2.pvfSetProtocolParameters;
00061
00062 if (NULL == IFDH_set_protocol_parameters)
00063 return SCARD_E_UNSUPPORTED_FEATURE;
00064 }
00065 #endif
00066
00067
00068
00069
00070 SYS_MutexLock(rContext->mMutex);
00071
00072 ucValue[0] = rContext->dwSlot;
00073
00074 #ifndef PCSCLITE_STATIC_DRIVER
00075 if (rContext->dwVersion == IFD_HVERSION_1_0)
00076 {
00077 ucValue[0] = rContext->dwSlot;
00078 IFDSetCapabilities(rContext, TAG_IFD_SLOTNUM, 1, ucValue);
00079 rv = (*IFD_set_protocol_parameters) (dwProtocol,
00080 ucFlags, ucPTS1, ucPTS2, ucPTS3);
00081 }
00082 else
00083 {
00084 rv = (*IFDH_set_protocol_parameters) (rContext->dwSlot,
00085 dwProtocol,
00086 ucFlags, ucPTS1,
00087 ucPTS2, ucPTS3);
00088 }
00089 #else
00090 if (rContext->dwVersion == IFD_HVERSION_1_0)
00091 {
00092 ucValue[0] = rContext->dwSlot;
00093 IFDSetCapabilities(rContext, TAG_IFD_SLOTNUM, 1, ucValue);
00094 rv = IFD_Set_Protocol_Parameters(dwProtocol, ucFlags, ucPTS1,
00095 ucPTS2, ucPTS3);
00096 }
00097 else
00098 {
00099 rv = IFDHSetProtocolParameters(rContext->dwSlot, dwProtocol,
00100 ucFlags, ucPTS1, ucPTS2, ucPTS3);
00101 }
00102 #endif
00103
00104 SYS_MutexUnLock(rContext->mMutex);
00105
00106
00107
00108
00109 return rv;
00110 }
00111
00112
00113
00114
00115
00116
00117 LONG IFDOpenIFD(PREADER_CONTEXT rContext)
00118 {
00119 RESPONSECODE rv = 0;
00120
00121 #ifndef PCSCLITE_STATIC_DRIVER
00122 RESPONSECODE(*IO_create_channel) (DWORD) = NULL;
00123 RESPONSECODE(*IFDH_create_channel) (DWORD, DWORD) = NULL;
00124 RESPONSECODE(*IFDH_create_channel_by_name) (DWORD, LPSTR) = NULL;
00125
00126 if (rContext->dwVersion == IFD_HVERSION_1_0)
00127 IO_create_channel =
00128 rContext->psFunctions.psFunctions_v1.pvfCreateChannel;
00129 else
00130 if (rContext->dwVersion == IFD_HVERSION_2_0)
00131 IFDH_create_channel =
00132 rContext->psFunctions.psFunctions_v2.pvfCreateChannel;
00133 else
00134 {
00135 IFDH_create_channel =
00136 rContext->psFunctions.psFunctions_v3.pvfCreateChannel;
00137 IFDH_create_channel_by_name =
00138 rContext->psFunctions.psFunctions_v3.pvfCreateChannelByName;
00139 }
00140 #endif
00141
00142
00143
00144
00145
00146 SYS_MutexLock(rContext->mMutex);
00147 #ifndef PCSCLITE_STATIC_DRIVER
00148 if (rContext->dwVersion == IFD_HVERSION_1_0)
00149 {
00150 rv = (*IO_create_channel) (rContext->dwPort);
00151 } else if (rContext->dwVersion == IFD_HVERSION_2_0)
00152 {
00153 rv = (*IFDH_create_channel) (rContext->dwSlot, rContext->dwPort);
00154 } else
00155 {
00156
00157 if (rContext->lpcDevice[0] != '\0')
00158 rv = (*IFDH_create_channel_by_name) (rContext->dwSlot, rContext->lpcDevice);
00159 else
00160 rv = (*IFDH_create_channel) (rContext->dwSlot, rContext->dwPort);
00161 }
00162 #else
00163 if (rContext->dwVersion == IFD_HVERSION_1_0)
00164 {
00165 rv = IO_Create_Channel(rContext->dwPort);
00166 } else if (rContext->dwVersion == IFD_HVERSION_2_0)
00167 {
00168 rv = IFDHCreateChannel(rContext->dwSlot, rContext->dwPort);
00169 } else
00170 {
00171
00172 if (rContext->lpcDevice[0] != '\0')
00173 rv = IFDHCreateChannelByName(rContext->dwSlot, rContext->lpcDevice);
00174 else
00175 rv = IFDHCreateChannel(rContext->dwSlot, rContext->dwPort);
00176 }
00177 #endif
00178 SYS_MutexUnLock(rContext->mMutex);
00179
00180
00181
00182
00183
00184 return rv;
00185 }
00186
00187
00188
00189
00190
00191
00192 LONG IFDCloseIFD(PREADER_CONTEXT rContext)
00193 {
00194 RESPONSECODE rv = IFD_SUCCESS;
00195
00196 #ifndef PCSCLITE_STATIC_DRIVER
00197 RESPONSECODE(*IO_close_channel) () = NULL;
00198 RESPONSECODE(*IFDH_close_channel) (DWORD) = NULL;
00199
00200 if (rContext->dwVersion == IFD_HVERSION_1_0)
00201 IO_close_channel = rContext->psFunctions.psFunctions_v1.pvfCloseChannel;
00202 else
00203 IFDH_close_channel = rContext->psFunctions.psFunctions_v2.pvfCloseChannel;
00204 #endif
00205
00206
00207
00208
00209
00210 SYS_MutexLock(rContext->mMutex);
00211 #ifndef PCSCLITE_STATIC_DRIVER
00212 if (rContext->dwVersion == IFD_HVERSION_1_0)
00213
00214 rv = (*IO_close_channel) ();
00215 else
00216 rv = (*IFDH_close_channel) (rContext->dwSlot);
00217 #else
00218 if (rContext->dwVersion == IFD_HVERSION_1_0)
00219 rv = IO_Close_Channel();
00220 else
00221 rv = IFDHCloseChannel(rContext->dwSlot);
00222 #endif
00223 SYS_MutexUnLock(rContext->mMutex);
00224
00225
00226
00227
00228
00229 return rv;
00230 }
00231
00232
00233
00234
00235
00236
00237 LONG IFDSetCapabilities(PREADER_CONTEXT rContext, DWORD dwTag,
00238 DWORD dwLength, PUCHAR pucValue)
00239 {
00240 RESPONSECODE rv = IFD_SUCCESS;
00241
00242 #ifndef PCSCLITE_STATIC_DRIVER
00243 RESPONSECODE(*IFD_set_capabilities) (DWORD, PUCHAR) = NULL;
00244 RESPONSECODE(*IFDH_set_capabilities) (DWORD, DWORD, DWORD, PUCHAR) = NULL;
00245
00246 if (rContext->dwVersion == IFD_HVERSION_1_0)
00247 IFD_set_capabilities = rContext->psFunctions.psFunctions_v1.pvfSetCapabilities;
00248 else
00249 IFDH_set_capabilities = rContext->psFunctions.psFunctions_v2.pvfSetCapabilities;
00250 #endif
00251
00252
00253
00254
00255
00256
00257 #ifndef PCSCLITE_STATIC_DRIVER
00258 if (rContext->dwVersion == IFD_HVERSION_1_0)
00259 rv = (*IFD_set_capabilities) (dwTag, pucValue);
00260 else
00261 rv = (*IFDH_set_capabilities) (rContext->dwSlot, dwTag,
00262 dwLength, pucValue);
00263 #else
00264 if (rContext->dwVersion == IFD_HVERSION_1_0)
00265 rv = IFD_Set_Capabilities(dwTag, pucValue);
00266 else
00267 rv = IFDHSetCapabilities(rContext->dwSlot, dwTag, dwLength,
00268 pucValue);
00269 #endif
00270
00271 return rv;
00272 }
00273
00274
00275
00276
00277
00278
00279
00280 LONG IFDGetCapabilities(PREADER_CONTEXT rContext, DWORD dwTag,
00281 PDWORD pdwLength, PUCHAR pucValue)
00282 {
00283 RESPONSECODE rv = IFD_SUCCESS;
00284
00285 #ifndef PCSCLITE_STATIC_DRIVER
00286 RESPONSECODE(*IFD_get_capabilities) (DWORD, PUCHAR) = NULL;
00287 RESPONSECODE(*IFDH_get_capabilities) (DWORD, DWORD, PDWORD, PUCHAR) = NULL;
00288
00289 if (rContext->dwVersion == IFD_HVERSION_1_0)
00290 IFD_get_capabilities =
00291 rContext->psFunctions.psFunctions_v1.pvfGetCapabilities;
00292 else
00293 IFDH_get_capabilities =
00294 rContext->psFunctions.psFunctions_v2.pvfGetCapabilities;
00295 #endif
00296
00297
00298
00299
00300
00301 SYS_MutexLock(rContext->mMutex);
00302
00303 #ifndef PCSCLITE_STATIC_DRIVER
00304 if (rContext->dwVersion == IFD_HVERSION_1_0)
00305 rv = (*IFD_get_capabilities) (dwTag, pucValue);
00306 else
00307 rv = (*IFDH_get_capabilities) (rContext->dwSlot, dwTag,
00308 pdwLength, pucValue);
00309 #else
00310 if (rContext->dwVersion == IFD_HVERSION_1_0)
00311 rv = IFD_Get_Capabilities(dwTag, pucValue);
00312 else
00313 rv = IFDHGetCapabilities(rContext->dwSlot, dwTag, pdwLength,
00314 pucValue);
00315 #endif
00316
00317 SYS_MutexUnLock(rContext->mMutex);
00318
00319
00320
00321
00322
00323 return rv;
00324 }
00325
00326
00327
00328
00329
00330
00331 LONG IFDPowerICC(PREADER_CONTEXT rContext, DWORD dwAction,
00332 PUCHAR pucAtr, PDWORD pdwAtrLen)
00333 {
00334 RESPONSECODE rv;
00335 short ret;
00336 SMARTCARD_EXTENSION sSmartCard;
00337 DWORD dwStatus;
00338 UCHAR ucValue[1];
00339
00340 #ifndef PCSCLITE_STATIC_DRIVER
00341 RESPONSECODE(*IFD_power_icc) (DWORD) = NULL;
00342 RESPONSECODE(*IFDH_power_icc) (DWORD, DWORD, PUCHAR, PDWORD) = NULL;
00343 #endif
00344
00345
00346
00347
00348 rv = IFD_SUCCESS;
00349 dwStatus = 0;
00350 ucValue[0] = 0;
00351
00352
00353
00354
00355 IFDStatusICC(rContext, &dwStatus, pucAtr, pdwAtrLen);
00356
00357 if (dwStatus & SCARD_ABSENT)
00358 return SCARD_W_REMOVED_CARD;
00359 #ifndef PCSCLITE_STATIC_DRIVER
00360 if (rContext->dwVersion == IFD_HVERSION_1_0)
00361 IFD_power_icc = rContext->psFunctions.psFunctions_v1.pvfPowerICC;
00362 else
00363 IFDH_power_icc = rContext->psFunctions.psFunctions_v2.pvfPowerICC;
00364 #endif
00365
00366
00367
00368
00369
00370 SYS_MutexLock(rContext->mMutex);
00371
00372 #ifndef PCSCLITE_STATIC_DRIVER
00373 if (rContext->dwVersion == IFD_HVERSION_1_0)
00374 {
00375 ucValue[0] = rContext->dwSlot;
00376 IFDSetCapabilities(rContext, TAG_IFD_SLOTNUM, 1, ucValue);
00377 rv = (*IFD_power_icc) (dwAction);
00378 }
00379 else
00380 {
00381 rv = (*IFDH_power_icc) (rContext->dwSlot, dwAction,
00382 pucAtr, pdwAtrLen);
00383
00384 ret = ATRDecodeAtr(&sSmartCard, pucAtr, *pdwAtrLen);
00385 }
00386 #else
00387 if (rContext->dwVersion == IFD_HVERSION_1_0)
00388 {
00389 ucValue[0] = rContext->dwSlot;
00390 IFDSetCapabilities(rContext, TAG_IFD_SLOTNUM, 1, ucValue);
00391 rv = IFD_Power_ICC(dwAction);
00392 }
00393 else
00394 rv = IFDHPowerICC(rContext->dwSlot, dwAction, pucAtr, pdwAtrLen);
00395 #endif
00396 SYS_MutexUnLock(rContext->mMutex);
00397
00398
00399
00400
00401
00402
00403 if (rv != IFD_SUCCESS)
00404 {
00405 *pdwAtrLen = 0;
00406 pucAtr[0] = '\0';
00407
00408 if (rv == IFD_NO_SUCH_DEVICE)
00409 {
00410 SendHotplugSignal();
00411 return SCARD_E_READER_UNAVAILABLE;
00412 }
00413
00414 return SCARD_E_NOT_TRANSACTED;
00415 }
00416
00417
00418
00419
00420 if (rContext->dwVersion == IFD_HVERSION_1_0)
00421 IFDStatusICC(rContext, &dwStatus, pucAtr, pdwAtrLen);
00422
00423 return rv;
00424 }
00425
00426
00427
00428
00429
00430
00431
00432 LONG IFDStatusICC(PREADER_CONTEXT rContext, PDWORD pdwStatus,
00433 PUCHAR pucAtr, PDWORD pdwAtrLen)
00434 {
00435 RESPONSECODE rv = IFD_SUCCESS;
00436 DWORD dwTag = 0, dwCardStatus = 0;
00437 SMARTCARD_EXTENSION sSmartCard;
00438 UCHAR ucValue[1] = "\x00";
00439
00440 #ifndef PCSCLITE_STATIC_DRIVER
00441 RESPONSECODE(*IFD_is_icc_present) () = NULL;
00442 RESPONSECODE(*IFDH_icc_presence) (DWORD) = NULL;
00443 RESPONSECODE(*IFD_get_capabilities) (DWORD, PUCHAR) = NULL;
00444
00445 if (rContext->dwVersion == IFD_HVERSION_1_0)
00446 {
00447 IFD_is_icc_present =
00448 rContext->psFunctions.psFunctions_v1.pvfICCPresence;
00449 IFD_get_capabilities =
00450 rContext->psFunctions.psFunctions_v1.pvfGetCapabilities;
00451 }
00452 else
00453 IFDH_icc_presence = rContext->psFunctions.psFunctions_v2.pvfICCPresence;
00454 #endif
00455
00456
00457
00458
00459
00460 SYS_MutexLock(rContext->mMutex);
00461
00462 #ifndef PCSCLITE_STATIC_DRIVER
00463 if (rContext->dwVersion == IFD_HVERSION_1_0)
00464 {
00465 ucValue[0] = rContext->dwSlot;
00466 IFDSetCapabilities(rContext, TAG_IFD_SLOTNUM, 1, ucValue);
00467 rv = (*IFD_is_icc_present) ();
00468 }
00469 else
00470 rv = (*IFDH_icc_presence) (rContext->dwSlot);
00471 #else
00472 if (rContext->dwVersion == IFD_HVERSION_1_0)
00473 {
00474 ucValue[0] = rContext->dwSlot;
00475 IFDSetCapabilities(rContext, TAG_IFD_SLOTNUM, 1, ucValue);
00476 rv = IFD_Is_ICC_Present();
00477 }
00478 else
00479 rv = IFDHICCPresence(rContext->dwSlot);
00480 #endif
00481 SYS_MutexUnLock(rContext->mMutex);
00482
00483
00484
00485
00486
00487 if (rv == IFD_SUCCESS || rv == IFD_ICC_PRESENT)
00488 dwCardStatus |= SCARD_PRESENT;
00489 else
00490 if (rv == IFD_ICC_NOT_PRESENT)
00491 dwCardStatus |= SCARD_ABSENT;
00492 else
00493 {
00494 Log2(PCSC_LOG_ERROR, "Card not transacted: %ld", rv);
00495 *pdwStatus = SCARD_UNKNOWN;
00496
00497 if (rv == IFD_NO_SUCH_DEVICE)
00498 {
00499 SendHotplugSignal();
00500 return SCARD_E_READER_UNAVAILABLE;
00501 }
00502
00503 return SCARD_E_NOT_TRANSACTED;
00504 }
00505
00506
00507
00508
00509
00510
00511
00512 if (rContext->dwVersion == IFD_HVERSION_1_0)
00513 {
00514 if (rv == IFD_SUCCESS || rv == IFD_ICC_PRESENT)
00515 {
00516 short ret;
00517
00518 dwTag = TAG_IFD_ATR;
00519
00520
00521
00522
00523
00524 SYS_MutexLock(rContext->mMutex);
00525
00526 ucValue[0] = rContext->dwSlot;
00527 IFDSetCapabilities(rContext, TAG_IFD_SLOTNUM, 1, ucValue);
00528
00529 #ifndef PCSCLITE_STATIC_DRIVER
00530 rv = (*IFD_get_capabilities) (dwTag, pucAtr);
00531 #else
00532 rv = IFD_Get_Capabilities(dwTag, pucAtr);
00533 #endif
00534 SYS_MutexUnLock(rContext->mMutex);
00535
00536
00537
00538
00539
00540
00541
00542
00543
00544
00545 ret = ATRDecodeAtr(&sSmartCard, pucAtr, MAX_ATR_SIZE);
00546
00547
00548
00549
00550 if (ret == 0)
00551 *pdwAtrLen = 0;
00552 else
00553 *pdwAtrLen = sSmartCard.ATR.Length;
00554 }
00555 else
00556 {
00557
00558
00559
00560 *pdwAtrLen = 0;
00561 }
00562
00563
00564
00565 }
00566
00567 *pdwStatus = dwCardStatus;
00568
00569 return SCARD_S_SUCCESS;
00570 }
00571
00572
00573
00574
00575
00576
00577
00578
00579
00580
00581
00582 LONG IFDControl_v2(PREADER_CONTEXT rContext, PUCHAR TxBuffer,
00583 DWORD TxLength, PUCHAR RxBuffer, PDWORD RxLength)
00584 {
00585 RESPONSECODE rv = IFD_SUCCESS;
00586
00587 #ifndef PCSCLITE_STATIC_DRIVER
00588 RESPONSECODE(*IFDH_control_v2) (DWORD, PUCHAR, DWORD, PUCHAR, PDWORD);
00589 #endif
00590
00591 if (rContext->dwVersion != IFD_HVERSION_2_0)
00592 return SCARD_E_UNSUPPORTED_FEATURE;
00593
00594 #ifndef PCSCLITE_STATIC_DRIVER
00595 IFDH_control_v2 = rContext->psFunctions.psFunctions_v2.pvfControl;
00596 #endif
00597
00598
00599
00600
00601 SYS_MutexLock(rContext->mMutex);
00602
00603 #ifndef PCSCLITE_STATIC_DRIVER
00604 rv = (*IFDH_control_v2) (rContext->dwSlot, TxBuffer, TxLength,
00605 RxBuffer, RxLength);
00606 #else
00607 rv = IFDHControl_v2(rContext->dwSlot, TxBuffer, TxLength,
00608 RxBuffer, RxLength);
00609 #endif
00610 SYS_MutexUnLock(rContext->mMutex);
00611
00612
00613
00614
00615 if (rv == IFD_SUCCESS)
00616 return SCARD_S_SUCCESS;
00617 else
00618 {
00619 Log2(PCSC_LOG_ERROR, "Card not transacted: %ld", rv);
00620 return SCARD_E_NOT_TRANSACTED;
00621 }
00622 }
00623
00624
00625
00626
00627
00628
00629
00630
00631
00632
00633
00634 LONG IFDControl(PREADER_CONTEXT rContext, DWORD ControlCode,
00635 LPCVOID TxBuffer, DWORD TxLength, LPVOID RxBuffer, DWORD RxLength,
00636 LPDWORD BytesReturned)
00637 {
00638 RESPONSECODE rv = IFD_SUCCESS;
00639
00640 #ifndef PCSCLITE_STATIC_DRIVER
00641 RESPONSECODE(*IFDH_control) (DWORD, DWORD, LPCVOID, DWORD, LPVOID, DWORD, LPDWORD);
00642 #endif
00643
00644 if (rContext->dwVersion < IFD_HVERSION_3_0)
00645 return SCARD_E_UNSUPPORTED_FEATURE;
00646
00647 #ifndef PCSCLITE_STATIC_DRIVER
00648 IFDH_control = rContext->psFunctions.psFunctions_v3.pvfControl;
00649 #endif
00650
00651
00652
00653
00654
00655 SYS_MutexLock(rContext->mMutex);
00656
00657 #ifndef PCSCLITE_STATIC_DRIVER
00658 rv = (*IFDH_control) (rContext->dwSlot, ControlCode, TxBuffer,
00659 TxLength, RxBuffer, RxLength, BytesReturned);
00660 #else
00661 rv = IFDHControl(rContext->dwSlot, ControlCode, TxBuffer,
00662 TxLength, RxBuffer, RxLength, BytesReturned);
00663 #endif
00664 SYS_MutexUnLock(rContext->mMutex);
00665
00666
00667
00668
00669
00670 if (rv == IFD_SUCCESS)
00671 return SCARD_S_SUCCESS;
00672 else
00673 {
00674 Log2(PCSC_LOG_ERROR, "Card not transacted: %ld", rv);
00675
00676 if (rv == IFD_NO_SUCH_DEVICE)
00677 {
00678 SendHotplugSignal();
00679 return SCARD_E_READER_UNAVAILABLE;
00680 }
00681
00682 return SCARD_E_NOT_TRANSACTED;
00683 }
00684 }
00685
00686
00687
00688
00689
00690
00691 LONG IFDTransmit(PREADER_CONTEXT rContext, SCARD_IO_HEADER pioTxPci,
00692 PUCHAR pucTxBuffer, DWORD dwTxLength, PUCHAR pucRxBuffer,
00693 PDWORD pdwRxLength, PSCARD_IO_HEADER pioRxPci)
00694 {
00695 RESPONSECODE rv = IFD_SUCCESS;
00696 UCHAR ucValue[1] = "\x00";
00697
00698 #ifndef PCSCLITE_STATIC_DRIVER
00699 RESPONSECODE(*IFD_transmit_to_icc) (SCARD_IO_HEADER, PUCHAR, DWORD,
00700 PUCHAR, PDWORD, PSCARD_IO_HEADER) = NULL;
00701 RESPONSECODE(*IFDH_transmit_to_icc) (DWORD, SCARD_IO_HEADER, PUCHAR,
00702 DWORD, PUCHAR, PDWORD, PSCARD_IO_HEADER) = NULL;
00703 #endif
00704
00705
00706 DebugLogCategory(DEBUG_CATEGORY_APDU, pucTxBuffer, dwTxLength);
00707
00708 #ifndef PCSCLITE_STATIC_DRIVER
00709 if (rContext->dwVersion == IFD_HVERSION_1_0)
00710 IFD_transmit_to_icc =
00711 rContext->psFunctions.psFunctions_v1.pvfTransmitToICC;
00712 else
00713 IFDH_transmit_to_icc =
00714 rContext->psFunctions.psFunctions_v2.pvfTransmitToICC;
00715 #endif
00716
00717
00718
00719
00720
00721 SYS_MutexLock(rContext->mMutex);
00722
00723
00724 #ifndef PCSCLITE_STATIC_DRIVER
00725 if (rContext->dwVersion == IFD_HVERSION_1_0)
00726 {
00727 ucValue[0] = rContext->dwSlot;
00728 IFDSetCapabilities(rContext, TAG_IFD_SLOTNUM, 1, ucValue);
00729 rv = (*IFD_transmit_to_icc) (pioTxPci, (LPBYTE) pucTxBuffer,
00730 dwTxLength, pucRxBuffer, pdwRxLength, pioRxPci);
00731 }
00732 else
00733 rv = (*IFDH_transmit_to_icc) (rContext->dwSlot, pioTxPci,
00734 (LPBYTE) pucTxBuffer, dwTxLength,
00735 pucRxBuffer, pdwRxLength, pioRxPci);
00736 #else
00737 if (rContext->dwVersion == IFD_HVERSION_1_0)
00738 {
00739 ucValue[0] = rContext->dwSlot;
00740 IFDSetCapabilities(rContext, TAG_IFD_SLOTNUM, 1, ucValue);
00741 rv = IFD_Transmit_to_ICC(pioTxPci, (LPBYTE) pucTxBuffer,
00742 dwTxLength, pucRxBuffer, pdwRxLength, pioRxPci);
00743 }
00744 else
00745 rv = IFDHTransmitToICC(rContext->dwSlot, pioTxPci,
00746 (LPBYTE) pucTxBuffer, dwTxLength,
00747 pucRxBuffer, pdwRxLength, pioRxPci);
00748 #endif
00749 SYS_MutexUnLock(rContext->mMutex);
00750
00751
00752
00753
00754
00755
00756 DebugLogCategory(DEBUG_CATEGORY_SW, pucRxBuffer, *pdwRxLength);
00757
00758 if (rv == IFD_SUCCESS)
00759 return SCARD_S_SUCCESS;
00760 else
00761 {
00762 Log2(PCSC_LOG_ERROR, "Card not transacted: %ld", rv);
00763
00764 if (rv == IFD_NO_SUCH_DEVICE)
00765 {
00766 SendHotplugSignal();
00767 return SCARD_E_READER_UNAVAILABLE;
00768 }
00769
00770 return SCARD_E_NOT_TRANSACTED;
00771 }
00772 }
00773