diff --git a/lib/ssl/config.mk b/lib/ssl/config.mk --- a/lib/ssl/config.mk +++ b/lib/ssl/config.mk @@ -2,16 +2,20 @@ # 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/. ifdef NISCC_TEST DEFINES += -DNISCC_TEST endif +ifdef NSS_NO_SSL2_NO_EXPORT +DEFINES += -DNSS_NO_SSL2_NO_EXPORT +endif + # Allow build-time configuration of TLS 1.3 (Experimental) ifdef NSS_ENABLE_TLS_1_3 DEFINES += -DNSS_ENABLE_TLS_1_3 endif ifdef NSS_NO_PKCS11_BYPASS DEFINES += -DNO_PKCS11_BYPASS else diff --git a/lib/ssl/sslsock.c b/lib/ssl/sslsock.c --- a/lib/ssl/sslsock.c +++ b/lib/ssl/sslsock.c @@ -674,16 +674,22 @@ SSL_OptionSet(PRFileDesc *fd, PRInt32 wh if (ss->cipherSpecs) { PORT_Free(ss->cipherSpecs); ss->cipherSpecs = NULL; ss->sizeCipherSpecs = 0; } break; case SSL_ENABLE_SSL2: +#ifdef NSS_NO_SSL2_NO_EXPORT + if (on) { + PORT_SetError(SSL_ERROR_SSL2_DISABLED); + rv = SECFailure; /* not allowed */ + } +#else if (IS_DTLS(ss)) { if (on) { PORT_SetError(SEC_ERROR_INVALID_ARGS); rv = SECFailure; /* not allowed */ } break; } ss->opt.enableSSL2 = on; @@ -691,52 +697,67 @@ SSL_OptionSet(PRFileDesc *fd, PRInt32 wh ss->opt.v2CompatibleHello = on; } ss->preferredCipher = NULL; if (ss->cipherSpecs) { PORT_Free(ss->cipherSpecs); ss->cipherSpecs = NULL; ss->sizeCipherSpecs = 0; } +#endif /* NSS_NO_SSL2_NO_EXPORT */ 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: +#ifdef NSS_NO_SSL2_NO_EXPORT + if (on) { + PORT_SetError(SSL_ERROR_SSL2_DISABLED); + rv = SECFailure; /* not allowed */ + } +#else 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; } +#endif /* NSS_NO_SSL2_NO_EXPORT */ break; case SSL_ROLLBACK_DETECTION: ss->opt.detectRollBack = on; break; case SSL_NO_STEP_DOWN: +#ifdef NSS_NO_SSL2_NO_EXPORT + if (!on) { + PORT_SetError(SSL_ERROR_SSL2_DISABLED); + rv = SECFailure; /* not allowed */ + } +#else ss->opt.noStepDown = on; if (on) SSL_DisableExportCipherSuites(fd); +#endif /* NSS_NO_SSL2_NO_EXPORT */ break; case SSL_BYPASS_PKCS11: if (ss->handshakeBegun) { PORT_SetError(PR_INVALID_STATE_ERROR); rv = SECFailure; } else { if (PR_FALSE != on) { @@ -1163,16 +1184,32 @@ SSL_OptionSetDefault(PRInt32 which, PRBo } return SECSuccess; } /* function tells us if the cipher suite is one that we no longer support. */ static PRBool ssl_IsRemovedCipherSuite(PRInt32 suite) { +#ifdef NSS_NO_SSL2_NO_EXPORT + /* both ssl2 and export cipher suites disabled */ + if (SSL_IS_SSL2_CIPHER(suite)) + return PR_TRUE; + if (SSL_IsExportCipherSuite(suite)) { + SSLCipherSuiteInfo csdef; + if (SSL_GetCipherSuiteInfo(suite, &csdef, sizeof(csdef)) != SECSuccess) { + /* failure to retrieve info, disable */ + return PR_TRUE; + } + if (csdef.symCipher != ssl_calg_null) { + /* disable all except NULL ciphersuites */ + return PR_TRUE; + } + } +#endif /* NSS_NO_SSL2_NO_EXPORT */ 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; }