summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorian.mcgreer%sun.com <devnull@localhost>2002-12-04 18:32:41 +0000
committerian.mcgreer%sun.com <devnull@localhost>2002-12-04 18:32:41 +0000
commitce7931f9ff7229b9217bd3234ded9b39a228fd89 (patch)
tree9a3deb01bbffe8adbb7984a1bada501034e822d2
parent1abc803ca8899f1c0c5a2872fc3d274382a881ae (diff)
downloadnss-hg-ce7931f9ff7229b9217bd3234ded9b39a228fd89.tar.gz
bug 126769, sessionID overflow issues
r/a=wtc, sr=relyea
-rw-r--r--security/nss/lib/softoken/pkcs11.c32
-rw-r--r--security/nss/lib/softoken/pkcs11i.h4
2 files changed, 26 insertions, 10 deletions
diff --git a/security/nss/lib/softoken/pkcs11.c b/security/nss/lib/softoken/pkcs11.c
index 33d4e39a6..56c340984 100644
--- a/security/nss/lib/softoken/pkcs11.c
+++ b/security/nss/lib/softoken/pkcs11.c
@@ -2406,7 +2406,8 @@ PK11_SlotInit(CK_SLOT_ID slotID, PRBool needLogin)
}
slot->password = NULL;
slot->hasTokens = PR_FALSE;
- slot->sessionIDCount = 1;
+ slot->sessionIDCount = 0;
+ slot->sessionIDConflict = 0;
slot->sessionCount = 0;
slot->rwSessionCount = 0;
slot->tokenIDCount = 1;
@@ -2898,6 +2899,7 @@ CK_RV NSC_OpenSession(CK_SLOT_ID slotID, CK_FLAGS flags,
PK11Slot *slot;
CK_SESSION_HANDLE sessionID;
PK11Session *session;
+ PK11Session *sameID;
slot = pk11_SlotFromID(slotID);
if (slot == NULL) return CKR_SLOT_ID_INVALID;
@@ -2908,19 +2910,29 @@ CK_RV NSC_OpenSession(CK_SLOT_ID slotID, CK_FLAGS flags,
if (session == NULL) return CKR_HOST_MEMORY;
PK11_USE_THREADS(PZ_Lock(slot->sessionLock);)
- sessionID = slot->sessionIDCount++;
- if (slotID == PRIVATE_KEY_SLOT_ID) {
- sessionID |= PK11_PRIVATE_KEY_FLAG;
- } else if (slotID == FIPS_SLOT_ID) {
- sessionID |= PK11_FIPS_FLAG;
- } else if (flags & CKF_RW_SESSION) {
+ if (slotID == NETSCAPE_SLOT_ID && (flags & CKF_RW_SESSION)) {
/* NETSCAPE_SLOT_ID is Read ONLY */
session->info.flags &= ~CKF_RW_SESSION;
}
+ do {
+ do {
+ sessionID = (slot->sessionIDCount++ & MAX_SESSION_ID);
+ } while (sessionID == CK_INVALID_HANDLE);
+ if (slotID == PRIVATE_KEY_SLOT_ID) {
+ sessionID |= PK11_PRIVATE_KEY_FLAG;
+ } else if (slotID == FIPS_SLOT_ID) {
+ sessionID |= PK11_FIPS_FLAG;
+ }
+ pk11queue_find(sameID, sessionID, slot->head, SESSION_HASH_SIZE);
+ if (sameID == NULL) {
+ session->handle = sessionID;
+ pk11_update_state(slot, session);
+ pk11queue_add(session, sessionID, slot->head, SESSION_HASH_SIZE);
+ } else {
+ slot->sessionIDConflict++; /* for debugging */
+ }
+ } while (sameID != NULL);
- session->handle = sessionID;
- pk11_update_state(slot, session);
- pk11queue_add(session, sessionID, slot->head, SESSION_HASH_SIZE);
slot->sessionCount++;
if (session->info.flags & CKF_RW_SESSION) {
slot->rwSessionCount++;
diff --git a/security/nss/lib/softoken/pkcs11i.h b/security/nss/lib/softoken/pkcs11i.h
index 8831fb140..acce33c29 100644
--- a/security/nss/lib/softoken/pkcs11i.h
+++ b/security/nss/lib/softoken/pkcs11i.h
@@ -265,6 +265,7 @@ struct PK11SlotStr {
PRBool needLogin;
PRBool DB_loaded;
int sessionIDCount;
+ int sessionIDConflict;
int sessionCount;
int rwSessionCount;
int tokenIDCount;
@@ -303,6 +304,9 @@ struct PK11SSLMACInfoStr {
#define PK11_PRIVATE_KEY_FLAG 0x80000000L
#define PK11_FIPS_FLAG 0x40000000L
+/* session IDs mask the modifiers above in the high-order bits */
+#define MAX_SESSION_ID 0x3fffffff
+
/*
* object handle modifiers
*/