1 /* This Source Code Form is subject to the terms of the Mozilla Public
2  * License, v. 2.0. If a copy of the MPL was not distributed with this
3  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
4 
5 /*
6  * wrap.c
7  *
8  * This file contains the routines that actually implement the cryptoki
9  * API, using the internal APIs of the NSS Cryptoki Framework.  There is
10  * one routine here for every cryptoki routine.  For linking reasons
11  * the actual entry points passed back with C_GetFunctionList have to
12  * exist in one of the Module's source files; however, those are merely
13  * simple wrappers that call these routines.  The intelligence of the
14  * implementations is here.
15  */
16 
17 #ifndef CK_T
18 #include "ck.h"
19 #endif /* CK_T */
20 
21 /*
22  * NSSCKFWC_Initialize
23  * NSSCKFWC_Finalize
24  * NSSCKFWC_GetInfo
25  * -- NSSCKFWC_GetFunctionList -- see the API insert file
26  * NSSCKFWC_GetSlotList
27  * NSSCKFWC_GetSlotInfo
28  * NSSCKFWC_GetTokenInfo
29  * NSSCKFWC_WaitForSlotEvent
30  * NSSCKFWC_GetMechanismList
31  * NSSCKFWC_GetMechanismInfo
32  * NSSCKFWC_InitToken
33  * NSSCKFWC_InitPIN
34  * NSSCKFWC_SetPIN
35  * NSSCKFWC_OpenSession
36  * NSSCKFWC_CloseSession
37  * NSSCKFWC_CloseAllSessions
38  * NSSCKFWC_GetSessionInfo
39  * NSSCKFWC_GetOperationState
40  * NSSCKFWC_SetOperationState
41  * NSSCKFWC_Login
42  * NSSCKFWC_Logout
43  * NSSCKFWC_CreateObject
44  * NSSCKFWC_CopyObject
45  * NSSCKFWC_DestroyObject
46  * NSSCKFWC_GetObjectSize
47  * NSSCKFWC_GetAttributeValue
48  * NSSCKFWC_SetAttributeValue
49  * NSSCKFWC_FindObjectsInit
50  * NSSCKFWC_FindObjects
51  * NSSCKFWC_FindObjectsFinal
52  * NSSCKFWC_EncryptInit
53  * NSSCKFWC_Encrypt
54  * NSSCKFWC_EncryptUpdate
55  * NSSCKFWC_EncryptFinal
56  * NSSCKFWC_DecryptInit
57  * NSSCKFWC_Decrypt
58  * NSSCKFWC_DecryptUpdate
59  * NSSCKFWC_DecryptFinal
60  * NSSCKFWC_DigestInit
61  * NSSCKFWC_Digest
62  * NSSCKFWC_DigestUpdate
63  * NSSCKFWC_DigestKey
64  * NSSCKFWC_DigestFinal
65  * NSSCKFWC_SignInit
66  * NSSCKFWC_Sign
67  * NSSCKFWC_SignUpdate
68  * NSSCKFWC_SignFinal
69  * NSSCKFWC_SignRecoverInit
70  * NSSCKFWC_SignRecover
71  * NSSCKFWC_VerifyInit
72  * NSSCKFWC_Verify
73  * NSSCKFWC_VerifyUpdate
74  * NSSCKFWC_VerifyFinal
75  * NSSCKFWC_VerifyRecoverInit
76  * NSSCKFWC_VerifyRecover
77  * NSSCKFWC_DigestEncryptUpdate
78  * NSSCKFWC_DecryptDigestUpdate
79  * NSSCKFWC_SignEncryptUpdate
80  * NSSCKFWC_DecryptVerifyUpdate
81  * NSSCKFWC_GenerateKey
82  * NSSCKFWC_GenerateKeyPair
83  * NSSCKFWC_WrapKey
84  * NSSCKFWC_UnwrapKey
85  * NSSCKFWC_DeriveKey
86  * NSSCKFWC_SeedRandom
87  * NSSCKFWC_GenerateRandom
88  * NSSCKFWC_GetFunctionStatus
89  * NSSCKFWC_CancelFunction
90  */
91 
92 /* figure out out locking semantics */
93 static CK_RV
nssCKFW_GetThreadSafeState(CK_C_INITIALIZE_ARGS_PTR pInitArgs,CryptokiLockingState * pLocking_state)94 nssCKFW_GetThreadSafeState(CK_C_INITIALIZE_ARGS_PTR pInitArgs,
95                            CryptokiLockingState *pLocking_state)
96 {
97     int functionCount = 0;
98 
99     /* parsed according to (PKCS #11 Section 11.4) */
100     /* no args, the degenerate version of case 1 */
101     if (!pInitArgs) {
102         *pLocking_state = SingleThreaded;
103         return CKR_OK;
104     }
105 
106     /* CKF_OS_LOCKING_OK set, Cases 2 and 4 */
107     if (pInitArgs->flags & CKF_OS_LOCKING_OK) {
108         *pLocking_state = MultiThreaded;
109         return CKR_OK;
110     }
111     if ((CK_CREATEMUTEX)NULL != pInitArgs->CreateMutex)
112         functionCount++;
113     if ((CK_DESTROYMUTEX)NULL != pInitArgs->DestroyMutex)
114         functionCount++;
115     if ((CK_LOCKMUTEX)NULL != pInitArgs->LockMutex)
116         functionCount++;
117     if ((CK_UNLOCKMUTEX)NULL != pInitArgs->UnlockMutex)
118         functionCount++;
119 
120     /* CKF_OS_LOCKING_OK is not set, and not functions supplied,
121      * explicit case 1 */
122     if (0 == functionCount) {
123         *pLocking_state = SingleThreaded;
124         return CKR_OK;
125     }
126 
127     /* OS_LOCKING_OK is not set and functions have been supplied. Since
128      * ckfw uses nssbase library which explicitly calls NSPR, and since
129      * there is no way to reliably override these explicit calls to NSPR,
130      * therefore we can't support applications which have their own threading
131      * module.  Return CKR_CANT_LOCK if they supplied the correct number of
132      * arguments, or CKR_ARGUMENTS_BAD if they did not in either case we will
133      * fail the initialize */
134     return (4 == functionCount) ? CKR_CANT_LOCK : CKR_ARGUMENTS_BAD;
135 }
136 
137 static PRInt32 liveInstances;
138 
139 /*
140  * NSSCKFWC_Initialize
141  *
142  */
143 NSS_IMPLEMENT CK_RV
NSSCKFWC_Initialize(NSSCKFWInstance ** pFwInstance,NSSCKMDInstance * mdInstance,CK_VOID_PTR pInitArgs)144 NSSCKFWC_Initialize(
145     NSSCKFWInstance **pFwInstance,
146     NSSCKMDInstance *mdInstance,
147     CK_VOID_PTR pInitArgs)
148 {
149     CK_RV error = CKR_OK;
150     CryptokiLockingState locking_state;
151 
152     if ((NSSCKFWInstance **)NULL == pFwInstance) {
153         error = CKR_GENERAL_ERROR;
154         goto loser;
155     }
156 
157     if (*pFwInstance) {
158         error = CKR_CRYPTOKI_ALREADY_INITIALIZED;
159         goto loser;
160     }
161 
162     if (!mdInstance) {
163         error = CKR_GENERAL_ERROR;
164         goto loser;
165     }
166 
167     error = nssCKFW_GetThreadSafeState(pInitArgs, &locking_state);
168     if (CKR_OK != error) {
169         goto loser;
170     }
171 
172     *pFwInstance = nssCKFWInstance_Create(pInitArgs, locking_state, mdInstance, &error);
173     if (!*pFwInstance) {
174         goto loser;
175     }
176     PR_ATOMIC_INCREMENT(&liveInstances);
177     return CKR_OK;
178 
179 loser:
180     switch (error) {
181         case CKR_ARGUMENTS_BAD:
182         case CKR_CANT_LOCK:
183         case CKR_CRYPTOKI_ALREADY_INITIALIZED:
184         case CKR_FUNCTION_FAILED:
185         case CKR_GENERAL_ERROR:
186         case CKR_HOST_MEMORY:
187         case CKR_NEED_TO_CREATE_THREADS:
188             break;
189         default:
190         case CKR_OK:
191             error = CKR_GENERAL_ERROR;
192             break;
193     }
194 
195     return error;
196 }
197 
198 /*
199  * NSSCKFWC_Finalize
200  *
201  */
202 NSS_IMPLEMENT CK_RV
NSSCKFWC_Finalize(NSSCKFWInstance ** pFwInstance)203 NSSCKFWC_Finalize(
204     NSSCKFWInstance **pFwInstance)
205 {
206     CK_RV error = CKR_OK;
207 
208     if ((NSSCKFWInstance **)NULL == pFwInstance) {
209         error = CKR_GENERAL_ERROR;
210         goto loser;
211     }
212 
213     if (!*pFwInstance) {
214         error = CKR_CRYPTOKI_NOT_INITIALIZED;
215         goto loser;
216     }
217 
218     error = nssCKFWInstance_Destroy(*pFwInstance);
219 
220     /* In any case */
221     *pFwInstance = (NSSCKFWInstance *)NULL;
222 
223 loser:
224     switch (error) {
225         PRInt32 remainingInstances;
226         case CKR_OK:
227             remainingInstances = PR_ATOMIC_DECREMENT(&liveInstances);
228             if (!remainingInstances) {
229                 nssArena_Shutdown();
230             }
231             break;
232         case CKR_CRYPTOKI_NOT_INITIALIZED:
233         case CKR_FUNCTION_FAILED:
234         case CKR_GENERAL_ERROR:
235         case CKR_HOST_MEMORY:
236             break;
237         default:
238             error = CKR_GENERAL_ERROR;
239             break;
240     }
241 
242     /*
243      * A thread's error stack is automatically destroyed when the thread
244      * terminates or, for the primordial thread, by PR_Cleanup.  On
245      * Windows with MinGW, the thread private data destructor PR_Free
246      * registered by this module is actually a thunk for PR_Free defined
247      * in this module.  When the thread that unloads this module terminates
248      * or calls PR_Cleanup, the thunk for PR_Free is already gone with the
249      * module.  Therefore we need to destroy the error stack before the
250      * module is unloaded.
251      */
252     nss_DestroyErrorStack();
253     return error;
254 }
255 
256 /*
257  * NSSCKFWC_GetInfo
258  *
259  */
260 NSS_IMPLEMENT CK_RV
NSSCKFWC_GetInfo(NSSCKFWInstance * fwInstance,CK_INFO_PTR pInfo)261 NSSCKFWC_GetInfo(
262     NSSCKFWInstance *fwInstance,
263     CK_INFO_PTR pInfo)
264 {
265     CK_RV error = CKR_OK;
266 
267     if ((CK_INFO_PTR)CK_NULL_PTR == pInfo) {
268         error = CKR_ARGUMENTS_BAD;
269         goto loser;
270     }
271 
272     /*
273      * A purify error here means a caller error
274      */
275     (void)nsslibc_memset(pInfo, 0, sizeof(CK_INFO));
276 
277     pInfo->cryptokiVersion = nssCKFWInstance_GetCryptokiVersion(fwInstance);
278 
279     error = nssCKFWInstance_GetManufacturerID(fwInstance, pInfo->manufacturerID);
280     if (CKR_OK != error) {
281         goto loser;
282     }
283 
284     pInfo->flags = nssCKFWInstance_GetFlags(fwInstance);
285 
286     error = nssCKFWInstance_GetLibraryDescription(fwInstance, pInfo->libraryDescription);
287     if (CKR_OK != error) {
288         goto loser;
289     }
290 
291     pInfo->libraryVersion = nssCKFWInstance_GetLibraryVersion(fwInstance);
292 
293     return CKR_OK;
294 
295 loser:
296     switch (error) {
297         case CKR_CRYPTOKI_NOT_INITIALIZED:
298         case CKR_FUNCTION_FAILED:
299         case CKR_GENERAL_ERROR:
300         case CKR_HOST_MEMORY:
301             break;
302         default:
303             error = CKR_GENERAL_ERROR;
304             break;
305     }
306 
307     return error;
308 }
309 
310 /*
311  * C_GetFunctionList is implemented entirely in the Module's file which
312  * includes the Framework API insert file.  It requires no "actual"
313  * NSSCKFW routine.
314  */
315 
316 /*
317  * NSSCKFWC_GetSlotList
318  *
319  */
320 NSS_IMPLEMENT CK_RV
NSSCKFWC_GetSlotList(NSSCKFWInstance * fwInstance,CK_BBOOL tokenPresent,CK_SLOT_ID_PTR pSlotList,CK_ULONG_PTR pulCount)321 NSSCKFWC_GetSlotList(
322     NSSCKFWInstance *fwInstance,
323     CK_BBOOL tokenPresent,
324     CK_SLOT_ID_PTR pSlotList,
325     CK_ULONG_PTR pulCount)
326 {
327     CK_RV error = CKR_OK;
328     CK_ULONG nSlots;
329 
330     if (!fwInstance) {
331         error = CKR_CRYPTOKI_NOT_INITIALIZED;
332         goto loser;
333     }
334 
335     switch (tokenPresent) {
336         case CK_TRUE:
337         case CK_FALSE:
338             break;
339         default:
340             error = CKR_ARGUMENTS_BAD;
341             goto loser;
342     }
343 
344     if ((CK_ULONG_PTR)CK_NULL_PTR == pulCount) {
345         error = CKR_ARGUMENTS_BAD;
346         goto loser;
347     }
348 
349     nSlots = nssCKFWInstance_GetNSlots(fwInstance, &error);
350     if ((CK_ULONG)0 == nSlots) {
351         goto loser;
352     }
353 
354     if ((CK_SLOT_ID_PTR)CK_NULL_PTR == pSlotList) {
355         *pulCount = nSlots;
356         return CKR_OK;
357     }
358 
359     /*
360      * A purify error here indicates caller error.
361      */
362     (void)nsslibc_memset(pSlotList, 0, *pulCount * sizeof(CK_SLOT_ID));
363 
364     if (*pulCount < nSlots) {
365         *pulCount = nSlots;
366         error = CKR_BUFFER_TOO_SMALL;
367         goto loser;
368     } else {
369         CK_ULONG i;
370         *pulCount = nSlots;
371 
372         /*
373          * Our secret "mapping": CK_SLOT_IDs are integers [1,N], and we
374          * just index one when we need it.
375          */
376 
377         for (i = 0; i < nSlots; i++) {
378             pSlotList[i] = i + 1;
379         }
380 
381         return CKR_OK;
382     }
383 
384 loser:
385     switch (error) {
386         case CKR_BUFFER_TOO_SMALL:
387         case CKR_CRYPTOKI_NOT_INITIALIZED:
388         case CKR_FUNCTION_FAILED:
389         case CKR_GENERAL_ERROR:
390         case CKR_HOST_MEMORY:
391             break;
392         default:
393         case CKR_OK:
394             error = CKR_GENERAL_ERROR;
395             break;
396     }
397 
398     return error;
399 }
400 
401 /*
402  * NSSCKFWC_GetSlotInfo
403  *
404  */
405 NSS_IMPLEMENT CK_RV
NSSCKFWC_GetSlotInfo(NSSCKFWInstance * fwInstance,CK_SLOT_ID slotID,CK_SLOT_INFO_PTR pInfo)406 NSSCKFWC_GetSlotInfo(
407     NSSCKFWInstance *fwInstance,
408     CK_SLOT_ID slotID,
409     CK_SLOT_INFO_PTR pInfo)
410 {
411     CK_RV error = CKR_OK;
412     CK_ULONG nSlots;
413     NSSCKFWSlot **slots;
414     NSSCKFWSlot *fwSlot;
415 
416     if (!fwInstance) {
417         error = CKR_CRYPTOKI_NOT_INITIALIZED;
418         goto loser;
419     }
420 
421     nSlots = nssCKFWInstance_GetNSlots(fwInstance, &error);
422     if ((CK_ULONG)0 == nSlots) {
423         goto loser;
424     }
425 
426     if ((slotID < 1) || (slotID > nSlots)) {
427         error = CKR_SLOT_ID_INVALID;
428         goto loser;
429     }
430 
431     if ((CK_SLOT_INFO_PTR)CK_NULL_PTR == pInfo) {
432         error = CKR_ARGUMENTS_BAD;
433         goto loser;
434     }
435 
436     /*
437      * A purify error here indicates caller error.
438      */
439     (void)nsslibc_memset(pInfo, 0, sizeof(CK_SLOT_INFO));
440 
441     slots = nssCKFWInstance_GetSlots(fwInstance, &error);
442     if ((NSSCKFWSlot **)NULL == slots) {
443         goto loser;
444     }
445 
446     fwSlot = slots[slotID - 1];
447 
448     error = nssCKFWSlot_GetSlotDescription(fwSlot, pInfo->slotDescription);
449     if (CKR_OK != error) {
450         goto loser;
451     }
452 
453     error = nssCKFWSlot_GetManufacturerID(fwSlot, pInfo->manufacturerID);
454     if (CKR_OK != error) {
455         goto loser;
456     }
457 
458     if (nssCKFWSlot_GetTokenPresent(fwSlot)) {
459         pInfo->flags |= CKF_TOKEN_PRESENT;
460     }
461 
462     if (nssCKFWSlot_GetRemovableDevice(fwSlot)) {
463         pInfo->flags |= CKF_REMOVABLE_DEVICE;
464     }
465 
466     if (nssCKFWSlot_GetHardwareSlot(fwSlot)) {
467         pInfo->flags |= CKF_HW_SLOT;
468     }
469 
470     pInfo->hardwareVersion = nssCKFWSlot_GetHardwareVersion(fwSlot);
471     pInfo->firmwareVersion = nssCKFWSlot_GetFirmwareVersion(fwSlot);
472 
473     return CKR_OK;
474 
475 loser:
476     switch (error) {
477         case CKR_CRYPTOKI_NOT_INITIALIZED:
478         case CKR_DEVICE_ERROR:
479         case CKR_FUNCTION_FAILED:
480         case CKR_GENERAL_ERROR:
481         case CKR_HOST_MEMORY:
482         case CKR_SLOT_ID_INVALID:
483             break;
484         default:
485         case CKR_OK:
486             error = CKR_GENERAL_ERROR;
487     }
488 
489     return error;
490 }
491 
492 /*
493  * NSSCKFWC_GetTokenInfo
494  *
495  */
496 NSS_IMPLEMENT CK_RV
NSSCKFWC_GetTokenInfo(NSSCKFWInstance * fwInstance,CK_SLOT_ID slotID,CK_TOKEN_INFO_PTR pInfo)497 NSSCKFWC_GetTokenInfo(
498     NSSCKFWInstance *fwInstance,
499     CK_SLOT_ID slotID,
500     CK_TOKEN_INFO_PTR pInfo)
501 {
502     CK_RV error = CKR_OK;
503     CK_ULONG nSlots;
504     NSSCKFWSlot **slots;
505     NSSCKFWSlot *fwSlot;
506     NSSCKFWToken *fwToken = (NSSCKFWToken *)NULL;
507 
508     if (!fwInstance) {
509         error = CKR_CRYPTOKI_NOT_INITIALIZED;
510         goto loser;
511     }
512 
513     nSlots = nssCKFWInstance_GetNSlots(fwInstance, &error);
514     if ((CK_ULONG)0 == nSlots) {
515         goto loser;
516     }
517 
518     if ((slotID < 1) || (slotID > nSlots)) {
519         error = CKR_SLOT_ID_INVALID;
520         goto loser;
521     }
522 
523     if ((CK_TOKEN_INFO_PTR)CK_NULL_PTR == pInfo) {
524         error = CKR_ARGUMENTS_BAD;
525         goto loser;
526     }
527 
528     /*
529      * A purify error here indicates caller error.
530      */
531     (void)nsslibc_memset(pInfo, 0, sizeof(CK_TOKEN_INFO));
532 
533     slots = nssCKFWInstance_GetSlots(fwInstance, &error);
534     if ((NSSCKFWSlot **)NULL == slots) {
535         goto loser;
536     }
537 
538     fwSlot = slots[slotID - 1];
539 
540     if (CK_TRUE != nssCKFWSlot_GetTokenPresent(fwSlot)) {
541         error = CKR_TOKEN_NOT_PRESENT;
542         goto loser;
543     }
544 
545     fwToken = nssCKFWSlot_GetToken(fwSlot, &error);
546     if (!fwToken) {
547         goto loser;
548     }
549 
550     error = nssCKFWToken_GetLabel(fwToken, pInfo->label);
551     if (CKR_OK != error) {
552         goto loser;
553     }
554 
555     error = nssCKFWToken_GetManufacturerID(fwToken, pInfo->manufacturerID);
556     if (CKR_OK != error) {
557         goto loser;
558     }
559 
560     error = nssCKFWToken_GetModel(fwToken, pInfo->model);
561     if (CKR_OK != error) {
562         goto loser;
563     }
564 
565     error = nssCKFWToken_GetSerialNumber(fwToken, pInfo->serialNumber);
566     if (CKR_OK != error) {
567         goto loser;
568     }
569 
570     if (nssCKFWToken_GetHasRNG(fwToken)) {
571         pInfo->flags |= CKF_RNG;
572     }
573 
574     if (nssCKFWToken_GetIsWriteProtected(fwToken)) {
575         pInfo->flags |= CKF_WRITE_PROTECTED;
576     }
577 
578     if (nssCKFWToken_GetLoginRequired(fwToken)) {
579         pInfo->flags |= CKF_LOGIN_REQUIRED;
580     }
581 
582     if (nssCKFWToken_GetUserPinInitialized(fwToken)) {
583         pInfo->flags |= CKF_USER_PIN_INITIALIZED;
584     }
585 
586     if (nssCKFWToken_GetRestoreKeyNotNeeded(fwToken)) {
587         pInfo->flags |= CKF_RESTORE_KEY_NOT_NEEDED;
588     }
589 
590     if (nssCKFWToken_GetHasClockOnToken(fwToken)) {
591         pInfo->flags |= CKF_CLOCK_ON_TOKEN;
592     }
593 
594     if (nssCKFWToken_GetHasProtectedAuthenticationPath(fwToken)) {
595         pInfo->flags |= CKF_PROTECTED_AUTHENTICATION_PATH;
596     }
597 
598     if (nssCKFWToken_GetSupportsDualCryptoOperations(fwToken)) {
599         pInfo->flags |= CKF_DUAL_CRYPTO_OPERATIONS;
600     }
601 
602     pInfo->ulMaxSessionCount = nssCKFWToken_GetMaxSessionCount(fwToken);
603     pInfo->ulSessionCount = nssCKFWToken_GetSessionCount(fwToken);
604     pInfo->ulMaxRwSessionCount = nssCKFWToken_GetMaxRwSessionCount(fwToken);
605     pInfo->ulRwSessionCount = nssCKFWToken_GetRwSessionCount(fwToken);
606     pInfo->ulMaxPinLen = nssCKFWToken_GetMaxPinLen(fwToken);
607     pInfo->ulMinPinLen = nssCKFWToken_GetMinPinLen(fwToken);
608     pInfo->ulTotalPublicMemory = nssCKFWToken_GetTotalPublicMemory(fwToken);
609     pInfo->ulFreePublicMemory = nssCKFWToken_GetFreePublicMemory(fwToken);
610     pInfo->ulTotalPrivateMemory = nssCKFWToken_GetTotalPrivateMemory(fwToken);
611     pInfo->ulFreePrivateMemory = nssCKFWToken_GetFreePrivateMemory(fwToken);
612     pInfo->hardwareVersion = nssCKFWToken_GetHardwareVersion(fwToken);
613     pInfo->firmwareVersion = nssCKFWToken_GetFirmwareVersion(fwToken);
614 
615     error = nssCKFWToken_GetUTCTime(fwToken, pInfo->utcTime);
616     if (CKR_OK != error) {
617         goto loser;
618     }
619 
620     return CKR_OK;
621 
622 loser:
623     switch (error) {
624         case CKR_DEVICE_REMOVED:
625         case CKR_TOKEN_NOT_PRESENT:
626             if (fwToken)
627                 nssCKFWToken_Destroy(fwToken);
628             break;
629         case CKR_CRYPTOKI_NOT_INITIALIZED:
630         case CKR_DEVICE_ERROR:
631         case CKR_DEVICE_MEMORY:
632         case CKR_FUNCTION_FAILED:
633         case CKR_GENERAL_ERROR:
634         case CKR_HOST_MEMORY:
635         case CKR_SLOT_ID_INVALID:
636         case CKR_TOKEN_NOT_RECOGNIZED:
637             break;
638         default:
639         case CKR_OK:
640             error = CKR_GENERAL_ERROR;
641             break;
642     }
643 
644     return error;
645 }
646 
647 /*
648  * NSSCKFWC_WaitForSlotEvent
649  *
650  */
651 NSS_IMPLEMENT CK_RV
NSSCKFWC_WaitForSlotEvent(NSSCKFWInstance * fwInstance,CK_FLAGS flags,CK_SLOT_ID_PTR pSlot,CK_VOID_PTR pReserved)652 NSSCKFWC_WaitForSlotEvent(
653     NSSCKFWInstance *fwInstance,
654     CK_FLAGS flags,
655     CK_SLOT_ID_PTR pSlot,
656     CK_VOID_PTR pReserved)
657 {
658     CK_RV error = CKR_OK;
659     CK_ULONG nSlots;
660     CK_BBOOL block;
661     NSSCKFWSlot **slots;
662     NSSCKFWSlot *fwSlot;
663     CK_ULONG i;
664 
665     if (!fwInstance) {
666         error = CKR_CRYPTOKI_NOT_INITIALIZED;
667         goto loser;
668     }
669 
670     if (flags & ~CKF_DONT_BLOCK) {
671         error = CKR_ARGUMENTS_BAD;
672         goto loser;
673     }
674 
675     block = (flags & CKF_DONT_BLOCK) ? CK_TRUE : CK_FALSE;
676 
677     nSlots = nssCKFWInstance_GetNSlots(fwInstance, &error);
678     if ((CK_ULONG)0 == nSlots) {
679         goto loser;
680     }
681 
682     if ((CK_SLOT_ID_PTR)CK_NULL_PTR == pSlot) {
683         error = CKR_ARGUMENTS_BAD;
684         goto loser;
685     }
686 
687     if ((CK_VOID_PTR)CK_NULL_PTR != pReserved) {
688         error = CKR_ARGUMENTS_BAD;
689         goto loser;
690     }
691 
692     slots = nssCKFWInstance_GetSlots(fwInstance, &error);
693     if ((NSSCKFWSlot **)NULL == slots) {
694         goto loser;
695     }
696 
697     fwSlot = nssCKFWInstance_WaitForSlotEvent(fwInstance, block, &error);
698     if (!fwSlot) {
699         goto loser;
700     }
701 
702     for (i = 0; i < nSlots; i++) {
703         if (fwSlot == slots[i]) {
704             *pSlot = (CK_SLOT_ID)(CK_ULONG)(i + 1);
705             return CKR_OK;
706         }
707     }
708 
709     error = CKR_GENERAL_ERROR; /* returned something not in the slot list */
710 
711 loser:
712     switch (error) {
713         case CKR_CRYPTOKI_NOT_INITIALIZED:
714         case CKR_FUNCTION_FAILED:
715         case CKR_GENERAL_ERROR:
716         case CKR_HOST_MEMORY:
717         case CKR_NO_EVENT:
718             break;
719         default:
720         case CKR_OK:
721             error = CKR_GENERAL_ERROR;
722             break;
723     }
724 
725     return error;
726 }
727 
728 /*
729  * NSSCKFWC_GetMechanismList
730  *
731  */
732 NSS_IMPLEMENT CK_RV
NSSCKFWC_GetMechanismList(NSSCKFWInstance * fwInstance,CK_SLOT_ID slotID,CK_MECHANISM_TYPE_PTR pMechanismList,CK_ULONG_PTR pulCount)733 NSSCKFWC_GetMechanismList(
734     NSSCKFWInstance *fwInstance,
735     CK_SLOT_ID slotID,
736     CK_MECHANISM_TYPE_PTR pMechanismList,
737     CK_ULONG_PTR pulCount)
738 {
739     CK_RV error = CKR_OK;
740     CK_ULONG nSlots;
741     NSSCKFWSlot **slots;
742     NSSCKFWSlot *fwSlot;
743     NSSCKFWToken *fwToken = (NSSCKFWToken *)NULL;
744     CK_ULONG count;
745 
746     if (!fwInstance) {
747         error = CKR_CRYPTOKI_NOT_INITIALIZED;
748         goto loser;
749     }
750 
751     nSlots = nssCKFWInstance_GetNSlots(fwInstance, &error);
752     if ((CK_ULONG)0 == nSlots) {
753         goto loser;
754     }
755 
756     if ((slotID < 1) || (slotID > nSlots)) {
757         error = CKR_SLOT_ID_INVALID;
758         goto loser;
759     }
760 
761     if ((CK_ULONG_PTR)CK_NULL_PTR == pulCount) {
762         error = CKR_ARGUMENTS_BAD;
763         goto loser;
764     }
765 
766     slots = nssCKFWInstance_GetSlots(fwInstance, &error);
767     if ((NSSCKFWSlot **)NULL == slots) {
768         goto loser;
769     }
770 
771     fwSlot = slots[slotID - 1];
772 
773     if (CK_TRUE != nssCKFWSlot_GetTokenPresent(fwSlot)) {
774         error = CKR_TOKEN_NOT_PRESENT;
775         goto loser;
776     }
777 
778     fwToken = nssCKFWSlot_GetToken(fwSlot, &error);
779     if (!fwToken) {
780         goto loser;
781     }
782 
783     count = nssCKFWToken_GetMechanismCount(fwToken);
784 
785     if ((CK_MECHANISM_TYPE_PTR)CK_NULL_PTR == pMechanismList) {
786         *pulCount = count;
787         return CKR_OK;
788     }
789 
790     if (*pulCount < count) {
791         *pulCount = count;
792         error = CKR_BUFFER_TOO_SMALL;
793         goto loser;
794     }
795 
796     /*
797      * A purify error here indicates caller error.
798      */
799     (void)nsslibc_memset(pMechanismList, 0, *pulCount * sizeof(CK_MECHANISM_TYPE));
800 
801     *pulCount = count;
802 
803     if (0 != count) {
804         error = nssCKFWToken_GetMechanismTypes(fwToken, pMechanismList);
805     } else {
806         error = CKR_OK;
807     }
808 
809     if (CKR_OK == error) {
810         return CKR_OK;
811     }
812 
813 loser:
814     switch (error) {
815         case CKR_DEVICE_REMOVED:
816         case CKR_TOKEN_NOT_PRESENT:
817             if (fwToken)
818                 nssCKFWToken_Destroy(fwToken);
819             break;
820         case CKR_ARGUMENTS_BAD:
821         case CKR_BUFFER_TOO_SMALL:
822         case CKR_CRYPTOKI_NOT_INITIALIZED:
823         case CKR_DEVICE_ERROR:
824         case CKR_DEVICE_MEMORY:
825         case CKR_FUNCTION_FAILED:
826         case CKR_GENERAL_ERROR:
827         case CKR_HOST_MEMORY:
828         case CKR_SLOT_ID_INVALID:
829         case CKR_TOKEN_NOT_RECOGNIZED:
830             break;
831         default:
832         case CKR_OK:
833             error = CKR_GENERAL_ERROR;
834             break;
835     }
836 
837     return error;
838 }
839 
840 /*
841  * NSSCKFWC_GetMechanismInfo
842  *
843  */
844 NSS_IMPLEMENT CK_RV
NSSCKFWC_GetMechanismInfo(NSSCKFWInstance * fwInstance,CK_SLOT_ID slotID,CK_MECHANISM_TYPE type,CK_MECHANISM_INFO_PTR pInfo)845 NSSCKFWC_GetMechanismInfo(
846     NSSCKFWInstance *fwInstance,
847     CK_SLOT_ID slotID,
848     CK_MECHANISM_TYPE type,
849     CK_MECHANISM_INFO_PTR pInfo)
850 {
851     CK_RV error = CKR_OK;
852     CK_ULONG nSlots;
853     NSSCKFWSlot **slots;
854     NSSCKFWSlot *fwSlot;
855     NSSCKFWToken *fwToken = (NSSCKFWToken *)NULL;
856     NSSCKFWMechanism *fwMechanism;
857 
858     if (!fwInstance) {
859         error = CKR_CRYPTOKI_NOT_INITIALIZED;
860         goto loser;
861     }
862 
863     nSlots = nssCKFWInstance_GetNSlots(fwInstance, &error);
864     if ((CK_ULONG)0 == nSlots) {
865         goto loser;
866     }
867 
868     if ((slotID < 1) || (slotID > nSlots)) {
869         error = CKR_SLOT_ID_INVALID;
870         goto loser;
871     }
872 
873     slots = nssCKFWInstance_GetSlots(fwInstance, &error);
874     if ((NSSCKFWSlot **)NULL == slots) {
875         goto loser;
876     }
877 
878     fwSlot = slots[slotID - 1];
879 
880     if (CK_TRUE != nssCKFWSlot_GetTokenPresent(fwSlot)) {
881         error = CKR_TOKEN_NOT_PRESENT;
882         goto loser;
883     }
884 
885     if ((CK_MECHANISM_INFO_PTR)CK_NULL_PTR == pInfo) {
886         error = CKR_ARGUMENTS_BAD;
887         goto loser;
888     }
889 
890     /*
891      * A purify error here indicates caller error.
892      */
893     (void)nsslibc_memset(pInfo, 0, sizeof(CK_MECHANISM_INFO));
894 
895     fwToken = nssCKFWSlot_GetToken(fwSlot, &error);
896     if (!fwToken) {
897         goto loser;
898     }
899 
900     fwMechanism = nssCKFWToken_GetMechanism(fwToken, type, &error);
901     if (!fwMechanism) {
902         goto loser;
903     }
904 
905     pInfo->ulMinKeySize = nssCKFWMechanism_GetMinKeySize(fwMechanism, &error);
906     pInfo->ulMaxKeySize = nssCKFWMechanism_GetMaxKeySize(fwMechanism, &error);
907 
908     if (nssCKFWMechanism_GetInHardware(fwMechanism, &error)) {
909         pInfo->flags |= CKF_HW;
910     }
911     if (nssCKFWMechanism_GetCanEncrypt(fwMechanism, &error)) {
912         pInfo->flags |= CKF_ENCRYPT;
913     }
914     if (nssCKFWMechanism_GetCanDecrypt(fwMechanism, &error)) {
915         pInfo->flags |= CKF_DECRYPT;
916     }
917     if (nssCKFWMechanism_GetCanDigest(fwMechanism, &error)) {
918         pInfo->flags |= CKF_DIGEST;
919     }
920     if (nssCKFWMechanism_GetCanSign(fwMechanism, &error)) {
921         pInfo->flags |= CKF_SIGN;
922     }
923     if (nssCKFWMechanism_GetCanSignRecover(fwMechanism, &error)) {
924         pInfo->flags |= CKF_SIGN_RECOVER;
925     }
926     if (nssCKFWMechanism_GetCanVerify(fwMechanism, &error)) {
927         pInfo->flags |= CKF_VERIFY;
928     }
929     if (nssCKFWMechanism_GetCanVerifyRecover(fwMechanism, &error)) {
930         pInfo->flags |= CKF_VERIFY_RECOVER;
931     }
932     if (nssCKFWMechanism_GetCanGenerate(fwMechanism, &error)) {
933         pInfo->flags |= CKF_GENERATE;
934     }
935     if (nssCKFWMechanism_GetCanGenerateKeyPair(fwMechanism, &error)) {
936         pInfo->flags |= CKF_GENERATE_KEY_PAIR;
937     }
938     if (nssCKFWMechanism_GetCanWrap(fwMechanism, &error)) {
939         pInfo->flags |= CKF_WRAP;
940     }
941     if (nssCKFWMechanism_GetCanUnwrap(fwMechanism, &error)) {
942         pInfo->flags |= CKF_UNWRAP;
943     }
944     if (nssCKFWMechanism_GetCanDerive(fwMechanism, &error)) {
945         pInfo->flags |= CKF_DERIVE;
946     }
947     nssCKFWMechanism_Destroy(fwMechanism);
948 
949     return error;
950 
951 loser:
952     switch (error) {
953         case CKR_DEVICE_REMOVED:
954         case CKR_TOKEN_NOT_PRESENT:
955             if (fwToken)
956                 nssCKFWToken_Destroy(fwToken);
957             break;
958         case CKR_ARGUMENTS_BAD:
959         case CKR_CRYPTOKI_NOT_INITIALIZED:
960         case CKR_DEVICE_ERROR:
961         case CKR_DEVICE_MEMORY:
962         case CKR_FUNCTION_FAILED:
963         case CKR_GENERAL_ERROR:
964         case CKR_HOST_MEMORY:
965         case CKR_MECHANISM_INVALID:
966         case CKR_SLOT_ID_INVALID:
967         case CKR_TOKEN_NOT_RECOGNIZED:
968             break;
969         default:
970         case CKR_OK:
971             error = CKR_GENERAL_ERROR;
972             break;
973     }
974 
975     return error;
976 }
977 
978 /*
979  * NSSCKFWC_InitToken
980  *
981  */
982 NSS_IMPLEMENT CK_RV
NSSCKFWC_InitToken(NSSCKFWInstance * fwInstance,CK_SLOT_ID slotID,CK_CHAR_PTR pPin,CK_ULONG ulPinLen,CK_CHAR_PTR pLabel)983 NSSCKFWC_InitToken(
984     NSSCKFWInstance *fwInstance,
985     CK_SLOT_ID slotID,
986     CK_CHAR_PTR pPin,
987     CK_ULONG ulPinLen,
988     CK_CHAR_PTR pLabel)
989 {
990     CK_RV error = CKR_OK;
991     CK_ULONG nSlots;
992     NSSCKFWSlot **slots;
993     NSSCKFWSlot *fwSlot;
994     NSSCKFWToken *fwToken = (NSSCKFWToken *)NULL;
995     NSSItem pin;
996     NSSUTF8 *label;
997 
998     if (!fwInstance) {
999         error = CKR_CRYPTOKI_NOT_INITIALIZED;
1000         goto loser;
1001     }
1002 
1003     nSlots = nssCKFWInstance_GetNSlots(fwInstance, &error);
1004     if ((CK_ULONG)0 == nSlots) {
1005         goto loser;
1006     }
1007 
1008     if ((slotID < 1) || (slotID > nSlots)) {
1009         error = CKR_SLOT_ID_INVALID;
1010         goto loser;
1011     }
1012 
1013     slots = nssCKFWInstance_GetSlots(fwInstance, &error);
1014     if ((NSSCKFWSlot **)NULL == slots) {
1015         goto loser;
1016     }
1017 
1018     fwSlot = slots[slotID - 1];
1019 
1020     if (CK_TRUE != nssCKFWSlot_GetTokenPresent(fwSlot)) {
1021         error = CKR_TOKEN_NOT_PRESENT;
1022         goto loser;
1023     }
1024 
1025     fwToken = nssCKFWSlot_GetToken(fwSlot, &error);
1026     if (!fwToken) {
1027         goto loser;
1028     }
1029 
1030     pin.size = (PRUint32)ulPinLen;
1031     pin.data = (void *)pPin;
1032     label = (NSSUTF8 *)pLabel; /* identity conversion */
1033 
1034     error = nssCKFWToken_InitToken(fwToken, &pin, label);
1035     if (CKR_OK != error) {
1036         goto loser;
1037     }
1038 
1039     return CKR_OK;
1040 
1041 loser:
1042     switch (error) {
1043         case CKR_DEVICE_REMOVED:
1044         case CKR_TOKEN_NOT_PRESENT:
1045             if (fwToken)
1046                 nssCKFWToken_Destroy(fwToken);
1047             break;
1048         case CKR_ARGUMENTS_BAD:
1049         case CKR_CRYPTOKI_NOT_INITIALIZED:
1050         case CKR_DEVICE_ERROR:
1051         case CKR_DEVICE_MEMORY:
1052         case CKR_FUNCTION_FAILED:
1053         case CKR_GENERAL_ERROR:
1054         case CKR_HOST_MEMORY:
1055         case CKR_PIN_INCORRECT:
1056         case CKR_PIN_LOCKED:
1057         case CKR_SESSION_EXISTS:
1058         case CKR_SLOT_ID_INVALID:
1059         case CKR_TOKEN_NOT_RECOGNIZED:
1060         case CKR_TOKEN_WRITE_PROTECTED:
1061             break;
1062         default:
1063         case CKR_OK:
1064             error = CKR_GENERAL_ERROR;
1065             break;
1066     }
1067 
1068     return error;
1069 }
1070 
1071 /*
1072  * NSSCKFWC_InitPIN
1073  *
1074  */
1075 NSS_IMPLEMENT CK_RV
NSSCKFWC_InitPIN(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_CHAR_PTR pPin,CK_ULONG ulPinLen)1076 NSSCKFWC_InitPIN(
1077     NSSCKFWInstance *fwInstance,
1078     CK_SESSION_HANDLE hSession,
1079     CK_CHAR_PTR pPin,
1080     CK_ULONG ulPinLen)
1081 {
1082     CK_RV error = CKR_OK;
1083     NSSCKFWSession *fwSession;
1084     NSSItem pin, *arg;
1085 
1086     if (!fwInstance) {
1087         error = CKR_CRYPTOKI_NOT_INITIALIZED;
1088         goto loser;
1089     }
1090 
1091     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
1092     if (!fwSession) {
1093         error = CKR_SESSION_HANDLE_INVALID;
1094         goto loser;
1095     }
1096 
1097     if ((CK_CHAR_PTR)CK_NULL_PTR == pPin) {
1098         arg = (NSSItem *)NULL;
1099     } else {
1100         arg = &pin;
1101         pin.size = (PRUint32)ulPinLen;
1102         pin.data = (void *)pPin;
1103     }
1104 
1105     error = nssCKFWSession_InitPIN(fwSession, arg);
1106     if (CKR_OK != error) {
1107         goto loser;
1108     }
1109 
1110     return CKR_OK;
1111 
1112 loser:
1113     switch (error) {
1114         case CKR_SESSION_CLOSED:
1115             /* destroy session? */
1116             break;
1117         case CKR_DEVICE_REMOVED:
1118             /* (void)nssCKFWToken_Destroy(fwToken); */
1119             break;
1120         case CKR_ARGUMENTS_BAD:
1121         case CKR_CRYPTOKI_NOT_INITIALIZED:
1122         case CKR_DEVICE_ERROR:
1123         case CKR_DEVICE_MEMORY:
1124         case CKR_FUNCTION_FAILED:
1125         case CKR_GENERAL_ERROR:
1126         case CKR_HOST_MEMORY:
1127         case CKR_PIN_INVALID:
1128         case CKR_PIN_LEN_RANGE:
1129         case CKR_SESSION_READ_ONLY:
1130         case CKR_SESSION_HANDLE_INVALID:
1131         case CKR_TOKEN_WRITE_PROTECTED:
1132         case CKR_USER_NOT_LOGGED_IN:
1133             break;
1134         default:
1135         case CKR_OK:
1136             error = CKR_GENERAL_ERROR;
1137             break;
1138     }
1139 
1140     return error;
1141 }
1142 
1143 /*
1144  * NSSCKFWC_SetPIN
1145  *
1146  */
1147 NSS_IMPLEMENT CK_RV
NSSCKFWC_SetPIN(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_CHAR_PTR pOldPin,CK_ULONG ulOldLen,CK_CHAR_PTR pNewPin,CK_ULONG ulNewLen)1148 NSSCKFWC_SetPIN(
1149     NSSCKFWInstance *fwInstance,
1150     CK_SESSION_HANDLE hSession,
1151     CK_CHAR_PTR pOldPin,
1152     CK_ULONG ulOldLen,
1153     CK_CHAR_PTR pNewPin,
1154     CK_ULONG ulNewLen)
1155 {
1156     CK_RV error = CKR_OK;
1157     NSSCKFWSession *fwSession;
1158     NSSItem oldPin, newPin, *oldArg, *newArg;
1159 
1160     if (!fwInstance) {
1161         error = CKR_CRYPTOKI_NOT_INITIALIZED;
1162         goto loser;
1163     }
1164 
1165     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
1166     if (!fwSession) {
1167         error = CKR_SESSION_HANDLE_INVALID;
1168         goto loser;
1169     }
1170 
1171     if ((CK_CHAR_PTR)CK_NULL_PTR == pOldPin) {
1172         oldArg = (NSSItem *)NULL;
1173     } else {
1174         oldArg = &oldPin;
1175         oldPin.size = (PRUint32)ulOldLen;
1176         oldPin.data = (void *)pOldPin;
1177     }
1178 
1179     if ((CK_CHAR_PTR)CK_NULL_PTR == pNewPin) {
1180         newArg = (NSSItem *)NULL;
1181     } else {
1182         newArg = &newPin;
1183         newPin.size = (PRUint32)ulNewLen;
1184         newPin.data = (void *)pNewPin;
1185     }
1186 
1187     error = nssCKFWSession_SetPIN(fwSession, oldArg, newArg);
1188     if (CKR_OK != error) {
1189         goto loser;
1190     }
1191 
1192     return CKR_OK;
1193 
1194 loser:
1195     switch (error) {
1196         case CKR_SESSION_CLOSED:
1197             /* destroy session? */
1198             break;
1199         case CKR_DEVICE_REMOVED:
1200             /* (void)nssCKFWToken_Destroy(fwToken); */
1201             break;
1202         case CKR_ARGUMENTS_BAD:
1203         case CKR_CRYPTOKI_NOT_INITIALIZED:
1204         case CKR_DEVICE_ERROR:
1205         case CKR_DEVICE_MEMORY:
1206         case CKR_FUNCTION_FAILED:
1207         case CKR_GENERAL_ERROR:
1208         case CKR_HOST_MEMORY:
1209         case CKR_PIN_INCORRECT:
1210         case CKR_PIN_INVALID:
1211         case CKR_PIN_LEN_RANGE:
1212         case CKR_PIN_LOCKED:
1213         case CKR_SESSION_HANDLE_INVALID:
1214         case CKR_SESSION_READ_ONLY:
1215         case CKR_TOKEN_WRITE_PROTECTED:
1216             break;
1217         default:
1218         case CKR_OK:
1219             error = CKR_GENERAL_ERROR;
1220             break;
1221     }
1222 
1223     return error;
1224 }
1225 
1226 /*
1227  * NSSCKFWC_OpenSession
1228  *
1229  */
1230 NSS_IMPLEMENT CK_RV
NSSCKFWC_OpenSession(NSSCKFWInstance * fwInstance,CK_SLOT_ID slotID,CK_FLAGS flags,CK_VOID_PTR pApplication,CK_NOTIFY Notify,CK_SESSION_HANDLE_PTR phSession)1231 NSSCKFWC_OpenSession(
1232     NSSCKFWInstance *fwInstance,
1233     CK_SLOT_ID slotID,
1234     CK_FLAGS flags,
1235     CK_VOID_PTR pApplication,
1236     CK_NOTIFY Notify,
1237     CK_SESSION_HANDLE_PTR phSession)
1238 {
1239     CK_RV error = CKR_OK;
1240     CK_ULONG nSlots;
1241     NSSCKFWSlot **slots;
1242     NSSCKFWSlot *fwSlot;
1243     NSSCKFWToken *fwToken = (NSSCKFWToken *)NULL;
1244     NSSCKFWSession *fwSession;
1245     CK_BBOOL rw;
1246 
1247     if (!fwInstance) {
1248         error = CKR_CRYPTOKI_NOT_INITIALIZED;
1249         goto loser;
1250     }
1251 
1252     nSlots = nssCKFWInstance_GetNSlots(fwInstance, &error);
1253     if ((CK_ULONG)0 == nSlots) {
1254         goto loser;
1255     }
1256 
1257     if ((slotID < 1) || (slotID > nSlots)) {
1258         error = CKR_SLOT_ID_INVALID;
1259         goto loser;
1260     }
1261 
1262     if (flags & CKF_RW_SESSION) {
1263         rw = CK_TRUE;
1264     } else {
1265         rw = CK_FALSE;
1266     }
1267 
1268     if (flags & CKF_SERIAL_SESSION) {
1269         ;
1270     } else {
1271         error = CKR_SESSION_PARALLEL_NOT_SUPPORTED;
1272         goto loser;
1273     }
1274 
1275     if (flags & ~(CKF_RW_SESSION | CKF_SERIAL_SESSION)) {
1276         error = CKR_ARGUMENTS_BAD;
1277         goto loser;
1278     }
1279 
1280     if ((CK_SESSION_HANDLE_PTR)CK_NULL_PTR == phSession) {
1281         error = CKR_ARGUMENTS_BAD;
1282         goto loser;
1283     }
1284 
1285     /*
1286      * A purify error here indicates caller error.
1287      */
1288     *phSession = (CK_SESSION_HANDLE)0;
1289 
1290     slots = nssCKFWInstance_GetSlots(fwInstance, &error);
1291     if ((NSSCKFWSlot **)NULL == slots) {
1292         goto loser;
1293     }
1294 
1295     fwSlot = slots[slotID - 1];
1296 
1297     if (CK_TRUE != nssCKFWSlot_GetTokenPresent(fwSlot)) {
1298         error = CKR_TOKEN_NOT_PRESENT;
1299         goto loser;
1300     }
1301 
1302     fwToken = nssCKFWSlot_GetToken(fwSlot, &error);
1303     if (!fwToken) {
1304         goto loser;
1305     }
1306 
1307     fwSession = nssCKFWToken_OpenSession(fwToken, rw, pApplication,
1308                                          Notify, &error);
1309     if (!fwSession) {
1310         goto loser;
1311     }
1312 
1313     *phSession = nssCKFWInstance_CreateSessionHandle(fwInstance,
1314                                                      fwSession, &error);
1315     if ((CK_SESSION_HANDLE)0 == *phSession) {
1316         goto loser;
1317     }
1318 
1319     return CKR_OK;
1320 
1321 loser:
1322     switch (error) {
1323         case CKR_SESSION_CLOSED:
1324             /* destroy session? */
1325             break;
1326         case CKR_DEVICE_REMOVED:
1327             /* (void)nssCKFWToken_Destroy(fwToken); */
1328             break;
1329         case CKR_CRYPTOKI_NOT_INITIALIZED:
1330         case CKR_DEVICE_ERROR:
1331         case CKR_DEVICE_MEMORY:
1332         case CKR_FUNCTION_FAILED:
1333         case CKR_GENERAL_ERROR:
1334         case CKR_HOST_MEMORY:
1335         case CKR_SESSION_COUNT:
1336         case CKR_SESSION_EXISTS:
1337         case CKR_SESSION_PARALLEL_NOT_SUPPORTED:
1338         case CKR_SESSION_READ_WRITE_SO_EXISTS:
1339         case CKR_SLOT_ID_INVALID:
1340         case CKR_TOKEN_NOT_PRESENT:
1341         case CKR_TOKEN_NOT_RECOGNIZED:
1342         case CKR_TOKEN_WRITE_PROTECTED:
1343             break;
1344         default:
1345         case CKR_OK:
1346             error = CKR_GENERAL_ERROR;
1347             break;
1348     }
1349 
1350     return error;
1351 }
1352 
1353 /*
1354  * NSSCKFWC_CloseSession
1355  *
1356  */
1357 NSS_IMPLEMENT CK_RV
NSSCKFWC_CloseSession(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession)1358 NSSCKFWC_CloseSession(
1359     NSSCKFWInstance *fwInstance,
1360     CK_SESSION_HANDLE hSession)
1361 {
1362     CK_RV error = CKR_OK;
1363     NSSCKFWSession *fwSession;
1364 
1365     if (!fwInstance) {
1366         error = CKR_CRYPTOKI_NOT_INITIALIZED;
1367         goto loser;
1368     }
1369 
1370     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
1371     if (!fwSession) {
1372         error = CKR_SESSION_HANDLE_INVALID;
1373         goto loser;
1374     }
1375 
1376     nssCKFWInstance_DestroySessionHandle(fwInstance, hSession);
1377     error = nssCKFWSession_Destroy(fwSession, CK_TRUE);
1378 
1379     if (CKR_OK != error) {
1380         goto loser;
1381     }
1382 
1383     return CKR_OK;
1384 
1385 loser:
1386     switch (error) {
1387         case CKR_SESSION_CLOSED:
1388             /* destroy session? */
1389             break;
1390         case CKR_DEVICE_REMOVED:
1391             /* (void)nssCKFWToken_Destroy(fwToken); */
1392             break;
1393         case CKR_CRYPTOKI_NOT_INITIALIZED:
1394         case CKR_DEVICE_ERROR:
1395         case CKR_DEVICE_MEMORY:
1396         case CKR_FUNCTION_FAILED:
1397         case CKR_GENERAL_ERROR:
1398         case CKR_HOST_MEMORY:
1399         case CKR_SESSION_HANDLE_INVALID:
1400             break;
1401         default:
1402         case CKR_OK:
1403             error = CKR_GENERAL_ERROR;
1404             break;
1405     }
1406 
1407     return error;
1408 }
1409 
1410 /*
1411  * NSSCKFWC_CloseAllSessions
1412  *
1413  */
1414 NSS_IMPLEMENT CK_RV
NSSCKFWC_CloseAllSessions(NSSCKFWInstance * fwInstance,CK_SLOT_ID slotID)1415 NSSCKFWC_CloseAllSessions(
1416     NSSCKFWInstance *fwInstance,
1417     CK_SLOT_ID slotID)
1418 {
1419     CK_RV error = CKR_OK;
1420     CK_ULONG nSlots;
1421     NSSCKFWSlot **slots;
1422     NSSCKFWSlot *fwSlot;
1423     NSSCKFWToken *fwToken = (NSSCKFWToken *)NULL;
1424 
1425     if (!fwInstance) {
1426         error = CKR_CRYPTOKI_NOT_INITIALIZED;
1427         goto loser;
1428     }
1429 
1430     nSlots = nssCKFWInstance_GetNSlots(fwInstance, &error);
1431     if ((CK_ULONG)0 == nSlots) {
1432         goto loser;
1433     }
1434 
1435     if ((slotID < 1) || (slotID > nSlots)) {
1436         error = CKR_SLOT_ID_INVALID;
1437         goto loser;
1438     }
1439 
1440     slots = nssCKFWInstance_GetSlots(fwInstance, &error);
1441     if ((NSSCKFWSlot **)NULL == slots) {
1442         goto loser;
1443     }
1444 
1445     fwSlot = slots[slotID - 1];
1446 
1447     if (CK_TRUE != nssCKFWSlot_GetTokenPresent(fwSlot)) {
1448         error = CKR_TOKEN_NOT_PRESENT;
1449         goto loser;
1450     }
1451 
1452     fwToken = nssCKFWSlot_GetToken(fwSlot, &error);
1453     if (!fwToken) {
1454         goto loser;
1455     }
1456 
1457     error = nssCKFWToken_CloseAllSessions(fwToken);
1458     if (CKR_OK != error) {
1459         goto loser;
1460     }
1461 
1462     return CKR_OK;
1463 
1464 loser:
1465     switch (error) {
1466         case CKR_DEVICE_REMOVED:
1467             /* (void)nssCKFWToken_Destroy(fwToken); */
1468             break;
1469         case CKR_CRYPTOKI_NOT_INITIALIZED:
1470         case CKR_DEVICE_ERROR:
1471         case CKR_DEVICE_MEMORY:
1472         case CKR_FUNCTION_FAILED:
1473         case CKR_GENERAL_ERROR:
1474         case CKR_HOST_MEMORY:
1475         case CKR_SLOT_ID_INVALID:
1476         case CKR_TOKEN_NOT_PRESENT:
1477             break;
1478         default:
1479         case CKR_OK:
1480             error = CKR_GENERAL_ERROR;
1481             break;
1482     }
1483 
1484     return error;
1485 }
1486 
1487 /*
1488  * NSSCKFWC_GetSessionInfo
1489  *
1490  */
1491 NSS_IMPLEMENT CK_RV
NSSCKFWC_GetSessionInfo(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_SESSION_INFO_PTR pInfo)1492 NSSCKFWC_GetSessionInfo(
1493     NSSCKFWInstance *fwInstance,
1494     CK_SESSION_HANDLE hSession,
1495     CK_SESSION_INFO_PTR pInfo)
1496 {
1497     CK_RV error = CKR_OK;
1498     NSSCKFWSession *fwSession;
1499     NSSCKFWSlot *fwSlot;
1500 
1501     if (!fwInstance) {
1502         error = CKR_CRYPTOKI_NOT_INITIALIZED;
1503         goto loser;
1504     }
1505 
1506     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
1507     if (!fwSession) {
1508         error = CKR_SESSION_HANDLE_INVALID;
1509         goto loser;
1510     }
1511 
1512     if ((CK_SESSION_INFO_PTR)CK_NULL_PTR == pInfo) {
1513         error = CKR_ARGUMENTS_BAD;
1514         goto loser;
1515     }
1516 
1517     /*
1518      * A purify error here indicates caller error.
1519      */
1520     (void)nsslibc_memset(pInfo, 0, sizeof(CK_SESSION_INFO));
1521 
1522     fwSlot = nssCKFWSession_GetFWSlot(fwSession);
1523     if (!fwSlot) {
1524         error = CKR_GENERAL_ERROR;
1525         goto loser;
1526     }
1527 
1528     pInfo->slotID = nssCKFWSlot_GetSlotID(fwSlot);
1529     pInfo->state = nssCKFWSession_GetSessionState(fwSession);
1530 
1531     if (CK_TRUE == nssCKFWSession_IsRWSession(fwSession)) {
1532         pInfo->flags |= CKF_RW_SESSION;
1533     }
1534 
1535     pInfo->flags |= CKF_SERIAL_SESSION; /* Always true */
1536 
1537     pInfo->ulDeviceError = nssCKFWSession_GetDeviceError(fwSession);
1538 
1539     return CKR_OK;
1540 
1541 loser:
1542     switch (error) {
1543         case CKR_SESSION_CLOSED:
1544             /* destroy session? */
1545             break;
1546         case CKR_DEVICE_REMOVED:
1547             /* (void)nssCKFWToken_Destroy(fwToken); */
1548             break;
1549         case CKR_CRYPTOKI_NOT_INITIALIZED:
1550         case CKR_DEVICE_ERROR:
1551         case CKR_DEVICE_MEMORY:
1552         case CKR_FUNCTION_FAILED:
1553         case CKR_GENERAL_ERROR:
1554         case CKR_HOST_MEMORY:
1555         case CKR_SESSION_HANDLE_INVALID:
1556             break;
1557         default:
1558         case CKR_OK:
1559             error = CKR_GENERAL_ERROR;
1560             break;
1561     }
1562 
1563     return error;
1564 }
1565 
1566 /*
1567  * NSSCKFWC_GetOperationState
1568  *
1569  */
1570 NSS_IMPLEMENT CK_RV
NSSCKFWC_GetOperationState(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_BYTE_PTR pOperationState,CK_ULONG_PTR pulOperationStateLen)1571 NSSCKFWC_GetOperationState(
1572     NSSCKFWInstance *fwInstance,
1573     CK_SESSION_HANDLE hSession,
1574     CK_BYTE_PTR pOperationState,
1575     CK_ULONG_PTR pulOperationStateLen)
1576 {
1577     CK_RV error = CKR_OK;
1578     NSSCKFWSession *fwSession;
1579     CK_ULONG len;
1580     NSSItem buf;
1581 
1582     if (!fwInstance) {
1583         error = CKR_CRYPTOKI_NOT_INITIALIZED;
1584         goto loser;
1585     }
1586 
1587     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
1588     if (!fwSession) {
1589         error = CKR_SESSION_HANDLE_INVALID;
1590         goto loser;
1591     }
1592 
1593     if ((CK_ULONG_PTR)CK_NULL_PTR == pulOperationStateLen) {
1594         error = CKR_ARGUMENTS_BAD;
1595         goto loser;
1596     }
1597 
1598     len = nssCKFWSession_GetOperationStateLen(fwSession, &error);
1599     if (((CK_ULONG)0 == len) && (CKR_OK != error)) {
1600         goto loser;
1601     }
1602 
1603     if ((CK_BYTE_PTR)CK_NULL_PTR == pOperationState) {
1604         *pulOperationStateLen = len;
1605         return CKR_OK;
1606     }
1607 
1608     if (*pulOperationStateLen < len) {
1609         *pulOperationStateLen = len;
1610         error = CKR_BUFFER_TOO_SMALL;
1611         goto loser;
1612     }
1613 
1614     buf.size = (PRUint32)*pulOperationStateLen;
1615     buf.data = (void *)pOperationState;
1616     *pulOperationStateLen = len;
1617     error = nssCKFWSession_GetOperationState(fwSession, &buf);
1618 
1619     if (CKR_OK != error) {
1620         goto loser;
1621     }
1622 
1623     return CKR_OK;
1624 
1625 loser:
1626     switch (error) {
1627         case CKR_SESSION_CLOSED:
1628             /* destroy session? */
1629             break;
1630         case CKR_DEVICE_REMOVED:
1631             /* (void)nssCKFWToken_Destroy(fwToken); */
1632             break;
1633         case CKR_BUFFER_TOO_SMALL:
1634         case CKR_CRYPTOKI_NOT_INITIALIZED:
1635         case CKR_DEVICE_ERROR:
1636         case CKR_DEVICE_MEMORY:
1637         case CKR_FUNCTION_FAILED:
1638         case CKR_GENERAL_ERROR:
1639         case CKR_HOST_MEMORY:
1640         case CKR_OPERATION_NOT_INITIALIZED:
1641         case CKR_SESSION_HANDLE_INVALID:
1642         case CKR_STATE_UNSAVEABLE:
1643             break;
1644         default:
1645         case CKR_OK:
1646             error = CKR_GENERAL_ERROR;
1647             break;
1648     }
1649 
1650     return error;
1651 }
1652 
1653 /*
1654  * NSSCKFWC_SetOperationState
1655  *
1656  */
1657 NSS_IMPLEMENT CK_RV
NSSCKFWC_SetOperationState(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_BYTE_PTR pOperationState,CK_ULONG ulOperationStateLen,CK_OBJECT_HANDLE hEncryptionKey,CK_OBJECT_HANDLE hAuthenticationKey)1658 NSSCKFWC_SetOperationState(
1659     NSSCKFWInstance *fwInstance,
1660     CK_SESSION_HANDLE hSession,
1661     CK_BYTE_PTR pOperationState,
1662     CK_ULONG ulOperationStateLen,
1663     CK_OBJECT_HANDLE hEncryptionKey,
1664     CK_OBJECT_HANDLE hAuthenticationKey)
1665 {
1666     CK_RV error = CKR_OK;
1667     NSSCKFWSession *fwSession;
1668     NSSCKFWObject *eKey;
1669     NSSCKFWObject *aKey;
1670     NSSItem state;
1671 
1672     if (!fwInstance) {
1673         error = CKR_CRYPTOKI_NOT_INITIALIZED;
1674         goto loser;
1675     }
1676 
1677     if ((CK_BYTE_PTR)CK_NULL_PTR == pOperationState) {
1678         error = CKR_ARGUMENTS_BAD;
1679         goto loser;
1680     }
1681 
1682     /*
1683      * We could loop through the buffer, to catch any purify errors
1684      * in a place with a "user error" note.
1685      */
1686 
1687     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
1688     if (!fwSession) {
1689         error = CKR_SESSION_HANDLE_INVALID;
1690         goto loser;
1691     }
1692 
1693     if ((CK_OBJECT_HANDLE)0 == hEncryptionKey) {
1694         eKey = (NSSCKFWObject *)NULL;
1695     } else {
1696         eKey = nssCKFWInstance_ResolveObjectHandle(fwInstance, hEncryptionKey);
1697         if (!eKey) {
1698             error = CKR_KEY_HANDLE_INVALID;
1699             goto loser;
1700         }
1701     }
1702 
1703     if ((CK_OBJECT_HANDLE)0 == hAuthenticationKey) {
1704         aKey = (NSSCKFWObject *)NULL;
1705     } else {
1706         aKey = nssCKFWInstance_ResolveObjectHandle(fwInstance, hAuthenticationKey);
1707         if (!aKey) {
1708             error = CKR_KEY_HANDLE_INVALID;
1709             goto loser;
1710         }
1711     }
1712 
1713     state.data = pOperationState;
1714     state.size = ulOperationStateLen;
1715 
1716     error = nssCKFWSession_SetOperationState(fwSession, &state, eKey, aKey);
1717     if (CKR_OK != error) {
1718         goto loser;
1719     }
1720 
1721     return CKR_OK;
1722 
1723 loser:
1724     switch (error) {
1725         case CKR_SESSION_CLOSED:
1726             /* destroy session? */
1727             break;
1728         case CKR_DEVICE_REMOVED:
1729             /* (void)nssCKFWToken_Destroy(fwToken); */
1730             break;
1731         case CKR_CRYPTOKI_NOT_INITIALIZED:
1732         case CKR_DEVICE_ERROR:
1733         case CKR_DEVICE_MEMORY:
1734         case CKR_FUNCTION_FAILED:
1735         case CKR_GENERAL_ERROR:
1736         case CKR_HOST_MEMORY:
1737         case CKR_KEY_CHANGED:
1738         case CKR_KEY_NEEDED:
1739         case CKR_KEY_NOT_NEEDED:
1740         case CKR_SAVED_STATE_INVALID:
1741         case CKR_SESSION_HANDLE_INVALID:
1742             break;
1743         default:
1744         case CKR_OK:
1745             error = CKR_GENERAL_ERROR;
1746             break;
1747     }
1748 
1749     return error;
1750 }
1751 
1752 /*
1753  * NSSCKFWC_Login
1754  *
1755  */
1756 NSS_IMPLEMENT CK_RV
NSSCKFWC_Login(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_USER_TYPE userType,CK_CHAR_PTR pPin,CK_ULONG ulPinLen)1757 NSSCKFWC_Login(
1758     NSSCKFWInstance *fwInstance,
1759     CK_SESSION_HANDLE hSession,
1760     CK_USER_TYPE userType,
1761     CK_CHAR_PTR pPin,
1762     CK_ULONG ulPinLen)
1763 {
1764     CK_RV error = CKR_OK;
1765     NSSCKFWSession *fwSession;
1766     NSSItem pin, *arg;
1767 
1768     if (!fwInstance) {
1769         error = CKR_CRYPTOKI_NOT_INITIALIZED;
1770         goto loser;
1771     }
1772 
1773     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
1774     if (!fwSession) {
1775         error = CKR_SESSION_HANDLE_INVALID;
1776         goto loser;
1777     }
1778 
1779     if ((CK_CHAR_PTR)CK_NULL_PTR == pPin) {
1780         arg = (NSSItem *)NULL;
1781     } else {
1782         arg = &pin;
1783         pin.size = (PRUint32)ulPinLen;
1784         pin.data = (void *)pPin;
1785     }
1786 
1787     error = nssCKFWSession_Login(fwSession, userType, arg);
1788     if (CKR_OK != error) {
1789         goto loser;
1790     }
1791 
1792     return CKR_OK;
1793 
1794 loser:
1795     switch (error) {
1796         case CKR_SESSION_CLOSED:
1797             /* destroy session? */
1798             break;
1799         case CKR_DEVICE_REMOVED:
1800             /* (void)nssCKFWToken_Destroy(fwToken); */
1801             break;
1802         case CKR_CRYPTOKI_NOT_INITIALIZED:
1803         case CKR_DEVICE_ERROR:
1804         case CKR_DEVICE_MEMORY:
1805         case CKR_FUNCTION_FAILED:
1806         case CKR_GENERAL_ERROR:
1807         case CKR_HOST_MEMORY:
1808         case CKR_PIN_EXPIRED:
1809         case CKR_PIN_INCORRECT:
1810         case CKR_PIN_LOCKED:
1811         case CKR_SESSION_HANDLE_INVALID:
1812         case CKR_SESSION_READ_ONLY_EXISTS:
1813         case CKR_USER_ALREADY_LOGGED_IN:
1814         case CKR_USER_ANOTHER_ALREADY_LOGGED_IN:
1815         case CKR_USER_PIN_NOT_INITIALIZED:
1816         case CKR_USER_TOO_MANY_TYPES:
1817         case CKR_USER_TYPE_INVALID:
1818             break;
1819         default:
1820         case CKR_OK:
1821             error = CKR_GENERAL_ERROR;
1822             break;
1823     }
1824 
1825     return error;
1826 }
1827 
1828 /*
1829  * NSSCKFWC_Logout
1830  *
1831  */
1832 NSS_IMPLEMENT CK_RV
NSSCKFWC_Logout(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession)1833 NSSCKFWC_Logout(
1834     NSSCKFWInstance *fwInstance,
1835     CK_SESSION_HANDLE hSession)
1836 {
1837     CK_RV error = CKR_OK;
1838     NSSCKFWSession *fwSession;
1839 
1840     if (!fwInstance) {
1841         error = CKR_CRYPTOKI_NOT_INITIALIZED;
1842         goto loser;
1843     }
1844 
1845     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
1846     if (!fwSession) {
1847         error = CKR_SESSION_HANDLE_INVALID;
1848         goto loser;
1849     }
1850 
1851     error = nssCKFWSession_Logout(fwSession);
1852     if (CKR_OK != error) {
1853         goto loser;
1854     }
1855 
1856     return CKR_OK;
1857 
1858 loser:
1859     switch (error) {
1860         case CKR_SESSION_CLOSED:
1861             /* destroy session? */
1862             break;
1863         case CKR_DEVICE_REMOVED:
1864             /* (void)nssCKFWToken_Destroy(fwToken); */
1865             break;
1866         case CKR_CRYPTOKI_NOT_INITIALIZED:
1867         case CKR_DEVICE_ERROR:
1868         case CKR_DEVICE_MEMORY:
1869         case CKR_FUNCTION_FAILED:
1870         case CKR_GENERAL_ERROR:
1871         case CKR_HOST_MEMORY:
1872         case CKR_SESSION_HANDLE_INVALID:
1873         case CKR_USER_NOT_LOGGED_IN:
1874             break;
1875         default:
1876         case CKR_OK:
1877             error = CKR_GENERAL_ERROR;
1878             break;
1879     }
1880 
1881     return error;
1882 }
1883 
1884 /*
1885  * NSSCKFWC_CreateObject
1886  *
1887  */
1888 NSS_IMPLEMENT CK_RV
NSSCKFWC_CreateObject(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_ATTRIBUTE_PTR pTemplate,CK_ULONG ulCount,CK_OBJECT_HANDLE_PTR phObject)1889 NSSCKFWC_CreateObject(
1890     NSSCKFWInstance *fwInstance,
1891     CK_SESSION_HANDLE hSession,
1892     CK_ATTRIBUTE_PTR pTemplate,
1893     CK_ULONG ulCount,
1894     CK_OBJECT_HANDLE_PTR phObject)
1895 {
1896     CK_RV error = CKR_OK;
1897     NSSCKFWSession *fwSession;
1898     NSSCKFWObject *fwObject;
1899 
1900     if (!fwInstance) {
1901         error = CKR_CRYPTOKI_NOT_INITIALIZED;
1902         goto loser;
1903     }
1904 
1905     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
1906     if (!fwSession) {
1907         error = CKR_SESSION_HANDLE_INVALID;
1908         goto loser;
1909     }
1910 
1911     if ((CK_OBJECT_HANDLE_PTR)CK_NULL_PTR == phObject) {
1912         error = CKR_ARGUMENTS_BAD;
1913         goto loser;
1914     }
1915 
1916     /*
1917      * A purify error here indicates caller error.
1918      */
1919     *phObject = (CK_OBJECT_HANDLE)0;
1920 
1921     fwObject = nssCKFWSession_CreateObject(fwSession, pTemplate,
1922                                            ulCount, &error);
1923     if (!fwObject) {
1924         goto loser;
1925     }
1926 
1927     *phObject = nssCKFWInstance_CreateObjectHandle(fwInstance, fwObject, &error);
1928     if ((CK_OBJECT_HANDLE)0 == *phObject) {
1929         nssCKFWObject_Destroy(fwObject);
1930         goto loser;
1931     }
1932 
1933     return CKR_OK;
1934 
1935 loser:
1936     switch (error) {
1937         case CKR_SESSION_CLOSED:
1938             /* destroy session? */
1939             break;
1940         case CKR_DEVICE_REMOVED:
1941             /* (void)nssCKFWToken_Destroy(fwToken); */
1942             break;
1943         case CKR_ATTRIBUTE_READ_ONLY:
1944         case CKR_ATTRIBUTE_TYPE_INVALID:
1945         case CKR_ATTRIBUTE_VALUE_INVALID:
1946         case CKR_CRYPTOKI_NOT_INITIALIZED:
1947         case CKR_DEVICE_ERROR:
1948         case CKR_DEVICE_MEMORY:
1949         case CKR_FUNCTION_FAILED:
1950         case CKR_GENERAL_ERROR:
1951         case CKR_HOST_MEMORY:
1952         case CKR_SESSION_HANDLE_INVALID:
1953         case CKR_SESSION_READ_ONLY:
1954         case CKR_TEMPLATE_INCOMPLETE:
1955         case CKR_TEMPLATE_INCONSISTENT:
1956         case CKR_TOKEN_WRITE_PROTECTED:
1957         case CKR_USER_NOT_LOGGED_IN:
1958             break;
1959         default:
1960         case CKR_OK:
1961             error = CKR_GENERAL_ERROR;
1962             break;
1963     }
1964 
1965     return error;
1966 }
1967 
1968 /*
1969  * NSSCKFWC_CopyObject
1970  *
1971  */
1972 NSS_IMPLEMENT CK_RV
NSSCKFWC_CopyObject(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_OBJECT_HANDLE hObject,CK_ATTRIBUTE_PTR pTemplate,CK_ULONG ulCount,CK_OBJECT_HANDLE_PTR phNewObject)1973 NSSCKFWC_CopyObject(
1974     NSSCKFWInstance *fwInstance,
1975     CK_SESSION_HANDLE hSession,
1976     CK_OBJECT_HANDLE hObject,
1977     CK_ATTRIBUTE_PTR pTemplate,
1978     CK_ULONG ulCount,
1979     CK_OBJECT_HANDLE_PTR phNewObject)
1980 {
1981     CK_RV error = CKR_OK;
1982     NSSCKFWSession *fwSession;
1983     NSSCKFWObject *fwObject;
1984     NSSCKFWObject *fwNewObject;
1985 
1986     if (!fwInstance) {
1987         error = CKR_CRYPTOKI_NOT_INITIALIZED;
1988         goto loser;
1989     }
1990 
1991     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
1992     if (!fwSession) {
1993         error = CKR_SESSION_HANDLE_INVALID;
1994         goto loser;
1995     }
1996 
1997     if ((CK_OBJECT_HANDLE_PTR)CK_NULL_PTR == phNewObject) {
1998         error = CKR_ARGUMENTS_BAD;
1999         goto loser;
2000     }
2001 
2002     /*
2003      * A purify error here indicates caller error.
2004      */
2005     *phNewObject = (CK_OBJECT_HANDLE)0;
2006 
2007     fwObject = nssCKFWInstance_ResolveObjectHandle(fwInstance, hObject);
2008     if (!fwObject) {
2009         error = CKR_OBJECT_HANDLE_INVALID;
2010         goto loser;
2011     }
2012 
2013     fwNewObject = nssCKFWSession_CopyObject(fwSession, fwObject,
2014                                             pTemplate, ulCount, &error);
2015     if (!fwNewObject) {
2016         goto loser;
2017     }
2018 
2019     *phNewObject = nssCKFWInstance_CreateObjectHandle(fwInstance,
2020                                                       fwNewObject, &error);
2021     if ((CK_OBJECT_HANDLE)0 == *phNewObject) {
2022         nssCKFWObject_Destroy(fwNewObject);
2023         goto loser;
2024     }
2025 
2026     return CKR_OK;
2027 
2028 loser:
2029     switch (error) {
2030         case CKR_SESSION_CLOSED:
2031             /* destroy session? */
2032             break;
2033         case CKR_DEVICE_REMOVED:
2034             /* (void)nssCKFWToken_Destroy(fwToken); */
2035             break;
2036         case CKR_ATTRIBUTE_READ_ONLY:
2037         case CKR_ATTRIBUTE_TYPE_INVALID:
2038         case CKR_ATTRIBUTE_VALUE_INVALID:
2039         case CKR_CRYPTOKI_NOT_INITIALIZED:
2040         case CKR_DEVICE_ERROR:
2041         case CKR_DEVICE_MEMORY:
2042         case CKR_FUNCTION_FAILED:
2043         case CKR_GENERAL_ERROR:
2044         case CKR_HOST_MEMORY:
2045         case CKR_OBJECT_HANDLE_INVALID:
2046         case CKR_SESSION_HANDLE_INVALID:
2047         case CKR_SESSION_READ_ONLY:
2048         case CKR_TEMPLATE_INCONSISTENT:
2049         case CKR_TOKEN_WRITE_PROTECTED:
2050         case CKR_USER_NOT_LOGGED_IN:
2051             break;
2052         default:
2053         case CKR_OK:
2054             error = CKR_GENERAL_ERROR;
2055             break;
2056     }
2057 
2058     return error;
2059 }
2060 
2061 /*
2062  * NSSCKFWC_DestroyObject
2063  *
2064  */
2065 NSS_IMPLEMENT CK_RV
NSSCKFWC_DestroyObject(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_OBJECT_HANDLE hObject)2066 NSSCKFWC_DestroyObject(
2067     NSSCKFWInstance *fwInstance,
2068     CK_SESSION_HANDLE hSession,
2069     CK_OBJECT_HANDLE hObject)
2070 {
2071     CK_RV error = CKR_OK;
2072     NSSCKFWSession *fwSession;
2073     NSSCKFWObject *fwObject;
2074 
2075     if (!fwInstance) {
2076         error = CKR_CRYPTOKI_NOT_INITIALIZED;
2077         goto loser;
2078     }
2079 
2080     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
2081     if (!fwSession) {
2082         error = CKR_SESSION_HANDLE_INVALID;
2083         goto loser;
2084     }
2085 
2086     fwObject = nssCKFWInstance_ResolveObjectHandle(fwInstance, hObject);
2087     if (!fwObject) {
2088         error = CKR_OBJECT_HANDLE_INVALID;
2089         goto loser;
2090     }
2091 
2092     nssCKFWInstance_DestroyObjectHandle(fwInstance, hObject);
2093     nssCKFWObject_Destroy(fwObject);
2094 
2095     return CKR_OK;
2096 
2097 loser:
2098     switch (error) {
2099         case CKR_SESSION_CLOSED:
2100             /* destroy session? */
2101             break;
2102         case CKR_DEVICE_REMOVED:
2103             /* (void)nssCKFWToken_Destroy(fwToken); */
2104             break;
2105         case CKR_CRYPTOKI_NOT_INITIALIZED:
2106         case CKR_DEVICE_ERROR:
2107         case CKR_DEVICE_MEMORY:
2108         case CKR_FUNCTION_FAILED:
2109         case CKR_GENERAL_ERROR:
2110         case CKR_HOST_MEMORY:
2111         case CKR_OBJECT_HANDLE_INVALID:
2112         case CKR_SESSION_HANDLE_INVALID:
2113         case CKR_SESSION_READ_ONLY:
2114         case CKR_TOKEN_WRITE_PROTECTED:
2115             break;
2116         default:
2117         case CKR_OK:
2118             error = CKR_GENERAL_ERROR;
2119             break;
2120     }
2121 
2122     return error;
2123 }
2124 
2125 /*
2126  * NSSCKFWC_GetObjectSize
2127  *
2128  */
2129 NSS_IMPLEMENT CK_RV
NSSCKFWC_GetObjectSize(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_OBJECT_HANDLE hObject,CK_ULONG_PTR pulSize)2130 NSSCKFWC_GetObjectSize(
2131     NSSCKFWInstance *fwInstance,
2132     CK_SESSION_HANDLE hSession,
2133     CK_OBJECT_HANDLE hObject,
2134     CK_ULONG_PTR pulSize)
2135 {
2136     CK_RV error = CKR_OK;
2137     NSSCKFWSession *fwSession;
2138     NSSCKFWObject *fwObject;
2139 
2140     if (!fwInstance) {
2141         error = CKR_CRYPTOKI_NOT_INITIALIZED;
2142         goto loser;
2143     }
2144 
2145     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
2146     if (!fwSession) {
2147         error = CKR_SESSION_HANDLE_INVALID;
2148         goto loser;
2149     }
2150 
2151     fwObject = nssCKFWInstance_ResolveObjectHandle(fwInstance, hObject);
2152     if (!fwObject) {
2153         error = CKR_OBJECT_HANDLE_INVALID;
2154         goto loser;
2155     }
2156 
2157     if ((CK_ULONG_PTR)CK_NULL_PTR == pulSize) {
2158         error = CKR_ARGUMENTS_BAD;
2159         goto loser;
2160     }
2161 
2162     /*
2163      * A purify error here indicates caller error.
2164      */
2165     *pulSize = (CK_ULONG)0;
2166 
2167     *pulSize = nssCKFWObject_GetObjectSize(fwObject, &error);
2168     if (((CK_ULONG)0 == *pulSize) && (CKR_OK != error)) {
2169         goto loser;
2170     }
2171 
2172     return CKR_OK;
2173 
2174 loser:
2175     switch (error) {
2176         case CKR_SESSION_CLOSED:
2177             /* destroy session? */
2178             break;
2179         case CKR_DEVICE_REMOVED:
2180             /* (void)nssCKFWToken_Destroy(fwToken); */
2181             break;
2182         case CKR_CRYPTOKI_NOT_INITIALIZED:
2183         case CKR_DEVICE_ERROR:
2184         case CKR_DEVICE_MEMORY:
2185         case CKR_FUNCTION_FAILED:
2186         case CKR_GENERAL_ERROR:
2187         case CKR_HOST_MEMORY:
2188         case CKR_INFORMATION_SENSITIVE:
2189         case CKR_OBJECT_HANDLE_INVALID:
2190         case CKR_SESSION_HANDLE_INVALID:
2191             break;
2192         default:
2193         case CKR_OK:
2194             error = CKR_GENERAL_ERROR;
2195             break;
2196     }
2197 
2198     return error;
2199 }
2200 
2201 /*
2202  * NSSCKFWC_GetAttributeValue
2203  *
2204  */
2205 NSS_IMPLEMENT CK_RV
NSSCKFWC_GetAttributeValue(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_OBJECT_HANDLE hObject,CK_ATTRIBUTE_PTR pTemplate,CK_ULONG ulCount)2206 NSSCKFWC_GetAttributeValue(
2207     NSSCKFWInstance *fwInstance,
2208     CK_SESSION_HANDLE hSession,
2209     CK_OBJECT_HANDLE hObject,
2210     CK_ATTRIBUTE_PTR pTemplate,
2211     CK_ULONG ulCount)
2212 {
2213     CK_RV error = CKR_OK;
2214     NSSCKFWSession *fwSession;
2215     NSSCKFWObject *fwObject;
2216     CK_BBOOL sensitive = CK_FALSE;
2217     CK_BBOOL invalid = CK_FALSE;
2218     CK_BBOOL tooSmall = CK_FALSE;
2219     CK_ULONG i;
2220 
2221     if (!fwInstance) {
2222         error = CKR_CRYPTOKI_NOT_INITIALIZED;
2223         goto loser;
2224     }
2225 
2226     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
2227     if (!fwSession) {
2228         error = CKR_SESSION_HANDLE_INVALID;
2229         goto loser;
2230     }
2231 
2232     fwObject = nssCKFWInstance_ResolveObjectHandle(fwInstance, hObject);
2233     if (!fwObject) {
2234         error = CKR_OBJECT_HANDLE_INVALID;
2235         goto loser;
2236     }
2237 
2238     if ((CK_ATTRIBUTE_PTR)CK_NULL_PTR == pTemplate) {
2239         error = CKR_ARGUMENTS_BAD;
2240         goto loser;
2241     }
2242 
2243     for (i = 0; i < ulCount; i++) {
2244         CK_ULONG size = nssCKFWObject_GetAttributeSize(fwObject,
2245                                                        pTemplate[i].type, &error);
2246         if ((CK_ULONG)0 == size) {
2247             switch (error) {
2248                 case CKR_ATTRIBUTE_SENSITIVE:
2249                 case CKR_INFORMATION_SENSITIVE:
2250                     sensitive =
2251                         CK_TRUE;
2252                     pTemplate[i].ulValueLen =
2253                         (CK_ULONG)(-1);
2254                     continue;
2255                 case CKR_ATTRIBUTE_TYPE_INVALID:
2256                     invalid =
2257                         CK_TRUE;
2258                     pTemplate[i].ulValueLen =
2259                         (CK_ULONG)(-1);
2260                     continue;
2261                 case CKR_OK:
2262                     break;
2263                 default:
2264                     goto loser;
2265             }
2266         }
2267 
2268         if ((CK_VOID_PTR)CK_NULL_PTR == pTemplate[i].pValue) {
2269             pTemplate[i].ulValueLen = size;
2270         } else {
2271             NSSItem it, *p;
2272 
2273             if (pTemplate[i].ulValueLen < size) {
2274                 tooSmall = CK_TRUE;
2275                 continue;
2276             }
2277 
2278             it.size = (PRUint32)pTemplate[i].ulValueLen;
2279             it.data = (void *)pTemplate[i].pValue;
2280             p = nssCKFWObject_GetAttribute(fwObject, pTemplate[i].type, &it,
2281                                            (NSSArena *)NULL, &error);
2282             if (!p) {
2283                 switch (error) {
2284                     case CKR_ATTRIBUTE_SENSITIVE:
2285                     case CKR_INFORMATION_SENSITIVE:
2286                         sensitive =
2287                             CK_TRUE;
2288                         pTemplate[i].ulValueLen =
2289                             (CK_ULONG)(-1);
2290                         continue;
2291                     case CKR_ATTRIBUTE_TYPE_INVALID:
2292                         invalid =
2293                             CK_TRUE;
2294                         pTemplate[i].ulValueLen =
2295                             (CK_ULONG)(-1);
2296                         continue;
2297                     default:
2298                         goto loser;
2299                 }
2300             }
2301 
2302             pTemplate[i].ulValueLen = size;
2303         }
2304     }
2305 
2306     if (sensitive) {
2307         error = CKR_ATTRIBUTE_SENSITIVE;
2308         goto loser;
2309     } else if (invalid) {
2310         error = CKR_ATTRIBUTE_TYPE_INVALID;
2311         goto loser;
2312     } else if (tooSmall) {
2313         error = CKR_BUFFER_TOO_SMALL;
2314         goto loser;
2315     }
2316 
2317     return CKR_OK;
2318 
2319 loser:
2320     switch (error) {
2321         case CKR_SESSION_CLOSED:
2322             /* destroy session? */
2323             break;
2324         case CKR_DEVICE_REMOVED:
2325             /* (void)nssCKFWToken_Destroy(fwToken); */
2326             break;
2327         case CKR_ATTRIBUTE_SENSITIVE:
2328         case CKR_ATTRIBUTE_TYPE_INVALID:
2329         case CKR_BUFFER_TOO_SMALL:
2330         case CKR_CRYPTOKI_NOT_INITIALIZED:
2331         case CKR_DEVICE_ERROR:
2332         case CKR_DEVICE_MEMORY:
2333         case CKR_FUNCTION_FAILED:
2334         case CKR_GENERAL_ERROR:
2335         case CKR_HOST_MEMORY:
2336         case CKR_OBJECT_HANDLE_INVALID:
2337         case CKR_SESSION_HANDLE_INVALID:
2338             break;
2339         default:
2340         case CKR_OK:
2341             error = CKR_GENERAL_ERROR;
2342             break;
2343     }
2344 
2345     return error;
2346 }
2347 
2348 /*
2349  * NSSCKFWC_SetAttributeValue
2350  *
2351  */
2352 NSS_IMPLEMENT CK_RV
NSSCKFWC_SetAttributeValue(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_OBJECT_HANDLE hObject,CK_ATTRIBUTE_PTR pTemplate,CK_ULONG ulCount)2353 NSSCKFWC_SetAttributeValue(
2354     NSSCKFWInstance *fwInstance,
2355     CK_SESSION_HANDLE hSession,
2356     CK_OBJECT_HANDLE hObject,
2357     CK_ATTRIBUTE_PTR pTemplate,
2358     CK_ULONG ulCount)
2359 {
2360     CK_RV error = CKR_OK;
2361     NSSCKFWSession *fwSession;
2362     NSSCKFWObject *fwObject;
2363     CK_ULONG i;
2364 
2365     if (!fwInstance) {
2366         error = CKR_CRYPTOKI_NOT_INITIALIZED;
2367         goto loser;
2368     }
2369 
2370     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
2371     if (!fwSession) {
2372         error = CKR_SESSION_HANDLE_INVALID;
2373         goto loser;
2374     }
2375 
2376     fwObject = nssCKFWInstance_ResolveObjectHandle(fwInstance, hObject);
2377     if (!fwObject) {
2378         error = CKR_OBJECT_HANDLE_INVALID;
2379         goto loser;
2380     }
2381 
2382     if ((CK_ATTRIBUTE_PTR)CK_NULL_PTR == pTemplate) {
2383         error = CKR_ARGUMENTS_BAD;
2384         goto loser;
2385     }
2386 
2387     for (i = 0; i < ulCount; i++) {
2388         NSSItem value;
2389 
2390         value.data = pTemplate[i].pValue;
2391         value.size = pTemplate[i].ulValueLen;
2392 
2393         error = nssCKFWObject_SetAttribute(fwObject, fwSession,
2394                                            pTemplate[i].type, &value);
2395 
2396         if (CKR_OK != error) {
2397             goto loser;
2398         }
2399     }
2400 
2401     return CKR_OK;
2402 
2403 loser:
2404     switch (error) {
2405         case CKR_SESSION_CLOSED:
2406             /* destroy session? */
2407             break;
2408         case CKR_DEVICE_REMOVED:
2409             /* (void)nssCKFWToken_Destroy(fwToken); */
2410             break;
2411         case CKR_ATTRIBUTE_READ_ONLY:
2412         case CKR_ATTRIBUTE_TYPE_INVALID:
2413         case CKR_ATTRIBUTE_VALUE_INVALID:
2414         case CKR_CRYPTOKI_NOT_INITIALIZED:
2415         case CKR_DEVICE_ERROR:
2416         case CKR_DEVICE_MEMORY:
2417         case CKR_FUNCTION_FAILED:
2418         case CKR_GENERAL_ERROR:
2419         case CKR_HOST_MEMORY:
2420         case CKR_OBJECT_HANDLE_INVALID:
2421         case CKR_SESSION_HANDLE_INVALID:
2422         case CKR_SESSION_READ_ONLY:
2423         case CKR_TEMPLATE_INCONSISTENT:
2424         case CKR_TOKEN_WRITE_PROTECTED:
2425             break;
2426         default:
2427         case CKR_OK:
2428             error = CKR_GENERAL_ERROR;
2429             break;
2430     }
2431 
2432     return error;
2433 }
2434 
2435 /*
2436  * NSSCKFWC_FindObjectsInit
2437  *
2438  */
2439 NSS_IMPLEMENT CK_RV
NSSCKFWC_FindObjectsInit(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_ATTRIBUTE_PTR pTemplate,CK_ULONG ulCount)2440 NSSCKFWC_FindObjectsInit(
2441     NSSCKFWInstance *fwInstance,
2442     CK_SESSION_HANDLE hSession,
2443     CK_ATTRIBUTE_PTR pTemplate,
2444     CK_ULONG ulCount)
2445 {
2446     CK_RV error = CKR_OK;
2447     NSSCKFWSession *fwSession;
2448     NSSCKFWFindObjects *fwFindObjects;
2449 
2450     if (!fwInstance) {
2451         error = CKR_CRYPTOKI_NOT_INITIALIZED;
2452         goto loser;
2453     }
2454 
2455     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
2456     if (!fwSession) {
2457         error = CKR_SESSION_HANDLE_INVALID;
2458         goto loser;
2459     }
2460 
2461     if (((CK_ATTRIBUTE_PTR)CK_NULL_PTR == pTemplate) && (ulCount != 0)) {
2462         error = CKR_ARGUMENTS_BAD;
2463         goto loser;
2464     }
2465 
2466     fwFindObjects = nssCKFWSession_GetFWFindObjects(fwSession, &error);
2467     if (fwFindObjects) {
2468         error = CKR_OPERATION_ACTIVE;
2469         goto loser;
2470     }
2471 
2472     if (CKR_OPERATION_NOT_INITIALIZED != error) {
2473         goto loser;
2474     }
2475 
2476     fwFindObjects = nssCKFWSession_FindObjectsInit(fwSession,
2477                                                    pTemplate, ulCount, &error);
2478     if (!fwFindObjects) {
2479         goto loser;
2480     }
2481 
2482     error = nssCKFWSession_SetFWFindObjects(fwSession, fwFindObjects);
2483 
2484     if (CKR_OK != error) {
2485         nssCKFWFindObjects_Destroy(fwFindObjects);
2486         goto loser;
2487     }
2488 
2489     return CKR_OK;
2490 
2491 loser:
2492     switch (error) {
2493         case CKR_SESSION_CLOSED:
2494             /* destroy session? */
2495             break;
2496         case CKR_DEVICE_REMOVED:
2497             /* (void)nssCKFWToken_Destroy(fwToken); */
2498             break;
2499         case CKR_ATTRIBUTE_TYPE_INVALID:
2500         case CKR_ATTRIBUTE_VALUE_INVALID:
2501         case CKR_CRYPTOKI_NOT_INITIALIZED:
2502         case CKR_DEVICE_ERROR:
2503         case CKR_DEVICE_MEMORY:
2504         case CKR_FUNCTION_FAILED:
2505         case CKR_GENERAL_ERROR:
2506         case CKR_HOST_MEMORY:
2507         case CKR_OPERATION_ACTIVE:
2508         case CKR_SESSION_HANDLE_INVALID:
2509             break;
2510         default:
2511         case CKR_OK:
2512             error = CKR_GENERAL_ERROR;
2513             break;
2514     }
2515 
2516     return error;
2517 }
2518 
2519 /*
2520  * NSSCKFWC_FindObjects
2521  *
2522  */
2523 NSS_IMPLEMENT CK_RV
NSSCKFWC_FindObjects(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_OBJECT_HANDLE_PTR phObject,CK_ULONG ulMaxObjectCount,CK_ULONG_PTR pulObjectCount)2524 NSSCKFWC_FindObjects(
2525     NSSCKFWInstance *fwInstance,
2526     CK_SESSION_HANDLE hSession,
2527     CK_OBJECT_HANDLE_PTR phObject,
2528     CK_ULONG ulMaxObjectCount,
2529     CK_ULONG_PTR pulObjectCount)
2530 {
2531     CK_RV error = CKR_OK;
2532     NSSCKFWSession *fwSession;
2533     NSSCKFWFindObjects *fwFindObjects;
2534     CK_ULONG i;
2535 
2536     if (!fwInstance) {
2537         error = CKR_CRYPTOKI_NOT_INITIALIZED;
2538         goto loser;
2539     }
2540 
2541     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
2542     if (!fwSession) {
2543         error = CKR_SESSION_HANDLE_INVALID;
2544         goto loser;
2545     }
2546 
2547     if ((CK_OBJECT_HANDLE_PTR)CK_NULL_PTR == phObject) {
2548         error = CKR_ARGUMENTS_BAD;
2549         goto loser;
2550     }
2551 
2552     /*
2553      * A purify error here indicates caller error.
2554      */
2555     (void)nsslibc_memset(phObject, 0, sizeof(CK_OBJECT_HANDLE) * ulMaxObjectCount);
2556     *pulObjectCount = (CK_ULONG)0;
2557 
2558     fwFindObjects = nssCKFWSession_GetFWFindObjects(fwSession, &error);
2559     if (!fwFindObjects) {
2560         goto loser;
2561     }
2562 
2563     for (i = 0; i < ulMaxObjectCount; i++) {
2564         NSSCKFWObject *fwObject = nssCKFWFindObjects_Next(fwFindObjects,
2565                                                           NULL, &error);
2566         if (!fwObject) {
2567             break;
2568         }
2569 
2570         phObject[i] = nssCKFWInstance_FindObjectHandle(fwInstance, fwObject);
2571         if ((CK_OBJECT_HANDLE)0 == phObject[i]) {
2572             phObject[i] = nssCKFWInstance_CreateObjectHandle(fwInstance, fwObject, &error);
2573         }
2574         if ((CK_OBJECT_HANDLE)0 == phObject[i]) {
2575             /* This isn't right either, is it? */
2576             nssCKFWObject_Destroy(fwObject);
2577             goto loser;
2578         }
2579     }
2580 
2581     *pulObjectCount = i;
2582 
2583     return CKR_OK;
2584 
2585 loser:
2586     switch (error) {
2587         case CKR_SESSION_CLOSED:
2588             /* destroy session? */
2589             break;
2590         case CKR_DEVICE_REMOVED:
2591             /* (void)nssCKFWToken_Destroy(fwToken); */
2592             break;
2593         case CKR_CRYPTOKI_NOT_INITIALIZED:
2594         case CKR_DEVICE_ERROR:
2595         case CKR_DEVICE_MEMORY:
2596         case CKR_FUNCTION_FAILED:
2597         case CKR_GENERAL_ERROR:
2598         case CKR_HOST_MEMORY:
2599         case CKR_OPERATION_NOT_INITIALIZED:
2600         case CKR_SESSION_HANDLE_INVALID:
2601             break;
2602         default:
2603         case CKR_OK:
2604             error = CKR_GENERAL_ERROR;
2605             break;
2606     }
2607 
2608     return error;
2609 }
2610 
2611 /*
2612  * NSSCKFWC_FindObjectsFinal
2613  *
2614  */
2615 NSS_IMPLEMENT CK_RV
NSSCKFWC_FindObjectsFinal(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession)2616 NSSCKFWC_FindObjectsFinal(
2617     NSSCKFWInstance *fwInstance,
2618     CK_SESSION_HANDLE hSession)
2619 {
2620     CK_RV error = CKR_OK;
2621     NSSCKFWSession *fwSession;
2622     NSSCKFWFindObjects *fwFindObjects;
2623 
2624     if (!fwInstance) {
2625         error = CKR_CRYPTOKI_NOT_INITIALIZED;
2626         goto loser;
2627     }
2628 
2629     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
2630     if (!fwSession) {
2631         error = CKR_SESSION_HANDLE_INVALID;
2632         goto loser;
2633     }
2634 
2635     fwFindObjects = nssCKFWSession_GetFWFindObjects(fwSession, &error);
2636     if (!fwFindObjects) {
2637         error = CKR_OPERATION_NOT_INITIALIZED;
2638         goto loser;
2639     }
2640 
2641     nssCKFWFindObjects_Destroy(fwFindObjects);
2642     error = nssCKFWSession_SetFWFindObjects(fwSession,
2643                                             (NSSCKFWFindObjects *)NULL);
2644 
2645     if (CKR_OK != error) {
2646         goto loser;
2647     }
2648 
2649     return CKR_OK;
2650 
2651 loser:
2652     switch (error) {
2653         case CKR_SESSION_CLOSED:
2654             /* destroy session? */
2655             break;
2656         case CKR_DEVICE_REMOVED:
2657             /* (void)nssCKFWToken_Destroy(fwToken); */
2658             break;
2659         case CKR_CRYPTOKI_NOT_INITIALIZED:
2660         case CKR_DEVICE_ERROR:
2661         case CKR_DEVICE_MEMORY:
2662         case CKR_FUNCTION_FAILED:
2663         case CKR_GENERAL_ERROR:
2664         case CKR_HOST_MEMORY:
2665         case CKR_OPERATION_NOT_INITIALIZED:
2666         case CKR_SESSION_HANDLE_INVALID:
2667             break;
2668         default:
2669         case CKR_OK:
2670             error = CKR_GENERAL_ERROR;
2671             break;
2672     }
2673 
2674     return error;
2675 }
2676 
2677 /*
2678  * NSSCKFWC_EncryptInit
2679  *
2680  */
2681 NSS_IMPLEMENT CK_RV
NSSCKFWC_EncryptInit(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_MECHANISM_PTR pMechanism,CK_OBJECT_HANDLE hKey)2682 NSSCKFWC_EncryptInit(
2683     NSSCKFWInstance *fwInstance,
2684     CK_SESSION_HANDLE hSession,
2685     CK_MECHANISM_PTR pMechanism,
2686     CK_OBJECT_HANDLE hKey)
2687 {
2688     CK_RV error = CKR_OK;
2689     NSSCKFWSession *fwSession;
2690     NSSCKFWObject *fwObject;
2691     NSSCKFWSlot *fwSlot;
2692     NSSCKFWToken *fwToken;
2693     NSSCKFWMechanism *fwMechanism;
2694 
2695     if (!fwInstance) {
2696         error = CKR_CRYPTOKI_NOT_INITIALIZED;
2697         goto loser;
2698     }
2699 
2700     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
2701     if (!fwSession) {
2702         error = CKR_SESSION_HANDLE_INVALID;
2703         goto loser;
2704     }
2705 
2706     fwObject = nssCKFWInstance_ResolveObjectHandle(fwInstance, hKey);
2707     if (!fwObject) {
2708         error = CKR_KEY_HANDLE_INVALID;
2709         goto loser;
2710     }
2711 
2712     fwSlot = nssCKFWSession_GetFWSlot(fwSession);
2713     if (!fwSlot) {
2714         error = CKR_GENERAL_ERROR; /* should never happen! */
2715         goto loser;
2716     }
2717 
2718     if (CK_TRUE != nssCKFWSlot_GetTokenPresent(fwSlot)) {
2719         error = CKR_TOKEN_NOT_PRESENT;
2720         goto loser;
2721     }
2722 
2723     fwToken = nssCKFWSlot_GetToken(fwSlot, &error);
2724     if (!fwToken) {
2725         goto loser;
2726     }
2727 
2728     fwMechanism = nssCKFWToken_GetMechanism(fwToken, pMechanism->mechanism, &error);
2729     if (!fwMechanism) {
2730         goto loser;
2731     }
2732 
2733     error = nssCKFWMechanism_EncryptInit(fwMechanism, pMechanism,
2734                                          fwSession, fwObject);
2735 
2736     nssCKFWMechanism_Destroy(fwMechanism);
2737 
2738     if (CKR_OK == error) {
2739         return CKR_OK;
2740     }
2741 
2742 loser:
2743     /* verify error */
2744     switch (error) {
2745         case CKR_CRYPTOKI_NOT_INITIALIZED:
2746         case CKR_DEVICE_ERROR:
2747         case CKR_DEVICE_MEMORY:
2748         case CKR_DEVICE_REMOVED:
2749         case CKR_FUNCTION_CANCELED:
2750         case CKR_FUNCTION_FAILED:
2751         case CKR_GENERAL_ERROR:
2752         case CKR_HOST_MEMORY:
2753         case CKR_KEY_FUNCTION_NOT_PERMITTED:
2754         case CKR_KEY_HANDLE_INVALID:
2755         case CKR_KEY_SIZE_RANGE:
2756         case CKR_KEY_TYPE_INCONSISTENT:
2757         case CKR_MECHANISM_INVALID:
2758         case CKR_MECHANISM_PARAM_INVALID:
2759         case CKR_OPERATION_ACTIVE:
2760         case CKR_PIN_EXPIRED:
2761         case CKR_SESSION_CLOSED:
2762         case CKR_SESSION_HANDLE_INVALID:
2763         case CKR_USER_NOT_LOGGED_IN:
2764             break;
2765         default:
2766         case CKR_OK:
2767             error = CKR_GENERAL_ERROR;
2768             break;
2769     }
2770     return error;
2771 }
2772 
2773 /*
2774  * NSSCKFWC_Encrypt
2775  *
2776  */
2777 NSS_IMPLEMENT CK_RV
NSSCKFWC_Encrypt(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_BYTE_PTR pData,CK_ULONG ulDataLen,CK_BYTE_PTR pEncryptedData,CK_ULONG_PTR pulEncryptedDataLen)2778 NSSCKFWC_Encrypt(
2779     NSSCKFWInstance *fwInstance,
2780     CK_SESSION_HANDLE hSession,
2781     CK_BYTE_PTR pData,
2782     CK_ULONG ulDataLen,
2783     CK_BYTE_PTR pEncryptedData,
2784     CK_ULONG_PTR pulEncryptedDataLen)
2785 {
2786     CK_RV error = CKR_OK;
2787     NSSCKFWSession *fwSession;
2788 
2789     if (!fwInstance) {
2790         error = CKR_CRYPTOKI_NOT_INITIALIZED;
2791         goto loser;
2792     }
2793 
2794     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
2795     if (!fwSession) {
2796         error = CKR_SESSION_HANDLE_INVALID;
2797         goto loser;
2798     }
2799 
2800     error = nssCKFWSession_UpdateFinal(fwSession,
2801                                        NSSCKFWCryptoOperationType_Encrypt,
2802                                        NSSCKFWCryptoOperationState_EncryptDecrypt,
2803                                        pData, ulDataLen, pEncryptedData, pulEncryptedDataLen);
2804 
2805     if (CKR_OK == error) {
2806         return CKR_OK;
2807     }
2808 
2809 loser:
2810     /* verify error */
2811     switch (error) {
2812         case CKR_ARGUMENTS_BAD:
2813         case CKR_BUFFER_TOO_SMALL:
2814         case CKR_CRYPTOKI_NOT_INITIALIZED:
2815         case CKR_DATA_INVALID:
2816         case CKR_DATA_LEN_RANGE:
2817         case CKR_DEVICE_ERROR:
2818         case CKR_DEVICE_MEMORY:
2819         case CKR_DEVICE_REMOVED:
2820         case CKR_FUNCTION_CANCELED:
2821         case CKR_FUNCTION_FAILED:
2822         case CKR_GENERAL_ERROR:
2823         case CKR_HOST_MEMORY:
2824         case CKR_OPERATION_NOT_INITIALIZED:
2825         case CKR_SESSION_HANDLE_INVALID:
2826         case CKR_SESSION_CLOSED:
2827             break;
2828         default:
2829         case CKR_OK:
2830             error = CKR_GENERAL_ERROR;
2831             break;
2832     }
2833     return error;
2834 }
2835 
2836 /*
2837  * NSSCKFWC_EncryptUpdate
2838  *
2839  */
2840 NSS_IMPLEMENT CK_RV
NSSCKFWC_EncryptUpdate(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_BYTE_PTR pPart,CK_ULONG ulPartLen,CK_BYTE_PTR pEncryptedPart,CK_ULONG_PTR pulEncryptedPartLen)2841 NSSCKFWC_EncryptUpdate(
2842     NSSCKFWInstance *fwInstance,
2843     CK_SESSION_HANDLE hSession,
2844     CK_BYTE_PTR pPart,
2845     CK_ULONG ulPartLen,
2846     CK_BYTE_PTR pEncryptedPart,
2847     CK_ULONG_PTR pulEncryptedPartLen)
2848 {
2849     CK_RV error = CKR_OK;
2850     NSSCKFWSession *fwSession;
2851 
2852     if (!fwInstance) {
2853         error = CKR_CRYPTOKI_NOT_INITIALIZED;
2854         goto loser;
2855     }
2856 
2857     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
2858     if (!fwSession) {
2859         error = CKR_SESSION_HANDLE_INVALID;
2860         goto loser;
2861     }
2862 
2863     error = nssCKFWSession_Update(fwSession,
2864                                   NSSCKFWCryptoOperationType_Encrypt,
2865                                   NSSCKFWCryptoOperationState_EncryptDecrypt,
2866                                   pPart, ulPartLen, pEncryptedPart, pulEncryptedPartLen);
2867 
2868     if (CKR_OK == error) {
2869         return CKR_OK;
2870     }
2871 
2872 loser:
2873     /* verify error */
2874     switch (error) {
2875         case CKR_ARGUMENTS_BAD:
2876         case CKR_BUFFER_TOO_SMALL:
2877         case CKR_CRYPTOKI_NOT_INITIALIZED:
2878         case CKR_DATA_LEN_RANGE:
2879         case CKR_DEVICE_ERROR:
2880         case CKR_DEVICE_MEMORY:
2881         case CKR_DEVICE_REMOVED:
2882         case CKR_FUNCTION_CANCELED:
2883         case CKR_FUNCTION_FAILED:
2884         case CKR_GENERAL_ERROR:
2885         case CKR_HOST_MEMORY:
2886         case CKR_OPERATION_NOT_INITIALIZED:
2887         case CKR_SESSION_CLOSED:
2888         case CKR_SESSION_HANDLE_INVALID:
2889             break;
2890         default:
2891         case CKR_OK:
2892             error = CKR_GENERAL_ERROR;
2893             break;
2894     }
2895     return error;
2896 }
2897 
2898 /*
2899  * NSSCKFWC_EncryptFinal
2900  *
2901  */
2902 NSS_IMPLEMENT CK_RV
NSSCKFWC_EncryptFinal(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_BYTE_PTR pLastEncryptedPart,CK_ULONG_PTR pulLastEncryptedPartLen)2903 NSSCKFWC_EncryptFinal(
2904     NSSCKFWInstance *fwInstance,
2905     CK_SESSION_HANDLE hSession,
2906     CK_BYTE_PTR pLastEncryptedPart,
2907     CK_ULONG_PTR pulLastEncryptedPartLen)
2908 {
2909     CK_RV error = CKR_OK;
2910     NSSCKFWSession *fwSession;
2911 
2912     if (!fwInstance) {
2913         error = CKR_CRYPTOKI_NOT_INITIALIZED;
2914         goto loser;
2915     }
2916 
2917     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
2918     if (!fwSession) {
2919         error = CKR_SESSION_HANDLE_INVALID;
2920         goto loser;
2921     }
2922 
2923     error = nssCKFWSession_Final(fwSession,
2924                                  NSSCKFWCryptoOperationType_Encrypt,
2925                                  NSSCKFWCryptoOperationState_EncryptDecrypt,
2926                                  pLastEncryptedPart, pulLastEncryptedPartLen);
2927 
2928     if (CKR_OK == error) {
2929         return CKR_OK;
2930     }
2931 
2932 loser:
2933     /* verify error */
2934     switch (error) {
2935         case CKR_ARGUMENTS_BAD:
2936         case CKR_BUFFER_TOO_SMALL:
2937         case CKR_CRYPTOKI_NOT_INITIALIZED:
2938         case CKR_DATA_LEN_RANGE:
2939         case CKR_DEVICE_ERROR:
2940         case CKR_DEVICE_MEMORY:
2941         case CKR_DEVICE_REMOVED:
2942         case CKR_FUNCTION_CANCELED:
2943         case CKR_FUNCTION_FAILED:
2944         case CKR_GENERAL_ERROR:
2945         case CKR_HOST_MEMORY:
2946         case CKR_OPERATION_NOT_INITIALIZED:
2947         case CKR_SESSION_CLOSED:
2948         case CKR_SESSION_HANDLE_INVALID:
2949             break;
2950         default:
2951         case CKR_OK:
2952             error = CKR_GENERAL_ERROR;
2953             break;
2954     }
2955     return error;
2956 }
2957 
2958 /*
2959  * NSSCKFWC_DecryptInit
2960  *
2961  */
2962 NSS_IMPLEMENT CK_RV
NSSCKFWC_DecryptInit(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_MECHANISM_PTR pMechanism,CK_OBJECT_HANDLE hKey)2963 NSSCKFWC_DecryptInit(
2964     NSSCKFWInstance *fwInstance,
2965     CK_SESSION_HANDLE hSession,
2966     CK_MECHANISM_PTR pMechanism,
2967     CK_OBJECT_HANDLE hKey)
2968 {
2969     CK_RV error = CKR_OK;
2970     NSSCKFWSession *fwSession;
2971     NSSCKFWObject *fwObject;
2972     NSSCKFWSlot *fwSlot;
2973     NSSCKFWToken *fwToken;
2974     NSSCKFWMechanism *fwMechanism;
2975 
2976     if (!fwInstance) {
2977         error = CKR_CRYPTOKI_NOT_INITIALIZED;
2978         goto loser;
2979     }
2980 
2981     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
2982     if (!fwSession) {
2983         error = CKR_SESSION_HANDLE_INVALID;
2984         goto loser;
2985     }
2986 
2987     fwObject = nssCKFWInstance_ResolveObjectHandle(fwInstance, hKey);
2988     if (!fwObject) {
2989         error = CKR_KEY_HANDLE_INVALID;
2990         goto loser;
2991     }
2992 
2993     fwSlot = nssCKFWSession_GetFWSlot(fwSession);
2994     if (!fwSlot) {
2995         error = CKR_GENERAL_ERROR; /* should never happen! */
2996         goto loser;
2997     }
2998 
2999     if (CK_TRUE != nssCKFWSlot_GetTokenPresent(fwSlot)) {
3000         error = CKR_TOKEN_NOT_PRESENT;
3001         goto loser;
3002     }
3003 
3004     fwToken = nssCKFWSlot_GetToken(fwSlot, &error);
3005     if (!fwToken) {
3006         goto loser;
3007     }
3008 
3009     fwMechanism = nssCKFWToken_GetMechanism(fwToken, pMechanism->mechanism, &error);
3010     if (!fwMechanism) {
3011         goto loser;
3012     }
3013 
3014     error = nssCKFWMechanism_DecryptInit(fwMechanism, pMechanism,
3015                                          fwSession, fwObject);
3016     nssCKFWMechanism_Destroy(fwMechanism);
3017 
3018     if (CKR_OK == error) {
3019         return CKR_OK;
3020     }
3021 
3022 loser:
3023     /* verify error */
3024     switch (error) {
3025         case CKR_ARGUMENTS_BAD:
3026         case CKR_CRYPTOKI_NOT_INITIALIZED:
3027         case CKR_DEVICE_ERROR:
3028         case CKR_DEVICE_MEMORY:
3029         case CKR_DEVICE_REMOVED:
3030         case CKR_FUNCTION_CANCELED:
3031         case CKR_FUNCTION_FAILED:
3032         case CKR_GENERAL_ERROR:
3033         case CKR_HOST_MEMORY:
3034         case CKR_KEY_FUNCTION_NOT_PERMITTED:
3035         case CKR_KEY_HANDLE_INVALID:
3036         case CKR_KEY_SIZE_RANGE:
3037         case CKR_KEY_TYPE_INCONSISTENT:
3038         case CKR_MECHANISM_INVALID:
3039         case CKR_MECHANISM_PARAM_INVALID:
3040         case CKR_OPERATION_ACTIVE:
3041         case CKR_PIN_EXPIRED:
3042         case CKR_SESSION_CLOSED:
3043         case CKR_SESSION_HANDLE_INVALID:
3044         case CKR_USER_NOT_LOGGED_IN:
3045             break;
3046         default:
3047         case CKR_OK:
3048             error = CKR_GENERAL_ERROR;
3049             break;
3050     }
3051     return error;
3052 }
3053 
3054 /*
3055  * NSSCKFWC_Decrypt
3056  *
3057  */
3058 NSS_IMPLEMENT CK_RV
NSSCKFWC_Decrypt(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_BYTE_PTR pEncryptedData,CK_ULONG ulEncryptedDataLen,CK_BYTE_PTR pData,CK_ULONG_PTR pulDataLen)3059 NSSCKFWC_Decrypt(
3060     NSSCKFWInstance *fwInstance,
3061     CK_SESSION_HANDLE hSession,
3062     CK_BYTE_PTR pEncryptedData,
3063     CK_ULONG ulEncryptedDataLen,
3064     CK_BYTE_PTR pData,
3065     CK_ULONG_PTR pulDataLen)
3066 {
3067     CK_RV error = CKR_OK;
3068     NSSCKFWSession *fwSession;
3069 
3070     if (!fwInstance) {
3071         error = CKR_CRYPTOKI_NOT_INITIALIZED;
3072         goto loser;
3073     }
3074 
3075     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
3076     if (!fwSession) {
3077         error = CKR_SESSION_HANDLE_INVALID;
3078         goto loser;
3079     }
3080 
3081     error = nssCKFWSession_UpdateFinal(fwSession,
3082                                        NSSCKFWCryptoOperationType_Decrypt,
3083                                        NSSCKFWCryptoOperationState_EncryptDecrypt,
3084                                        pEncryptedData, ulEncryptedDataLen, pData, pulDataLen);
3085 
3086     if (CKR_OK == error) {
3087         return CKR_OK;
3088     }
3089 
3090 loser:
3091     /* verify error */
3092     switch (error) {
3093         case CKR_ARGUMENTS_BAD:
3094         case CKR_BUFFER_TOO_SMALL:
3095         case CKR_CRYPTOKI_NOT_INITIALIZED:
3096         case CKR_DEVICE_ERROR:
3097         case CKR_DEVICE_MEMORY:
3098         case CKR_DEVICE_REMOVED:
3099         case CKR_ENCRYPTED_DATA_INVALID:
3100         case CKR_ENCRYPTED_DATA_LEN_RANGE:
3101         case CKR_FUNCTION_CANCELED:
3102         case CKR_FUNCTION_FAILED:
3103         case CKR_GENERAL_ERROR:
3104         case CKR_HOST_MEMORY:
3105         case CKR_OPERATION_NOT_INITIALIZED:
3106         case CKR_SESSION_CLOSED:
3107         case CKR_SESSION_HANDLE_INVALID:
3108         case CKR_USER_NOT_LOGGED_IN:
3109             break;
3110         case CKR_DATA_LEN_RANGE:
3111             error = CKR_ENCRYPTED_DATA_LEN_RANGE;
3112             break;
3113         case CKR_DATA_INVALID:
3114             error = CKR_ENCRYPTED_DATA_INVALID;
3115             break;
3116         default:
3117         case CKR_OK:
3118             error = CKR_GENERAL_ERROR;
3119             break;
3120     }
3121     return error;
3122 }
3123 
3124 /*
3125  * NSSCKFWC_DecryptUpdate
3126  *
3127  */
3128 NSS_IMPLEMENT CK_RV
NSSCKFWC_DecryptUpdate(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_BYTE_PTR pEncryptedPart,CK_ULONG ulEncryptedPartLen,CK_BYTE_PTR pPart,CK_ULONG_PTR pulPartLen)3129 NSSCKFWC_DecryptUpdate(
3130     NSSCKFWInstance *fwInstance,
3131     CK_SESSION_HANDLE hSession,
3132     CK_BYTE_PTR pEncryptedPart,
3133     CK_ULONG ulEncryptedPartLen,
3134     CK_BYTE_PTR pPart,
3135     CK_ULONG_PTR pulPartLen)
3136 {
3137     CK_RV error = CKR_OK;
3138     NSSCKFWSession *fwSession;
3139 
3140     if (!fwInstance) {
3141         error = CKR_CRYPTOKI_NOT_INITIALIZED;
3142         goto loser;
3143     }
3144 
3145     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
3146     if (!fwSession) {
3147         error = CKR_SESSION_HANDLE_INVALID;
3148         goto loser;
3149     }
3150 
3151     error = nssCKFWSession_Update(fwSession,
3152                                   NSSCKFWCryptoOperationType_Decrypt,
3153                                   NSSCKFWCryptoOperationState_EncryptDecrypt,
3154                                   pEncryptedPart, ulEncryptedPartLen, pPart, pulPartLen);
3155 
3156     if (CKR_OK == error) {
3157         return CKR_OK;
3158     }
3159 
3160 loser:
3161     /* verify error */
3162     switch (error) {
3163         case CKR_ARGUMENTS_BAD:
3164         case CKR_BUFFER_TOO_SMALL:
3165         case CKR_CRYPTOKI_NOT_INITIALIZED:
3166         case CKR_DEVICE_ERROR:
3167         case CKR_DEVICE_MEMORY:
3168         case CKR_DEVICE_REMOVED:
3169         case CKR_ENCRYPTED_DATA_INVALID:
3170         case CKR_ENCRYPTED_DATA_LEN_RANGE:
3171         case CKR_FUNCTION_CANCELED:
3172         case CKR_FUNCTION_FAILED:
3173         case CKR_GENERAL_ERROR:
3174         case CKR_HOST_MEMORY:
3175         case CKR_OPERATION_NOT_INITIALIZED:
3176         case CKR_SESSION_CLOSED:
3177         case CKR_SESSION_HANDLE_INVALID:
3178         case CKR_USER_NOT_LOGGED_IN:
3179             break;
3180         case CKR_DATA_LEN_RANGE:
3181             error = CKR_ENCRYPTED_DATA_LEN_RANGE;
3182             break;
3183         case CKR_DATA_INVALID:
3184             error = CKR_ENCRYPTED_DATA_INVALID;
3185             break;
3186         default:
3187         case CKR_OK:
3188             error = CKR_GENERAL_ERROR;
3189             break;
3190     }
3191     return error;
3192 }
3193 
3194 /*
3195  * NSSCKFWC_DecryptFinal
3196  *
3197  */
3198 NSS_IMPLEMENT CK_RV
NSSCKFWC_DecryptFinal(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_BYTE_PTR pLastPart,CK_ULONG_PTR pulLastPartLen)3199 NSSCKFWC_DecryptFinal(
3200     NSSCKFWInstance *fwInstance,
3201     CK_SESSION_HANDLE hSession,
3202     CK_BYTE_PTR pLastPart,
3203     CK_ULONG_PTR pulLastPartLen)
3204 {
3205     CK_RV error = CKR_OK;
3206     NSSCKFWSession *fwSession;
3207 
3208     if (!fwInstance) {
3209         error = CKR_CRYPTOKI_NOT_INITIALIZED;
3210         goto loser;
3211     }
3212 
3213     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
3214     if (!fwSession) {
3215         error = CKR_SESSION_HANDLE_INVALID;
3216         goto loser;
3217     }
3218 
3219     error = nssCKFWSession_Final(fwSession,
3220                                  NSSCKFWCryptoOperationType_Decrypt,
3221                                  NSSCKFWCryptoOperationState_EncryptDecrypt,
3222                                  pLastPart, pulLastPartLen);
3223 
3224     if (CKR_OK == error) {
3225         return CKR_OK;
3226     }
3227 
3228 loser:
3229     /* verify error */
3230     switch (error) {
3231         case CKR_ARGUMENTS_BAD:
3232         case CKR_BUFFER_TOO_SMALL:
3233         case CKR_CRYPTOKI_NOT_INITIALIZED:
3234         case CKR_DEVICE_ERROR:
3235         case CKR_DEVICE_MEMORY:
3236         case CKR_DEVICE_REMOVED:
3237         case CKR_FUNCTION_FAILED:
3238         case CKR_FUNCTION_CANCELED:
3239         case CKR_ENCRYPTED_DATA_INVALID:
3240         case CKR_ENCRYPTED_DATA_LEN_RANGE:
3241         case CKR_GENERAL_ERROR:
3242         case CKR_HOST_MEMORY:
3243         case CKR_OPERATION_NOT_INITIALIZED:
3244         case CKR_SESSION_CLOSED:
3245         case CKR_SESSION_HANDLE_INVALID:
3246         case CKR_USER_NOT_LOGGED_IN:
3247             break;
3248         case CKR_DATA_LEN_RANGE:
3249             error = CKR_ENCRYPTED_DATA_LEN_RANGE;
3250             break;
3251         case CKR_DATA_INVALID:
3252             error = CKR_ENCRYPTED_DATA_INVALID;
3253             break;
3254         default:
3255         case CKR_OK:
3256             error = CKR_GENERAL_ERROR;
3257             break;
3258     }
3259     return error;
3260 }
3261 
3262 /*
3263  * NSSCKFWC_DigestInit
3264  *
3265  */
3266 NSS_IMPLEMENT CK_RV
NSSCKFWC_DigestInit(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_MECHANISM_PTR pMechanism)3267 NSSCKFWC_DigestInit(
3268     NSSCKFWInstance *fwInstance,
3269     CK_SESSION_HANDLE hSession,
3270     CK_MECHANISM_PTR pMechanism)
3271 {
3272     CK_RV error = CKR_OK;
3273     NSSCKFWSession *fwSession;
3274     NSSCKFWSlot *fwSlot;
3275     NSSCKFWToken *fwToken;
3276     NSSCKFWMechanism *fwMechanism;
3277 
3278     if (!fwInstance) {
3279         error = CKR_CRYPTOKI_NOT_INITIALIZED;
3280         goto loser;
3281     }
3282 
3283     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
3284     if (!fwSession) {
3285         error = CKR_SESSION_HANDLE_INVALID;
3286         goto loser;
3287     }
3288 
3289     fwSlot = nssCKFWSession_GetFWSlot(fwSession);
3290     if (!fwSlot) {
3291         error = CKR_GENERAL_ERROR; /* should never happen! */
3292         goto loser;
3293     }
3294 
3295     if (CK_TRUE != nssCKFWSlot_GetTokenPresent(fwSlot)) {
3296         error = CKR_TOKEN_NOT_PRESENT;
3297         goto loser;
3298     }
3299 
3300     fwToken = nssCKFWSlot_GetToken(fwSlot, &error);
3301     if (!fwToken) {
3302         goto loser;
3303     }
3304 
3305     fwMechanism = nssCKFWToken_GetMechanism(fwToken, pMechanism->mechanism, &error);
3306     if (!fwMechanism) {
3307         goto loser;
3308     }
3309 
3310     error = nssCKFWMechanism_DigestInit(fwMechanism, pMechanism, fwSession);
3311 
3312     nssCKFWMechanism_Destroy(fwMechanism);
3313 
3314     if (CKR_OK == error) {
3315         return CKR_OK;
3316     }
3317 
3318 loser:
3319     /* verify error */
3320     switch (error) {
3321         case CKR_ARGUMENTS_BAD:
3322         case CKR_CRYPTOKI_NOT_INITIALIZED:
3323         case CKR_DEVICE_ERROR:
3324         case CKR_DEVICE_MEMORY:
3325         case CKR_DEVICE_REMOVED:
3326         case CKR_FUNCTION_CANCELED:
3327         case CKR_FUNCTION_FAILED:
3328         case CKR_GENERAL_ERROR:
3329         case CKR_HOST_MEMORY:
3330         case CKR_MECHANISM_INVALID:
3331         case CKR_MECHANISM_PARAM_INVALID:
3332         case CKR_OPERATION_ACTIVE:
3333         case CKR_PIN_EXPIRED:
3334         case CKR_SESSION_CLOSED:
3335         case CKR_SESSION_HANDLE_INVALID:
3336         case CKR_USER_NOT_LOGGED_IN:
3337             break;
3338         default:
3339         case CKR_OK:
3340             error = CKR_GENERAL_ERROR;
3341             break;
3342     }
3343     return error;
3344 }
3345 
3346 /*
3347  * NSSCKFWC_Digest
3348  *
3349  */
3350 NSS_IMPLEMENT CK_RV
NSSCKFWC_Digest(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_BYTE_PTR pData,CK_ULONG ulDataLen,CK_BYTE_PTR pDigest,CK_ULONG_PTR pulDigestLen)3351 NSSCKFWC_Digest(
3352     NSSCKFWInstance *fwInstance,
3353     CK_SESSION_HANDLE hSession,
3354     CK_BYTE_PTR pData,
3355     CK_ULONG ulDataLen,
3356     CK_BYTE_PTR pDigest,
3357     CK_ULONG_PTR pulDigestLen)
3358 {
3359     CK_RV error = CKR_OK;
3360     NSSCKFWSession *fwSession;
3361 
3362     if (!fwInstance) {
3363         error = CKR_CRYPTOKI_NOT_INITIALIZED;
3364         goto loser;
3365     }
3366 
3367     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
3368     if (!fwSession) {
3369         error = CKR_SESSION_HANDLE_INVALID;
3370         goto loser;
3371     }
3372 
3373     error = nssCKFWSession_UpdateFinal(fwSession,
3374                                        NSSCKFWCryptoOperationType_Digest,
3375                                        NSSCKFWCryptoOperationState_Digest,
3376                                        pData, ulDataLen, pDigest, pulDigestLen);
3377 
3378     if (CKR_OK == error) {
3379         return CKR_OK;
3380     }
3381 
3382 loser:
3383     /* verify error */
3384     switch (error) {
3385         case CKR_ARGUMENTS_BAD:
3386         case CKR_BUFFER_TOO_SMALL:
3387         case CKR_CRYPTOKI_NOT_INITIALIZED:
3388         case CKR_DEVICE_ERROR:
3389         case CKR_DEVICE_MEMORY:
3390         case CKR_DEVICE_REMOVED:
3391         case CKR_FUNCTION_CANCELED:
3392         case CKR_FUNCTION_FAILED:
3393         case CKR_GENERAL_ERROR:
3394         case CKR_HOST_MEMORY:
3395         case CKR_OPERATION_NOT_INITIALIZED:
3396         case CKR_SESSION_CLOSED:
3397         case CKR_SESSION_HANDLE_INVALID:
3398             break;
3399         default:
3400         case CKR_OK:
3401             error = CKR_GENERAL_ERROR;
3402             break;
3403     }
3404     return error;
3405 }
3406 
3407 /*
3408  * NSSCKFWC_DigestUpdate
3409  *
3410  */
3411 NSS_IMPLEMENT CK_RV
NSSCKFWC_DigestUpdate(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_BYTE_PTR pData,CK_ULONG ulDataLen)3412 NSSCKFWC_DigestUpdate(
3413     NSSCKFWInstance *fwInstance,
3414     CK_SESSION_HANDLE hSession,
3415     CK_BYTE_PTR pData,
3416     CK_ULONG ulDataLen)
3417 {
3418     CK_RV error = CKR_OK;
3419     NSSCKFWSession *fwSession;
3420 
3421     if (!fwInstance) {
3422         error = CKR_CRYPTOKI_NOT_INITIALIZED;
3423         goto loser;
3424     }
3425 
3426     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
3427     if (!fwSession) {
3428         error = CKR_SESSION_HANDLE_INVALID;
3429         goto loser;
3430     }
3431 
3432     error = nssCKFWSession_DigestUpdate(fwSession,
3433                                         NSSCKFWCryptoOperationType_Digest,
3434                                         NSSCKFWCryptoOperationState_Digest,
3435                                         pData, ulDataLen);
3436 
3437     if (CKR_OK == error) {
3438         return CKR_OK;
3439     }
3440 
3441 loser:
3442     /* verify error */
3443     switch (error) {
3444         case CKR_ARGUMENTS_BAD:
3445         case CKR_CRYPTOKI_NOT_INITIALIZED:
3446         case CKR_DEVICE_ERROR:
3447         case CKR_DEVICE_MEMORY:
3448         case CKR_DEVICE_REMOVED:
3449         case CKR_FUNCTION_CANCELED:
3450         case CKR_FUNCTION_FAILED:
3451         case CKR_GENERAL_ERROR:
3452         case CKR_HOST_MEMORY:
3453         case CKR_OPERATION_NOT_INITIALIZED:
3454         case CKR_SESSION_CLOSED:
3455         case CKR_SESSION_HANDLE_INVALID:
3456             break;
3457         default:
3458         case CKR_OK:
3459             error = CKR_GENERAL_ERROR;
3460             break;
3461     }
3462     return error;
3463 }
3464 
3465 /*
3466  * NSSCKFWC_DigestKey
3467  *
3468  */
3469 NSS_IMPLEMENT CK_RV
NSSCKFWC_DigestKey(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_OBJECT_HANDLE hKey)3470 NSSCKFWC_DigestKey(
3471     NSSCKFWInstance *fwInstance,
3472     CK_SESSION_HANDLE hSession,
3473     CK_OBJECT_HANDLE hKey)
3474 {
3475     CK_RV error = CKR_OK;
3476     NSSCKFWSession *fwSession;
3477     NSSCKFWObject *fwObject;
3478 
3479     if (!fwInstance) {
3480         error = CKR_CRYPTOKI_NOT_INITIALIZED;
3481         goto loser;
3482     }
3483 
3484     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
3485     if (!fwSession) {
3486         error = CKR_SESSION_HANDLE_INVALID;
3487         goto loser;
3488     }
3489 
3490     fwObject = nssCKFWInstance_ResolveObjectHandle(fwInstance, hKey);
3491     if (!fwObject) {
3492         error = CKR_KEY_HANDLE_INVALID;
3493         goto loser;
3494     }
3495 
3496     error = nssCKFWSession_DigestKey(fwSession, fwObject);
3497 
3498     if (CKR_OK == error) {
3499         return CKR_OK;
3500     }
3501 
3502 loser:
3503     /* verify error */
3504     switch (error) {
3505         case CKR_CRYPTOKI_NOT_INITIALIZED:
3506         case CKR_DEVICE_ERROR:
3507         case CKR_DEVICE_MEMORY:
3508         case CKR_DEVICE_REMOVED:
3509         case CKR_FUNCTION_CANCELED:
3510         case CKR_FUNCTION_FAILED:
3511         case CKR_GENERAL_ERROR:
3512         case CKR_HOST_MEMORY:
3513         case CKR_KEY_HANDLE_INVALID:
3514         case CKR_KEY_INDIGESTIBLE:
3515         case CKR_KEY_SIZE_RANGE:
3516         case CKR_OPERATION_NOT_INITIALIZED:
3517         case CKR_SESSION_CLOSED:
3518         case CKR_SESSION_HANDLE_INVALID:
3519             break;
3520         default:
3521         case CKR_OK:
3522             error = CKR_GENERAL_ERROR;
3523             break;
3524     }
3525     return error;
3526 }
3527 
3528 /*
3529  * NSSCKFWC_DigestFinal
3530  *
3531  */
3532 NSS_IMPLEMENT CK_RV
NSSCKFWC_DigestFinal(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_BYTE_PTR pDigest,CK_ULONG_PTR pulDigestLen)3533 NSSCKFWC_DigestFinal(
3534     NSSCKFWInstance *fwInstance,
3535     CK_SESSION_HANDLE hSession,
3536     CK_BYTE_PTR pDigest,
3537     CK_ULONG_PTR pulDigestLen)
3538 {
3539     CK_RV error = CKR_OK;
3540     NSSCKFWSession *fwSession;
3541 
3542     if (!fwInstance) {
3543         error = CKR_CRYPTOKI_NOT_INITIALIZED;
3544         goto loser;
3545     }
3546 
3547     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
3548     if (!fwSession) {
3549         error = CKR_SESSION_HANDLE_INVALID;
3550         goto loser;
3551     }
3552 
3553     error = nssCKFWSession_Final(fwSession,
3554                                  NSSCKFWCryptoOperationType_Digest,
3555                                  NSSCKFWCryptoOperationState_Digest,
3556                                  pDigest, pulDigestLen);
3557 
3558     if (CKR_OK == error) {
3559         return CKR_OK;
3560     }
3561 
3562 loser:
3563     /* verify error */
3564     switch (error) {
3565         case CKR_ARGUMENTS_BAD:
3566         case CKR_BUFFER_TOO_SMALL:
3567         case CKR_CRYPTOKI_NOT_INITIALIZED:
3568         case CKR_DEVICE_ERROR:
3569         case CKR_DEVICE_MEMORY:
3570         case CKR_DEVICE_REMOVED:
3571         case CKR_FUNCTION_CANCELED:
3572         case CKR_FUNCTION_FAILED:
3573         case CKR_GENERAL_ERROR:
3574         case CKR_HOST_MEMORY:
3575         case CKR_OPERATION_NOT_INITIALIZED:
3576         case CKR_SESSION_CLOSED:
3577         case CKR_SESSION_HANDLE_INVALID:
3578             break;
3579         default:
3580         case CKR_OK:
3581             error = CKR_GENERAL_ERROR;
3582             break;
3583     }
3584     return error;
3585 }
3586 
3587 /*
3588  * NSSCKFWC_SignInit
3589  *
3590  */
3591 NSS_IMPLEMENT CK_RV
NSSCKFWC_SignInit(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_MECHANISM_PTR pMechanism,CK_OBJECT_HANDLE hKey)3592 NSSCKFWC_SignInit(
3593     NSSCKFWInstance *fwInstance,
3594     CK_SESSION_HANDLE hSession,
3595     CK_MECHANISM_PTR pMechanism,
3596     CK_OBJECT_HANDLE hKey)
3597 {
3598     CK_RV error = CKR_OK;
3599     NSSCKFWSession *fwSession;
3600     NSSCKFWObject *fwObject;
3601     NSSCKFWSlot *fwSlot;
3602     NSSCKFWToken *fwToken;
3603     NSSCKFWMechanism *fwMechanism;
3604 
3605     if (!fwInstance) {
3606         error = CKR_CRYPTOKI_NOT_INITIALIZED;
3607         goto loser;
3608     }
3609 
3610     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
3611     if (!fwSession) {
3612         error = CKR_SESSION_HANDLE_INVALID;
3613         goto loser;
3614     }
3615 
3616     fwObject = nssCKFWInstance_ResolveObjectHandle(fwInstance, hKey);
3617     if (!fwObject) {
3618         error = CKR_KEY_HANDLE_INVALID;
3619         goto loser;
3620     }
3621 
3622     fwSlot = nssCKFWSession_GetFWSlot(fwSession);
3623     if (!fwSlot) {
3624         error = CKR_GENERAL_ERROR; /* should never happen! */
3625         goto loser;
3626     }
3627 
3628     if (CK_TRUE != nssCKFWSlot_GetTokenPresent(fwSlot)) {
3629         error = CKR_TOKEN_NOT_PRESENT;
3630         goto loser;
3631     }
3632 
3633     fwToken = nssCKFWSlot_GetToken(fwSlot, &error);
3634     if (!fwToken) {
3635         goto loser;
3636     }
3637 
3638     fwMechanism = nssCKFWToken_GetMechanism(fwToken, pMechanism->mechanism, &error);
3639     if (!fwMechanism) {
3640         goto loser;
3641     }
3642 
3643     error = nssCKFWMechanism_SignInit(fwMechanism, pMechanism, fwSession,
3644                                       fwObject);
3645 
3646     nssCKFWMechanism_Destroy(fwMechanism);
3647 
3648     if (CKR_OK == error) {
3649         return CKR_OK;
3650     }
3651 
3652 loser:
3653     /* verify error */
3654     switch (error) {
3655         case CKR_ARGUMENTS_BAD:
3656         case CKR_CRYPTOKI_NOT_INITIALIZED:
3657         case CKR_DEVICE_ERROR:
3658         case CKR_DEVICE_MEMORY:
3659         case CKR_DEVICE_REMOVED:
3660         case CKR_FUNCTION_CANCELED:
3661         case CKR_FUNCTION_FAILED:
3662         case CKR_GENERAL_ERROR:
3663         case CKR_HOST_MEMORY:
3664         case CKR_KEY_FUNCTION_NOT_PERMITTED:
3665         case CKR_KEY_HANDLE_INVALID:
3666         case CKR_KEY_SIZE_RANGE:
3667         case CKR_KEY_TYPE_INCONSISTENT:
3668         case CKR_MECHANISM_INVALID:
3669         case CKR_MECHANISM_PARAM_INVALID:
3670         case CKR_OPERATION_ACTIVE:
3671         case CKR_PIN_EXPIRED:
3672         case CKR_SESSION_CLOSED:
3673         case CKR_SESSION_HANDLE_INVALID:
3674         case CKR_USER_NOT_LOGGED_IN:
3675             break;
3676         default:
3677         case CKR_OK:
3678             error = CKR_GENERAL_ERROR;
3679             break;
3680     }
3681     return error;
3682 }
3683 
3684 /*
3685  * NSSCKFWC_Sign
3686  *
3687  */
3688 NSS_IMPLEMENT CK_RV
NSSCKFWC_Sign(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_BYTE_PTR pData,CK_ULONG ulDataLen,CK_BYTE_PTR pSignature,CK_ULONG_PTR pulSignatureLen)3689 NSSCKFWC_Sign(
3690     NSSCKFWInstance *fwInstance,
3691     CK_SESSION_HANDLE hSession,
3692     CK_BYTE_PTR pData,
3693     CK_ULONG ulDataLen,
3694     CK_BYTE_PTR pSignature,
3695     CK_ULONG_PTR pulSignatureLen)
3696 {
3697     CK_RV error = CKR_OK;
3698     NSSCKFWSession *fwSession;
3699 
3700     if (!fwInstance) {
3701         error = CKR_CRYPTOKI_NOT_INITIALIZED;
3702         goto loser;
3703     }
3704 
3705     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
3706     if (!fwSession) {
3707         error = CKR_SESSION_HANDLE_INVALID;
3708         goto loser;
3709     }
3710 
3711     error = nssCKFWSession_UpdateFinal(fwSession,
3712                                        NSSCKFWCryptoOperationType_Sign,
3713                                        NSSCKFWCryptoOperationState_SignVerify,
3714                                        pData, ulDataLen, pSignature, pulSignatureLen);
3715 
3716     if (CKR_OK == error) {
3717         return CKR_OK;
3718     }
3719 
3720 loser:
3721     /* verify error */
3722     switch (error) {
3723         case CKR_ARGUMENTS_BAD:
3724         case CKR_BUFFER_TOO_SMALL:
3725         case CKR_CRYPTOKI_NOT_INITIALIZED:
3726         case CKR_DATA_INVALID:
3727         case CKR_DATA_LEN_RANGE:
3728         case CKR_DEVICE_ERROR:
3729         case CKR_DEVICE_MEMORY:
3730         case CKR_DEVICE_REMOVED:
3731         case CKR_FUNCTION_CANCELED:
3732         case CKR_FUNCTION_FAILED:
3733         case CKR_GENERAL_ERROR:
3734         case CKR_HOST_MEMORY:
3735         case CKR_OPERATION_NOT_INITIALIZED:
3736         case CKR_SESSION_CLOSED:
3737         case CKR_SESSION_HANDLE_INVALID:
3738         case CKR_USER_NOT_LOGGED_IN:
3739         case CKR_FUNCTION_REJECTED:
3740             break;
3741         default:
3742         case CKR_OK:
3743             error = CKR_GENERAL_ERROR;
3744             break;
3745     }
3746     return error;
3747 }
3748 
3749 /*
3750  * NSSCKFWC_SignUpdate
3751  *
3752  */
3753 NSS_IMPLEMENT CK_RV
NSSCKFWC_SignUpdate(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_BYTE_PTR pPart,CK_ULONG ulPartLen)3754 NSSCKFWC_SignUpdate(
3755     NSSCKFWInstance *fwInstance,
3756     CK_SESSION_HANDLE hSession,
3757     CK_BYTE_PTR pPart,
3758     CK_ULONG ulPartLen)
3759 {
3760     CK_RV error = CKR_OK;
3761     NSSCKFWSession *fwSession;
3762 
3763     if (!fwInstance) {
3764         error = CKR_CRYPTOKI_NOT_INITIALIZED;
3765         goto loser;
3766     }
3767 
3768     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
3769     if (!fwSession) {
3770         error = CKR_SESSION_HANDLE_INVALID;
3771         goto loser;
3772     }
3773 
3774     error = nssCKFWSession_DigestUpdate(fwSession,
3775                                         NSSCKFWCryptoOperationType_Sign,
3776                                         NSSCKFWCryptoOperationState_SignVerify,
3777                                         pPart, ulPartLen);
3778 
3779     if (CKR_OK == error) {
3780         return CKR_OK;
3781     }
3782 
3783 loser:
3784     /* verify error */
3785     switch (error) {
3786         case CKR_ARGUMENTS_BAD:
3787         case CKR_CRYPTOKI_NOT_INITIALIZED:
3788         case CKR_DATA_LEN_RANGE:
3789         case CKR_DEVICE_ERROR:
3790         case CKR_DEVICE_MEMORY:
3791         case CKR_DEVICE_REMOVED:
3792         case CKR_FUNCTION_CANCELED:
3793         case CKR_FUNCTION_FAILED:
3794         case CKR_GENERAL_ERROR:
3795         case CKR_HOST_MEMORY:
3796         case CKR_OPERATION_NOT_INITIALIZED:
3797         case CKR_SESSION_CLOSED:
3798         case CKR_SESSION_HANDLE_INVALID:
3799         case CKR_USER_NOT_LOGGED_IN:
3800             break;
3801         default:
3802         case CKR_OK:
3803             error = CKR_GENERAL_ERROR;
3804             break;
3805     }
3806     return error;
3807 }
3808 
3809 /*
3810  * NSSCKFWC_SignFinal
3811  *
3812  */
3813 NSS_IMPLEMENT CK_RV
NSSCKFWC_SignFinal(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_BYTE_PTR pSignature,CK_ULONG_PTR pulSignatureLen)3814 NSSCKFWC_SignFinal(
3815     NSSCKFWInstance *fwInstance,
3816     CK_SESSION_HANDLE hSession,
3817     CK_BYTE_PTR pSignature,
3818     CK_ULONG_PTR pulSignatureLen)
3819 {
3820     CK_RV error = CKR_OK;
3821     NSSCKFWSession *fwSession;
3822 
3823     if (!fwInstance) {
3824         error = CKR_CRYPTOKI_NOT_INITIALIZED;
3825         goto loser;
3826     }
3827 
3828     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
3829     if (!fwSession) {
3830         error = CKR_SESSION_HANDLE_INVALID;
3831         goto loser;
3832     }
3833 
3834     error = nssCKFWSession_Final(fwSession,
3835                                  NSSCKFWCryptoOperationType_Sign,
3836                                  NSSCKFWCryptoOperationState_SignVerify,
3837                                  pSignature, pulSignatureLen);
3838 
3839     if (CKR_OK == error) {
3840         return CKR_OK;
3841     }
3842 
3843 loser:
3844     /* verify error */
3845     switch (error) {
3846         case CKR_ARGUMENTS_BAD:
3847         case CKR_BUFFER_TOO_SMALL:
3848         case CKR_CRYPTOKI_NOT_INITIALIZED:
3849         case CKR_DATA_LEN_RANGE:
3850         case CKR_DEVICE_ERROR:
3851         case CKR_DEVICE_MEMORY:
3852         case CKR_DEVICE_REMOVED:
3853         case CKR_FUNCTION_CANCELED:
3854         case CKR_FUNCTION_FAILED:
3855         case CKR_GENERAL_ERROR:
3856         case CKR_HOST_MEMORY:
3857         case CKR_OPERATION_NOT_INITIALIZED:
3858         case CKR_SESSION_CLOSED:
3859         case CKR_SESSION_HANDLE_INVALID:
3860         case CKR_USER_NOT_LOGGED_IN:
3861         case CKR_FUNCTION_REJECTED:
3862             break;
3863         default:
3864         case CKR_OK:
3865             error = CKR_GENERAL_ERROR;
3866             break;
3867     }
3868     return error;
3869 }
3870 
3871 /*
3872  * NSSCKFWC_SignRecoverInit
3873  *
3874  */
3875 NSS_IMPLEMENT CK_RV
NSSCKFWC_SignRecoverInit(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_MECHANISM_PTR pMechanism,CK_OBJECT_HANDLE hKey)3876 NSSCKFWC_SignRecoverInit(
3877     NSSCKFWInstance *fwInstance,
3878     CK_SESSION_HANDLE hSession,
3879     CK_MECHANISM_PTR pMechanism,
3880     CK_OBJECT_HANDLE hKey)
3881 {
3882     CK_RV error = CKR_OK;
3883     NSSCKFWSession *fwSession;
3884     NSSCKFWObject *fwObject;
3885     NSSCKFWSlot *fwSlot;
3886     NSSCKFWToken *fwToken;
3887     NSSCKFWMechanism *fwMechanism;
3888 
3889     if (!fwInstance) {
3890         error = CKR_CRYPTOKI_NOT_INITIALIZED;
3891         goto loser;
3892     }
3893 
3894     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
3895     if (!fwSession) {
3896         error = CKR_SESSION_HANDLE_INVALID;
3897         goto loser;
3898     }
3899 
3900     fwObject = nssCKFWInstance_ResolveObjectHandle(fwInstance, hKey);
3901     if (!fwObject) {
3902         error = CKR_KEY_HANDLE_INVALID;
3903         goto loser;
3904     }
3905 
3906     fwSlot = nssCKFWSession_GetFWSlot(fwSession);
3907     if (!fwSlot) {
3908         error = CKR_GENERAL_ERROR; /* should never happen! */
3909         goto loser;
3910     }
3911 
3912     if (CK_TRUE != nssCKFWSlot_GetTokenPresent(fwSlot)) {
3913         error = CKR_TOKEN_NOT_PRESENT;
3914         goto loser;
3915     }
3916 
3917     fwToken = nssCKFWSlot_GetToken(fwSlot, &error);
3918     if (!fwToken) {
3919         goto loser;
3920     }
3921 
3922     fwMechanism = nssCKFWToken_GetMechanism(fwToken, pMechanism->mechanism, &error);
3923     if (!fwMechanism) {
3924         goto loser;
3925     }
3926 
3927     error = nssCKFWMechanism_SignRecoverInit(fwMechanism, pMechanism, fwSession,
3928                                              fwObject);
3929 
3930     nssCKFWMechanism_Destroy(fwMechanism);
3931 
3932     if (CKR_OK == error) {
3933         return CKR_OK;
3934     }
3935 
3936 loser:
3937     /* verify error */
3938     switch (error) {
3939         case CKR_ARGUMENTS_BAD:
3940         case CKR_CRYPTOKI_NOT_INITIALIZED:
3941         case CKR_DEVICE_ERROR:
3942         case CKR_DEVICE_MEMORY:
3943         case CKR_DEVICE_REMOVED:
3944         case CKR_FUNCTION_CANCELED:
3945         case CKR_FUNCTION_FAILED:
3946         case CKR_GENERAL_ERROR:
3947         case CKR_HOST_MEMORY:
3948         case CKR_KEY_FUNCTION_NOT_PERMITTED:
3949         case CKR_KEY_HANDLE_INVALID:
3950         case CKR_KEY_SIZE_RANGE:
3951         case CKR_KEY_TYPE_INCONSISTENT:
3952         case CKR_MECHANISM_INVALID:
3953         case CKR_MECHANISM_PARAM_INVALID:
3954         case CKR_OPERATION_ACTIVE:
3955         case CKR_PIN_EXPIRED:
3956         case CKR_SESSION_CLOSED:
3957         case CKR_SESSION_HANDLE_INVALID:
3958         case CKR_USER_NOT_LOGGED_IN:
3959             break;
3960         default:
3961         case CKR_OK:
3962             error = CKR_GENERAL_ERROR;
3963             break;
3964     }
3965     return error;
3966 }
3967 
3968 /*
3969  * NSSCKFWC_SignRecover
3970  *
3971  */
3972 NSS_IMPLEMENT CK_RV
NSSCKFWC_SignRecover(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_BYTE_PTR pData,CK_ULONG ulDataLen,CK_BYTE_PTR pSignature,CK_ULONG_PTR pulSignatureLen)3973 NSSCKFWC_SignRecover(
3974     NSSCKFWInstance *fwInstance,
3975     CK_SESSION_HANDLE hSession,
3976     CK_BYTE_PTR pData,
3977     CK_ULONG ulDataLen,
3978     CK_BYTE_PTR pSignature,
3979     CK_ULONG_PTR pulSignatureLen)
3980 {
3981     CK_RV error = CKR_OK;
3982     NSSCKFWSession *fwSession;
3983 
3984     if (!fwInstance) {
3985         error = CKR_CRYPTOKI_NOT_INITIALIZED;
3986         goto loser;
3987     }
3988 
3989     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
3990     if (!fwSession) {
3991         error = CKR_SESSION_HANDLE_INVALID;
3992         goto loser;
3993     }
3994 
3995     error = nssCKFWSession_UpdateFinal(fwSession,
3996                                        NSSCKFWCryptoOperationType_SignRecover,
3997                                        NSSCKFWCryptoOperationState_SignVerify,
3998                                        pData, ulDataLen, pSignature, pulSignatureLen);
3999 
4000     if (CKR_OK == error) {
4001         return CKR_OK;
4002     }
4003 
4004 loser:
4005     /* verify error */
4006     switch (error) {
4007         case CKR_ARGUMENTS_BAD:
4008         case CKR_BUFFER_TOO_SMALL:
4009         case CKR_CRYPTOKI_NOT_INITIALIZED:
4010         case CKR_DATA_INVALID:
4011         case CKR_DATA_LEN_RANGE:
4012         case CKR_DEVICE_ERROR:
4013         case CKR_DEVICE_MEMORY:
4014         case CKR_DEVICE_REMOVED:
4015         case CKR_FUNCTION_CANCELED:
4016         case CKR_FUNCTION_FAILED:
4017         case CKR_GENERAL_ERROR:
4018         case CKR_HOST_MEMORY:
4019         case CKR_OPERATION_NOT_INITIALIZED:
4020         case CKR_SESSION_CLOSED:
4021         case CKR_SESSION_HANDLE_INVALID:
4022         case CKR_USER_NOT_LOGGED_IN:
4023             break;
4024         default:
4025         case CKR_OK:
4026             error = CKR_GENERAL_ERROR;
4027             break;
4028     }
4029     return error;
4030 }
4031 
4032 /*
4033  * NSSCKFWC_VerifyInit
4034  *
4035  */
4036 NSS_IMPLEMENT CK_RV
NSSCKFWC_VerifyInit(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_MECHANISM_PTR pMechanism,CK_OBJECT_HANDLE hKey)4037 NSSCKFWC_VerifyInit(
4038     NSSCKFWInstance *fwInstance,
4039     CK_SESSION_HANDLE hSession,
4040     CK_MECHANISM_PTR pMechanism,
4041     CK_OBJECT_HANDLE hKey)
4042 {
4043     CK_RV error = CKR_OK;
4044     NSSCKFWSession *fwSession;
4045     NSSCKFWObject *fwObject;
4046     NSSCKFWSlot *fwSlot;
4047     NSSCKFWToken *fwToken;
4048     NSSCKFWMechanism *fwMechanism;
4049 
4050     if (!fwInstance) {
4051         error = CKR_CRYPTOKI_NOT_INITIALIZED;
4052         goto loser;
4053     }
4054 
4055     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
4056     if (!fwSession) {
4057         error = CKR_SESSION_HANDLE_INVALID;
4058         goto loser;
4059     }
4060 
4061     fwObject = nssCKFWInstance_ResolveObjectHandle(fwInstance, hKey);
4062     if (!fwObject) {
4063         error = CKR_KEY_HANDLE_INVALID;
4064         goto loser;
4065     }
4066 
4067     fwSlot = nssCKFWSession_GetFWSlot(fwSession);
4068     if (!fwSlot) {
4069         error = CKR_GENERAL_ERROR; /* should never happen! */
4070         goto loser;
4071     }
4072 
4073     if (CK_TRUE != nssCKFWSlot_GetTokenPresent(fwSlot)) {
4074         error = CKR_TOKEN_NOT_PRESENT;
4075         goto loser;
4076     }
4077 
4078     fwToken = nssCKFWSlot_GetToken(fwSlot, &error);
4079     if (!fwToken) {
4080         goto loser;
4081     }
4082 
4083     fwMechanism = nssCKFWToken_GetMechanism(fwToken, pMechanism->mechanism, &error);
4084     if (!fwMechanism) {
4085         goto loser;
4086     }
4087 
4088     error = nssCKFWMechanism_VerifyInit(fwMechanism, pMechanism, fwSession,
4089                                         fwObject);
4090 
4091     nssCKFWMechanism_Destroy(fwMechanism);
4092 
4093     if (CKR_OK == error) {
4094         return CKR_OK;
4095     }
4096 
4097 loser:
4098     /* verify error */
4099     switch (error) {
4100         case CKR_ARGUMENTS_BAD:
4101         case CKR_CRYPTOKI_NOT_INITIALIZED:
4102         case CKR_DEVICE_ERROR:
4103         case CKR_DEVICE_MEMORY:
4104         case CKR_DEVICE_REMOVED:
4105         case CKR_FUNCTION_CANCELED:
4106         case CKR_FUNCTION_FAILED:
4107         case CKR_GENERAL_ERROR:
4108         case CKR_HOST_MEMORY:
4109         case CKR_KEY_FUNCTION_NOT_PERMITTED:
4110         case CKR_KEY_HANDLE_INVALID:
4111         case CKR_KEY_SIZE_RANGE:
4112         case CKR_KEY_TYPE_INCONSISTENT:
4113         case CKR_MECHANISM_INVALID:
4114         case CKR_MECHANISM_PARAM_INVALID:
4115         case CKR_OPERATION_ACTIVE:
4116         case CKR_PIN_EXPIRED:
4117         case CKR_SESSION_CLOSED:
4118         case CKR_SESSION_HANDLE_INVALID:
4119         case CKR_USER_NOT_LOGGED_IN:
4120             break;
4121         default:
4122         case CKR_OK:
4123             error = CKR_GENERAL_ERROR;
4124             break;
4125     }
4126     return error;
4127 }
4128 
4129 /*
4130  * NSSCKFWC_Verify
4131  *
4132  */
4133 NSS_IMPLEMENT CK_RV
NSSCKFWC_Verify(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_BYTE_PTR pData,CK_ULONG ulDataLen,CK_BYTE_PTR pSignature,CK_ULONG ulSignatureLen)4134 NSSCKFWC_Verify(
4135     NSSCKFWInstance *fwInstance,
4136     CK_SESSION_HANDLE hSession,
4137     CK_BYTE_PTR pData,
4138     CK_ULONG ulDataLen,
4139     CK_BYTE_PTR pSignature,
4140     CK_ULONG ulSignatureLen)
4141 {
4142     CK_RV error = CKR_OK;
4143     NSSCKFWSession *fwSession;
4144 
4145     if (!fwInstance) {
4146         error = CKR_CRYPTOKI_NOT_INITIALIZED;
4147         goto loser;
4148     }
4149 
4150     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
4151     if (!fwSession) {
4152         error = CKR_SESSION_HANDLE_INVALID;
4153         goto loser;
4154     }
4155 
4156     error = nssCKFWSession_UpdateFinal(fwSession,
4157                                        NSSCKFWCryptoOperationType_Verify,
4158                                        NSSCKFWCryptoOperationState_SignVerify,
4159                                        pData, ulDataLen, pSignature, &ulSignatureLen);
4160 
4161     if (CKR_OK == error) {
4162         return CKR_OK;
4163     }
4164 
4165 loser:
4166     /* verify error */
4167     switch (error) {
4168         case CKR_ARGUMENTS_BAD:
4169         case CKR_CRYPTOKI_NOT_INITIALIZED:
4170         case CKR_DATA_INVALID:
4171         case CKR_DATA_LEN_RANGE:
4172         case CKR_DEVICE_ERROR:
4173         case CKR_DEVICE_MEMORY:
4174         case CKR_DEVICE_REMOVED:
4175         case CKR_FUNCTION_CANCELED:
4176         case CKR_FUNCTION_FAILED:
4177         case CKR_GENERAL_ERROR:
4178         case CKR_HOST_MEMORY:
4179         case CKR_OPERATION_NOT_INITIALIZED:
4180         case CKR_SESSION_CLOSED:
4181         case CKR_SESSION_HANDLE_INVALID:
4182         case CKR_SIGNATURE_INVALID:
4183         case CKR_SIGNATURE_LEN_RANGE:
4184             break;
4185         default:
4186         case CKR_OK:
4187             error = CKR_GENERAL_ERROR;
4188             break;
4189     }
4190     return error;
4191 }
4192 
4193 /*
4194  * NSSCKFWC_VerifyUpdate
4195  *
4196  */
4197 NSS_IMPLEMENT CK_RV
NSSCKFWC_VerifyUpdate(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_BYTE_PTR pPart,CK_ULONG ulPartLen)4198 NSSCKFWC_VerifyUpdate(
4199     NSSCKFWInstance *fwInstance,
4200     CK_SESSION_HANDLE hSession,
4201     CK_BYTE_PTR pPart,
4202     CK_ULONG ulPartLen)
4203 {
4204     CK_RV error = CKR_OK;
4205     NSSCKFWSession *fwSession;
4206 
4207     if (!fwInstance) {
4208         error = CKR_CRYPTOKI_NOT_INITIALIZED;
4209         goto loser;
4210     }
4211 
4212     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
4213     if (!fwSession) {
4214         error = CKR_SESSION_HANDLE_INVALID;
4215         goto loser;
4216     }
4217 
4218     error = nssCKFWSession_DigestUpdate(fwSession,
4219                                         NSSCKFWCryptoOperationType_Verify,
4220                                         NSSCKFWCryptoOperationState_SignVerify,
4221                                         pPart, ulPartLen);
4222 
4223     if (CKR_OK == error) {
4224         return CKR_OK;
4225     }
4226 
4227 loser:
4228     /* verify error */
4229     switch (error) {
4230         case CKR_ARGUMENTS_BAD:
4231         case CKR_CRYPTOKI_NOT_INITIALIZED:
4232         case CKR_DATA_LEN_RANGE:
4233         case CKR_DEVICE_ERROR:
4234         case CKR_DEVICE_MEMORY:
4235         case CKR_DEVICE_REMOVED:
4236         case CKR_FUNCTION_CANCELED:
4237         case CKR_FUNCTION_FAILED:
4238         case CKR_GENERAL_ERROR:
4239         case CKR_HOST_MEMORY:
4240         case CKR_OPERATION_NOT_INITIALIZED:
4241         case CKR_SESSION_CLOSED:
4242         case CKR_SESSION_HANDLE_INVALID:
4243             break;
4244         default:
4245         case CKR_OK:
4246             error = CKR_GENERAL_ERROR;
4247             break;
4248     }
4249     return error;
4250 }
4251 
4252 /*
4253  * NSSCKFWC_VerifyFinal
4254  *
4255  */
4256 NSS_IMPLEMENT CK_RV
NSSCKFWC_VerifyFinal(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_BYTE_PTR pSignature,CK_ULONG ulSignatureLen)4257 NSSCKFWC_VerifyFinal(
4258     NSSCKFWInstance *fwInstance,
4259     CK_SESSION_HANDLE hSession,
4260     CK_BYTE_PTR pSignature,
4261     CK_ULONG ulSignatureLen)
4262 {
4263     CK_RV error = CKR_OK;
4264     NSSCKFWSession *fwSession;
4265 
4266     if (!fwInstance) {
4267         error = CKR_CRYPTOKI_NOT_INITIALIZED;
4268         goto loser;
4269     }
4270 
4271     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
4272     if (!fwSession) {
4273         error = CKR_SESSION_HANDLE_INVALID;
4274         goto loser;
4275     }
4276 
4277     error = nssCKFWSession_Final(fwSession,
4278                                  NSSCKFWCryptoOperationType_Verify,
4279                                  NSSCKFWCryptoOperationState_SignVerify,
4280                                  pSignature, &ulSignatureLen);
4281 
4282     if (CKR_OK == error) {
4283         return CKR_OK;
4284     }
4285 
4286 loser:
4287     /* verify error */
4288     switch (error) {
4289         case CKR_ARGUMENTS_BAD:
4290         case CKR_CRYPTOKI_NOT_INITIALIZED:
4291         case CKR_DATA_LEN_RANGE:
4292         case CKR_DEVICE_ERROR:
4293         case CKR_DEVICE_MEMORY:
4294         case CKR_DEVICE_REMOVED:
4295         case CKR_FUNCTION_CANCELED:
4296         case CKR_FUNCTION_FAILED:
4297         case CKR_GENERAL_ERROR:
4298         case CKR_HOST_MEMORY:
4299         case CKR_OPERATION_NOT_INITIALIZED:
4300         case CKR_SESSION_CLOSED:
4301         case CKR_SESSION_HANDLE_INVALID:
4302         case CKR_SIGNATURE_INVALID:
4303         case CKR_SIGNATURE_LEN_RANGE:
4304             break;
4305         default:
4306         case CKR_OK:
4307             error = CKR_GENERAL_ERROR;
4308             break;
4309     }
4310     return error;
4311 }
4312 
4313 /*
4314  * NSSCKFWC_VerifyRecoverInit
4315  *
4316  */
4317 NSS_IMPLEMENT CK_RV
NSSCKFWC_VerifyRecoverInit(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_MECHANISM_PTR pMechanism,CK_OBJECT_HANDLE hKey)4318 NSSCKFWC_VerifyRecoverInit(
4319     NSSCKFWInstance *fwInstance,
4320     CK_SESSION_HANDLE hSession,
4321     CK_MECHANISM_PTR pMechanism,
4322     CK_OBJECT_HANDLE hKey)
4323 {
4324     CK_RV error = CKR_OK;
4325     NSSCKFWSession *fwSession;
4326     NSSCKFWObject *fwObject;
4327     NSSCKFWSlot *fwSlot;
4328     NSSCKFWToken *fwToken;
4329     NSSCKFWMechanism *fwMechanism;
4330 
4331     if (!fwInstance) {
4332         error = CKR_CRYPTOKI_NOT_INITIALIZED;
4333         goto loser;
4334     }
4335 
4336     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
4337     if (!fwSession) {
4338         error = CKR_SESSION_HANDLE_INVALID;
4339         goto loser;
4340     }
4341 
4342     fwObject = nssCKFWInstance_ResolveObjectHandle(fwInstance, hKey);
4343     if (!fwObject) {
4344         error = CKR_KEY_HANDLE_INVALID;
4345         goto loser;
4346     }
4347 
4348     fwSlot = nssCKFWSession_GetFWSlot(fwSession);
4349     if (!fwSlot) {
4350         error = CKR_GENERAL_ERROR; /* should never happen! */
4351         goto loser;
4352     }
4353 
4354     if (CK_TRUE != nssCKFWSlot_GetTokenPresent(fwSlot)) {
4355         error = CKR_TOKEN_NOT_PRESENT;
4356         goto loser;
4357     }
4358 
4359     fwToken = nssCKFWSlot_GetToken(fwSlot, &error);
4360     if (!fwToken) {
4361         goto loser;
4362     }
4363 
4364     fwMechanism = nssCKFWToken_GetMechanism(fwToken, pMechanism->mechanism, &error);
4365     if (!fwMechanism) {
4366         goto loser;
4367     }
4368 
4369     error = nssCKFWMechanism_VerifyRecoverInit(fwMechanism, pMechanism,
4370                                                fwSession, fwObject);
4371 
4372     nssCKFWMechanism_Destroy(fwMechanism);
4373 
4374     if (CKR_OK == error) {
4375         return CKR_OK;
4376     }
4377 
4378 loser:
4379     /* verify error */
4380     switch (error) {
4381         case CKR_ARGUMENTS_BAD:
4382         case CKR_CRYPTOKI_NOT_INITIALIZED:
4383         case CKR_DEVICE_ERROR:
4384         case CKR_DEVICE_MEMORY:
4385         case CKR_DEVICE_REMOVED:
4386         case CKR_FUNCTION_CANCELED:
4387         case CKR_FUNCTION_FAILED:
4388         case CKR_GENERAL_ERROR:
4389         case CKR_HOST_MEMORY:
4390         case CKR_KEY_FUNCTION_NOT_PERMITTED:
4391         case CKR_KEY_HANDLE_INVALID:
4392         case CKR_KEY_SIZE_RANGE:
4393         case CKR_KEY_TYPE_INCONSISTENT:
4394         case CKR_MECHANISM_INVALID:
4395         case CKR_MECHANISM_PARAM_INVALID:
4396         case CKR_OPERATION_ACTIVE:
4397         case CKR_PIN_EXPIRED:
4398         case CKR_SESSION_HANDLE_INVALID:
4399         case CKR_SESSION_CLOSED:
4400         case CKR_USER_NOT_LOGGED_IN:
4401             break;
4402         default:
4403         case CKR_OK:
4404             error = CKR_GENERAL_ERROR;
4405             break;
4406     }
4407     return error;
4408 }
4409 
4410 /*
4411  * NSSCKFWC_VerifyRecover
4412  *
4413  */
4414 NSS_IMPLEMENT CK_RV
NSSCKFWC_VerifyRecover(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_BYTE_PTR pSignature,CK_ULONG ulSignatureLen,CK_BYTE_PTR pData,CK_ULONG_PTR pulDataLen)4415 NSSCKFWC_VerifyRecover(
4416     NSSCKFWInstance *fwInstance,
4417     CK_SESSION_HANDLE hSession,
4418     CK_BYTE_PTR pSignature,
4419     CK_ULONG ulSignatureLen,
4420     CK_BYTE_PTR pData,
4421     CK_ULONG_PTR pulDataLen)
4422 {
4423     CK_RV error = CKR_OK;
4424     NSSCKFWSession *fwSession;
4425 
4426     if (!fwInstance) {
4427         error = CKR_CRYPTOKI_NOT_INITIALIZED;
4428         goto loser;
4429     }
4430 
4431     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
4432     if (!fwSession) {
4433         error = CKR_SESSION_HANDLE_INVALID;
4434         goto loser;
4435     }
4436 
4437     error = nssCKFWSession_UpdateFinal(fwSession,
4438                                        NSSCKFWCryptoOperationType_VerifyRecover,
4439                                        NSSCKFWCryptoOperationState_SignVerify,
4440                                        pSignature, ulSignatureLen, pData, pulDataLen);
4441     if (CKR_OK == error) {
4442         return CKR_OK;
4443     }
4444 loser:
4445     /* verify error */
4446     switch (error) {
4447         case CKR_ARGUMENTS_BAD:
4448         case CKR_BUFFER_TOO_SMALL:
4449         case CKR_CRYPTOKI_NOT_INITIALIZED:
4450         case CKR_DATA_INVALID:
4451         case CKR_DATA_LEN_RANGE:
4452         case CKR_DEVICE_ERROR:
4453         case CKR_DEVICE_MEMORY:
4454         case CKR_DEVICE_REMOVED:
4455         case CKR_FUNCTION_CANCELED:
4456         case CKR_FUNCTION_FAILED:
4457         case CKR_GENERAL_ERROR:
4458         case CKR_HOST_MEMORY:
4459         case CKR_OPERATION_NOT_INITIALIZED:
4460         case CKR_SESSION_CLOSED:
4461         case CKR_SESSION_HANDLE_INVALID:
4462         case CKR_SIGNATURE_INVALID:
4463         case CKR_SIGNATURE_LEN_RANGE:
4464             break;
4465         default:
4466         case CKR_OK:
4467             error = CKR_GENERAL_ERROR;
4468             break;
4469     }
4470     return error;
4471 }
4472 
4473 /*
4474  * NSSCKFWC_DigestEncryptUpdate
4475  *
4476  */
4477 NSS_IMPLEMENT CK_RV
NSSCKFWC_DigestEncryptUpdate(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_BYTE_PTR pPart,CK_ULONG ulPartLen,CK_BYTE_PTR pEncryptedPart,CK_ULONG_PTR pulEncryptedPartLen)4478 NSSCKFWC_DigestEncryptUpdate(
4479     NSSCKFWInstance *fwInstance,
4480     CK_SESSION_HANDLE hSession,
4481     CK_BYTE_PTR pPart,
4482     CK_ULONG ulPartLen,
4483     CK_BYTE_PTR pEncryptedPart,
4484     CK_ULONG_PTR pulEncryptedPartLen)
4485 {
4486     CK_RV error = CKR_OK;
4487     NSSCKFWSession *fwSession;
4488 
4489     if (!fwInstance) {
4490         error = CKR_CRYPTOKI_NOT_INITIALIZED;
4491         goto loser;
4492     }
4493 
4494     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
4495     if (!fwSession) {
4496         error = CKR_SESSION_HANDLE_INVALID;
4497         goto loser;
4498     }
4499 
4500     error = nssCKFWSession_UpdateCombo(fwSession,
4501                                        NSSCKFWCryptoOperationType_Encrypt,
4502                                        NSSCKFWCryptoOperationType_Digest,
4503                                        NSSCKFWCryptoOperationState_Digest,
4504                                        pPart, ulPartLen, pEncryptedPart, pulEncryptedPartLen);
4505 
4506     if (CKR_OK == error) {
4507         return CKR_OK;
4508     }
4509 
4510 loser:
4511     /* verify error */
4512     switch (error) {
4513         case CKR_ARGUMENTS_BAD:
4514         case CKR_BUFFER_TOO_SMALL:
4515         case CKR_CRYPTOKI_NOT_INITIALIZED:
4516         case CKR_DATA_LEN_RANGE:
4517         case CKR_DEVICE_ERROR:
4518         case CKR_DEVICE_MEMORY:
4519         case CKR_DEVICE_REMOVED:
4520         case CKR_FUNCTION_CANCELED:
4521         case CKR_FUNCTION_FAILED:
4522         case CKR_GENERAL_ERROR:
4523         case CKR_HOST_MEMORY:
4524         case CKR_OPERATION_NOT_INITIALIZED:
4525         case CKR_SESSION_CLOSED:
4526         case CKR_SESSION_HANDLE_INVALID:
4527             break;
4528         default:
4529         case CKR_OK:
4530             error = CKR_GENERAL_ERROR;
4531             break;
4532     }
4533     return error;
4534 }
4535 
4536 /*
4537  * NSSCKFWC_DecryptDigestUpdate
4538  *
4539  */
4540 NSS_IMPLEMENT CK_RV
NSSCKFWC_DecryptDigestUpdate(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_BYTE_PTR pEncryptedPart,CK_ULONG ulEncryptedPartLen,CK_BYTE_PTR pPart,CK_ULONG_PTR pulPartLen)4541 NSSCKFWC_DecryptDigestUpdate(
4542     NSSCKFWInstance *fwInstance,
4543     CK_SESSION_HANDLE hSession,
4544     CK_BYTE_PTR pEncryptedPart,
4545     CK_ULONG ulEncryptedPartLen,
4546     CK_BYTE_PTR pPart,
4547     CK_ULONG_PTR pulPartLen)
4548 {
4549     CK_RV error = CKR_OK;
4550     NSSCKFWSession *fwSession;
4551 
4552     if (!fwInstance) {
4553         error = CKR_CRYPTOKI_NOT_INITIALIZED;
4554         goto loser;
4555     }
4556 
4557     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
4558     if (!fwSession) {
4559         error = CKR_SESSION_HANDLE_INVALID;
4560         goto loser;
4561     }
4562 
4563     error = nssCKFWSession_UpdateCombo(fwSession,
4564                                        NSSCKFWCryptoOperationType_Decrypt,
4565                                        NSSCKFWCryptoOperationType_Digest,
4566                                        NSSCKFWCryptoOperationState_Digest,
4567                                        pEncryptedPart, ulEncryptedPartLen, pPart, pulPartLen);
4568 
4569     if (CKR_OK == error) {
4570         return CKR_OK;
4571     }
4572 
4573 loser:
4574     /* verify error */
4575     switch (error) {
4576         case CKR_ARGUMENTS_BAD:
4577         case CKR_BUFFER_TOO_SMALL:
4578         case CKR_CRYPTOKI_NOT_INITIALIZED:
4579         case CKR_DEVICE_ERROR:
4580         case CKR_DEVICE_MEMORY:
4581         case CKR_DEVICE_REMOVED:
4582         case CKR_ENCRYPTED_DATA_INVALID:
4583         case CKR_ENCRYPTED_DATA_LEN_RANGE:
4584         case CKR_FUNCTION_CANCELED:
4585         case CKR_FUNCTION_FAILED:
4586         case CKR_GENERAL_ERROR:
4587         case CKR_HOST_MEMORY:
4588         case CKR_OPERATION_NOT_INITIALIZED:
4589         case CKR_SESSION_CLOSED:
4590         case CKR_SESSION_HANDLE_INVALID:
4591             break;
4592         case CKR_DATA_INVALID:
4593             error = CKR_ENCRYPTED_DATA_INVALID;
4594             break;
4595         case CKR_DATA_LEN_RANGE:
4596             error = CKR_ENCRYPTED_DATA_LEN_RANGE;
4597             break;
4598         default:
4599         case CKR_OK:
4600             error = CKR_GENERAL_ERROR;
4601             break;
4602     }
4603     return error;
4604 }
4605 
4606 /*
4607  * NSSCKFWC_SignEncryptUpdate
4608  *
4609  */
4610 NSS_IMPLEMENT CK_RV
NSSCKFWC_SignEncryptUpdate(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_BYTE_PTR pPart,CK_ULONG ulPartLen,CK_BYTE_PTR pEncryptedPart,CK_ULONG_PTR pulEncryptedPartLen)4611 NSSCKFWC_SignEncryptUpdate(
4612     NSSCKFWInstance *fwInstance,
4613     CK_SESSION_HANDLE hSession,
4614     CK_BYTE_PTR pPart,
4615     CK_ULONG ulPartLen,
4616     CK_BYTE_PTR pEncryptedPart,
4617     CK_ULONG_PTR pulEncryptedPartLen)
4618 {
4619     CK_RV error = CKR_OK;
4620     NSSCKFWSession *fwSession;
4621 
4622     if (!fwInstance) {
4623         error = CKR_CRYPTOKI_NOT_INITIALIZED;
4624         goto loser;
4625     }
4626 
4627     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
4628     if (!fwSession) {
4629         error = CKR_SESSION_HANDLE_INVALID;
4630         goto loser;
4631     }
4632 
4633     error = nssCKFWSession_UpdateCombo(fwSession,
4634                                        NSSCKFWCryptoOperationType_Encrypt,
4635                                        NSSCKFWCryptoOperationType_Sign,
4636                                        NSSCKFWCryptoOperationState_SignVerify,
4637                                        pPart, ulPartLen, pEncryptedPart, pulEncryptedPartLen);
4638 
4639     if (CKR_OK == error) {
4640         return CKR_OK;
4641     }
4642 
4643 loser:
4644     /* verify error */
4645     switch (error) {
4646         case CKR_ARGUMENTS_BAD:
4647         case CKR_BUFFER_TOO_SMALL:
4648         case CKR_CRYPTOKI_NOT_INITIALIZED:
4649         case CKR_DATA_LEN_RANGE:
4650         case CKR_DEVICE_ERROR:
4651         case CKR_DEVICE_MEMORY:
4652         case CKR_DEVICE_REMOVED:
4653         case CKR_FUNCTION_CANCELED:
4654         case CKR_FUNCTION_FAILED:
4655         case CKR_GENERAL_ERROR:
4656         case CKR_HOST_MEMORY:
4657         case CKR_OPERATION_NOT_INITIALIZED:
4658         case CKR_SESSION_CLOSED:
4659         case CKR_SESSION_HANDLE_INVALID:
4660         case CKR_USER_NOT_LOGGED_IN:
4661             break;
4662         default:
4663         case CKR_OK:
4664             error = CKR_GENERAL_ERROR;
4665             break;
4666     }
4667     return error;
4668 }
4669 
4670 /*
4671  * NSSCKFWC_DecryptVerifyUpdate
4672  *
4673  */
4674 NSS_IMPLEMENT CK_RV
NSSCKFWC_DecryptVerifyUpdate(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_BYTE_PTR pEncryptedPart,CK_ULONG ulEncryptedPartLen,CK_BYTE_PTR pPart,CK_ULONG_PTR pulPartLen)4675 NSSCKFWC_DecryptVerifyUpdate(
4676     NSSCKFWInstance *fwInstance,
4677     CK_SESSION_HANDLE hSession,
4678     CK_BYTE_PTR pEncryptedPart,
4679     CK_ULONG ulEncryptedPartLen,
4680     CK_BYTE_PTR pPart,
4681     CK_ULONG_PTR pulPartLen)
4682 {
4683     CK_RV error = CKR_OK;
4684     NSSCKFWSession *fwSession;
4685 
4686     if (!fwInstance) {
4687         error = CKR_CRYPTOKI_NOT_INITIALIZED;
4688         goto loser;
4689     }
4690 
4691     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
4692     if (!fwSession) {
4693         error = CKR_SESSION_HANDLE_INVALID;
4694         goto loser;
4695     }
4696 
4697     error = nssCKFWSession_UpdateCombo(fwSession,
4698                                        NSSCKFWCryptoOperationType_Decrypt,
4699                                        NSSCKFWCryptoOperationType_Verify,
4700                                        NSSCKFWCryptoOperationState_SignVerify,
4701                                        pEncryptedPart, ulEncryptedPartLen, pPart, pulPartLen);
4702 
4703     if (CKR_OK == error) {
4704         return CKR_OK;
4705     }
4706 
4707 loser:
4708     /* verify error */
4709     switch (error) {
4710         case CKR_ARGUMENTS_BAD:
4711         case CKR_BUFFER_TOO_SMALL:
4712         case CKR_CRYPTOKI_NOT_INITIALIZED:
4713         case CKR_DATA_LEN_RANGE:
4714         case CKR_DEVICE_ERROR:
4715         case CKR_DEVICE_MEMORY:
4716         case CKR_DEVICE_REMOVED:
4717         case CKR_ENCRYPTED_DATA_INVALID:
4718         case CKR_ENCRYPTED_DATA_LEN_RANGE:
4719         case CKR_FUNCTION_CANCELED:
4720         case CKR_FUNCTION_FAILED:
4721         case CKR_GENERAL_ERROR:
4722         case CKR_HOST_MEMORY:
4723         case CKR_OPERATION_NOT_INITIALIZED:
4724         case CKR_SESSION_CLOSED:
4725         case CKR_SESSION_HANDLE_INVALID:
4726             break;
4727         case CKR_DATA_INVALID:
4728             error = CKR_ENCRYPTED_DATA_INVALID;
4729             break;
4730         default:
4731         case CKR_OK:
4732             error = CKR_GENERAL_ERROR;
4733             break;
4734     }
4735     return error;
4736 }
4737 
4738 /*
4739  * NSSCKFWC_GenerateKey
4740  *
4741  */
4742 NSS_IMPLEMENT CK_RV
NSSCKFWC_GenerateKey(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_MECHANISM_PTR pMechanism,CK_ATTRIBUTE_PTR pTemplate,CK_ULONG ulCount,CK_OBJECT_HANDLE_PTR phKey)4743 NSSCKFWC_GenerateKey(
4744     NSSCKFWInstance *fwInstance,
4745     CK_SESSION_HANDLE hSession,
4746     CK_MECHANISM_PTR pMechanism,
4747     CK_ATTRIBUTE_PTR pTemplate,
4748     CK_ULONG ulCount,
4749     CK_OBJECT_HANDLE_PTR phKey)
4750 {
4751     CK_RV error = CKR_OK;
4752     NSSCKFWSession *fwSession;
4753     NSSCKFWObject *fwObject;
4754     NSSCKFWSlot *fwSlot;
4755     NSSCKFWToken *fwToken;
4756     NSSCKFWMechanism *fwMechanism;
4757 
4758     if (!fwInstance) {
4759         error = CKR_CRYPTOKI_NOT_INITIALIZED;
4760         goto loser;
4761     }
4762 
4763     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
4764     if (!fwSession) {
4765         error = CKR_SESSION_HANDLE_INVALID;
4766         goto loser;
4767     }
4768 
4769     fwSlot = nssCKFWSession_GetFWSlot(fwSession);
4770     if (!fwSlot) {
4771         error = CKR_GENERAL_ERROR; /* should never happen! */
4772         goto loser;
4773     }
4774 
4775     if (CK_TRUE != nssCKFWSlot_GetTokenPresent(fwSlot)) {
4776         error = CKR_TOKEN_NOT_PRESENT;
4777         goto loser;
4778     }
4779 
4780     fwToken = nssCKFWSlot_GetToken(fwSlot, &error);
4781     if (!fwToken) {
4782         goto loser;
4783     }
4784 
4785     fwMechanism = nssCKFWToken_GetMechanism(fwToken, pMechanism->mechanism, &error);
4786     if (!fwMechanism) {
4787         goto loser;
4788     }
4789 
4790     fwObject = nssCKFWMechanism_GenerateKey(
4791         fwMechanism,
4792         pMechanism,
4793         fwSession,
4794         pTemplate,
4795         ulCount,
4796         &error);
4797 
4798     nssCKFWMechanism_Destroy(fwMechanism);
4799     if (!fwObject) {
4800         goto loser;
4801     }
4802     *phKey = nssCKFWInstance_CreateObjectHandle(fwInstance, fwObject, &error);
4803 
4804     if (CKR_OK == error) {
4805         return CKR_OK;
4806     }
4807 
4808 loser:
4809     /* verify error */
4810     switch (error) {
4811         case CKR_ARGUMENTS_BAD:
4812         case CKR_ATTRIBUTE_READ_ONLY:
4813         case CKR_ATTRIBUTE_TYPE_INVALID:
4814         case CKR_ATTRIBUTE_VALUE_INVALID:
4815         case CKR_CRYPTOKI_NOT_INITIALIZED:
4816         case CKR_DEVICE_ERROR:
4817         case CKR_DEVICE_MEMORY:
4818         case CKR_DEVICE_REMOVED:
4819         case CKR_FUNCTION_CANCELED:
4820         case CKR_FUNCTION_FAILED:
4821         case CKR_GENERAL_ERROR:
4822         case CKR_HOST_MEMORY:
4823         case CKR_MECHANISM_INVALID:
4824         case CKR_MECHANISM_PARAM_INVALID:
4825         case CKR_OPERATION_ACTIVE:
4826         case CKR_PIN_EXPIRED:
4827         case CKR_SESSION_CLOSED:
4828         case CKR_SESSION_HANDLE_INVALID:
4829         case CKR_SESSION_READ_ONLY:
4830         case CKR_TEMPLATE_INCOMPLETE:
4831         case CKR_TEMPLATE_INCONSISTENT:
4832         case CKR_TOKEN_WRITE_PROTECTED:
4833         case CKR_USER_NOT_LOGGED_IN:
4834             break;
4835         default:
4836         case CKR_OK:
4837             error = CKR_GENERAL_ERROR;
4838             break;
4839     }
4840     return error;
4841 }
4842 
4843 /*
4844  * NSSCKFWC_GenerateKeyPair
4845  *
4846  */
4847 NSS_IMPLEMENT CK_RV
NSSCKFWC_GenerateKeyPair(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_MECHANISM_PTR pMechanism,CK_ATTRIBUTE_PTR pPublicKeyTemplate,CK_ULONG ulPublicKeyAttributeCount,CK_ATTRIBUTE_PTR pPrivateKeyTemplate,CK_ULONG ulPrivateKeyAttributeCount,CK_OBJECT_HANDLE_PTR phPublicKey,CK_OBJECT_HANDLE_PTR phPrivateKey)4848 NSSCKFWC_GenerateKeyPair(
4849     NSSCKFWInstance *fwInstance,
4850     CK_SESSION_HANDLE hSession,
4851     CK_MECHANISM_PTR pMechanism,
4852     CK_ATTRIBUTE_PTR pPublicKeyTemplate,
4853     CK_ULONG ulPublicKeyAttributeCount,
4854     CK_ATTRIBUTE_PTR pPrivateKeyTemplate,
4855     CK_ULONG ulPrivateKeyAttributeCount,
4856     CK_OBJECT_HANDLE_PTR phPublicKey,
4857     CK_OBJECT_HANDLE_PTR phPrivateKey)
4858 {
4859     CK_RV error = CKR_OK;
4860     NSSCKFWSession *fwSession;
4861     NSSCKFWObject *fwPrivateKeyObject;
4862     NSSCKFWObject *fwPublicKeyObject;
4863     NSSCKFWSlot *fwSlot;
4864     NSSCKFWToken *fwToken;
4865     NSSCKFWMechanism *fwMechanism;
4866 
4867     if (!fwInstance) {
4868         error = CKR_CRYPTOKI_NOT_INITIALIZED;
4869         goto loser;
4870     }
4871 
4872     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
4873     if (!fwSession) {
4874         error = CKR_SESSION_HANDLE_INVALID;
4875         goto loser;
4876     }
4877 
4878     fwSlot = nssCKFWSession_GetFWSlot(fwSession);
4879     if (!fwSlot) {
4880         error = CKR_GENERAL_ERROR; /* should never happen! */
4881         goto loser;
4882     }
4883 
4884     if (CK_TRUE != nssCKFWSlot_GetTokenPresent(fwSlot)) {
4885         error = CKR_TOKEN_NOT_PRESENT;
4886         goto loser;
4887     }
4888 
4889     fwToken = nssCKFWSlot_GetToken(fwSlot, &error);
4890     if (!fwToken) {
4891         goto loser;
4892     }
4893 
4894     fwMechanism = nssCKFWToken_GetMechanism(fwToken, pMechanism->mechanism, &error);
4895     if (!fwMechanism) {
4896         goto loser;
4897     }
4898 
4899     error = nssCKFWMechanism_GenerateKeyPair(
4900         fwMechanism,
4901         pMechanism,
4902         fwSession,
4903         pPublicKeyTemplate,
4904         ulPublicKeyAttributeCount,
4905         pPublicKeyTemplate,
4906         ulPublicKeyAttributeCount,
4907         &fwPublicKeyObject,
4908         &fwPrivateKeyObject);
4909 
4910     nssCKFWMechanism_Destroy(fwMechanism);
4911     if (CKR_OK != error) {
4912         goto loser;
4913     }
4914     *phPublicKey = nssCKFWInstance_CreateObjectHandle(fwInstance,
4915                                                       fwPublicKeyObject,
4916                                                       &error);
4917     if (CKR_OK != error) {
4918         goto loser;
4919     }
4920     *phPrivateKey = nssCKFWInstance_CreateObjectHandle(fwInstance,
4921                                                        fwPrivateKeyObject,
4922                                                        &error);
4923     if (CKR_OK == error) {
4924         return CKR_OK;
4925     }
4926 
4927 loser:
4928     /* verify error */
4929     switch (error) {
4930         case CKR_ARGUMENTS_BAD:
4931         case CKR_ATTRIBUTE_READ_ONLY:
4932         case CKR_ATTRIBUTE_TYPE_INVALID:
4933         case CKR_ATTRIBUTE_VALUE_INVALID:
4934         case CKR_CRYPTOKI_NOT_INITIALIZED:
4935         case CKR_DEVICE_ERROR:
4936         case CKR_DEVICE_MEMORY:
4937         case CKR_DEVICE_REMOVED:
4938         case CKR_DOMAIN_PARAMS_INVALID:
4939         case CKR_FUNCTION_CANCELED:
4940         case CKR_FUNCTION_FAILED:
4941         case CKR_GENERAL_ERROR:
4942         case CKR_HOST_MEMORY:
4943         case CKR_MECHANISM_INVALID:
4944         case CKR_MECHANISM_PARAM_INVALID:
4945         case CKR_OPERATION_ACTIVE:
4946         case CKR_PIN_EXPIRED:
4947         case CKR_SESSION_CLOSED:
4948         case CKR_SESSION_HANDLE_INVALID:
4949         case CKR_SESSION_READ_ONLY:
4950         case CKR_TEMPLATE_INCOMPLETE:
4951         case CKR_TEMPLATE_INCONSISTENT:
4952         case CKR_TOKEN_WRITE_PROTECTED:
4953         case CKR_USER_NOT_LOGGED_IN:
4954             break;
4955         default:
4956         case CKR_OK:
4957             error = CKR_GENERAL_ERROR;
4958             break;
4959     }
4960     return error;
4961 }
4962 
4963 /*
4964  * NSSCKFWC_WrapKey
4965  *
4966  */
4967 NSS_IMPLEMENT CK_RV
NSSCKFWC_WrapKey(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_MECHANISM_PTR pMechanism,CK_OBJECT_HANDLE hWrappingKey,CK_OBJECT_HANDLE hKey,CK_BYTE_PTR pWrappedKey,CK_ULONG_PTR pulWrappedKeyLen)4968 NSSCKFWC_WrapKey(
4969     NSSCKFWInstance *fwInstance,
4970     CK_SESSION_HANDLE hSession,
4971     CK_MECHANISM_PTR pMechanism,
4972     CK_OBJECT_HANDLE hWrappingKey,
4973     CK_OBJECT_HANDLE hKey,
4974     CK_BYTE_PTR pWrappedKey,
4975     CK_ULONG_PTR pulWrappedKeyLen)
4976 {
4977     CK_RV error = CKR_OK;
4978     NSSCKFWSession *fwSession;
4979     NSSCKFWObject *fwKeyObject;
4980     NSSCKFWObject *fwWrappingKeyObject;
4981     NSSCKFWSlot *fwSlot;
4982     NSSCKFWToken *fwToken;
4983     NSSCKFWMechanism *fwMechanism;
4984     NSSItem wrappedKey;
4985     CK_ULONG wrappedKeyLength = 0;
4986 
4987     if (!fwInstance) {
4988         error = CKR_CRYPTOKI_NOT_INITIALIZED;
4989         goto loser;
4990     }
4991 
4992     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
4993     if (!fwSession) {
4994         error = CKR_SESSION_HANDLE_INVALID;
4995         goto loser;
4996     }
4997 
4998     fwWrappingKeyObject = nssCKFWInstance_ResolveObjectHandle(fwInstance,
4999                                                               hWrappingKey);
5000     if (!fwWrappingKeyObject) {
5001         error = CKR_WRAPPING_KEY_HANDLE_INVALID;
5002         goto loser;
5003     }
5004 
5005     fwKeyObject = nssCKFWInstance_ResolveObjectHandle(fwInstance, hKey);
5006     if (!fwKeyObject) {
5007         error = CKR_KEY_HANDLE_INVALID;
5008         goto loser;
5009     }
5010 
5011     fwSlot = nssCKFWSession_GetFWSlot(fwSession);
5012     if (!fwSlot) {
5013         error = CKR_GENERAL_ERROR; /* should never happen! */
5014         goto loser;
5015     }
5016 
5017     if (CK_TRUE != nssCKFWSlot_GetTokenPresent(fwSlot)) {
5018         error = CKR_TOKEN_NOT_PRESENT;
5019         goto loser;
5020     }
5021 
5022     fwToken = nssCKFWSlot_GetToken(fwSlot, &error);
5023     if (!fwToken) {
5024         goto loser;
5025     }
5026 
5027     fwMechanism = nssCKFWToken_GetMechanism(fwToken, pMechanism->mechanism, &error);
5028     if (!fwMechanism) {
5029         goto loser;
5030     }
5031 
5032     /*
5033    * first get the length...
5034    */
5035     wrappedKeyLength = nssCKFWMechanism_GetWrapKeyLength(
5036         fwMechanism,
5037         pMechanism,
5038         fwSession,
5039         fwWrappingKeyObject,
5040         fwKeyObject,
5041         &error);
5042     if ((CK_ULONG)0 == wrappedKeyLength) {
5043         nssCKFWMechanism_Destroy(fwMechanism);
5044         goto loser;
5045     }
5046     if ((CK_BYTE_PTR)NULL == pWrappedKey) {
5047         *pulWrappedKeyLen = wrappedKeyLength;
5048         nssCKFWMechanism_Destroy(fwMechanism);
5049         return CKR_OK;
5050     }
5051     if (wrappedKeyLength > *pulWrappedKeyLen) {
5052         *pulWrappedKeyLen = wrappedKeyLength;
5053         nssCKFWMechanism_Destroy(fwMechanism);
5054         error = CKR_BUFFER_TOO_SMALL;
5055         goto loser;
5056     }
5057 
5058     wrappedKey.data = pWrappedKey;
5059     wrappedKey.size = wrappedKeyLength;
5060 
5061     error = nssCKFWMechanism_WrapKey(
5062         fwMechanism,
5063         pMechanism,
5064         fwSession,
5065         fwWrappingKeyObject,
5066         fwKeyObject,
5067         &wrappedKey);
5068 
5069     nssCKFWMechanism_Destroy(fwMechanism);
5070     *pulWrappedKeyLen = wrappedKey.size;
5071 
5072     if (CKR_OK == error) {
5073         return CKR_OK;
5074     }
5075 
5076 loser:
5077     /* verify error */
5078     switch (error) {
5079         case CKR_ARGUMENTS_BAD:
5080         case CKR_BUFFER_TOO_SMALL:
5081         case CKR_CRYPTOKI_NOT_INITIALIZED:
5082         case CKR_DEVICE_ERROR:
5083         case CKR_DEVICE_MEMORY:
5084         case CKR_DEVICE_REMOVED:
5085         case CKR_FUNCTION_CANCELED:
5086         case CKR_FUNCTION_FAILED:
5087         case CKR_GENERAL_ERROR:
5088         case CKR_HOST_MEMORY:
5089         case CKR_KEY_HANDLE_INVALID:
5090         case CKR_KEY_NOT_WRAPPABLE:
5091         case CKR_KEY_SIZE_RANGE:
5092         case CKR_KEY_UNEXTRACTABLE:
5093         case CKR_MECHANISM_INVALID:
5094         case CKR_MECHANISM_PARAM_INVALID:
5095         case CKR_OPERATION_ACTIVE:
5096         case CKR_PIN_EXPIRED:
5097         case CKR_SESSION_CLOSED:
5098         case CKR_SESSION_HANDLE_INVALID:
5099         case CKR_WRAPPING_KEY_HANDLE_INVALID:
5100         case CKR_WRAPPING_KEY_SIZE_RANGE:
5101         case CKR_WRAPPING_KEY_TYPE_INCONSISTENT:
5102             break;
5103         case CKR_KEY_TYPE_INCONSISTENT:
5104             error = CKR_WRAPPING_KEY_TYPE_INCONSISTENT;
5105             break;
5106         default:
5107         case CKR_OK:
5108             error = CKR_GENERAL_ERROR;
5109             break;
5110     }
5111     return error;
5112 }
5113 
5114 /*
5115  * NSSCKFWC_UnwrapKey
5116  *
5117  */
5118 NSS_IMPLEMENT CK_RV
NSSCKFWC_UnwrapKey(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_MECHANISM_PTR pMechanism,CK_OBJECT_HANDLE hUnwrappingKey,CK_BYTE_PTR pWrappedKey,CK_ULONG ulWrappedKeyLen,CK_ATTRIBUTE_PTR pTemplate,CK_ULONG ulAttributeCount,CK_OBJECT_HANDLE_PTR phKey)5119 NSSCKFWC_UnwrapKey(
5120     NSSCKFWInstance *fwInstance,
5121     CK_SESSION_HANDLE hSession,
5122     CK_MECHANISM_PTR pMechanism,
5123     CK_OBJECT_HANDLE hUnwrappingKey,
5124     CK_BYTE_PTR pWrappedKey,
5125     CK_ULONG ulWrappedKeyLen,
5126     CK_ATTRIBUTE_PTR pTemplate,
5127     CK_ULONG ulAttributeCount,
5128     CK_OBJECT_HANDLE_PTR phKey)
5129 {
5130     CK_RV error = CKR_OK;
5131     NSSCKFWSession *fwSession;
5132     NSSCKFWObject *fwObject;
5133     NSSCKFWObject *fwWrappingKeyObject;
5134     NSSCKFWSlot *fwSlot;
5135     NSSCKFWToken *fwToken;
5136     NSSCKFWMechanism *fwMechanism;
5137     NSSItem wrappedKey;
5138 
5139     if (!fwInstance) {
5140         error = CKR_CRYPTOKI_NOT_INITIALIZED;
5141         goto loser;
5142     }
5143 
5144     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
5145     if (!fwSession) {
5146         error = CKR_SESSION_HANDLE_INVALID;
5147         goto loser;
5148     }
5149 
5150     fwWrappingKeyObject = nssCKFWInstance_ResolveObjectHandle(fwInstance,
5151                                                               hUnwrappingKey);
5152     if (!fwWrappingKeyObject) {
5153         error = CKR_WRAPPING_KEY_HANDLE_INVALID;
5154         goto loser;
5155     }
5156 
5157     fwSlot = nssCKFWSession_GetFWSlot(fwSession);
5158     if (!fwSlot) {
5159         error = CKR_GENERAL_ERROR; /* should never happen! */
5160         goto loser;
5161     }
5162 
5163     if (CK_TRUE != nssCKFWSlot_GetTokenPresent(fwSlot)) {
5164         error = CKR_TOKEN_NOT_PRESENT;
5165         goto loser;
5166     }
5167 
5168     fwToken = nssCKFWSlot_GetToken(fwSlot, &error);
5169     if (!fwToken) {
5170         goto loser;
5171     }
5172 
5173     fwMechanism = nssCKFWToken_GetMechanism(fwToken, pMechanism->mechanism, &error);
5174     if (!fwMechanism) {
5175         goto loser;
5176     }
5177 
5178     wrappedKey.data = pWrappedKey;
5179     wrappedKey.size = ulWrappedKeyLen;
5180 
5181     fwObject = nssCKFWMechanism_UnwrapKey(
5182         fwMechanism,
5183         pMechanism,
5184         fwSession,
5185         fwWrappingKeyObject,
5186         &wrappedKey,
5187         pTemplate,
5188         ulAttributeCount,
5189         &error);
5190 
5191     nssCKFWMechanism_Destroy(fwMechanism);
5192     if (!fwObject) {
5193         goto loser;
5194     }
5195     *phKey = nssCKFWInstance_CreateObjectHandle(fwInstance, fwObject, &error);
5196 
5197     if (CKR_OK == error) {
5198         return CKR_OK;
5199     }
5200 
5201 loser:
5202     /* verify error */
5203     switch (error) {
5204         case CKR_ARGUMENTS_BAD:
5205         case CKR_ATTRIBUTE_READ_ONLY:
5206         case CKR_ATTRIBUTE_TYPE_INVALID:
5207         case CKR_ATTRIBUTE_VALUE_INVALID:
5208         case CKR_BUFFER_TOO_SMALL:
5209         case CKR_CRYPTOKI_NOT_INITIALIZED:
5210         case CKR_DEVICE_ERROR:
5211         case CKR_DEVICE_MEMORY:
5212         case CKR_DEVICE_REMOVED:
5213         case CKR_DOMAIN_PARAMS_INVALID:
5214         case CKR_FUNCTION_CANCELED:
5215         case CKR_FUNCTION_FAILED:
5216         case CKR_GENERAL_ERROR:
5217         case CKR_HOST_MEMORY:
5218         case CKR_MECHANISM_INVALID:
5219         case CKR_MECHANISM_PARAM_INVALID:
5220         case CKR_OPERATION_ACTIVE:
5221         case CKR_PIN_EXPIRED:
5222         case CKR_SESSION_CLOSED:
5223         case CKR_SESSION_HANDLE_INVALID:
5224         case CKR_SESSION_READ_ONLY:
5225         case CKR_TEMPLATE_INCOMPLETE:
5226         case CKR_TEMPLATE_INCONSISTENT:
5227         case CKR_TOKEN_WRITE_PROTECTED:
5228         case CKR_UNWRAPPING_KEY_HANDLE_INVALID:
5229         case CKR_UNWRAPPING_KEY_SIZE_RANGE:
5230         case CKR_UNWRAPPING_KEY_TYPE_INCONSISTENT:
5231         case CKR_USER_NOT_LOGGED_IN:
5232         case CKR_WRAPPED_KEY_INVALID:
5233         case CKR_WRAPPED_KEY_LEN_RANGE:
5234             break;
5235         case CKR_KEY_HANDLE_INVALID:
5236             error = CKR_UNWRAPPING_KEY_HANDLE_INVALID;
5237             break;
5238         case CKR_KEY_SIZE_RANGE:
5239             error = CKR_UNWRAPPING_KEY_SIZE_RANGE;
5240             break;
5241         case CKR_KEY_TYPE_INCONSISTENT:
5242             error = CKR_UNWRAPPING_KEY_TYPE_INCONSISTENT;
5243             break;
5244         case CKR_ENCRYPTED_DATA_INVALID:
5245             error = CKR_WRAPPED_KEY_INVALID;
5246             break;
5247         case CKR_ENCRYPTED_DATA_LEN_RANGE:
5248             error = CKR_WRAPPED_KEY_LEN_RANGE;
5249             break;
5250         default:
5251         case CKR_OK:
5252             error = CKR_GENERAL_ERROR;
5253             break;
5254     }
5255     return error;
5256 }
5257 
5258 /*
5259  * NSSCKFWC_DeriveKey
5260  *
5261  */
5262 NSS_IMPLEMENT CK_RV
NSSCKFWC_DeriveKey(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_MECHANISM_PTR pMechanism,CK_OBJECT_HANDLE hBaseKey,CK_ATTRIBUTE_PTR pTemplate,CK_ULONG ulAttributeCount,CK_OBJECT_HANDLE_PTR phKey)5263 NSSCKFWC_DeriveKey(
5264     NSSCKFWInstance *fwInstance,
5265     CK_SESSION_HANDLE hSession,
5266     CK_MECHANISM_PTR pMechanism,
5267     CK_OBJECT_HANDLE hBaseKey,
5268     CK_ATTRIBUTE_PTR pTemplate,
5269     CK_ULONG ulAttributeCount,
5270     CK_OBJECT_HANDLE_PTR phKey)
5271 {
5272     CK_RV error = CKR_OK;
5273     NSSCKFWSession *fwSession;
5274     NSSCKFWObject *fwObject;
5275     NSSCKFWObject *fwBaseKeyObject;
5276     NSSCKFWSlot *fwSlot;
5277     NSSCKFWToken *fwToken;
5278     NSSCKFWMechanism *fwMechanism;
5279 
5280     if (!fwInstance) {
5281         error = CKR_CRYPTOKI_NOT_INITIALIZED;
5282         goto loser;
5283     }
5284 
5285     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
5286     if (!fwSession) {
5287         error = CKR_SESSION_HANDLE_INVALID;
5288         goto loser;
5289     }
5290 
5291     fwBaseKeyObject = nssCKFWInstance_ResolveObjectHandle(fwInstance, hBaseKey);
5292     if (!fwBaseKeyObject) {
5293         error = CKR_KEY_HANDLE_INVALID;
5294         goto loser;
5295     }
5296 
5297     fwSlot = nssCKFWSession_GetFWSlot(fwSession);
5298     if (!fwSlot) {
5299         error = CKR_GENERAL_ERROR; /* should never happen! */
5300         goto loser;
5301     }
5302 
5303     if (CK_TRUE != nssCKFWSlot_GetTokenPresent(fwSlot)) {
5304         error = CKR_TOKEN_NOT_PRESENT;
5305         goto loser;
5306     }
5307 
5308     fwToken = nssCKFWSlot_GetToken(fwSlot, &error);
5309     if (!fwToken) {
5310         goto loser;
5311     }
5312 
5313     fwMechanism = nssCKFWToken_GetMechanism(fwToken, pMechanism->mechanism, &error);
5314     if (!fwMechanism) {
5315         goto loser;
5316     }
5317 
5318     fwObject = nssCKFWMechanism_DeriveKey(
5319         fwMechanism,
5320         pMechanism,
5321         fwSession,
5322         fwBaseKeyObject,
5323         pTemplate,
5324         ulAttributeCount,
5325         &error);
5326 
5327     nssCKFWMechanism_Destroy(fwMechanism);
5328     if (!fwObject) {
5329         goto loser;
5330     }
5331     *phKey = nssCKFWInstance_CreateObjectHandle(fwInstance, fwObject, &error);
5332 
5333     if (CKR_OK == error) {
5334         return CKR_OK;
5335     }
5336 
5337 loser:
5338     /* verify error */
5339     switch (error) {
5340         case CKR_ARGUMENTS_BAD:
5341         case CKR_ATTRIBUTE_READ_ONLY:
5342         case CKR_ATTRIBUTE_TYPE_INVALID:
5343         case CKR_ATTRIBUTE_VALUE_INVALID:
5344         case CKR_CRYPTOKI_NOT_INITIALIZED:
5345         case CKR_DEVICE_ERROR:
5346         case CKR_DEVICE_MEMORY:
5347         case CKR_DEVICE_REMOVED:
5348         case CKR_DOMAIN_PARAMS_INVALID:
5349         case CKR_FUNCTION_CANCELED:
5350         case CKR_FUNCTION_FAILED:
5351         case CKR_GENERAL_ERROR:
5352         case CKR_HOST_MEMORY:
5353         case CKR_KEY_HANDLE_INVALID:
5354         case CKR_KEY_SIZE_RANGE:
5355         case CKR_KEY_TYPE_INCONSISTENT:
5356         case CKR_MECHANISM_INVALID:
5357         case CKR_MECHANISM_PARAM_INVALID:
5358         case CKR_OPERATION_ACTIVE:
5359         case CKR_PIN_EXPIRED:
5360         case CKR_SESSION_CLOSED:
5361         case CKR_SESSION_HANDLE_INVALID:
5362         case CKR_SESSION_READ_ONLY:
5363         case CKR_TEMPLATE_INCOMPLETE:
5364         case CKR_TEMPLATE_INCONSISTENT:
5365         case CKR_TOKEN_WRITE_PROTECTED:
5366         case CKR_USER_NOT_LOGGED_IN:
5367             break;
5368         default:
5369         case CKR_OK:
5370             error = CKR_GENERAL_ERROR;
5371             break;
5372     }
5373     return error;
5374 }
5375 
5376 /*
5377  * NSSCKFWC_SeedRandom
5378  *
5379  */
5380 NSS_IMPLEMENT CK_RV
NSSCKFWC_SeedRandom(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_BYTE_PTR pSeed,CK_ULONG ulSeedLen)5381 NSSCKFWC_SeedRandom(
5382     NSSCKFWInstance *fwInstance,
5383     CK_SESSION_HANDLE hSession,
5384     CK_BYTE_PTR pSeed,
5385     CK_ULONG ulSeedLen)
5386 {
5387     CK_RV error = CKR_OK;
5388     NSSCKFWSession *fwSession;
5389     NSSItem seed;
5390 
5391     if (!fwInstance) {
5392         error = CKR_CRYPTOKI_NOT_INITIALIZED;
5393         goto loser;
5394     }
5395 
5396     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
5397     if (!fwSession) {
5398         error = CKR_SESSION_HANDLE_INVALID;
5399         goto loser;
5400     }
5401 
5402     if ((CK_BYTE_PTR)CK_NULL_PTR == pSeed) {
5403         error = CKR_ARGUMENTS_BAD;
5404         goto loser;
5405     }
5406 
5407     /* We could read through the buffer in a Purify trap */
5408 
5409     seed.size = (PRUint32)ulSeedLen;
5410     seed.data = (void *)pSeed;
5411 
5412     error = nssCKFWSession_SeedRandom(fwSession, &seed);
5413 
5414     if (CKR_OK != error) {
5415         goto loser;
5416     }
5417 
5418     return CKR_OK;
5419 
5420 loser:
5421     switch (error) {
5422         case CKR_SESSION_CLOSED:
5423             /* destroy session? */
5424             break;
5425         case CKR_DEVICE_REMOVED:
5426             /* (void)nssCKFWToken_Destroy(fwToken); */
5427             break;
5428         case CKR_ARGUMENTS_BAD:
5429         case CKR_CRYPTOKI_NOT_INITIALIZED:
5430         case CKR_DEVICE_ERROR:
5431         case CKR_DEVICE_MEMORY:
5432         case CKR_FUNCTION_CANCELED:
5433         case CKR_FUNCTION_FAILED:
5434         case CKR_GENERAL_ERROR:
5435         case CKR_HOST_MEMORY:
5436         case CKR_OPERATION_ACTIVE:
5437         case CKR_RANDOM_SEED_NOT_SUPPORTED:
5438         case CKR_RANDOM_NO_RNG:
5439         case CKR_SESSION_HANDLE_INVALID:
5440         case CKR_USER_NOT_LOGGED_IN:
5441             break;
5442         default:
5443         case CKR_OK:
5444             error = CKR_GENERAL_ERROR;
5445             break;
5446     }
5447 
5448     return error;
5449 }
5450 
5451 /*
5452  * NSSCKFWC_GenerateRandom
5453  *
5454  */
5455 NSS_IMPLEMENT CK_RV
NSSCKFWC_GenerateRandom(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession,CK_BYTE_PTR pRandomData,CK_ULONG ulRandomLen)5456 NSSCKFWC_GenerateRandom(
5457     NSSCKFWInstance *fwInstance,
5458     CK_SESSION_HANDLE hSession,
5459     CK_BYTE_PTR pRandomData,
5460     CK_ULONG ulRandomLen)
5461 {
5462     CK_RV error = CKR_OK;
5463     NSSCKFWSession *fwSession;
5464     NSSItem buffer;
5465 
5466     if (!fwInstance) {
5467         error = CKR_CRYPTOKI_NOT_INITIALIZED;
5468         goto loser;
5469     }
5470 
5471     fwSession = nssCKFWInstance_ResolveSessionHandle(fwInstance, hSession);
5472     if (!fwSession) {
5473         error = CKR_SESSION_HANDLE_INVALID;
5474         goto loser;
5475     }
5476 
5477     if ((CK_BYTE_PTR)CK_NULL_PTR == pRandomData) {
5478         error = CKR_ARGUMENTS_BAD;
5479         goto loser;
5480     }
5481 
5482     /*
5483    * A purify error here indicates caller error.
5484    */
5485     (void)nsslibc_memset(pRandomData, 0, ulRandomLen);
5486 
5487     buffer.size = (PRUint32)ulRandomLen;
5488     buffer.data = (void *)pRandomData;
5489 
5490     error = nssCKFWSession_GetRandom(fwSession, &buffer);
5491 
5492     if (CKR_OK != error) {
5493         goto loser;
5494     }
5495 
5496     return CKR_OK;
5497 
5498 loser:
5499     switch (error) {
5500         case CKR_SESSION_CLOSED:
5501             /* destroy session? */
5502             break;
5503         case CKR_DEVICE_REMOVED:
5504             /* (void)nssCKFWToken_Destroy(fwToken); */
5505             break;
5506         case CKR_ARGUMENTS_BAD:
5507         case CKR_CRYPTOKI_NOT_INITIALIZED:
5508         case CKR_DEVICE_ERROR:
5509         case CKR_DEVICE_MEMORY:
5510         case CKR_FUNCTION_CANCELED:
5511         case CKR_FUNCTION_FAILED:
5512         case CKR_GENERAL_ERROR:
5513         case CKR_HOST_MEMORY:
5514         case CKR_OPERATION_ACTIVE:
5515         case CKR_RANDOM_NO_RNG:
5516         case CKR_SESSION_HANDLE_INVALID:
5517         case CKR_USER_NOT_LOGGED_IN:
5518             break;
5519         default:
5520         case CKR_OK:
5521             error = CKR_GENERAL_ERROR;
5522             break;
5523     }
5524 
5525     return error;
5526 }
5527 
5528 /*
5529  * NSSCKFWC_GetFunctionStatus
5530  *
5531  */
5532 NSS_IMPLEMENT CK_RV
NSSCKFWC_GetFunctionStatus(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession)5533 NSSCKFWC_GetFunctionStatus(
5534     NSSCKFWInstance *fwInstance,
5535     CK_SESSION_HANDLE hSession)
5536 {
5537     return CKR_FUNCTION_NOT_PARALLEL;
5538 }
5539 
5540 /*
5541  * NSSCKFWC_CancelFunction
5542  *
5543  */
5544 NSS_IMPLEMENT CK_RV
NSSCKFWC_CancelFunction(NSSCKFWInstance * fwInstance,CK_SESSION_HANDLE hSession)5545 NSSCKFWC_CancelFunction(
5546     NSSCKFWInstance *fwInstance,
5547     CK_SESSION_HANDLE hSession)
5548 {
5549     return CKR_FUNCTION_NOT_PARALLEL;
5550 }
5551