/*
 * vtables (and methods that call through them) for the 4 types of 
 * SSLSockets supported.  Only one type is still supported.
 * Various other functions.
 *
 * This Source Code Form is subject to the terms of the Mozilla Public
 * License, v. 2.0. If a copy of the MPL was not distributed with this
 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
#include "seccomon.h"
#include "cert.h"
#include "keyhi.h"
#include "ssl.h"
#include "sslimpl.h"
#include "sslproto.h"
#include "nspr.h"
#include "private/pprio.h"
#ifndef NO_PKCS11_BYPASS
#include "blapi.h"
#endif
#include "pk11pub.h"
#include "nss.h"

/* This is a bodge to allow this code to be compiled against older NSS headers
 * that don't contain the TLS 1.2 changes. */
#ifndef CKM_NSS_TLS_MASTER_KEY_DERIVE_DH_SHA256
#define CKM_NSS_TLS_MASTER_KEY_DERIVE_DH_SHA256 (CKM_NSS + 24)
#endif

#define SET_ERROR_CODE   /* reminder */

struct cipherPolicyStr {
	int		cipher;
	unsigned char 	export;	/* policy value for export policy */
	unsigned char 	france;	/* policy value for france policy */
};

typedef struct cipherPolicyStr cipherPolicy;

/* This table contains two preconfigured policies: Export and France.
** It is used only by the functions NSS_SetDomesticPolicy, 
** NSS_SetExportPolicy, and NSS_SetFrancePolicy.
** Order of entries is not important.
*/
static cipherPolicy ssl_ciphers[] = {	   /*   Export           France   */
 {  SSL_EN_RC4_128_WITH_MD5,		    SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  SSL_EN_RC4_128_EXPORT40_WITH_MD5,	    SSL_ALLOWED,     SSL_ALLOWED },
 {  SSL_EN_RC2_128_CBC_WITH_MD5,	    SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  SSL_EN_RC2_128_CBC_EXPORT40_WITH_MD5,   SSL_ALLOWED,     SSL_ALLOWED },
 {  SSL_EN_DES_64_CBC_WITH_MD5,		    SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  SSL_EN_DES_192_EDE3_CBC_WITH_MD5,	    SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  SSL_RSA_WITH_RC4_128_MD5,		    SSL_RESTRICTED,  SSL_NOT_ALLOWED },
 {  SSL_RSA_WITH_RC4_128_SHA,		    SSL_RESTRICTED,  SSL_NOT_ALLOWED },
 {  SSL_RSA_FIPS_WITH_3DES_EDE_CBC_SHA,	    SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  SSL_RSA_WITH_3DES_EDE_CBC_SHA,	    SSL_RESTRICTED,  SSL_NOT_ALLOWED },
 {  SSL_RSA_FIPS_WITH_DES_CBC_SHA,	    SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  SSL_RSA_WITH_DES_CBC_SHA,		    SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  SSL_RSA_EXPORT_WITH_RC4_40_MD5,	    SSL_ALLOWED,     SSL_ALLOWED },
 {  SSL_RSA_EXPORT_WITH_RC2_CBC_40_MD5,	    SSL_ALLOWED,     SSL_ALLOWED },
 {  SSL_DHE_RSA_WITH_DES_CBC_SHA,           SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  SSL_DHE_DSS_WITH_DES_CBC_SHA,           SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  SSL_DHE_RSA_WITH_3DES_EDE_CBC_SHA,      SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  SSL_DHE_DSS_WITH_3DES_EDE_CBC_SHA,      SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_DHE_DSS_WITH_RC4_128_SHA,           SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  SSL_RSA_WITH_NULL_MD5,		    SSL_ALLOWED,     SSL_ALLOWED },
 {  SSL_RSA_WITH_NULL_SHA,		    SSL_ALLOWED,     SSL_ALLOWED },
 {  TLS_RSA_WITH_NULL_SHA256,		    SSL_ALLOWED,     SSL_ALLOWED },
 {  TLS_DHE_DSS_WITH_AES_128_CBC_SHA, 	    SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_DHE_RSA_WITH_AES_128_CBC_SHA,       SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_DHE_RSA_WITH_AES_128_CBC_SHA256,    SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_RSA_WITH_AES_128_CBC_SHA,     	    SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_RSA_WITH_AES_128_CBC_SHA256,        SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_DHE_DSS_WITH_AES_256_CBC_SHA, 	    SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_DHE_RSA_WITH_AES_256_CBC_SHA,       SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_DHE_RSA_WITH_AES_256_CBC_SHA256,    SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_RSA_WITH_AES_256_CBC_SHA,     	    SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_RSA_WITH_AES_256_CBC_SHA256,        SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_DHE_DSS_WITH_CAMELLIA_128_CBC_SHA,  SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_DHE_RSA_WITH_CAMELLIA_128_CBC_SHA,  SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_RSA_WITH_CAMELLIA_128_CBC_SHA, 	    SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_DHE_DSS_WITH_CAMELLIA_256_CBC_SHA,  SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_DHE_RSA_WITH_CAMELLIA_256_CBC_SHA,  SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_RSA_WITH_CAMELLIA_256_CBC_SHA, 	    SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_RSA_WITH_SEED_CBC_SHA,		    SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_RSA_EXPORT1024_WITH_DES_CBC_SHA,    SSL_ALLOWED,     SSL_NOT_ALLOWED },
 {  TLS_RSA_EXPORT1024_WITH_RC4_56_SHA,     SSL_ALLOWED,     SSL_NOT_ALLOWED },
#ifdef NSS_ENABLE_ECC
 {  TLS_ECDH_ECDSA_WITH_NULL_SHA,           SSL_ALLOWED,     SSL_ALLOWED },
 {  TLS_ECDH_ECDSA_WITH_RC4_128_SHA,        SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA,   SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA,    SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA,    SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_ECDHE_ECDSA_WITH_NULL_SHA,          SSL_ALLOWED,     SSL_ALLOWED },
 {  TLS_ECDHE_ECDSA_WITH_RC4_128_SHA,       SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA,  SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA,   SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256,SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA,   SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_ECDH_RSA_WITH_NULL_SHA,             SSL_ALLOWED,     SSL_ALLOWED },
 {  TLS_ECDH_RSA_WITH_RC4_128_SHA,          SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA,     SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_ECDH_RSA_WITH_AES_128_CBC_SHA,      SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_ECDH_RSA_WITH_AES_256_CBC_SHA,      SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_ECDHE_RSA_WITH_NULL_SHA,            SSL_ALLOWED,     SSL_ALLOWED },
 {  TLS_ECDHE_RSA_WITH_RC4_128_SHA,         SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA,    SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA,     SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256,  SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
 {  TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA,     SSL_NOT_ALLOWED, SSL_NOT_ALLOWED },
#endif /* NSS_ENABLE_ECC */
 {  0,					    SSL_NOT_ALLOWED, SSL_NOT_ALLOWED }
};

static const sslSocketOps ssl_default_ops = {	/* No SSL. */
    ssl_DefConnect,
    NULL,
    ssl_DefBind,
    ssl_DefListen,
    ssl_DefShutdown,
    ssl_DefClose,
    ssl_DefRecv,
    ssl_DefSend,
    ssl_DefRead,
    ssl_DefWrite,
    ssl_DefGetpeername,
    ssl_DefGetsockname
};

static const sslSocketOps ssl_secure_ops = {	/* SSL. */
    ssl_SecureConnect,
    NULL,
    ssl_DefBind,
    ssl_DefListen,
    ssl_SecureShutdown,
    ssl_SecureClose,
    ssl_SecureRecv,
    ssl_SecureSend,
    ssl_SecureRead,
    ssl_SecureWrite,
    ssl_DefGetpeername,
    ssl_DefGetsockname
};

/*
** default settings for socket enables
*/
static sslOptions ssl_defaults = {
    { siBuffer, NULL, 0 }, /* nextProtoNego */
    PR_TRUE, 	/* useSecurity        */
    PR_FALSE,	/* useSocks           */
    PR_FALSE,	/* requestCertificate */
    2,	        /* requireCertificate */
    PR_FALSE,	/* handshakeAsClient  */
    PR_FALSE,	/* handshakeAsServer  */
    PR_FALSE,	/* enableSSL2         */ /* now defaults to off in NSS 3.13 */
    PR_FALSE,	/* unusedBit9         */
    PR_FALSE, 	/* unusedBit10        */
    PR_FALSE,	/* noCache            */
    PR_FALSE,	/* fdx                */
    PR_FALSE,	/* v2CompatibleHello  */ /* now defaults to off in NSS 3.13 */
    PR_TRUE,	/* detectRollBack     */
    PR_FALSE,   /* noStepDown         */
    PR_FALSE,   /* bypassPKCS11       */
    PR_FALSE,   /* noLocks            */
    PR_FALSE,   /* enableSessionTickets */
    PR_FALSE,   /* enableDeflate      */
    2,          /* enableRenegotiation (default: requires extension) */
    PR_FALSE,   /* requireSafeNegotiation */
    PR_FALSE,   /* enableFalseStart   */
    PR_TRUE,    /* cbcRandomIV        */
    PR_FALSE    /* enableOCSPStapling */
};

/*
 * default range of enabled SSL/TLS protocols
 */
static SSLVersionRange versions_defaults_stream = {
    SSL_LIBRARY_VERSION_3_0,
    SSL_LIBRARY_VERSION_TLS_1_0
};

static SSLVersionRange versions_defaults_datagram = {
    SSL_LIBRARY_VERSION_TLS_1_1,
    SSL_LIBRARY_VERSION_TLS_1_1
};

#define VERSIONS_DEFAULTS(variant) \
    (variant == ssl_variant_stream ? &versions_defaults_stream : \
                                     &versions_defaults_datagram)

sslSessionIDLookupFunc  ssl_sid_lookup;
sslSessionIDCacheFunc   ssl_sid_cache;
sslSessionIDUncacheFunc ssl_sid_uncache;

static PRBool ssl_inited = PR_FALSE;
static PRDescIdentity ssl_layer_id;

PRBool                  locksEverDisabled; 	/* implicitly PR_FALSE */
PRBool			ssl_force_locks;  	/* implicitly PR_FALSE */
int                     ssl_lock_readers	= 1;	/* default true. */
char                    ssl_debug;
char                    ssl_trace;
FILE *                  ssl_trace_iob;
FILE *                  ssl_keylog_iob;
char lockStatus[] = "Locks are ENABLED.  ";
#define LOCKSTATUS_OFFSET 10 /* offset of ENABLED */

/* SRTP_NULL_HMAC_SHA1_80 and SRTP_NULL_HMAC_SHA1_32 are not implemented. */
static const PRUint16 srtpCiphers[] = {
    SRTP_AES128_CM_HMAC_SHA1_80,
    SRTP_AES128_CM_HMAC_SHA1_32,
    0
};

/* forward declarations. */
static sslSocket *ssl_NewSocket(PRBool makeLocks, SSLProtocolVariant variant);
static SECStatus  ssl_MakeLocks(sslSocket *ss);
static void       ssl_SetDefaultsFromEnvironment(void);
static PRStatus   ssl_PushIOLayer(sslSocket *ns, PRFileDesc *stack, 
                                  PRDescIdentity id);

/************************************************************************/

/*
** Lookup a socket structure from a file descriptor.
** Only functions called through the PRIOMethods table should use this.
** Other app-callable functions should use ssl_FindSocket.
*/
static sslSocket *
ssl_GetPrivate(PRFileDesc *fd)
{
    sslSocket *ss;

    PORT_Assert(fd != NULL);
    PORT_Assert(fd->methods->file_type == PR_DESC_LAYERED);
    PORT_Assert(fd->identity == ssl_layer_id);

    if (fd->methods->file_type != PR_DESC_LAYERED ||
        fd->identity != ssl_layer_id) {
	PORT_SetError(PR_BAD_DESCRIPTOR_ERROR);
	return NULL;
    }

    ss = (sslSocket *)fd->secret;
    ss->fd = fd;
    return ss;
}

/* This function tries to find the SSL layer in the stack. 
 * It searches for the first SSL layer at or below the argument fd,
 * and failing that, it searches for the nearest SSL layer above the 
 * argument fd.  It returns the private sslSocket from the found layer.
 */
sslSocket *
ssl_FindSocket(PRFileDesc *fd)
{
    PRFileDesc *layer;
    sslSocket *ss;

    PORT_Assert(fd != NULL);
    PORT_Assert(ssl_layer_id != 0);

    layer = PR_GetIdentitiesLayer(fd, ssl_layer_id);
    if (layer == NULL) {
	PORT_SetError(PR_BAD_DESCRIPTOR_ERROR);
	return NULL;
    }

    ss = (sslSocket *)layer->secret;
    ss->fd = layer;
    return ss;
}

static sslSocket *
ssl_DupSocket(sslSocket *os)
{
    sslSocket *ss;
    SECStatus rv;

    ss = ssl_NewSocket((PRBool)(!os->opt.noLocks), os->protocolVariant);
    if (ss) {
	ss->opt                = os->opt;
	ss->opt.useSocks       = PR_FALSE;
	ss->vrange             = os->vrange;

	ss->peerID             = !os->peerID ? NULL : PORT_Strdup(os->peerID);
	ss->url                = !os->url    ? NULL : PORT_Strdup(os->url);

	ss->ops      = os->ops;
	ss->rTimeout = os->rTimeout;
	ss->wTimeout = os->wTimeout;
	ss->cTimeout = os->cTimeout;
	ss->dbHandle = os->dbHandle;

	/* copy ssl2&3 policy & prefs, even if it's not selected (yet) */
	ss->allowedByPolicy	= os->allowedByPolicy;
	ss->maybeAllowedByPolicy= os->maybeAllowedByPolicy;
	ss->chosenPreference 	= os->chosenPreference;
	PORT_Memcpy(ss->cipherSuites, os->cipherSuites, sizeof os->cipherSuites);
	PORT_Memcpy(ss->ssl3.dtlsSRTPCiphers, os->ssl3.dtlsSRTPCiphers,
		    sizeof(PRUint16) * os->ssl3.dtlsSRTPCipherCount);
	ss->ssl3.dtlsSRTPCipherCount = os->ssl3.dtlsSRTPCipherCount;

	if (os->cipherSpecs) {
	    ss->cipherSpecs  = (unsigned char*)PORT_Alloc(os->sizeCipherSpecs);
	    if (ss->cipherSpecs) 
	    	PORT_Memcpy(ss->cipherSpecs, os->cipherSpecs, 
		            os->sizeCipherSpecs);
	    ss->sizeCipherSpecs    = os->sizeCipherSpecs;
	    ss->preferredCipher    = os->preferredCipher;
	} else {
	    ss->cipherSpecs        = NULL;  /* produced lazily */
	    ss->sizeCipherSpecs    = 0;
	    ss->preferredCipher    = NULL;
	}
	if (ss->opt.useSecurity) {
	    /* This int should be SSLKEAType, but CC on Irix complains,
	     * during the for loop.
	     */
	    int i;
	    sslServerCerts * oc = os->serverCerts;
	    sslServerCerts * sc = ss->serverCerts;
            
	    for (i=kt_null; i < kt_kea_size; i++, oc++, sc++) {
		if (oc->serverCert && oc->serverCertChain) {
		    sc->serverCert      = CERT_DupCertificate(oc->serverCert);
		    sc->serverCertChain = CERT_DupCertList(oc->serverCertChain);
		    if (!sc->serverCertChain) 
		    	goto loser;
		} else {
		    sc->serverCert      = NULL;
		    sc->serverCertChain = NULL;
		}
		sc->serverKeyPair = oc->serverKeyPair ?
				ssl3_GetKeyPairRef(oc->serverKeyPair) : NULL;
		if (oc->serverKeyPair && !sc->serverKeyPair)
		    goto loser;
	        sc->serverKeyBits = oc->serverKeyBits;
		ss->certStatusArray[i] = !os->certStatusArray[i] ? NULL :
				SECITEM_DupArray(NULL, os->certStatusArray[i]);
	    }
	    ss->stepDownKeyPair = !os->stepDownKeyPair ? NULL :
		                  ssl3_GetKeyPairRef(os->stepDownKeyPair);
	    ss->ephemeralECDHKeyPair = !os->ephemeralECDHKeyPair ? NULL :
		                  ssl3_GetKeyPairRef(os->ephemeralECDHKeyPair);
/*
 * XXX the preceding CERT_ and SECKEY_ functions can fail and return NULL.
 * XXX We should detect this, and not just march on with NULL pointers.
 */
	    ss->authCertificate       = os->authCertificate;
	    ss->authCertificateArg    = os->authCertificateArg;
	    ss->getClientAuthData     = os->getClientAuthData;
	    ss->getClientAuthDataArg  = os->getClientAuthDataArg;
#ifdef NSS_PLATFORM_CLIENT_AUTH
	    ss->getPlatformClientAuthData    = os->getPlatformClientAuthData;
	    ss->getPlatformClientAuthDataArg = os->getPlatformClientAuthDataArg;
#endif
            ss->sniSocketConfig       = os->sniSocketConfig;
            ss->sniSocketConfigArg    = os->sniSocketConfigArg;
	    ss->handleBadCert         = os->handleBadCert;
	    ss->badCertArg            = os->badCertArg;
	    ss->handshakeCallback     = os->handshakeCallback;
	    ss->handshakeCallbackData = os->handshakeCallbackData;
	    ss->pkcs11PinArg          = os->pkcs11PinArg;
	    ss->getChannelID          = os->getChannelID;
	    ss->getChannelIDArg       = os->getChannelIDArg;
    
	    /* Create security data */
	    rv = ssl_CopySecurityInfo(ss, os);
	    if (rv != SECSuccess) {
		goto loser;
	    }
	}
    }
    return ss;

loser:
    ssl_FreeSocket(ss);
    return NULL;
}

static void
ssl_DestroyLocks(sslSocket *ss)
{
    /* Destroy locks. */
    if (ss->firstHandshakeLock) {
    	PZ_DestroyMonitor(ss->firstHandshakeLock);
	ss->firstHandshakeLock = NULL;
    }
    if (ss->ssl3HandshakeLock) {
    	PZ_DestroyMonitor(ss->ssl3HandshakeLock);
	ss->ssl3HandshakeLock = NULL;
    }
    if (ss->specLock) {
    	NSSRWLock_Destroy(ss->specLock);
	ss->specLock = NULL;
    }

    if (ss->recvLock) {
    	PZ_DestroyLock(ss->recvLock);
	ss->recvLock = NULL;
    }
    if (ss->sendLock) {
    	PZ_DestroyLock(ss->sendLock);
	ss->sendLock = NULL;
    }
    if (ss->xmitBufLock) {
    	PZ_DestroyMonitor(ss->xmitBufLock);
	ss->xmitBufLock = NULL;
    }
    if (ss->recvBufLock) {
    	PZ_DestroyMonitor(ss->recvBufLock);
	ss->recvBufLock = NULL;
    }
}

/* Caller holds any relevant locks */
static void
ssl_DestroySocketContents(sslSocket *ss)
{
    /* "i" should be of type SSLKEAType, but CC on IRIX complains during
     * the for loop.
     */
    int        i;

    /* Free up socket */
    ssl_DestroySecurityInfo(&ss->sec);

    ssl3_DestroySSL3Info(ss);

    PORT_Free(ss->saveBuf.buf);
    PORT_Free(ss->pendingBuf.buf);
    ssl_DestroyGather(&ss->gs);

    if (ss->peerID != NULL)
	PORT_Free(ss->peerID);
    if (ss->url != NULL)
	PORT_Free((void *)ss->url);	/* CONST */
    if (ss->cipherSpecs) {
	PORT_Free(ss->cipherSpecs);
	ss->cipherSpecs     = NULL;
	ss->sizeCipherSpecs = 0;
    }

    /* Clean up server configuration */
    for (i=kt_null; i < kt_kea_size; i++) {
	sslServerCerts * sc = ss->serverCerts + i;
	if (sc->serverCert != NULL)
	    CERT_DestroyCertificate(sc->serverCert);
	if (sc->serverCertChain != NULL)
	    CERT_DestroyCertificateList(sc->serverCertChain);
	if (sc->serverKeyPair != NULL)
	    ssl3_FreeKeyPair(sc->serverKeyPair);
	if (ss->certStatusArray[i] != NULL) {
	    SECITEM_FreeArray(ss->certStatusArray[i], PR_TRUE);
	    ss->certStatusArray[i] = NULL;
	}
    }
    if (ss->stepDownKeyPair) {
	ssl3_FreeKeyPair(ss->stepDownKeyPair);
	ss->stepDownKeyPair = NULL;
    }
    if (ss->ephemeralECDHKeyPair) {
	ssl3_FreeKeyPair(ss->ephemeralECDHKeyPair);
	ss->ephemeralECDHKeyPair = NULL;
    }
    SECITEM_FreeItem(&ss->opt.nextProtoNego, PR_FALSE);
    PORT_Assert(!ss->xtnData.sniNameArr);
    if (ss->xtnData.sniNameArr) {
        PORT_Free(ss->xtnData.sniNameArr);
        ss->xtnData.sniNameArr = NULL;
    }
}

/*
 * free an sslSocket struct, and all the stuff that hangs off of it
 */
void
ssl_FreeSocket(sslSocket *ss)
{
/* Get every lock you can imagine!
** Caller already holds these:
**  SSL_LOCK_READER(ss);
**  SSL_LOCK_WRITER(ss);
*/
    ssl_Get1stHandshakeLock(ss);
    ssl_GetRecvBufLock(ss);
    ssl_GetSSL3HandshakeLock(ss);
    ssl_GetXmitBufLock(ss);
    ssl_GetSpecWriteLock(ss);

    ssl_DestroySocketContents(ss);

    /* Release all the locks acquired above.  */
    SSL_UNLOCK_READER(ss);
    SSL_UNLOCK_WRITER(ss);
    ssl_Release1stHandshakeLock(ss);
    ssl_ReleaseRecvBufLock(ss);
    ssl_ReleaseSSL3HandshakeLock(ss);
    ssl_ReleaseXmitBufLock(ss);
    ssl_ReleaseSpecWriteLock(ss);

    ssl_DestroyLocks(ss);

#ifdef DEBUG
    PORT_Memset(ss, 0x1f, sizeof *ss);
#endif
    PORT_Free(ss);
    return;
}

/************************************************************************/
SECStatus 
ssl_EnableNagleDelay(sslSocket *ss, PRBool enabled)
{
    PRFileDesc *       osfd = ss->fd->lower;
    SECStatus         rv = SECFailure;
    PRSocketOptionData opt;

    opt.option         = PR_SockOpt_NoDelay;
    opt.value.no_delay = (PRBool)!enabled;

    if (osfd->methods->setsocketoption) {
        rv = (SECStatus) osfd->methods->setsocketoption(osfd, &opt);
    } else {
        PR_SetError(PR_NOT_IMPLEMENTED_ERROR, 0);
    }

    return rv;
}

static void
ssl_ChooseOps(sslSocket *ss)
{
    ss->ops = ss->opt.useSecurity ? &ssl_secure_ops : &ssl_default_ops;
}

/* Called from SSL_Enable (immediately below) */
static SECStatus
PrepareSocket(sslSocket *ss)
{
    SECStatus     rv = SECSuccess;

    ssl_ChooseOps(ss);
    return rv;
}

SECStatus
SSL_Enable(PRFileDesc *fd, int which, PRBool on)
{
    return SSL_OptionSet(fd, which, on);
}

#ifndef NO_PKCS11_BYPASS
static const PRCallOnceType pristineCallOnce;
static PRCallOnceType setupBypassOnce;

static SECStatus SSL_BypassShutdown(void* appData, void* nssData)
{
    /* unload freeBL shared library from memory */
    BL_Unload();
    setupBypassOnce = pristineCallOnce;
    return SECSuccess;
}

static PRStatus SSL_BypassRegisterShutdown(void)
{
    SECStatus rv = NSS_RegisterShutdown(SSL_BypassShutdown, NULL);
    PORT_Assert(SECSuccess == rv);
    return SECSuccess == rv ? PR_SUCCESS : PR_FAILURE;
}
#endif

static PRStatus SSL_BypassSetup(void)
{
#ifdef NO_PKCS11_BYPASS
    /* Guarantee binary compatibility */
    return PR_SUCCESS;
#else
    return PR_CallOnce(&setupBypassOnce, &SSL_BypassRegisterShutdown);
#endif
}

/* Implements the semantics for SSL_OptionSet(SSL_ENABLE_TLS, on) described in
 * ssl.h in the section "SSL version range setting API".
 */
static void
ssl_EnableTLS(SSLVersionRange *vrange, PRBool on)
{
    if (SSL3_ALL_VERSIONS_DISABLED(vrange)) {
	if (on) {
	    vrange->min = SSL_LIBRARY_VERSION_TLS_1_0;
	    vrange->max = SSL_LIBRARY_VERSION_TLS_1_0;
	} /* else don't change anything */
	return;
    }

    if (on) {
	/* Expand the range of enabled version to include TLS 1.0 */
	vrange->min = PR_MIN(vrange->min, SSL_LIBRARY_VERSION_TLS_1_0);
	vrange->max = PR_MAX(vrange->max, SSL_LIBRARY_VERSION_TLS_1_0);
    } else {
	/* Disable all TLS versions, leaving only SSL 3.0 if it was enabled */
	if (vrange->min == SSL_LIBRARY_VERSION_3_0) {
	    vrange->max = SSL_LIBRARY_VERSION_3_0;
	} else {
	    /* Only TLS was enabled, so now no versions are. */
	    vrange->min = SSL_LIBRARY_VERSION_NONE;
	    vrange->max = SSL_LIBRARY_VERSION_NONE;
	}
    }
}

/* Implements the semantics for SSL_OptionSet(SSL_ENABLE_SSL3, on) described in
 * ssl.h in the section "SSL version range setting API".
 */
static void
ssl_EnableSSL3(SSLVersionRange *vrange, PRBool on)
{
   if (SSL3_ALL_VERSIONS_DISABLED(vrange)) {
	if (on) {
	    vrange->min = SSL_LIBRARY_VERSION_3_0;
	    vrange->max = SSL_LIBRARY_VERSION_3_0;
	} /* else don't change anything */
	return;
    }

   if (on) {
	/* Expand the range of enabled versions to include SSL 3.0. We know
	 * SSL 3.0 or some version of TLS is already enabled at this point, so
	 * we don't need to change vrange->max.
	 */
	vrange->min = SSL_LIBRARY_VERSION_3_0;
   } else {
	/* Disable SSL 3.0, leaving TLS unaffected. */
	if (vrange->max > SSL_LIBRARY_VERSION_3_0) {
	    vrange->min = PR_MAX(vrange->min, SSL_LIBRARY_VERSION_TLS_1_0);
	} else {
	    /* Only SSL 3.0 was enabled, so now no versions are. */
	    vrange->min = SSL_LIBRARY_VERSION_NONE;
	    vrange->max = SSL_LIBRARY_VERSION_NONE;
	}
    }
}

SECStatus
SSL_OptionSet(PRFileDesc *fd, PRInt32 which, PRBool on)
{
    sslSocket *ss = ssl_FindSocket(fd);
    SECStatus  rv = SECSuccess;
    PRBool     holdingLocks;

    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in Enable", SSL_GETPID(), fd));
	return SECFailure;
    }

    holdingLocks = (!ss->opt.noLocks);
    ssl_Get1stHandshakeLock(ss);
    ssl_GetSSL3HandshakeLock(ss);

    switch (which) {
      case SSL_SOCKS:
	ss->opt.useSocks = PR_FALSE;
	rv = PrepareSocket(ss);
	if (on) {
	    PORT_SetError(SEC_ERROR_INVALID_ARGS);
	    rv = SECFailure;
	}
	break;

      case SSL_SECURITY:
	ss->opt.useSecurity = on;
	rv = PrepareSocket(ss);
	break;

      case SSL_REQUEST_CERTIFICATE:
	ss->opt.requestCertificate = on;
	break;

      case SSL_REQUIRE_CERTIFICATE:
	ss->opt.requireCertificate = on;
	break;

      case SSL_HANDSHAKE_AS_CLIENT:
	if ( ss->opt.handshakeAsServer && on ) {
	    PORT_SetError(SEC_ERROR_INVALID_ARGS);
	    rv = SECFailure;
	    break;
	}
	ss->opt.handshakeAsClient = on;
	break;

      case SSL_HANDSHAKE_AS_SERVER:
	if ( ss->opt.handshakeAsClient && on ) {
	    PORT_SetError(SEC_ERROR_INVALID_ARGS);
	    rv = SECFailure;
	    break;
	}
	ss->opt.handshakeAsServer = on;
	break;

      case SSL_ENABLE_TLS:
        if (IS_DTLS(ss)) {
	    if (on) {
		PORT_SetError(SEC_ERROR_INVALID_ARGS);
		rv = SECFailure; /* not allowed */
	    }
	    break;
	}
	ssl_EnableTLS(&ss->vrange, on);
	ss->preferredCipher     = NULL;
	if (ss->cipherSpecs) {
	    PORT_Free(ss->cipherSpecs);
	    ss->cipherSpecs     = NULL;
	    ss->sizeCipherSpecs = 0;
	}
	break;

      case SSL_ENABLE_SSL3:
        if (IS_DTLS(ss)) {
	    if (on) {
		PORT_SetError(SEC_ERROR_INVALID_ARGS);
		rv = SECFailure; /* not allowed */
	    }
	    break;
	}
	ssl_EnableSSL3(&ss->vrange, on);
	ss->preferredCipher     = NULL;
	if (ss->cipherSpecs) {
	    PORT_Free(ss->cipherSpecs);
	    ss->cipherSpecs     = NULL;
	    ss->sizeCipherSpecs = 0;
	}
	break;

      case SSL_ENABLE_SSL2:
        if (IS_DTLS(ss)) {
	    if (on) {
		PORT_SetError(SEC_ERROR_INVALID_ARGS);
		rv = SECFailure; /* not allowed */
	    }
	    break;
	}
	ss->opt.enableSSL2       = on;
	if (on) {
	    ss->opt.v2CompatibleHello = on;
	}
	ss->preferredCipher     = NULL;
	if (ss->cipherSpecs) {
	    PORT_Free(ss->cipherSpecs);
	    ss->cipherSpecs     = NULL;
	    ss->sizeCipherSpecs = 0;
	}
	break;

      case SSL_NO_CACHE:
	ss->opt.noCache = on;
	break;

      case SSL_ENABLE_FDX:
	if (on && ss->opt.noLocks) {
	    PORT_SetError(SEC_ERROR_INVALID_ARGS);
	    rv = SECFailure;
	}
      	ss->opt.fdx = on;
	break;

      case SSL_V2_COMPATIBLE_HELLO:
        if (IS_DTLS(ss)) {
	    if (on) {
		PORT_SetError(SEC_ERROR_INVALID_ARGS);
		rv = SECFailure; /* not allowed */
	    }
	    break;
	}
      	ss->opt.v2CompatibleHello = on;
	if (!on) {
	    ss->opt.enableSSL2    = on;
	}
	break;

      case SSL_ROLLBACK_DETECTION:  
	ss->opt.detectRollBack = on;
        break;

      case SSL_NO_STEP_DOWN:        
	ss->opt.noStepDown     = on;         
	if (on) 
	    SSL_DisableExportCipherSuites(fd);
	break;

      case SSL_BYPASS_PKCS11:
	if (ss->handshakeBegun) {
	    PORT_SetError(PR_INVALID_STATE_ERROR);
	    rv = SECFailure;
	} else {
            if (PR_FALSE != on) {
                if (PR_SUCCESS == SSL_BypassSetup() ) {
#ifdef NO_PKCS11_BYPASS
                    ss->opt.bypassPKCS11 = PR_FALSE;
#else
                    ss->opt.bypassPKCS11 = on;
#endif
                } else {
                    rv = SECFailure;
                }
            } else {
                ss->opt.bypassPKCS11 = PR_FALSE;
            }
	}
	break;

      case SSL_NO_LOCKS:
	if (on && ss->opt.fdx) {
	    PORT_SetError(SEC_ERROR_INVALID_ARGS);
	    rv = SECFailure;
	}
	if (on && ssl_force_locks) 
	    on = PR_FALSE;	/* silent override */
	ss->opt.noLocks   = on;
	if (on) {
	    locksEverDisabled = PR_TRUE;
	    strcpy(lockStatus + LOCKSTATUS_OFFSET, "DISABLED.");
	} else if (!holdingLocks) {
	    rv = ssl_MakeLocks(ss);
	    if (rv != SECSuccess) {
		ss->opt.noLocks   = PR_TRUE;
	    }
	}
	break;

      case SSL_ENABLE_SESSION_TICKETS:
	ss->opt.enableSessionTickets = on;
	break;

      case SSL_ENABLE_DEFLATE:
	ss->opt.enableDeflate = on;
	break;

      case SSL_ENABLE_RENEGOTIATION:
	ss->opt.enableRenegotiation = on;
	break;

      case SSL_REQUIRE_SAFE_NEGOTIATION:
	ss->opt.requireSafeNegotiation = on;
	break;

      case SSL_ENABLE_FALSE_START:
	ss->opt.enableFalseStart = on;
	break;

      case SSL_CBC_RANDOM_IV:
	ss->opt.cbcRandomIV = on;
	break;

      case SSL_ENABLE_OCSP_STAPLING:
       ss->opt.enableOCSPStapling = on;
       break;

      default:
	PORT_SetError(SEC_ERROR_INVALID_ARGS);
	rv = SECFailure;
    }

    /* We can't use the macros for releasing the locks here,
     * because ss->opt.noLocks might have changed just above.
     * We must release these locks (monitors) here, if we aquired them above,
     * regardless of the current value of ss->opt.noLocks.
     */
    if (holdingLocks) {
	PZ_ExitMonitor((ss)->ssl3HandshakeLock);
	PZ_ExitMonitor((ss)->firstHandshakeLock);
    }

    return rv;
}

SECStatus
SSL_OptionGet(PRFileDesc *fd, PRInt32 which, PRBool *pOn)
{
    sslSocket *ss = ssl_FindSocket(fd);
    SECStatus  rv = SECSuccess;
    PRBool     on = PR_FALSE;

    if (!pOn) {
	PORT_SetError(SEC_ERROR_INVALID_ARGS);
	return SECFailure;
    }
    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in Enable", SSL_GETPID(), fd));
	*pOn = PR_FALSE;
	return SECFailure;
    }

    ssl_Get1stHandshakeLock(ss);
    ssl_GetSSL3HandshakeLock(ss);

    switch (which) {
    case SSL_SOCKS:               on = PR_FALSE;               break;
    case SSL_SECURITY:            on = ss->opt.useSecurity;        break;
    case SSL_REQUEST_CERTIFICATE: on = ss->opt.requestCertificate; break;
    case SSL_REQUIRE_CERTIFICATE: on = ss->opt.requireCertificate; break;
    case SSL_HANDSHAKE_AS_CLIENT: on = ss->opt.handshakeAsClient;  break;
    case SSL_HANDSHAKE_AS_SERVER: on = ss->opt.handshakeAsServer;  break;
    case SSL_ENABLE_TLS:
	on = ss->vrange.max >= SSL_LIBRARY_VERSION_TLS_1_0;
	break;
    case SSL_ENABLE_SSL3:
	on = ss->vrange.min == SSL_LIBRARY_VERSION_3_0;
	break;
    case SSL_ENABLE_SSL2:         on = ss->opt.enableSSL2;         break;
    case SSL_NO_CACHE:            on = ss->opt.noCache;            break;
    case SSL_ENABLE_FDX:          on = ss->opt.fdx;                break;
    case SSL_V2_COMPATIBLE_HELLO: on = ss->opt.v2CompatibleHello;  break;
    case SSL_ROLLBACK_DETECTION:  on = ss->opt.detectRollBack;     break;
    case SSL_NO_STEP_DOWN:        on = ss->opt.noStepDown;         break;
    case SSL_BYPASS_PKCS11:       on = ss->opt.bypassPKCS11;       break;
    case SSL_NO_LOCKS:            on = ss->opt.noLocks;            break;
    case SSL_ENABLE_SESSION_TICKETS:
	on = ss->opt.enableSessionTickets;
	break;
    case SSL_ENABLE_DEFLATE:      on = ss->opt.enableDeflate;      break;
    case SSL_ENABLE_RENEGOTIATION:     
                                  on = ss->opt.enableRenegotiation; break;
    case SSL_REQUIRE_SAFE_NEGOTIATION: 
                                  on = ss->opt.requireSafeNegotiation; break;
    case SSL_ENABLE_FALSE_START:  on = ss->opt.enableFalseStart;   break;
    case SSL_CBC_RANDOM_IV:       on = ss->opt.cbcRandomIV;        break;
    case SSL_ENABLE_OCSP_STAPLING: on = ss->opt.enableOCSPStapling; break;

    default:
	PORT_SetError(SEC_ERROR_INVALID_ARGS);
	rv = SECFailure;
    }

    ssl_ReleaseSSL3HandshakeLock(ss);
    ssl_Release1stHandshakeLock(ss);

    *pOn = on;
    return rv;
}

SECStatus
SSL_OptionGetDefault(PRInt32 which, PRBool *pOn)
{
    SECStatus  rv = SECSuccess;
    PRBool     on = PR_FALSE;

    if (!pOn) {
	PORT_SetError(SEC_ERROR_INVALID_ARGS);
	return SECFailure;
    }

    ssl_SetDefaultsFromEnvironment();

    switch (which) {
    case SSL_SOCKS:               on = PR_FALSE;                        break;
    case SSL_SECURITY:            on = ssl_defaults.useSecurity;        break;
    case SSL_REQUEST_CERTIFICATE: on = ssl_defaults.requestCertificate; break;
    case SSL_REQUIRE_CERTIFICATE: on = ssl_defaults.requireCertificate; break;
    case SSL_HANDSHAKE_AS_CLIENT: on = ssl_defaults.handshakeAsClient;  break;
    case SSL_HANDSHAKE_AS_SERVER: on = ssl_defaults.handshakeAsServer;  break;
    case SSL_ENABLE_TLS:
	on = versions_defaults_stream.max >= SSL_LIBRARY_VERSION_TLS_1_0;
	break;
    case SSL_ENABLE_SSL3:
	on = versions_defaults_stream.min == SSL_LIBRARY_VERSION_3_0;
	break;
    case SSL_ENABLE_SSL2:         on = ssl_defaults.enableSSL2;         break;
    case SSL_NO_CACHE:            on = ssl_defaults.noCache;		break;
    case SSL_ENABLE_FDX:          on = ssl_defaults.fdx;                break;
    case SSL_V2_COMPATIBLE_HELLO: on = ssl_defaults.v2CompatibleHello;  break;
    case SSL_ROLLBACK_DETECTION:  on = ssl_defaults.detectRollBack;     break;
    case SSL_NO_STEP_DOWN:        on = ssl_defaults.noStepDown;         break;
    case SSL_BYPASS_PKCS11:       on = ssl_defaults.bypassPKCS11;       break;
    case SSL_NO_LOCKS:            on = ssl_defaults.noLocks;            break;
    case SSL_ENABLE_SESSION_TICKETS:
	on = ssl_defaults.enableSessionTickets;
	break;
    case SSL_ENABLE_DEFLATE:      on = ssl_defaults.enableDeflate;      break;
    case SSL_ENABLE_RENEGOTIATION:     
                                  on = ssl_defaults.enableRenegotiation; break;
    case SSL_REQUIRE_SAFE_NEGOTIATION: 
                                  on = ssl_defaults.requireSafeNegotiation; 
				  break;
    case SSL_ENABLE_FALSE_START:  on = ssl_defaults.enableFalseStart;   break;
    case SSL_CBC_RANDOM_IV:       on = ssl_defaults.cbcRandomIV;        break;
    case SSL_ENABLE_OCSP_STAPLING:
       on = ssl_defaults.enableOCSPStapling;
       break;

    default:
	PORT_SetError(SEC_ERROR_INVALID_ARGS);
	rv = SECFailure;
    }

    *pOn = on;
    return rv;
}

/* XXX Use Global Lock to protect this stuff. */
SECStatus
SSL_EnableDefault(int which, PRBool on)
{
    return SSL_OptionSetDefault(which, on);
}

SECStatus
SSL_OptionSetDefault(PRInt32 which, PRBool on)
{
    SECStatus status = ssl_Init();

    if (status != SECSuccess) {
	return status;
    }

    ssl_SetDefaultsFromEnvironment();

    switch (which) {
      case SSL_SOCKS:
	ssl_defaults.useSocks = PR_FALSE;
	if (on) {
	    PORT_SetError(SEC_ERROR_INVALID_ARGS);
	    return SECFailure;
	}
	break;

      case SSL_SECURITY:
	ssl_defaults.useSecurity = on;
	break;

      case SSL_REQUEST_CERTIFICATE:
	ssl_defaults.requestCertificate = on;
	break;

      case SSL_REQUIRE_CERTIFICATE:
	ssl_defaults.requireCertificate = on;
	break;

      case SSL_HANDSHAKE_AS_CLIENT:
	if ( ssl_defaults.handshakeAsServer && on ) {
	    PORT_SetError(SEC_ERROR_INVALID_ARGS);
	    return SECFailure;
	}
	ssl_defaults.handshakeAsClient = on;
	break;

      case SSL_HANDSHAKE_AS_SERVER:
	if ( ssl_defaults.handshakeAsClient && on ) {
	    PORT_SetError(SEC_ERROR_INVALID_ARGS);
	    return SECFailure;
	}
	ssl_defaults.handshakeAsServer = on;
	break;

      case SSL_ENABLE_TLS:
	ssl_EnableTLS(&versions_defaults_stream, on);
	break;

      case SSL_ENABLE_SSL3:
	ssl_EnableSSL3(&versions_defaults_stream, on);
	break;

      case SSL_ENABLE_SSL2:
	ssl_defaults.enableSSL2 = on;
	if (on) {
	    ssl_defaults.v2CompatibleHello = on;
	}
	break;

      case SSL_NO_CACHE:
	ssl_defaults.noCache = on;
	break;

      case SSL_ENABLE_FDX:
	if (on && ssl_defaults.noLocks) {
	    PORT_SetError(SEC_ERROR_INVALID_ARGS);
	    return SECFailure;
	}
      	ssl_defaults.fdx = on;
	break;

      case SSL_V2_COMPATIBLE_HELLO:
      	ssl_defaults.v2CompatibleHello = on;
	if (!on) {
	    ssl_defaults.enableSSL2    = on;
	}
	break;

      case SSL_ROLLBACK_DETECTION:  
	ssl_defaults.detectRollBack = on;
	break;

      case SSL_NO_STEP_DOWN:        
	ssl_defaults.noStepDown     = on;         
	if (on)
	    SSL_DisableDefaultExportCipherSuites();
	break;

      case SSL_BYPASS_PKCS11:
        if (PR_FALSE != on) {
            if (PR_SUCCESS == SSL_BypassSetup()) {
#ifdef NO_PKCS11_BYPASS
                ssl_defaults.bypassPKCS11   = PR_FALSE;
#else
                ssl_defaults.bypassPKCS11   = on;
#endif
            } else {
                return SECFailure;
            }
        } else {
            ssl_defaults.bypassPKCS11   = PR_FALSE;
        }
	break;

      case SSL_NO_LOCKS:
	if (on && ssl_defaults.fdx) {
	    PORT_SetError(SEC_ERROR_INVALID_ARGS);
	    return SECFailure;
	}
	if (on && ssl_force_locks) 
	    on = PR_FALSE;		/* silent override */
	ssl_defaults.noLocks        = on;
	if (on) {
	    locksEverDisabled = PR_TRUE;
	    strcpy(lockStatus + LOCKSTATUS_OFFSET, "DISABLED.");
	}
	break;

      case SSL_ENABLE_SESSION_TICKETS:
	ssl_defaults.enableSessionTickets = on;
	break;

      case SSL_ENABLE_DEFLATE:
	ssl_defaults.enableDeflate = on;
	break;

      case SSL_ENABLE_RENEGOTIATION:
	ssl_defaults.enableRenegotiation = on;
	break;

      case SSL_REQUIRE_SAFE_NEGOTIATION:
	ssl_defaults.requireSafeNegotiation = on;
	break;

      case SSL_ENABLE_FALSE_START:
	ssl_defaults.enableFalseStart = on;
	break;

      case SSL_CBC_RANDOM_IV:
	ssl_defaults.cbcRandomIV = on;
	break;

      case SSL_ENABLE_OCSP_STAPLING:
       ssl_defaults.enableOCSPStapling = on;
       break;

      default:
	PORT_SetError(SEC_ERROR_INVALID_ARGS);
	return SECFailure;
    }
    return SECSuccess;
}

/* function tells us if the cipher suite is one that we no longer support. */
static PRBool 
ssl_IsRemovedCipherSuite(PRInt32 suite)
{
    switch (suite) {
    case SSL_FORTEZZA_DMS_WITH_NULL_SHA:
    case SSL_FORTEZZA_DMS_WITH_FORTEZZA_CBC_SHA:
    case SSL_FORTEZZA_DMS_WITH_RC4_128_SHA:
    	return PR_TRUE;
    default:
    	return PR_FALSE;
    }
}

/* Part of the public NSS API.
 * Since this is a global (not per-socket) setting, we cannot use the
 * HandshakeLock to protect this.  Probably want a global lock.
 */
SECStatus
SSL_SetPolicy(long which, int policy)
{
    if ((which & 0xfffe) == SSL_RSA_OLDFIPS_WITH_3DES_EDE_CBC_SHA) {
    	/* one of the two old FIPS ciphers */
	if (which == SSL_RSA_OLDFIPS_WITH_3DES_EDE_CBC_SHA) 
	    which = SSL_RSA_FIPS_WITH_3DES_EDE_CBC_SHA;
	else if (which == SSL_RSA_OLDFIPS_WITH_DES_CBC_SHA)
	    which = SSL_RSA_FIPS_WITH_DES_CBC_SHA;
    }
    if (ssl_IsRemovedCipherSuite(which))
    	return SECSuccess;
    return SSL_CipherPolicySet(which, policy);
}

SECStatus
SSL_CipherPolicySet(PRInt32 which, PRInt32 policy)
{
    SECStatus rv = ssl_Init();

    if (rv != SECSuccess) {
	return rv;
    }

    if (ssl_IsRemovedCipherSuite(which)) {
    	rv = SECSuccess;
    } else if (SSL_IS_SSL2_CIPHER(which)) {
	rv = ssl2_SetPolicy(which, policy);
    } else {
	rv = ssl3_SetPolicy((ssl3CipherSuite)which, policy);
    }
    return rv;
}

SECStatus
SSL_CipherPolicyGet(PRInt32 which, PRInt32 *oPolicy)
{
    SECStatus rv;

    if (!oPolicy) {
	PORT_SetError(SEC_ERROR_INVALID_ARGS);
	return SECFailure;
    }
    if (ssl_IsRemovedCipherSuite(which)) {
	*oPolicy = SSL_NOT_ALLOWED;
    	rv = SECSuccess;
    } else if (SSL_IS_SSL2_CIPHER(which)) {
	rv = ssl2_GetPolicy(which, oPolicy);
    } else {
	rv = ssl3_GetPolicy((ssl3CipherSuite)which, oPolicy);
    }
    return rv;
}

/* Part of the public NSS API.
 * Since this is a global (not per-socket) setting, we cannot use the
 * HandshakeLock to protect this.  Probably want a global lock.
 * These changes have no effect on any sslSockets already created. 
 */
SECStatus
SSL_EnableCipher(long which, PRBool enabled)
{
    if ((which & 0xfffe) == SSL_RSA_OLDFIPS_WITH_3DES_EDE_CBC_SHA) {
    	/* one of the two old FIPS ciphers */
	if (which == SSL_RSA_OLDFIPS_WITH_3DES_EDE_CBC_SHA) 
	    which = SSL_RSA_FIPS_WITH_3DES_EDE_CBC_SHA;
	else if (which == SSL_RSA_OLDFIPS_WITH_DES_CBC_SHA)
	    which = SSL_RSA_FIPS_WITH_DES_CBC_SHA;
    }
    if (ssl_IsRemovedCipherSuite(which))
    	return SECSuccess;
    return SSL_CipherPrefSetDefault(which, enabled);
}

SECStatus
SSL_CipherPrefSetDefault(PRInt32 which, PRBool enabled)
{
    SECStatus rv = ssl_Init();

    if (rv != SECSuccess) {
	return rv;
    }

    if (ssl_IsRemovedCipherSuite(which))
    	return SECSuccess;
    if (enabled && ssl_defaults.noStepDown && SSL_IsExportCipherSuite(which)) {
    	PORT_SetError(SEC_ERROR_INVALID_ALGORITHM);
	return SECFailure;
    }
    if (SSL_IS_SSL2_CIPHER(which)) {
	rv = ssl2_CipherPrefSetDefault(which, enabled);
    } else {
	rv = ssl3_CipherPrefSetDefault((ssl3CipherSuite)which, enabled);
    }
    return rv;
}

SECStatus 
SSL_CipherPrefGetDefault(PRInt32 which, PRBool *enabled)
{
    SECStatus  rv;
    
    if (!enabled) {
	PORT_SetError(SEC_ERROR_INVALID_ARGS);
	return SECFailure;
    }
    if (ssl_IsRemovedCipherSuite(which)) {
	*enabled = PR_FALSE;
    	rv = SECSuccess;
    } else if (SSL_IS_SSL2_CIPHER(which)) {
	rv = ssl2_CipherPrefGetDefault(which, enabled);
    } else {
	rv = ssl3_CipherPrefGetDefault((ssl3CipherSuite)which, enabled);
    }
    return rv;
}

SECStatus
SSL_CipherPrefSet(PRFileDesc *fd, PRInt32 which, PRBool enabled)
{
    SECStatus rv;
    sslSocket *ss = ssl_FindSocket(fd);
    
    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in CipherPrefSet", SSL_GETPID(), fd));
	return SECFailure;
    }
    if (ssl_IsRemovedCipherSuite(which))
    	return SECSuccess;
    if (enabled && ss->opt.noStepDown && SSL_IsExportCipherSuite(which)) {
    	PORT_SetError(SEC_ERROR_INVALID_ALGORITHM);
	return SECFailure;
    }
    if (SSL_IS_SSL2_CIPHER(which)) {
	rv = ssl2_CipherPrefSet(ss, which, enabled);
    } else {
	rv = ssl3_CipherPrefSet(ss, (ssl3CipherSuite)which, enabled);
    }
    return rv;
}

SECStatus 
SSL_CipherPrefGet(PRFileDesc *fd, PRInt32 which, PRBool *enabled)
{
    SECStatus  rv;
    sslSocket *ss = ssl_FindSocket(fd);
    
    if (!enabled) {
	PORT_SetError(SEC_ERROR_INVALID_ARGS);
	return SECFailure;
    }
    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in CipherPrefGet", SSL_GETPID(), fd));
	*enabled = PR_FALSE;
	return SECFailure;
    }
    if (ssl_IsRemovedCipherSuite(which)) {
	*enabled = PR_FALSE;
    	rv = SECSuccess;
    } else if (SSL_IS_SSL2_CIPHER(which)) {
	rv = ssl2_CipherPrefGet(ss, which, enabled);
    } else {
	rv = ssl3_CipherPrefGet(ss, (ssl3CipherSuite)which, enabled);
    }
    return rv;
}

SECStatus
NSS_SetDomesticPolicy(void)
{
    SECStatus      status = SECSuccess;
    cipherPolicy * policy;

    for (policy = ssl_ciphers; policy->cipher != 0; ++policy) {
	status = SSL_SetPolicy(policy->cipher, SSL_ALLOWED);
	if (status != SECSuccess)
	    break;
    }
    return status;
}

SECStatus
NSS_SetExportPolicy(void)
{
    return NSS_SetDomesticPolicy();
}

SECStatus
NSS_SetFrancePolicy(void)
{
    return NSS_SetDomesticPolicy();
}

SECStatus
SSL_GetChannelBinding(PRFileDesc *fd,
		      SSLChannelBindingType binding_type,
		      unsigned char *out,
		      unsigned int *outLen,
		      unsigned int outLenMax) {
    sslSocket *ss = ssl_FindSocket(fd);

    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in SSL_GetChannelBinding",
		 SSL_GETPID(), fd));
	return SECFailure;
    }

    if (binding_type != SSL_CHANNEL_BINDING_TLS_UNIQUE) {
	PORT_SetError(PR_INVALID_ARGUMENT_ERROR);
	return SECFailure;
    }

    return ssl3_GetTLSUniqueChannelBinding(ss, out, outLen, outLenMax);
}


/* LOCKS ??? XXX */
static PRFileDesc *
ssl_ImportFD(PRFileDesc *model, PRFileDesc *fd, SSLProtocolVariant variant)
{
    sslSocket * ns = NULL;
    PRStatus    rv;
    PRNetAddr   addr;
    SECStatus	status = ssl_Init();

    if (status != SECSuccess) {
	return NULL;
    }

    if (model == NULL) {
	/* Just create a default socket if we're given NULL for the model */
	ns = ssl_NewSocket((PRBool)(!ssl_defaults.noLocks), variant);
    } else {
	sslSocket * ss = ssl_FindSocket(model);
	if (ss == NULL || ss->protocolVariant != variant) {
	    SSL_DBG(("%d: SSL[%d]: bad model socket in ssl_ImportFD", 
	    	      SSL_GETPID(), model));
	    return NULL;
	}
	ns = ssl_DupSocket(ss);
    }
    if (ns == NULL)
    	return NULL;

    rv = ssl_PushIOLayer(ns, fd, PR_TOP_IO_LAYER);
    if (rv != PR_SUCCESS) {
	ssl_FreeSocket(ns);
	SET_ERROR_CODE
	return NULL;
    }
    ns = ssl_FindSocket(fd);
    PORT_Assert(ns);
    if (ns)
	ns->TCPconnected = (PR_SUCCESS == ssl_DefGetpeername(ns, &addr));
    return fd;
}

PRFileDesc *
SSL_ImportFD(PRFileDesc *model, PRFileDesc *fd)
{
    return ssl_ImportFD(model, fd, ssl_variant_stream);
}

PRFileDesc *
DTLS_ImportFD(PRFileDesc *model, PRFileDesc *fd)
{
    return ssl_ImportFD(model, fd, ssl_variant_datagram);
}

SECStatus
SSL_SetNextProtoCallback(PRFileDesc *fd, SSLNextProtoCallback callback,
			 void *arg)
{
    sslSocket *ss = ssl_FindSocket(fd);

    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in SSL_SetNextProtoCallback", SSL_GETPID(),
		 fd));
	return SECFailure;
    }

    ssl_GetSSL3HandshakeLock(ss);
    ss->nextProtoCallback = callback;
    ss->nextProtoArg = arg;
    ssl_ReleaseSSL3HandshakeLock(ss);

    return SECSuccess;
}

/* ssl_NextProtoNegoCallback is set as an NPN callback for the case when
 * SSL_SetNextProtoNego is used.
 */
static SECStatus
ssl_NextProtoNegoCallback(void *arg, PRFileDesc *fd,
			  const unsigned char *protos, unsigned int protos_len,
			  unsigned char *protoOut, unsigned int *protoOutLen,
			  unsigned int protoMaxLen)
{
    unsigned int i, j;
    const unsigned char *result;
    sslSocket *ss = ssl_FindSocket(fd);

    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in ssl_NextProtoNegoCallback",
		 SSL_GETPID(), fd));
	return SECFailure;
    }

    if (protos_len == 0) {
	/* The server supports the extension, but doesn't have any protocols
	 * configured. In this case we request our favoured protocol. */
	goto pick_first;
    }

    /* For each protocol in server preference, see if we support it. */
    for (i = 0; i < protos_len; ) {
	for (j = 0; j < ss->opt.nextProtoNego.len; ) {
	    if (protos[i] == ss->opt.nextProtoNego.data[j] &&
		PORT_Memcmp(&protos[i+1], &ss->opt.nextProtoNego.data[j+1],
			     protos[i]) == 0) {
		/* We found a match. */
		ss->ssl3.nextProtoState = SSL_NEXT_PROTO_NEGOTIATED;
		result = &protos[i];
		goto found;
	    }
	    j += 1 + (unsigned int)ss->opt.nextProtoNego.data[j];
	}
	i += 1 + (unsigned int)protos[i];
    }

pick_first:
    ss->ssl3.nextProtoState = SSL_NEXT_PROTO_NO_OVERLAP;
    result = ss->opt.nextProtoNego.data;

found:
    if (protoMaxLen < result[0]) {
	PORT_SetError(SEC_ERROR_OUTPUT_LEN);
	return SECFailure;
    }
    memcpy(protoOut, result + 1, result[0]);
    *protoOutLen = result[0];
    return SECSuccess;
}

SECStatus
SSL_SetNextProtoNego(PRFileDesc *fd, const unsigned char *data,
		     unsigned int length)
{
    sslSocket *ss;
    SECStatus rv;
    SECItem dataItem = { siBuffer, (unsigned char *) data, length };

    ss = ssl_FindSocket(fd);
    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in SSL_SetNextProtoNego",
		 SSL_GETPID(), fd));
	return SECFailure;
    }

    if (ssl3_ValidateNextProtoNego(data, length) != SECSuccess)
	return SECFailure;

    ssl_GetSSL3HandshakeLock(ss);
    SECITEM_FreeItem(&ss->opt.nextProtoNego, PR_FALSE);
    rv = SECITEM_CopyItem(NULL, &ss->opt.nextProtoNego, &dataItem);
    ssl_ReleaseSSL3HandshakeLock(ss);

    if (rv != SECSuccess)
	return rv;

    return SSL_SetNextProtoCallback(fd, ssl_NextProtoNegoCallback, NULL);
}

SECStatus
SSL_GetNextProto(PRFileDesc *fd, SSLNextProtoState *state, unsigned char *buf,
		 unsigned int *bufLen, unsigned int bufLenMax)
{
    sslSocket *ss = ssl_FindSocket(fd);

    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in SSL_GetNextProto", SSL_GETPID(),
		 fd));
	return SECFailure;
    }

    if (!state || !buf || !bufLen) {
	PORT_SetError(SEC_ERROR_INVALID_ARGS);
	return SECFailure;
    }

    *state = ss->ssl3.nextProtoState;

    if (ss->ssl3.nextProtoState != SSL_NEXT_PROTO_NO_SUPPORT &&
	ss->ssl3.nextProto.data) {
	if (ss->ssl3.nextProto.len > bufLenMax) {
	    PORT_SetError(SEC_ERROR_OUTPUT_LEN);
	    return SECFailure;
	}
	PORT_Memcpy(buf, ss->ssl3.nextProto.data, ss->ssl3.nextProto.len);
	*bufLen = ss->ssl3.nextProto.len;
    } else {
	*bufLen = 0;
    }

    return SECSuccess;
}

SECStatus SSL_SetSRTPCiphers(PRFileDesc *fd,
			     const PRUint16 *ciphers,
			     unsigned int numCiphers)
{
    sslSocket *ss;
    unsigned int i;

    ss = ssl_FindSocket(fd);
    if (!ss || !IS_DTLS(ss)) {
	SSL_DBG(("%d: SSL[%d]: bad socket in SSL_SetSRTPCiphers",
		 SSL_GETPID(), fd));
	PORT_SetError(SEC_ERROR_INVALID_ARGS);
	return SECFailure;
    }

    if (numCiphers > MAX_DTLS_SRTP_CIPHER_SUITES) {
	PORT_SetError(SEC_ERROR_INVALID_ARGS);
	return SECFailure;
    }

    ss->ssl3.dtlsSRTPCipherCount = 0;
    for (i = 0; i < numCiphers; i++) {
	const PRUint16 *srtpCipher = srtpCiphers;

	while (*srtpCipher) {
	    if (ciphers[i] == *srtpCipher)
		break;
	    srtpCipher++;
	}
	if (*srtpCipher) {
	    ss->ssl3.dtlsSRTPCiphers[ss->ssl3.dtlsSRTPCipherCount++] =
		ciphers[i];
	} else {
	    SSL_DBG(("%d: SSL[%d]: invalid or unimplemented SRTP cipher "
		    "suite specified: 0x%04hx", SSL_GETPID(), fd,
		    ciphers[i]));
	}
    }

    if (ss->ssl3.dtlsSRTPCipherCount == 0) {
	PORT_SetError(SEC_ERROR_INVALID_ARGS);
	return SECFailure;
    }

    return SECSuccess;
}

SECStatus
SSL_GetSRTPCipher(PRFileDesc *fd, PRUint16 *cipher)
{
    sslSocket * ss;

    ss = ssl_FindSocket(fd);
    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in SSL_GetSRTPCipher",
		 SSL_GETPID(), fd));
	PORT_SetError(SEC_ERROR_INVALID_ARGS);
	return SECFailure;
    }

    if (!ss->ssl3.dtlsSRTPCipherSuite) {
	PORT_SetError(SEC_ERROR_INVALID_ARGS);
	return SECFailure;
    }

    *cipher = ss->ssl3.dtlsSRTPCipherSuite;
    return SECSuccess;
}

PRFileDesc *
SSL_ReconfigFD(PRFileDesc *model, PRFileDesc *fd)
{
    PORT_SetError(PR_NOT_IMPLEMENTED_ERROR);
    PR_NOT_REACHED("not implemented");
    return NULL;

#if 0
    sslSocket * sm = NULL, *ss = NULL;
    int i;
    sslServerCerts * mc = NULL;
    sslServerCerts * sc = NULL;

    if (model == NULL) {
        PR_SetError(SEC_ERROR_INVALID_ARGS, 0);
        return NULL;
    }
    sm = ssl_FindSocket(model);
    if (sm == NULL) {
        SSL_DBG(("%d: SSL[%d]: bad model socket in ssl_ReconfigFD", 
                 SSL_GETPID(), model));
        return NULL;
    }
    ss = ssl_FindSocket(fd);
    PORT_Assert(ss);
    if (ss == NULL) {
        PORT_SetError(SEC_ERROR_INVALID_ARGS);
        return NULL;
    }
    
    ss->opt  = sm->opt;
    ss->vrange = sm->vrange;
    PORT_Memcpy(ss->cipherSuites, sm->cipherSuites, sizeof sm->cipherSuites);
    PORT_Memcpy(ss->ssl3.dtlsSRTPCiphers, sm->ssl3.dtlsSRTPCiphers,
                sizeof(PRUint16) * sm->ssl3.dtlsSRTPCipherCount);
    ss->ssl3.dtlsSRTPCipherCount = sm->ssl3.dtlsSRTPCipherCount;

    if (!ss->opt.useSecurity) {
        PORT_SetError(SEC_ERROR_INVALID_ARGS);
        return NULL;
    }
    /* This int should be SSLKEAType, but CC on Irix complains,
     * during the for loop.
     */
    for (i=kt_null; i < kt_kea_size; i++) {
        mc = &(sm->serverCerts[i]);
        sc = &(ss->serverCerts[i]);
        if (mc->serverCert && mc->serverCertChain) {
            if (sc->serverCert) {
                CERT_DestroyCertificate(sc->serverCert);
            }
            sc->serverCert      = CERT_DupCertificate(mc->serverCert);
            if (sc->serverCertChain) {
                CERT_DestroyCertificateList(sc->serverCertChain);
            }
            sc->serverCertChain = CERT_DupCertList(mc->serverCertChain);
            if (!sc->serverCertChain)
                goto loser;
	    if (sm->certStatusArray[i]) {
		if (ss->certStatusArray[i]) {
		    SECITEM_FreeArray(ss->certStatusArray[i], PR_TRUE);
		    ss->certStatusArray[i] = NULL;
		}
		ss->certStatusArray[i] = SECITEM_DupArray(NULL, sm->certStatusArray[i]);
		if (!ss->certStatusArray[i])
		    goto loser;
	    }
        }
        if (mc->serverKeyPair) {
            if (sc->serverKeyPair) {
                ssl3_FreeKeyPair(sc->serverKeyPair);
            }
            sc->serverKeyPair = ssl3_GetKeyPairRef(mc->serverKeyPair);
            sc->serverKeyBits = mc->serverKeyBits;
        }
    }
    if (sm->stepDownKeyPair) {
        if (ss->stepDownKeyPair) {
            ssl3_FreeKeyPair(ss->stepDownKeyPair);
        }
        ss->stepDownKeyPair = ssl3_GetKeyPairRef(sm->stepDownKeyPair);
    }
    if (sm->ephemeralECDHKeyPair) {
        if (ss->ephemeralECDHKeyPair) {
            ssl3_FreeKeyPair(ss->ephemeralECDHKeyPair);
        }
        ss->ephemeralECDHKeyPair =
            ssl3_GetKeyPairRef(sm->ephemeralECDHKeyPair);
    }
    /* copy trust anchor names */
    if (sm->ssl3.ca_list) {
        if (ss->ssl3.ca_list) {
            CERT_FreeDistNames(ss->ssl3.ca_list);
        }
        ss->ssl3.ca_list = CERT_DupDistNames(sm->ssl3.ca_list);
        if (!ss->ssl3.ca_list) {
            goto loser;
        }
    }
    
    if (sm->authCertificate)
        ss->authCertificate       = sm->authCertificate;
    if (sm->authCertificateArg)
        ss->authCertificateArg    = sm->authCertificateArg;
    if (sm->getClientAuthData)
        ss->getClientAuthData     = sm->getClientAuthData;
    if (sm->getClientAuthDataArg)
        ss->getClientAuthDataArg  = sm->getClientAuthDataArg;
#ifdef NSS_PLATFORM_CLIENT_AUTH
    if (sm->getPlatformClientAuthData)
        ss->getPlatformClientAuthData    = sm->getPlatformClientAuthData;
    if (sm->getPlatformClientAuthDataArg)
        ss->getPlatformClientAuthDataArg = sm->getPlatformClientAuthDataArg;
#endif
    if (sm->sniSocketConfig)
        ss->sniSocketConfig       = sm->sniSocketConfig;
    if (sm->sniSocketConfigArg)
        ss->sniSocketConfigArg    = sm->sniSocketConfigArg;
    if (sm->handleBadCert)
        ss->handleBadCert         = sm->handleBadCert;
    if (sm->badCertArg)
        ss->badCertArg            = sm->badCertArg;
    if (sm->handshakeCallback)
        ss->handshakeCallback     = sm->handshakeCallback;
    if (sm->handshakeCallbackData)
        ss->handshakeCallbackData = sm->handshakeCallbackData;
    if (sm->pkcs11PinArg)
        ss->pkcs11PinArg          = sm->pkcs11PinArg;
    if (sm->getChannelID)
        ss->getChannelID          = sm->getChannelID;
    if (sm->getChannelIDArg)
        ss->getChannelIDArg       = sm->getChannelIDArg;
    return fd;
loser:
    return NULL;
#endif
}

PRBool
ssl3_VersionIsSupported(SSLProtocolVariant protocolVariant,
			SSL3ProtocolVersion version)
{
    switch (protocolVariant) {
    case ssl_variant_stream:
	return (version >= SSL_LIBRARY_VERSION_3_0 &&
		version <= SSL_LIBRARY_VERSION_MAX_SUPPORTED);
    case ssl_variant_datagram:
	return (version >= SSL_LIBRARY_VERSION_TLS_1_1 &&
		version <= SSL_LIBRARY_VERSION_MAX_SUPPORTED);
    default:
	/* Can't get here */
	PORT_Assert(PR_FALSE);
	return PR_FALSE;
    }
}

/* Returns PR_TRUE if the given version range is valid and
** fully supported; otherwise, returns PR_FALSE.
*/
static PRBool
ssl3_VersionRangeIsValid(SSLProtocolVariant protocolVariant,
			 const SSLVersionRange *vrange)
{
    return vrange &&
	   vrange->min <= vrange->max &&
	   ssl3_VersionIsSupported(protocolVariant, vrange->min) &&
	   ssl3_VersionIsSupported(protocolVariant, vrange->max);
}

SECStatus
SSL_VersionRangeGetSupported(SSLProtocolVariant protocolVariant,
			     SSLVersionRange *vrange)
{
    if (!vrange) {
	PORT_SetError(SEC_ERROR_INVALID_ARGS);
	return SECFailure;
    }

    switch (protocolVariant) {
    case ssl_variant_stream:
	vrange->min = SSL_LIBRARY_VERSION_3_0;
	vrange->max = SSL_LIBRARY_VERSION_MAX_SUPPORTED;
	break;
    case ssl_variant_datagram:
	vrange->min = SSL_LIBRARY_VERSION_TLS_1_1;
	vrange->max = SSL_LIBRARY_VERSION_MAX_SUPPORTED;
	break;
    default:
	PORT_SetError(SEC_ERROR_INVALID_ARGS);
	return SECFailure;
    }

    return SECSuccess;
}

SECStatus
SSL_VersionRangeGetDefault(SSLProtocolVariant protocolVariant,
			   SSLVersionRange *vrange)
{
    if ((protocolVariant != ssl_variant_stream &&
	 protocolVariant != ssl_variant_datagram) || !vrange) {
	PORT_SetError(SEC_ERROR_INVALID_ARGS);
	return SECFailure;
    }

    *vrange = *VERSIONS_DEFAULTS(protocolVariant);

    return SECSuccess;
}

SECStatus
SSL_VersionRangeSetDefault(SSLProtocolVariant protocolVariant,
			   const SSLVersionRange *vrange)
{
    if (!ssl3_VersionRangeIsValid(protocolVariant, vrange)) {
	PORT_SetError(SSL_ERROR_INVALID_VERSION_RANGE);
	return SECFailure;
    }

    *VERSIONS_DEFAULTS(protocolVariant) = *vrange;

    return SECSuccess;
}

SECStatus
SSL_VersionRangeGet(PRFileDesc *fd, SSLVersionRange *vrange)
{
    sslSocket *ss = ssl_FindSocket(fd);

    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in SSL3_VersionRangeGet",
		SSL_GETPID(), fd));
	return SECFailure;
    }

    if (!vrange) {
	PORT_SetError(SEC_ERROR_INVALID_ARGS);
	return SECFailure;
    }

    ssl_Get1stHandshakeLock(ss);
    ssl_GetSSL3HandshakeLock(ss);

    *vrange = ss->vrange;

    ssl_ReleaseSSL3HandshakeLock(ss);
    ssl_Release1stHandshakeLock(ss);

    return SECSuccess;
}

static PRCallOnceType checkTLS12TokenOnce;
static PRBool tls12TokenExists;

static PRStatus  
ssl_CheckTLS12Token(void)
{
    tls12TokenExists =
	PK11_TokenExists(CKM_NSS_TLS_MASTER_KEY_DERIVE_DH_SHA256);
    return PR_SUCCESS;
}

static PRBool
ssl_TLS12TokenExists(void)
{
    (void) PR_CallOnce(&checkTLS12TokenOnce, ssl_CheckTLS12Token);
    return tls12TokenExists;
}

SECStatus
SSL_VersionRangeSet(PRFileDesc *fd, const SSLVersionRange *vrange)
{
    sslSocket *ss = ssl_FindSocket(fd);

    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in SSL3_VersionRangeSet",
		SSL_GETPID(), fd));
	return SECFailure;
    }

    if (!ssl3_VersionRangeIsValid(ss->protocolVariant, vrange)) {
	PORT_SetError(SSL_ERROR_INVALID_VERSION_RANGE);
	return SECFailure;
    }

    ssl_Get1stHandshakeLock(ss);
    ssl_GetSSL3HandshakeLock(ss);

    ss->vrange = *vrange;
    /* If we don't have a sufficiently up-to-date softoken then we cannot do
     * TLS 1.2. */
    if (ss->vrange.max >= SSL_LIBRARY_VERSION_TLS_1_2 &&
        !ssl_TLS12TokenExists()) {
	/* If the user requested a minimum version of 1.2, then we don't
	 * silently downgrade. */
	if (ss->vrange.min >= SSL_LIBRARY_VERSION_TLS_1_2) {
	    ssl_ReleaseSSL3HandshakeLock(ss);
	    ssl_Release1stHandshakeLock(ss);
	    PORT_SetError(SSL_ERROR_INVALID_VERSION_RANGE);
	    return SECFailure;
	}
	ss->vrange.max = SSL_LIBRARY_VERSION_TLS_1_1;
    }

    ssl_ReleaseSSL3HandshakeLock(ss);
    ssl_Release1stHandshakeLock(ss);

    return SECSuccess;
}

const SECItemArray *
SSL_PeerStapledOCSPResponses(PRFileDesc *fd)
{
    sslSocket *ss = ssl_FindSocket(fd);

    if (!ss) {
       SSL_DBG(("%d: SSL[%d]: bad socket in SSL_PeerStapledOCSPResponses",
                SSL_GETPID(), fd));
       return NULL;
    }

    if (!ss->sec.ci.sid) {
       PORT_SetError(SEC_ERROR_NOT_INITIALIZED);
       return NULL;
    }
    
    return &ss->sec.ci.sid->peerCertStatus;
}

SECStatus
SSL_HandshakeResumedSession(PRFileDesc *fd, PRBool *handshake_resumed) {
    sslSocket *ss = ssl_FindSocket(fd);

    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in SSL_HandshakeResumedSession",
		 SSL_GETPID(), fd));
	return SECFailure;
    }

    *handshake_resumed = ss->ssl3.hs.isResuming;
    return SECSuccess;
}

const SECItem *
SSL_GetRequestedClientCertificateTypes(PRFileDesc *fd)
{
  sslSocket *ss = ssl_FindSocket(fd);

  if (!ss) {
      SSL_DBG(("%d: SSL[%d]: bad socket in "
               "SSL_GetRequestedClientCertificateTypes", SSL_GETPID(), fd));
      return NULL;
  }

  return ss->requestedCertTypes;
}

/************************************************************************/
/* The following functions are the TOP LEVEL SSL functions.
** They all get called through the NSPRIOMethods table below.
*/

static PRFileDesc * PR_CALLBACK
ssl_Accept(PRFileDesc *fd, PRNetAddr *sockaddr, PRIntervalTime timeout)
{
    sslSocket  *ss;
    sslSocket  *ns 	= NULL;
    PRFileDesc *newfd 	= NULL;
    PRFileDesc *osfd;
    PRStatus    status;

    ss = ssl_GetPrivate(fd);
    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in accept", SSL_GETPID(), fd));
	return NULL;
    }

    /* IF this is a listen socket, there shouldn't be any I/O going on */
    SSL_LOCK_READER(ss);
    SSL_LOCK_WRITER(ss);
    ssl_Get1stHandshakeLock(ss);
    ssl_GetSSL3HandshakeLock(ss);

    ss->cTimeout = timeout;

    osfd = ss->fd->lower;

    /* First accept connection */
    newfd = osfd->methods->accept(osfd, sockaddr, timeout);
    if (newfd == NULL) {
	SSL_DBG(("%d: SSL[%d]: accept failed, errno=%d",
		 SSL_GETPID(), ss->fd, PORT_GetError()));
    } else {
	/* Create ssl module */
	ns = ssl_DupSocket(ss);
    }

    ssl_ReleaseSSL3HandshakeLock(ss);
    ssl_Release1stHandshakeLock(ss);
    SSL_UNLOCK_WRITER(ss);
    SSL_UNLOCK_READER(ss);			/* ss isn't used below here. */

    if (ns == NULL)
	goto loser;

    /* push ssl module onto the new socket */
    status = ssl_PushIOLayer(ns, newfd, PR_TOP_IO_LAYER);
    if (status != PR_SUCCESS)
	goto loser;

    /* Now start server connection handshake with client.
    ** Don't need locks here because nobody else has a reference to ns yet.
    */
    if ( ns->opt.useSecurity ) {
	if ( ns->opt.handshakeAsClient ) {
	    ns->handshake = ssl2_BeginClientHandshake;
	    ss->handshaking = sslHandshakingAsClient;
	} else {
	    ns->handshake = ssl2_BeginServerHandshake;
	    ss->handshaking = sslHandshakingAsServer;
	}
    }
    ns->TCPconnected = 1;
    return newfd;

loser:
    if (ns != NULL)
	ssl_FreeSocket(ns);
    if (newfd != NULL)
	PR_Close(newfd);
    return NULL;
}

static PRStatus PR_CALLBACK
ssl_Connect(PRFileDesc *fd, const PRNetAddr *sockaddr, PRIntervalTime timeout)
{
    sslSocket *ss;
    PRStatus   rv;

    ss = ssl_GetPrivate(fd);
    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in connect", SSL_GETPID(), fd));
	return PR_FAILURE;
    }

    /* IF this is a listen socket, there shouldn't be any I/O going on */
    SSL_LOCK_READER(ss);
    SSL_LOCK_WRITER(ss);

    ss->cTimeout = timeout;
    rv = (PRStatus)(*ss->ops->connect)(ss, sockaddr);

    SSL_UNLOCK_WRITER(ss);
    SSL_UNLOCK_READER(ss);

    return rv;
}

static PRStatus PR_CALLBACK
ssl_Bind(PRFileDesc *fd, const PRNetAddr *addr)
{
    sslSocket * ss = ssl_GetPrivate(fd);
    PRStatus    rv;

    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in bind", SSL_GETPID(), fd));
	return PR_FAILURE;
    }
    SSL_LOCK_READER(ss);
    SSL_LOCK_WRITER(ss);

    rv = (PRStatus)(*ss->ops->bind)(ss, addr);

    SSL_UNLOCK_WRITER(ss);
    SSL_UNLOCK_READER(ss);
    return rv;
}

static PRStatus PR_CALLBACK
ssl_Listen(PRFileDesc *fd, PRIntn backlog)
{
    sslSocket * ss = ssl_GetPrivate(fd);
    PRStatus    rv;

    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in listen", SSL_GETPID(), fd));
	return PR_FAILURE;
    }
    SSL_LOCK_READER(ss);
    SSL_LOCK_WRITER(ss);

    rv = (PRStatus)(*ss->ops->listen)(ss, backlog);

    SSL_UNLOCK_WRITER(ss);
    SSL_UNLOCK_READER(ss);
    return rv;
}

static PRStatus PR_CALLBACK
ssl_Shutdown(PRFileDesc *fd, PRIntn how)
{
    sslSocket * ss = ssl_GetPrivate(fd);
    PRStatus    rv;

    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in shutdown", SSL_GETPID(), fd));
	return PR_FAILURE;
    }
    if (how == PR_SHUTDOWN_RCV || how == PR_SHUTDOWN_BOTH) {
    	SSL_LOCK_READER(ss);
    }
    if (how == PR_SHUTDOWN_SEND || how == PR_SHUTDOWN_BOTH) {
    	SSL_LOCK_WRITER(ss);
    }

    rv = (PRStatus)(*ss->ops->shutdown)(ss, how);

    if (how == PR_SHUTDOWN_SEND || how == PR_SHUTDOWN_BOTH) {
    	SSL_UNLOCK_WRITER(ss);
    }
    if (how == PR_SHUTDOWN_RCV || how == PR_SHUTDOWN_BOTH) {
    	SSL_UNLOCK_READER(ss);
    }
    return rv;
}

static PRStatus PR_CALLBACK
ssl_Close(PRFileDesc *fd)
{
    sslSocket *ss;
    PRStatus   rv;

    ss = ssl_GetPrivate(fd);
    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in close", SSL_GETPID(), fd));
	return PR_FAILURE;
    }

    /* There must not be any I/O going on */
    SSL_LOCK_READER(ss);
    SSL_LOCK_WRITER(ss);

    /* By the time this function returns, 
    ** ss is an invalid pointer, and the locks to which it points have 
    ** been unlocked and freed.  So, this is the ONE PLACE in all of SSL
    ** where the LOCK calls and the corresponding UNLOCK calls are not in
    ** the same function scope.  The unlock calls are in ssl_FreeSocket().
    */
    rv = (PRStatus)(*ss->ops->close)(ss);

    return rv;
}

static int PR_CALLBACK
ssl_Recv(PRFileDesc *fd, void *buf, PRInt32 len, PRIntn flags,
	 PRIntervalTime timeout)
{
    sslSocket *ss;
    int        rv;

    ss = ssl_GetPrivate(fd);
    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in recv", SSL_GETPID(), fd));
	return SECFailure;
    }
    SSL_LOCK_READER(ss);
    ss->rTimeout = timeout;
    if (!ss->opt.fdx)
	ss->wTimeout = timeout;
    rv = (*ss->ops->recv)(ss, (unsigned char*)buf, len, flags);
    SSL_UNLOCK_READER(ss);
    return rv;
}

static int PR_CALLBACK
ssl_Send(PRFileDesc *fd, const void *buf, PRInt32 len, PRIntn flags,
	 PRIntervalTime timeout)
{
    sslSocket *ss;
    int        rv;

    ss = ssl_GetPrivate(fd);
    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in send", SSL_GETPID(), fd));
	return SECFailure;
    }
    SSL_LOCK_WRITER(ss);
    ss->wTimeout = timeout;
    if (!ss->opt.fdx)
	ss->rTimeout = timeout;
    rv = (*ss->ops->send)(ss, (const unsigned char*)buf, len, flags);
    SSL_UNLOCK_WRITER(ss);
    return rv;
}

static int PR_CALLBACK
ssl_Read(PRFileDesc *fd, void *buf, PRInt32 len)
{
    sslSocket *ss;
    int        rv;

    ss = ssl_GetPrivate(fd);
    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in read", SSL_GETPID(), fd));
	return SECFailure;
    }
    SSL_LOCK_READER(ss);
    ss->rTimeout = PR_INTERVAL_NO_TIMEOUT;
    if (!ss->opt.fdx)
	ss->wTimeout = PR_INTERVAL_NO_TIMEOUT;
    rv = (*ss->ops->read)(ss, (unsigned char*)buf, len);
    SSL_UNLOCK_READER(ss);
    return rv;
}

static int PR_CALLBACK
ssl_Write(PRFileDesc *fd, const void *buf, PRInt32 len)
{
    sslSocket *ss;
    int        rv;

    ss = ssl_GetPrivate(fd);
    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in write", SSL_GETPID(), fd));
	return SECFailure;
    }
    SSL_LOCK_WRITER(ss);
    ss->wTimeout = PR_INTERVAL_NO_TIMEOUT;
    if (!ss->opt.fdx)
	ss->rTimeout = PR_INTERVAL_NO_TIMEOUT;
    rv = (*ss->ops->write)(ss, (const unsigned char*)buf, len);
    SSL_UNLOCK_WRITER(ss);
    return rv;
}

static PRStatus PR_CALLBACK
ssl_GetPeerName(PRFileDesc *fd, PRNetAddr *addr)
{
    sslSocket *ss;

    ss = ssl_GetPrivate(fd);
    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in getpeername", SSL_GETPID(), fd));
	return PR_FAILURE;
    }
    return (PRStatus)(*ss->ops->getpeername)(ss, addr);
}

/*
*/
SECStatus
ssl_GetPeerInfo(sslSocket *ss)
{
    PRFileDesc *      osfd;
    int               rv;
    PRNetAddr         sin;

    osfd = ss->fd->lower;

    PORT_Memset(&sin, 0, sizeof(sin));
    rv = osfd->methods->getpeername(osfd, &sin);
    if (rv < 0) {
	return SECFailure;
    }
    ss->TCPconnected = 1;
    if (sin.inet.family == PR_AF_INET) {
        PR_ConvertIPv4AddrToIPv6(sin.inet.ip, &ss->sec.ci.peer);
	ss->sec.ci.port = sin.inet.port;
    } else if (sin.ipv6.family == PR_AF_INET6) {
	ss->sec.ci.peer = sin.ipv6.ip;
	ss->sec.ci.port = sin.ipv6.port;
    } else {
	PORT_SetError(PR_ADDRESS_NOT_SUPPORTED_ERROR);
    	return SECFailure;
    }
    return SECSuccess;
}

static PRStatus PR_CALLBACK
ssl_GetSockName(PRFileDesc *fd, PRNetAddr *name)
{
    sslSocket *ss;

    ss = ssl_GetPrivate(fd);
    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in getsockname", SSL_GETPID(), fd));
	return PR_FAILURE;
    }
    return (PRStatus)(*ss->ops->getsockname)(ss, name);
}

SECStatus
SSL_SetStapledOCSPResponses(PRFileDesc *fd, const SECItemArray *responses,
			    SSLKEAType kea)
{
    sslSocket *ss;

    ss = ssl_FindSocket(fd);
    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in SSL_SetStapledOCSPResponses",
		 SSL_GETPID(), fd));
	return SECFailure;
    }

    if ( kea <= 0 || kea >= kt_kea_size) {
	SSL_DBG(("%d: SSL[%d]: invalid key in SSL_SetStapledOCSPResponses",
		 SSL_GETPID(), fd));
	return SECFailure;
    }

    if (ss->certStatusArray[kea]) {
        SECITEM_FreeArray(ss->certStatusArray[kea], PR_TRUE);
        ss->certStatusArray[kea] = NULL;
    }
    if (responses) {
	ss->certStatusArray[kea] = SECITEM_DupArray(NULL, responses);
    }
    return (ss->certStatusArray[kea] || !responses) ? SECSuccess : SECFailure;
}

SECStatus
SSL_SetSockPeerID(PRFileDesc *fd, const char *peerID)
{
    sslSocket *ss;

    ss = ssl_FindSocket(fd);
    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in SSL_SetSockPeerID",
		 SSL_GETPID(), fd));
	return SECFailure;
    }

    if (ss->peerID) {
    	PORT_Free(ss->peerID);
	ss->peerID = NULL;
    }
    if (peerID)
	ss->peerID = PORT_Strdup(peerID);
    return (ss->peerID || !peerID) ? SECSuccess : SECFailure;
}

#define PR_POLL_RW (PR_POLL_WRITE | PR_POLL_READ)

static PRInt16 PR_CALLBACK
ssl_Poll(PRFileDesc *fd, PRInt16 how_flags, PRInt16 *p_out_flags)
{
    sslSocket *ss;
    PRInt16    new_flags = how_flags;	/* should select on these flags. */
    PRNetAddr  addr;

    *p_out_flags = 0;
    ss = ssl_GetPrivate(fd);
    if (!ss) {
	SSL_DBG(("%d: SSL[%d]: bad socket in SSL_Poll",
		 SSL_GETPID(), fd));
	return 0;	/* don't poll on this socket */
    }

    if (ss->opt.useSecurity && 
	ss->handshaking != sslHandshakingUndetermined &&
        !ss->firstHsDone &&
	(how_flags & PR_POLL_RW)) {
	if (!ss->TCPconnected) {
	    ss->TCPconnected = (PR_SUCCESS == ssl_DefGetpeername(ss, &addr));
	}
	/* If it's not connected, then presumably the application is polling
	** on read or write appropriately, so don't change it. 
	*/
	if (ss->TCPconnected) {
	    if (!ss->handshakeBegun) {
		/* If the handshake has not begun, poll on read or write 
		** based on the local application's role in the handshake,
		** not based on what the application requested.
		*/
		new_flags &= ~PR_POLL_RW;
		if (ss->handshaking == sslHandshakingAsClient) {
		    new_flags |= PR_POLL_WRITE;
		} else { /* handshaking as server */
		    new_flags |= PR_POLL_READ;
		}
	    } else 
	    /* First handshake is in progress */
	    if (ss->lastWriteBlocked) {
		if (new_flags & PR_POLL_READ) {
		    /* The caller is waiting for data to be received, 
		    ** but the initial handshake is blocked on write, or the 
		    ** client's first handshake record has not been written.
		    ** The code should select on write, not read.
		    */
		    new_flags ^=  PR_POLL_READ;	   /* don't select on read. */
		    new_flags |=  PR_POLL_WRITE;   /* do    select on write. */
		}
	    } else if (new_flags & PR_POLL_WRITE) {
		    /* The caller is trying to write, but the handshake is 
		    ** blocked waiting for data to read, and the first 
		    ** handshake has been sent.  so do NOT to poll on write.
		    */
		    new_flags ^=  PR_POLL_WRITE;   /* don't select on write. */
		    new_flags |=  PR_POLL_READ;	   /* do    select on read. */
	    }
	}
    } else if ((new_flags & PR_POLL_READ) && (SSL_DataPending(fd) > 0)) {
	*p_out_flags = PR_POLL_READ;	/* it's ready already. */
	return new_flags;
    } else if ((ss->lastWriteBlocked) && (how_flags & PR_POLL_READ) &&
	       (ss->pendingBuf.len != 0)) { /* write data waiting to be sent */
	new_flags |=  PR_POLL_WRITE;   /* also select on write. */
    }

    if (ss->version >= SSL_LIBRARY_VERSION_3_0 &&
	ss->ssl3.hs.restartTarget != NULL) {
	/* Read and write will block until the asynchronous callback completes
	 * (e.g. until SSL_AuthCertificateComplete is called), so don't tell
	 * the caller to poll the socket unless there is pending write data.
	 */
	if (ss->lastWriteBlocked && ss->pendingBuf.len != 0) {
	    /* Ignore any newly-received data on the socket, but do wait for
	     * the socket to become writable again. Here, it is OK for an error
	     * to be detected, because our logic for sending pending write data
	     * will allow us to report the error to the caller without the risk
	     * of the application spinning.
	     */
	    new_flags &= (PR_POLL_WRITE | PR_POLL_EXCEPT);
	} else {
	    /* Unfortunately, clearing new_flags will make it impossible for
	     * the application to detect errors that it would otherwise be
	     * able to detect with PR_POLL_EXCEPT, until the asynchronous
	     * callback completes. However, we must clear all the flags to
	     * prevent the application from spinning (alternating between
	     * calling PR_Poll that would return PR_POLL_EXCEPT, and send/recv
	     * which won't actually report the I/O error while we are waiting
	     * for the asynchronous callback to complete).
	     */
	    new_flags = 0;
	}
    }

    if (new_flags && (fd->lower->methods->poll != NULL)) {
	PRInt16    lower_out_flags = 0;
	PRInt16    lower_new_flags;
        lower_new_flags = fd->lower->methods->poll(fd->lower, new_flags, 
					           &lower_out_flags);
	if ((lower_new_flags & lower_out_flags) && (how_flags != new_flags)) {
	    PRInt16 out_flags = lower_out_flags & ~PR_POLL_RW;
	    if (lower_out_flags & PR_POLL_READ) 
		out_flags |= PR_POLL_WRITE;
	    if (lower_out_flags & PR_POLL_WRITE) 
		out_flags |= PR_POLL_READ;
	    *p_out_flags = out_flags;
	    new_flags = how_flags;
	} else {
	    *p_out_flags = lower_out_flags;
	    new_flags    = lower_new_flags;
	}
    }

    return new_flags;
}

static PRInt32 PR_CALLBACK
ssl_TransmitFile(PRFileDesc *sd, PRFileDesc *fd,
		 const void *headers, PRInt32 hlen,
		 PRTransmitFileFlags flags, PRIntervalTime timeout)
{
    PRSendFileData sfd;

    sfd.fd = fd;
    sfd.file_offset = 0;
    sfd.file_nbytes = 0;
    sfd.header = headers;
    sfd.hlen = hlen;
    sfd.trailer = NULL;
    sfd.tlen = 0;

    return sd->methods->sendfile(sd, &sfd, flags, timeout);
}


PRBool
ssl_FdIsBlocking(PRFileDesc *fd)
{
    PRSocketOptionData opt;
    PRStatus           status;

    opt.option             = PR_SockOpt_Nonblocking;
    opt.value.non_blocking = PR_FALSE;
    status = PR_GetSocketOption(fd, &opt);
    if (status != PR_SUCCESS)
	return PR_FALSE;
    return (PRBool)!opt.value.non_blocking;
}

PRBool
ssl_SocketIsBlocking(sslSocket *ss)
{
    return ssl_FdIsBlocking(ss->fd);
}

PRInt32  sslFirstBufSize = 8 * 1024;
PRInt32  sslCopyLimit    = 1024;

static PRInt32 PR_CALLBACK
ssl_WriteV(PRFileDesc *fd, const PRIOVec *iov, PRInt32 vectors, 
           PRIntervalTime timeout)
{
    PRInt32            bufLen;
    PRInt32            left;
    PRInt32            rv;
    PRInt32            sent      =  0;
    const PRInt32      first_len = sslFirstBufSize;
    const PRInt32      limit     = sslCopyLimit;
    PRBool             blocking;
    PRIOVec            myIov	 = { 0, 0 };
    char               buf[MAX_FRAGMENT_LENGTH];

    if (vectors > PR_MAX_IOVECTOR_SIZE) {
    	PORT_SetError(PR_BUFFER_OVERFLOW_ERROR);
	return -1;
    }
    blocking = ssl_FdIsBlocking(fd);

#define K16 sizeof(buf)
#define KILL_VECTORS while (vectors && !iov->iov_len) { ++iov; --vectors; }
#define GET_VECTOR   do { myIov = *iov++; --vectors; KILL_VECTORS } while (0)
#define HANDLE_ERR(rv, len) \
    if (rv != len) { \
	if (rv < 0) { \
	    if (!blocking \
		&& (PR_GetError() == PR_WOULD_BLOCK_ERROR) \
		&& (sent > 0)) { \
		return sent; \
	    } else { \
		return -1; \
	    } \
	} \
	/* Only a nonblocking socket can have partial sends */ \
	PR_ASSERT(!blocking); \
	return sent + rv; \
    } 
#define SEND(bfr, len) \
    do { \
	rv = ssl_Send(fd, bfr, len, 0, timeout); \
	HANDLE_ERR(rv, len) \
	sent += len; \
    } while (0)

    /* Make sure the first write is at least 8 KB, if possible. */
    KILL_VECTORS
    if (!vectors)
	return ssl_Send(fd, 0, 0, 0, timeout);
    GET_VECTOR;
    if (!vectors) {
	return ssl_Send(fd, myIov.iov_base, myIov.iov_len, 0, timeout);
    }
    if (myIov.iov_len < first_len) {
	PORT_Memcpy(buf, myIov.iov_base, myIov.iov_len);
	bufLen = myIov.iov_len;
	left = first_len - bufLen;
	while (vectors && left) {
	    int toCopy;
	    GET_VECTOR;
	    toCopy = PR_MIN(left, myIov.iov_len);
	    PORT_Memcpy(buf + bufLen, myIov.iov_base, toCopy);
	    bufLen         += toCopy;
	    left           -= toCopy;
	    myIov.iov_base += toCopy;
	    myIov.iov_len  -= toCopy;
	}
	SEND( buf, bufLen );
    }

    while (vectors || myIov.iov_len) {
	PRInt32   addLen;
	if (!myIov.iov_len) {
	    GET_VECTOR;
	}
	while (myIov.iov_len >= K16) {
	    SEND(myIov.iov_base, K16);
	    myIov.iov_base += K16;
	    myIov.iov_len  -= K16;
	}
	if (!myIov.iov_len)
	    continue;

	if (!vectors || myIov.iov_len > limit) {
	    addLen = 0;
	} else if ((addLen = iov->iov_len % K16) + myIov.iov_len <= limit) {
	    /* Addlen is already computed. */;
	} else if (vectors > 1 && 
	     iov[1].iov_len % K16 + addLen + myIov.iov_len <= 2 * limit) {
	     addLen = limit - myIov.iov_len;
	} else 
	    addLen = 0;

	if (!addLen) {
	    SEND( myIov.iov_base, myIov.iov_len );
	    myIov.iov_len = 0;
	    continue;
	}
	PORT_Memcpy(buf, myIov.iov_base, myIov.iov_len);
	bufLen = myIov.iov_len;
	do {
	    GET_VECTOR;
	    PORT_Memcpy(buf + bufLen, myIov.iov_base, addLen);
	    myIov.iov_base += addLen;
	    myIov.iov_len  -= addLen;
	    bufLen         += addLen;

	    left = PR_MIN( limit, K16 - bufLen);
	    if (!vectors 		/* no more left */
	    ||  myIov.iov_len > 0	/* we didn't use that one all up */
	    ||  bufLen >= K16		/* it's full. */
	    ) {
		addLen = 0;
	    } else if ((addLen = iov->iov_len % K16) <= left) {
		/* Addlen is already computed. */;
	    } else if (vectors > 1 && 
		 iov[1].iov_len % K16 + addLen <= left + limit) {
		 addLen = left;
	    } else 
		addLen = 0;

	} while (addLen);
	SEND( buf, bufLen );
    } 
    return sent;
}

/*
 * These functions aren't implemented.
 */

static PRInt32 PR_CALLBACK
ssl_Available(PRFileDesc *fd)
{
    PORT_Assert(0);
    PR_SetError(PR_NOT_IMPLEMENTED_ERROR, 0);
    return SECFailure;
}

static PRInt64 PR_CALLBACK
ssl_Available64(PRFileDesc *fd)
{
    PRInt64 res;

    PORT_Assert(0);
    PR_SetError(PR_NOT_IMPLEMENTED_ERROR, 0);
    LL_I2L(res, -1L);
    return res;
}

static PRStatus PR_CALLBACK
ssl_FSync(PRFileDesc *fd)
{
    PORT_Assert(0);
    PR_SetError(PR_NOT_IMPLEMENTED_ERROR, 0);
    return PR_FAILURE;
}

static PRInt32 PR_CALLBACK
ssl_Seek(PRFileDesc *fd, PRInt32 offset, PRSeekWhence how) {
    PORT_Assert(0);
    PR_SetError(PR_NOT_IMPLEMENTED_ERROR, 0);
    return SECFailure;
}

static PRInt64 PR_CALLBACK
ssl_Seek64(PRFileDesc *fd, PRInt64 offset, PRSeekWhence how) {
    PRInt64 res;

    PORT_Assert(0);
    PR_SetError(PR_NOT_IMPLEMENTED_ERROR, 0);
    LL_I2L(res, -1L);
    return res;
}

static PRStatus PR_CALLBACK
ssl_FileInfo(PRFileDesc *fd, PRFileInfo *info)
{
    PORT_Assert(0);
    PR_SetError(PR_NOT_IMPLEMENTED_ERROR, 0);
    return PR_FAILURE;
}

static PRStatus PR_CALLBACK
ssl_FileInfo64(PRFileDesc *fd, PRFileInfo64 *info)
{
    PORT_Assert(0);
    PR_SetError(PR_NOT_IMPLEMENTED_ERROR, 0);
    return PR_FAILURE;
}

static PRInt32 PR_CALLBACK
ssl_RecvFrom(PRFileDesc *fd, void *buf, PRInt32 amount, PRIntn flags,
	     PRNetAddr *addr, PRIntervalTime timeout)
{
    PORT_Assert(0);
    PR_SetError(PR_NOT_IMPLEMENTED_ERROR, 0);
    return SECFailure;
}

static PRInt32 PR_CALLBACK
ssl_SendTo(PRFileDesc *fd, const void *buf, PRInt32 amount, PRIntn flags,
	   const PRNetAddr *addr, PRIntervalTime timeout)
{
    PORT_Assert(0);
    PR_SetError(PR_NOT_IMPLEMENTED_ERROR, 0);
    return SECFailure;
}

static const PRIOMethods ssl_methods = {
    PR_DESC_LAYERED,
    ssl_Close,           	/* close        */
    ssl_Read,            	/* read         */
    ssl_Write,           	/* write        */
    ssl_Available,       	/* available    */
    ssl_Available64,     	/* available64  */
    ssl_FSync,           	/* fsync        */
    ssl_Seek,            	/* seek         */
    ssl_Seek64,          	/* seek64       */
    ssl_FileInfo,        	/* fileInfo     */
    ssl_FileInfo64,      	/* fileInfo64   */
    ssl_WriteV,          	/* writev       */
    ssl_Connect,         	/* connect      */
    ssl_Accept,          	/* accept       */
    ssl_Bind,            	/* bind         */
    ssl_Listen,          	/* listen       */
    ssl_Shutdown,        	/* shutdown     */
    ssl_Recv,            	/* recv         */
    ssl_Send,            	/* send         */
    ssl_RecvFrom,        	/* recvfrom     */
    ssl_SendTo,          	/* sendto       */
    ssl_Poll,            	/* poll         */
    PR_EmulateAcceptRead,       /* acceptread   */
    ssl_TransmitFile,           /* transmitfile */
    ssl_GetSockName,     	/* getsockname  */
    ssl_GetPeerName,     	/* getpeername  */
    NULL,                	/* getsockopt   OBSOLETE */
    NULL,                	/* setsockopt   OBSOLETE */
    NULL,                	/* getsocketoption   */
    NULL,                	/* setsocketoption   */
    PR_EmulateSendFile, 	/* Send a (partial) file with header/trailer*/
    NULL,                	/* reserved for future use */
    NULL,                	/* reserved for future use */
    NULL,                	/* reserved for future use */
    NULL,                	/* reserved for future use */
    NULL                 	/* reserved for future use */
};


static PRIOMethods combined_methods;

static void
ssl_SetupIOMethods(void)
{
          PRIOMethods *new_methods  = &combined_methods;
    const PRIOMethods *nspr_methods = PR_GetDefaultIOMethods();
    const PRIOMethods *my_methods   = &ssl_methods;

    *new_methods = *nspr_methods;

    new_methods->file_type         = my_methods->file_type;
    new_methods->close             = my_methods->close;
    new_methods->read              = my_methods->read;
    new_methods->write             = my_methods->write;
    new_methods->available         = my_methods->available;
    new_methods->available64       = my_methods->available64;
    new_methods->fsync             = my_methods->fsync;
    new_methods->seek              = my_methods->seek;
    new_methods->seek64            = my_methods->seek64;
    new_methods->fileInfo          = my_methods->fileInfo;
    new_methods->fileInfo64        = my_methods->fileInfo64;
    new_methods->writev            = my_methods->writev;
    new_methods->connect           = my_methods->connect;
    new_methods->accept            = my_methods->accept;
    new_methods->bind              = my_methods->bind;
    new_methods->listen            = my_methods->listen;
    new_methods->shutdown          = my_methods->shutdown;
    new_methods->recv              = my_methods->recv;
    new_methods->send              = my_methods->send;
    new_methods->recvfrom          = my_methods->recvfrom;
    new_methods->sendto            = my_methods->sendto;
    new_methods->poll              = my_methods->poll;
    new_methods->acceptread        = my_methods->acceptread;
    new_methods->transmitfile      = my_methods->transmitfile;
    new_methods->getsockname       = my_methods->getsockname;
    new_methods->getpeername       = my_methods->getpeername;
/*  new_methods->getsocketoption   = my_methods->getsocketoption;	*/
/*  new_methods->setsocketoption   = my_methods->setsocketoption;	*/
    new_methods->sendfile          = my_methods->sendfile;

}

static PRCallOnceType initIoLayerOnce;

static PRStatus  
ssl_InitIOLayer(void)
{
    ssl_layer_id = PR_GetUniqueIdentity("SSL");
    ssl_SetupIOMethods();
    ssl_inited = PR_TRUE;
    return PR_SUCCESS;
}

static PRStatus
ssl_PushIOLayer(sslSocket *ns, PRFileDesc *stack, PRDescIdentity id)
{
    PRFileDesc *layer	= NULL;
    PRStatus    status;

    if (!ssl_inited) {
	status = PR_CallOnce(&initIoLayerOnce, &ssl_InitIOLayer);
	if (status != PR_SUCCESS)
	    goto loser;
    }

    if (ns == NULL)
	goto loser;

    layer = PR_CreateIOLayerStub(ssl_layer_id, &combined_methods);
    if (layer == NULL)
	goto loser;
    layer->secret = (PRFilePrivate *)ns;

    /* Here, "stack" points to the PRFileDesc on the top of the stack.
    ** "layer" points to a new FD that is to be inserted into the stack.
    ** If layer is being pushed onto the top of the stack, then 
    ** PR_PushIOLayer switches the contents of stack and layer, and then
    ** puts stack on top of layer, so that after it is done, the top of 
    ** stack is the same "stack" as it was before, and layer is now the 
    ** FD for the former top of stack.
    ** After this call, stack always points to the top PRFD on the stack.
    ** If this function fails, the contents of stack and layer are as 
    ** they were before the call.
    */
    status = PR_PushIOLayer(stack, id, layer);
    if (status != PR_SUCCESS)
	goto loser;

    ns->fd = (id == PR_TOP_IO_LAYER) ? stack : layer;
    return PR_SUCCESS;

loser:
    if (layer) {
	layer->dtor(layer); /* free layer */
    }
    return PR_FAILURE;
}

/* if this fails, caller must destroy socket. */
static SECStatus
ssl_MakeLocks(sslSocket *ss)
{
    ss->firstHandshakeLock = PZ_NewMonitor(nssILockSSL);
    if (!ss->firstHandshakeLock) 
	goto loser;
    ss->ssl3HandshakeLock  = PZ_NewMonitor(nssILockSSL);
    if (!ss->ssl3HandshakeLock) 
	goto loser;
    ss->specLock           = NSSRWLock_New(SSL_LOCK_RANK_SPEC, NULL);
    if (!ss->specLock) 
	goto loser;
    ss->recvBufLock        = PZ_NewMonitor(nssILockSSL);
    if (!ss->recvBufLock) 
	goto loser;
    ss->xmitBufLock        = PZ_NewMonitor(nssILockSSL);
    if (!ss->xmitBufLock) 
	goto loser;
    ss->writerThread       = NULL;
    if (ssl_lock_readers) {
	ss->recvLock       = PZ_NewLock(nssILockSSL);
	if (!ss->recvLock) 
	    goto loser;
	ss->sendLock       = PZ_NewLock(nssILockSSL);
	if (!ss->sendLock) 
	    goto loser;
    }
    return SECSuccess;
loser:
    ssl_DestroyLocks(ss);
    return SECFailure;
}

#if defined(XP_UNIX) || defined(XP_WIN32) || defined(XP_BEOS)
#define NSS_HAVE_GETENV 1
#endif

#define LOWER(x) (x | 0x20)  /* cheap ToLower function ignores LOCALE */

static void
ssl_SetDefaultsFromEnvironment(void)
{
#if defined( NSS_HAVE_GETENV )
    static int firsttime = 1;

    if (firsttime) {
	char * ev;
	firsttime = 0;
#ifdef DEBUG
	ev = getenv("SSLDEBUGFILE");
	if (ev && ev[0]) {
	    ssl_trace_iob = fopen(ev, "w");
	}
	if (!ssl_trace_iob) {
	    ssl_trace_iob = stderr;
	}
#ifdef TRACE
	ev = getenv("SSLTRACE");
	if (ev && ev[0]) {
	    ssl_trace = atoi(ev);
	    SSL_TRACE(("SSL: tracing set to %d", ssl_trace));
	}
#endif /* TRACE */
	ev = getenv("SSLDEBUG");
	if (ev && ev[0]) {
	    ssl_debug = atoi(ev);
	    SSL_TRACE(("SSL: debugging set to %d", ssl_debug));
	}
#endif /* DEBUG */
	ev = getenv("SSLKEYLOGFILE");
	if (ev && ev[0]) {
	    ssl_keylog_iob = fopen(ev, "a");
	    if (!ssl_keylog_iob) {
		SSL_TRACE(("SSL: failed to open key log file"));
	    } else {
		if (ftell(ssl_keylog_iob) == 0) {
		    fputs("# SSL/TLS secrets log file, generated by NSS\n",
			  ssl_keylog_iob);
		}
		SSL_TRACE(("SSL: logging SSL/TLS secrets to %s", ev));
	    }
	}
#ifndef NO_PKCS11_BYPASS
	ev = getenv("SSLBYPASS");
	if (ev && ev[0]) {
	    ssl_defaults.bypassPKCS11 = (ev[0] == '1');
	    SSL_TRACE(("SSL: bypass default set to %d", \
		      ssl_defaults.bypassPKCS11));
	}
#endif /* NO_PKCS11_BYPASS */
	ev = getenv("SSLFORCELOCKS");
	if (ev && ev[0] == '1') {
	    ssl_force_locks = PR_TRUE;
	    ssl_defaults.noLocks = 0;
	    strcpy(lockStatus + LOCKSTATUS_OFFSET, "FORCED.  ");
	    SSL_TRACE(("SSL: force_locks set to %d", ssl_force_locks));
	}
	ev = getenv("NSS_SSL_ENABLE_RENEGOTIATION");
	if (ev) {
	    if (ev[0] == '1' || LOWER(ev[0]) == 'u')
	    	ssl_defaults.enableRenegotiation = SSL_RENEGOTIATE_UNRESTRICTED;
	    else if (ev[0] == '0' || LOWER(ev[0]) == 'n')
	    	ssl_defaults.enableRenegotiation = SSL_RENEGOTIATE_NEVER;
	    else if (ev[0] == '2' || LOWER(ev[0]) == 'r')
		ssl_defaults.enableRenegotiation = SSL_RENEGOTIATE_REQUIRES_XTN;
	    else if (ev[0] == '3' || LOWER(ev[0]) == 't')
	    	ssl_defaults.enableRenegotiation = SSL_RENEGOTIATE_TRANSITIONAL;
	    SSL_TRACE(("SSL: enableRenegotiation set to %d", 
	               ssl_defaults.enableRenegotiation));
	}
	ev = getenv("NSS_SSL_REQUIRE_SAFE_NEGOTIATION");
	if (ev && ev[0] == '1') {
	    ssl_defaults.requireSafeNegotiation = PR_TRUE;
	    SSL_TRACE(("SSL: requireSafeNegotiation set to %d", 
	                PR_TRUE));
	}
	ev = getenv("NSS_SSL_CBC_RANDOM_IV");
	if (ev && ev[0] == '0') {
	    ssl_defaults.cbcRandomIV = PR_FALSE;
	    SSL_TRACE(("SSL: cbcRandomIV set to 0"));
	}
    }
#endif /* NSS_HAVE_GETENV */
}

/*
** Create a newsocket structure for a file descriptor.
*/
static sslSocket *
ssl_NewSocket(PRBool makeLocks, SSLProtocolVariant protocolVariant)
{
    sslSocket *ss;

    ssl_SetDefaultsFromEnvironment();

    if (ssl_force_locks)
	makeLocks = PR_TRUE;

    /* Make a new socket and get it ready */
    ss = (sslSocket*) PORT_ZAlloc(sizeof(sslSocket));
    if (ss) {
        /* This should be of type SSLKEAType, but CC on IRIX
	 * complains during the for loop.
	 */
	int i;
	SECStatus status;
 
	ss->opt                = ssl_defaults;
	ss->opt.useSocks       = PR_FALSE;
	ss->opt.noLocks        = !makeLocks;
	ss->vrange             = *VERSIONS_DEFAULTS(protocolVariant);
	ss->protocolVariant    = protocolVariant;

	ss->peerID             = NULL;
	ss->rTimeout	       = PR_INTERVAL_NO_TIMEOUT;
	ss->wTimeout	       = PR_INTERVAL_NO_TIMEOUT;
	ss->cTimeout	       = PR_INTERVAL_NO_TIMEOUT;
	ss->cipherSpecs        = NULL;
        ss->sizeCipherSpecs    = 0;  /* produced lazily */
        ss->preferredCipher    = NULL;
        ss->url                = NULL;

	for (i=kt_null; i < kt_kea_size; i++) {
	    sslServerCerts * sc = ss->serverCerts + i;
	    sc->serverCert      = NULL;
	    sc->serverCertChain = NULL;
	    sc->serverKeyPair   = NULL;
	    sc->serverKeyBits   = 0;
	    ss->certStatusArray[i] = NULL;
	}
	ss->requestedCertTypes = NULL;
	ss->stepDownKeyPair    = NULL;
	ss->dbHandle           = CERT_GetDefaultCertDB();

	/* Provide default implementation of hooks */
	ss->authCertificate    = SSL_AuthCertificate;
	ss->authCertificateArg = (void *)ss->dbHandle;
        ss->sniSocketConfig    = NULL;
        ss->sniSocketConfigArg = NULL;
	ss->getClientAuthData  = NULL;
#ifdef NSS_PLATFORM_CLIENT_AUTH
	ss->getPlatformClientAuthData = NULL;
	ss->getPlatformClientAuthDataArg = NULL;
#endif   /* NSS_PLATFORM_CLIENT_AUTH */
	ss->handleBadCert      = NULL;
	ss->badCertArg         = NULL;
	ss->pkcs11PinArg       = NULL;
	ss->ephemeralECDHKeyPair = NULL;
	ss->getChannelID       = NULL;
	ss->getChannelIDArg    = NULL;

	ssl_ChooseOps(ss);
	ssl2_InitSocketPolicy(ss);
	ssl3_InitSocketPolicy(ss);
	PR_INIT_CLIST(&ss->ssl3.hs.lastMessageFlight);

	if (makeLocks) {
	    status = ssl_MakeLocks(ss);
	    if (status != SECSuccess)
		goto loser;
	}
	status = ssl_CreateSecurityInfo(ss);
	if (status != SECSuccess) 
	    goto loser;
	status = ssl_InitGather(&ss->gs);
	if (status != SECSuccess) {
loser:
	    ssl_DestroySocketContents(ss);
	    ssl_DestroyLocks(ss);
	    PORT_Free(ss);
	    ss = NULL;
	}
    }
    return ss;
}

