зеркало из https://github.com/mozilla/gecko-dev.git
Implement two new SSL socket options: SSL_BYPASS_PKCS11 and SSL_NO_LOCKS.
Reorganize the SSL Socket structure contents to obviate ssl3 pointer. Move much of the ECC code from ssl3con to new file ssl3ecc.c. derive.c implements derivation of the SSL/TLS master secret and the encryption and MAC keys and IVs without using PKCS11. Bug 305147. r=rrelyea. Modified Files: ssl/config.mk ssl/manifest.mn ssl/ssl.h ssl/ssl3con.c ssl/ssl3gthr.c ssl/sslauth.c ssl/sslcon.c ssl/ssldef.c ssl/sslgathr.c ssl/sslimpl.h ssl/sslinfo.c ssl/sslnonce.c ssl/sslsecur.c ssl/sslsnce.c ssl/sslsock.c Added Files: ssl/derive.c ssl/ssl3ecc.c
This commit is contained in:
Родитель
ec09744d98
Коммит
4b56704437
|
@ -66,8 +66,32 @@ EXTRA_SHARED_LIBS += \
|
|||
$(NULL)
|
||||
endif # NS_USE_GCC
|
||||
|
||||
# $(PROGRAM) has explicit dependencies on $(EXTRA_LIBS)
|
||||
CRYPTOLIB=$(DIST)/lib/$(LIB_PREFIX)freebl.$(LIB_SUFFIX)
|
||||
CRYPTODIR=../freebl
|
||||
ifdef MOZILLA_SECURITY_BUILD
|
||||
CRYPTOLIB=$(DIST)/lib/$(LIB_PREFIX)crypto.$(LIB_SUFFIX)
|
||||
CRYPTODIR=../crypto
|
||||
endif
|
||||
|
||||
EXTRA_LIBS += \
|
||||
$(CRYPTOLIB) \
|
||||
$(NULL)
|
||||
|
||||
else
|
||||
|
||||
# $(PROGRAM) has explicit dependencies on $(EXTRA_LIBS)
|
||||
CRYPTOLIB=$(DIST)/lib/$(LIB_PREFIX)freebl.$(LIB_SUFFIX)
|
||||
CRYPTODIR=../freebl
|
||||
ifdef MOZILLA_SECURITY_BUILD
|
||||
CRYPTOLIB=$(DIST)/lib/$(LIB_PREFIX)crypto.$(LIB_SUFFIX)
|
||||
CRYPTODIR=../crypto
|
||||
endif
|
||||
|
||||
EXTRA_LIBS += \
|
||||
$(CRYPTOLIB) \
|
||||
$(NULL)
|
||||
|
||||
|
||||
# $(PROGRAM) has NO explicit dependencies on $(EXTRA_SHARED_LIBS)
|
||||
# $(EXTRA_SHARED_LIBS) come before $(OS_LIBS), except on AIX.
|
||||
|
@ -92,6 +116,7 @@ ifeq ($(OS_TARGET),SunOS)
|
|||
# The -R '$ORIGIN' linker option instructs this library to search for its
|
||||
# dependencies in the same directory where it resides.
|
||||
MKSHLIB += -R '$$ORIGIN'
|
||||
#EXTRA_SHARED_LIBS += -ldl -lrt -lc -z defs
|
||||
endif
|
||||
|
||||
endif
|
||||
|
|
|
@ -0,0 +1,481 @@
|
|||
/*
|
||||
* Key Derivation that doesn't use PKCS11
|
||||
*
|
||||
* ***** BEGIN LICENSE BLOCK *****
|
||||
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
|
||||
*
|
||||
* The contents of this file are subject to the Mozilla Public License Version
|
||||
* 1.1 (the "License"); you may not use this file except in compliance with
|
||||
* the License. You may obtain a copy of the License at
|
||||
* http://www.mozilla.org/MPL/
|
||||
*
|
||||
* Software distributed under the License is distributed on an "AS IS" basis,
|
||||
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
|
||||
* for the specific language governing rights and limitations under the
|
||||
* License.
|
||||
*
|
||||
* The Original Code is the Netscape security libraries.
|
||||
*
|
||||
* The Initial Developer of the Original Code is
|
||||
* Netscape Communications Corporation.
|
||||
* Portions created by the Initial Developer are Copyright (C) 1994-2005
|
||||
* the Initial Developer. All Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
*
|
||||
* Alternatively, the contents of this file may be used under the terms of
|
||||
* either the GNU General Public License Version 2 or later (the "GPL"), or
|
||||
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
|
||||
* in which case the provisions of the GPL or the LGPL are applicable instead
|
||||
* of those above. If you wish to allow use of your version of this file only
|
||||
* under the terms of either the GPL or the LGPL, and not to allow others to
|
||||
* use your version of this file under the terms of the MPL, indicate your
|
||||
* decision by deleting the provisions above and replace them with the notice
|
||||
* and other provisions required by the GPL or the LGPL. If you do not delete
|
||||
* the provisions above, a recipient may use your version of this file under
|
||||
* the terms of any one of the MPL, the GPL or the LGPL.
|
||||
*
|
||||
* ***** END LICENSE BLOCK ***** */
|
||||
/* $Id: derive.c,v 1.2 2005/09/09 03:02:16 nelsonb%netscape.com Exp $ */
|
||||
|
||||
#include "ssl.h" /* prereq to sslimpl.h */
|
||||
#include "certt.h" /* prereq to sslimpl.h */
|
||||
#include "keythi.h" /* prereq to sslimpl.h */
|
||||
#include "sslimpl.h"
|
||||
#include "blapi.h"
|
||||
|
||||
/* make this a macro! */
|
||||
#ifdef NOT_A_MACRO
|
||||
static void
|
||||
buildSSLKey(unsigned char * keyBlock, unsigned int keyLen, SECItem * result)
|
||||
{
|
||||
result->type = siBuffer;
|
||||
result->data = keyBlock;
|
||||
result->len = keyLen;
|
||||
}
|
||||
#else
|
||||
#define buildSSLKey(keyBlock, keyLen, result) \
|
||||
{ \
|
||||
(result)->type = siBuffer; \
|
||||
(result)->data = keyBlock; \
|
||||
(result)->len = keyLen; \
|
||||
}
|
||||
#endif
|
||||
|
||||
/*
|
||||
* SSL Key generation given pre master secret
|
||||
*/
|
||||
#ifndef NUM_MIXERS
|
||||
#define NUM_MIXERS 9
|
||||
#endif
|
||||
static const char * const mixers[NUM_MIXERS] = {
|
||||
"A",
|
||||
"BB",
|
||||
"CCC",
|
||||
"DDDD",
|
||||
"EEEEE",
|
||||
"FFFFFF",
|
||||
"GGGGGGG",
|
||||
"HHHHHHHH",
|
||||
"IIIIIIIII"
|
||||
};
|
||||
|
||||
|
||||
SECStatus
|
||||
ssl3_KeyAndMacDeriveBypass(
|
||||
ssl3CipherSpec * pwSpec,
|
||||
const unsigned char * cr,
|
||||
const unsigned char * sr,
|
||||
PRBool isTLS,
|
||||
PRBool isExport)
|
||||
{
|
||||
const ssl3BulkCipherDef *cipher_def = pwSpec->cipher_def;
|
||||
unsigned char * key_block = pwSpec->key_block;
|
||||
unsigned char * key_block2 = NULL;
|
||||
unsigned int block_bytes = 0;
|
||||
unsigned int block_needed = 0;
|
||||
unsigned int i;
|
||||
unsigned int keySize; /* actual size of cipher keys */
|
||||
unsigned int effKeySize; /* effective size of cipher keys */
|
||||
unsigned int macSize; /* size of MAC secret */
|
||||
unsigned int IVSize; /* size of IV */
|
||||
SECStatus rv = SECFailure;
|
||||
SECStatus status = SECSuccess;
|
||||
PRBool isFIPS = PR_FALSE;
|
||||
|
||||
SECItem srcr;
|
||||
SECItem crsr;
|
||||
|
||||
unsigned char srcrdata[SSL3_RANDOM_LENGTH * 2];
|
||||
unsigned char crsrdata[SSL3_RANDOM_LENGTH * 2];
|
||||
PRUint64 md5buf[22];
|
||||
PRUint64 shabuf[40];
|
||||
|
||||
#define md5Ctx ((MD5Context *)md5buf)
|
||||
#define shaCtx ((SHA1Context *)shabuf)
|
||||
|
||||
static const SECItem zed = { siBuffer, NULL, 0 };
|
||||
|
||||
if (pwSpec->msItem.data == NULL ||
|
||||
pwSpec->msItem.len != SSL3_MASTER_SECRET_LENGTH) {
|
||||
PORT_SetError(SEC_ERROR_INVALID_ARGS);
|
||||
return rv;
|
||||
}
|
||||
|
||||
/* figure out how much is needed */
|
||||
macSize = pwSpec->mac_size;
|
||||
keySize = cipher_def->key_size;
|
||||
effKeySize = cipher_def->secret_key_size;
|
||||
IVSize = cipher_def->iv_size;
|
||||
if (keySize == 0) {
|
||||
effKeySize = IVSize = 0; /* only MACing */
|
||||
}
|
||||
block_needed = 2 * (macSize + effKeySize + ((!isExport) * IVSize));
|
||||
|
||||
/*
|
||||
* clear out our returned keys so we can recover on failure
|
||||
*/
|
||||
pwSpec->client.write_key_item = zed;
|
||||
pwSpec->client.write_mac_key_item = zed;
|
||||
pwSpec->server.write_key_item = zed;
|
||||
pwSpec->server.write_mac_key_item = zed;
|
||||
|
||||
/* initialize the server random, client random block */
|
||||
srcr.type = siBuffer;
|
||||
srcr.data = srcrdata;
|
||||
srcr.len = sizeof srcrdata;
|
||||
PORT_Memcpy(srcrdata, sr, SSL3_RANDOM_LENGTH);
|
||||
PORT_Memcpy(srcrdata + SSL3_RANDOM_LENGTH, cr, SSL3_RANDOM_LENGTH);
|
||||
|
||||
/* initialize the client random, server random block */
|
||||
crsr.type = siBuffer;
|
||||
crsr.data = crsrdata;
|
||||
crsr.len = sizeof crsrdata;
|
||||
PORT_Memcpy(crsrdata, cr, SSL3_RANDOM_LENGTH);
|
||||
PORT_Memcpy(crsrdata + SSL3_RANDOM_LENGTH, sr, SSL3_RANDOM_LENGTH);
|
||||
|
||||
/*
|
||||
* generate the key material:
|
||||
*/
|
||||
if (isTLS) {
|
||||
SECItem keyblk;
|
||||
|
||||
keyblk.type = siBuffer;
|
||||
keyblk.data = key_block;
|
||||
keyblk.len = block_needed;
|
||||
|
||||
status = TLS_PRF(&pwSpec->msItem, "key expansion", &srcr, &keyblk,
|
||||
isFIPS);
|
||||
if (status != SECSuccess) {
|
||||
goto key_and_mac_derive_fail;
|
||||
}
|
||||
block_bytes = keyblk.len;
|
||||
} else {
|
||||
/* key_block =
|
||||
* MD5(master_secret + SHA('A' + master_secret +
|
||||
* ServerHello.random + ClientHello.random)) +
|
||||
* MD5(master_secret + SHA('BB' + master_secret +
|
||||
* ServerHello.random + ClientHello.random)) +
|
||||
* MD5(master_secret + SHA('CCC' + master_secret +
|
||||
* ServerHello.random + ClientHello.random)) +
|
||||
* [...];
|
||||
*/
|
||||
int made = 0;
|
||||
for (i = 0; made < block_needed && i < NUM_MIXERS; ++i) {
|
||||
unsigned int outLen;
|
||||
unsigned char sha_out[SHA1_LENGTH];
|
||||
|
||||
SHA1_Begin(shaCtx);
|
||||
SHA1_Update(shaCtx, (unsigned char*)(mixers[i]), i+1);
|
||||
SHA1_Update(shaCtx, pwSpec->msItem.data, pwSpec->msItem.len);
|
||||
SHA1_Update(shaCtx, srcr.data, srcr.len);
|
||||
SHA1_End(shaCtx, sha_out, &outLen, SHA1_LENGTH);
|
||||
PORT_Assert(outLen == SHA1_LENGTH);
|
||||
|
||||
MD5_Begin(md5Ctx);
|
||||
MD5_Update(md5Ctx, pwSpec->msItem.data, pwSpec->msItem.len);
|
||||
MD5_Update(md5Ctx, sha_out, outLen);
|
||||
MD5_End(md5Ctx, key_block + made, &outLen, MD5_LENGTH);
|
||||
PORT_Assert(outLen == MD5_LENGTH);
|
||||
made += MD5_LENGTH;
|
||||
}
|
||||
block_bytes = made;
|
||||
}
|
||||
PORT_Assert(block_bytes >= block_needed);
|
||||
PORT_Assert(block_bytes <= sizeof pwSpec->key_block);
|
||||
|
||||
/*
|
||||
* Put the key material where it goes.
|
||||
*/
|
||||
key_block2 = key_block + block_bytes;
|
||||
i = 0; /* now shows how much consumed */
|
||||
|
||||
/*
|
||||
* The key_block is partitioned as follows:
|
||||
* client_write_MAC_secret[CipherSpec.hash_size]
|
||||
*/
|
||||
buildSSLKey(&key_block[i],macSize, &pwSpec->client.write_mac_key_item);
|
||||
i += macSize;
|
||||
|
||||
/*
|
||||
* server_write_MAC_secret[CipherSpec.hash_size]
|
||||
*/
|
||||
buildSSLKey(&key_block[i],macSize, &pwSpec->server.write_mac_key_item);
|
||||
i += macSize;
|
||||
|
||||
if (!keySize) {
|
||||
/* only MACing */
|
||||
buildSSLKey(NULL, 0, &pwSpec->client.write_key_item);
|
||||
buildSSLKey(NULL, 0, &pwSpec->server.write_key_item);
|
||||
buildSSLKey(NULL, 0, &pwSpec->client.write_iv_item);
|
||||
buildSSLKey(NULL, 0, &pwSpec->server.write_iv_item);
|
||||
} else if (!isExport) {
|
||||
/*
|
||||
** Generate Domestic write keys and IVs.
|
||||
** client_write_key[CipherSpec.key_material]
|
||||
*/
|
||||
buildSSLKey(&key_block[i], keySize, &pwSpec->client.write_key_item);
|
||||
i += keySize;
|
||||
|
||||
/*
|
||||
** server_write_key[CipherSpec.key_material]
|
||||
*/
|
||||
buildSSLKey(&key_block[i], keySize, &pwSpec->server.write_key_item);
|
||||
i += keySize;
|
||||
|
||||
if (IVSize > 0) {
|
||||
/*
|
||||
** client_write_IV[CipherSpec.IV_size]
|
||||
*/
|
||||
buildSSLKey(&key_block[i], IVSize, &pwSpec->client.write_iv_item);
|
||||
i += IVSize;
|
||||
|
||||
/*
|
||||
** server_write_IV[CipherSpec.IV_size]
|
||||
*/
|
||||
buildSSLKey(&key_block[i], IVSize, &pwSpec->server.write_iv_item);
|
||||
i += IVSize;
|
||||
}
|
||||
PORT_Assert(i <= block_bytes);
|
||||
|
||||
} else if (!isTLS) {
|
||||
/*
|
||||
** Generate SSL3 Export write keys and IVs.
|
||||
*/
|
||||
unsigned int outLen;
|
||||
|
||||
/*
|
||||
** client_write_key[CipherSpec.key_material]
|
||||
** final_client_write_key = MD5(client_write_key +
|
||||
** ClientHello.random + ServerHello.random);
|
||||
*/
|
||||
MD5_Begin(md5Ctx);
|
||||
MD5_Update(md5Ctx, &key_block[i], effKeySize);
|
||||
MD5_Update(md5Ctx, crsr.data, crsr.len);
|
||||
MD5_End(md5Ctx, key_block2, &outLen, MD5_LENGTH);
|
||||
i += effKeySize;
|
||||
buildSSLKey(key_block2, keySize, &pwSpec->client.write_key_item);
|
||||
key_block2 += keySize;
|
||||
|
||||
/*
|
||||
** server_write_key[CipherSpec.key_material]
|
||||
** final_server_write_key = MD5(server_write_key +
|
||||
** ServerHello.random + ClientHello.random);
|
||||
*/
|
||||
MD5_Begin(md5Ctx);
|
||||
MD5_Update(md5Ctx, &key_block[i], effKeySize);
|
||||
MD5_Update(md5Ctx, srcr.data, srcr.len);
|
||||
MD5_End(md5Ctx, key_block2, &outLen, MD5_LENGTH);
|
||||
i += effKeySize;
|
||||
buildSSLKey(key_block2, keySize, &pwSpec->server.write_key_item);
|
||||
key_block2 += keySize;
|
||||
PORT_Assert(i <= block_bytes);
|
||||
|
||||
if (IVSize) {
|
||||
/*
|
||||
** client_write_IV =
|
||||
** MD5(ClientHello.random + ServerHello.random);
|
||||
*/
|
||||
MD5_Begin(md5Ctx);
|
||||
MD5_Update(md5Ctx, crsr.data, crsr.len);
|
||||
MD5_End(md5Ctx, key_block2, &outLen, MD5_LENGTH);
|
||||
buildSSLKey(key_block2, IVSize, &pwSpec->client.write_iv_item);
|
||||
key_block2 += IVSize;
|
||||
|
||||
/*
|
||||
** server_write_IV =
|
||||
** MD5(ServerHello.random + ClientHello.random);
|
||||
*/
|
||||
MD5_Begin(md5Ctx);
|
||||
MD5_Update(md5Ctx, srcr.data, srcr.len);
|
||||
MD5_End(md5Ctx, key_block2, &outLen, MD5_LENGTH);
|
||||
buildSSLKey(key_block2, IVSize, &pwSpec->server.write_iv_item);
|
||||
key_block2 += IVSize;
|
||||
}
|
||||
|
||||
PORT_Assert(key_block2 - key_block <= sizeof pwSpec->key_block);
|
||||
} else {
|
||||
/*
|
||||
** Generate TLS Export write keys and IVs.
|
||||
*/
|
||||
SECItem secret ;
|
||||
SECItem keyblk ;
|
||||
|
||||
secret.type = siBuffer;
|
||||
keyblk.type = siBuffer;
|
||||
/*
|
||||
** client_write_key[CipherSpec.key_material]
|
||||
** final_client_write_key = PRF(client_write_key,
|
||||
** "client write key",
|
||||
** client_random + server_random);
|
||||
*/
|
||||
secret.data = &key_block[i];
|
||||
secret.len = effKeySize;
|
||||
i += effKeySize;
|
||||
keyblk.data = key_block2;
|
||||
keyblk.len = keySize;
|
||||
status = TLS_PRF(&secret, "client write key", &crsr, &keyblk, isFIPS);
|
||||
if (status != SECSuccess) {
|
||||
goto key_and_mac_derive_fail;
|
||||
}
|
||||
buildSSLKey(key_block2, keySize, &pwSpec->client.write_key_item);
|
||||
key_block2 += keySize;
|
||||
|
||||
/*
|
||||
** server_write_key[CipherSpec.key_material]
|
||||
** final_server_write_key = PRF(server_write_key,
|
||||
** "server write key",
|
||||
** client_random + server_random);
|
||||
*/
|
||||
secret.data = &key_block[i];
|
||||
secret.len = effKeySize;
|
||||
i += effKeySize;
|
||||
keyblk.data = key_block2;
|
||||
keyblk.len = keySize;
|
||||
status = TLS_PRF(&secret, "server write key", &crsr, &keyblk, isFIPS);
|
||||
if (status != SECSuccess) {
|
||||
goto key_and_mac_derive_fail;
|
||||
}
|
||||
buildSSLKey(key_block2, keySize, &pwSpec->server.write_key_item);
|
||||
key_block2 += keySize;
|
||||
|
||||
/*
|
||||
** iv_block = PRF("", "IV block", client_random + server_random);
|
||||
** client_write_IV[SecurityParameters.IV_size]
|
||||
** server_write_IV[SecurityParameters.IV_size]
|
||||
*/
|
||||
if (IVSize) {
|
||||
secret.data = NULL;
|
||||
secret.len = 0;
|
||||
keyblk.data = key_block2;
|
||||
keyblk.len = 2 * IVSize;
|
||||
status = TLS_PRF(&secret, "IV block", &crsr, &keyblk, isFIPS);
|
||||
if (status != SECSuccess) {
|
||||
goto key_and_mac_derive_fail;
|
||||
}
|
||||
buildSSLKey(key_block2, IVSize, &pwSpec->client.write_iv_item);
|
||||
buildSSLKey(key_block2 + IVSize, IVSize, &pwSpec->server.write_iv_item);
|
||||
key_block2 += 2 * IVSize;
|
||||
}
|
||||
PORT_Assert(key_block2 - key_block <= sizeof pwSpec->key_block);
|
||||
}
|
||||
rv = SECSuccess;
|
||||
|
||||
key_and_mac_derive_fail:
|
||||
|
||||
MD5_DestroyContext(md5Ctx, PR_FALSE);
|
||||
SHA1_DestroyContext(shaCtx, PR_FALSE);
|
||||
|
||||
if (rv != SECSuccess) {
|
||||
PORT_SetError(SSL_ERROR_SESSION_KEY_GEN_FAILURE);
|
||||
}
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
|
||||
/* derive the Master Secret from the PMS */
|
||||
/* Presently, this is only done wtih RSA PMS, os isRSA is always true. */
|
||||
SECStatus
|
||||
ssl3_MasterKeyDeriveBypass(
|
||||
ssl3CipherSpec * pwSpec,
|
||||
const unsigned char * cr,
|
||||
const unsigned char * sr,
|
||||
const SECItem * pms,
|
||||
PRBool isTLS,
|
||||
PRBool isRSA)
|
||||
{
|
||||
unsigned char * key_block = pwSpec->key_block;
|
||||
SECStatus rv = SECSuccess;
|
||||
PRBool isFIPS = PR_FALSE;
|
||||
|
||||
SECItem crsr;
|
||||
|
||||
unsigned char crsrdata[SSL3_RANDOM_LENGTH * 2];
|
||||
PRUint64 md5buf[22];
|
||||
PRUint64 shabuf[40];
|
||||
|
||||
#define md5Ctx ((MD5Context *)md5buf)
|
||||
#define shaCtx ((SHA1Context *)shabuf)
|
||||
|
||||
/* first do the consistancy checks */
|
||||
if (isRSA) {
|
||||
PORT_Assert(pms->len == SSL3_RSA_PMS_LENGTH);
|
||||
if (pms->len != SSL3_RSA_PMS_LENGTH) {
|
||||
PORT_SetError(SEC_ERROR_INVALID_ARGS);
|
||||
return SECFailure;
|
||||
}
|
||||
/* test PMS version for rollback here? or in caller? */
|
||||
}
|
||||
|
||||
/* initialize the client random, server random block */
|
||||
crsr.type = siBuffer;
|
||||
crsr.data = crsrdata;
|
||||
crsr.len = sizeof crsrdata;
|
||||
PORT_Memcpy(crsrdata, cr, SSL3_RANDOM_LENGTH);
|
||||
PORT_Memcpy(crsrdata + SSL3_RANDOM_LENGTH, sr, SSL3_RANDOM_LENGTH);
|
||||
|
||||
/* finally do the key gen */
|
||||
if (isTLS) {
|
||||
SECItem master = { siBuffer, NULL, 0 };
|
||||
|
||||
master.data = key_block;
|
||||
master.len = SSL3_MASTER_SECRET_LENGTH;
|
||||
|
||||
rv = TLS_PRF(pms, "master secret", &crsr, &master, isFIPS);
|
||||
if (rv != SECSuccess) {
|
||||
PORT_SetError(SSL_ERROR_SESSION_KEY_GEN_FAILURE);
|
||||
}
|
||||
} else {
|
||||
int i;
|
||||
int made = 0;
|
||||
for (i = 0; i < 3; i++) {
|
||||
unsigned int outLen;
|
||||
unsigned char sha_out[SHA1_LENGTH];
|
||||
|
||||
SHA1_Begin(shaCtx);
|
||||
SHA1_Update(shaCtx, (unsigned char*) mixers[i], i+1);
|
||||
SHA1_Update(shaCtx, pms->data, pms->len);
|
||||
SHA1_Update(shaCtx, crsr.data, crsr.len);
|
||||
SHA1_End(shaCtx, sha_out, &outLen, SHA1_LENGTH);
|
||||
PORT_Assert(outLen == SHA1_LENGTH);
|
||||
|
||||
MD5_Begin(md5Ctx);
|
||||
MD5_Update(md5Ctx, pms->data, pms->len);
|
||||
MD5_Update(md5Ctx, sha_out, outLen);
|
||||
MD5_End(md5Ctx, key_block + made, &outLen, MD5_LENGTH);
|
||||
PORT_Assert(outLen == MD5_LENGTH);
|
||||
made += outLen;
|
||||
}
|
||||
}
|
||||
|
||||
/* store the results */
|
||||
PORT_Memcpy(pwSpec->raw_master_secret, key_block,
|
||||
SSL3_MASTER_SECRET_LENGTH);
|
||||
pwSpec->msItem.data = pwSpec->raw_master_secret;
|
||||
pwSpec->msItem.len = SSL3_MASTER_SECRET_LENGTH;
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
|
|
@ -55,6 +55,7 @@ MODULE = nss
|
|||
MAPFILE = $(OBJDIR)/ssl.def
|
||||
|
||||
CSRCS = \
|
||||
derive.c \
|
||||
emulate.c \
|
||||
prelib.c \
|
||||
ssl3con.c \
|
||||
|
@ -77,14 +78,13 @@ CSRCS = \
|
|||
cmpcert.c \
|
||||
nsskea.c \
|
||||
sslinfo.c \
|
||||
ssl3ecc.c \
|
||||
$(NULL)
|
||||
|
||||
|
||||
REQUIRES = dbm
|
||||
|
||||
ifdef NSS_ENABLE_ECC
|
||||
DEFINES += -DNSS_ENABLE_ECC
|
||||
endif
|
||||
|
||||
LIBRARY_NAME = ssl
|
||||
LIBRARY_VERSION = 3
|
||||
|
||||
|
|
|
@ -36,7 +36,7 @@
|
|||
* the terms of any one of the MPL, the GPL or the LGPL.
|
||||
*
|
||||
* ***** END LICENSE BLOCK ***** */
|
||||
/* $Id: ssl.h,v 1.22 2005/08/16 03:42:26 nelsonb%netscape.com Exp $ */
|
||||
/* $Id: ssl.h,v 1.23 2005/09/09 03:02:16 nelsonb%netscape.com Exp $ */
|
||||
|
||||
#ifndef __ssl_h_
|
||||
#define __ssl_h_
|
||||
|
@ -110,6 +110,8 @@ SSL_IMPORT PRFileDesc *SSL_ImportFD(PRFileDesc *model, PRFileDesc *fd);
|
|||
/* if step-down keys are needed. */
|
||||
/* default: off, generate */
|
||||
/* step-down keys if needed. */
|
||||
#define SSL_BYPASS_PKCS11 16 /* use PKCS#11 for pub key only */
|
||||
#define SSL_NO_LOCKS 17 /* Don't use locks for protection */
|
||||
|
||||
#ifdef SSL_DEPRECATED_FUNCTION
|
||||
/* Old deprecated function names */
|
||||
|
|
Разница между файлами не показана из-за своего большого размера
Загрузить разницу
|
@ -0,0 +1,675 @@
|
|||
/*
|
||||
* SSL3 Protocol
|
||||
*
|
||||
* ***** BEGIN LICENSE BLOCK *****
|
||||
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
|
||||
*
|
||||
* The contents of this file are subject to the Mozilla Public License Version
|
||||
* 1.1 (the "License"); you may not use this file except in compliance with
|
||||
* the License. You may obtain a copy of the License at
|
||||
* http://www.mozilla.org/MPL/
|
||||
*
|
||||
* Software distributed under the License is distributed on an "AS IS" basis,
|
||||
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
|
||||
* for the specific language governing rights and limitations under the
|
||||
* License.
|
||||
*
|
||||
* The Original Code is the Netscape security libraries.
|
||||
*
|
||||
* The Initial Developer of the Original Code is
|
||||
* Netscape Communications Corporation.
|
||||
* Portions created by the Initial Developer are Copyright (C) 1994-2000
|
||||
* the Initial Developer. All Rights Reserved.
|
||||
*
|
||||
* Contributor(s):
|
||||
* Dr Vipul Gupta <vipul.gupta@sun.com> and
|
||||
* Douglas Stebila <douglas@stebila.ca>, Sun Microsystems Laboratories
|
||||
*
|
||||
* Alternatively, the contents of this file may be used under the terms of
|
||||
* either the GNU General Public License Version 2 or later (the "GPL"), or
|
||||
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
|
||||
* in which case the provisions of the GPL or the LGPL are applicable instead
|
||||
* of those above. If you wish to allow use of your version of this file only
|
||||
* under the terms of either the GPL or the LGPL, and not to allow others to
|
||||
* use your version of this file under the terms of the MPL, indicate your
|
||||
* decision by deleting the provisions above and replace them with the notice
|
||||
* and other provisions required by the GPL or the LGPL. If you do not delete
|
||||
* the provisions above, a recipient may use your version of this file under
|
||||
* the terms of any one of the MPL, the GPL or the LGPL.
|
||||
*
|
||||
* ***** END LICENSE BLOCK ***** */
|
||||
|
||||
/* ECC code moved here from ssl3con.c */
|
||||
/* $Id: ssl3ecc.c,v 1.2 2005/09/09 03:02:16 nelsonb%netscape.com Exp $ */
|
||||
|
||||
#ifdef NSS_ENABLE_ECC
|
||||
|
||||
#include "nssrenam.h"
|
||||
#include "cert.h"
|
||||
#include "ssl.h"
|
||||
#include "cryptohi.h" /* for DSAU_ stuff */
|
||||
#include "keyhi.h"
|
||||
#include "secder.h"
|
||||
#include "secitem.h"
|
||||
|
||||
#include "sslimpl.h"
|
||||
#include "sslproto.h"
|
||||
#include "sslerr.h"
|
||||
#include "prtime.h"
|
||||
#include "prinrval.h"
|
||||
#include "prerror.h"
|
||||
#include "pratom.h"
|
||||
#include "prthread.h"
|
||||
|
||||
#include "pk11func.h"
|
||||
#include "secmod.h"
|
||||
#include "nsslocks.h"
|
||||
#include "ec.h"
|
||||
#include "blapi.h"
|
||||
|
||||
#include <stdio.h>
|
||||
|
||||
/*
|
||||
line 297: implicit function declaration: ssl3_InitPendingCipherSpec
|
||||
line 305: implicit function declaration: ssl3_AppendHandshakeHeader
|
||||
line 311: implicit function declaration: ssl3_AppendHandshakeVariable
|
||||
line 356: implicit function declaration: ssl3_ConsumeHandshakeVariable
|
||||
*/
|
||||
|
||||
|
||||
#ifndef PK11_SETATTRS
|
||||
#define PK11_SETATTRS(x,id,v,l) (x)->type = (id); \
|
||||
(x)->pValue=(v); (x)->ulValueLen = (l);
|
||||
#endif
|
||||
|
||||
/* Types and names of elliptic curves used in TLS */
|
||||
typedef enum { ec_type_explicitPrime = 1,
|
||||
ec_type_explicitChar2Curve,
|
||||
ec_type_named
|
||||
} ECType;
|
||||
|
||||
typedef enum { ec_noName = 0,
|
||||
ec_sect163k1, ec_sect163r1, ec_sect163r2,
|
||||
ec_sect193r1, ec_sect193r2, ec_sect233k1,
|
||||
ec_sect233r1, ec_sect239k1, ec_sect283k1,
|
||||
ec_sect283r1, ec_sect409k1, ec_sect409r1,
|
||||
ec_sect571k1, ec_sect571r1, ec_secp160k1,
|
||||
ec_secp160r1, ec_secp160r2, ec_secp192k1,
|
||||
ec_secp192r1, ec_secp224k1, ec_secp224r1,
|
||||
ec_secp256k1, ec_secp256r1, ec_secp384r1,
|
||||
ec_secp521r1,
|
||||
ec_pastLastName
|
||||
} ECName;
|
||||
|
||||
#define supportedCurve(x) (((x) > ec_noName) && ((x) < ec_pastLastName))
|
||||
|
||||
/* Table containing OID tags for elliptic curves named in the
|
||||
* ECC-TLS IETF draft.
|
||||
*/
|
||||
static const SECOidTag ecName2OIDTag[] = {
|
||||
0,
|
||||
SEC_OID_SECG_EC_SECT163K1, /* 1 */
|
||||
SEC_OID_SECG_EC_SECT163R1, /* 2 */
|
||||
SEC_OID_SECG_EC_SECT163R2, /* 3 */
|
||||
SEC_OID_SECG_EC_SECT193R1, /* 4 */
|
||||
SEC_OID_SECG_EC_SECT193R2, /* 5 */
|
||||
SEC_OID_SECG_EC_SECT233K1, /* 6 */
|
||||
SEC_OID_SECG_EC_SECT233R1, /* 7 */
|
||||
SEC_OID_SECG_EC_SECT239K1, /* 8 */
|
||||
SEC_OID_SECG_EC_SECT283K1, /* 9 */
|
||||
SEC_OID_SECG_EC_SECT283R1, /* 10 */
|
||||
SEC_OID_SECG_EC_SECT409K1, /* 11 */
|
||||
SEC_OID_SECG_EC_SECT409R1, /* 12 */
|
||||
SEC_OID_SECG_EC_SECT571K1, /* 13 */
|
||||
SEC_OID_SECG_EC_SECT571R1, /* 14 */
|
||||
SEC_OID_SECG_EC_SECP160K1, /* 15 */
|
||||
SEC_OID_SECG_EC_SECP160R1, /* 16 */
|
||||
SEC_OID_SECG_EC_SECP160R2, /* 17 */
|
||||
SEC_OID_SECG_EC_SECP192K1, /* 18 */
|
||||
SEC_OID_SECG_EC_SECP192R1, /* 19 */
|
||||
SEC_OID_SECG_EC_SECP224K1, /* 20 */
|
||||
SEC_OID_SECG_EC_SECP224R1, /* 21 */
|
||||
SEC_OID_SECG_EC_SECP256K1, /* 22 */
|
||||
SEC_OID_SECG_EC_SECP256R1, /* 23 */
|
||||
SEC_OID_SECG_EC_SECP384R1, /* 24 */
|
||||
SEC_OID_SECG_EC_SECP521R1, /* 25 */
|
||||
};
|
||||
|
||||
static SECStatus
|
||||
ecName2params(PRArenaPool * arena, ECName curve, SECKEYECParams * params)
|
||||
{
|
||||
SECOidData *oidData = NULL;
|
||||
|
||||
if ((curve <= ec_noName) || (curve >= ec_pastLastName) ||
|
||||
((oidData = SECOID_FindOIDByTag(ecName2OIDTag[curve])) == NULL)) {
|
||||
PORT_SetError(SEC_ERROR_UNSUPPORTED_ELLIPTIC_CURVE);
|
||||
return SECFailure;
|
||||
}
|
||||
|
||||
SECITEM_AllocItem(arena, params, (2 + oidData->oid.len));
|
||||
/*
|
||||
* params->data needs to contain the ASN encoding of an object ID (OID)
|
||||
* representing the named curve. The actual OID is in
|
||||
* oidData->oid.data so we simply prepend 0x06 and OID length
|
||||
*/
|
||||
params->data[0] = SEC_ASN1_OBJECT_ID;
|
||||
params->data[1] = oidData->oid.len;
|
||||
memcpy(params->data + 2, oidData->oid.data, oidData->oid.len);
|
||||
|
||||
return SECSuccess;
|
||||
}
|
||||
|
||||
static ECName
|
||||
params2ecName(SECKEYECParams * params)
|
||||
{
|
||||
SECItem oid = { siBuffer, NULL, 0};
|
||||
SECOidData *oidData = NULL;
|
||||
ECName i;
|
||||
|
||||
/*
|
||||
* params->data needs to contain the ASN encoding of an object ID (OID)
|
||||
* representing a named curve. Here, we strip away everything
|
||||
* before the actual OID and use the OID to look up a named curve.
|
||||
*/
|
||||
if (params->data[0] != SEC_ASN1_OBJECT_ID) return ec_noName;
|
||||
oid.len = params->len - 2;
|
||||
oid.data = params->data + 2;
|
||||
if ((oidData = SECOID_FindOID(&oid)) == NULL) return ec_noName;
|
||||
for (i = ec_noName + 1; i < ec_pastLastName; i++) {
|
||||
if (ecName2OIDTag[i] == oidData->offset)
|
||||
return i;
|
||||
}
|
||||
|
||||
return ec_noName;
|
||||
}
|
||||
|
||||
/* Caller must set hiLevel error code. */
|
||||
static SECStatus
|
||||
ssl3_ComputeECDHKeyHash(SECItem ec_params, SECItem server_ecpoint,
|
||||
SSL3Random *client_rand, SSL3Random *server_rand,
|
||||
SSL3Hashes *hashes, PRBool bypassPKCS11)
|
||||
{
|
||||
PRUint8 * hashBuf;
|
||||
PRUint8 * pBuf;
|
||||
SECStatus rv = SECSuccess;
|
||||
unsigned int bufLen;
|
||||
/*
|
||||
* XXX For now, we only support named curves (the appropriate
|
||||
* checks are made before this method is called) so ec_params
|
||||
* takes up only two bytes. ECPoint needs to fit in 256 bytes
|
||||
* (because the spec says the length must fit in one byte)
|
||||
*/
|
||||
PRUint8 buf[2*SSL3_RANDOM_LENGTH + 2 + 1 + 256];
|
||||
|
||||
bufLen = 2*SSL3_RANDOM_LENGTH + ec_params.len + 1 + server_ecpoint.len;
|
||||
if (bufLen <= sizeof buf) {
|
||||
hashBuf = buf;
|
||||
} else {
|
||||
hashBuf = PORT_Alloc(bufLen);
|
||||
if (!hashBuf) {
|
||||
return SECFailure;
|
||||
}
|
||||
}
|
||||
|
||||
memcpy(hashBuf, client_rand, SSL3_RANDOM_LENGTH);
|
||||
pBuf = hashBuf + SSL3_RANDOM_LENGTH;
|
||||
memcpy(pBuf, server_rand, SSL3_RANDOM_LENGTH);
|
||||
pBuf += SSL3_RANDOM_LENGTH;
|
||||
memcpy(pBuf, ec_params.data, ec_params.len);
|
||||
pBuf += ec_params.len;
|
||||
pBuf[0] = (PRUint8)(server_ecpoint.len);
|
||||
pBuf += 1;
|
||||
memcpy(pBuf, server_ecpoint.data, server_ecpoint.len);
|
||||
pBuf += server_ecpoint.len;
|
||||
PORT_Assert((unsigned int)(pBuf - hashBuf) == bufLen);
|
||||
|
||||
rv = ssl3_ComputeCommonKeyHash(hashBuf, bufLen, hashes, bypassPKCS11);
|
||||
|
||||
PRINT_BUF(95, (NULL, "ECDHkey hash: ", hashBuf, bufLen));
|
||||
PRINT_BUF(95, (NULL, "ECDHkey hash: MD5 result", hashes->md5, MD5_LENGTH));
|
||||
PRINT_BUF(95, (NULL, "ECDHkey hash: SHA1 result", hashes->sha, SHA1_LENGTH));
|
||||
|
||||
done:
|
||||
if (hashBuf != buf && hashBuf != NULL)
|
||||
PORT_Free(hashBuf);
|
||||
return rv;
|
||||
}
|
||||
|
||||
|
||||
/* Called from ssl3_SendClientKeyExchange(). */
|
||||
SECStatus
|
||||
ssl3_SendECDHClientKeyExchange(sslSocket * ss, SECKEYPublicKey * svrPubKey)
|
||||
{
|
||||
PK11SymKey * pms = NULL;
|
||||
SECStatus rv = SECFailure;
|
||||
PRBool isTLS;
|
||||
CK_MECHANISM_TYPE target;
|
||||
SECKEYPublicKey *pubKey = NULL; /* Ephemeral ECDH key */
|
||||
SECKEYPrivateKey *privKey = NULL; /* Ephemeral ECDH key */
|
||||
CK_EC_KDF_TYPE kdf;
|
||||
|
||||
PORT_Assert( ss->opt.noLocks || ssl_HaveSSL3HandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_HaveXmitBufLock(ss));
|
||||
|
||||
isTLS = (PRBool)(ss->ssl3.pwSpec->version > SSL_LIBRARY_VERSION_3_0);
|
||||
|
||||
/* Generate ephemeral EC keypair */
|
||||
privKey = SECKEY_CreateECPrivateKey(&svrPubKey->u.ec.DEREncodedParams,
|
||||
&pubKey, NULL);
|
||||
if (!privKey || !pubKey) {
|
||||
ssl_MapLowLevelError(SEC_ERROR_KEYGEN_FAIL);
|
||||
rv = SECFailure;
|
||||
goto loser;
|
||||
}
|
||||
PRINT_BUF(50, (ss, "ECDH public value:",
|
||||
pubKey->u.ec.publicValue.data,
|
||||
pubKey->u.ec.publicValue.len));
|
||||
|
||||
if (isTLS) target = CKM_TLS_MASTER_KEY_DERIVE_DH;
|
||||
else target = CKM_SSL3_MASTER_KEY_DERIVE_DH;
|
||||
|
||||
/* If field size is not more than 24 octets, then use SHA-1 hash of result;
|
||||
* otherwise, use result (see section 4.8 of draft-ietf-tls-ecc-03.txt).
|
||||
*/
|
||||
if ((pubKey->u.ec.publicValue.len - 1) / 2 <= 24) {
|
||||
kdf = CKD_SHA1_KDF;
|
||||
} else {
|
||||
kdf = CKD_NULL;
|
||||
}
|
||||
|
||||
/* Determine the PMS */
|
||||
pms = PK11_PubDeriveWithKDF(privKey, svrPubKey, PR_FALSE, NULL, NULL,
|
||||
CKM_ECDH1_DERIVE, target, CKA_DERIVE, 0,
|
||||
kdf, NULL, NULL);
|
||||
|
||||
if (pms == NULL) {
|
||||
ssl_MapLowLevelError(SSL_ERROR_CLIENT_KEY_EXCHANGE_FAILURE);
|
||||
goto loser;
|
||||
}
|
||||
|
||||
SECKEY_DestroyPrivateKey(privKey);
|
||||
privKey = NULL;
|
||||
|
||||
rv = ssl3_InitPendingCipherSpec(ss, pms);
|
||||
PK11_FreeSymKey(pms); pms = NULL;
|
||||
|
||||
if (rv != SECSuccess) {
|
||||
ssl_MapLowLevelError(SSL_ERROR_CLIENT_KEY_EXCHANGE_FAILURE);
|
||||
goto loser;
|
||||
}
|
||||
|
||||
rv = ssl3_AppendHandshakeHeader(ss, client_key_exchange,
|
||||
pubKey->u.ec.publicValue.len + 1);
|
||||
if (rv != SECSuccess) {
|
||||
goto loser; /* err set by ssl3_AppendHandshake* */
|
||||
}
|
||||
|
||||
rv = ssl3_AppendHandshakeVariable(ss,
|
||||
pubKey->u.ec.publicValue.data,
|
||||
pubKey->u.ec.publicValue.len, 1);
|
||||
SECKEY_DestroyPublicKey(pubKey);
|
||||
pubKey = NULL;
|
||||
|
||||
if (rv != SECSuccess) {
|
||||
goto loser; /* err set by ssl3_AppendHandshake* */
|
||||
}
|
||||
|
||||
rv = SECSuccess;
|
||||
|
||||
loser:
|
||||
if(pms) PK11_FreeSymKey(pms);
|
||||
if(privKey) SECKEY_DestroyPrivateKey(privKey);
|
||||
if(pubKey) SECKEY_DestroyPublicKey(pubKey);
|
||||
return rv;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
** Called from ssl3_HandleClientKeyExchange()
|
||||
*/
|
||||
SECStatus
|
||||
ssl3_HandleECDHClientKeyExchange(sslSocket *ss, SSL3Opaque *b,
|
||||
PRUint32 length,
|
||||
SECKEYPublicKey *srvrPubKey,
|
||||
SECKEYPrivateKey *srvrPrivKey)
|
||||
{
|
||||
PK11SymKey * pms;
|
||||
SECStatus rv;
|
||||
SECKEYPublicKey clntPubKey;
|
||||
CK_MECHANISM_TYPE target;
|
||||
PRBool isTLS;
|
||||
CK_EC_KDF_TYPE kdf;
|
||||
|
||||
PORT_Assert( ss->opt.noLocks || ssl_HaveRecvBufLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_HaveSSL3HandshakeLock(ss) );
|
||||
|
||||
clntPubKey.keyType = ecKey;
|
||||
clntPubKey.u.ec.DEREncodedParams.len =
|
||||
srvrPubKey->u.ec.DEREncodedParams.len;
|
||||
clntPubKey.u.ec.DEREncodedParams.data =
|
||||
srvrPubKey->u.ec.DEREncodedParams.data;
|
||||
|
||||
rv = ssl3_ConsumeHandshakeVariable(ss, &clntPubKey.u.ec.publicValue,
|
||||
1, &b, &length);
|
||||
if (rv != SECSuccess) {
|
||||
SEND_ALERT
|
||||
return SECFailure; /* XXX Who sets the error code?? */
|
||||
}
|
||||
|
||||
isTLS = (PRBool)(ss->ssl3.prSpec->version > SSL_LIBRARY_VERSION_3_0);
|
||||
|
||||
if (isTLS) target = CKM_TLS_MASTER_KEY_DERIVE_DH;
|
||||
else target = CKM_SSL3_MASTER_KEY_DERIVE_DH;
|
||||
|
||||
/* If field size is not more than 24 octets, then use SHA-1 hash of result;
|
||||
* otherwise, use result (see section 4.8 of draft-ietf-tls-ecc-03.txt).
|
||||
*/
|
||||
if (srvrPubKey->u.ec.size <= 24 * 8) {
|
||||
kdf = CKD_SHA1_KDF;
|
||||
} else {
|
||||
kdf = CKD_NULL;
|
||||
}
|
||||
|
||||
/* Determine the PMS */
|
||||
pms = PK11_PubDeriveWithKDF(srvrPrivKey, &clntPubKey, PR_FALSE, NULL, NULL,
|
||||
CKM_ECDH1_DERIVE, target, CKA_DERIVE, 0,
|
||||
kdf, NULL, NULL);
|
||||
|
||||
PORT_Free(clntPubKey.u.ec.publicValue.data);
|
||||
|
||||
if (pms == NULL) {
|
||||
/* last gasp. */
|
||||
ssl_MapLowLevelError(SSL_ERROR_CLIENT_KEY_EXCHANGE_FAILURE);
|
||||
return SECFailure;
|
||||
}
|
||||
|
||||
rv = ssl3_InitPendingCipherSpec(ss, pms);
|
||||
PK11_FreeSymKey(pms);
|
||||
if (rv != SECSuccess) {
|
||||
SEND_ALERT
|
||||
return SECFailure; /* error code set by ssl3_InitPendingCipherSpec */
|
||||
}
|
||||
return SECSuccess;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Creates the ephemeral public and private ECDH keys used by
|
||||
* server in ECDHE_RSA and ECDHE_ECDSA handshakes.
|
||||
* XXX For now, the elliptic curve is hardcoded to NIST P-224.
|
||||
* We need an API to specify the curve. This won't be a real
|
||||
* issue until we further develop server-side support for ECC
|
||||
* cipher suites.
|
||||
*/
|
||||
SECStatus
|
||||
ssl3_CreateECDHEphemeralKeys(sslSocket *ss)
|
||||
{
|
||||
SECStatus rv = SECSuccess;
|
||||
SECKEYPrivateKey * privKey;
|
||||
SECKEYPublicKey * pubKey;
|
||||
SECKEYECParams ecParams = { siBuffer, NULL, 0 };
|
||||
|
||||
if (ss->ephemeralECDHKeyPair)
|
||||
ssl3_FreeKeyPair(ss->ephemeralECDHKeyPair);
|
||||
ss->ephemeralECDHKeyPair = NULL;
|
||||
|
||||
if (ecName2params(NULL, ec_secp224r1, &ecParams) == SECFailure)
|
||||
return SECFailure;
|
||||
privKey = SECKEY_CreateECPrivateKey(&ecParams, &pubKey, NULL);
|
||||
if (!privKey || !pubKey ||
|
||||
!(ss->ephemeralECDHKeyPair = ssl3_NewKeyPair(privKey, pubKey))) {
|
||||
ssl_MapLowLevelError(SEC_ERROR_KEYGEN_FAIL);
|
||||
rv = SECFailure;
|
||||
}
|
||||
|
||||
PORT_Free(ecParams.data);
|
||||
return rv;
|
||||
}
|
||||
|
||||
SECStatus
|
||||
ssl3_HandleECDHServerKeyExchange(sslSocket *ss, SSL3Opaque *b, PRUint32 length)
|
||||
{
|
||||
PRArenaPool * arena = NULL;
|
||||
SECKEYPublicKey *peerKey = NULL;
|
||||
PRBool isTLS;
|
||||
SECStatus rv;
|
||||
int errCode = SSL_ERROR_RX_MALFORMED_SERVER_KEY_EXCH;
|
||||
SSL3AlertDescription desc = illegal_parameter;
|
||||
SSL3Hashes hashes;
|
||||
SECItem signature = {siBuffer, NULL, 0};
|
||||
|
||||
SECItem ec_params = {siBuffer, NULL, 0};
|
||||
SECItem ec_point = {siBuffer, NULL, 0};
|
||||
unsigned char paramBuf[2];
|
||||
|
||||
isTLS = (PRBool)(ss->ssl3.prSpec->version > SSL_LIBRARY_VERSION_3_0);
|
||||
|
||||
/* XXX This works only for named curves, revisit this when
|
||||
* we support generic curves.
|
||||
*/
|
||||
ec_params.len = 2;
|
||||
ec_params.data = paramBuf;
|
||||
rv = ssl3_ConsumeHandshake(ss, ec_params.data, ec_params.len,
|
||||
&b, &length);
|
||||
if (rv != SECSuccess) {
|
||||
goto loser; /* malformed. */
|
||||
}
|
||||
|
||||
/* Fail if the curve is not a named curve */
|
||||
if ((ec_params.data[0] != ec_type_named) ||
|
||||
!supportedCurve(ec_params.data[1])) {
|
||||
errCode = SEC_ERROR_UNSUPPORTED_ELLIPTIC_CURVE;
|
||||
desc = handshake_failure;
|
||||
goto alert_loser;
|
||||
}
|
||||
|
||||
rv = ssl3_ConsumeHandshakeVariable(ss, &ec_point, 1, &b, &length);
|
||||
if (rv != SECSuccess) {
|
||||
goto loser; /* malformed. */
|
||||
}
|
||||
/* Fail if the ec point uses compressed representation */
|
||||
if (ec_point.data[0] != EC_POINT_FORM_UNCOMPRESSED) {
|
||||
errCode = SEC_ERROR_UNSUPPORTED_EC_POINT_FORM;
|
||||
desc = handshake_failure;
|
||||
goto alert_loser;
|
||||
}
|
||||
|
||||
rv = ssl3_ConsumeHandshakeVariable(ss, &signature, 2, &b, &length);
|
||||
if (rv != SECSuccess) {
|
||||
goto loser; /* malformed. */
|
||||
}
|
||||
|
||||
if (length != 0) {
|
||||
if (isTLS)
|
||||
desc = decode_error;
|
||||
goto alert_loser; /* malformed. */
|
||||
}
|
||||
|
||||
PRINT_BUF(60, (NULL, "Server EC params", ec_params.data,
|
||||
ec_params.len));
|
||||
PRINT_BUF(60, (NULL, "Server EC point", ec_point.data, ec_point.len));
|
||||
|
||||
/* failures after this point are not malformed handshakes. */
|
||||
/* TLS: send decrypt_error if signature failed. */
|
||||
desc = isTLS ? decrypt_error : handshake_failure;
|
||||
|
||||
/*
|
||||
* check to make sure the hash is signed by right guy
|
||||
*/
|
||||
rv = ssl3_ComputeECDHKeyHash(ec_params, ec_point,
|
||||
&ss->ssl3.hs.client_random,
|
||||
&ss->ssl3.hs.server_random,
|
||||
&hashes, ss->opt.bypassPKCS11);
|
||||
|
||||
if (rv != SECSuccess) {
|
||||
errCode =
|
||||
ssl_MapLowLevelError(SSL_ERROR_SERVER_KEY_EXCHANGE_FAILURE);
|
||||
goto alert_loser;
|
||||
}
|
||||
rv = ssl3_VerifySignedHashes(&hashes, ss->sec.peerCert, &signature,
|
||||
isTLS, ss->pkcs11PinArg);
|
||||
if (rv != SECSuccess) {
|
||||
errCode =
|
||||
ssl_MapLowLevelError(SSL_ERROR_SERVER_KEY_EXCHANGE_FAILURE);
|
||||
goto alert_loser;
|
||||
}
|
||||
|
||||
arena = PORT_NewArena(DER_DEFAULT_CHUNKSIZE);
|
||||
if (arena == NULL) {
|
||||
goto no_memory;
|
||||
}
|
||||
|
||||
ss->sec.peerKey = peerKey = PORT_ArenaZNew(arena, SECKEYPublicKey);
|
||||
if (peerKey == NULL) {
|
||||
goto no_memory;
|
||||
}
|
||||
|
||||
peerKey->arena = arena;
|
||||
peerKey->keyType = ecKey;
|
||||
|
||||
/* set up EC parameters in peerKey */
|
||||
if (ecName2params(arena, ec_params.data[1],
|
||||
&peerKey->u.ec.DEREncodedParams) != SECSuccess) {
|
||||
/* we should never get here since we already
|
||||
* checked that we are dealing with a supported curve
|
||||
*/
|
||||
errCode = SEC_ERROR_UNSUPPORTED_ELLIPTIC_CURVE;
|
||||
goto alert_loser;
|
||||
}
|
||||
|
||||
/* copy publicValue in peerKey */
|
||||
if (SECITEM_CopyItem(arena, &peerKey->u.ec.publicValue, &ec_point))
|
||||
{
|
||||
PORT_FreeArena(arena, PR_FALSE);
|
||||
goto no_memory;
|
||||
}
|
||||
peerKey->pkcs11Slot = NULL;
|
||||
peerKey->pkcs11ID = CK_INVALID_HANDLE;
|
||||
|
||||
ss->sec.peerKey = peerKey;
|
||||
ss->ssl3.hs.ws = wait_cert_request;
|
||||
|
||||
return SECSuccess;
|
||||
|
||||
alert_loser:
|
||||
(void)SSL3_SendAlert(ss, alert_fatal, desc);
|
||||
loser:
|
||||
PORT_SetError( errCode );
|
||||
return SECFailure;
|
||||
|
||||
no_memory: /* no-memory error has already been set. */
|
||||
ssl_MapLowLevelError(SSL_ERROR_SERVER_KEY_EXCHANGE_FAILURE);
|
||||
return SECFailure;
|
||||
}
|
||||
|
||||
SECStatus
|
||||
ssl3_SendECDHServerKeyExchange(sslSocket *ss)
|
||||
{
|
||||
const ssl3KEADef * kea_def = ss->ssl3.hs.kea_def;
|
||||
SECStatus rv = SECFailure;
|
||||
int length;
|
||||
PRBool isTLS;
|
||||
SECItem signed_hash = {siBuffer, NULL, 0};
|
||||
SSL3Hashes hashes;
|
||||
|
||||
SECKEYPublicKey * ecdhePub;
|
||||
SECItem ec_params = {siBuffer, NULL, 0};
|
||||
ECName curve;
|
||||
SSL3KEAType certIndex;
|
||||
|
||||
|
||||
/* Generate ephemeral ECDH key pair and send the public key */
|
||||
rv = ssl3_CreateECDHEphemeralKeys(ss);
|
||||
if (rv != SECSuccess) {
|
||||
goto loser; /* err set by AppendHandshake. */
|
||||
}
|
||||
ecdhePub = ss->ephemeralECDHKeyPair->pubKey;
|
||||
PORT_Assert(ecdhePub != NULL);
|
||||
if (!ecdhePub) {
|
||||
PORT_SetError(SSL_ERROR_SERVER_KEY_EXCHANGE_FAILURE);
|
||||
return SECFailure;
|
||||
}
|
||||
|
||||
ec_params.len = 2;
|
||||
ec_params.data = (unsigned char*)PORT_Alloc(ec_params.len);
|
||||
curve = params2ecName(&ecdhePub->u.ec.DEREncodedParams);
|
||||
if (curve != ec_noName) {
|
||||
ec_params.data[0] = ec_type_named;
|
||||
ec_params.data[1] = curve;
|
||||
} else {
|
||||
PORT_SetError(SEC_ERROR_UNSUPPORTED_ELLIPTIC_CURVE);
|
||||
goto loser;
|
||||
}
|
||||
|
||||
rv = ssl3_ComputeECDHKeyHash(ec_params, ecdhePub->u.ec.publicValue,
|
||||
&ss->ssl3.hs.client_random,
|
||||
&ss->ssl3.hs.server_random,
|
||||
&hashes, ss->opt.bypassPKCS11);
|
||||
if (rv != SECSuccess) {
|
||||
ssl_MapLowLevelError(SSL_ERROR_SERVER_KEY_EXCHANGE_FAILURE);
|
||||
goto loser;
|
||||
}
|
||||
|
||||
isTLS = (PRBool)(ss->ssl3.pwSpec->version > SSL_LIBRARY_VERSION_3_0);
|
||||
|
||||
/* XXX SSLKEAType isn't really a good choice for
|
||||
* indexing certificates but that's all we have
|
||||
* for now.
|
||||
*/
|
||||
if (kea_def->kea == kea_ecdhe_rsa)
|
||||
certIndex = kt_rsa;
|
||||
else /* kea_def->kea == kea_ecdhe_ecdsa */
|
||||
certIndex = kt_ecdh;
|
||||
|
||||
rv = ssl3_SignHashes(&hashes, ss->serverCerts[certIndex].SERVERKEY,
|
||||
&signed_hash, isTLS);
|
||||
if (rv != SECSuccess) {
|
||||
goto loser; /* ssl3_SignHashes has set err. */
|
||||
}
|
||||
if (signed_hash.data == NULL) {
|
||||
/* how can this happen and rv == SECSuccess ?? */
|
||||
PORT_SetError(SSL_ERROR_SERVER_KEY_EXCHANGE_FAILURE);
|
||||
goto loser;
|
||||
}
|
||||
|
||||
length = ec_params.len +
|
||||
1 + ecdhePub->u.ec.publicValue.len +
|
||||
2 + signed_hash.len;
|
||||
|
||||
rv = ssl3_AppendHandshakeHeader(ss, server_key_exchange, length);
|
||||
if (rv != SECSuccess) {
|
||||
goto loser; /* err set by AppendHandshake. */
|
||||
}
|
||||
|
||||
rv = ssl3_AppendHandshake(ss, ec_params.data, ec_params.len);
|
||||
if (rv != SECSuccess) {
|
||||
goto loser; /* err set by AppendHandshake. */
|
||||
}
|
||||
|
||||
rv = ssl3_AppendHandshakeVariable(ss, ecdhePub->u.ec.publicValue.data,
|
||||
ecdhePub->u.ec.publicValue.len, 1);
|
||||
if (rv != SECSuccess) {
|
||||
goto loser; /* err set by AppendHandshake. */
|
||||
}
|
||||
|
||||
rv = ssl3_AppendHandshakeVariable(ss, signed_hash.data,
|
||||
signed_hash.len, 2);
|
||||
if (rv != SECSuccess) {
|
||||
goto loser; /* err set by AppendHandshake. */
|
||||
}
|
||||
|
||||
PORT_Free(ec_params.data);
|
||||
PORT_Free(signed_hash.data);
|
||||
return SECSuccess;
|
||||
|
||||
loser:
|
||||
if (ec_params.data != NULL)
|
||||
PORT_Free(ec_params.data);
|
||||
if (signed_hash.data != NULL)
|
||||
PORT_Free(signed_hash.data);
|
||||
return SECFailure;
|
||||
}
|
||||
|
||||
|
||||
#endif /* NSS_ENABLE_ECC */
|
||||
|
|
@ -36,7 +36,7 @@
|
|||
* the terms of any one of the MPL, the GPL or the LGPL.
|
||||
*
|
||||
* ***** END LICENSE BLOCK ***** */
|
||||
/* $Id: ssl3gthr.c,v 1.6 2004/04/27 23:04:39 gerv%gerv.net Exp $ */
|
||||
/* $Id: ssl3gthr.c,v 1.7 2005/09/09 03:02:16 nelsonb%netscape.com Exp $ */
|
||||
|
||||
#include "cert.h"
|
||||
#include "ssl.h"
|
||||
|
@ -72,7 +72,7 @@ ssl3_GatherData(sslSocket *ss, sslGather *gs, int flags)
|
|||
int err;
|
||||
int rv = 1;
|
||||
|
||||
PORT_Assert( ssl_HaveRecvBufLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_HaveRecvBufLock(ss) );
|
||||
if (gs->state == GS_INIT) {
|
||||
gs->state = GS_HEADER;
|
||||
gs->remainder = 5;
|
||||
|
@ -189,7 +189,7 @@ ssl3_GatherCompleteHandshake(sslSocket *ss, int flags)
|
|||
SSL3Ciphertext cText;
|
||||
int rv;
|
||||
|
||||
PORT_Assert( ssl_HaveRecvBufLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_HaveRecvBufLock(ss) );
|
||||
do {
|
||||
/* bring in the next sslv3 record. */
|
||||
rv = ssl3_GatherData(ss, &ss->gs, flags);
|
||||
|
@ -207,7 +207,7 @@ ssl3_GatherCompleteHandshake(sslSocket *ss, int flags)
|
|||
if (rv < 0) {
|
||||
return ss->recvdCloseNotify ? 0 : rv;
|
||||
}
|
||||
} while (ss->ssl3->hs.ws != idle_handshake && ss->gs.buf.len == 0);
|
||||
} while (ss->ssl3.hs.ws != idle_handshake && ss->gs.buf.len == 0);
|
||||
|
||||
ss->gs.readOffset = 0;
|
||||
ss->gs.writeOffset = ss->gs.buf.len;
|
||||
|
@ -230,7 +230,7 @@ ssl3_GatherAppDataRecord(sslSocket *ss, int flags)
|
|||
{
|
||||
int rv;
|
||||
|
||||
PORT_Assert( ssl_HaveRecvBufLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_HaveRecvBufLock(ss) );
|
||||
do {
|
||||
rv = ssl3_GatherCompleteHandshake(ss, flags);
|
||||
} while (rv > 0 && ss->gs.buf.len == 0);
|
||||
|
|
|
@ -33,7 +33,7 @@
|
|||
* the terms of any one of the MPL, the GPL or the LGPL.
|
||||
*
|
||||
* ***** END LICENSE BLOCK ***** */
|
||||
/* $Id: sslauth.c,v 1.14 2005/08/16 03:42:26 nelsonb%netscape.com Exp $ */
|
||||
/* $Id: sslauth.c,v 1.15 2005/09/09 03:02:16 nelsonb%netscape.com Exp $ */
|
||||
#include "cert.h"
|
||||
#include "secitem.h"
|
||||
#include "ssl.h"
|
||||
|
@ -53,7 +53,7 @@ SSL_PeerCertificate(PRFileDesc *fd)
|
|||
SSL_GETPID(), fd));
|
||||
return 0;
|
||||
}
|
||||
if (ss->useSecurity && ss->sec.peerCert) {
|
||||
if (ss->opt.useSecurity && ss->sec.peerCert) {
|
||||
return CERT_DupCertificate(ss->sec.peerCert);
|
||||
}
|
||||
return 0;
|
||||
|
@ -71,7 +71,7 @@ SSL_LocalCertificate(PRFileDesc *fd)
|
|||
SSL_GETPID(), fd));
|
||||
return NULL;
|
||||
}
|
||||
if (ss->useSecurity) {
|
||||
if (ss->opt.useSecurity) {
|
||||
if (ss->sec.localCert) {
|
||||
return CERT_DupCertificate(ss->sec.localCert);
|
||||
}
|
||||
|
@ -109,7 +109,7 @@ SSL_SecurityStatus(PRFileDesc *fd, int *op, char **cp, int *kp0, int *kp1,
|
|||
*op = SSL_SECURITY_STATUS_OFF;
|
||||
}
|
||||
|
||||
if (ss->useSecurity && ss->firstHsDone) {
|
||||
if (ss->opt.useSecurity && ss->firstHsDone) {
|
||||
|
||||
if (ss->version < SSL_LIBRARY_VERSION_3_0) {
|
||||
cipherName = ssl_cipherName[ss->sec.cipherType];
|
||||
|
|
|
@ -37,7 +37,7 @@
|
|||
* the terms of any one of the MPL, the GPL or the LGPL.
|
||||
*
|
||||
* ***** END LICENSE BLOCK ***** */
|
||||
/* $Id: sslcon.c,v 1.27 2005/08/16 03:42:26 nelsonb%netscape.com Exp $ */
|
||||
/* $Id: sslcon.c,v 1.28 2005/09/09 03:02:16 nelsonb%netscape.com Exp $ */
|
||||
|
||||
#include "nssrenam.h"
|
||||
#include "cert.h"
|
||||
|
@ -186,11 +186,11 @@ ssl2_ConstructCipherSpecs(sslSocket *ss)
|
|||
int i;
|
||||
SECStatus rv;
|
||||
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
|
||||
count = 0;
|
||||
PORT_Assert(ss != 0);
|
||||
allowed = !ss->enableSSL2 ? 0 :
|
||||
allowed = !ss->opt.enableSSL2 ? 0 :
|
||||
(ss->allowedByPolicy & ss->chosenPreference & SSL_CB_IMPLEMENTED);
|
||||
while (allowed) {
|
||||
if (allowed & 1)
|
||||
|
@ -226,7 +226,7 @@ ssl2_ConstructCipherSpecs(sslSocket *ss)
|
|||
ss->sizeCipherSpecs = count * 3;
|
||||
|
||||
/* fill in cipher specs for SSL2 cipher suites */
|
||||
allowed = !ss->enableSSL2 ? 0 :
|
||||
allowed = !ss->opt.enableSSL2 ? 0 :
|
||||
(ss->allowedByPolicy & ss->chosenPreference & SSL_CB_IMPLEMENTED);
|
||||
for (i = 0; i < ssl2_NUM_SUITES_IMPLEMENTED * 3; i += 3) {
|
||||
const PRUint8 * hs = implementedCipherSuites + i;
|
||||
|
@ -271,17 +271,17 @@ ssl2_CheckConfigSanity(sslSocket *ss)
|
|||
|
||||
allowed = ss->allowedByPolicy & ss->chosenPreference;
|
||||
if (! allowed)
|
||||
ss->enableSSL2 = PR_FALSE; /* not really enabled if no ciphers */
|
||||
ss->opt.enableSSL2 = PR_FALSE; /* not really enabled if no ciphers */
|
||||
|
||||
/* ssl3_config_match_init was called in ssl2_ConstructCipherSpecs(). */
|
||||
/* Ask how many ssl3 CipherSuites were enabled. */
|
||||
rv = ssl3_ConstructV2CipherSpecsHack(ss, NULL, &ssl3CipherCount);
|
||||
if (rv != SECSuccess || ssl3CipherCount <= 0) {
|
||||
ss->enableSSL3 = PR_FALSE; /* not really enabled if no ciphers */
|
||||
ss->enableTLS = PR_FALSE;
|
||||
ss->opt.enableSSL3 = PR_FALSE; /* not really enabled if no ciphers */
|
||||
ss->opt.enableTLS = PR_FALSE;
|
||||
}
|
||||
|
||||
if (!ss->enableSSL2 && !ss->enableSSL3 && !ss->enableTLS) {
|
||||
if (!ss->opt.enableSSL2 && !ss->opt.enableSSL3 && !ss->opt.enableTLS) {
|
||||
SSL_DBG(("%d: SSL[%d]: Can't handshake! both v2 and v3 disabled.",
|
||||
SSL_GETPID(), ss->fd));
|
||||
disabled:
|
||||
|
@ -495,7 +495,7 @@ ssl2_GetSendBuffer(sslSocket *ss, unsigned int len)
|
|||
{
|
||||
SECStatus rv = SECSuccess;
|
||||
|
||||
PORT_Assert(ssl_HaveXmitBufLock(ss));
|
||||
PORT_Assert(ss->opt.noLocks || ssl_HaveXmitBufLock(ss));
|
||||
|
||||
if (len < 128) {
|
||||
len = 128;
|
||||
|
@ -530,7 +530,7 @@ ssl2_SendErrorMessage(sslSocket *ss, int error)
|
|||
int rv;
|
||||
PRUint8 msg[SSL_HL_ERROR_HBYTES];
|
||||
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
|
||||
msg[0] = SSL_MT_ERROR;
|
||||
msg[1] = MSB(error);
|
||||
|
@ -559,7 +559,7 @@ ssl2_SendClientFinishedMessage(sslSocket *ss)
|
|||
int sent;
|
||||
PRUint8 msg[1 + SSL_CONNECTIONID_BYTES];
|
||||
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
|
||||
ssl_GetXmitBufLock(ss); /***************************************/
|
||||
|
||||
|
@ -595,7 +595,7 @@ ssl2_SendServerVerifyMessage(sslSocket *ss)
|
|||
int sent;
|
||||
SECStatus rv;
|
||||
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
|
||||
ssl_GetXmitBufLock(ss); /***************************************/
|
||||
|
||||
|
@ -630,7 +630,7 @@ ssl2_SendServerFinishedMessage(sslSocket *ss)
|
|||
int sendLen, sent;
|
||||
SECStatus rv = SECSuccess;
|
||||
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
|
||||
ssl_GetXmitBufLock(ss); /***************************************/
|
||||
|
||||
|
@ -660,7 +660,7 @@ ssl2_SendServerFinishedMessage(sslSocket *ss)
|
|||
/* If send failed, it is now a bogus session-id */
|
||||
(*ss->sec.uncache)(sid);
|
||||
rv = (SECStatus)sent;
|
||||
} else if (!ss->noCache) {
|
||||
} else if (!ss->opt.noCache) {
|
||||
/* Put the sid in session-id cache, (may already be there) */
|
||||
(*ss->sec.cache)(sid);
|
||||
rv = SECSuccess;
|
||||
|
@ -689,7 +689,7 @@ ssl2_SendSessionKeyMessage(sslSocket *ss, int cipher, int keySize,
|
|||
int sent;
|
||||
SECStatus rv;
|
||||
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
|
||||
ssl_GetXmitBufLock(ss); /***************************************/
|
||||
|
||||
|
@ -735,7 +735,7 @@ ssl2_SendCertificateRequestMessage(sslSocket *ss)
|
|||
int sendLen;
|
||||
SECStatus rv;
|
||||
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
|
||||
ssl_GetXmitBufLock(ss); /***************************************/
|
||||
|
||||
|
@ -775,7 +775,7 @@ ssl2_SendCertificateResponseMessage(sslSocket *ss, SECItem *cert,
|
|||
PRUint8 *msg;
|
||||
int rv, sendLen;
|
||||
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
|
||||
ssl_GetXmitBufLock(ss); /***************************************/
|
||||
|
||||
|
@ -887,7 +887,7 @@ ssl2_SendClear(sslSocket *ss, const PRUint8 *in, PRInt32 len, PRInt32 flags)
|
|||
int amount;
|
||||
int count = 0;
|
||||
|
||||
PORT_Assert( ssl_HaveXmitBufLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_HaveXmitBufLock(ss) );
|
||||
|
||||
SSL_TRC(10, ("%d: SSL[%d]: sending %d bytes in the clear",
|
||||
SSL_GETPID(), ss->fd, len));
|
||||
|
@ -962,7 +962,7 @@ ssl2_SendStream(sslSocket *ss, const PRUint8 *in, PRInt32 len, PRInt32 flags)
|
|||
int nout;
|
||||
int buflen;
|
||||
|
||||
PORT_Assert( ssl_HaveXmitBufLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_HaveXmitBufLock(ss) );
|
||||
|
||||
SSL_TRC(10, ("%d: SSL[%d]: sending %d bytes using stream cipher",
|
||||
SSL_GETPID(), ss->fd, len));
|
||||
|
@ -1067,7 +1067,7 @@ ssl2_SendBlock(sslSocket *ss, const PRUint8 *in, PRInt32 len, PRInt32 flags)
|
|||
int nout; /* ciphertext size after header. */
|
||||
int buflen; /* size of generated record. */
|
||||
|
||||
PORT_Assert( ssl_HaveXmitBufLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_HaveXmitBufLock(ss) );
|
||||
|
||||
SSL_TRC(10, ("%d: SSL[%d]: sending %d bytes using block cipher",
|
||||
SSL_GETPID(), ss->fd, len));
|
||||
|
@ -1251,7 +1251,7 @@ ssl_GatherRecord1stHandshake(sslSocket *ss)
|
|||
{
|
||||
int rv;
|
||||
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
|
||||
ssl_GetRecvBufLock(ss);
|
||||
|
||||
|
@ -1369,7 +1369,7 @@ ssl2_ProduceKeys(sslSocket * ss,
|
|||
readKey->data = 0;
|
||||
writeKey->data = 0;
|
||||
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
|
||||
rv = SECSuccess;
|
||||
cx = PK11_CreateDigestContext(SEC_OID_MD5);
|
||||
|
@ -1441,7 +1441,7 @@ ssl2_CreateSessionCypher(sslSocket *ss, sslSessionID *sid, PRBool isClient)
|
|||
readKey.data = 0;
|
||||
writeKey.data = 0;
|
||||
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
if((ss->sec.ci.sid == 0))
|
||||
goto sec_loser; /* don't crash if asserts are off */
|
||||
|
||||
|
@ -1591,9 +1591,9 @@ ssl2_ServerSetupSessionCypher(sslSocket *ss, int cipher, unsigned int keyBits,
|
|||
PRUint8 mkbuf[SSL_MAX_MASTER_KEY_BYTES];
|
||||
sslServerCerts * sc = ss->serverCerts + kt_rsa;
|
||||
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ssl_HaveRecvBufLock(ss) );
|
||||
PORT_Assert((sc->serverKey != 0));
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_HaveRecvBufLock(ss) );
|
||||
PORT_Assert((sc->SERVERKEY != 0));
|
||||
PORT_Assert((ss->sec.ci.sid != 0));
|
||||
sid = ss->sec.ci.sid;
|
||||
|
||||
|
@ -1651,11 +1651,11 @@ ssl2_ServerSetupSessionCypher(sslSocket *ss, int cipher, unsigned int keyBits,
|
|||
** NOTE: PK11_PubDecryptRaw will barf on a non-RSA key. This is
|
||||
** desired behavior here.
|
||||
*/
|
||||
rv = PK11_PubDecryptRaw(sc->serverKey, kbuf, &el1, ekLen, ek, ekLen);
|
||||
rv = PK11_PubDecryptRaw(sc->SERVERKEY, kbuf, &el1, ekLen, ek, ekLen);
|
||||
if (rv != SECSuccess)
|
||||
goto hide_loser;
|
||||
|
||||
modulusLen = PK11_GetPrivateModulusLen(sc->serverKey);
|
||||
modulusLen = PK11_GetPrivateModulusLen(sc->SERVERKEY);
|
||||
if (modulusLen == -1) {
|
||||
/* If the key was really bad, then PK11_pubDecryptRaw
|
||||
* would have failed, therefore the we must assume that the card
|
||||
|
@ -1679,7 +1679,7 @@ ssl2_ServerSetupSessionCypher(sslSocket *ss, int cipher, unsigned int keyBits,
|
|||
}
|
||||
|
||||
/* Make sure we're not subject to a version rollback attack. */
|
||||
if (ss->enableSSL3 || ss->enableTLS) {
|
||||
if (ss->opt.enableSSL3 || ss->opt.enableTLS) {
|
||||
PRUint8 threes[8] = { 0x03, 0x03, 0x03, 0x03,
|
||||
0x03, 0x03, 0x03, 0x03 };
|
||||
|
||||
|
@ -1763,8 +1763,8 @@ ssl2_QualifyCypherSpecs(sslSocket *ss,
|
|||
int hc;
|
||||
PRUint8 qualifiedSpecs[ssl2_NUM_SUITES_IMPLEMENTED * 3];
|
||||
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ssl_HaveRecvBufLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_HaveRecvBufLock(ss) );
|
||||
|
||||
if (!ss->cipherSpecs) {
|
||||
ssl2_ConstructCipherSpecs(ss);
|
||||
|
@ -1824,8 +1824,8 @@ ssl2_ChooseSessionCypher(sslSocket *ss,
|
|||
int realKeySize;
|
||||
PRUint8 * ohs = hs;
|
||||
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ssl_HaveRecvBufLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_HaveRecvBufLock(ss) );
|
||||
|
||||
if (!ss->cipherSpecs) {
|
||||
ssl2_ConstructCipherSpecs(ss);
|
||||
|
@ -2044,7 +2044,7 @@ ssl2_ClientSetupSessionCypher(sslSocket *ss, PRUint8 *cs, int csLen)
|
|||
PRUint8 keyData[SSL_MAX_MASTER_KEY_BYTES];
|
||||
PRUint8 iv [8];
|
||||
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
|
||||
eblock = NULL;
|
||||
|
||||
|
@ -2131,7 +2131,7 @@ ssl2_ClientSetupSessionCypher(sslSocket *ss, PRUint8 *cs, int csLen)
|
|||
|
||||
/* Set up the padding for version 2 rollback detection. */
|
||||
/* XXX We should really use defines here */
|
||||
if (ss->enableSSL3 || ss->enableTLS) {
|
||||
if (ss->opt.enableSSL3 || ss->opt.enableTLS) {
|
||||
PORT_Assert((modulusLen - rek.len) > 12);
|
||||
PORT_Memset(eblock + modulusLen - rek.len - 8 - 1, 0x03, 8);
|
||||
}
|
||||
|
@ -2185,7 +2185,7 @@ ssl2_ClientRegSessionID(sslSocket *ss, PRUint8 *s)
|
|||
sid->peerCert = CERT_DupCertificate(ss->sec.peerCert);
|
||||
|
||||
}
|
||||
if (!ss->noCache)
|
||||
if (!ss->opt.noCache)
|
||||
(*ss->sec.cache)(sid);
|
||||
}
|
||||
|
||||
|
@ -2195,7 +2195,7 @@ ssl2_TriggerNextMessage(sslSocket *ss)
|
|||
{
|
||||
SECStatus rv;
|
||||
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
|
||||
if ((ss->sec.ci.requiredElements & CIS_HAVE_CERTIFICATE) &&
|
||||
!(ss->sec.ci.sentElements & CIS_HAVE_CERTIFICATE)) {
|
||||
|
@ -2223,7 +2223,7 @@ ssl2_TryToFinish(sslSocket *ss)
|
|||
SECStatus rv;
|
||||
char e, ef;
|
||||
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
|
||||
e = ss->sec.ci.elements;
|
||||
ef = e | CIS_HAVE_FINISHED;
|
||||
|
@ -2261,7 +2261,7 @@ ssl2_SignResponse(sslSocket *ss,
|
|||
unsigned int len;
|
||||
SECStatus rv = SECFailure;
|
||||
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
|
||||
challenge = ss->sec.ci.serverChallenge;
|
||||
len = ss->sec.ci.serverChallengeLen;
|
||||
|
@ -2424,8 +2424,8 @@ ssl2_HandleClientCertificate(sslSocket * ss,
|
|||
SECItem certItem;
|
||||
SECItem rep;
|
||||
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ssl_HaveRecvBufLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_HaveRecvBufLock(ss) );
|
||||
|
||||
/* Extract the certificate */
|
||||
certItem.data = cd;
|
||||
|
@ -2512,7 +2512,7 @@ ssl2_HandleMessage(sslSocket *ss)
|
|||
int rv;
|
||||
int rv2;
|
||||
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
|
||||
ssl_GetRecvBufLock(ss);
|
||||
|
||||
|
@ -2706,7 +2706,7 @@ ssl2_HandleVerifyMessage(sslSocket *ss)
|
|||
PRUint8 * data;
|
||||
SECStatus rv;
|
||||
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
ssl_GetRecvBufLock(ss);
|
||||
|
||||
data = ss->gs.buf.buf + ss->gs.recordOffset;
|
||||
|
@ -2758,9 +2758,9 @@ ssl2_HandleServerHelloMessage(sslSocket *ss)
|
|||
SECStatus rv;
|
||||
int needed, sidHit, certLen, csLen, cidLen, certType, err;
|
||||
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
|
||||
if (!ss->enableSSL2) {
|
||||
if (!ss->opt.enableSSL2) {
|
||||
PORT_SetError(SSL_ERROR_SSL2_DISABLED);
|
||||
return SECFailure;
|
||||
}
|
||||
|
@ -2989,7 +2989,7 @@ ssl2_BeginClientHandshake(sslSocket *ss)
|
|||
int sendLen, sidLen = 0;
|
||||
SECStatus rv;
|
||||
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
|
||||
ss->sec.isServer = 0;
|
||||
ss->sec.sendSequence = 0;
|
||||
|
@ -3035,7 +3035,7 @@ ssl2_BeginClientHandshake(sslSocket *ss)
|
|||
SSL_TRC(3, ("%d: SSL[%d]: sending client-hello", SSL_GETPID(), ss->fd));
|
||||
|
||||
/* Try to find server in our session-id cache */
|
||||
if (ss->noCache) {
|
||||
if (ss->opt.noCache) {
|
||||
sid = NULL;
|
||||
} else {
|
||||
sid = ssl_LookupSID(&ss->sec.ci.peer, ss->sec.ci.port, ss->peerID,
|
||||
|
@ -3043,15 +3043,15 @@ ssl2_BeginClientHandshake(sslSocket *ss)
|
|||
}
|
||||
while (sid) { /* this isn't really a loop */
|
||||
/* if we're not doing this SID's protocol any more, drop it. */
|
||||
if (((sid->version < SSL_LIBRARY_VERSION_3_0) && !ss->enableSSL2) ||
|
||||
((sid->version == SSL_LIBRARY_VERSION_3_0) && !ss->enableSSL3) ||
|
||||
((sid->version > SSL_LIBRARY_VERSION_3_0) && !ss->enableTLS)) {
|
||||
if (((sid->version < SSL_LIBRARY_VERSION_3_0) && !ss->opt.enableSSL2) ||
|
||||
((sid->version == SSL_LIBRARY_VERSION_3_0) && !ss->opt.enableSSL3) ||
|
||||
((sid->version > SSL_LIBRARY_VERSION_3_0) && !ss->opt.enableTLS)) {
|
||||
ss->sec.uncache(sid);
|
||||
ssl_FreeSID(sid);
|
||||
sid = NULL;
|
||||
break;
|
||||
}
|
||||
if (ss->enableSSL2 && sid->version < SSL_LIBRARY_VERSION_3_0) {
|
||||
if (ss->opt.enableSSL2 && sid->version < SSL_LIBRARY_VERSION_3_0) {
|
||||
/* If the cipher in this sid is not enabled, drop it. */
|
||||
for (i = 0; i < ss->sizeCipherSpecs; i += 3) {
|
||||
if (ss->cipherSpecs[i] == sid->u.ssl2.cipherType)
|
||||
|
@ -3096,8 +3096,8 @@ ssl2_BeginClientHandshake(sslSocket *ss)
|
|||
|
||||
PORT_Assert(sid != NULL);
|
||||
|
||||
if ((sid->version >= SSL_LIBRARY_VERSION_3_0 || !ss->v2CompatibleHello) &&
|
||||
(ss->enableSSL3 || ss->enableTLS)) {
|
||||
if ((sid->version >= SSL_LIBRARY_VERSION_3_0 || !ss->opt.v2CompatibleHello) &&
|
||||
(ss->opt.enableSSL3 || ss->opt.enableTLS)) {
|
||||
|
||||
ss->gs.state = GS_INIT;
|
||||
ss->handshake = ssl_GatherRecord1stHandshake;
|
||||
|
@ -3138,9 +3138,9 @@ ssl2_BeginClientHandshake(sslSocket *ss)
|
|||
/* Construct client-hello message */
|
||||
cp = msg = ss->sec.ci.sendBuf.buf;
|
||||
msg[0] = SSL_MT_CLIENT_HELLO;
|
||||
if ( ss->enableTLS ) {
|
||||
if ( ss->opt.enableTLS ) {
|
||||
ss->clientHelloVersion = SSL_LIBRARY_VERSION_3_1_TLS;
|
||||
} else if ( ss->enableSSL3 ) {
|
||||
} else if ( ss->opt.enableSSL3 ) {
|
||||
ss->clientHelloVersion = SSL_LIBRARY_VERSION_3_0;
|
||||
} else {
|
||||
ss->clientHelloVersion = SSL_LIBRARY_VERSION_2;
|
||||
|
@ -3441,7 +3441,7 @@ ssl2_HandleClientHelloMessage(sslSocket *ss)
|
|||
#endif
|
||||
PRUint8 csImpl[sizeof implementedCipherSuites];
|
||||
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
|
||||
sc = ss->serverCerts + kt_rsa;
|
||||
serverCert = sc->serverCert;
|
||||
|
@ -3470,7 +3470,7 @@ ssl2_HandleClientHelloMessage(sslSocket *ss)
|
|||
*/
|
||||
if ((data[0] == SSL_MT_CLIENT_HELLO) &&
|
||||
(data[1] >= MSB(SSL_LIBRARY_VERSION_3_0)) &&
|
||||
(ss->enableSSL3 || ss->enableTLS)) {
|
||||
(ss->opt.enableSSL3 || ss->opt.enableTLS)) {
|
||||
rv = ssl3_HandleV2ClientHello(ss, data, ss->gs.recordLen);
|
||||
if (rv != SECFailure) { /* Success */
|
||||
ss->handshake = NULL;
|
||||
|
@ -3558,7 +3558,7 @@ ssl2_HandleClientHelloMessage(sslSocket *ss)
|
|||
goto loser;
|
||||
}
|
||||
/* Since this handhsake is going to fail, don't cache it. */
|
||||
ss->noCache = 1;
|
||||
ss->opt.noCache = 1;
|
||||
}
|
||||
|
||||
/* Squirrel away the challenge for later */
|
||||
|
@ -3566,7 +3566,7 @@ ssl2_HandleClientHelloMessage(sslSocket *ss)
|
|||
|
||||
/* Examine message and see if session-id is good */
|
||||
ss->sec.ci.elements = 0;
|
||||
if (sdLen > 0 && !ss->noCache) {
|
||||
if (sdLen > 0 && !ss->opt.noCache) {
|
||||
SSL_TRC(7, ("%d: SSL[%d]: server, lookup client session-id for 0x%08x%08x%08x%08x",
|
||||
SSL_GETPID(), ss->fd, ss->sec.ci.peer.pr_s6_addr32[0],
|
||||
ss->sec.ci.peer.pr_s6_addr32[1],
|
||||
|
@ -3648,7 +3648,7 @@ ssl2_HandleClientHelloMessage(sslSocket *ss)
|
|||
|
||||
/* Build up final list of required elements */
|
||||
ss->sec.ci.requiredElements = CIS_HAVE_MASTER_KEY | CIS_HAVE_FINISHED;
|
||||
if (ss->requestCertificate) {
|
||||
if (ss->opt.requestCertificate) {
|
||||
ss->sec.ci.requiredElements |= CIS_HAVE_CERTIFICATE;
|
||||
}
|
||||
ss->sec.ci.sentElements = 0;
|
||||
|
@ -3742,8 +3742,8 @@ ssl2_BeginServerHandshake(sslSocket *ss)
|
|||
ss->sec.rcvSequence = 0;
|
||||
|
||||
/* don't turn on SSL2 if we don't have an RSA key and cert */
|
||||
if (!rsaAuth->serverKey || !rsaAuth->serverCert) {
|
||||
ss->enableSSL2 = PR_FALSE;
|
||||
if (!rsaAuth->SERVERKEY || !rsaAuth->serverCert) {
|
||||
ss->opt.enableSSL2 = PR_FALSE;
|
||||
}
|
||||
|
||||
if (!ss->cipherSpecs) {
|
||||
|
|
|
@ -36,7 +36,7 @@
|
|||
* the terms of any one of the MPL, the GPL or the LGPL.
|
||||
*
|
||||
* ***** END LICENSE BLOCK ***** */
|
||||
/* $Id: ssldef.c,v 1.9 2004/04/27 23:04:39 gerv%gerv.net Exp $ */
|
||||
/* $Id: ssldef.c,v 1.10 2005/09/09 03:02:16 nelsonb%netscape.com Exp $ */
|
||||
|
||||
#include "cert.h"
|
||||
#include "ssl.h"
|
||||
|
@ -117,7 +117,7 @@ int ssl_DefSend(sslSocket *ss, const unsigned char *buf, int len, int flags)
|
|||
/* Although this is overkill, we disable Nagle delays completely for
|
||||
** SSL sockets.
|
||||
*/
|
||||
if (ss->useSecurity && !ss->delayDisabled) {
|
||||
if (ss->opt.useSecurity && !ss->delayDisabled) {
|
||||
ssl_EnableNagleDelay(ss, PR_FALSE); /* ignore error */
|
||||
ss->delayDisabled = 1;
|
||||
}
|
||||
|
|
|
@ -36,7 +36,7 @@
|
|||
* the terms of any one of the MPL, the GPL or the LGPL.
|
||||
*
|
||||
* ***** END LICENSE BLOCK ***** */
|
||||
/* $Id: sslgathr.c,v 1.7 2004/04/27 23:04:39 gerv%gerv.net Exp $ */
|
||||
/* $Id: sslgathr.c,v 1.8 2005/09/09 03:02:16 nelsonb%netscape.com Exp $ */
|
||||
#include "cert.h"
|
||||
#include "ssl.h"
|
||||
#include "sslimpl.h"
|
||||
|
@ -90,7 +90,7 @@ ssl2_GatherData(sslSocket *ss, sslGather *gs, int flags)
|
|||
unsigned char * pBuf;
|
||||
int nb, err, rv;
|
||||
|
||||
PORT_Assert( ssl_HaveRecvBufLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_HaveRecvBufLock(ss) );
|
||||
|
||||
if (gs->state == GS_INIT) {
|
||||
/* Initialize gathering engine */
|
||||
|
@ -141,9 +141,9 @@ ssl2_GatherData(sslSocket *ss, sslGather *gs, int flags)
|
|||
/* Probably finished this piece */
|
||||
switch (gs->state) {
|
||||
case GS_HEADER:
|
||||
if ((ss->enableSSL3 || ss->enableTLS) && !ss->firstHsDone) {
|
||||
if ((ss->opt.enableSSL3 || ss->opt.enableTLS) && !ss->firstHsDone) {
|
||||
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
|
||||
/* If this looks like an SSL3 handshake record,
|
||||
** and we're expecting an SSL2 Hello message from our peer,
|
||||
|
@ -185,7 +185,7 @@ ssl2_GatherData(sslSocket *ss, sslGather *gs, int flags)
|
|||
return SECFailure;
|
||||
}
|
||||
}
|
||||
} /* ((ss->enableSSL3 || ss->enableTLS) && !ss->firstHsDone) */
|
||||
} /* ((ss->opt.enableSSL3 || ss->opt.enableTLS) && !ss->firstHsDone) */
|
||||
|
||||
/* we've got the first 3 bytes. The header may be two or three. */
|
||||
if (gs->hdr[0] & 0x80) {
|
||||
|
@ -411,7 +411,7 @@ ssl2_StartGatherBytes(sslSocket *ss, sslGather *gs, unsigned int count)
|
|||
{
|
||||
int rv;
|
||||
|
||||
PORT_Assert( ssl_HaveRecvBufLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_HaveRecvBufLock(ss) );
|
||||
gs->state = GS_DATA;
|
||||
gs->remainder = count;
|
||||
gs->count = count;
|
||||
|
@ -455,8 +455,8 @@ ssl2_HandleV3HandshakeRecord(sslSocket *ss)
|
|||
SECStatus rv;
|
||||
SSL3ProtocolVersion version = (ss->gs.hdr[1] << 8) | ss->gs.hdr[2];
|
||||
|
||||
PORT_Assert( ssl_HaveRecvBufLock(ss) );
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_HaveRecvBufLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
|
||||
/* We've read in 3 bytes, there are 2 more to go in an ssl3 header. */
|
||||
ss->gs.remainder = 2;
|
||||
|
|
|
@ -39,7 +39,7 @@
|
|||
* the terms of any one of the MPL, the GPL or the LGPL.
|
||||
*
|
||||
* ***** END LICENSE BLOCK ***** */
|
||||
/* $Id: sslimpl.h,v 1.39 2005/08/16 03:42:26 nelsonb%netscape.com Exp $ */
|
||||
/* $Id: sslimpl.h,v 1.40 2005/09/09 03:02:16 nelsonb%netscape.com Exp $ */
|
||||
|
||||
#ifndef __sslimpl_h_
|
||||
#define __sslimpl_h_
|
||||
|
@ -93,6 +93,10 @@ typedef SSLSignType SSL3SignType;
|
|||
#define hmac_md5 ssl_hmac_md5
|
||||
#define hmac_sha ssl_hmac_sha
|
||||
|
||||
#define SET_ERROR_CODE /* reminder */
|
||||
#define SEND_ALERT /* reminder */
|
||||
#define TEST_FOR_FAILURE /* reminder */
|
||||
#define DEAL_WITH_FAILURE /* reminder */
|
||||
|
||||
#if defined(DEBUG) || defined(TRACE)
|
||||
#ifdef __cplusplus
|
||||
|
@ -162,12 +166,17 @@ typedef enum { SSLAppOpRead = 0,
|
|||
|
||||
#define SSL_MAX_MAC_BYTES 16
|
||||
|
||||
#define SSL3_RSA_PMS_LENGTH 48
|
||||
#define SSL3_MASTER_SECRET_LENGTH 48
|
||||
|
||||
/* number of wrap mechanisms potentially used to wrap master secrets. */
|
||||
#define SSL_NUM_WRAP_MECHS 13
|
||||
|
||||
/* This makes the cert cache entry exactly 4k. */
|
||||
#define SSL_MAX_CACHED_CERT_LEN 4060
|
||||
|
||||
#define NUM_MIXERS 9
|
||||
|
||||
#ifndef BPB
|
||||
#define BPB 8 /* Bits Per Byte */
|
||||
#endif
|
||||
|
@ -281,6 +290,8 @@ typedef struct sslOptionsStr {
|
|||
unsigned int v2CompatibleHello : 1; /* 13 */
|
||||
unsigned int detectRollBack : 1; /* 14 */
|
||||
unsigned int noStepDown : 1; /* 15 */
|
||||
unsigned int bypassPKCS11 : 1; /* 16 */
|
||||
unsigned int noLocks : 1; /* 17 */
|
||||
} sslOptions;
|
||||
|
||||
typedef enum { sslHandshakingUndetermined = 0,
|
||||
|
@ -292,10 +303,11 @@ typedef struct sslServerCertsStr {
|
|||
/* Configuration state for server sockets */
|
||||
CERTCertificate * serverCert;
|
||||
CERTCertificateList * serverCertChain;
|
||||
SECKEYPrivateKey * serverKey;
|
||||
ssl3KeyPair * serverKeyPair;
|
||||
unsigned int serverKeyBits;
|
||||
} sslServerCerts;
|
||||
|
||||
#define SERVERKEY serverKeyPair->privKey
|
||||
|
||||
#define SSL_LOCK_RANK_SPEC 255
|
||||
#define SSL_LOCK_RANK_GLOBAL NSS_RWLOCK_RANK_NONE
|
||||
|
@ -432,21 +444,31 @@ typedef struct {
|
|||
uint32 low;
|
||||
} SSL3SequenceNumber;
|
||||
|
||||
typedef struct {
|
||||
SSL3Opaque write_iv[MAX_IV_LENGTH];
|
||||
PK11SymKey *write_key;
|
||||
PK11SymKey *write_mac_key;
|
||||
PK11Context *write_mac_context;
|
||||
} ssl3KeyMaterial;
|
||||
#define MAX_MAC_CONTEXT_BYTES 400
|
||||
#define MAX_MAC_CONTEXT_LLONGS (MAX_MAC_CONTEXT_BYTES / 8)
|
||||
|
||||
#define MAX_CIPHER_CONTEXT_BYTES 2080
|
||||
#define MAX_CIPHER_CONTEXT_LLONGS (MAX_CIPHER_CONTEXT_BYTES / 8)
|
||||
|
||||
typedef struct {
|
||||
SSL3Opaque wrapped_client_write_key[12]; /* wrapped with Ks */
|
||||
SSL3Opaque wrapped_server_write_key[12]; /* wrapped with Ks */
|
||||
SSL3Opaque client_write_iv [24];
|
||||
SSL3Opaque server_write_iv [24];
|
||||
SSL3Opaque wrapped_master_secret [48];
|
||||
PRUint16 wrapped_master_secret_len;
|
||||
} ssl3SidKeys;
|
||||
PRUint8 msIsWrapped;
|
||||
PRUint8 resumable;
|
||||
} ssl3SidKeys; /* 100 bytes */
|
||||
|
||||
typedef struct {
|
||||
PK11SymKey *write_key;
|
||||
PK11SymKey *write_mac_key;
|
||||
PK11Context *write_mac_context;
|
||||
SECItem write_key_item;
|
||||
SECItem write_iv_item;
|
||||
SECItem write_mac_key_item;
|
||||
SSL3Opaque write_iv[MAX_IV_LENGTH];
|
||||
PRUint64 cipher_context[MAX_CIPHER_CONTEXT_LLONGS];
|
||||
} ssl3KeyMaterial;
|
||||
|
||||
/*
|
||||
** These are the "specs" in the "ssl3" struct.
|
||||
|
@ -458,16 +480,20 @@ typedef struct {
|
|||
const ssl3MACDef * mac_def;
|
||||
int mac_size;
|
||||
SSLCipher encode;
|
||||
void * encodeContext;
|
||||
SSLCipher decode;
|
||||
void * decodeContext;
|
||||
SSLDestroy destroy;
|
||||
void * encodeContext;
|
||||
void * decodeContext;
|
||||
PRBool bypassCiphers; /* did double bypass (at least) */
|
||||
PK11SymKey * master_secret;
|
||||
ssl3KeyMaterial client;
|
||||
ssl3KeyMaterial server;
|
||||
SSL3SequenceNumber write_seq_num;
|
||||
SSL3SequenceNumber read_seq_num;
|
||||
SSL3ProtocolVersion version;
|
||||
ssl3KeyMaterial client;
|
||||
ssl3KeyMaterial server;
|
||||
SECItem msItem;
|
||||
unsigned char key_block[NUM_MIXERS * MD5_LENGTH];
|
||||
unsigned char raw_master_secret[56];
|
||||
} ssl3CipherSpec;
|
||||
|
||||
typedef enum { never_cached,
|
||||
|
@ -519,7 +545,6 @@ struct sslSessionIDStr {
|
|||
|
||||
ssl3CipherSuite cipherSuite;
|
||||
SSL3CompressionMethod compression;
|
||||
PRBool resumable;
|
||||
int policy;
|
||||
ssl3SidKeys keys;
|
||||
CK_MECHANISM_TYPE masterWrapMech;
|
||||
|
@ -533,7 +558,6 @@ struct sslSessionIDStr {
|
|||
*/
|
||||
PK11SymKey * clientWriteKey;
|
||||
PK11SymKey * serverWriteKey;
|
||||
PK11SymKey * tek;
|
||||
|
||||
/* The following values pertain to the slot that wrapped the
|
||||
** master secret. (used only in client)
|
||||
|
@ -631,6 +655,8 @@ typedef struct SSL3HandshakeStateStr {
|
|||
SSL3Random server_random;
|
||||
SSL3Random client_random;
|
||||
SSL3WaitState ws;
|
||||
PRUint64 md5_cx[MAX_MAC_CONTEXT_LLONGS];
|
||||
PRUint64 sha_cx[MAX_MAC_CONTEXT_LLONGS];
|
||||
PK11Context * md5; /* handshake running hashes */
|
||||
PK11Context * sha;
|
||||
const ssl3KEADef * kea_def;
|
||||
|
@ -673,9 +699,6 @@ struct ssl3StateStr {
|
|||
ssl3CipherSpec * prSpec; /* pending read spec. */
|
||||
ssl3CipherSpec * cwSpec; /* current write spec. */
|
||||
ssl3CipherSpec * pwSpec; /* pending write spec. */
|
||||
ssl3CipherSpec specs[2]; /* one is current, one is pending. */
|
||||
|
||||
SSL3HandshakeState hs;
|
||||
|
||||
CERTCertificate * clientCertificate; /* used by client */
|
||||
SECKEYPrivateKey * clientPrivateKey; /* used by client */
|
||||
|
@ -692,7 +715,9 @@ struct ssl3StateStr {
|
|||
/* chain while we are trying to validate it. */
|
||||
CERTDistNames * ca_list;
|
||||
/* used by server. trusted CAs for this socket. */
|
||||
|
||||
PRBool initialized;
|
||||
SSL3HandshakeState hs;
|
||||
ssl3CipherSpec specs[2]; /* one is current, one is pending. */
|
||||
};
|
||||
|
||||
typedef struct {
|
||||
|
@ -739,7 +764,7 @@ typedef struct SSLWrappedSymWrappingKeyStr {
|
|||
*/
|
||||
|
||||
/*
|
||||
** This is "ci", as in "ss->sec->ci".
|
||||
** This is "ci", as in "ss->sec.ci".
|
||||
**
|
||||
** Protection: All the variables in here are protected by
|
||||
** firstHandshakeLock AND (in ssl3) ssl3HandshakeLock
|
||||
|
@ -861,30 +886,17 @@ struct sslSocketStr {
|
|||
/* Pointer to operations vector for this socket */
|
||||
const sslSocketOps * ops;
|
||||
|
||||
/* SSL socket options */
|
||||
sslOptions opt;
|
||||
|
||||
/* State flags */
|
||||
unsigned int useSocks : 1;
|
||||
unsigned int useSecurity : 1;
|
||||
unsigned int requestCertificate : 1;
|
||||
unsigned int requireCertificate : 2;
|
||||
unsigned int handshakeAsClient : 1;
|
||||
unsigned int handshakeAsServer : 1;
|
||||
unsigned int enableSSL2 : 1;
|
||||
|
||||
unsigned int enableSSL3 : 1;
|
||||
unsigned int enableTLS : 1;
|
||||
unsigned int clientAuthRequested: 1;
|
||||
unsigned int noCache : 1;
|
||||
unsigned int fdx : 1; /* simultaneous R/W threads */
|
||||
unsigned int v2CompatibleHello : 1; /* Send v3+ client hello in v2 format */
|
||||
unsigned int detectRollBack : 1; /* Detect rollback to SSL v3 */
|
||||
unsigned int firstHsDone : 1; /* first handshake is complete. */
|
||||
|
||||
unsigned int recvdCloseNotify : 1; /* received SSL EOF. */
|
||||
unsigned int lastWriteBlocked : 1;
|
||||
unsigned int TCPconnected : 1;
|
||||
unsigned int handshakeBegun : 1;
|
||||
unsigned int delayDisabled : 1; /* Nagle delay disabled */
|
||||
unsigned int noStepDown : 1;
|
||||
unsigned long clientAuthRequested;
|
||||
unsigned long delayDisabled; /* Nagle delay disabled */
|
||||
unsigned long firstHsDone; /* first handshake is complete. */
|
||||
unsigned long handshakeBegun;
|
||||
unsigned long lastWriteBlocked;
|
||||
unsigned long recvdCloseNotify; /* received SSL EOF. */
|
||||
unsigned long TCPconnected;
|
||||
|
||||
/* version of the protocol to use */
|
||||
SSL3ProtocolVersion version;
|
||||
|
@ -895,28 +907,17 @@ struct sslSocketStr {
|
|||
/* protected by firstHandshakeLock AND (in ssl3) ssl3HandshakeLock. */
|
||||
const char *url; /* ssl 2 & 3 */
|
||||
|
||||
/* Gather object used for gathering data */
|
||||
sslGather gs; /*recvBufLock*/
|
||||
|
||||
sslHandshakeFunc handshake; /*firstHandshakeLock*/
|
||||
sslHandshakeFunc nextHandshake; /*firstHandshakeLock*/
|
||||
sslHandshakeFunc securityHandshake; /*firstHandshakeLock*/
|
||||
|
||||
sslBuffer saveBuf; /*xmitBufLock*/
|
||||
sslBuffer pendingBuf; /*xmitBufLock*/
|
||||
|
||||
/* the following variable is only used with socks or other proxies. */
|
||||
char * peerID; /* String uniquely identifies target server. */
|
||||
|
||||
ssl3State * ssl3;
|
||||
unsigned char * cipherSpecs;
|
||||
unsigned int sizeCipherSpecs;
|
||||
const unsigned char * preferredCipher;
|
||||
|
||||
/* Configuration state for server sockets */
|
||||
/* server cert and key for each KEA type */
|
||||
sslServerCerts serverCerts[kt_kea_size];
|
||||
|
||||
ssl3KeyPair * stepDownKeyPair; /* RSA step down keys */
|
||||
|
||||
/* Callbacks */
|
||||
|
@ -971,8 +972,21 @@ const unsigned char * preferredCipher;
|
|||
|
||||
sslHandshakingType handshaking;
|
||||
|
||||
/* Gather object used for gathering data */
|
||||
sslGather gs; /*recvBufLock*/
|
||||
|
||||
sslBuffer saveBuf; /*xmitBufLock*/
|
||||
sslBuffer pendingBuf; /*xmitBufLock*/
|
||||
|
||||
/* Configuration state for server sockets */
|
||||
/* server cert and key for each KEA type */
|
||||
sslServerCerts serverCerts[kt_kea_size];
|
||||
|
||||
ssl3CipherSuiteCfg cipherSuites[ssl_V3_SUITES_IMPLEMENTED];
|
||||
ssl3KeyPair * ephemeralECDHKeyPair; /* for ECDHE-* handshake */
|
||||
|
||||
/* SSL3 state info. Formerly was a pointer */
|
||||
ssl3State ssl3;
|
||||
};
|
||||
|
||||
|
||||
|
@ -1062,7 +1076,7 @@ extern int ssl2_StartGatherBytes(sslSocket *ss, sslGather *gs,
|
|||
|
||||
extern SECStatus ssl_CreateSecurityInfo(sslSocket *ss);
|
||||
extern SECStatus ssl_CopySecurityInfo(sslSocket *ss, sslSocket *os);
|
||||
extern void ssl_ResetSecurityInfo(sslSecurityInfo *sec);
|
||||
extern void ssl_ResetSecurityInfo(sslSecurityInfo *sec, PRBool doMemset);
|
||||
extern void ssl_DestroySecurityInfo(sslSecurityInfo *sec);
|
||||
|
||||
extern sslSocket * ssl_DupSocket(sslSocket *old);
|
||||
|
@ -1099,34 +1113,58 @@ extern void ssl_SetAlwaysBlock(sslSocket *ss);
|
|||
extern SECStatus ssl_EnableNagleDelay(sslSocket *ss, PRBool enabled);
|
||||
|
||||
#define SSL_LOCK_READER(ss) if (ss->recvLock) PZ_Lock(ss->recvLock)
|
||||
#define SSL_UNLOCK_READER(ss) if (ss->recvLock) PZ_Unlock(ss->recvLock)
|
||||
#define SSL_UNLOCK_READER(ss) if (ss->recvLock) PZ_Unlock(ss->recvLock)
|
||||
#define SSL_LOCK_WRITER(ss) if (ss->sendLock) PZ_Lock(ss->sendLock)
|
||||
#define SSL_UNLOCK_WRITER(ss) if (ss->sendLock) PZ_Unlock(ss->sendLock)
|
||||
#define SSL_UNLOCK_WRITER(ss) if (ss->sendLock) PZ_Unlock(ss->sendLock)
|
||||
|
||||
#define ssl_Get1stHandshakeLock(ss) PZ_EnterMonitor((ss)->firstHandshakeLock)
|
||||
#define ssl_Release1stHandshakeLock(ss) PZ_ExitMonitor((ss)->firstHandshakeLock)
|
||||
#define ssl_Have1stHandshakeLock(ss) PZ_InMonitor( (ss)->firstHandshakeLock)
|
||||
#define ssl_Get1stHandshakeLock(ss) \
|
||||
{ if (!ss->opt.noLocks) PZ_EnterMonitor((ss)->firstHandshakeLock); }
|
||||
#define ssl_Release1stHandshakeLock(ss) \
|
||||
{ if (!ss->opt.noLocks) PZ_ExitMonitor((ss)->firstHandshakeLock); }
|
||||
#define ssl_Have1stHandshakeLock(ss) \
|
||||
(PZ_InMonitor((ss)->firstHandshakeLock))
|
||||
|
||||
#define ssl_GetSSL3HandshakeLock(ss) PZ_EnterMonitor((ss)->ssl3HandshakeLock)
|
||||
#define ssl_ReleaseSSL3HandshakeLock(ss) PZ_ExitMonitor((ss)->ssl3HandshakeLock)
|
||||
#define ssl_HaveSSL3HandshakeLock(ss) PZ_InMonitor( (ss)->ssl3HandshakeLock)
|
||||
#define ssl_GetSSL3HandshakeLock(ss) \
|
||||
{ if (!ss->opt.noLocks) PZ_EnterMonitor((ss)->ssl3HandshakeLock); }
|
||||
#define ssl_ReleaseSSL3HandshakeLock(ss) \
|
||||
{ if (!ss->opt.noLocks) PZ_ExitMonitor((ss)->ssl3HandshakeLock); }
|
||||
#define ssl_HaveSSL3HandshakeLock(ss) \
|
||||
(PZ_InMonitor((ss)->ssl3HandshakeLock))
|
||||
|
||||
#define ssl_GetSpecReadLock(ss) NSSRWLock_LockRead( (ss)->specLock)
|
||||
#define ssl_ReleaseSpecReadLock(ss) NSSRWLock_UnlockRead( (ss)->specLock)
|
||||
#define ssl_GetSpecReadLock(ss) \
|
||||
{ if (!ss->opt.noLocks) NSSRWLock_LockRead((ss)->specLock); }
|
||||
#define ssl_ReleaseSpecReadLock(ss) \
|
||||
{ if (!ss->opt.noLocks) NSSRWLock_UnlockRead((ss)->specLock); }
|
||||
|
||||
#define ssl_GetSpecWriteLock(ss) NSSRWLock_LockWrite( (ss)->specLock)
|
||||
#define ssl_ReleaseSpecWriteLock(ss) NSSRWLock_UnlockWrite((ss)->specLock)
|
||||
#define ssl_HaveSpecWriteLock(ss) NSSRWLock_HaveWriteLock((ss)->specLock)
|
||||
#define ssl_GetSpecWriteLock(ss) \
|
||||
{ if (!ss->opt.noLocks) NSSRWLock_LockWrite((ss)->specLock); }
|
||||
#define ssl_ReleaseSpecWriteLock(ss) \
|
||||
{ if (!ss->opt.noLocks) NSSRWLock_UnlockWrite((ss)->specLock); }
|
||||
#define ssl_HaveSpecWriteLock(ss) \
|
||||
(NSSRWLock_HaveWriteLock((ss)->specLock))
|
||||
|
||||
#define ssl_GetRecvBufLock(ss) PZ_EnterMonitor((ss)->recvBufLock)
|
||||
#define ssl_ReleaseRecvBufLock(ss) PZ_ExitMonitor( (ss)->recvBufLock)
|
||||
#define ssl_HaveRecvBufLock(ss) PZ_InMonitor( (ss)->recvBufLock)
|
||||
#define ssl_GetRecvBufLock(ss) \
|
||||
{ if (!ss->opt.noLocks) PZ_EnterMonitor((ss)->recvBufLock); }
|
||||
#define ssl_ReleaseRecvBufLock(ss) \
|
||||
{ if (!ss->opt.noLocks) PZ_ExitMonitor( (ss)->recvBufLock); }
|
||||
#define ssl_HaveRecvBufLock(ss) \
|
||||
(PZ_InMonitor((ss)->recvBufLock))
|
||||
|
||||
#define ssl_GetXmitBufLock(ss) PZ_EnterMonitor((ss)->xmitBufLock)
|
||||
#define ssl_ReleaseXmitBufLock(ss) PZ_ExitMonitor( (ss)->xmitBufLock)
|
||||
#define ssl_HaveXmitBufLock(ss) PZ_InMonitor( (ss)->xmitBufLock)
|
||||
#define ssl_GetXmitBufLock(ss) \
|
||||
{ if (!ss->opt.noLocks) PZ_EnterMonitor((ss)->xmitBufLock); }
|
||||
#define ssl_ReleaseXmitBufLock(ss) \
|
||||
{ if (!ss->opt.noLocks) PZ_ExitMonitor( (ss)->xmitBufLock); }
|
||||
#define ssl_HaveXmitBufLock(ss) \
|
||||
(PZ_InMonitor((ss)->xmitBufLock))
|
||||
|
||||
|
||||
extern SECStatus ssl3_KeyAndMacDeriveBypass(ssl3CipherSpec * pwSpec,
|
||||
const unsigned char * cr, const unsigned char * sr,
|
||||
PRBool isTLS, PRBool isExport);
|
||||
extern SECStatus ssl3_MasterKeyDeriveBypass( ssl3CipherSpec * pwSpec,
|
||||
const unsigned char * cr, const unsigned char * sr,
|
||||
const SECItem * pms, PRBool isTLS, PRBool isRSA);
|
||||
|
||||
/* These functions are called from secnav, even though they're "private". */
|
||||
|
||||
extern int ssl2_SendErrorMessage(struct sslSocketStr *ss, int error);
|
||||
|
@ -1208,13 +1246,46 @@ extern SECStatus ssl3_ConstructV2CipherSpecsHack(sslSocket *ss,
|
|||
|
||||
extern SECStatus ssl3_RedoHandshake(sslSocket *ss, PRBool flushCache);
|
||||
|
||||
extern void ssl3_DestroySSL3Info(ssl3State *ssl3);
|
||||
extern void ssl3_DestroySSL3Info(sslSocket *ss);
|
||||
|
||||
extern SECStatus ssl3_NegotiateVersion(sslSocket *ss,
|
||||
SSL3ProtocolVersion peerVersion);
|
||||
|
||||
extern SECStatus ssl_GetPeerInfo(sslSocket *ss);
|
||||
|
||||
#ifdef NSS_ENABLE_ECC
|
||||
/* ECDH functions */
|
||||
extern SECStatus ssl3_SendECDHClientKeyExchange(sslSocket * ss,
|
||||
SECKEYPublicKey * svrPubKey);
|
||||
extern SECStatus ssl3_HandleECDHServerKeyExchange(sslSocket *ss,
|
||||
SSL3Opaque *b, PRUint32 length);
|
||||
extern SECStatus ssl3_HandleECDHClientKeyExchange(sslSocket *ss,
|
||||
SSL3Opaque *b, PRUint32 length,
|
||||
SECKEYPublicKey *srvrPubKey,
|
||||
SECKEYPrivateKey *srvrPrivKey);
|
||||
extern SECStatus ssl3_SendECDHServerKeyExchange(sslSocket *ss);
|
||||
#endif
|
||||
|
||||
extern SECStatus ssl3_ComputeCommonKeyHash(PRUint8 * hashBuf,
|
||||
unsigned int bufLen, SSL3Hashes *hashes,
|
||||
PRBool bypassPKCS11);
|
||||
extern SECStatus ssl3_InitPendingCipherSpec(sslSocket *ss, PK11SymKey *pms);
|
||||
extern SECStatus ssl3_AppendHandshake(sslSocket *ss, const void *void_src,
|
||||
PRInt32 bytes);
|
||||
extern SECStatus ssl3_AppendHandshakeHeader(sslSocket *ss,
|
||||
SSL3HandshakeType t, PRUint32 length);
|
||||
extern SECStatus ssl3_AppendHandshakeVariable( sslSocket *ss,
|
||||
const SSL3Opaque *src, PRInt32 bytes, PRInt32 lenSize);
|
||||
extern SECStatus ssl3_ConsumeHandshake(sslSocket *ss, void *v, PRInt32 bytes,
|
||||
SSL3Opaque **b, PRUint32 *length);
|
||||
extern SECStatus ssl3_ConsumeHandshakeVariable(sslSocket *ss, SECItem *i,
|
||||
PRInt32 bytes, SSL3Opaque **b, PRUint32 *length);
|
||||
extern SECStatus ssl3_SignHashes(SSL3Hashes *hash, SECKEYPrivateKey *key,
|
||||
SECItem *buf, PRBool isTLS);
|
||||
extern SECStatus ssl3_VerifySignedHashes(SSL3Hashes *hash,
|
||||
CERTCertificate *cert, SECItem *buf, PRBool isTLS,
|
||||
void *pwArg);
|
||||
|
||||
/* Construct a new NSPR socket for the app to use */
|
||||
extern PRFileDesc *ssl_NewPRSocket(sslSocket *ss, PRFileDesc *fd);
|
||||
extern void ssl_FreePRSocket(PRFileDesc *fd);
|
||||
|
|
|
@ -34,7 +34,7 @@
|
|||
* the terms of any one of the MPL, the GPL or the LGPL.
|
||||
*
|
||||
* ***** END LICENSE BLOCK ***** */
|
||||
/* $Id: sslinfo.c,v 1.13 2005/09/06 17:15:32 glen.beasley%sun.com Exp $ */
|
||||
/* $Id: sslinfo.c,v 1.14 2005/09/09 03:02:16 nelsonb%netscape.com Exp $ */
|
||||
#include "ssl.h"
|
||||
#include "sslimpl.h"
|
||||
#include "sslproto.h"
|
||||
|
@ -60,17 +60,17 @@ SSL_GetChannelInfo(PRFileDesc *fd, SSLChannelInfo *info, PRUintn len)
|
|||
memset(&inf, 0, sizeof inf);
|
||||
inf.length = PR_MIN(sizeof inf, len);
|
||||
|
||||
if (ss->useSecurity && ss->firstHsDone) {
|
||||
if (ss->opt.useSecurity && ss->firstHsDone) {
|
||||
sid = ss->sec.ci.sid;
|
||||
inf.protocolVersion = ss->version;
|
||||
inf.authKeyBits = ss->sec.authKeyBits;
|
||||
inf.keaKeyBits = ss->sec.keaKeyBits;
|
||||
if (ss->version < SSL_LIBRARY_VERSION_3_0) { /* SSL2 */
|
||||
inf.cipherSuite = ss->sec.cipherType | 0xff00;
|
||||
} else if (ss->ssl3) { /* SSL3 and TLS */
|
||||
} else if (ss->ssl3.initialized) { /* SSL3 and TLS */
|
||||
|
||||
/* XXX These should come from crSpec */
|
||||
inf.cipherSuite = ss->ssl3->hs.cipher_suite;
|
||||
inf.cipherSuite = ss->ssl3.hs.cipher_suite;
|
||||
}
|
||||
if (sid) {
|
||||
inf.creationTime = sid->creationTime;
|
||||
|
@ -78,7 +78,8 @@ SSL_GetChannelInfo(PRFileDesc *fd, SSLChannelInfo *info, PRUintn len)
|
|||
inf.expirationTime = sid->expirationTime;
|
||||
if (ss->version < SSL_LIBRARY_VERSION_3_0) { /* SSL2 */
|
||||
inf.sessionIDLength = SSL2_SESSIONID_BYTES;
|
||||
memcpy(inf.sessionID, sid->u.ssl2.sessionID, SSL2_SESSIONID_BYTES);
|
||||
memcpy(inf.sessionID, sid->u.ssl2.sessionID,
|
||||
SSL2_SESSIONID_BYTES);
|
||||
} else {
|
||||
unsigned int sidLen = sid->u.ssl3.sessionIDLength;
|
||||
sidLen = PR_MIN(sidLen, sizeof inf.sessionID);
|
||||
|
|
|
@ -36,7 +36,7 @@
|
|||
* the terms of any one of the MPL, the GPL or the LGPL.
|
||||
*
|
||||
* ***** END LICENSE BLOCK ***** */
|
||||
/* $Id: sslnonce.c,v 1.16 2004/12/17 02:01:35 julien.pierre.bugs%sun.com Exp $ */
|
||||
/* $Id: sslnonce.c,v 1.17 2005/09/09 03:02:16 nelsonb%netscape.com Exp $ */
|
||||
|
||||
#include "nssrenam.h"
|
||||
#include "cert.h"
|
||||
|
@ -193,7 +193,7 @@ ssl_LookupSID(const PRIPv6Addr *addr, PRUint16 port, const char *peerID,
|
|||
PORT_Strcmp(sid->peerID, peerID) == 0)) &&
|
||||
/* is cacheable */
|
||||
(sid->version < SSL_LIBRARY_VERSION_3_0 ||
|
||||
sid->u.ssl3.resumable) &&
|
||||
sid->u.ssl3.keys.resumable) &&
|
||||
/* server hostname matches. */
|
||||
(sid->urlSvrName != NULL) &&
|
||||
((0 == PORT_Strcmp(urlSvrName, sid->urlSvrName)) ||
|
||||
|
|
|
@ -37,7 +37,7 @@
|
|||
* the terms of any one of the MPL, the GPL or the LGPL.
|
||||
*
|
||||
* ***** END LICENSE BLOCK ***** */
|
||||
/* $Id: sslsecur.c,v 1.31 2005/08/16 03:42:26 nelsonb%netscape.com Exp $ */
|
||||
/* $Id: sslsecur.c,v 1.32 2005/09/09 03:02:16 nelsonb%netscape.com Exp $ */
|
||||
#include "cert.h"
|
||||
#include "secitem.h"
|
||||
#include "keyhi.h"
|
||||
|
@ -112,9 +112,9 @@ ssl_Do1stHandshake(sslSocket *ss)
|
|||
int loopCount = 0;
|
||||
|
||||
do {
|
||||
PORT_Assert( ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert( !ssl_HaveRecvBufLock(ss) );
|
||||
PORT_Assert( !ssl_HaveXmitBufLock(ss) );
|
||||
PORT_Assert(ss->opt.noLocks || ssl_Have1stHandshakeLock(ss) );
|
||||
PORT_Assert(ss->opt.noLocks || !ssl_HaveRecvBufLock(ss));
|
||||
PORT_Assert(ss->opt.noLocks || !ssl_HaveXmitBufLock(ss));
|
||||
|
||||
if (ss->handshake == 0) {
|
||||
/* Previous handshake finished. Switch to next one */
|
||||
|
@ -153,8 +153,8 @@ ssl_Do1stHandshake(sslSocket *ss)
|
|||
*/
|
||||
} while (rv != SECFailure); /* was (rv >= 0); XXX_1 */
|
||||
|
||||
PORT_Assert( !ssl_HaveRecvBufLock(ss) );
|
||||
PORT_Assert( !ssl_HaveXmitBufLock(ss) );
|
||||
PORT_Assert(ss->opt.noLocks || !ssl_HaveRecvBufLock(ss));
|
||||
PORT_Assert(ss->opt.noLocks || !ssl_HaveXmitBufLock(ss));
|
||||
|
||||
if (rv == SECWouldBlock) {
|
||||
PORT_SetError(PR_WOULD_BLOCK_ERROR);
|
||||
|
@ -202,7 +202,7 @@ SSL_ResetHandshake(PRFileDesc *s, PRBool asServer)
|
|||
}
|
||||
|
||||
/* Don't waste my time */
|
||||
if (!ss->useSecurity)
|
||||
if (!ss->opt.useSecurity)
|
||||
return SECSuccess;
|
||||
|
||||
SSL_LOCK_READER(ss);
|
||||
|
@ -231,7 +231,7 @@ SSL_ResetHandshake(PRFileDesc *s, PRBool asServer)
|
|||
** Blow away old security state and get a fresh setup.
|
||||
*/
|
||||
ssl_GetXmitBufLock(ss);
|
||||
ssl_ResetSecurityInfo(&ss->sec);
|
||||
ssl_ResetSecurityInfo(&ss->sec, PR_TRUE);
|
||||
status = ssl_CreateSecurityInfo(ss);
|
||||
ssl_ReleaseXmitBufLock(ss);
|
||||
|
||||
|
@ -264,7 +264,7 @@ SSL_ReHandshake(PRFileDesc *fd, PRBool flushCache)
|
|||
return SECFailure;
|
||||
}
|
||||
|
||||
if (!ss->useSecurity)
|
||||
if (!ss->opt.useSecurity)
|
||||
return SECSuccess;
|
||||
|
||||
ssl_Get1stHandshakeLock(ss);
|
||||
|
@ -306,7 +306,7 @@ SSL_HandshakeCallback(PRFileDesc *fd, SSLHandshakeCallback cb,
|
|||
return SECFailure;
|
||||
}
|
||||
|
||||
if (!ss->useSecurity) {
|
||||
if (!ss->opt.useSecurity) {
|
||||
PORT_SetError(SEC_ERROR_INVALID_ARGS);
|
||||
return SECFailure;
|
||||
}
|
||||
|
@ -347,7 +347,7 @@ SSL_ForceHandshake(PRFileDesc *fd)
|
|||
}
|
||||
|
||||
/* Don't waste my time */
|
||||
if (!ss->useSecurity)
|
||||
if (!ss->opt.useSecurity)
|
||||
return SECSuccess;
|
||||
|
||||
ssl_Get1stHandshakeLock(ss);
|
||||
|
@ -388,6 +388,7 @@ SSL_ForceHandshake(PRFileDesc *fd)
|
|||
SECStatus
|
||||
sslBuffer_Grow(sslBuffer *b, unsigned int newLen)
|
||||
{
|
||||
newLen = PR_MAX(newLen, MAX_FRAGMENT_LENGTH + 2048);
|
||||
if (newLen > b->space) {
|
||||
unsigned char *newBuf;
|
||||
if (b->buf) {
|
||||
|
@ -419,7 +420,7 @@ ssl_SaveWriteData(sslSocket *ss, sslBuffer *buf, const void *data,
|
|||
unsigned int newlen;
|
||||
SECStatus rv;
|
||||
|
||||
PORT_Assert( ssl_HaveXmitBufLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_HaveXmitBufLock(ss) );
|
||||
newlen = buf->len + len;
|
||||
if (newlen > buf->space) {
|
||||
rv = sslBuffer_Grow(buf, newlen);
|
||||
|
@ -446,7 +447,7 @@ ssl_SendSavedWriteData(sslSocket *ss, sslBuffer *buf, sslSendFunc send)
|
|||
int rv = 0;
|
||||
int len = buf->len;
|
||||
|
||||
PORT_Assert( ssl_HaveXmitBufLock(ss) );
|
||||
PORT_Assert( ss->opt.noLocks || ssl_HaveXmitBufLock(ss) );
|
||||
if (len != 0) {
|
||||
SSL_TRC(5, ("%d: SSL[%d]: sending %d bytes of saved data",
|
||||
SSL_GETPID(), ss->fd, len));
|
||||
|
@ -664,19 +665,47 @@ SSL_ConfigSecureServer(PRFileDesc *fd, CERTCertificate *cert,
|
|||
}
|
||||
|
||||
/* load the private key */
|
||||
if (sc->serverKey != NULL) {
|
||||
SECKEY_DestroyPrivateKey(sc->serverKey);
|
||||
sc->serverKey = NULL;
|
||||
if (sc->serverKeyPair != NULL) {
|
||||
ssl3_FreeKeyPair(sc->serverKeyPair);
|
||||
sc->serverKeyPair = NULL;
|
||||
}
|
||||
if (key) {
|
||||
sc->serverKey = SECKEY_CopyPrivateKey(key);
|
||||
if (sc->serverKey == NULL)
|
||||
SECKEYPrivateKey * keyCopy = NULL;
|
||||
CK_MECHANISM_TYPE keyMech = CKM_INVALID_MECHANISM;
|
||||
|
||||
if (key->pkcs11Slot) {
|
||||
PK11SlotInfo * bestSlot;
|
||||
bestSlot = PK11_ReferenceSlot(key->pkcs11Slot);
|
||||
if (bestSlot) {
|
||||
keyCopy = PK11_CopyTokenPrivKeyToSessionPrivKey(bestSlot, key);
|
||||
PK11_FreeSlot(bestSlot);
|
||||
}
|
||||
}
|
||||
if (keyCopy == NULL)
|
||||
keyMech = PK11_MapSignKeyType(key->keyType);
|
||||
if (keyMech != CKM_INVALID_MECHANISM) {
|
||||
PK11SlotInfo * bestSlot;
|
||||
/* XXX Maybe should be bestSlotMultiple? */
|
||||
bestSlot = PK11_GetBestSlot(keyMech, NULL /* wincx */);
|
||||
if (bestSlot) {
|
||||
keyCopy = PK11_CopyTokenPrivKeyToSessionPrivKey(bestSlot, key);
|
||||
PK11_FreeSlot(bestSlot);
|
||||
}
|
||||
}
|
||||
if (keyCopy == NULL)
|
||||
keyCopy = SECKEY_CopyPrivateKey(key);
|
||||
if (keyCopy == NULL)
|
||||
goto loser;
|
||||
SECKEY_CacheStaticFlags(sc->serverKey);
|
||||
SECKEY_CacheStaticFlags(keyCopy);
|
||||
sc->serverKeyPair = ssl3_NewKeyPair(keyCopy, NULL);
|
||||
if (sc->serverKeyPair == NULL) {
|
||||
SECKEY_DestroyPrivateKey(keyCopy);
|
||||
goto loser;
|
||||
}
|
||||
}
|
||||
|
||||
if (kea == kt_rsa && cert && sc->serverKeyBits > 512) {
|
||||
if (ss->noStepDown) {
|
||||
if (ss->opt.noStepDown) {
|
||||
/* disable all export ciphersuites */
|
||||
} else {
|
||||
rv = ssl3_CreateRSAStepDownKeys(ss);
|
||||
|
@ -701,9 +730,9 @@ loser:
|
|||
CERT_DestroyCertificateList(sc->serverCertChain);
|
||||
sc->serverCertChain = NULL;
|
||||
}
|
||||
if (sc->serverKey != NULL) {
|
||||
SECKEY_DestroyPrivateKey(sc->serverKey);
|
||||
sc->serverKey = NULL;
|
||||
if (sc->serverKeyPair != NULL) {
|
||||
ssl3_FreeKeyPair(sc->serverKeyPair);
|
||||
sc->serverKeyPair = NULL;
|
||||
}
|
||||
return SECFailure;
|
||||
}
|
||||
|
@ -788,7 +817,7 @@ loser:
|
|||
** Caller holds any relevant locks.
|
||||
*/
|
||||
void
|
||||
ssl_ResetSecurityInfo(sslSecurityInfo *sec)
|
||||
ssl_ResetSecurityInfo(sslSecurityInfo *sec, PRBool doMemset)
|
||||
{
|
||||
/* Destroy MAC */
|
||||
if (sec->hash && sec->hashcx) {
|
||||
|
@ -830,7 +859,10 @@ ssl_ResetSecurityInfo(sslSecurityInfo *sec)
|
|||
ssl_FreeSID(sec->ci.sid);
|
||||
}
|
||||
PORT_ZFree(sec->ci.sendBuf.buf, sec->ci.sendBuf.space);
|
||||
memset(&sec->ci, 0, sizeof sec->ci);
|
||||
if (doMemset) {
|
||||
memset(&sec->ci, 0, sizeof sec->ci);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -841,7 +873,7 @@ ssl_ResetSecurityInfo(sslSecurityInfo *sec)
|
|||
void
|
||||
ssl_DestroySecurityInfo(sslSecurityInfo *sec)
|
||||
{
|
||||
ssl_ResetSecurityInfo(sec);
|
||||
ssl_ResetSecurityInfo(sec, PR_FALSE);
|
||||
|
||||
PORT_ZFree(sec->writeBuf.buf, sec->writeBuf.space);
|
||||
sec->writeBuf.buf = 0;
|
||||
|
@ -857,7 +889,7 @@ ssl_SecureConnect(sslSocket *ss, const PRNetAddr *sa)
|
|||
PRFileDesc *osfd = ss->fd->lower;
|
||||
int rv;
|
||||
|
||||
if ( ss->handshakeAsServer ) {
|
||||
if ( ss->opt.handshakeAsServer ) {
|
||||
ss->securityHandshake = ssl2_BeginServerHandshake;
|
||||
ss->handshaking = sslHandshakingAsServer;
|
||||
} else {
|
||||
|
@ -892,7 +924,7 @@ ssl_SecureClose(sslSocket *ss)
|
|||
ss->firstHsDone &&
|
||||
!(ss->shutdownHow & ssl_SHUTDOWN_SEND) &&
|
||||
!ss->recvdCloseNotify &&
|
||||
(ss->ssl3 != NULL)) {
|
||||
ss->ssl3.initialized) {
|
||||
|
||||
/* We don't want the final alert to be Nagle delayed. */
|
||||
if (!ss->delayDisabled) {
|
||||
|
@ -924,7 +956,7 @@ ssl_SecureShutdown(sslSocket *ss, int nsprHow)
|
|||
(ss->version >= SSL_LIBRARY_VERSION_3_0) &&
|
||||
ss->firstHsDone &&
|
||||
!ss->recvdCloseNotify &&
|
||||
(ss->ssl3 != NULL)) {
|
||||
ss->ssl3.initialized) {
|
||||
|
||||
(void) SSL3_SendAlert(ss, alert_warning, close_notify);
|
||||
}
|
||||
|
@ -956,7 +988,7 @@ ssl_SecureRecv(sslSocket *ss, unsigned char *buf, int len, int flags)
|
|||
return PR_FAILURE;
|
||||
}
|
||||
|
||||
if (!ssl_SocketIsBlocking(ss) && !ss->fdx) {
|
||||
if (!ssl_SocketIsBlocking(ss) && !ss->opt.fdx) {
|
||||
ssl_GetXmitBufLock(ss);
|
||||
if (ss->pendingBuf.len != 0) {
|
||||
rv = ssl_SendSavedWriteData(ss, &ss->pendingBuf, ssl_DefSend);
|
||||
|
@ -1132,7 +1164,7 @@ SSL_DataPending(PRFileDesc *fd)
|
|||
|
||||
ss = ssl_FindSocket(fd);
|
||||
|
||||
if (ss && ss->useSecurity) {
|
||||
if (ss && ss->opt.useSecurity) {
|
||||
|
||||
ssl_Get1stHandshakeLock(ss);
|
||||
ssl_GetSSL3HandshakeLock(ss);
|
||||
|
@ -1180,7 +1212,7 @@ SSL_GetSessionID(PRFileDesc *fd)
|
|||
ssl_Get1stHandshakeLock(ss);
|
||||
ssl_GetSSL3HandshakeLock(ss);
|
||||
|
||||
if (ss->useSecurity && ss->firstHsDone && ss->sec.ci.sid) {
|
||||
if (ss->opt.useSecurity && ss->firstHsDone && ss->sec.ci.sid) {
|
||||
item = (SECItem *)PORT_Alloc(sizeof(SECItem));
|
||||
if (item) {
|
||||
sslSessionID * sid = ss->sec.ci.sid;
|
||||
|
|
|
@ -36,7 +36,7 @@
|
|||
* the terms of any one of the MPL, the GPL or the LGPL.
|
||||
*
|
||||
* ***** END LICENSE BLOCK ***** */
|
||||
/* $Id: sslsnce.c,v 1.34 2005/08/16 03:42:26 nelsonb%netscape.com Exp $ */
|
||||
/* $Id: sslsnce.c,v 1.35 2005/09/09 03:02:16 nelsonb%netscape.com Exp $ */
|
||||
|
||||
/* Note: ssl_FreeSID() in sslnonce.c gets used for both client and server
|
||||
* cache sids!
|
||||
|
@ -146,17 +146,15 @@ struct sidCacheEntryStr {
|
|||
/* 2 */ ssl3CipherSuite cipherSuite;
|
||||
/* 2 */ PRUint16 compression; /* SSL3CompressionMethod */
|
||||
|
||||
/*122 */ ssl3SidKeys keys; /* keys and ivs, wrapped as needed. */
|
||||
/* 1 */ PRUint8 unused; /* was hasFortezza; */
|
||||
/* 1 */ PRUint8 resumable;
|
||||
/*100 */ ssl3SidKeys keys; /* keys and ivs, wrapped as needed. */
|
||||
|
||||
/* 4 */ PRUint32 masterWrapMech;
|
||||
/* 4 */ SSL3KEAType exchKeyType;
|
||||
/* 4 */ PRInt32 certIndex;
|
||||
/*140 */} ssl3;
|
||||
#if defined(LINUX)
|
||||
/*116 */} ssl3;
|
||||
#if defined(LINUX) /* XXX Why only on Linux ? */
|
||||
struct {
|
||||
PRUint8 filler[144];
|
||||
PRUint8 filler[144]; /* XXX why this number ? */
|
||||
} forceSize;
|
||||
#endif
|
||||
} u;
|
||||
|
@ -441,7 +439,6 @@ ConvertFromSID(sidCacheEntry *to, sslSessionID *from)
|
|||
|
||||
to->u.ssl3.cipherSuite = from->u.ssl3.cipherSuite;
|
||||
to->u.ssl3.compression = (uint16)from->u.ssl3.compression;
|
||||
to->u.ssl3.resumable = from->u.ssl3.resumable;
|
||||
to->u.ssl3.keys = from->u.ssl3.keys;
|
||||
to->u.ssl3.masterWrapMech = from->u.ssl3.masterWrapMech;
|
||||
to->u.ssl3.exchKeyType = from->u.ssl3.exchKeyType;
|
||||
|
@ -516,7 +513,6 @@ ConvertToSID(sidCacheEntry *from, certCacheEntry *pcce,
|
|||
to->u.ssl3.sessionIDLength = from->sessionIDLength;
|
||||
to->u.ssl3.cipherSuite = from->u.ssl3.cipherSuite;
|
||||
to->u.ssl3.compression = (SSL3CompressionMethod)from->u.ssl3.compression;
|
||||
to->u.ssl3.resumable = from->u.ssl3.resumable;
|
||||
to->u.ssl3.keys = from->u.ssl3.keys;
|
||||
to->u.ssl3.masterWrapMech = from->u.ssl3.masterWrapMech;
|
||||
to->u.ssl3.exchKeyType = from->u.ssl3.exchKeyType;
|
||||
|
@ -528,7 +524,7 @@ ConvertToSID(sidCacheEntry *from, certCacheEntry *pcce,
|
|||
*/
|
||||
to->u.ssl3.clientWriteKey = NULL;
|
||||
to->u.ssl3.serverWriteKey = NULL;
|
||||
to->u.ssl3.tek = NULL;
|
||||
|
||||
to->urlSvrName = NULL;
|
||||
|
||||
to->u.ssl3.masterModuleID = (SECMODModuleID)-1; /* invalid value */
|
||||
|
|
|
@ -40,7 +40,7 @@
|
|||
* the terms of any one of the MPL, the GPL or the LGPL.
|
||||
*
|
||||
* ***** END LICENSE BLOCK ***** */
|
||||
/* $Id: sslsock.c,v 1.38 2005/08/16 03:42:26 nelsonb%netscape.com Exp $ */
|
||||
/* $Id: sslsock.c,v 1.39 2005/09/09 03:02:16 nelsonb%netscape.com Exp $ */
|
||||
#include "seccomon.h"
|
||||
#include "cert.h"
|
||||
#include "keyhi.h"
|
||||
|
@ -161,6 +161,8 @@ static sslOptions ssl_defaults = {
|
|||
PR_TRUE, /* v2CompatibleHello */
|
||||
PR_TRUE, /* detectRollBack */
|
||||
PR_FALSE, /* noStepDown */
|
||||
PR_FALSE, /* bypassPKCS11 */
|
||||
PR_FALSE, /* noLocks */
|
||||
};
|
||||
|
||||
sslSessionIDLookupFunc ssl_sid_lookup;
|
||||
|
@ -170,13 +172,15 @@ sslSessionIDUncacheFunc ssl_sid_uncache;
|
|||
static PRBool ssl_inited = PR_FALSE;
|
||||
static PRDescIdentity ssl_layer_id;
|
||||
|
||||
PRBool locksEverDisabled; /* implicitly PR_FALSE */
|
||||
int ssl_lock_readers = 1; /* default true. */
|
||||
char ssl_debug;
|
||||
char ssl_trace;
|
||||
|
||||
|
||||
/* forward declarations. */
|
||||
static sslSocket *ssl_NewSocket(void);
|
||||
static sslSocket *ssl_NewSocket(PRBool makeLocks);
|
||||
static SECStatus ssl_MakeLocks(sslSocket *ss);
|
||||
static PRStatus ssl_PushIOLayer(sslSocket *ns, PRFileDesc *stack,
|
||||
PRDescIdentity id);
|
||||
|
||||
|
@ -227,22 +231,10 @@ ssl_DupSocket(sslSocket *os)
|
|||
sslSocket *ss;
|
||||
SECStatus rv;
|
||||
|
||||
ss = ssl_NewSocket();
|
||||
ss = ssl_NewSocket((PRBool)(!os->opt.noLocks));
|
||||
if (ss) {
|
||||
ss->useSocks = PR_FALSE;
|
||||
ss->useSecurity = os->useSecurity;
|
||||
ss->requestCertificate = os->requestCertificate;
|
||||
ss->requireCertificate = os->requireCertificate;
|
||||
ss->handshakeAsClient = os->handshakeAsClient;
|
||||
ss->handshakeAsServer = os->handshakeAsServer;
|
||||
ss->enableSSL2 = os->enableSSL2;
|
||||
ss->enableSSL3 = os->enableSSL3;
|
||||
ss->enableTLS = os->enableTLS;
|
||||
ss->noCache = os->noCache;
|
||||
ss->fdx = os->fdx;
|
||||
ss->v2CompatibleHello = os->v2CompatibleHello;
|
||||
ss->detectRollBack = os->detectRollBack;
|
||||
ss->noStepDown = os->noStepDown;
|
||||
ss->opt = os->opt;
|
||||
ss->opt.useSocks = PR_FALSE;
|
||||
|
||||
ss->peerID = !os->peerID ? NULL : PORT_Strdup(os->peerID);
|
||||
ss->url = !os->url ? NULL : PORT_Strdup(os->url);
|
||||
|
@ -271,7 +263,7 @@ ssl_DupSocket(sslSocket *os)
|
|||
ss->sizeCipherSpecs = 0;
|
||||
ss->preferredCipher = NULL;
|
||||
}
|
||||
if (ss->useSecurity) {
|
||||
if (ss->opt.useSecurity) {
|
||||
/* This int should be SSLKEAType, but CC on Irix complains,
|
||||
* during the for loop.
|
||||
*/
|
||||
|
@ -289,9 +281,9 @@ ssl_DupSocket(sslSocket *os)
|
|||
sc->serverCert = NULL;
|
||||
sc->serverCertChain = NULL;
|
||||
}
|
||||
sc->serverKey = oc->serverKey ?
|
||||
SECKEY_CopyPrivateKey(oc->serverKey) : NULL;
|
||||
if (oc->serverKey && !sc->serverKey)
|
||||
sc->serverKeyPair = oc->serverKeyPair ?
|
||||
ssl3_GetKeyPairRef(oc->serverKeyPair) : NULL;
|
||||
if (oc->serverKeyPair && !sc->serverKeyPair)
|
||||
goto loser;
|
||||
sc->serverKeyBits = oc->serverKeyBits;
|
||||
}
|
||||
|
@ -328,7 +320,6 @@ loser:
|
|||
static void
|
||||
ssl_DestroyLocks(sslSocket *ss)
|
||||
{
|
||||
|
||||
/* Destroy locks. */
|
||||
if (ss->firstHandshakeLock) {
|
||||
PZ_DestroyMonitor(ss->firstHandshakeLock);
|
||||
|
@ -373,7 +364,7 @@ ssl_DestroySocketContents(sslSocket *ss)
|
|||
/* Free up socket */
|
||||
ssl_DestroySecurityInfo(&ss->sec);
|
||||
|
||||
ssl3_DestroySSL3Info(ss->ssl3);
|
||||
ssl3_DestroySSL3Info(ss);
|
||||
|
||||
PORT_Free(ss->saveBuf.buf);
|
||||
PORT_Free(ss->pendingBuf.buf);
|
||||
|
@ -396,8 +387,8 @@ ssl_DestroySocketContents(sslSocket *ss)
|
|||
CERT_DestroyCertificate(sc->serverCert);
|
||||
if (sc->serverCertChain != NULL)
|
||||
CERT_DestroyCertificateList(sc->serverCertChain);
|
||||
if (sc->serverKey != NULL)
|
||||
SECKEY_DestroyPrivateKey(sc->serverKey);
|
||||
if (sc->serverKeyPair != NULL)
|
||||
ssl3_FreeKeyPair(sc->serverKeyPair);
|
||||
}
|
||||
if (ss->stepDownKeyPair) {
|
||||
ssl3_FreeKeyPair(ss->stepDownKeyPair);
|
||||
|
@ -476,7 +467,7 @@ ssl_EnableNagleDelay(sslSocket *ss, PRBool enabled)
|
|||
static void
|
||||
ssl_ChooseOps(sslSocket *ss)
|
||||
{
|
||||
ss->ops = ss->useSecurity ? &ssl_secure_ops : &ssl_default_ops;
|
||||
ss->ops = ss->opt.useSecurity ? &ssl_secure_ops : &ssl_default_ops;
|
||||
}
|
||||
|
||||
/* Called from SSL_Enable (immediately below) */
|
||||
|
@ -511,7 +502,7 @@ SSL_OptionSet(PRFileDesc *fd, PRInt32 which, PRBool on)
|
|||
|
||||
switch (which) {
|
||||
case SSL_SOCKS:
|
||||
ss->useSocks = PR_FALSE;
|
||||
ss->opt.useSocks = PR_FALSE;
|
||||
rv = PrepareSocket(ss);
|
||||
if (on) {
|
||||
PORT_SetError(SEC_ERROR_INVALID_ARGS);
|
||||
|
@ -520,38 +511,38 @@ SSL_OptionSet(PRFileDesc *fd, PRInt32 which, PRBool on)
|
|||
break;
|
||||
|
||||
case SSL_SECURITY:
|
||||
ss->useSecurity = on;
|
||||
ss->opt.useSecurity = on;
|
||||
rv = PrepareSocket(ss);
|
||||
break;
|
||||
|
||||
case SSL_REQUEST_CERTIFICATE:
|
||||
ss->requestCertificate = on;
|
||||
ss->opt.requestCertificate = on;
|
||||
break;
|
||||
|
||||
case SSL_REQUIRE_CERTIFICATE:
|
||||
ss->requireCertificate = on;
|
||||
ss->opt.requireCertificate = on;
|
||||
break;
|
||||
|
||||
case SSL_HANDSHAKE_AS_CLIENT:
|
||||
if ( ss->handshakeAsServer && on ) {
|
||||
if ( ss->opt.handshakeAsServer && on ) {
|
||||
PORT_SetError(SEC_ERROR_INVALID_ARGS);
|
||||
rv = SECFailure;
|
||||
break;
|
||||
}
|
||||
ss->handshakeAsClient = on;
|
||||
ss->opt.handshakeAsClient = on;
|
||||
break;
|
||||
|
||||
case SSL_HANDSHAKE_AS_SERVER:
|
||||
if ( ss->handshakeAsClient && on ) {
|
||||
if ( ss->opt.handshakeAsClient && on ) {
|
||||
PORT_SetError(SEC_ERROR_INVALID_ARGS);
|
||||
rv = SECFailure;
|
||||
break;
|
||||
}
|
||||
ss->handshakeAsServer = on;
|
||||
ss->opt.handshakeAsServer = on;
|
||||
break;
|
||||
|
||||
case SSL_ENABLE_TLS:
|
||||
ss->enableTLS = on;
|
||||
ss->opt.enableTLS = on;
|
||||
ss->preferredCipher = NULL;
|
||||
if (ss->cipherSpecs) {
|
||||
PORT_Free(ss->cipherSpecs);
|
||||
|
@ -561,7 +552,7 @@ SSL_OptionSet(PRFileDesc *fd, PRInt32 which, PRBool on)
|
|||
break;
|
||||
|
||||
case SSL_ENABLE_SSL3:
|
||||
ss->enableSSL3 = on;
|
||||
ss->opt.enableSSL3 = on;
|
||||
ss->preferredCipher = NULL;
|
||||
if (ss->cipherSpecs) {
|
||||
PORT_Free(ss->cipherSpecs);
|
||||
|
@ -571,9 +562,9 @@ SSL_OptionSet(PRFileDesc *fd, PRInt32 which, PRBool on)
|
|||
break;
|
||||
|
||||
case SSL_ENABLE_SSL2:
|
||||
ss->enableSSL2 = on;
|
||||
ss->opt.enableSSL2 = on;
|
||||
if (on) {
|
||||
ss->v2CompatibleHello = on;
|
||||
ss->opt.v2CompatibleHello = on;
|
||||
}
|
||||
ss->preferredCipher = NULL;
|
||||
if (ss->cipherSpecs) {
|
||||
|
@ -584,30 +575,45 @@ SSL_OptionSet(PRFileDesc *fd, PRInt32 which, PRBool on)
|
|||
break;
|
||||
|
||||
case SSL_NO_CACHE:
|
||||
ss->noCache = on;
|
||||
ss->opt.noCache = on;
|
||||
break;
|
||||
|
||||
case SSL_ENABLE_FDX:
|
||||
ss->fdx = on;
|
||||
ss->opt.fdx = on;
|
||||
break;
|
||||
|
||||
case SSL_V2_COMPATIBLE_HELLO:
|
||||
ss->v2CompatibleHello = on;
|
||||
ss->opt.v2CompatibleHello = on;
|
||||
if (!on) {
|
||||
ss->enableSSL2 = on;
|
||||
ss->opt.enableSSL2 = on;
|
||||
}
|
||||
break;
|
||||
|
||||
case SSL_ROLLBACK_DETECTION:
|
||||
ss->detectRollBack = on;
|
||||
ss->opt.detectRollBack = on;
|
||||
break;
|
||||
|
||||
case SSL_NO_STEP_DOWN:
|
||||
ss->noStepDown = on;
|
||||
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 {
|
||||
ss->opt.bypassPKCS11 = on;
|
||||
}
|
||||
break;
|
||||
|
||||
case SSL_NO_LOCKS:
|
||||
ss->opt.noLocks = on;
|
||||
if (on)
|
||||
locksEverDisabled = PR_TRUE;
|
||||
break;
|
||||
|
||||
default:
|
||||
PORT_SetError(SEC_ERROR_INVALID_ARGS);
|
||||
rv = SECFailure;
|
||||
|
@ -641,19 +647,21 @@ SSL_OptionGet(PRFileDesc *fd, PRInt32 which, PRBool *pOn)
|
|||
|
||||
switch (which) {
|
||||
case SSL_SOCKS: on = PR_FALSE; break;
|
||||
case SSL_SECURITY: on = ss->useSecurity; break;
|
||||
case SSL_REQUEST_CERTIFICATE: on = ss->requestCertificate; break;
|
||||
case SSL_REQUIRE_CERTIFICATE: on = ss->requireCertificate; break;
|
||||
case SSL_HANDSHAKE_AS_CLIENT: on = ss->handshakeAsClient; break;
|
||||
case SSL_HANDSHAKE_AS_SERVER: on = ss->handshakeAsServer; break;
|
||||
case SSL_ENABLE_TLS: on = ss->enableTLS; break;
|
||||
case SSL_ENABLE_SSL3: on = ss->enableSSL3; break;
|
||||
case SSL_ENABLE_SSL2: on = ss->enableSSL2; break;
|
||||
case SSL_NO_CACHE: on = ss->noCache; break;
|
||||
case SSL_ENABLE_FDX: on = ss->fdx; break;
|
||||
case SSL_V2_COMPATIBLE_HELLO: on = ss->v2CompatibleHello; break;
|
||||
case SSL_ROLLBACK_DETECTION: on = ss->detectRollBack; break;
|
||||
case SSL_NO_STEP_DOWN: on = ss->noStepDown; 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->opt.enableTLS; break;
|
||||
case SSL_ENABLE_SSL3: on = ss->opt.enableSSL3; 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;
|
||||
|
||||
default:
|
||||
PORT_SetError(SEC_ERROR_INVALID_ARGS);
|
||||
|
@ -693,6 +701,8 @@ SSL_OptionGetDefault(PRInt32 which, PRBool *pOn)
|
|||
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;
|
||||
|
||||
default:
|
||||
PORT_SetError(SEC_ERROR_INVALID_ARGS);
|
||||
|
@ -790,6 +800,16 @@ SSL_OptionSetDefault(PRInt32 which, PRBool on)
|
|||
SSL_DisableDefaultExportCipherSuites();
|
||||
break;
|
||||
|
||||
case SSL_BYPASS_PKCS11:
|
||||
ssl_defaults.bypassPKCS11 = on;
|
||||
break;
|
||||
|
||||
case SSL_NO_LOCKS:
|
||||
ssl_defaults.noLocks = on;
|
||||
if (on)
|
||||
locksEverDisabled = PR_TRUE;
|
||||
break;
|
||||
|
||||
default:
|
||||
PORT_SetError(SEC_ERROR_INVALID_ARGS);
|
||||
return SECFailure;
|
||||
|
@ -906,7 +926,7 @@ SSL_CipherPrefSet(PRFileDesc *fd, PRInt32 which, PRBool enabled)
|
|||
SSL_DBG(("%d: SSL[%d]: bad socket in CipherPrefSet", SSL_GETPID(), fd));
|
||||
return SECFailure;
|
||||
}
|
||||
if (enabled && ss->noStepDown && SSL_IsExportCipherSuite(which)) {
|
||||
if (enabled && ss->opt.noStepDown && SSL_IsExportCipherSuite(which)) {
|
||||
PORT_SetError(SEC_ERROR_INVALID_ALGORITHM);
|
||||
return SECFailure;
|
||||
}
|
||||
|
@ -999,7 +1019,7 @@ SSL_ImportFD(PRFileDesc *model, PRFileDesc *fd)
|
|||
|
||||
if (model == NULL) {
|
||||
/* Just create a default socket if we're given NULL for the model */
|
||||
ns = ssl_NewSocket();
|
||||
ns = ssl_NewSocket((PRBool)(!ssl_defaults.noLocks));
|
||||
} else {
|
||||
sslSocket * ss = ssl_FindSocket(model);
|
||||
if (ss == NULL) {
|
||||
|
@ -1084,8 +1104,8 @@ ssl_Accept(PRFileDesc *fd, PRNetAddr *sockaddr, PRIntervalTime timeout)
|
|||
/* Now start server connection handshake with client.
|
||||
** Don't need locks here because nobody else has a reference to ns yet.
|
||||
*/
|
||||
if ( ns->useSecurity ) {
|
||||
if ( ns->handshakeAsClient ) {
|
||||
if ( ns->opt.useSecurity ) {
|
||||
if ( ns->opt.handshakeAsClient ) {
|
||||
ns->handshake = ssl2_BeginClientHandshake;
|
||||
ss->handshaking = sslHandshakingAsClient;
|
||||
} else {
|
||||
|
@ -1241,7 +1261,7 @@ ssl_Recv(PRFileDesc *fd, void *buf, PRInt32 len, PRIntn flags,
|
|||
}
|
||||
SSL_LOCK_READER(ss);
|
||||
ss->rTimeout = timeout;
|
||||
if (!ss->fdx)
|
||||
if (!ss->opt.fdx)
|
||||
ss->wTimeout = timeout;
|
||||
rv = (*ss->ops->recv)(ss, (unsigned char*)buf, len, flags);
|
||||
SSL_UNLOCK_READER(ss);
|
||||
|
@ -1262,7 +1282,7 @@ ssl_Send(PRFileDesc *fd, const void *buf, PRInt32 len, PRIntn flags,
|
|||
}
|
||||
SSL_LOCK_WRITER(ss);
|
||||
ss->wTimeout = timeout;
|
||||
if (!ss->fdx)
|
||||
if (!ss->opt.fdx)
|
||||
ss->rTimeout = timeout;
|
||||
rv = (*ss->ops->send)(ss, (const unsigned char*)buf, len, flags);
|
||||
SSL_UNLOCK_WRITER(ss);
|
||||
|
@ -1282,7 +1302,7 @@ ssl_Read(PRFileDesc *fd, void *buf, PRInt32 len)
|
|||
}
|
||||
SSL_LOCK_READER(ss);
|
||||
ss->rTimeout = PR_INTERVAL_NO_TIMEOUT;
|
||||
if (!ss->fdx)
|
||||
if (!ss->opt.fdx)
|
||||
ss->wTimeout = PR_INTERVAL_NO_TIMEOUT;
|
||||
rv = (*ss->ops->read)(ss, (unsigned char*)buf, len);
|
||||
SSL_UNLOCK_READER(ss);
|
||||
|
@ -1302,7 +1322,7 @@ ssl_Write(PRFileDesc *fd, const void *buf, PRInt32 len)
|
|||
}
|
||||
SSL_LOCK_WRITER(ss);
|
||||
ss->wTimeout = PR_INTERVAL_NO_TIMEOUT;
|
||||
if (!ss->fdx)
|
||||
if (!ss->opt.fdx)
|
||||
ss->rTimeout = PR_INTERVAL_NO_TIMEOUT;
|
||||
rv = (*ss->ops->write)(ss, (const unsigned char*)buf, len);
|
||||
SSL_UNLOCK_WRITER(ss);
|
||||
|
@ -1398,7 +1418,7 @@ ssl_Poll(PRFileDesc *fd, PRInt16 how_flags, PRInt16 *p_out_flags)
|
|||
return 0; /* don't poll on this socket */
|
||||
}
|
||||
|
||||
if (ss->useSecurity &&
|
||||
if (ss->opt.useSecurity &&
|
||||
ss->handshaking != sslHandshakingUndetermined &&
|
||||
!ss->firstHsDone &&
|
||||
(how_flags & PR_POLL_RW)) {
|
||||
|
@ -1840,38 +1860,83 @@ loser:
|
|||
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:
|
||||
return SECFailure;
|
||||
}
|
||||
|
||||
#if (defined(XP_UNIX) || defined(XP_WIN32) || defined(XP_BEOS)) && !defined(_WIN32_WCE)
|
||||
#define NSS_HAVE_GETENV 1
|
||||
#endif
|
||||
|
||||
/*
|
||||
** Create a newsocket structure for a file descriptor.
|
||||
*/
|
||||
static sslSocket *
|
||||
ssl_NewSocket(void)
|
||||
ssl_NewSocket(PRBool makeLocks)
|
||||
{
|
||||
sslSocket *ss;
|
||||
#ifdef DEBUG
|
||||
#if (defined(XP_UNIX) || defined(XP_WIN32) || defined(XP_BEOS)) && !defined(_WIN32_WCE)
|
||||
#if defined( NSS_HAVE_GETENV )
|
||||
static int firsttime = 1;
|
||||
|
||||
if (firsttime) {
|
||||
char * ev;
|
||||
firsttime = 0;
|
||||
{
|
||||
char *ev = getenv("SSLDEBUG");
|
||||
if (ev && ev[0]) {
|
||||
ssl_debug = atoi(ev);
|
||||
SSL_TRACE(("SSL: debugging set to %d", ssl_debug));
|
||||
}
|
||||
}
|
||||
#ifdef DEBUG
|
||||
#ifdef TRACE
|
||||
{
|
||||
char *ev = getenv("SSLTRACE");
|
||||
if (ev && ev[0]) {
|
||||
ssl_trace = atoi(ev);
|
||||
SSL_TRACE(("SSL: tracing set to %d", ssl_trace));
|
||||
}
|
||||
ev = getenv("SSLTRACE");
|
||||
if (ev && ev[0]) {
|
||||
ssl_trace = atoi(ev);
|
||||
SSL_TRACE(("SSL: tracing set to %d", ssl_trace));
|
||||
}
|
||||
#endif /* TRACE */
|
||||
}
|
||||
#endif /* XP_UNIX || XP_WIN32 */
|
||||
ev = getenv("SSLDEBUG");
|
||||
if (ev && ev[0]) {
|
||||
ssl_debug = atoi(ev);
|
||||
SSL_TRACE(("SSL: debugging set to %d", ssl_debug));
|
||||
}
|
||||
#endif /* DEBUG */
|
||||
ev = getenv("SSLBYPASS");
|
||||
if (ev && ev[0]) {
|
||||
ssl_defaults.bypassPKCS11 = (ev[0] == '1');
|
||||
SSL_TRACE(("SSL: bypass default set to %d", \
|
||||
ssl_defaults.bypassPKCS11));
|
||||
}
|
||||
ev = getenv("SSLNOLOCKS");
|
||||
if (ev && ev[0]) {
|
||||
ssl_defaults.noLocks = (ev[0] == '1');
|
||||
SSL_TRACE(("SSL: noLocks default set to %d", ssl_defaults.noLocks));
|
||||
}
|
||||
}
|
||||
#endif /* NSS_HAVE_GETENV */
|
||||
|
||||
/* Make a new socket and get it ready */
|
||||
ss = (sslSocket*) PORT_ZAlloc(sizeof(sslSocket));
|
||||
|
@ -1882,20 +1947,10 @@ ssl_NewSocket(void)
|
|||
int i;
|
||||
SECStatus status;
|
||||
|
||||
ss->useSecurity = ssl_defaults.useSecurity;
|
||||
ss->useSocks = PR_FALSE;
|
||||
ss->requestCertificate = ssl_defaults.requestCertificate;
|
||||
ss->requireCertificate = ssl_defaults.requireCertificate;
|
||||
ss->handshakeAsClient = ssl_defaults.handshakeAsClient;
|
||||
ss->handshakeAsServer = ssl_defaults.handshakeAsServer;
|
||||
ss->enableSSL2 = ssl_defaults.enableSSL2;
|
||||
ss->enableSSL3 = ssl_defaults.enableSSL3;
|
||||
ss->enableTLS = ssl_defaults.enableTLS ;
|
||||
ss->fdx = ssl_defaults.fdx;
|
||||
ss->v2CompatibleHello = ssl_defaults.v2CompatibleHello;
|
||||
ss->detectRollBack = ssl_defaults.detectRollBack;
|
||||
ss->noStepDown = ssl_defaults.noStepDown;
|
||||
ss->noCache = ssl_defaults.noCache;
|
||||
ss->opt = ssl_defaults;
|
||||
ss->opt.useSocks = PR_FALSE;
|
||||
ss->opt.noLocks = !makeLocks;
|
||||
|
||||
ss->peerID = NULL;
|
||||
ss->rTimeout = PR_INTERVAL_NO_TIMEOUT;
|
||||
ss->wTimeout = PR_INTERVAL_NO_TIMEOUT;
|
||||
|
@ -1909,7 +1964,7 @@ ssl_NewSocket(void)
|
|||
sslServerCerts * sc = ss->serverCerts + i;
|
||||
sc->serverCert = NULL;
|
||||
sc->serverCertChain = NULL;
|
||||
sc->serverKey = NULL;
|
||||
sc->serverKeyPair = NULL;
|
||||
sc->serverKeyBits = 0;
|
||||
}
|
||||
ss->stepDownKeyPair = NULL;
|
||||
|
@ -1927,25 +1982,14 @@ ssl_NewSocket(void)
|
|||
ssl2_InitSocketPolicy(ss);
|
||||
ssl3_InitSocketPolicy(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;
|
||||
if (makeLocks) {
|
||||
status = ssl_MakeLocks(ss);
|
||||
if (status != SECSuccess)
|
||||
goto loser;
|
||||
}
|
||||
status = ssl_CreateSecurityInfo(ss);
|
||||
if (status != SECSuccess) goto loser;
|
||||
if (status != SECSuccess)
|
||||
goto loser;
|
||||
status = ssl_InitGather(&ss->gs);
|
||||
if (status != SECSuccess) {
|
||||
loser:
|
||||
|
|
Загрузка…
Ссылка в новой задаче