00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019 #ifdef WITH_PKCS
00020 #define _TDECRYPTOGRAPHICCARDDEVICE_INTERNAL 1
00021 #endif
00022
00023 #include "tdecryptographiccarddevice_private.h"
00024 #include "tdecryptographiccarddevice.h"
00025
00026 #include <tqpixmap.h>
00027 #include <tqtimer.h>
00028 #include <ntqthread.h>
00029 #include <ntqeventloop.h>
00030 #include <ntqapplication.h>
00031
00032 #include "tdeglobal.h"
00033 #include "tdelocale.h"
00034 #include "tdeapplication.h"
00035
00036 #include "tdehardwaredevices.h"
00037
00038 #include "config.h"
00039
00040
00041 #define PCSC_POLL_TIMEOUT_S 1000
00042
00043 #define CARD_MAX_LOGIN_RETRY_COUNT 3
00044
00045
00046
00047
00048 #ifdef WITH_PCSC
00049 static TQString pcsc_error_code_to_string(long errcode) {
00050 if (errcode == SCARD_W_UNPOWERED_CARD) {
00051 return i18n("card not powered on");
00052 }
00053 else if (errcode == SCARD_E_PROTO_MISMATCH) {
00054 return i18n("protocol mismatch");
00055 }
00056 else {
00057 return TQString::null;
00058 }
00059 }
00060 #endif
00061
00062 CryptoCardDeviceWatcher::CryptoCardDeviceWatcher() {
00063 #ifdef WITH_PCSC
00064 m_readerStates = NULL;
00065 #endif
00066 m_cardPINPromptDone = true;
00067 m_pinCallbacksEnabled = false;
00068 m_cardReusePIN = false;
00069 }
00070
00071 CryptoCardDeviceWatcher::~CryptoCardDeviceWatcher() {
00072 #ifdef WITH_PCSC
00073 free(m_readerStates);
00074 #endif
00075 }
00076
00077 void CryptoCardDeviceWatcher::run() {
00078 #ifdef WITH_PCSC
00079 bool first_loop;
00080 unsigned int i;
00081 long ret;
00082
00083 DWORD dword_readers;
00084 LPSTR lpstring_readers = NULL;
00085
00086 TQStringList readers;
00087
00088 first_loop = true;
00089 m_terminationRequested = false;
00090
00091 TQEventLoop* eventLoop = TQApplication::eventLoop();
00092 if (!eventLoop) return;
00093
00094 ret = SCardEstablishContext(SCARD_SCOPE_SYSTEM, NULL, NULL, &m_cardContext);
00095 if (ret != SCARD_S_SUCCESS) {
00096 printf("TDECryptographicCardDevice: PCSC SCardEstablishContext cannot connect to resource manager (%lX)", ret);
00097 eventLoop->exit(0);
00098 return;
00099 }
00100
00101 ret = SCardListReaders(m_cardContext, NULL, NULL, &dword_readers);
00102 if (ret == SCARD_S_SUCCESS) {
00103 lpstring_readers = (LPSTR)malloc(sizeof(char)*dword_readers);
00104 if (lpstring_readers == NULL) {
00105 printf("TDECryptographicCardDevice: insufficient memory, aborting");
00106 eventLoop->exit(0);
00107 return;
00108 }
00109
00110 ret = SCardListReaders(m_cardContext, NULL, lpstring_readers, &dword_readers);
00111 if (ret == SCARD_S_SUCCESS) {
00112
00113 char *ptr = lpstring_readers;
00114 while (*ptr != '\0') {
00115 readers.append(ptr);
00116 ptr += strlen(ptr)+1;
00117 }
00118
00119 free(lpstring_readers);
00120
00121 m_readerStates = (SCARD_READERSTATE*)calloc(readers.count(), sizeof(*m_readerStates));
00122 if (m_readerStates == NULL) {
00123 printf("TDECryptographicCardDevice: insufficient memory, aborting");
00124 free(lpstring_readers);
00125 eventLoop->exit(0);
00126 return;
00127 }
00128
00129 for (i=0; i<readers.count(); i++) {
00130 m_readerStates[i].szReader = strdup(readers[i].ascii());
00131 m_readerStates[i].dwCurrentState = SCARD_STATE_UNAWARE;
00132 }
00133
00134 ret = SCardGetStatusChange(m_cardContext, PCSC_POLL_TIMEOUT_S, m_readerStates, readers.count());
00135 while ((ret == SCARD_S_SUCCESS) || (ret == SCARD_E_TIMEOUT)) {
00136 if (m_terminationRequested) {
00137 for (i=0; i<readers.count(); i++) {
00138 free((char*)m_readerStates[i].szReader);
00139 m_readerStates[i].szReader = NULL;
00140 }
00141 eventLoop->exit(0);
00142 return;
00143 }
00144
00145 for (i=0; i<readers.count(); i++) {
00146
00147
00148
00149 SCARDHANDLE hCard = 0;
00150 DWORD dwActiveProtocol = 0;
00151 DWORD cByte = 0;
00152 TQString reader_vendor_name;
00153 TQString reader_interface_type;
00154
00155 ret = SCardConnect(m_cardContext, readers[i].ascii(), SCARD_SHARE_DIRECT, SCARD_PROTOCOL_T0 | SCARD_PROTOCOL_T1, &hCard, &dwActiveProtocol);
00156 if (ret == SCARD_S_SUCCESS) {
00157 ret = SCardGetAttrib(hCard, SCARD_ATTR_VENDOR_NAME, NULL, &cByte);
00158 if (ret == SCARD_S_SUCCESS) {
00159 char* data = new char[cByte];
00160 ret = SCardGetAttrib(hCard, SCARD_ATTR_VENDOR_NAME, (LPBYTE)data, &cByte);
00161 reader_vendor_name = data;
00162 delete [] data;
00163 }
00164 ret = SCardGetAttrib(hCard, SCARD_ATTR_VENDOR_IFD_TYPE, NULL, &cByte);
00165 if (ret == SCARD_S_SUCCESS) {
00166 char* data = new char[cByte];
00167 ret = SCardGetAttrib(hCard, SCARD_ATTR_VENDOR_IFD_TYPE, (LPBYTE)data, &cByte);
00168 reader_interface_type = data;
00169 delete [] data;
00170 }
00171 SCardDisconnect(hCard, SCARD_LEAVE_CARD);
00172 }
00173
00174
00175
00176
00177
00178
00179 if (readers.count() > 1) {
00180 if (!readers[i].contains(cardDevice->friendlyName())) {
00181 if (!cardDevice->friendlyName().contains(reader_vendor_name) ||
00182 ((reader_interface_type != "") && !cardDevice->friendlyName().contains(reader_vendor_name))) {
00183 continue;
00184 }
00185 }
00186 }
00187
00188 if (first_loop) {
00189 if (m_readerStates[i].dwEventState & SCARD_STATE_PRESENT) {
00190
00191 TQString atr = getCardATR(readers[i]);
00192 retrieveCardCertificates(readers[i]);
00193 statusChanged("PRESENT", atr);
00194 }
00195 else {
00196 deleteAllCertificatesFromCache();
00197 }
00198 first_loop = false;
00199 }
00200 if (m_readerStates[i].dwEventState & SCARD_STATE_CHANGED) {
00201 if ((m_readerStates[i].dwCurrentState & SCARD_STATE_PRESENT)
00202 && (m_readerStates[i].dwEventState & SCARD_STATE_EMPTY)) {
00203 deleteAllCertificatesFromCache();
00204 statusChanged("REMOVED", TQString::null);
00205 }
00206 else if ((m_readerStates[i].dwCurrentState & SCARD_STATE_EMPTY)
00207 && (m_readerStates[i].dwEventState & SCARD_STATE_PRESENT)) {
00208
00209 TQString atr = getCardATR(readers[i]);
00210 retrieveCardCertificates(readers[i]);
00211 statusChanged("INSERTED", atr);
00212 }
00213 m_readerStates[i].dwCurrentState = m_readerStates[i].dwEventState;
00214 }
00215 else {
00216 continue;
00217 }
00218 }
00219 ret = SCardGetStatusChange(m_cardContext, PCSC_POLL_TIMEOUT_S, m_readerStates, readers.count());
00220 }
00221 }
00222 }
00223
00224 eventLoop->exit(0);
00225 #endif
00226 }
00227
00228 void CryptoCardDeviceWatcher::requestTermination() {
00229 m_terminationRequested = true;
00230 }
00231
00232 void CryptoCardDeviceWatcher::setProvidedPin(TQString pin) {
00233 m_cardPIN = pin;
00234 m_cardPINPromptDone = true;
00235 }
00236
00237 void CryptoCardDeviceWatcher::retrySamePin(bool enable) {
00238 m_cardReusePIN = enable;
00239 if (!enable) {
00240 m_cardPIN = "SHREDDINGTHEPINISMOSTSECURE";
00241 m_cardPIN = TQString::null;
00242 }
00243 }
00244
00245 TQString CryptoCardDeviceWatcher::getCardATR(TQString readerName) {
00246 #ifdef WITH_PCSC
00247 unsigned int i;
00248 long ret;
00249 TQString atr_formatted;
00250 SCARDHANDLE hCard = 0;
00251 DWORD dwActiveProtocol = 0;
00252 DWORD cByte = 0;
00253
00254 ret = SCardConnect(m_cardContext, readerName.ascii(), SCARD_SHARE_SHARED, SCARD_PROTOCOL_T0 | SCARD_PROTOCOL_T1, &hCard, &dwActiveProtocol);
00255 if (ret == SCARD_S_SUCCESS) {
00256 ret = SCardGetAttrib(hCard, SCARD_ATTR_ATR_STRING, NULL, &cByte);
00257 if (ret == SCARD_S_SUCCESS) {
00258 char* data = new char[cByte];
00259 ret = SCardGetAttrib(hCard, SCARD_ATTR_ATR_STRING, (LPBYTE)data, &cByte);
00260 atr_formatted = TQString::null;
00261 for (i=0; i<cByte; i++) {
00262 TQString formatted;
00263 formatted.sprintf("%02x ", ((uint8_t)(*(data+i))));
00264 atr_formatted.append(formatted.upper());
00265 }
00266 atr_formatted = atr_formatted.stripWhiteSpace();
00267 delete [] data;
00268 SCardDisconnect(hCard, SCARD_LEAVE_CARD);
00269 }
00270 }
00271 else {
00272 TQString errstring = pcsc_error_code_to_string(ret);
00273 if (errstring != "") {
00274 atr_formatted = i18n("Unknown (%1)").arg(errstring);
00275 }
00276 else {
00277 atr_formatted = TQString("CARD_CONNECT_FAIL (%1)").arg(ret, 0, 16);
00278 }
00279 }
00280
00281 return atr_formatted;
00282 #else
00283 return TQString::null;
00284 #endif
00285 }
00286
00287 void CryptoCardDeviceWatcher::enablePINEntryCallbacks(bool enable) {
00288 m_pinCallbacksEnabled = enable;
00289 }
00290
00291 TQString CryptoCardDeviceWatcher::doPinRequest(TQString prompt) {
00292 if (!m_pinCallbacksEnabled) {
00293 return TQString::null;
00294 }
00295
00296 if (m_cardReusePIN) {
00297 return m_cardPIN;
00298 }
00299
00300 m_cardPINPromptDone = false;
00301 emit(pinRequested(prompt));
00302 while (!m_cardPINPromptDone) {
00303 usleep(100);
00304 }
00305
00306 if (m_cardPIN.length() > 0) {
00307 return m_cardPIN;
00308 }
00309 else {
00310 return TQString::null;
00311 }
00312 }
00313
00314 #ifdef WITH_PKCS
00315 static void pkcs_log_hook(IN void * const global_data, IN unsigned flags, IN const char * const format, IN va_list args) {
00316 vprintf(format, args);
00317 printf("\n");
00318 }
00319
00320 static PKCS11H_BOOL pkcs_pin_hook(IN void * const global_data, IN void * const user_data, IN const pkcs11h_token_id_t token, IN const unsigned retry, OUT char * const pin, IN const size_t pin_max) {
00321 CryptoCardDeviceWatcher* watcher = (CryptoCardDeviceWatcher*)global_data;
00322
00323 TQString providedPin = watcher->doPinRequest(i18n("Please enter the PIN for '%1'").arg(token->display));
00324 if (providedPin.length() > 0) {
00325 snprintf(pin, pin_max, "%s", providedPin.ascii());
00326
00327
00328 return 1;
00329 }
00330 else {
00331
00332 return 0;
00333 }
00334 }
00335 #endif
00336
00337 int CryptoCardDeviceWatcher::initializePkcs() {
00338 #if defined(WITH_PKCS)
00339 CK_RV rv;
00340 printf("Initializing pkcs11-helper\n");
00341 if ((rv = pkcs11h_initialize()) != CKR_OK) {
00342 printf("pkcs11h_initialize failed: %s\n", pkcs11h_getMessage(rv));
00343 return -1;
00344 }
00345
00346 printf("Registering pkcs11-helper hooks\n");
00347 if ((rv = pkcs11h_setLogHook(pkcs_log_hook, this)) != CKR_OK) {
00348 printf("pkcs11h_setLogHook failed: %s\n", pkcs11h_getMessage(rv));
00349 return -1;
00350 }
00351 pkcs11h_setLogLevel(PKCS11H_LOG_WARN);
00352
00353
00354 #if 0
00355 if ((rv = pkcs11h_setTokenPromptHook(_pkcs11h_hooks_token_prompt, NULL)) != CKR_OK) {
00356 printf("pkcs11h_setTokenPromptHook failed: %s\n", pkcs11h_getMessage(rv));
00357 return -1;
00358 }
00359 #endif
00360
00361 if ((rv = pkcs11h_setMaxLoginRetries(CARD_MAX_LOGIN_RETRY_COUNT)) != CKR_OK) {
00362 printf("pkcs11h_setMaxLoginRetries failed: %s\n", pkcs11h_getMessage(rv));
00363 return -1;
00364 }
00365
00366 if ((rv = pkcs11h_setPINPromptHook(pkcs_pin_hook, this)) != CKR_OK) {
00367 printf("pkcs11h_setPINPromptHook failed: %s\n", pkcs11h_getMessage(rv));
00368 return -1;
00369 }
00370
00371 printf("Adding provider '%s'\n", OPENSC_PKCS11_PROVIDER_LIBRARY);
00372 if ((rv = pkcs11h_addProvider(OPENSC_PKCS11_PROVIDER_LIBRARY, OPENSC_PKCS11_PROVIDER_LIBRARY, FALSE, PKCS11H_PRIVATEMODE_MASK_AUTO, PKCS11H_SLOTEVENT_METHOD_AUTO, 0, FALSE)) != CKR_OK) {
00373 printf("pkcs11h_addProvider failed: %s\n", pkcs11h_getMessage(rv));
00374 return -1;
00375 }
00376
00377 return 0;
00378 #else
00379 return -1;
00380 #endif
00381 }
00382
00383 int CryptoCardDeviceWatcher::retrieveCardCertificates(TQString readerName) {
00384 #if defined(WITH_PKCS)
00385 int ret = -1;
00386
00387 CK_RV rv;
00388 pkcs11h_certificate_id_list_t issuers;
00389 pkcs11h_certificate_id_list_t certs;
00390
00391 if (initializePkcs() < 0) {
00392 printf("Unable to initialize PKCS\n");
00393 return -1;
00394 }
00395
00396 rv = pkcs11h_certificate_enumCertificateIds(PKCS11H_ENUM_METHOD_CACHE, NULL, PKCS11H_PROMPT_MASK_ALLOW_PIN_PROMPT, &issuers, &certs);
00397 if ((rv != CKR_OK) || (certs == NULL)) {
00398 printf("Cannot enumerate certificates: %s\n", pkcs11h_getMessage(rv));
00399 return -1;
00400 }
00401 printf("Successfully enumerated certificates\n");
00402
00403 int i = 0;
00404 for (pkcs11h_certificate_id_list_t cert = certs; cert != NULL; cert = cert->next) {
00405 TQString label = cert->certificate_id->displayName;
00406 printf("Certificate %d name: '%s'\n", i, label.ascii());
00407
00408 pkcs11h_certificate_t certificate;
00409 rv = pkcs11h_certificate_create(certs->certificate_id, NULL, PKCS11H_PROMPT_MASK_ALLOW_PIN_PROMPT, PKCS11H_PIN_CACHE_INFINITE, &certificate);
00410 if (rv != CKR_OK) {
00411 printf("Cannot read certificate: %s\n", pkcs11h_getMessage(rv));
00412 pkcs11h_certificate_freeCertificateId(certs->certificate_id);
00413 ret = -1;
00414 break;
00415 }
00416
00417 pkcs11h_certificate_freeCertificateId(certs->certificate_id);
00418
00419 pkcs11h_openssl_session_t openssl_session = NULL;
00420 if ((openssl_session = pkcs11h_openssl_createSession(certificate)) == NULL) {
00421 printf("Cannot initialize openssl session to retrieve cryptographic objects\n");
00422 pkcs11h_certificate_freeCertificate(certificate);
00423 ret = -1;
00424 break;
00425 }
00426 certificate = NULL;
00427
00428 X509* x509_local;
00429 x509_local = pkcs11h_openssl_session_getX509(openssl_session);
00430 if (x509_local) {
00431 printf("Successfully retrieved X509 certificate\n");
00432 }
00433 else {
00434 printf("Cannot get X509 object\n");
00435 ret = -1;
00436 }
00437 #if 0
00438 RSA* rsa_local;
00439 rsa_local = pkcs11h_openssl_session_getRSA(openssl_session);
00440 if (rsa_local) {
00441 printf("Successfully retrieved RSA public key\n");
00442 }
00443 else {
00444 printf("Cannot get RSA object\n");
00445 ret = -1;
00446 }
00447 #endif
00448
00449 X509* x509_copy = X509_dup(x509_local);
00450 if (x509_copy) {
00451 cardDevice->m_cardCertificates.append(x509_copy);
00452 }
00453 else {
00454 printf("Unable to copy X509 certificate\n");
00455 }
00456
00457 pkcs11h_openssl_freeSession(openssl_session);
00458 i++;
00459 }
00460
00461 pkcs11h_certificate_freeCertificateIdList(issuers);
00462
00463 return ret;
00464 #else
00465 return -1;
00466 #endif
00467 }
00468
00469 void CryptoCardDeviceWatcher::deleteAllCertificatesFromCache() {
00470 #ifdef WITH_PKCS
00471 X509 *x509_cert;
00472
00473 X509CertificatePtrListIterator it;
00474 for (it = cardDevice->m_cardCertificates.begin(); it != cardDevice->m_cardCertificates.end(); ++it) {
00475 x509_cert = *it;
00476 X509_free(x509_cert);
00477 }
00478
00479 cardDevice->m_cardCertificates.clear();
00480 #endif
00481 }
00482
00483 TDECryptographicCardDevice::TDECryptographicCardDevice(TDEGenericDeviceType::TDEGenericDeviceType dt, TQString dn) : TDEGenericDevice(dt, dn),
00484 m_watcherThread(NULL),
00485 m_watcherObject(NULL),
00486 m_cardPresent(false) {
00487 }
00488
00489 TDECryptographicCardDevice::~TDECryptographicCardDevice() {
00490 enableCardMonitoring(false);
00491 }
00492
00493 void TDECryptographicCardDevice::enableCardMonitoring(bool enable) {
00494 #ifdef WITH_PCSC
00495 if (enable) {
00496 if (m_watcherObject && m_watcherThread) {
00497
00498 if ((cardPresent() == 1) && (cardX509Certificates().count() > 0)) {
00499
00500 emit(certificateListAvailable(this));
00501 }
00502
00503
00504 return;
00505 }
00506
00507 m_watcherThread = new TQEventLoopThread();
00508 m_watcherObject = new CryptoCardDeviceWatcher();
00509
00510 m_watcherObject->cardDevice = this;
00511 m_watcherObject->moveToThread(m_watcherThread);
00512 TQObject::connect(m_watcherObject, SIGNAL(statusChanged(TQString,TQString)), this, SLOT(cardStatusChanged(TQString,TQString)));
00513 TQObject::connect(m_watcherObject, SIGNAL(pinRequested(TQString)), this, SLOT(workerRequestedPin(TQString)));
00514 TQTimer::singleShot(0, m_watcherObject, SLOT(run()));
00515
00516 m_watcherThread->start();
00517 }
00518 else {
00519 if (m_watcherObject) {
00520 m_watcherObject->requestTermination();
00521 }
00522 if (m_watcherThread) {
00523 m_watcherThread->wait();
00524 delete m_watcherThread;
00525 m_watcherThread = NULL;
00526 }
00527 if (m_watcherObject) {
00528 delete m_watcherObject;
00529 m_watcherObject = NULL;
00530 }
00531 }
00532 #endif
00533 }
00534
00535 void TDECryptographicCardDevice::enablePINEntryCallbacks(bool enable) {
00536 if (m_watcherObject) {
00537 m_watcherObject->enablePINEntryCallbacks(enable);
00538 }
00539 }
00540
00541 int TDECryptographicCardDevice::cardPresent() {
00542 if (m_watcherObject && m_watcherThread) {
00543 if (m_cardPresent)
00544 return 1;
00545 else
00546 return 0;
00547 }
00548 else {
00549 return -1;
00550 }
00551 }
00552
00553 TQString TDECryptographicCardDevice::cardATR() {
00554 if (m_watcherObject && m_watcherThread) {
00555 if (m_cardPresent)
00556 return m_cardATR;
00557 else
00558 return TQString::null;
00559 }
00560 else {
00561 return TQString::null;
00562 }
00563 }
00564
00565 X509CertificatePtrList TDECryptographicCardDevice::cardX509Certificates() {
00566 if (m_watcherObject && m_watcherThread) {
00567 if (m_cardPresent) {
00568 return m_cardCertificates;
00569 }
00570 else {
00571 return X509CertificatePtrList();
00572 }
00573 }
00574 else {
00575 return X509CertificatePtrList();
00576 }
00577 }
00578
00579 void TDECryptographicCardDevice::cardStatusChanged(TQString status, TQString atr) {
00580 if (status == "INSERTED") {
00581 m_cardPresent = true;
00582 m_cardATR = atr;
00583 emit(cardInserted(this));
00584 if (m_cardCertificates.count() > 0) {
00585 emit(certificateListAvailable(this));
00586 }
00587 }
00588 else if (status == "REMOVED") {
00589 m_cardPresent = false;
00590 m_cardATR = atr;
00591 emit(cardRemoved(this));
00592 }
00593 else if (status == "PRESENT") {
00594 m_cardATR = atr;
00595 m_cardPresent = true;
00596 if (m_cardCertificates.count() > 0) {
00597 emit(certificateListAvailable(this));
00598 }
00599 }
00600 }
00601
00602 void TDECryptographicCardDevice::setProvidedPin(TQString pin) {
00603 if (m_watcherObject) {
00604 m_watcherObject->setProvidedPin(pin);
00605 }
00606 }
00607
00608 TQString TDECryptographicCardDevice::autoPIN() {
00609 #if defined(WITH_PKCS)
00610 TQString retString = TQString::null;
00611
00612
00613
00614
00615
00616
00617
00618
00619
00620
00621
00622 ASN1_OBJECT* tde_autopin_data_object = OBJ_txt2obj("1.3.6.1.4.1.40364.1.2.1", 0);
00623
00624 int i;
00625 X509CertificatePtrListIterator it;
00626 for (it = m_cardCertificates.begin(); it != m_cardCertificates.end(); ++it) {
00627 X509* x509_cert = *it;
00628 GENERAL_NAMES* subjectAltNames = (GENERAL_NAMES*)X509_get_ext_d2i(x509_cert, NID_subject_alt_name, NULL, NULL);
00629 int altNameCount = sk_GENERAL_NAME_num(subjectAltNames);
00630 for (i=0; i < altNameCount; i++) {
00631 GENERAL_NAME* generalName = sk_GENERAL_NAME_value(subjectAltNames, i);
00632 if (generalName->type == GEN_OTHERNAME) {
00633 OTHERNAME* otherName = generalName->d.otherName;
00634 if (!OBJ_cmp(otherName->type_id, tde_autopin_data_object)) {
00635 ASN1_TYPE* asnValue = otherName->value;
00636 if (asnValue) {
00637
00638 int index;
00639 ASN1_TYPE* asnSeqValue = NULL;
00640 ASN1_GENERALSTRING* asnGeneralString = NULL;
00641 STACK_OF(ASN1_TYPE) *asnSeqValueStack = NULL;
00642 long asn1SeqValueObjectLength;
00643 int asn1SeqValueObjectTag;
00644 int asn1SeqValueObjectClass;
00645 int returnCode;
00646
00647 index = 0;
00648 asnSeqValueStack = ASN1_seq_unpack_ASN1_TYPE(ASN1_STRING_data(asnValue->value.sequence), ASN1_STRING_length(asnValue->value.sequence), d2i_ASN1_TYPE, ASN1_TYPE_free);
00649 asnSeqValue = sk_ASN1_TYPE_value(asnSeqValueStack, index);
00650 if (asnSeqValue) {
00651 if (asnSeqValue->value.octet_string->data[0] == ((V_ASN1_CONSTRUCTED | V_ASN1_CONTEXT_SPECIFIC) + index)) {
00652 const unsigned char* asn1SeqValueObjectData = asnSeqValue->value.sequence->data;
00653 returnCode = ASN1_get_object(&asn1SeqValueObjectData, &asn1SeqValueObjectLength, &asn1SeqValueObjectTag, &asn1SeqValueObjectClass, asnSeqValue->value.sequence->length);
00654 if (!(returnCode & 0x80)) {
00655 if (returnCode == (V_ASN1_CONSTRUCTED + index)) {
00656 if (d2i_ASN1_GENERALSTRING(&asnGeneralString, &asn1SeqValueObjectData, asn1SeqValueObjectLength) != NULL) {
00657 retString = TQString((const char *)ASN1_STRING_data(asnGeneralString));
00658 }
00659 }
00660 }
00661 }
00662 }
00663 }
00664 }
00665 }
00666 }
00667 }
00668
00669
00670 OBJ_cleanup();
00671
00672 return retString;
00673 #else
00674 return TQString::null;
00675 #endif
00676 }
00677
00678 void TDECryptographicCardDevice::workerRequestedPin(TQString prompt) {
00679 emit(pinRequested(prompt, this));
00680 }
00681
00682 int TDECryptographicCardDevice::decryptDataEncryptedWithCertPublicKey(TQByteArray &ciphertext, TQByteArray &plaintext, TQString *errstr) {
00683 TQValueList<TQByteArray> cipherTextList;
00684 TQValueList<TQByteArray> plainTextList;
00685 TQValueList<int> retCodeList;
00686
00687 cipherTextList.append(ciphertext);
00688
00689 this->decryptDataEncryptedWithCertPublicKey(cipherTextList, plainTextList, retCodeList, errstr);
00690
00691 plaintext = plainTextList[0];
00692 return retCodeList[0];
00693 }
00694
00695 int TDECryptographicCardDevice::decryptDataEncryptedWithCertPublicKey(TQValueList<TQByteArray> &cipherTextList, TQValueList<TQByteArray> &plainTextList, TQValueList<int> &retcodes, TQString *errstr) {
00696 #if defined(WITH_PKCS)
00697 int ret = -1;
00698
00699 if (!m_watcherObject) {
00700 if (errstr) *errstr = i18n("Card watcher object not available");
00701 return -1;
00702 }
00703
00704 CK_RV rv;
00705 pkcs11h_certificate_id_list_t issuers;
00706 pkcs11h_certificate_id_list_t certs;
00707
00708 if (m_watcherObject->initializePkcs() < 0) {
00709 if (errstr) *errstr = i18n("Unable to initialize PKCS");
00710 return -1;
00711 }
00712
00713 rv = pkcs11h_certificate_enumCertificateIds(PKCS11H_ENUM_METHOD_CACHE, NULL, PKCS11H_PROMPT_MASK_ALLOW_PIN_PROMPT, &issuers, &certs);
00714 if ((rv != CKR_OK) || (certs == NULL)) {
00715 if (errstr) *errstr = i18n("Cannot enumerate certificates: %1").arg(pkcs11h_getMessage(rv));
00716 return -1;
00717 }
00718
00719 int i = 0;
00720 for (pkcs11h_certificate_id_list_t cert = certs; cert != NULL; cert = cert->next) {
00721 TQString label = cert->certificate_id->displayName;
00722
00723 pkcs11h_certificate_t certificate;
00724 rv = pkcs11h_certificate_create(certs->certificate_id, NULL, PKCS11H_PROMPT_MASK_ALLOW_PIN_PROMPT, PKCS11H_PIN_CACHE_INFINITE, &certificate);
00725 if (rv != CKR_OK) {
00726 if (errstr) *errstr = i18n("Cannot read certificate: %1").arg(pkcs11h_getMessage(rv));
00727 pkcs11h_certificate_freeCertificateId(certs->certificate_id);
00728 ret = -1;
00729 break;
00730 }
00731
00732 pkcs11h_certificate_freeCertificateId(certs->certificate_id);
00733
00734 pkcs11h_openssl_session_t openssl_session = NULL;
00735 if ((openssl_session = pkcs11h_openssl_createSession(certificate)) == NULL) {
00736 if (errstr) *errstr = i18n("Cannot initialize openssl session to retrieve cryptographic objects");
00737 pkcs11h_certificate_freeCertificate(certificate);
00738 ret = -1;
00739 break;
00740 }
00741
00742
00743 X509* x509_local;
00744 x509_local = pkcs11h_openssl_session_getX509(openssl_session);
00745 if (!x509_local) {
00746 if (errstr) *errstr = i18n("Cannot get X509 object");
00747 ret = -1;
00748 }
00749
00750
00751 EVP_PKEY* x509_pubkey = NULL;
00752 RSA* rsa_pubkey = NULL;
00753 x509_pubkey = X509_get_pubkey(x509_local);
00754 if (x509_pubkey) {
00755 rsa_pubkey = EVP_PKEY_get1_RSA(x509_pubkey);
00756 }
00757
00758
00759 rv = pkcs11h_certificate_ensureKeyAccess(certificate);
00760 if (rv != CKR_OK) {
00761 if (rv == CKR_CANCEL) {
00762 ret = -3;
00763 break;
00764 }
00765 else if ((rv == CKR_PIN_INCORRECT) || (rv == CKR_USER_NOT_LOGGED_IN)) {
00766 ret = -2;
00767 break;
00768 }
00769 else {
00770 ret = -2;
00771 break;
00772 }
00773 }
00774
00775
00776 m_watcherObject->retrySamePin(true);
00777
00778 TQValueList<TQByteArray>::iterator it;
00779 TQValueList<TQByteArray>::iterator it2;
00780 TQValueList<int>::iterator it3;
00781 plainTextList.clear();
00782 retcodes.clear();
00783 for (it = cipherTextList.begin(); it != cipherTextList.end(); ++it) {
00784 plainTextList.append(TQByteArray());
00785 retcodes.append(-1);
00786 }
00787 for (it = cipherTextList.begin(), it2 = plainTextList.begin(), it3 = retcodes.begin(); it != cipherTextList.end(); ++it, ++it2, ++it3) {
00788 TQByteArray& ciphertext = *it;
00789 TQByteArray& plaintext = *it2;
00790 int& retcode = *it3;
00791
00792
00793 if (ciphertext.size() < 16) {
00794 if (errstr) *errstr = i18n("Cannot decrypt: %1").arg(i18n("Ciphertext too small"));
00795 ret = -2;
00796 retcode = -2;
00797 continue;
00798 }
00799
00800
00801 if (rsa_pubkey) {
00802 unsigned int rsa_length = RSA_size(rsa_pubkey);
00803 if (ciphertext.size() > rsa_length) {
00804 if (errstr) *errstr = i18n("Cannot decrypt: %1").arg(i18n("Ciphertext too large"));
00805 ret = -2;
00806 retcode = -2;
00807 continue;
00808 }
00809 }
00810
00811 size_t size = 0;
00812
00813 rv = pkcs11h_certificate_decryptAny(certificate, CKM_RSA_PKCS, (unsigned char*)ciphertext.data(), ciphertext.size(), NULL, &size);
00814 if (rv != CKR_OK) {
00815 if (errstr) *errstr = i18n("Cannot determine decrypted message length: %1 (%2)").arg(pkcs11h_getMessage(rv)).arg(rv);
00816 if (rv == CKR_CANCEL) {
00817 ret = -3;
00818 retcode = -3;
00819 break;
00820 }
00821 else if ((rv == CKR_PIN_INCORRECT) || (rv == CKR_USER_NOT_LOGGED_IN)) {
00822 ret = -2;
00823 retcode = -2;
00824 break;
00825 }
00826 else {
00827 ret = -2;
00828 retcode = -2;
00829 }
00830 }
00831 else {
00832
00833 plaintext.resize(size);
00834 rv = pkcs11h_certificate_decryptAny(certificate, CKM_RSA_PKCS, (unsigned char*)ciphertext.data(), ciphertext.size(), (unsigned char*)plaintext.data(), &size);
00835 if (rv != CKR_OK) {
00836 if (errstr) *errstr = i18n("Cannot decrypt: %1 (%2)").arg(pkcs11h_getMessage(rv)).arg(rv);
00837 if (rv == CKR_CANCEL) {
00838 ret = -3;
00839 retcode = -3;
00840 break;
00841 }
00842 else if ((rv == CKR_PIN_INCORRECT) || (rv == CKR_USER_NOT_LOGGED_IN)) {
00843 ret = -2;
00844 retcode = -2;
00845 break;
00846 }
00847 else {
00848 ret = -2;
00849 retcode = -2;
00850 }
00851 }
00852 else {
00853 if (errstr) *errstr = TQString::null;
00854 ret = 0;
00855 retcode = 0;
00856 }
00857 }
00858 }
00859
00860 pkcs11h_openssl_freeSession(openssl_session);
00861
00862
00863
00864
00865
00866 break;
00867
00868 i++;
00869 }
00870 pkcs11h_certificate_freeCertificateIdList(issuers);
00871
00872
00873 m_watcherObject->retrySamePin(false);
00874
00875 return ret;
00876 #else
00877 return -1;
00878 #endif
00879 }
00880
00881 int TDECryptographicCardDevice::createNewSecretRSAKeyFromCertificate(TQByteArray &plaintext, TQByteArray &ciphertext, X509* certificate) {
00882 #if defined(WITH_PKCS)
00883 unsigned int i;
00884 int retcode = -1;
00885
00886
00887 EVP_PKEY* x509_pubkey = NULL;
00888 RSA* rsa_pubkey = NULL;
00889 x509_pubkey = X509_get_pubkey(certificate);
00890 if (x509_pubkey) {
00891 rsa_pubkey = EVP_PKEY_get1_RSA(x509_pubkey);
00892 }
00893
00894 if (rsa_pubkey) {
00895
00896
00897
00898
00899 int rsa_padding_style = RSA_PKCS1_PADDING;
00900 unsigned int rsa_length = RSA_size(rsa_pubkey);
00901 unsigned int max_key_length = rsa_length - 41;
00902
00903
00904 plaintext.resize(max_key_length);
00905 for (i=0; i < max_key_length; i++) {
00906 plaintext[i] = TDEApplication::random();
00907 }
00908
00909
00910 ciphertext.resize(rsa_length);
00911 if (RSA_public_encrypt(plaintext.size(), (unsigned char *)plaintext.data(), (unsigned char *)ciphertext.data(), rsa_pubkey, rsa_padding_style) < 0) {
00912 retcode = -2;
00913 }
00914
00915
00916 retcode = 0;
00917 }
00918
00919
00920 if (rsa_pubkey) {
00921 RSA_free(rsa_pubkey);
00922 }
00923 if (x509_pubkey) {
00924 EVP_PKEY_free(x509_pubkey);
00925 }
00926
00927 return retcode;
00928 #else
00929 return -1;
00930 #endif
00931 }
00932
00933 TQString TDECryptographicCardDevice::pkcsProviderLibrary() {
00934 #if defined(WITH_PKCS)
00935 return OPENSC_PKCS11_PROVIDER_LIBRARY;
00936 #else
00937 return TQString::null;
00938 #endif
00939 }
00940
00941 #include "tdecryptographiccarddevice.moc"
00942 #include "tdecryptographiccarddevice_private.moc"