&ss->ssl3->hs.client_random.rand[SSL3_RANDOM_LENGTH - rand_length],
&ss->ssl3.hs.client_random.rand[SSL3_RANDOM_LENGTH - rand_length],
ssl3_HandleV2ClientHello(sslSocket *ss, unsigned char *buffer, int length){    sslSessionID *      sid 		= NULL;    unsigned char *     suites;    unsigned char *     random;    SSL3ProtocolVersion version;    SECStatus           rv;    int                 i;    int                 j;    int                 sid_length;    int                 suite_length;    int                 rand_length;    int                 errCode  = SSL_ERROR_RX_MALFORMED_CLIENT_HELLO;    SSL3AlertDescription desc    = handshake_failure;    SSL_TRC(3, ("%d: SSL3[%d]: handle v2 client_hello", SSL_GETPID(), ss->fd));    PORT_Assert( ssl_HaveRecvBufLock(ss) );    ssl_GetSSL3HandshakeLock(ss);    rv = ssl3_InitState(ss);    if (rv != SECSuccess) {	ssl_ReleaseSSL3HandshakeLock(ss);	return rv;		/* ssl3_InitState has set the error code. */    }    if (ss->ssl3->hs.ws != wait_client_hello) {	desc    = unexpected_message;	errCode = SSL_ERROR_RX_UNEXPECTED_CLIENT_HELLO;	goto loser;	/* alert_loser */    }    version      = (buffer[1] << 8) | buffer[2];    suite_length = (buffer[3] << 8) | buffer[4];    sid_length   = (buffer[5] << 8) | buffer[6];    rand_length  = (buffer[7] << 8) | buffer[8];    ss->clientHelloVersion = version;    rv = ssl3_NegotiateVersion(ss, version);    if (rv != SECSuccess) {	/* send back which ever alert client will understand. */    	desc = (version > SSL_LIBRARY_VERSION_3_0) ? protocol_version : handshake_failure;	errCode = SSL_ERROR_NO_CYPHER_OVERLAP;	goto alert_loser;    }    /* if we get a non-zero SID, just ignore it. */    if (length !=        SSL_HL_CLIENT_HELLO_HBYTES + suite_length + sid_length + rand_length) {	SSL_DBG(("%d: SSL3[%d]: bad v2 client hello message, len=%d should=%d",		 SSL_GETPID(), ss->fd, length,		 SSL_HL_CLIENT_HELLO_HBYTES + suite_length + sid_length +		 rand_length));	goto loser;	/* malformed */	/* alert_loser */    }    suites = buffer + SSL_HL_CLIENT_HELLO_HBYTES;    random = suites + suite_length + sid_length;    if (rand_length < SSL_MIN_CHALLENGE_BYTES ||	rand_length > SSL_MAX_CHALLENGE_BYTES) {	goto loser;	/* malformed */	/* alert_loser */    }    PORT_Assert(SSL_MAX_CHALLENGE_BYTES == SSL3_RANDOM_LENGTH);    PORT_Memset(&ss->ssl3->hs.client_random, 0, SSL3_RANDOM_LENGTH);    PORT_Memcpy(	&ss->ssl3->hs.client_random.rand[SSL3_RANDOM_LENGTH - rand_length],	random, rand_length);    PRINT_BUF(60, (ss, "client random:", &ss->ssl3->hs.client_random.rand[0],		   SSL3_RANDOM_LENGTH));    i = ssl3_config_match_init(ss);    if (i <= 0) {    	errCode = PORT_GetError();	/* error code is already set. */	goto alert_loser;    }    /* Select a cipher suite.    ** NOTE: This suite selection algorithm should be the same as the one in    ** ssl3_HandleClientHello().      */    for (j = 0; j < ssl_V3_SUITES_IMPLEMENTED; j++) {	ssl3CipherSuiteCfg *suite = &ss->cipherSuites[j];	if (!config_match(suite, ss->ssl3->policy, PR_TRUE))	    continue;	for (i = 0; i < suite_length; i += 3) {	    if ((suites[i]   == 0) &&		(suites[i+1] == MSB(suite->cipher_suite)) &&		(suites[i+2] == LSB(suite->cipher_suite))) {		ss->ssl3->hs.cipher_suite = suite->cipher_suite;		ss->ssl3->hs.suite_def =		    ssl_LookupCipherSuiteDef(ss->ssl3->hs.cipher_suite);		goto suite_found;	    }	}    }    errCode = SSL_ERROR_NO_CYPHER_OVERLAP;    goto alert_loser;suite_found:    ss->ssl3->hs.compression = compression_null;    ss->sec.send            = ssl3_SendApplicationData;    /* we don't even search for a cache hit here.  It's just a miss. */    ++ssl3stats.hch_sid_cache_misses;    sid = ssl3_NewSessionID(ss, PR_TRUE);    if (sid == NULL) {    	errCode = PORT_GetError();	goto loser;	/* memory error is set. */    }    ss->sec.ci.sid = sid;    /* do not worry about memory leak of sid since it now belongs to ci */    /* We have to update the handshake hashes before we can send stuff */    rv = ssl3_UpdateHandshakeHashes(ss, buffer, length);    if (rv != SECSuccess) {    	errCode = PORT_GetError();	goto loser;    }    ssl_GetXmitBufLock(ss);    rv = ssl3_SendServerHelloSequence(ss);    ssl_ReleaseXmitBufLock(ss);    if (rv != SECSuccess) {    	errCode = PORT_GetError();	goto loser;    }    /* XXX_1 	The call stack to here is:     * ssl_Do1stHandshake -> ssl2_HandleClientHelloMessage -> here.     * ssl2_HandleClientHelloMessage returns whatever we return here.     * ssl_Do1stHandshake will continue looping if it gets back either     *		SECSuccess or SECWouldBlock.     * SECSuccess is preferable here.  See XXX_1 in sslgathr.c.     */    ssl_ReleaseSSL3HandshakeLock(ss);    return SECSuccess;alert_loser:    SSL3_SendAlert(ss, alert_fatal, desc);loser:    ssl_ReleaseSSL3HandshakeLock(ss);    PORT_SetError(errCode);    return SECFailure;}