reuse old key structures on a given token rather than building it up and

tearing it down every time.
This commit is contained in:
relyea%netscape.com 2000-06-13 21:37:28 +00:00
Родитель 78671954d3
Коммит d43393b11b
4 изменённых файлов: 106 добавлений и 11 удалений

Просмотреть файл

@ -89,6 +89,8 @@ SECStatus PK11_Logout(PK11SlotInfo *slot);
void PK11_LogoutAll(void);
void PK11_EnterSlotMonitor(PK11SlotInfo *);
void PK11_ExitSlotMonitor(PK11SlotInfo *);
void PK11_CleanKeyList(PK11SlotInfo *slot);
/************************************************************

Просмотреть файл

@ -154,6 +154,54 @@ pk11_ExitKeyMonitor(PK11SymKey *symKey) {
PK11_ExitSlotMonitor(symKey->slot);
}
static PK11SymKey *pk11SymKeyHead = NULL;
static PK11SymKey *
pk11_getKeyFromList(PK11SlotInfo *slot) {
PK11SymKey *symKey;
PK11_USE_THREADS(PR_Lock(slot->freeListLock);)
if (slot->freeSymKeysHead) {
symKey = slot->freeSymKeysHead;
slot->freeSymKeysHead = symKey->next;
slot->keyCount--;
}
PK11_USE_THREADS(PR_Unlock(slot->freeListLock);)
if (symKey) {
symKey->next = NULL;
return symKey;
}
symKey = (PK11SymKey *)PORT_ZAlloc(sizeof(PK11SymKey));
if (symKey == NULL) {
return NULL;
}
symKey->refLock = PR_NewLock();
if (symKey->refLock == NULL) {
PORT_Free(symKey);
return NULL;
}
symKey->session = pk11_GetNewSession(slot,&symKey->sessionOwner);
symKey->next = NULL;
return symKey;
}
void
PK11_CleanKeyList(PK11SlotInfo *slot)
{
PK11SymKey *symKey = NULL;
while (slot->freeSymKeysHead) {
symKey = slot->freeSymKeysHead;
slot->freeSymKeysHead = symKey->next;
pk11_CloseSession(symKey->slot, symKey->session,symKey->sessionOwner);
PK11_USE_THREADS(PR_DestroyLock(symKey->refLock);)
PORT_Free(symKey);
};
return;
}
/*
* create a symetric key:
* Slot is the slot to create the key in.
@ -163,15 +211,13 @@ PK11SymKey *
PK11_CreateSymKey(PK11SlotInfo *slot, CK_MECHANISM_TYPE type, void *wincx)
{
PK11SymKey *symKey = (PK11SymKey *)PORT_Alloc(sizeof(PK11SymKey));
PK11SymKey *symKey = pk11_getKeyFromList(slot);
if (symKey == NULL) {
return NULL;
}
symKey->refLock = PR_NewLock();
if (symKey->refLock == NULL) {
PORT_Free(symKey);
return NULL;
}
symKey->type = type;
symKey->data.data = NULL;
symKey->data.len = 0;
@ -183,7 +229,6 @@ PK11_CreateSymKey(PK11SlotInfo *slot, CK_MECHANISM_TYPE type, void *wincx)
symKey->size = 0;
symKey->refCount = 1;
symKey->origin = PK11_OriginNULL;
symKey->session = pk11_GetNewSession(slot,&symKey->sessionOwner);
symKey->origin = PK11_OriginNULL;
PK11_ReferenceSlot(slot);
return symKey;
@ -196,6 +241,8 @@ void
PK11_FreeSymKey(PK11SymKey *symKey)
{
PRBool destroy = PR_FALSE;
PK11SlotInfo *slot;
PRBool freeit = PR_TRUE;
PK11_USE_THREADS(PR_Lock(symKey->refLock);)
if (symKey->refCount-- == 1) {
@ -209,14 +256,27 @@ PK11_FreeSymKey(PK11SymKey *symKey)
C_DestroyObject(symKey->session, symKey->objectID);
pk11_ExitKeyMonitor(symKey);
}
pk11_CloseSession(symKey->slot, symKey->session,symKey->sessionOwner);
if (symKey->data.data) {
PORT_Memset(symKey->data.data, 0, symKey->data.len);
PORT_Free(symKey->data.data);
}
PK11_USE_THREADS(PR_DestroyLock(symKey->refLock);)
PK11_FreeSlot(symKey->slot);
PORT_Free(symKey);
slot = symKey->slot;
PK11_USE_THREADS(PR_Lock(slot->freeListLock);)
if (slot->keyCount < slot->maxKeyCount) {
symKey->next = slot->freeSymKeysHead;
slot->freeSymKeysHead = symKey;
slot->keyCount++;
symKey->slot = NULL;
freeit = PR_FALSE;
}
PK11_USE_THREADS(PR_Unlock(slot->freeListLock);)
if (freeit) {
pk11_CloseSession(symKey->slot, symKey->session,
symKey->sessionOwner);
PK11_USE_THREADS(PR_DestroyLock(symKey->refLock);)
PORT_Free(symKey);
}
PK11_FreeSlot(slot);
}
}

Просмотреть файл

@ -385,10 +385,21 @@ PK11_NewSlotInfo(void)
PORT_Free(slot);
return slot;
}
slot->freeListLock = PR_NewLock();
if (slot->freeListLock == NULL) {
PR_DestroyLock(slot->sessionLock);
PR_DestroyLock(slot->refLock);
PORT_Free(slot);
return slot;
}
#else
slot->sessionLock = NULL;
slot->refLock = NULL;
slot->freeListLock = NULL;
#endif
slot->freeSymKeysHead = NULL;
slot->keyCount = 0;
slot->maxKeyCount = 0;
slot->functionList = NULL;
slot->needTest = PR_TRUE;
slot->isPerm = PR_FALSE;
@ -449,6 +460,9 @@ PK11_DestroySlot(PK11SlotInfo *slot)
/* now free up all the certificates we grabbed on this slot */
PK11_FreeSlotCerts(slot);
/* free up the cached keys and sessions */
PK11_CleanKeyList(slot);
/* finally Tell our parent module that we've gone away so it can unload */
if (slot->module) {
SECMOD_SlotDestroyModule(slot->module,PR_TRUE);
@ -462,6 +476,10 @@ PK11_DestroySlot(PK11SlotInfo *slot)
PR_DestroyLock(slot->sessionLock);
slot->sessionLock = NULL;
}
if (slot->freeListLock) {
PR_DestroyLock(slot->freeListLock);
slot->freeListLock = NULL;
}
#endif
/* ok, well not quit finally... now we free the memory */
@ -1587,6 +1605,16 @@ PK11_InitToken(PK11SlotInfo *slot, PRBool loadCerts)
slot->hasRSAInfo = PR_FALSE;
slot->RSAInfoFlags = 0;
/* initialize the maxKeyCount value */
if (tokenInfo.ulMaxSessionCount == 0) {
slot->maxKeyCount = 300; /* should be #define or a config param */
} else if (tokenInfo.ulMaxSessionCount < 20) {
/* don't have enough sessions to keep that many keys around */
slot->maxKeyCount = 0;
} else {
slot->maxKeyCount = tokenInfo.ulMaxSessionCount/2;
}
/* Make sure our session handle is valid */
if (slot->session == CK_INVALID_SESSION) {
/* we know we don't have a valid session, go get one */

Просмотреть файл

@ -83,6 +83,10 @@ struct PK11SlotInfoStr {
* still in use */
int refCount;
PRLock *refLock;
PRLock *freeListLock;
PK11SymKey *freeSymKeysHead;
int keyCount;
int maxKeyCount;
/* Password control functions for this slot. many of these are only
* active if the appropriate flag is on in defaultFlags */
int askpw; /* what our password options are */
@ -133,6 +137,7 @@ struct PK11SymKeyStr {
CK_OBJECT_HANDLE objectID; /* object id of this key in the slot */
PK11SlotInfo *slot; /* Slot this key is loaded into */
void *cx; /* window context in case we need to loggin */
PK11SymKey *next;
PRBool owner;
SECItem data; /* raw key data if available */
CK_SESSION_HANDLE session;