if ( ss->enableTLS ) {
if ( ss->opt.enableTLS ) {
ssl2_BeginClientHandshake(sslSocket *ss){    sslSessionID      *sid;    PRUint8           *msg;    PRUint8           *cp;    PRUint8           *localCipherSpecs = NULL;    unsigned int      localCipherSize;    unsigned int      i;    int               sendLen, sidLen = 0;    SECStatus         rv;    PORT_Assert( ssl_Have1stHandshakeLock(ss) );    ss->sec.isServer     = 0;    ss->sec.sendSequence = 0;    ss->sec.rcvSequence  = 0;    ssl_ChooseSessionIDProcs(&ss->sec);    if (!ss->cipherSpecs) {	rv = ssl2_ConstructCipherSpecs(ss);	if (rv != SECSuccess)	    goto loser;    }    /* count the SSL2 and SSL3 enabled ciphers.     * if either is zero, clear the socket's enable for that protocol.     */    rv = ssl2_CheckConfigSanity(ss);    if (rv != SECSuccess)	goto loser;    /* Get peer name of server */    rv = ssl_GetPeerInfo(ss);    if (rv < 0) {#ifdef HPUX11        /*         * On some HP-UX B.11.00 systems, getpeername() occasionally         * fails with ENOTCONN after a successful completion of         * non-blocking connect.  I found that if we do a write()         * and then retry getpeername(), it will work.         */        if (PR_GetError() == PR_NOT_CONNECTED_ERROR) {            char dummy;            (void) PR_Write(ss->fd->lower, &dummy, 0);            rv = ssl_GetPeerInfo(ss);            if (rv < 0) {                goto loser;            }        }#else	goto loser;#endif    }    SSL_TRC(3, ("%d: SSL[%d]: sending client-hello", SSL_GETPID(), ss->fd));    /* Try to find server in our session-id cache */    if (ss->noCache) {	sid = NULL;    } else {	sid = ssl_LookupSID(&ss->sec.ci.peer, ss->sec.ci.port, ss->peerID, 	                    ss->url);    }    while (sid) {  /* this isn't really a loop */	/* if we're not doing this SID's protocol any more, drop it. */	if (((sid->version  < SSL_LIBRARY_VERSION_3_0) && !ss->enableSSL2) ||	    ((sid->version == SSL_LIBRARY_VERSION_3_0) && !ss->enableSSL3) ||	    ((sid->version >  SSL_LIBRARY_VERSION_3_0) && !ss->enableTLS)) {	    ss->sec.uncache(sid);	    ssl_FreeSID(sid);	    sid = NULL;	    break;	}	if (ss->enableSSL2 && sid->version < SSL_LIBRARY_VERSION_3_0) {	    /* If the cipher in this sid is not enabled, drop it. */	    for (i = 0; i < ss->sizeCipherSpecs; i += 3) {		if (ss->cipherSpecs[i] == sid->u.ssl2.cipherType)		    break;	    }	    if (i >= ss->sizeCipherSpecs) {		ss->sec.uncache(sid);		ssl_FreeSID(sid);		sid = NULL;		break;	    }	}	sidLen = sizeof(sid->u.ssl2.sessionID);	PRINT_BUF(4, (ss, "client, found session-id:", sid->u.ssl2.sessionID,		      sidLen));	ss->version = sid->version;	PORT_Assert(!ss->sec.localCert);	if (ss->sec.localCert) {	    CERT_DestroyCertificate(ss->sec.localCert);	}	ss->sec.localCert     = CERT_DupCertificate(sid->localCert);	break;  /* this isn't really a loop */    }     if (!sid) {	sidLen = 0;	sid = (sslSessionID*) PORT_ZAlloc(sizeof(sslSessionID));	if (!sid) {	    goto loser;	}	sid->references = 1;	sid->cached     = never_cached;	sid->addr       = ss->sec.ci.peer;	sid->port       = ss->sec.ci.port;	if (ss->peerID != NULL) {	    sid->peerID = PORT_Strdup(ss->peerID);	}	if (ss->url != NULL) {	    sid->urlSvrName = PORT_Strdup(ss->url);	}    }    ss->sec.ci.sid = sid;    PORT_Assert(sid != NULL);    if ((sid->version >= SSL_LIBRARY_VERSION_3_0 || !ss->v2CompatibleHello) &&        (ss->enableSSL3 || ss->enableTLS)) {	ss->gs.state      = GS_INIT;	ss->handshake     = ssl_GatherRecord1stHandshake;	/* ssl3_SendClientHello will override this if it succeeds. */	ss->version       = SSL_LIBRARY_VERSION_3_0;	ssl_GetXmitBufLock(ss);    /***************************************/	ssl_GetSSL3HandshakeLock(ss);	rv =  ssl3_SendClientHello(ss);	ssl_ReleaseSSL3HandshakeLock(ss);	ssl_ReleaseXmitBufLock(ss); /***************************************/	return rv;    }       if (!ss->cipherSpecs) {        rv = ssl2_ConstructCipherSpecs(ss);	if (rv < 0) {	    return rv;    	}    }    localCipherSpecs = ss->cipherSpecs;    localCipherSize  = ss->sizeCipherSpecs;    sendLen = SSL_HL_CLIENT_HELLO_HBYTES + localCipherSize + sidLen +	SSL_CHALLENGE_BYTES;    /* Generate challenge bytes for server */    PK11_GenerateRandom(ss->sec.ci.clientChallenge, SSL_CHALLENGE_BYTES);    ssl_GetXmitBufLock(ss);    /***************************************/    rv = ssl2_GetSendBuffer(ss, sendLen);    if (rv)     	goto unlock_loser;    /* Construct client-hello message */    cp = msg = ss->sec.ci.sendBuf.buf;    msg[0] = SSL_MT_CLIENT_HELLO;    if ( ss->enableTLS ) {	ss->clientHelloVersion = SSL_LIBRARY_VERSION_3_1_TLS;    } else if ( ss->enableSSL3 ) {	ss->clientHelloVersion = SSL_LIBRARY_VERSION_3_0;    } else {	ss->clientHelloVersion = SSL_LIBRARY_VERSION_2;    }        msg[1] = MSB(ss->clientHelloVersion);    msg[2] = LSB(ss->clientHelloVersion);    msg[3] = MSB(localCipherSize);    msg[4] = LSB(localCipherSize);    msg[5] = MSB(sidLen);    msg[6] = LSB(sidLen);    msg[7] = MSB(SSL_CHALLENGE_BYTES);    msg[8] = LSB(SSL_CHALLENGE_BYTES);    cp += SSL_HL_CLIENT_HELLO_HBYTES;    PORT_Memcpy(cp, localCipherSpecs, localCipherSize);    cp += localCipherSize;    if (sidLen) {	PORT_Memcpy(cp, sid->u.ssl2.sessionID, sidLen);	cp += sidLen;    }    PORT_Memcpy(cp, ss->sec.ci.clientChallenge, SSL_CHALLENGE_BYTES);    /* Send it to the server */    DUMP_MSG(29, (ss, msg, sendLen));    ss->handshakeBegun = 1;    rv = (*ss->sec.send)(ss, msg, sendLen, 0);    ssl_ReleaseXmitBufLock(ss);    /***************************************/    if (rv < 0) {	goto loser;    }    rv = ssl3_StartHandshakeHash(ss, msg, sendLen);    if (rv < 0) {	goto loser;    }    /* Setup to receive servers hello message */    ssl_GetRecvBufLock(ss);    ss->gs.recordLen = 0;    ssl_ReleaseRecvBufLock(ss);    ss->handshake     = ssl_GatherRecord1stHandshake;    ss->nextHandshake = ssl2_HandleServerHelloMessage;    return SECSuccess;unlock_loser:    ssl_ReleaseXmitBufLock(ss);loser:    return SECFailure;}