00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013 #ifdef HAVE_CONFIG_H
00014 # include <config.h>
00015 #endif
00016
00017
00018 #include "ctfile_p.h"
00019 #include "i18n_l.h"
00020 #include <gwenhywfar/ctf_context_be.h>
00021 #include <gwenhywfar/misc.h>
00022 #include <gwenhywfar/debug.h>
00023 #include <gwenhywfar/padd.h>
00024 #include <gwenhywfar/cryptkeyrsa.h>
00025 #include <gwenhywfar/text.h>
00026
00027 #include <sys/types.h>
00028 #include <sys/stat.h>
00029 #include <fcntl.h>
00030 #include <string.h>
00031 #include <errno.h>
00032 #include <stdlib.h>
00033 #include <unistd.h>
00034
00035
00036
00037 GWEN_INHERIT(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE)
00038
00039
00040
00041
00042
00043 int GWEN_Crypt_TokenFile__OpenFile(GWEN_CRYPT_TOKEN *ct, int wr, uint32_t gid){
00044 int fd;
00045 GWEN_CRYPT_TOKEN_FILE *lct;
00046 GWEN_FSLOCK_RESULT lres;
00047 const char *fname;
00048
00049 assert(ct);
00050 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
00051 assert(lct);
00052
00053 fname = GWEN_Crypt_Token_GetTokenName(ct);
00054 if (!fname) {
00055 DBG_ERROR(GWEN_LOGDOMAIN, "No name of the crypt token set - maybe you need to set the key file as token name? Cannot lock token.");
00056 return GWEN_ERROR_IO;
00057 }
00058
00059 lct->lock=GWEN_FSLock_new(fname,
00060 GWEN_FSLock_TypeFile);
00061 lres=GWEN_FSLock_Lock(lct->lock, 10000, gid);
00062 if (lres!=GWEN_FSLock_ResultOk) {
00063 GWEN_FSLock_free(lct->lock);
00064 lct->lock=0;
00065 DBG_ERROR(GWEN_LOGDOMAIN, "Could not lock file");
00066 if (lres==GWEN_FSLock_ResultUserAbort)
00067 return GWEN_ERROR_USER_ABORTED;
00068 else
00069 return GWEN_ERROR_IO;
00070 }
00071 else {
00072 DBG_INFO(GWEN_LOGDOMAIN,
00073 "Keyfile [%s] locked.",
00074 GWEN_Crypt_Token_GetTokenName(ct));
00075 }
00076
00077 if (wr) {
00078
00079 fd=open(GWEN_Crypt_Token_GetTokenName(ct),
00080 O_RDWR|O_CREAT
00081 #ifdef OS_WIN32
00082 | O_BINARY
00083 #endif
00084 ,
00085 S_IRUSR|S_IWUSR | lct->keyfile_mode);
00086 }
00087 else {
00088
00089 struct stat statbuffer;
00090 if (!stat(GWEN_Crypt_Token_GetTokenName(ct), &statbuffer)) {
00091
00092
00093 lct->keyfile_mode =
00094 statbuffer.st_mode & (S_IRWXU
00095 #ifndef OS_WIN32
00096 | S_IRWXG | S_IRWXO
00097 #endif
00098 );
00099 }
00100 else {
00101 DBG_ERROR(GWEN_LOGDOMAIN,
00102 "stat(%s): %s",
00103 GWEN_Crypt_Token_GetTokenName(ct),
00104 strerror(errno));
00105
00106 GWEN_FSLock_Unlock(lct->lock);
00107 GWEN_FSLock_free(lct->lock);
00108 lct->lock=0;
00109 DBG_INFO(GWEN_LOGDOMAIN,
00110 "Keyfile [%s] unlocked.",
00111 GWEN_Crypt_Token_GetTokenName(ct));
00112 return GWEN_ERROR_IO;
00113 }
00114
00115
00116 fd=open(GWEN_Crypt_Token_GetTokenName(ct),
00117 O_RDONLY
00118 #ifdef OS_WIN32
00119 | O_BINARY
00120 #endif
00121 );
00122 }
00123
00124 if (fd==-1) {
00125 DBG_ERROR(GWEN_LOGDOMAIN,
00126 "open(%s): %s",
00127 GWEN_Crypt_Token_GetTokenName(ct),
00128 strerror(errno));
00129 GWEN_FSLock_Unlock(lct->lock);
00130 GWEN_FSLock_free(lct->lock);
00131 lct->lock=0;
00132 DBG_INFO(GWEN_LOGDOMAIN,
00133 "Keyfile [%s] unlocked.",
00134 GWEN_Crypt_Token_GetTokenName(ct));
00135 return GWEN_ERROR_IO;
00136 }
00137
00138 lct->fd=fd;
00139
00140 return 0;
00141 }
00142
00143
00144
00145 int GWEN_Crypt_TokenFile__CloseFile(GWEN_CRYPT_TOKEN *ct, uint32_t gid){
00146 GWEN_CRYPT_TOKEN_FILE *lct;
00147 GWEN_FSLOCK_RESULT lres;
00148 struct stat st;
00149
00150 assert(ct);
00151 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
00152 assert(lct);
00153
00154 if (lct->fd==-1) {
00155 DBG_ERROR(GWEN_LOGDOMAIN, "Keyfile \"%s\"not open",
00156 GWEN_Crypt_Token_GetTokenName(ct));
00157 return GWEN_ERROR_INTERNAL;
00158 }
00159
00160 if (close(lct->fd)) {
00161 DBG_ERROR(GWEN_LOGDOMAIN, "close(%s): %s",
00162 GWEN_Crypt_Token_GetTokenName(ct), strerror(errno));
00163 lct->fd=-1;
00164 GWEN_FSLock_Unlock(lct->lock);
00165 GWEN_FSLock_free(lct->lock);
00166 lct->lock=0;
00167 DBG_INFO(GWEN_LOGDOMAIN,
00168 "Keyfile [%s] unlocked.",
00169 GWEN_Crypt_Token_GetTokenName(ct));
00170 return GWEN_ERROR_IO;
00171 }
00172 lct->fd=-1;
00173
00174 lres=GWEN_FSLock_Unlock(lct->lock);
00175 if (lres!=GWEN_FSLock_ResultOk) {
00176 DBG_WARN(GWEN_LOGDOMAIN, "Error removing lock from \"%s\": %d",
00177 GWEN_Crypt_Token_GetTokenName(ct), lres);
00178 }
00179 GWEN_FSLock_free(lct->lock);
00180 lct->lock=0;
00181 DBG_INFO(GWEN_LOGDOMAIN,
00182 "Keyfile [%s] unlocked.",
00183 GWEN_Crypt_Token_GetTokenName(ct));
00184
00185
00186 if (stat(GWEN_Crypt_Token_GetTokenName(ct), &st)) {
00187 DBG_ERROR(GWEN_LOGDOMAIN,
00188 "stat(%s): %s",
00189 GWEN_Crypt_Token_GetTokenName(ct),
00190 strerror(errno));
00191 return GWEN_ERROR_IO;
00192 }
00193
00194 #ifndef OS_WIN32
00195 if (st.st_mode & 0007) {
00196 DBG_WARN(GWEN_LOGDOMAIN,
00197 "WARNING: Your keyfile \"%s\" is world accessible!\n"
00198 "Nobody but you should have access to the file. You \n"
00199 "should probably change this with \"chmod 600 %s\"",
00200 GWEN_Crypt_Token_GetTokenName(ct),
00201 GWEN_Crypt_Token_GetTokenName(ct));
00202 GWEN_Gui_ProgressLog(gid, GWEN_LoggerLevel_Warning,
00203 "WARNING: Your keyfile is world accessible!\n"
00204 "Nobody but you should have access to the file.");
00205 }
00206 #endif
00207 lct->mtime=st.st_mtime;
00208 lct->ctime=st.st_ctime;
00209
00210 return 0;
00211 }
00212
00213
00214
00215 int GWEN_Crypt_TokenFile__Read(GWEN_CRYPT_TOKEN *ct, uint32_t gid){
00216 GWEN_CRYPT_TOKEN_FILE *lct;
00217
00218 assert(ct);
00219 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
00220 assert(lct);
00221
00222 assert(lct->readFn);
00223 if (lseek(lct->fd, 0, SEEK_SET)==-1) {
00224 DBG_ERROR(GWEN_LOGDOMAIN, "lseek(%s): %s",
00225 GWEN_Crypt_Token_GetTokenName(ct),
00226 strerror(errno));
00227 return GWEN_ERROR_IO;
00228 }
00229 return lct->readFn(ct, lct->fd, gid);
00230 }
00231
00232
00233
00234 int GWEN_Crypt_TokenFile__Write(GWEN_CRYPT_TOKEN *ct, int cr, uint32_t gid){
00235 GWEN_CRYPT_TOKEN_FILE *lct;
00236
00237 assert(ct);
00238 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
00239 assert(lct);
00240
00241 if (lct->writeFn==0) {
00242 DBG_WARN(GWEN_LOGDOMAIN,
00243 "No write function in crypt token type \"%s\"",
00244 GWEN_Crypt_Token_GetTypeName(ct));
00245 return GWEN_ERROR_NOT_SUPPORTED;
00246 }
00247
00248 if (lseek(lct->fd, 0, SEEK_SET)==-1) {
00249 DBG_ERROR(GWEN_LOGDOMAIN, "lseek(%s): %s",
00250 GWEN_Crypt_Token_GetTokenName(ct),
00251 strerror(errno));
00252 return GWEN_ERROR_IO;
00253 }
00254 return lct->writeFn(ct, lct->fd, cr, gid);
00255 }
00256
00257
00258
00259 int GWEN_Crypt_TokenFile__ReadFile(GWEN_CRYPT_TOKEN *ct, uint32_t gid){
00260 GWEN_CRYPT_TOKEN_FILE *lct;
00261 int rv;
00262
00263 assert(ct);
00264 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
00265 assert(lct);
00266
00267
00268 GWEN_Crypt_Token_Context_List_Clear(lct->contextList);
00269
00270
00271 rv=GWEN_Crypt_TokenFile__OpenFile(ct, 0, gid);
00272 if (rv) {
00273 DBG_INFO(GWEN_LOGDOMAIN,
00274 "Could not open keyfile for reading (%d)", rv);
00275 return rv;
00276 }
00277
00278
00279 rv=GWEN_Crypt_TokenFile__Read(ct, gid);
00280 if (rv) {
00281 DBG_INFO(GWEN_LOGDOMAIN, "Error reading keyfile");
00282 GWEN_Crypt_TokenFile__CloseFile(ct, gid);
00283 return rv;
00284 }
00285
00286
00287 rv=GWEN_Crypt_TokenFile__CloseFile(ct, gid);
00288 if (rv) {
00289 DBG_INFO(GWEN_LOGDOMAIN, "Could not close keyfile");
00290 return rv;
00291 }
00292
00293 return 0;
00294 }
00295
00296
00297
00298 int GWEN_Crypt_TokenFile__WriteFile(GWEN_CRYPT_TOKEN *ct, int cr, uint32_t gid){
00299 GWEN_CRYPT_TOKEN_FILE *lct;
00300 int rv;
00301
00302 assert(ct);
00303 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
00304 assert(lct);
00305
00306
00307 rv=GWEN_Crypt_TokenFile__OpenFile(ct, 1, gid);
00308 if (rv) {
00309 DBG_INFO(GWEN_LOGDOMAIN,
00310 "Could not open keyfile for writing (%d)", rv);
00311 return rv;
00312 }
00313
00314
00315 rv=GWEN_Crypt_TokenFile__Write(ct, cr, gid);
00316 if (rv) {
00317 DBG_INFO(GWEN_LOGDOMAIN, "Error writing keyfile");
00318 GWEN_Crypt_TokenFile__CloseFile(ct, gid);
00319 return rv;
00320 }
00321
00322
00323 rv=GWEN_Crypt_TokenFile__CloseFile(ct, gid);
00324 if (rv) {
00325 DBG_INFO(GWEN_LOGDOMAIN, "Could not close keyfile");
00326 return rv;
00327 }
00328
00329 return 0;
00330 }
00331
00332
00333
00334 int GWEN_Crypt_TokenFile__ReloadIfNeeded(GWEN_CRYPT_TOKEN *ct, uint32_t gid){
00335 GWEN_CRYPT_TOKEN_FILE *lct;
00336 struct stat st;
00337
00338 assert(ct);
00339 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
00340 assert(lct);
00341
00342 if (stat(GWEN_Crypt_Token_GetTokenName(ct), &st)) {
00343 DBG_ERROR(GWEN_LOGDOMAIN,
00344 "stat(%s): %s",
00345 GWEN_Crypt_Token_GetTokenName(ct),
00346 strerror(errno));
00347 return -1;
00348 }
00349 if (lct->mtime!=st.st_mtime ||
00350 lct->ctime!=st.st_ctime) {
00351 int rv;
00352
00353
00354 DBG_NOTICE(GWEN_LOGDOMAIN,
00355 "Keyfile changed externally, reloading it");
00356
00357 rv=GWEN_Crypt_TokenFile__ReadFile(ct, gid);
00358 if (rv) {
00359 DBG_WARN(GWEN_LOGDOMAIN, "Error reloading keyfile");
00360 return rv;
00361 }
00362 }
00363 else {
00364 DBG_NOTICE(GWEN_LOGDOMAIN, "Keyfile unchanged, not reloading");
00365 }
00366 return 0;
00367 }
00368
00369
00370
00371 void GWEN_Crypt_TokenFile_AddContext(GWEN_CRYPT_TOKEN *ct, GWEN_CRYPT_TOKEN_CONTEXT *ctx) {
00372 GWEN_CRYPT_TOKEN_FILE *lct;
00373
00374 assert(ct);
00375 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
00376 assert(lct);
00377
00378
00379 assert(GWEN_CTF_Context_IsOfThisType(ctx));
00380 GWEN_Crypt_Token_Context_List_Add(ctx, lct->contextList);
00381 }
00382
00383
00384
00385 GWEN_CRYPT_TOKEN_CONTEXT *GWEN_Crypt_TokenFile_GetContext(GWEN_CRYPT_TOKEN *ct, int idx) {
00386 GWEN_CRYPT_TOKEN_FILE *lct;
00387 GWEN_CRYPT_TOKEN_CONTEXT *ctx;
00388
00389 assert(ct);
00390 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
00391 assert(lct);
00392
00393 ctx=GWEN_Crypt_Token_Context_List_First(lct->contextList);
00394 while(ctx) {
00395 if (idx==0)
00396 return ctx;
00397 ctx=GWEN_Crypt_Token_Context_List_Next(ctx);
00398 idx--;
00399 }
00400
00401 return NULL;
00402 }
00403
00404
00405
00406 GWEN_CRYPT_TOKEN_FILE_READ_FN GWEN_Crypt_TokenFile_SetReadFn(GWEN_CRYPT_TOKEN *ct,
00407 GWEN_CRYPT_TOKEN_FILE_READ_FN f) {
00408 GWEN_CRYPT_TOKEN_FILE *lct;
00409 GWEN_CRYPT_TOKEN_FILE_READ_FN of;
00410
00411 assert(ct);
00412 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
00413 assert(lct);
00414
00415 of=lct->readFn;
00416 lct->readFn=f;
00417
00418 return of;
00419 }
00420
00421
00422
00423 GWEN_CRYPT_TOKEN_FILE_WRITE_FN GWEN_Crypt_TokenFile_SetWriteFn(GWEN_CRYPT_TOKEN *ct,
00424 GWEN_CRYPT_TOKEN_FILE_WRITE_FN f) {
00425 GWEN_CRYPT_TOKEN_FILE *lct;
00426 GWEN_CRYPT_TOKEN_FILE_WRITE_FN of;
00427
00428 assert(ct);
00429 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
00430 assert(lct);
00431
00432 of=lct->writeFn;
00433 lct->writeFn=f;
00434
00435 return of;
00436 }
00437
00438
00439
00440 int GWENHYWFAR_CB GWEN_Crypt_TokenFile_Create(GWEN_CRYPT_TOKEN *ct, uint32_t gid){
00441 GWEN_CRYPT_TOKEN_FILE *lct;
00442 struct stat st;
00443 int fd;
00444 int rv;
00445
00446 assert(ct);
00447 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
00448 assert(lct);
00449
00450 if (!GWEN_Crypt_Token_GetTokenName(ct)) {
00451 DBG_ERROR(GWEN_LOGDOMAIN, "No medium name given");
00452 return GWEN_ERROR_INVALID;
00453 }
00454
00455 if (stat(GWEN_Crypt_Token_GetTokenName(ct), &st)) {
00456 if (errno!=ENOENT) {
00457 DBG_ERROR(GWEN_LOGDOMAIN,
00458 "stat(%s): %s",
00459 GWEN_Crypt_Token_GetTokenName(ct),
00460 strerror(errno));
00461 return GWEN_ERROR_IO;
00462 }
00463 }
00464 else {
00465 DBG_ERROR(GWEN_LOGDOMAIN,
00466 "Keyfile \"%s\" already exists, will not create it",
00467 GWEN_Crypt_Token_GetTokenName(ct));
00468 return GWEN_ERROR_INVALID;
00469 }
00470
00471
00472
00473 fd=open(GWEN_Crypt_Token_GetTokenName(ct),
00474 O_RDWR | O_CREAT | O_EXCL
00475 #ifdef OS_WIN32
00476 | O_BINARY
00477 #endif
00478 ,
00479 S_IRUSR|S_IWUSR);
00480
00481
00482 if (fd==-1) {
00483 DBG_ERROR(GWEN_LOGDOMAIN,
00484 "open(%s): %s",
00485 GWEN_Crypt_Token_GetTokenName(ct),
00486 strerror(errno));
00487 return GWEN_ERROR_IO;
00488 }
00489
00490 close(fd);
00491
00492 rv=GWEN_Crypt_TokenFile__WriteFile(ct, 1, gid);
00493 if (rv) {
00494 DBG_INFO(GWEN_LOGDOMAIN, "here");
00495 return rv;
00496 }
00497
00498 return 0;
00499 }
00500
00501
00502
00503 int GWENHYWFAR_CB GWEN_Crypt_TokenFile_Open(GWEN_CRYPT_TOKEN *ct, GWEN_UNUSED int admin, uint32_t gid){
00504 GWEN_CRYPT_TOKEN_FILE *lct;
00505 int rv;
00506
00507 assert(ct);
00508 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
00509 assert(lct);
00510
00511 rv=GWEN_Crypt_TokenFile__ReadFile(ct, gid);
00512 if (rv) {
00513 DBG_INFO(GWEN_LOGDOMAIN, "here");
00514 return rv;
00515 }
00516
00517 return 0;
00518 }
00519
00520
00521
00522 int GWENHYWFAR_CB GWEN_Crypt_TokenFile_Close(GWEN_CRYPT_TOKEN *ct, int abandon, uint32_t gid){
00523 GWEN_CRYPT_TOKEN_FILE *lct;
00524 int rv;
00525
00526 assert(ct);
00527 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
00528 assert(lct);
00529
00530 if (!abandon)
00531 rv=GWEN_Crypt_TokenFile__WriteFile(ct, 0, gid);
00532 else
00533 rv=0;
00534
00535
00536 GWEN_Crypt_Token_Context_List_Clear(lct->contextList);
00537 lct->mtime=0;
00538 lct->ctime=0;
00539
00540 return rv;
00541 }
00542
00543
00544
00545
00546 int GWENHYWFAR_CB GWEN_Crypt_TokenFile__GetKeyIdList(GWEN_CRYPT_TOKEN *ct,
00547 uint32_t *pIdList,
00548 uint32_t *pCount,
00549 uint32_t gid) {
00550 GWEN_CRYPT_TOKEN_FILE *lct;
00551 GWEN_CRYPT_TOKEN_CONTEXT *ctx;
00552 int i;
00553 int rv;
00554
00555 assert(ct);
00556 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
00557 assert(lct);
00558
00559
00560 rv=GWEN_Crypt_TokenFile__ReloadIfNeeded(ct, gid);
00561 if (rv) {
00562 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
00563 return rv;
00564 }
00565
00566
00567 i=0;
00568 ctx=GWEN_Crypt_Token_Context_List_First(lct->contextList);
00569 while(ctx) {
00570 i+=GWEN_CRYPT_TOKEN_CONTEXT_KEYS;
00571 ctx=GWEN_Crypt_Token_Context_List_Next(ctx);
00572 }
00573
00574
00575 if (pIdList==NULL) {
00576 *pCount=i;
00577 return 0;
00578 }
00579
00580 if (*pCount<i) {
00581 DBG_INFO(GWEN_LOGDOMAIN, "Buffer too small");
00582 return GWEN_ERROR_BUFFER_OVERFLOW;
00583 }
00584
00585 *pCount=i;
00586 i=0;
00587 ctx=GWEN_Crypt_Token_Context_List_First(lct->contextList);
00588 while(ctx) {
00589 int j;
00590
00591 for (j=1; j<=GWEN_CRYPT_TOKEN_CONTEXT_KEYS; j++)
00592 *(pIdList++)=(i<<16)+j;
00593
00594 ctx=GWEN_Crypt_Token_Context_List_Next(ctx);
00595 i++;
00596 }
00597
00598 return 0;
00599 }
00600
00601
00602
00603 const GWEN_CRYPT_TOKEN_KEYINFO* GWENHYWFAR_CB
00604 GWEN_Crypt_TokenFile__GetKeyInfo(GWEN_CRYPT_TOKEN *ct,
00605 uint32_t id,
00606 uint32_t flags,
00607 uint32_t gid) {
00608 GWEN_CRYPT_TOKEN_FILE *lct;
00609 GWEN_CRYPT_TOKEN_CONTEXT *ctx;
00610 GWEN_CRYPT_TOKEN_KEYINFO *ki;
00611 int i;
00612 int rv;
00613
00614 assert(ct);
00615 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
00616 assert(lct);
00617
00618
00619 rv=GWEN_Crypt_TokenFile__ReloadIfNeeded(ct, gid);
00620 if (rv) {
00621 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
00622 return NULL;
00623 }
00624
00625 i=id>>16;
00626 ctx=GWEN_Crypt_Token_Context_List_First(lct->contextList);
00627 while(ctx) {
00628 if (i==0)
00629 break;
00630 ctx=GWEN_Crypt_Token_Context_List_Next(ctx);
00631 i--;
00632 }
00633
00634 if (ctx==NULL) {
00635 DBG_INFO(GWEN_LOGDOMAIN, "No key by id [%x] known (context out of range)", id);
00636 return NULL;
00637 }
00638
00639 switch(id & 0xffff) {
00640 case 1: ki=GWEN_CTF_Context_GetLocalSignKeyInfo(ctx); break;
00641 case 2: ki=GWEN_CTF_Context_GetLocalCryptKeyInfo(ctx); break;
00642 case 3: ki=GWEN_CTF_Context_GetRemoteSignKeyInfo(ctx); break;
00643 case 4: ki=GWEN_CTF_Context_GetRemoteCryptKeyInfo(ctx); break;
00644 case 5: ki=GWEN_CTF_Context_GetLocalAuthKeyInfo(ctx); break;
00645 case 6: ki=GWEN_CTF_Context_GetRemoteAuthKeyInfo(ctx); break;
00646 default:
00647 DBG_INFO(GWEN_LOGDOMAIN, "No key by id [%x] known (key id out of range)", id);
00648 return NULL;
00649 }
00650
00651 if (ki==NULL) {
00652 DBG_INFO(GWEN_LOGDOMAIN, "No key info stored for key %d", id);
00653 return NULL;
00654 }
00655
00656 return ki;
00657 }
00658
00659
00660
00661 #if 0
00662 int GWENHYWFAR_CB
00663 GWEN_Crypt_TokenFile__SetKeyInfo(GWEN_CRYPT_TOKEN *ct,
00664 uint32_t id,
00665 const GWEN_CRYPT_TOKEN_KEYINFO *ki,
00666 uint32_t gid) {
00667 GWEN_CRYPT_TOKEN_FILE *lct;
00668 GWEN_CRYPT_TOKEN_CONTEXT *ctx;
00669 int i;
00670 int rv;
00671 GWEN_CRYPT_TOKEN_KEYINFO *nki;
00672 GWEN_CRYPT_KEY *key;
00673 uint32_t flags;
00674
00675 assert(ct);
00676 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
00677 assert(lct);
00678
00679 flags=GWEN_Crypt_Token_KeyInfo_GetFlags(ki);
00680
00681
00682 rv=GWEN_Crypt_TokenFile__ReloadIfNeeded(ct, gid);
00683 if (rv) {
00684 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
00685 return rv;
00686 }
00687
00688 i=id>>16;
00689 ctx=GWEN_Crypt_Token_Context_List_First(lct->contextList);
00690 while(ctx) {
00691 if (i==0)
00692 break;
00693 ctx=GWEN_Crypt_Token_Context_List_Next(ctx);
00694 i--;
00695 }
00696
00697 if (ctx==NULL) {
00698 DBG_INFO(GWEN_LOGDOMAIN, "No key by id [%x] known (context out of range)", id);
00699 return GWEN_ERROR_NOT_FOUND;
00700 }
00701
00702 nki=GWEN_Crypt_Token_KeyInfo_dup(ki);
00703 assert(nki);
00704 switch(id & 0xffff) {
00705 case 1:
00706 GWEN_CTF_Context_SetLocalSignKeyInfo(ctx, nki);
00707 key=GWEN_CTF_Context_GetLocalSignKey(ctx);
00708 break;
00709 case 2:
00710 GWEN_CTF_Context_SetLocalCryptKeyInfo(ctx, nki);
00711 key=GWEN_CTF_Context_GetLocalCryptKey(ctx);
00712 break;
00713 case 3:
00714 GWEN_CTF_Context_SetRemoteSignKeyInfo(ctx, nki);
00715 key=GWEN_CTF_Context_GetRemoteSignKey(ctx);
00716 break;
00717 case 4:
00718 GWEN_CTF_Context_SetRemoteCryptKeyInfo(ctx, nki);
00719 key=GWEN_CTF_Context_GetRemoteCryptKey(ctx);
00720 break;
00721 case 5:
00722 GWEN_CTF_Context_SetLocalAuthKeyInfo(ctx, nki);
00723 key=GWEN_CTF_Context_GetLocalAuthKey(ctx);
00724 break;
00725 case 6:
00726 GWEN_CTF_Context_SetRemoteAuthKeyInfo(ctx, nki);
00727 key=GWEN_CTF_Context_GetRemoteAuthKey(ctx);
00728 break;
00729 default:
00730 DBG_INFO(GWEN_LOGDOMAIN, "No key by id [%x] known (key id out of range)", id);
00731 GWEN_Crypt_Token_KeyInfo_free(nki);
00732 return GWEN_ERROR_NOT_FOUND;
00733 }
00734
00735
00736 if ((flags & GWEN_CRYPT_TOKEN_KEYFLAGS_HASMODULUS) &&
00737 (flags & GWEN_CRYPT_TOKEN_KEYFLAGS_HASEXPONENT) &&
00738 id!=1 &&
00739 id!=2 &&
00740 id!=5) {
00741 GWEN_CRYPT_KEY *nkey;
00742
00743 nkey=GWEN_Crypt_KeyRsa_fromModExp(GWEN_Crypt_Token_KeyInfo_GetKeySize(ki),
00744 GWEN_Crypt_Token_KeyInfo_GetModulusData(ki),
00745 GWEN_Crypt_Token_KeyInfo_GetModulusLen(ki),
00746 GWEN_Crypt_Token_KeyInfo_GetExponentData(ki),
00747 GWEN_Crypt_Token_KeyInfo_GetExponentLen(ki));
00748 assert(nkey);
00749
00750 if (flags & GWEN_CRYPT_TOKEN_KEYFLAGS_HASKEYNUMBER)
00751 GWEN_Crypt_Key_SetKeyNumber(nkey, GWEN_Crypt_Token_KeyInfo_GetKeyNumber(ki));
00752 if (flags & GWEN_CRYPT_TOKEN_KEYFLAGS_HASKEYVERSION)
00753 GWEN_Crypt_Key_SetKeyVersion(nkey, GWEN_Crypt_Token_KeyInfo_GetKeyVersion(ki));
00754
00755
00756 switch(id & 0xffff) {
00757 case 3:
00758 GWEN_CTF_Context_SetRemoteSignKey(ctx, nkey);
00759 break;
00760 case 4:
00761 GWEN_CTF_Context_SetRemoteCryptKey(ctx, nkey);
00762 break;
00763 case 6:
00764 GWEN_CTF_Context_SetRemoteAuthKey(ctx, nkey);
00765 break;
00766 default:
00767 DBG_ERROR(GWEN_LOGDOMAIN,
00768 "Can't set modulus and exponent for private key");
00769 GWEN_Crypt_Key_free(nkey);
00770 return GWEN_ERROR_INVALID;
00771 }
00772 GWEN_Gui_ProgressLog(gid, GWEN_LoggerLevel_Notice,
00773 I18N("Public key replaced"));
00774 }
00775 else {
00776 if (key) {
00777 if (flags & GWEN_CRYPT_TOKEN_KEYFLAGS_HASKEYNUMBER)
00778 GWEN_Crypt_Key_SetKeyNumber(key, GWEN_Crypt_Token_KeyInfo_GetKeyNumber(ki));
00779 if (flags & GWEN_CRYPT_TOKEN_KEYFLAGS_HASKEYVERSION)
00780 GWEN_Crypt_Key_SetKeyVersion(key, GWEN_Crypt_Token_KeyInfo_GetKeyVersion(ki));
00781 }
00782 }
00783
00784 rv=GWEN_Crypt_TokenFile__WriteFile(ct, 0, gid);
00785 if (rv) {
00786 DBG_INFO(GWEN_LOGDOMAIN, "Unable to write file");
00787 GWEN_Gui_ProgressLog(gid, GWEN_LoggerLevel_Error,
00788 I18N("Unable to write key file"));
00789 return rv;
00790 }
00791
00792 GWEN_Gui_ProgressLog(gid, GWEN_LoggerLevel_Notice,
00793 I18N("Key file saved"));
00794
00795 return 0;
00796 }
00797 #endif
00798
00799
00800 int GWENHYWFAR_CB
00801 GWEN_Crypt_TokenFile__SetKeyInfo(GWEN_CRYPT_TOKEN *ct,
00802 uint32_t id,
00803 const GWEN_CRYPT_TOKEN_KEYINFO *ski,
00804 uint32_t gid) {
00805 GWEN_CRYPT_TOKEN_FILE *lct;
00806 GWEN_CRYPT_TOKEN_CONTEXT *ctx;
00807 int i;
00808 int rv;
00809 GWEN_CRYPT_TOKEN_KEYINFO *ki;
00810 GWEN_CRYPT_KEY *key;
00811 uint32_t flags;
00812 uint32_t nflags;
00813
00814 assert(ct);
00815 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
00816 assert(lct);
00817
00818 flags=GWEN_Crypt_Token_KeyInfo_GetFlags(ski);
00819
00820
00821 rv=GWEN_Crypt_TokenFile__ReloadIfNeeded(ct, gid);
00822 if (rv) {
00823 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
00824 return rv;
00825 }
00826
00827 i=id>>16;
00828 ctx=GWEN_Crypt_Token_Context_List_First(lct->contextList);
00829 while(ctx) {
00830 if (i==0)
00831 break;
00832 ctx=GWEN_Crypt_Token_Context_List_Next(ctx);
00833 i--;
00834 }
00835
00836 if (ctx==NULL) {
00837 DBG_INFO(GWEN_LOGDOMAIN, "No key by id [%x] known (context out of range)", id);
00838 return GWEN_ERROR_NOT_FOUND;
00839 }
00840
00841 switch(id & 0xffff) {
00842 case 1:
00843 ki=GWEN_CTF_Context_GetLocalSignKeyInfo(ctx);
00844 key=GWEN_CTF_Context_GetLocalSignKey(ctx);
00845 break;
00846 case 2:
00847 ki=GWEN_CTF_Context_GetLocalCryptKeyInfo(ctx);
00848 key=GWEN_CTF_Context_GetLocalCryptKey(ctx);
00849 break;
00850 case 3:
00851 ki=GWEN_CTF_Context_GetRemoteSignKeyInfo(ctx);
00852 key=GWEN_CTF_Context_GetRemoteSignKey(ctx);
00853 break;
00854 case 4:
00855 ki=GWEN_CTF_Context_GetRemoteCryptKeyInfo(ctx);
00856 key=GWEN_CTF_Context_GetRemoteCryptKey(ctx);
00857 break;
00858 case 5:
00859 ki=GWEN_CTF_Context_GetLocalAuthKeyInfo(ctx);
00860 key=GWEN_CTF_Context_GetLocalAuthKey(ctx);
00861 break;
00862 case 6:
00863 ki=GWEN_CTF_Context_GetRemoteAuthKeyInfo(ctx);
00864 key=GWEN_CTF_Context_GetRemoteAuthKey(ctx);
00865 break;
00866 default:
00867 DBG_INFO(GWEN_LOGDOMAIN, "No key by id [%x] known (key id out of range)", id);
00868 return GWEN_ERROR_NOT_FOUND;
00869 }
00870 assert(ki);
00871
00872 nflags=GWEN_Crypt_Token_KeyInfo_GetFlags(ki);
00873
00874 if (flags & GWEN_CRYPT_TOKEN_KEYFLAGS_HASSTATUS) {
00875
00876 }
00877
00878 if (flags & GWEN_CRYPT_TOKEN_KEYFLAGS_HASACTIONFLAGS) {
00879 nflags&=~GWEN_CRYPT_TOKEN_KEYFLAGS_ACTIONMASK;
00880 nflags|=(flags & GWEN_CRYPT_TOKEN_KEYFLAGS_ACTIONMASK);
00881 }
00882
00883 if (flags & GWEN_CRYPT_TOKEN_KEYFLAGS_HASKEYVERSION) {
00884 uint32_t i=GWEN_Crypt_Token_KeyInfo_GetKeyVersion(ski);
00885 GWEN_Crypt_Token_KeyInfo_SetKeyVersion(ki, i);
00886 nflags|=GWEN_CRYPT_TOKEN_KEYFLAGS_HASKEYVERSION;
00887 if (key)
00888 GWEN_Crypt_Key_SetKeyVersion(key, GWEN_Crypt_Token_KeyInfo_GetKeyVersion(ski));
00889 DBG_INFO(GWEN_LOGDOMAIN, "Setting key version");
00890 }
00891
00892 if (flags & GWEN_CRYPT_TOKEN_KEYFLAGS_HASSIGNCOUNTER) {
00893 uint32_t i=GWEN_Crypt_Token_KeyInfo_GetSignCounter(ski);
00894 GWEN_Crypt_Token_KeyInfo_SetSignCounter(ki, i);
00895 nflags|=GWEN_CRYPT_TOKEN_KEYFLAGS_HASSIGNCOUNTER;
00896 DBG_INFO(GWEN_LOGDOMAIN, "Setting signature counter");
00897 }
00898
00899 if (flags & GWEN_CRYPT_TOKEN_KEYFLAGS_HASKEYNUMBER) {
00900 uint32_t i=GWEN_Crypt_Token_KeyInfo_GetKeyNumber(ski);
00901 GWEN_Crypt_Token_KeyInfo_SetKeyNumber(ki, i);
00902 nflags|=GWEN_CRYPT_TOKEN_KEYFLAGS_HASKEYNUMBER;
00903 if (key)
00904 GWEN_Crypt_Key_SetKeyNumber(key, GWEN_Crypt_Token_KeyInfo_GetKeyNumber(ski));
00905 DBG_INFO(GWEN_LOGDOMAIN, "Setting key number");
00906 }
00907
00908
00909 if ((flags & GWEN_CRYPT_TOKEN_KEYFLAGS_HASMODULUS) &&
00910 (flags & GWEN_CRYPT_TOKEN_KEYFLAGS_HASEXPONENT) &&
00911 id!=1 &&
00912 id!=2 &&
00913 id!=5) {
00914 GWEN_CRYPT_KEY *nkey;
00915
00916 GWEN_Crypt_Token_KeyInfo_SetKeySize(ki, GWEN_Crypt_Token_KeyInfo_GetKeySize(ski));
00917 GWEN_Crypt_Token_KeyInfo_SetModulus(ki,
00918 GWEN_Crypt_Token_KeyInfo_GetModulusData(ski),
00919 GWEN_Crypt_Token_KeyInfo_GetModulusLen(ski));
00920 nflags|=GWEN_CRYPT_TOKEN_KEYFLAGS_HASMODULUS;
00921 GWEN_Crypt_Token_KeyInfo_SetExponent(ki,
00922 GWEN_Crypt_Token_KeyInfo_GetExponentData(ski),
00923 GWEN_Crypt_Token_KeyInfo_GetExponentLen(ski));
00924 nflags|=GWEN_CRYPT_TOKEN_KEYFLAGS_HASEXPONENT;
00925 nkey=GWEN_Crypt_KeyRsa_fromModExp(GWEN_Crypt_Token_KeyInfo_GetKeySize(ski),
00926 GWEN_Crypt_Token_KeyInfo_GetModulusData(ski),
00927 GWEN_Crypt_Token_KeyInfo_GetModulusLen(ski),
00928 GWEN_Crypt_Token_KeyInfo_GetExponentData(ski),
00929 GWEN_Crypt_Token_KeyInfo_GetExponentLen(ski));
00930 assert(nkey);
00931
00932 if (nflags & GWEN_CRYPT_TOKEN_KEYFLAGS_HASKEYNUMBER)
00933 GWEN_Crypt_Key_SetKeyNumber(nkey, GWEN_Crypt_Token_KeyInfo_GetKeyNumber(ki));
00934 if (nflags & GWEN_CRYPT_TOKEN_KEYFLAGS_HASKEYVERSION)
00935 GWEN_Crypt_Key_SetKeyVersion(nkey, GWEN_Crypt_Token_KeyInfo_GetKeyVersion(ki));
00936
00937
00938 switch(id & 0xffff) {
00939 case 3:
00940 GWEN_CTF_Context_SetRemoteSignKey(ctx, nkey);
00941 break;
00942 case 4:
00943 GWEN_CTF_Context_SetRemoteCryptKey(ctx, nkey);
00944 break;
00945 case 6:
00946 GWEN_CTF_Context_SetRemoteAuthKey(ctx, nkey);
00947 break;
00948 default:
00949 DBG_ERROR(GWEN_LOGDOMAIN,
00950 "Can't set modulus and exponent for private key");
00951 GWEN_Crypt_Key_free(nkey);
00952 return GWEN_ERROR_INVALID;
00953 }
00954 GWEN_Gui_ProgressLog(gid, GWEN_LoggerLevel_Notice,
00955 I18N("Public key replaced"));
00956 }
00957 else {
00958 if (key) {
00959 if (flags & GWEN_CRYPT_TOKEN_KEYFLAGS_HASKEYNUMBER)
00960 GWEN_Crypt_Key_SetKeyNumber(key, GWEN_Crypt_Token_KeyInfo_GetKeyNumber(ki));
00961 if (flags & GWEN_CRYPT_TOKEN_KEYFLAGS_HASKEYVERSION)
00962 GWEN_Crypt_Key_SetKeyVersion(key, GWEN_Crypt_Token_KeyInfo_GetKeyVersion(ki));
00963 }
00964 }
00965
00966 GWEN_Crypt_Token_KeyInfo_SetFlags(ki, nflags);
00967
00968 rv=GWEN_Crypt_TokenFile__WriteFile(ct, 0, gid);
00969 if (rv) {
00970 DBG_INFO(GWEN_LOGDOMAIN, "Unable to write file");
00971 GWEN_Gui_ProgressLog(gid, GWEN_LoggerLevel_Error,
00972 I18N("Unable to write key file"));
00973 return rv;
00974 }
00975
00976 GWEN_Gui_ProgressLog(gid, GWEN_LoggerLevel_Notice,
00977 I18N("Key file saved"));
00978
00979 return 0;
00980 }
00981
00982
00983
00984 int GWENHYWFAR_CB
00985 GWEN_Crypt_TokenFile__GetContextIdList(GWEN_CRYPT_TOKEN *ct,
00986 uint32_t *pIdList,
00987 uint32_t *pCount,
00988 uint32_t gid) {
00989 GWEN_CRYPT_TOKEN_FILE *lct;
00990 GWEN_CRYPT_TOKEN_CONTEXT *ctx;
00991 int i;
00992 int rv;
00993
00994 assert(ct);
00995 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
00996 assert(lct);
00997
00998
00999 rv=GWEN_Crypt_TokenFile__ReloadIfNeeded(ct, gid);
01000 if (rv) {
01001 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
01002 return rv;
01003 }
01004
01005
01006 i=0;
01007 ctx=GWEN_Crypt_Token_Context_List_First(lct->contextList);
01008 while(ctx) {
01009 i++;
01010 ctx=GWEN_Crypt_Token_Context_List_Next(ctx);
01011 }
01012
01013
01014 *pCount=i;
01015
01016
01017 if (pIdList==NULL)
01018 return 0;
01019
01020 if (*pCount<i) {
01021 DBG_INFO(GWEN_LOGDOMAIN, "Buffer too small");
01022 return GWEN_ERROR_BUFFER_OVERFLOW;
01023 }
01024
01025 i=1;
01026 ctx=GWEN_Crypt_Token_Context_List_First(lct->contextList);
01027 while(ctx) {
01028 *(pIdList++)=i;
01029 ctx=GWEN_Crypt_Token_Context_List_Next(ctx);
01030 i++;
01031 }
01032
01033 return 0;
01034 }
01035
01036
01037
01038 const GWEN_CRYPT_TOKEN_CONTEXT* GWENHYWFAR_CB
01039 GWEN_Crypt_TokenFile__GetContext(GWEN_CRYPT_TOKEN *ct,
01040 uint32_t id,
01041 uint32_t gid) {
01042 GWEN_CRYPT_TOKEN_FILE *lct;
01043 GWEN_CRYPT_TOKEN_CONTEXT *ctx;
01044 int rv;
01045
01046 assert(ct);
01047 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
01048 assert(lct);
01049
01050
01051 rv=GWEN_Crypt_TokenFile__ReloadIfNeeded(ct, gid);
01052 if (rv) {
01053 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
01054 return NULL;
01055 }
01056
01057 if (id==0) {
01058 DBG_INFO(GWEN_LOGDOMAIN, "Invalid context id 0");
01059 return NULL;
01060 }
01061
01062 ctx=GWEN_Crypt_Token_Context_List_First(lct->contextList);
01063 while(ctx) {
01064 if (GWEN_Crypt_Token_Context_GetId(ctx)==id)
01065 break;
01066 ctx=GWEN_Crypt_Token_Context_List_Next(ctx);
01067 }
01068
01069 if (ctx==NULL) {
01070 DBG_INFO(GWEN_LOGDOMAIN, "No context by id [%x] known", id);
01071 return NULL;
01072 }
01073
01074 return ctx;
01075 }
01076
01077
01078
01079 int GWENHYWFAR_CB
01080 GWEN_Crypt_TokenFile__SetContext(GWEN_CRYPT_TOKEN *ct,
01081 uint32_t id,
01082 const GWEN_CRYPT_TOKEN_CONTEXT *nctx,
01083 uint32_t gid) {
01084 GWEN_CRYPT_TOKEN_FILE *lct;
01085 GWEN_CRYPT_TOKEN_CONTEXT *ctx;
01086 int rv;
01087 const char *s;
01088
01089 assert(ct);
01090 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
01091 assert(lct);
01092
01093 if (id==0) {
01094 DBG_INFO(GWEN_LOGDOMAIN, "Invalid context id 0");
01095 return GWEN_ERROR_INVALID;
01096 }
01097
01098
01099 rv=GWEN_Crypt_TokenFile__ReloadIfNeeded(ct, gid);
01100 if (rv) {
01101 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
01102 return rv;
01103 }
01104
01105 ctx=GWEN_Crypt_Token_Context_List_First(lct->contextList);
01106 while(ctx) {
01107 if (GWEN_Crypt_Token_Context_GetId(ctx)==id)
01108 break;
01109 ctx=GWEN_Crypt_Token_Context_List_Next(ctx);
01110 }
01111
01112 if (ctx==NULL) {
01113 DBG_INFO(GWEN_LOGDOMAIN, "No context by id [%x] known", id);
01114 return GWEN_ERROR_NOT_FOUND;
01115 }
01116
01117
01118 s=GWEN_Crypt_Token_Context_GetServiceId(nctx);
01119 GWEN_Crypt_Token_Context_SetServiceId(ctx, s);
01120 s=GWEN_Crypt_Token_Context_GetUserId(nctx);
01121 GWEN_Crypt_Token_Context_SetUserId(ctx, s);
01122 s=GWEN_Crypt_Token_Context_GetUserName(nctx);
01123 GWEN_Crypt_Token_Context_SetUserName(ctx, s);
01124 s=GWEN_Crypt_Token_Context_GetPeerId(nctx);
01125 GWEN_Crypt_Token_Context_SetPeerId(ctx, s);
01126 s=GWEN_Crypt_Token_Context_GetAddress(nctx);
01127 GWEN_Crypt_Token_Context_SetAddress(ctx, s);
01128 GWEN_Crypt_Token_Context_SetPort(ctx, GWEN_Crypt_Token_Context_GetPort(nctx));
01129 s=GWEN_Crypt_Token_Context_GetSystemId(nctx);
01130 GWEN_Crypt_Token_Context_SetSystemId(ctx, s);
01131
01132 return 0;
01133 }
01134
01135
01136
01137 GWEN_CRYPT_KEY *GWEN_Crypt_TokenFile__GetKey(GWEN_CRYPT_TOKEN *ct, uint32_t id, uint32_t gid) {
01138 GWEN_CRYPT_TOKEN_FILE *lct;
01139 GWEN_CRYPT_TOKEN_CONTEXT *ctx;
01140 int i;
01141 int rv;
01142
01143 assert(ct);
01144 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
01145 assert(lct);
01146
01147
01148 rv=GWEN_Crypt_TokenFile__ReloadIfNeeded(ct, gid);
01149 if (rv) {
01150 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
01151 return NULL;
01152 }
01153
01154 i=id>>16;
01155 ctx=GWEN_Crypt_Token_Context_List_First(lct->contextList);
01156 while(ctx) {
01157 if (i==0)
01158 break;
01159 ctx=GWEN_Crypt_Token_Context_List_Next(ctx);
01160 i--;
01161 }
01162
01163 if (ctx==NULL) {
01164 DBG_INFO(GWEN_LOGDOMAIN, "No key by id [%x] known (context out of range)", id);
01165 return NULL;
01166 }
01167
01168 switch(id & 0xffff) {
01169 case 1: return GWEN_CTF_Context_GetLocalSignKey(ctx);
01170 case 2: return GWEN_CTF_Context_GetLocalCryptKey(ctx);
01171 case 3: return GWEN_CTF_Context_GetRemoteSignKey(ctx);
01172 case 4: return GWEN_CTF_Context_GetRemoteCryptKey(ctx);
01173 case 5: return GWEN_CTF_Context_GetLocalAuthKey(ctx);
01174 case 6: return GWEN_CTF_Context_GetRemoteAuthKey(ctx);
01175 default:
01176 DBG_INFO(GWEN_LOGDOMAIN, "No key by id [%x] known (key id out of range)", id);
01177 return NULL;
01178 }
01179 }
01180
01181
01182
01183 int GWENHYWFAR_CB
01184 GWEN_Crypt_TokenFile__Sign(GWEN_CRYPT_TOKEN *ct,
01185 uint32_t keyId,
01186 GWEN_CRYPT_PADDALGO *a,
01187 const uint8_t *pInData,
01188 uint32_t inLen,
01189 uint8_t *pSignatureData,
01190 uint32_t *pSignatureLen,
01191 uint32_t *pSeqCounter,
01192 uint32_t gid) {
01193 GWEN_CRYPT_TOKEN_FILE *lct;
01194 GWEN_CRYPT_TOKEN_CONTEXT *ctx;
01195 GWEN_CRYPT_KEY *k;
01196 int keyNum;
01197 GWEN_BUFFER *srcBuf;
01198 int i;
01199 int rv;
01200 GWEN_CRYPT_PADDALGOID aid;
01201
01202 assert(ct);
01203 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
01204 assert(lct);
01205
01206 DBG_INFO(GWEN_LOGDOMAIN, "Signing with key %d", keyId);
01207 aid=GWEN_Crypt_PaddAlgo_GetId(a);
01208
01209
01210 rv=GWEN_Crypt_TokenFile__ReloadIfNeeded(ct, gid);
01211 if (rv) {
01212 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
01213 return rv;
01214 }
01215
01216
01217 i=(keyId>>16);
01218 ctx=GWEN_Crypt_Token_Context_List_First(lct->contextList);
01219 if (ctx==NULL) {
01220 DBG_ERROR(GWEN_LOGDOMAIN, "Token has no context");
01221 return GWEN_ERROR_NOT_FOUND;
01222 }
01223 while(ctx) {
01224 if (i==0)
01225 break;
01226 DBG_ERROR(GWEN_LOGDOMAIN, "Checking token %d (i==%d)",
01227 GWEN_Crypt_Token_Context_GetId(ctx), i);
01228 ctx=GWEN_Crypt_Token_Context_List_Next(ctx);
01229 i--;
01230 }
01231
01232 if (ctx==NULL) {
01233 DBG_INFO(GWEN_LOGDOMAIN, "No context by id [%x] known", (keyId>>16) & 0xffff);
01234 return GWEN_ERROR_NOT_FOUND;
01235 }
01236
01237
01238 keyNum=keyId & 0xffff;
01239 if (keyNum!=1 && keyNum!=5) {
01240
01241 DBG_INFO(GWEN_LOGDOMAIN, "Bad key for signing (%x)", keyId);
01242 return GWEN_ERROR_INVALID;
01243 }
01244
01245 k=GWEN_Crypt_TokenFile__GetKey(ct, keyId, gid);
01246 if (k==NULL) {
01247 DBG_INFO(GWEN_LOGDOMAIN, "Key not found");
01248 return GWEN_ERROR_NOT_FOUND;
01249 }
01250
01251
01252 srcBuf=GWEN_Buffer_new(0, inLen, 0, 0);
01253
01254 if (aid==GWEN_Crypt_PaddAlgoId_Pkcs1_Pss_Sha256) {
01255 const GWEN_CRYPT_TOKEN_KEYINFO *ki;
01256 int nbits;
01257 const uint8_t *modPtr;
01258 uint32_t modLen;
01259 GWEN_MDIGEST *md;
01260
01261 switch(keyId & 0xffff) {
01262 case 1: ki=GWEN_CTF_Context_GetLocalSignKeyInfo(ctx); break;
01263 case 5: ki=GWEN_CTF_Context_GetLocalAuthKeyInfo(ctx); break;
01264 default: ki=NULL;
01265 }
01266
01267 if (ki==NULL) {
01268 DBG_ERROR(GWEN_LOGDOMAIN, "No information for key %d", keyNum);
01269 GWEN_Buffer_free(srcBuf);
01270 return GWEN_ERROR_GENERIC;
01271 }
01272
01273
01274 modPtr=GWEN_Crypt_Token_KeyInfo_GetModulusData(ki);
01275 modLen=GWEN_Crypt_Token_KeyInfo_GetModulusLen(ki);
01276 nbits=modLen*8;
01277 while(modLen && *modPtr==0) {
01278 nbits-=8;
01279 modLen--;
01280 modPtr++;
01281 }
01282 if (modLen) {
01283 uint8_t b=*modPtr;
01284 int i;
01285 uint8_t mask=0x80;
01286
01287 for (i=0; i<8; i++) {
01288 if (b & mask)
01289 break;
01290 nbits--;
01291 mask>>=1;
01292 }
01293 }
01294
01295 if (nbits==0) {
01296 DBG_ERROR(GWEN_LOGDOMAIN, "Empty modulus");
01297 GWEN_Buffer_free(srcBuf);
01298 return GWEN_ERROR_GENERIC;
01299 }
01300
01301 md=GWEN_MDigest_Sha256_new();
01302 GWEN_Buffer_AllocRoom(srcBuf, modLen);
01303
01304 rv=GWEN_Padd_AddPkcs1Pss((uint8_t*) GWEN_Buffer_GetStart(srcBuf),
01305 GWEN_Buffer_GetMaxUnsegmentedWrite(srcBuf),
01306 nbits,
01307 pInData, inLen,
01308 inLen,
01309 md);
01310 GWEN_MDigest_free(md);
01311 if (rv<0) {
01312 DBG_ERROR(GWEN_LOGDOMAIN, "here (%d)", rv);
01313 GWEN_Buffer_free(srcBuf);
01314 return rv;
01315 }
01316
01317 GWEN_Buffer_IncrementPos(srcBuf, rv);
01318 GWEN_Buffer_AdjustUsedBytes(srcBuf);
01319 }
01320 else {
01321 GWEN_Buffer_AppendBytes(srcBuf, (const char*)pInData, inLen);
01322
01323
01324 rv=GWEN_Padd_ApplyPaddAlgo(a, srcBuf);
01325 if (rv) {
01326 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
01327 GWEN_Buffer_free(srcBuf);
01328 return rv;
01329 }
01330 }
01331
01332
01333 rv=GWEN_Crypt_Key_Sign(k,
01334 (const uint8_t*)GWEN_Buffer_GetStart(srcBuf),
01335 GWEN_Buffer_GetUsedBytes(srcBuf),
01336 pSignatureData,
01337 pSignatureLen);
01338 GWEN_Buffer_free(srcBuf);
01339 if (rv) {
01340 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
01341 return rv;
01342 }
01343
01344 if (pSeqCounter) {
01345 GWEN_CRYPT_TOKEN_KEYINFO *ki;
01346
01347
01348 switch(keyId & 0xffff) {
01349 case 1: ki=GWEN_CTF_Context_GetLocalSignKeyInfo(ctx); break;
01350 case 5: ki=GWEN_CTF_Context_GetLocalAuthKeyInfo(ctx); break;
01351 default: ki=NULL;
01352 }
01353 if (ki &&
01354 (GWEN_Crypt_Token_KeyInfo_GetFlags(ki) & GWEN_CRYPT_TOKEN_KEYFLAGS_HASSIGNCOUNTER)) {
01355 unsigned int seq;
01356
01357 seq=GWEN_Crypt_Token_KeyInfo_GetSignCounter(ki);
01358 *pSeqCounter=seq;
01359 GWEN_Crypt_Token_KeyInfo_SetSignCounter(ki, ++seq);
01360
01361 rv=GWEN_Crypt_TokenFile__WriteFile(ct, 0, gid);
01362 if (rv) {
01363 DBG_INFO(GWEN_LOGDOMAIN, "Unable to write file");
01364 return rv;
01365 }
01366 }
01367 else {
01368 DBG_WARN(GWEN_LOGDOMAIN, "No sign counter for key %04x", keyId);
01369 *pSeqCounter=0;
01370 }
01371 }
01372
01373 return 0;
01374 }
01375
01376
01377
01378 int GWENHYWFAR_CB
01379 GWEN_Crypt_TokenFile__Verify(GWEN_CRYPT_TOKEN *ct,
01380 uint32_t keyId,
01381 GWEN_CRYPT_PADDALGO *a,
01382 const uint8_t *pInData,
01383 uint32_t inLen,
01384 const uint8_t *pSignatureData,
01385 uint32_t signatureLen,
01386 uint32_t seqCounter,
01387 uint32_t gid) {
01388 GWEN_CRYPT_TOKEN_FILE *lct;
01389 GWEN_CRYPT_TOKEN_CONTEXT *ctx;
01390 GWEN_CRYPT_KEY *k;
01391 int keyNum;
01392 int i;
01393 int rv;
01394 GWEN_CRYPT_PADDALGOID aid;
01395
01396 assert(ct);
01397 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
01398 assert(lct);
01399
01400 DBG_INFO(GWEN_LOGDOMAIN, "Verifying with key %d", keyId);
01401
01402 aid=GWEN_Crypt_PaddAlgo_GetId(a);
01403
01404
01405 rv=GWEN_Crypt_TokenFile__ReloadIfNeeded(ct, gid);
01406 if (rv) {
01407 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
01408 return rv;
01409 }
01410
01411
01412 i=(keyId>>16);
01413 ctx=GWEN_Crypt_Token_Context_List_First(lct->contextList);
01414 while(ctx) {
01415 if (i==0)
01416 break;
01417 ctx=GWEN_Crypt_Token_Context_List_Next(ctx);
01418 i--;
01419 }
01420
01421 if (ctx==NULL) {
01422 DBG_INFO(GWEN_LOGDOMAIN, "No context by id [%x] known", (keyId>>16) & 0xffff);
01423 return GWEN_ERROR_NOT_FOUND;
01424 }
01425
01426
01427 keyNum=keyId & 0xffff;
01428 if (keyNum!=1 && keyNum!=3 && keyNum!=6) {
01429
01430 DBG_INFO(GWEN_LOGDOMAIN, "Bad key for verifying (%x)", keyId);
01431 return GWEN_ERROR_INVALID;
01432 }
01433
01434 k=GWEN_Crypt_TokenFile__GetKey(ct, keyId, gid);
01435 if (k==NULL) {
01436 DBG_INFO(GWEN_LOGDOMAIN, "Key not found");
01437 return GWEN_ERROR_NO_KEY;
01438 }
01439
01440 if (aid==GWEN_Crypt_PaddAlgoId_Iso9796_2 ||
01441 aid==GWEN_Crypt_PaddAlgoId_Pkcs1_2 ||
01442 aid==GWEN_Crypt_PaddAlgoId_Pkcs1_Pss_Sha256) {
01443 GWEN_BUFFER *tbuf;
01444 uint32_t l;
01445
01446
01447
01448 tbuf=GWEN_Buffer_new(0, signatureLen+16, 0, 0);
01449 l=GWEN_Buffer_GetMaxUnsegmentedWrite(tbuf);
01450 rv=GWEN_Crypt_Key_Encipher(k,
01451 pSignatureData, signatureLen,
01452 (uint8_t*)GWEN_Buffer_GetStart(tbuf),
01453 &l);
01454 if (rv<0) {
01455 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
01456 GWEN_Buffer_free(tbuf);
01457 return rv;
01458 }
01459 GWEN_Buffer_IncrementPos(tbuf, l);
01460 GWEN_Buffer_AdjustUsedBytes(tbuf);
01461
01462 if (aid==GWEN_Crypt_PaddAlgoId_Pkcs1_Pss_Sha256) {
01463 const GWEN_CRYPT_TOKEN_KEYINFO *ki;
01464 int nbits;
01465 const uint8_t *modPtr;
01466 uint32_t modLen;
01467 GWEN_MDIGEST *md;
01468
01469 if (keyNum==3)
01470 ki=GWEN_CTF_Context_GetRemoteSignKeyInfo(ctx);
01471 else
01472 ki=GWEN_CTF_Context_GetRemoteAuthKeyInfo(ctx);
01473 if (ki==NULL) {
01474 DBG_ERROR(GWEN_LOGDOMAIN, "No information for key %d", keyNum);
01475 GWEN_Buffer_free(tbuf);
01476 return GWEN_ERROR_GENERIC;
01477 }
01478
01479
01480 modPtr=GWEN_Crypt_Token_KeyInfo_GetModulusData(ki);
01481 modLen=GWEN_Crypt_Token_KeyInfo_GetModulusLen(ki);
01482 nbits=modLen*8;
01483 while(modLen && *modPtr==0) {
01484 nbits-=8;
01485 modLen--;
01486 modPtr++;
01487 }
01488 if (modLen) {
01489 uint8_t b=*modPtr;
01490 int i;
01491 uint8_t mask=0x80;
01492
01493 for (i=0; i<8; i++) {
01494 if (b & mask)
01495 break;
01496 nbits--;
01497 mask>>=1;
01498 }
01499 }
01500
01501 if (nbits==0) {
01502 DBG_ERROR(GWEN_LOGDOMAIN, "Empty modulus");
01503 GWEN_Buffer_free(tbuf);
01504 return GWEN_ERROR_GENERIC;
01505 }
01506
01507 md=GWEN_MDigest_Sha256_new();
01508 rv=GWEN_Padd_VerifyPkcs1Pss((const uint8_t*) GWEN_Buffer_GetStart(tbuf),
01509 GWEN_Buffer_GetUsedBytes(tbuf),
01510 nbits,
01511 pInData, inLen,
01512 inLen,
01513 md);
01514 GWEN_MDigest_free(md);
01515 if (rv<0) {
01516 DBG_ERROR(GWEN_LOGDOMAIN, "here (%d)", rv);
01517 return rv;
01518 }
01519 }
01520 else {
01521 rv=GWEN_Padd_UnapplyPaddAlgo(a, tbuf);
01522 if (rv<0) {
01523 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
01524 GWEN_Buffer_free(tbuf);
01525 return rv;
01526 }
01527 l=GWEN_Buffer_GetUsedBytes(tbuf);
01528
01529 if (l!=inLen) {
01530 DBG_ERROR(GWEN_LOGDOMAIN, "Signature length doesn't match");
01531 GWEN_Buffer_free(tbuf);
01532 return GWEN_ERROR_VERIFY;
01533 }
01534 if (memcmp(pInData, GWEN_Buffer_GetStart(tbuf), l)!=0) {
01535 DBG_ERROR(GWEN_LOGDOMAIN, "Signature doesn't match:");
01536 GWEN_Buffer_free(tbuf);
01537 return GWEN_ERROR_VERIFY;
01538 }
01539 }
01540 }
01541 else {
01542 GWEN_BUFFER *srcBuf;
01543
01544
01545 srcBuf=GWEN_Buffer_new(0, inLen, 0, 0);
01546 GWEN_Buffer_AppendBytes(srcBuf, (const char*)pInData, inLen);
01547
01548
01549 rv=GWEN_Padd_ApplyPaddAlgo(a, srcBuf);
01550 if (rv) {
01551 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
01552 GWEN_Buffer_free(srcBuf);
01553 return rv;
01554 }
01555
01556
01557 rv=GWEN_Crypt_Key_Verify(k,
01558 (const uint8_t*)GWEN_Buffer_GetStart(srcBuf),
01559 GWEN_Buffer_GetUsedBytes(srcBuf),
01560 pSignatureData,
01561 signatureLen);
01562 GWEN_Buffer_free(srcBuf);
01563 if (rv) {
01564 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
01565 return rv;
01566 }
01567 }
01568
01569 if (seqCounter) {
01570 GWEN_CRYPT_TOKEN_KEYINFO *ki;
01571
01572
01573 if (keyNum==3)
01574 ki=GWEN_CTF_Context_GetRemoteSignKeyInfo(ctx);
01575 else
01576 ki=GWEN_CTF_Context_GetRemoteAuthKeyInfo(ctx);
01577 if (ki &&
01578 (GWEN_Crypt_Token_KeyInfo_GetFlags(ki) & GWEN_CRYPT_TOKEN_KEYFLAGS_HASSIGNCOUNTER)) {
01579 unsigned int seq;
01580
01581 seq=GWEN_Crypt_Token_KeyInfo_GetSignCounter(ki);
01582
01583 if (seq>=seqCounter) {
01584 DBG_WARN(GWEN_LOGDOMAIN, "Bad remote sequence counter (possibly replay attack!)");
01585 return GWEN_ERROR_VERIFY;
01586 }
01587 GWEN_Crypt_Token_KeyInfo_SetSignCounter(ki, seqCounter);
01588
01589
01590 rv=GWEN_Crypt_TokenFile__WriteFile(ct, 0, gid);
01591 if (rv) {
01592 DBG_INFO(GWEN_LOGDOMAIN, "Unable to write file");
01593 return rv;
01594 }
01595 }
01596 else {
01597 DBG_WARN(GWEN_LOGDOMAIN, "No sign counter for key %04x", keyId);
01598 }
01599
01600 }
01601
01602 return 0;
01603 }
01604
01605
01606
01607 int GWENHYWFAR_CB
01608 GWEN_Crypt_TokenFile__Encipher(GWEN_CRYPT_TOKEN *ct,
01609 uint32_t keyId,
01610 GWEN_CRYPT_PADDALGO *a,
01611 const uint8_t *pInData,
01612 uint32_t inLen,
01613 uint8_t *pOutData,
01614 uint32_t *pOutLen,
01615 uint32_t gid) {
01616 GWEN_CRYPT_TOKEN_FILE *lct;
01617 GWEN_CRYPT_TOKEN_CONTEXT *ctx;
01618 GWEN_CRYPT_KEY *k;
01619 int keyNum;
01620 GWEN_BUFFER *srcBuf;
01621 int i;
01622 int rv;
01623
01624 assert(ct);
01625 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
01626 assert(lct);
01627
01628 DBG_INFO(GWEN_LOGDOMAIN, "Enciphering with key %d", keyId);
01629
01630
01631 rv=GWEN_Crypt_TokenFile__ReloadIfNeeded(ct, gid);
01632 if (rv) {
01633 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
01634 return rv;
01635 }
01636
01637
01638 i=(keyId>>16);
01639 ctx=GWEN_Crypt_Token_Context_List_First(lct->contextList);
01640 while(ctx) {
01641 if (i==0)
01642 break;
01643 ctx=GWEN_Crypt_Token_Context_List_Next(ctx);
01644 i--;
01645 }
01646
01647 if (ctx==NULL) {
01648 DBG_INFO(GWEN_LOGDOMAIN, "No context by id [%x] known", (keyId>>16) & 0xffff);
01649 return GWEN_ERROR_NOT_FOUND;
01650 }
01651
01652
01653 keyNum=keyId & 0xffff;
01654 if (keyNum!=2 && keyNum!=4) {
01655
01656 DBG_INFO(GWEN_LOGDOMAIN, "Bad key for encrypting (%x)", keyId);
01657 return GWEN_ERROR_INVALID;
01658 }
01659
01660 k=GWEN_Crypt_TokenFile__GetKey(ct, keyId, gid);
01661 if (k==NULL) {
01662 DBG_INFO(GWEN_LOGDOMAIN, "Key %d not found", keyId);
01663 return GWEN_ERROR_NOT_FOUND;
01664 }
01665
01666
01667 srcBuf=GWEN_Buffer_new(0, inLen, 0, 0);
01668 GWEN_Buffer_AppendBytes(srcBuf, (const char*)pInData, inLen);
01669 GWEN_Buffer_Rewind(srcBuf);
01670
01671
01672 rv=GWEN_Padd_ApplyPaddAlgo(a, srcBuf);
01673 if (rv) {
01674 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
01675 GWEN_Buffer_free(srcBuf);
01676 return rv;
01677 }
01678
01679
01680 rv=GWEN_Crypt_Key_Encipher(k,
01681 (const uint8_t*)GWEN_Buffer_GetStart(srcBuf),
01682 GWEN_Buffer_GetUsedBytes(srcBuf),
01683 pOutData,
01684 pOutLen);
01685 GWEN_Buffer_free(srcBuf);
01686 if (rv) {
01687 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
01688 return rv;
01689 }
01690
01691 return 0;
01692 }
01693
01694
01695
01696 int GWENHYWFAR_CB
01697 GWEN_Crypt_TokenFile__Decipher(GWEN_CRYPT_TOKEN *ct,
01698 uint32_t keyId,
01699 GWEN_CRYPT_PADDALGO *a,
01700 const uint8_t *pInData,
01701 uint32_t inLen,
01702 uint8_t *pOutData,
01703 uint32_t *pOutLen,
01704 uint32_t gid) {
01705 GWEN_CRYPT_TOKEN_FILE *lct;
01706 GWEN_CRYPT_TOKEN_CONTEXT *ctx;
01707 GWEN_CRYPT_KEY *k;
01708 int keyNum;
01709 GWEN_BUFFER *tbuf;
01710 int i;
01711 int rv;
01712 uint32_t l;
01713
01714 assert(ct);
01715 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
01716 assert(lct);
01717
01718 DBG_INFO(GWEN_LOGDOMAIN, "Deciphering with key %d", keyId);
01719
01720
01721 rv=GWEN_Crypt_TokenFile__ReloadIfNeeded(ct, gid);
01722 if (rv) {
01723 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
01724 return rv;
01725 }
01726
01727
01728 i=(keyId>>16);
01729 ctx=GWEN_Crypt_Token_Context_List_First(lct->contextList);
01730 while(ctx) {
01731 if (i==0)
01732 break;
01733 ctx=GWEN_Crypt_Token_Context_List_Next(ctx);
01734 i--;
01735 }
01736
01737 if (ctx==NULL) {
01738 DBG_INFO(GWEN_LOGDOMAIN, "No context by id [%x] known", (keyId>>16) & 0xffff);
01739 return GWEN_ERROR_NOT_FOUND;
01740 }
01741
01742
01743 keyNum=keyId & 0xffff;
01744 if (keyNum!=2 && keyNum!=4) {
01745
01746 DBG_INFO(GWEN_LOGDOMAIN, "Bad key for decrypting (%x)", keyId);
01747 return GWEN_ERROR_INVALID;
01748 }
01749
01750 k=GWEN_Crypt_TokenFile__GetKey(ct, keyId, gid);
01751 if (k==NULL) {
01752 DBG_INFO(GWEN_LOGDOMAIN, "Key not found");
01753 return GWEN_ERROR_NOT_FOUND;
01754 }
01755
01756
01757 tbuf=GWEN_Buffer_new(0, inLen+16, 0, 1);
01758 l=GWEN_Buffer_GetMaxUnsegmentedWrite(tbuf);
01759 rv=GWEN_Crypt_Key_Decipher(k,
01760 pInData, inLen,
01761 (uint8_t*)GWEN_Buffer_GetStart(tbuf), &l);
01762 if (rv<0) {
01763 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
01764 GWEN_Buffer_free(tbuf);
01765 return rv;
01766 }
01767 GWEN_Buffer_IncrementPos(tbuf, l);
01768 GWEN_Buffer_AdjustUsedBytes(tbuf);
01769
01770
01771 rv=GWEN_Padd_UnapplyPaddAlgo(a, tbuf);
01772 if (rv) {
01773 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
01774 GWEN_Buffer_free(tbuf);
01775 return rv;
01776 }
01777
01778
01779 l=GWEN_Buffer_GetUsedBytes(tbuf);
01780 if (l>*pOutLen) {
01781 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
01782 GWEN_Buffer_free(tbuf);
01783 return GWEN_ERROR_BUFFER_OVERFLOW;
01784 }
01785 memmove(pOutData, GWEN_Buffer_GetStart(tbuf), l);
01786 *pOutLen=l;
01787 GWEN_Buffer_free(tbuf);
01788
01789 return 0;
01790 }
01791
01792
01793
01794 int GWENHYWFAR_CB
01795 GWEN_Crypt_TokenFile__GenerateKey(GWEN_CRYPT_TOKEN *ct,
01796 uint32_t keyId,
01797 const GWEN_CRYPT_CRYPTALGO *a,
01798 uint32_t gid) {
01799 GWEN_CRYPT_TOKEN_FILE *lct;
01800 GWEN_CRYPT_KEY *pubKey;
01801 GWEN_CRYPT_KEY *secKey;
01802 int rv;
01803 uint32_t keyNum;
01804 GWEN_CRYPT_TOKEN_CONTEXT *ctx;
01805 int i;
01806 uint8_t kbuf[256];
01807 uint32_t klen;
01808 GWEN_CRYPT_TOKEN_KEYINFO *cki;
01809 GWEN_CRYPT_TOKEN_KEYINFO *ki;
01810 int sizeInBits;
01811
01812 assert(ct);
01813 lct=GWEN_INHERIT_GETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct);
01814 assert(lct);
01815
01816
01817 rv=GWEN_Crypt_TokenFile__ReloadIfNeeded(ct, gid);
01818 if (rv) {
01819 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
01820 return rv;
01821 }
01822
01823 keyNum=keyId & 0xffff;
01824
01825
01826 if (keyNum!=1 && keyNum!=2 && keyNum!=5) {
01827 DBG_INFO(GWEN_LOGDOMAIN, "Can only generate local keys.");
01828 GWEN_Gui_ProgressLog(gid, GWEN_LoggerLevel_Error,
01829 I18N("Can only generate local keys."));
01830 return GWEN_ERROR_NOT_SUPPORTED;
01831 }
01832
01833
01834 if (GWEN_Crypt_CryptAlgo_GetId(a)!=GWEN_Crypt_CryptAlgoId_Rsa) {
01835 DBG_INFO(GWEN_LOGDOMAIN, "Only RSA keys supported.");
01836 GWEN_Gui_ProgressLog(gid, GWEN_LoggerLevel_Error,
01837 I18N("Only RSA keys supported."));
01838 return GWEN_ERROR_NOT_SUPPORTED;
01839 }
01840
01841
01842 i=(keyId>>16);
01843 ctx=GWEN_Crypt_Token_Context_List_First(lct->contextList);
01844 while(ctx) {
01845 if (i==0)
01846 break;
01847 ctx=GWEN_Crypt_Token_Context_List_Next(ctx);
01848 i--;
01849 }
01850
01851 sizeInBits=GWEN_Crypt_CryptAlgo_GetKeySizeInBits(a);
01852 if (sizeInBits>0) {
01853
01854 DBG_DEBUG(GWEN_LOGDOMAIN, "Creating key pair using %d bits", sizeInBits);
01855 rv=GWEN_Crypt_KeyRsa_GeneratePair2(sizeInBits,
01856 (GWEN_Crypt_Token_GetModes(ct) &
01857 GWEN_CRYPT_TOKEN_MODE_EXP_65537)?1:0,
01858 &pubKey,
01859 &secKey);
01860 }
01861 else {
01862
01863 DBG_INFO(GWEN_LOGDOMAIN, "Creating key pair using %d bytes", GWEN_Crypt_CryptAlgo_GetChunkSize(a));
01864 rv=GWEN_Crypt_KeyRsa_GeneratePair(GWEN_Crypt_CryptAlgo_GetChunkSize(a),
01865 (GWEN_Crypt_Token_GetModes(ct) &
01866 GWEN_CRYPT_TOKEN_MODE_EXP_65537)?1:0,
01867 &pubKey,
01868 &secKey);
01869 }
01870 if (rv) {
01871 DBG_INFO(GWEN_LOGDOMAIN, "here (%d)", rv);
01872 GWEN_Gui_ProgressLog(gid, GWEN_LoggerLevel_Error,
01873 I18N("Could not generate key"));
01874 return rv;
01875 }
01876
01877 GWEN_Gui_ProgressLog(gid, GWEN_LoggerLevel_Notice,
01878 I18N("Key generated"));
01879
01880
01881 if (keyNum==1)
01882 cki=GWEN_CTF_Context_GetLocalSignKeyInfo(ctx);
01883 else if (keyNum==3)
01884 cki=GWEN_CTF_Context_GetLocalCryptKeyInfo(ctx);
01885 else
01886 cki=GWEN_CTF_Context_GetLocalAuthKeyInfo(ctx);
01887 if (cki==NULL) {
01888 GWEN_Gui_ProgressLog(gid, GWEN_LoggerLevel_Error,
01889 I18N("No key info found"));
01890 return GWEN_ERROR_NO_DATA;
01891 }
01892
01893
01894 ki=GWEN_Crypt_Token_KeyInfo_dup(cki);
01895 assert(ki);
01896
01897
01898 klen=sizeof(kbuf);
01899 rv=GWEN_Crypt_KeyRsa_GetModulus(pubKey, kbuf, &klen);
01900 if (rv) {
01901 DBG_INFO(GWEN_LOGDOMAIN, "No modulus for key");
01902 GWEN_Crypt_Token_KeyInfo_free(ki);
01903 GWEN_Crypt_Key_free(pubKey);
01904 return rv;
01905 }
01906 GWEN_Crypt_Token_KeyInfo_SetModulus(ki, kbuf, klen);
01907
01908
01909 klen=sizeof(kbuf);
01910 rv=GWEN_Crypt_KeyRsa_GetExponent(pubKey, kbuf, &klen);
01911 if (rv) {
01912 DBG_INFO(GWEN_LOGDOMAIN, "No exponent for key");
01913 GWEN_Crypt_Token_KeyInfo_free(ki);
01914 GWEN_Crypt_Key_free(pubKey);
01915 return rv;
01916 }
01917 GWEN_Crypt_Token_KeyInfo_SetExponent(ki, kbuf, klen);
01918 GWEN_Crypt_Token_KeyInfo_SetKeyNumber(ki, GWEN_Crypt_Key_GetKeyNumber(pubKey));
01919 GWEN_Crypt_Token_KeyInfo_SetKeyVersion(ki, GWEN_Crypt_Key_GetKeyVersion(pubKey));
01920
01921 if (keyNum==1) {
01922 if (GWEN_Crypt_Token_GetModes(ct) & GWEN_CRYPT_TOKEN_MODE_DIRECT_SIGN){
01923 DBG_DEBUG(GWEN_LOGDOMAIN, "Adding mode \"direct sign\" to key");
01924 GWEN_Crypt_KeyRsa_AddFlags(secKey, GWEN_CRYPT_KEYRSA_FLAGS_DIRECTSIGN);
01925 }
01926 GWEN_CTF_Context_SetLocalSignKey(ctx, secKey);
01927 GWEN_Crypt_Token_KeyInfo_AddFlags(ki,
01928 GWEN_CRYPT_TOKEN_KEYFLAGS_HASMODULUS |
01929 GWEN_CRYPT_TOKEN_KEYFLAGS_HASEXPONENT |
01930 GWEN_CRYPT_TOKEN_KEYFLAGS_HASKEYNUMBER |
01931 GWEN_CRYPT_TOKEN_KEYFLAGS_HASKEYVERSION |
01932 GWEN_CRYPT_TOKEN_KEYFLAGS_HASSIGNCOUNTER |
01933 GWEN_CRYPT_TOKEN_KEYFLAGS_HASACTIONFLAGS |
01934 GWEN_CRYPT_TOKEN_KEYFLAGS_CANVERIFY |
01935 GWEN_CRYPT_TOKEN_KEYFLAGS_CANSIGN);
01936 GWEN_Crypt_Token_KeyInfo_SetSignCounter(ki, 1);
01937 GWEN_CTF_Context_SetLocalSignKeyInfo(ctx, ki);
01938 }
01939 else if (keyNum==2) {
01940 GWEN_CTF_Context_SetLocalCryptKey(ctx, secKey);
01941 GWEN_Crypt_Token_KeyInfo_AddFlags(ki,
01942 GWEN_CRYPT_TOKEN_KEYFLAGS_HASMODULUS |
01943 GWEN_CRYPT_TOKEN_KEYFLAGS_HASEXPONENT |
01944 GWEN_CRYPT_TOKEN_KEYFLAGS_HASKEYNUMBER |
01945 GWEN_CRYPT_TOKEN_KEYFLAGS_HASKEYVERSION |
01946 GWEN_CRYPT_TOKEN_KEYFLAGS_HASSIGNCOUNTER |
01947 GWEN_CRYPT_TOKEN_KEYFLAGS_HASACTIONFLAGS |
01948 GWEN_CRYPT_TOKEN_KEYFLAGS_CANENCIPHER |
01949 GWEN_CRYPT_TOKEN_KEYFLAGS_CANDECIPHER);
01950 GWEN_CTF_Context_SetLocalCryptKeyInfo(ctx, ki);
01951 }
01952 else {
01953 if (GWEN_Crypt_Token_GetModes(ct) & GWEN_CRYPT_TOKEN_MODE_DIRECT_SIGN){
01954 DBG_DEBUG(GWEN_LOGDOMAIN, "Adding mode \"direct sign\" to key");
01955 GWEN_Crypt_KeyRsa_AddFlags(secKey, GWEN_CRYPT_KEYRSA_FLAGS_DIRECTSIGN);
01956 }
01957 GWEN_CTF_Context_SetLocalAuthKey(ctx, secKey);
01958 GWEN_Crypt_Token_KeyInfo_AddFlags(ki,
01959 GWEN_CRYPT_TOKEN_KEYFLAGS_HASMODULUS |
01960 GWEN_CRYPT_TOKEN_KEYFLAGS_HASEXPONENT |
01961 GWEN_CRYPT_TOKEN_KEYFLAGS_HASKEYNUMBER |
01962 GWEN_CRYPT_TOKEN_KEYFLAGS_HASKEYVERSION |
01963 GWEN_CRYPT_TOKEN_KEYFLAGS_HASSIGNCOUNTER |
01964 GWEN_CRYPT_TOKEN_KEYFLAGS_HASACTIONFLAGS |
01965 GWEN_CRYPT_TOKEN_KEYFLAGS_CANVERIFY |
01966 GWEN_CRYPT_TOKEN_KEYFLAGS_CANSIGN);
01967 GWEN_Crypt_Token_KeyInfo_SetSignCounter(ki, 1);
01968 GWEN_CTF_Context_SetLocalAuthKeyInfo(ctx, ki);
01969 }
01970
01971
01972 GWEN_Crypt_Key_free(pubKey);
01973
01974 rv=GWEN_Crypt_TokenFile__WriteFile(ct, 0, gid);
01975 if (rv) {
01976 DBG_INFO(GWEN_LOGDOMAIN, "Unable to write file");
01977 GWEN_Gui_ProgressLog(gid, GWEN_LoggerLevel_Error,
01978 I18N("Unable to write key file"));
01979 return rv;
01980 }
01981
01982 GWEN_Gui_ProgressLog(gid, GWEN_LoggerLevel_Notice,
01983 I18N("Key generated and set"));
01984
01985 return 0;
01986 }
01987
01988
01989
01990
01991
01992
01993 GWENHYWFAR_CB
01994 void GWEN_Crypt_TokenFile_freeData(GWEN_UNUSED void *bp, void *p) {
01995 GWEN_CRYPT_TOKEN_FILE *lct;
01996
01997 lct=(GWEN_CRYPT_TOKEN_FILE*) p;
01998 GWEN_Crypt_Token_Context_List_free(lct->contextList);
01999
02000 GWEN_FREE_OBJECT(lct);
02001 }
02002
02003
02004
02005 GWEN_CRYPT_TOKEN *GWEN_Crypt_TokenFile_new(const char *typeName,
02006 const char *tokenName) {
02007 GWEN_CRYPT_TOKEN *ct;
02008 GWEN_CRYPT_TOKEN_FILE *lct;
02009
02010 ct=GWEN_Crypt_Token_new(GWEN_Crypt_Token_Device_File, typeName, tokenName);
02011 assert(ct);
02012
02013 GWEN_NEW_OBJECT(GWEN_CRYPT_TOKEN_FILE, lct);
02014 lct->contextList=GWEN_Crypt_Token_Context_List_new();
02015 GWEN_INHERIT_SETDATA(GWEN_CRYPT_TOKEN, GWEN_CRYPT_TOKEN_FILE, ct, lct,
02016 GWEN_Crypt_TokenFile_freeData);
02017 GWEN_Crypt_Token_SetOpenFn(ct, GWEN_Crypt_TokenFile_Open);
02018 GWEN_Crypt_Token_SetCreateFn(ct, GWEN_Crypt_TokenFile_Create);
02019 GWEN_Crypt_Token_SetCloseFn(ct, GWEN_Crypt_TokenFile_Close);
02020 GWEN_Crypt_Token_SetGetKeyIdListFn(ct, GWEN_Crypt_TokenFile__GetKeyIdList);
02021 GWEN_Crypt_Token_SetGetKeyInfoFn(ct, GWEN_Crypt_TokenFile__GetKeyInfo);
02022 GWEN_Crypt_Token_SetSetKeyInfoFn(ct, GWEN_Crypt_TokenFile__SetKeyInfo);
02023 GWEN_Crypt_Token_SetGetContextIdListFn(ct, GWEN_Crypt_TokenFile__GetContextIdList);
02024 GWEN_Crypt_Token_SetGetContextFn(ct, GWEN_Crypt_TokenFile__GetContext);
02025 GWEN_Crypt_Token_SetSetContextFn(ct, GWEN_Crypt_TokenFile__SetContext);
02026 GWEN_Crypt_Token_SetSignFn(ct, GWEN_Crypt_TokenFile__Sign);
02027 GWEN_Crypt_Token_SetVerifyFn(ct, GWEN_Crypt_TokenFile__Verify);
02028 GWEN_Crypt_Token_SetEncipherFn(ct, GWEN_Crypt_TokenFile__Encipher);
02029 GWEN_Crypt_Token_SetDecipherFn(ct, GWEN_Crypt_TokenFile__Decipher);
02030 GWEN_Crypt_Token_SetGenerateKeyFn(ct, GWEN_Crypt_TokenFile__GenerateKey);
02031
02032 return ct;
02033 }
02034
02035
02036
02037
02038