PORT_Assert( ssl_HaveSSL3HandshakeLock(ss) );
PORT_Assert( ss->opt.noLocks || ssl_HaveSSL3HandshakeLock(ss) );
ssl3_GenerateRSAPMS(sslSocket *ss, ssl3CipherSpec *spec,                    PK11SlotInfo * serverKeySlot){    PK11SymKey *      pms		= NULL;    PK11SlotInfo *    slot		= serverKeySlot;    void *	      pwArg 		= ss->pkcs11PinArg;    SECItem           param;    CK_VERSION 	      version;    CK_MECHANISM_TYPE mechanism_array[3];    PORT_Assert( ssl_HaveSSL3HandshakeLock(ss) );    if (slot == NULL) {	SSLCipherAlgorithm calg;	/* The specReadLock would suffice here, but we cannot assert on	** read locks.  Also, all the callers who call with a non-null	** slot already hold the SpecWriteLock.	*/	PORT_Assert( ssl_HaveSpecWriteLock(ss));	PORT_Assert(ss->ssl3->prSpec == ss->ssl3->pwSpec);        calg = spec->cipher_def->calg;	PORT_Assert(alg2Mech[calg].calg == calg);	/* First get an appropriate slot.  */	mechanism_array[0] = CKM_SSL3_PRE_MASTER_KEY_GEN;	mechanism_array[1] = CKM_RSA_PKCS;	mechanism_array[2] = alg2Mech[calg].cmech;	slot = PK11_GetBestSlotMultiple(mechanism_array, 3, pwArg);	if (slot == NULL) {	   /* can't find a slot with all three, find a slot with the minimum */	    slot = PK11_GetBestSlotMultiple(mechanism_array, 2, pwArg);	    if (slot == NULL) {		PORT_SetError(SSL_ERROR_TOKEN_SLOT_NOT_FOUND);		return pms;	/* which is NULL */	    }	}    }    /* Generate the pre-master secret ...  */    version.major = MSB(ss->clientHelloVersion);    version.minor = LSB(ss->clientHelloVersion);    param.data = (unsigned char *)&version;    param.len  = sizeof version;    pms = PK11_KeyGen(slot, CKM_SSL3_PRE_MASTER_KEY_GEN, &param, 0, pwArg);    if (!serverKeySlot)	PK11_FreeSlot(slot);    if (pms == NULL) {	ssl_MapLowLevelError(SSL_ERROR_CLIENT_KEY_EXCHANGE_FAILURE);    }    return pms;}