Go to:
Gentoo Home
Documentation
Forums
Lists
Bugs
Planet
Store
Wiki
Get Gentoo!
Gentoo's Bugzilla – Attachment 500618 Details for
Bug 604978
net-libs/nodejs-7.3.0 with dev-libs/openssl-1.1.0c - node_crypto.h:95:54: error: invalid application of 'sizeof' to incomplete type 'SSL_CTX {aka ssl_ctx_st}'
Home
|
New
–
[Ex]
|
Browse
|
Search
|
Privacy Policy
|
[?]
|
Reports
|
Requests
|
Help
|
New Account
|
Log In
[x]
|
Forgot Password
Login:
[x]
[patch]
nodejs-8.8.1-openssl-1.1-p1-pr16130.patch
nodejs-8.8.1-openssl-1.1-p1-pr16130.patch (text/plain), 66.40 KB, created by
Mark Wright
on 2017-10-29 05:42:37 UTC
(
hide
)
Description:
nodejs-8.8.1-openssl-1.1-p1-pr16130.patch
Filename:
MIME Type:
Creator:
Mark Wright
Created:
2017-10-29 05:42:37 UTC
Size:
66.40 KB
patch
obsolete
>--- node-v8.8.1-orig/src/node_crypto.cc 2017-10-26 07:10:32.000000000 +1100 >+++ node-v8.8.1/src/node_crypto.cc 2017-10-29 11:51:11.037518215 +1100 >@@ -116,6 +116,120 @@ > using v8::Value; > > >+#if OPENSSL_VERSION_NUMBER < 0x10100000L >+static void RSA_get0_key(const RSA* r, const BIGNUM** n, const BIGNUM** e, >+ const BIGNUM** d) { >+ if (n != nullptr) { >+ *n = r->n; >+ } >+ if (e != nullptr) { >+ *e = r->e; >+ } >+ if (d != nullptr) { >+ *d = r->d; >+ } >+} >+ >+static void DH_get0_pqg(const DH* dh, const BIGNUM** p, const BIGNUM** q, >+ const BIGNUM** g) { >+ if (p != nullptr) { >+ *p = dh->p; >+ } >+ if (q != nullptr) { >+ *q = dh->q; >+ } >+ if (g != nullptr) { >+ *g = dh->g; >+ } >+} >+ >+static int DH_set0_pqg(DH* dh, BIGNUM* p, BIGNUM* q, BIGNUM* g) { >+ if ((dh->p == nullptr && p == nullptr) || >+ (dh->g == nullptr && g == nullptr)) { >+ return 0; >+ } >+ >+ if (p != nullptr) { >+ BN_free(dh->p); >+ dh->p = p; >+ } >+ if (q != nullptr) { >+ BN_free(dh->q); >+ dh->q = q; >+ } >+ if (g != nullptr) { >+ BN_free(dh->g); >+ dh->g = g; >+ } >+ >+ return 1; >+} >+ >+static void DH_get0_key(const DH* dh, const BIGNUM** pub_key, >+ const BIGNUM** priv_key) { >+ if (pub_key != nullptr) { >+ *pub_key = dh->pub_key; >+ } >+ if (priv_key != nullptr) { >+ *priv_key = dh->priv_key; >+ } >+} >+ >+static int DH_set0_key(DH* dh, BIGNUM* pub_key, BIGNUM* priv_key) { >+ if (pub_key != nullptr) { >+ BN_free(dh->pub_key); >+ dh->pub_key = pub_key; >+ } >+ if (priv_key != nullptr) { >+ BN_free(dh->priv_key); >+ dh->priv_key = priv_key; >+ } >+ >+ return 1; >+} >+ >+static const SSL_METHOD* TLS_method() { return SSLv23_method(); } >+ >+static void SSL_SESSION_get0_ticket(const SSL_SESSION* s, >+ const unsigned char** tick, size_t* len) { >+ *len = s->tlsext_ticklen; >+ if (tick != nullptr) { >+ *tick = s->tlsext_tick; >+ } >+} >+ >+#define SSL_get_tlsext_status_type(ssl) (ssl->tlsext_status_type) >+ >+#if !defined(OPENSSL_IS_BORINGSSL) >+static int X509_STORE_up_ref(X509_STORE* store) { >+ CRYPTO_add(&store->references, 1, CRYPTO_LOCK_X509_STORE); >+ return 1; >+} >+ >+static int X509_up_ref(X509* cert) { >+ CRYPTO_add(&cert->references, 1, CRYPTO_LOCK_X509); >+ return 1; >+} >+#endif // !OPENSSL_IS_BORINGSSL >+ >+#define EVP_MD_CTX_new EVP_MD_CTX_create >+#define EVP_MD_CTX_free EVP_MD_CTX_destroy >+ >+HMAC_CTX* HMAC_CTX_new() { >+ HMAC_CTX* ctx = Malloc<HMAC_CTX>(1); >+ HMAC_CTX_init(ctx); >+ return ctx; >+} >+ >+void HMAC_CTX_free(HMAC_CTX* ctx) { >+ if (ctx == nullptr) { >+ return; >+ } >+ HMAC_CTX_cleanup(ctx); >+ free(ctx); >+} >+#endif // OPENSSL_VERSION_NUMBER < 0x10100000L >+ > // Subject DER of CNNIC ROOT CA and CNNIC EV ROOT CA are taken from > // https://hg.mozilla.org/mozilla-central/file/98820360ab66/security/ > // certverifier/NSSCertDBTrustDomain.cpp#l672 >@@ -144,8 +258,6 @@ > d2i_X509_NAME(nullptr, &cnnic_ev_p, > sizeof(CNNIC_EV_ROOT_CA_SUBJECT_DATA)-1); > >-static Mutex* mutexes; >- > static const char* const root_certs[] = { > #include "node_root_certs.h" // NOLINT(build/include_order) > }; >@@ -160,11 +272,19 @@ > template void SSLWrap<TLSWrap>::InitNPN(SecureContext* sc); > template void SSLWrap<TLSWrap>::SetSNIContext(SecureContext* sc); > template int SSLWrap<TLSWrap>::SetCACerts(SecureContext* sc); >+#if OPENSSL_VERSION_NUMBER < 0x10100000L > template SSL_SESSION* SSLWrap<TLSWrap>::GetSessionCallback( > SSL* s, > unsigned char* key, > int len, > int* copy); >+#else >+template SSL_SESSION* SSLWrap<TLSWrap>::GetSessionCallback( >+ SSL* s, >+ const unsigned char* key, >+ int len, >+ int* copy); >+#endif > template int SSLWrap<TLSWrap>::NewSessionCallback(SSL* s, > SSL_SESSION* sess); > template void SSLWrap<TLSWrap>::OnClientHello( >@@ -204,6 +324,9 @@ > void* arg); > #endif // TLSEXT_TYPE_application_layer_protocol_negotiation > >+#if OPENSSL_VERSION_NUMBER < 0x10100000L >+static Mutex* mutexes; >+ > static void crypto_threadid_cb(CRYPTO_THREADID* tid) { > static_assert(sizeof(uv_thread_t) <= sizeof(void*), > "uv_thread_t does not fit in a pointer"); >@@ -226,6 +349,7 @@ > else > mutex->Unlock(); > } >+#endif > > > static int PasswordCallback(char *buf, int size, int rwflag, void *u) { >@@ -429,12 +553,12 @@ > ASSIGN_OR_RETURN_UNWRAP(&sc, args.Holder()); > Environment* env = sc->env(); > >- const SSL_METHOD* method = SSLv23_method(); >+ const SSL_METHOD* method = TLS_method(); > > if (args.Length() == 1 && args[0]->IsString()) { > const node::Utf8Value sslmethod(env->isolate(), args[0]); > >- // Note that SSLv2 and SSLv3 are disallowed but SSLv2_method and friends >+ // Note that SSLv2 and SSLv3 are disallowed but SSLv23_method and friends > // are still accepted. They are OpenSSL's way of saying that all known > // protocols are supported unless explicitly disabled (which we do below > // for SSLv2 and SSLv3.) >@@ -482,7 +606,7 @@ > sc->ctx_ = SSL_CTX_new(method); > SSL_CTX_set_app_data(sc->ctx_, sc); > >- // Disable SSLv2 in the case when method == SSLv23_method() and the >+ // Disable SSLv2 in the case when method == TLS_method() and the > // cipher list contains SSLv2 ciphers (not the default, should be rare.) > // The bundled OpenSSL doesn't have SSLv2 support but the system OpenSSL may. > // SSLv3 is disabled because it's susceptible to downgrade attacks (POODLE.) >@@ -496,6 +620,19 @@ > SSL_SESS_CACHE_NO_AUTO_CLEAR); > SSL_CTX_sess_set_get_cb(sc->ctx_, SSLWrap<Connection>::GetSessionCallback); > SSL_CTX_sess_set_new_cb(sc->ctx_, SSLWrap<Connection>::NewSessionCallback); >+ >+#if OPENSSL_VERSION_NUMBER >= 0x10100000L >+ // OpenSSL 1.1.0 changed the ticket key size, but the OpenSSL 1.0.x size was >+ // exposed in the public API. To retain compatibility, install a callback >+ // which restores the old algorithm. >+ if (RAND_bytes(sc->ticket_key_name_, sizeof(sc->ticket_key_name_)) <= 0 || >+ RAND_bytes(sc->ticket_key_hmac_, sizeof(sc->ticket_key_hmac_)) <= 0 || >+ RAND_bytes(sc->ticket_key_aes_, sizeof(sc->ticket_key_aes_)) <= 0) { >+ return env->ThrowError("Error generating ticket keys"); >+ } >+ SSL_CTX_set_tlsext_ticket_key_cb(sc->ctx_, >+ SecureContext::TicketCompatibilityCallback); >+#endif > } > > >@@ -573,19 +710,12 @@ > > > int SSL_CTX_get_issuer(SSL_CTX* ctx, X509* cert, X509** issuer) { >- int ret; >- > X509_STORE* store = SSL_CTX_get_cert_store(ctx); >- X509_STORE_CTX store_ctx; >- >- ret = X509_STORE_CTX_init(&store_ctx, store, nullptr, nullptr); >- if (!ret) >- goto end; >- >- ret = X509_STORE_CTX_get1_issuer(issuer, &store_ctx, cert); >- X509_STORE_CTX_cleanup(&store_ctx); >- >- end: >+ X509_STORE_CTX* store_ctx = X509_STORE_CTX_new(); >+ int ret = store_ctx != nullptr && >+ X509_STORE_CTX_init(store_ctx, store, nullptr, nullptr) == 1 && >+ X509_STORE_CTX_get1_issuer(issuer, store_ctx, cert) == 1; >+ X509_STORE_CTX_free(store_ctx); > return ret; > } > >@@ -676,7 +806,6 @@ > x = PEM_read_bio_X509_AUX(in, nullptr, NoPasswordCallback, nullptr); > > if (x == nullptr) { >- SSLerr(SSL_F_SSL_CTX_USE_CERTIFICATE_CHAIN_FILE, ERR_R_PEM_LIB); > return 0; > } > >@@ -687,7 +816,6 @@ > // Read extra certs > STACK_OF(X509)* extra_certs = sk_X509_new_null(); > if (extra_certs == nullptr) { >- SSLerr(SSL_F_SSL_CTX_USE_CERTIFICATE_CHAIN_FILE, ERR_R_MALLOC_FAILURE); > goto done; > } > >@@ -770,22 +898,6 @@ > } > > >-#if OPENSSL_VERSION_NUMBER < 0x10100000L && !defined(OPENSSL_IS_BORINGSSL) >-// This section contains OpenSSL 1.1.0 functions reimplemented for OpenSSL >-// 1.0.2 so that the following code can be written without lots of #if lines. >- >-static int X509_STORE_up_ref(X509_STORE* store) { >- CRYPTO_add(&store->references, 1, CRYPTO_LOCK_X509_STORE); >- return 1; >-} >- >-static int X509_up_ref(X509* cert) { >- CRYPTO_add(&cert->references, 1, CRYPTO_LOCK_X509); >- return 1; >-} >-#endif // OPENSSL_VERSION_NUMBER < 0x10100000L && !OPENSSL_IS_BORINGSSL >- >- > static X509_STORE* NewRootCertStore() { > static std::vector<X509*> root_certs_vector; > if (root_certs_vector.empty()) { >@@ -975,8 +1087,10 @@ > > node::Utf8Value curve(env->isolate(), args[0]); > >+#if OPENSSL_VERSION_NUMBER < 0x10100000L > SSL_CTX_set_options(sc->ctx_, SSL_OP_SINGLE_ECDH_USE); > SSL_CTX_set_ecdh_auto(sc->ctx_, 1); >+#endif > > if (strcmp(*curve, "auto") == 0) > return; >@@ -1008,7 +1122,9 @@ > if (dh == nullptr) > return; > >- const int size = BN_num_bits(dh->p); >+ const BIGNUM* p; >+ DH_get0_pqg(dh, &p, nullptr, nullptr); >+ const int size = BN_num_bits(p); > if (size < 1024) { > return env->ThrowError("DH parameter is less than 1024 bits"); > } else if (size < 2048) { >@@ -1193,11 +1309,17 @@ > ASSIGN_OR_RETURN_UNWRAP(&wrap, args.Holder()); > > Local<Object> buff = Buffer::New(wrap->env(), 48).ToLocalChecked(); >+#if OPENSSL_VERSION_NUMBER >= 0x10100000L >+ memcpy(Buffer::Data(buff), wrap->ticket_key_name_, 16); >+ memcpy(Buffer::Data(buff) + 16, wrap->ticket_key_hmac_, 16); >+ memcpy(Buffer::Data(buff) + 32, wrap->ticket_key_aes_, 16); >+#else > if (SSL_CTX_get_tlsext_ticket_keys(wrap->ctx_, > Buffer::Data(buff), > Buffer::Length(buff)) != 1) { > return wrap->env()->ThrowError("Failed to fetch tls ticket keys"); > } >+#endif > > args.GetReturnValue().Set(buff); > #endif // !def(OPENSSL_NO_TLSEXT) && def(SSL_CTX_get_tlsext_ticket_keys) >@@ -1220,11 +1342,17 @@ > return env->ThrowTypeError("Ticket keys length must be 48 bytes"); > } > >+#if OPENSSL_VERSION_NUMBER >= 0x10100000L >+ memcpy(wrap->ticket_key_name_, Buffer::Data(args[0]), 16); >+ memcpy(wrap->ticket_key_hmac_, Buffer::Data(args[0]) + 16, 16); >+ memcpy(wrap->ticket_key_aes_, Buffer::Data(args[0]) + 32, 16); >+#else > if (SSL_CTX_set_tlsext_ticket_keys(wrap->ctx_, > Buffer::Data(args[0]), > Buffer::Length(args[0])) != 1) { > return env->ThrowError("Failed to fetch tls ticket keys"); > } >+#endif > > args.GetReturnValue().Set(true); > #endif // !def(OPENSSL_NO_TLSEXT) && def(SSL_CTX_get_tlsext_ticket_keys) >@@ -1335,6 +1463,42 @@ > } > > >+#if OPENSSL_VERSION_NUMBER >= 0x10100000L >+int SecureContext::TicketCompatibilityCallback(SSL* ssl, >+ unsigned char* name, >+ unsigned char* iv, >+ EVP_CIPHER_CTX* ectx, >+ HMAC_CTX* hctx, >+ int enc) { >+ SecureContext* sc = static_cast<SecureContext*>( >+ SSL_CTX_get_app_data(SSL_get_SSL_CTX(ssl))); >+ >+ if (enc) { >+ memcpy(name, sc->ticket_key_name_, sizeof(sc->ticket_key_name_)); >+ if (RAND_bytes(iv, 16) <= 0 || >+ EVP_EncryptInit_ex(ectx, EVP_aes_128_cbc(), nullptr, >+ sc->ticket_key_aes_, iv) <= 0 || >+ HMAC_Init_ex(hctx, sc->ticket_key_hmac_, sizeof(sc->ticket_key_hmac_), >+ EVP_sha256(), nullptr) <= 0) { >+ return -1; >+ } >+ return 1; >+ } >+ >+ if (memcmp(name, sc->ticket_key_name_, sizeof(sc->ticket_key_name_)) != 0) { >+ // The ticket key name does not match. Discard the ticket. >+ return 0; >+ } >+ >+ if (EVP_DecryptInit_ex(ectx, EVP_aes_128_cbc(), nullptr, sc->ticket_key_aes_, >+ iv) <= 0 || >+ HMAC_Init_ex(hctx, sc->ticket_key_hmac_, sizeof(sc->ticket_key_hmac_), >+ EVP_sha256(), nullptr) <= 0) { >+ return -1; >+ } >+ return 1; >+} >+#endif > > > void SecureContext::CtxGetter(Local<String> property, >@@ -1439,11 +1603,19 @@ > } > > >+#if OPENSSL_VERSION_NUMBER < 0x10100000L > template <class Base> > SSL_SESSION* SSLWrap<Base>::GetSessionCallback(SSL* s, > unsigned char* key, > int len, > int* copy) { >+#else >+template <class Base> >+SSL_SESSION* SSLWrap<Base>::GetSessionCallback(SSL* s, >+ const unsigned char* key, >+ int len, >+ int* copy) { >+#endif > Base* w = static_cast<Base*>(SSL_get_app_data(s)); > > *copy = 0; >@@ -1620,14 +1792,17 @@ > rsa = EVP_PKEY_get1_RSA(pkey); > > if (rsa != nullptr) { >- BN_print(bio, rsa->n); >+ const BIGNUM* n; >+ const BIGNUM* e; >+ RSA_get0_key(rsa, &n, &e, nullptr); >+ BN_print(bio, n); > BIO_get_mem_ptr(bio, &mem); > info->Set(env->modulus_string(), > String::NewFromUtf8(env->isolate(), mem->data, > String::kNormalString, mem->length)); > (void) BIO_reset(bio); > >- uint64_t exponent_word = static_cast<uint64_t>(BN_get_word(rsa->e)); >+ uint64_t exponent_word = static_cast<uint64_t>(BN_get_word(e)); > uint32_t lo = static_cast<uint32_t>(exponent_word); > uint32_t hi = static_cast<uint32_t>(exponent_word >> 32); > if (hi == 0) { >@@ -1953,13 +2128,18 @@ > Environment* env = w->ssl_env(); > > SSL_SESSION* sess = SSL_get_session(w->ssl_); >- if (sess == nullptr || sess->tlsext_tick == nullptr) >+ if (sess == nullptr) >+ return; >+ >+ const unsigned char *ticket; >+ size_t length; >+ SSL_SESSION_get0_ticket(sess, &ticket, &length); >+ >+ if (ticket == nullptr) > return; > > Local<Object> buff = Buffer::Copy( >- env, >- reinterpret_cast<char*>(sess->tlsext_tick), >- sess->tlsext_ticklen).ToLocalChecked(); >+ env, reinterpret_cast<const char*>(ticket), length).ToLocalChecked(); > > args.GetReturnValue().Set(buff); > } >@@ -2150,9 +2330,8 @@ > Local<Object> info = Object::New(env->isolate()); > const char* cipher_name = SSL_CIPHER_get_name(c); > info->Set(env->name_string(), OneByteString(args.GetIsolate(), cipher_name)); >- const char* cipher_version = SSL_CIPHER_get_version(c); > info->Set(env->version_string(), >- OneByteString(args.GetIsolate(), cipher_version)); >+ OneByteString(args.GetIsolate(), "TLSv1/SSLv3")); > args.GetReturnValue().Set(info); > } > >@@ -2332,20 +2511,12 @@ > unsigned alpn_protos_len = Buffer::Length(alpn_buffer); > int status = SSL_select_next_proto(const_cast<unsigned char**>(out), outlen, > alpn_protos, alpn_protos_len, in, inlen); >- >- switch (status) { >- case OPENSSL_NPN_NO_OVERLAP: >- // According to 3.2. Protocol Selection of RFC7301, >- // fatal no_application_protocol alert shall be sent >- // but current openssl does not support it yet. See >- // https://rt.openssl.org/Ticket/Display.html?id=3463&user=guest&pass=guest >- // Instead, we send a warning alert for now. >- return SSL_TLSEXT_ERR_ALERT_WARNING; >- case OPENSSL_NPN_NEGOTIATED: >- return SSL_TLSEXT_ERR_OK; >- default: >- return SSL_TLSEXT_ERR_ALERT_FATAL; >- } >+ // According to 3.2. Protocol Selection of RFC7301, fatal >+ // no_application_protocol alert shall be sent but OpenSSL 1.0.2 does not >+ // support it yet. See >+ // https://rt.openssl.org/Ticket/Display.html?id=3463&user=guest&pass=guest >+ return status == OPENSSL_NPN_NEGOTIATED ? SSL_TLSEXT_ERR_OK >+ : SSL_TLSEXT_ERR_NOACK; > } > #endif // TLSEXT_TYPE_application_layer_protocol_negotiation > >@@ -2486,7 +2657,7 @@ > > bool ocsp = false; > #ifdef NODE__HAVE_TLSEXT_STATUS_CB >- ocsp = s->tlsext_status_type == TLSEXT_STATUSTYPE_ocsp; >+ ocsp = SSL_get_tlsext_status_type(s) == TLSEXT_STATUSTYPE_ocsp; > #endif > > info->Set(env->ocsp_request_string(), Boolean::New(env->isolate(), ocsp)); >@@ -3363,7 +3534,7 @@ > } > #endif // NODE_FIPS_MODE > >- CHECK_EQ(initialised_, false); >+ CHECK_EQ(ctx_, nullptr); > const EVP_CIPHER* const cipher = EVP_get_cipherbyname(cipher_type); > if (cipher == nullptr) { > return env()->ThrowError("Unknown cipher"); >@@ -3381,11 +3552,11 @@ > key, > iv); > >- EVP_CIPHER_CTX_init(&ctx_); >+ ctx_ = EVP_CIPHER_CTX_new(); > const bool encrypt = (kind_ == kCipher); >- EVP_CipherInit_ex(&ctx_, cipher, nullptr, nullptr, nullptr, encrypt); >+ EVP_CipherInit_ex(ctx_, cipher, nullptr, nullptr, nullptr, encrypt); > >- int mode = EVP_CIPHER_CTX_mode(&ctx_); >+ int mode = EVP_CIPHER_CTX_mode(ctx_); > if (encrypt && (mode == EVP_CIPH_CTR_MODE || mode == EVP_CIPH_GCM_MODE || > mode == EVP_CIPH_CCM_MODE)) { > ProcessEmitWarning(env(), "Use Cipheriv for counter mode of %s", >@@ -3393,17 +3564,16 @@ > } > > if (mode == EVP_CIPH_WRAP_MODE) >- EVP_CIPHER_CTX_set_flags(&ctx_, EVP_CIPHER_CTX_FLAG_WRAP_ALLOW); >+ EVP_CIPHER_CTX_set_flags(ctx_, EVP_CIPHER_CTX_FLAG_WRAP_ALLOW); > >- CHECK_EQ(1, EVP_CIPHER_CTX_set_key_length(&ctx_, key_len)); >+ CHECK_EQ(1, EVP_CIPHER_CTX_set_key_length(ctx_, key_len)); > >- EVP_CipherInit_ex(&ctx_, >+ EVP_CipherInit_ex(ctx_, > nullptr, > nullptr, > reinterpret_cast<unsigned char*>(key), > reinterpret_cast<unsigned char*>(iv), > kind_ == kCipher); >- initialised_ = true; > } > > >@@ -3446,32 +3616,33 @@ > return env()->ThrowError("Invalid IV length"); > } > >- EVP_CIPHER_CTX_init(&ctx_); >+ ctx_ = EVP_CIPHER_CTX_new(); > > if (mode == EVP_CIPH_WRAP_MODE) >- EVP_CIPHER_CTX_set_flags(&ctx_, EVP_CIPHER_CTX_FLAG_WRAP_ALLOW); >+ EVP_CIPHER_CTX_set_flags(ctx_, EVP_CIPHER_CTX_FLAG_WRAP_ALLOW); > > const bool encrypt = (kind_ == kCipher); >- EVP_CipherInit_ex(&ctx_, cipher, nullptr, nullptr, nullptr, encrypt); >+ EVP_CipherInit_ex(ctx_, cipher, nullptr, nullptr, nullptr, encrypt); > > if (is_gcm_mode && >- !EVP_CIPHER_CTX_ctrl(&ctx_, EVP_CTRL_GCM_SET_IVLEN, iv_len, nullptr)) { >- EVP_CIPHER_CTX_cleanup(&ctx_); >+ !EVP_CIPHER_CTX_ctrl(ctx_, EVP_CTRL_GCM_SET_IVLEN, iv_len, nullptr)) { >+ EVP_CIPHER_CTX_free(ctx_); >+ ctx_ = nullptr; > return env()->ThrowError("Invalid IV length"); > } > >- if (!EVP_CIPHER_CTX_set_key_length(&ctx_, key_len)) { >- EVP_CIPHER_CTX_cleanup(&ctx_); >+ if (!EVP_CIPHER_CTX_set_key_length(ctx_, key_len)) { >+ EVP_CIPHER_CTX_free(ctx_); >+ ctx_ = nullptr; > return env()->ThrowError("Invalid key length"); > } > >- EVP_CipherInit_ex(&ctx_, >+ EVP_CipherInit_ex(ctx_, > nullptr, > nullptr, > reinterpret_cast<const unsigned char*>(key), > reinterpret_cast<const unsigned char*>(iv), > kind_ == kCipher); >- initialised_ = true; > } > > >@@ -3499,8 +3670,8 @@ > > bool CipherBase::IsAuthenticatedMode() const { > // Check if this cipher operates in an AEAD mode that we support. >- CHECK_EQ(initialised_, true); >- const EVP_CIPHER* const cipher = EVP_CIPHER_CTX_cipher(&ctx_); >+ CHECK_NE(ctx_, nullptr); >+ const EVP_CIPHER* const cipher = EVP_CIPHER_CTX_cipher(ctx_); > int mode = EVP_CIPHER_mode(cipher); > return mode == EVP_CIPH_GCM_MODE; > } >@@ -3512,7 +3683,7 @@ > ASSIGN_OR_RETURN_UNWRAP(&cipher, args.Holder()); > > // Only callable after Final and if encrypting. >- if (cipher->initialised_ || >+ if (cipher->ctx_ || > cipher->kind_ != kCipher || > cipher->auth_tag_len_ == 0) { > return env->ThrowError("Attempting to get auth tag in unsupported state"); >@@ -3533,7 +3704,7 @@ > CipherBase* cipher; > ASSIGN_OR_RETURN_UNWRAP(&cipher, args.Holder()); > >- if (!cipher->initialised_ || >+ if (!cipher->ctx_ || > !cipher->IsAuthenticatedMode() || > cipher->kind_ != kDecipher) { > return env->ThrowError("Attempting to set auth tag in unsupported state"); >@@ -3551,10 +3722,10 @@ > > > bool CipherBase::SetAAD(const char* data, unsigned int len) { >- if (!initialised_ || !IsAuthenticatedMode()) >+ if (!ctx_ || !IsAuthenticatedMode()) > return false; > int outlen; >- if (!EVP_CipherUpdate(&ctx_, >+ if (!EVP_CipherUpdate(ctx_, > nullptr, > &outlen, > reinterpret_cast<const unsigned char*>(data), >@@ -3582,21 +3753,21 @@ > int len, > unsigned char** out, > int* out_len) { >- if (!initialised_) >+ if (!ctx_) > return 0; > > // on first update: > if (kind_ == kDecipher && IsAuthenticatedMode() && auth_tag_len_ > 0) { >- EVP_CIPHER_CTX_ctrl(&ctx_, >+ EVP_CIPHER_CTX_ctrl(ctx_, > EVP_CTRL_GCM_SET_TAG, > auth_tag_len_, > reinterpret_cast<unsigned char*>(auth_tag_)); > auth_tag_len_ = 0; > } > >- *out_len = len + EVP_CIPHER_CTX_block_size(&ctx_); >+ *out_len = len + EVP_CIPHER_CTX_block_size(ctx_); > *out = Malloc<unsigned char>(static_cast<size_t>(*out_len)); >- return EVP_CipherUpdate(&ctx_, >+ return EVP_CipherUpdate(ctx_, > *out, > out_len, > reinterpret_cast<const unsigned char*>(data), >@@ -3644,9 +3815,9 @@ > > > bool CipherBase::SetAutoPadding(bool auto_padding) { >- if (!initialised_) >+ if (!ctx_) > return false; >- return EVP_CIPHER_CTX_set_padding(&ctx_, auto_padding); >+ return EVP_CIPHER_CTX_set_padding(ctx_, auto_padding); > } > > >@@ -3662,22 +3833,22 @@ > > > bool CipherBase::Final(unsigned char** out, int *out_len) { >- if (!initialised_) >+ if (!ctx_) > return false; > > *out = Malloc<unsigned char>( >- static_cast<size_t>(EVP_CIPHER_CTX_block_size(&ctx_))); >- int r = EVP_CipherFinal_ex(&ctx_, *out, out_len); >+ static_cast<size_t>(EVP_CIPHER_CTX_block_size(ctx_))); >+ int r = EVP_CipherFinal_ex(ctx_, *out, out_len); > > if (r == 1 && kind_ == kCipher && IsAuthenticatedMode()) { > auth_tag_len_ = sizeof(auth_tag_); >- r = EVP_CIPHER_CTX_ctrl(&ctx_, EVP_CTRL_GCM_GET_TAG, auth_tag_len_, >+ r = EVP_CIPHER_CTX_ctrl(ctx_, EVP_CTRL_GCM_GET_TAG, auth_tag_len_, > reinterpret_cast<unsigned char*>(auth_tag_)); > CHECK_EQ(r, 1); > } > >- EVP_CIPHER_CTX_cleanup(&ctx_); >- initialised_ = false; >+ EVP_CIPHER_CTX_free(ctx_); >+ ctx_ = nullptr; > > return r == 1; > } >@@ -3688,7 +3859,7 @@ > > CipherBase* cipher; > ASSIGN_OR_RETURN_UNWRAP(&cipher, args.Holder()); >- if (!cipher->initialised_) return env->ThrowError("Unsupported state"); >+ if (!cipher->ctx_) return env->ThrowError("Unsupported state"); > > unsigned char* out_value = nullptr; > int out_len = -1; >@@ -3720,6 +3891,11 @@ > } > > >+Hmac::~Hmac() { >+ HMAC_CTX_free(ctx_); >+} >+ >+ > void Hmac::Initialize(Environment* env, v8::Local<v8::Object> target) { > Local<FunctionTemplate> t = env->NewFunctionTemplate(New); > >@@ -3747,14 +3923,16 @@ > if (md == nullptr) { > return env()->ThrowError("Unknown message digest"); > } >- HMAC_CTX_init(&ctx_); > if (key_len == 0) { > key = ""; > } >- if (!HMAC_Init_ex(&ctx_, key, key_len, md, nullptr)) { >+ ctx_ = HMAC_CTX_new(); >+ if (ctx_ == nullptr || >+ !HMAC_Init_ex(ctx_, key, key_len, md, nullptr)) { >+ HMAC_CTX_free(ctx_); >+ ctx_ = nullptr; > return ThrowCryptoError(env(), ERR_get_error()); > } >- initialised_ = true; > } > > >@@ -3778,9 +3956,9 @@ > > > bool Hmac::HmacUpdate(const char* data, int len) { >- if (!initialised_) >+ if (!ctx_) > return false; >- int r = HMAC_Update(&ctx_, reinterpret_cast<const unsigned char*>(data), len); >+ int r = HMAC_Update(ctx_, reinterpret_cast<const unsigned char*>(data), len); > return r == 1; > } > >@@ -3831,10 +4009,10 @@ > unsigned char md_value[EVP_MAX_MD_SIZE]; > unsigned int md_len = 0; > >- if (hmac->initialised_) { >- HMAC_Final(&hmac->ctx_, md_value, &md_len); >- HMAC_CTX_cleanup(&hmac->ctx_); >- hmac->initialised_ = false; >+ if (hmac->ctx_) { >+ HMAC_Final(hmac->ctx_, md_value, &md_len); >+ HMAC_CTX_free(hmac->ctx_); >+ hmac->ctx_ = nullptr; > } > > Local<Value> error; >@@ -3853,6 +4031,11 @@ > } > > >+Hash::~Hash() { >+ EVP_MD_CTX_free(mdctx_); >+} >+ >+ > void Hash::Initialize(Environment* env, v8::Local<v8::Object> target) { > Local<FunctionTemplate> t = env->NewFunctionTemplate(New); > >@@ -3887,20 +4070,22 @@ > const EVP_MD* md = EVP_get_digestbyname(hash_type); > if (md == nullptr) > return false; >- EVP_MD_CTX_init(&mdctx_); >- if (EVP_DigestInit_ex(&mdctx_, md, nullptr) <= 0) { >+ mdctx_ = EVP_MD_CTX_new(); >+ if (mdctx_ == nullptr || >+ EVP_DigestInit_ex(mdctx_, md, nullptr) <= 0) { >+ EVP_MD_CTX_free(mdctx_); >+ mdctx_ = nullptr; > return false; > } >- initialised_ = true; > finalized_ = false; > return true; > } > > > bool Hash::HashUpdate(const char* data, int len) { >- if (!initialised_) >+ if (!mdctx_) > return false; >- EVP_DigestUpdate(&mdctx_, data, len); >+ EVP_DigestUpdate(mdctx_, data, len); > return true; > } > >@@ -3965,8 +4150,7 @@ > unsigned char md_value[EVP_MAX_MD_SIZE]; > unsigned int md_len; > >- EVP_DigestFinal_ex(&hash->mdctx_, md_value, &md_len); >- EVP_MD_CTX_cleanup(&hash->mdctx_); >+ EVP_DigestFinal_ex(hash->mdctx_, md_value, &md_len); > hash->finalized_ = true; > > Local<Value> error; >@@ -3985,6 +4169,46 @@ > } > > >+SignBase::~SignBase() { >+ EVP_MD_CTX_free(mdctx_); >+} >+ >+ >+SignBase::Error SignBase::Init(const char* sign_type) { >+ CHECK_EQ(mdctx_, nullptr); >+#if OPENSSL_VERSION_NUMBER >= 0x10100000L >+ // Historically, "dss1" and "DSS1" were DSA aliases for SHA-1 >+ // exposed through the public API. >+ if (strcmp(sign_type, "dss1") == 0 || >+ strcmp(sign_type, "DSS1") == 0) { >+ sign_type = "SHA1"; >+ } >+#endif >+ const EVP_MD* md = EVP_get_digestbyname(sign_type); >+ if (md == nullptr) >+ return kSignUnknownDigest; >+ >+ mdctx_ = EVP_MD_CTX_new(); >+ if (mdctx_ == nullptr || >+ !EVP_DigestInit_ex(mdctx_, md, nullptr)) { >+ EVP_MD_CTX_free(mdctx_); >+ mdctx_ = nullptr; >+ return kSignInit; >+ } >+ >+ return kSignOk; >+} >+ >+ >+SignBase::Error SignBase::Update(const char* data, int len) { >+ if (!mdctx_) >+ return kSignNotInitialised; >+ if (!EVP_DigestUpdate(mdctx_, data, len)) >+ return kSignUpdate; >+ return kSignOk; >+} >+ >+ > void SignBase::CheckThrow(SignBase::Error error) { > HandleScope scope(env()->isolate()); > >@@ -4058,21 +4282,6 @@ > } > > >-SignBase::Error Sign::SignInit(const char* sign_type) { >- CHECK_EQ(initialised_, false); >- const EVP_MD* md = EVP_get_digestbyname(sign_type); >- if (md == nullptr) >- return kSignUnknownDigest; >- >- EVP_MD_CTX_init(&mdctx_); >- if (!EVP_DigestInit_ex(&mdctx_, md, nullptr)) >- return kSignInit; >- initialised_ = true; >- >- return kSignOk; >-} >- >- > void Sign::SignInit(const FunctionCallbackInfo<Value>& args) { > Sign* sign; > ASSIGN_OR_RETURN_UNWRAP(&sign, args.Holder()); >@@ -4085,16 +4294,7 @@ > THROW_AND_RETURN_IF_NOT_STRING(args[0], "Sign type"); > > const node::Utf8Value sign_type(args.GetIsolate(), args[0]); >- sign->CheckThrow(sign->SignInit(*sign_type)); >-} >- >- >-SignBase::Error Sign::SignUpdate(const char* data, int len) { >- if (!initialised_) >- return kSignNotInitialised; >- if (!EVP_DigestUpdate(&mdctx_, data, len)) >- return kSignUpdate; >- return kSignOk; >+ sign->CheckThrow(sign->Init(*sign_type)); > } > > >@@ -4112,11 +4312,11 @@ > StringBytes::InlineDecoder decoder; > if (!decoder.Decode(env, args[0].As<String>(), args[1], UTF8)) > return; >- err = sign->SignUpdate(decoder.out(), decoder.size()); >+ err = sign->Update(decoder.out(), decoder.size()); > } else { > char* buf = Buffer::Data(args[0]); > size_t buflen = Buffer::Length(args[0]); >- err = sign->SignUpdate(buf, buflen); >+ err = sign->Update(buf, buflen); > } > > sign->CheckThrow(err); >@@ -4160,7 +4360,7 @@ > unsigned int* sig_len, > int padding, > int salt_len) { >- if (!initialised_) >+ if (!mdctx_) > return kSignNotInitialised; > > BIO* bp = nullptr; >@@ -4205,18 +4405,17 @@ > } > #endif // NODE_FIPS_MODE > >- if (Node_SignFinal(&mdctx_, sig, sig_len, pkey, padding, salt_len)) >+ if (Node_SignFinal(mdctx_, sig, sig_len, pkey, padding, salt_len)) > fatal = false; > >- initialised_ = false; >- > exit: > if (pkey != nullptr) > EVP_PKEY_free(pkey); > if (bp != nullptr) > BIO_free_all(bp); > >- EVP_MD_CTX_cleanup(&mdctx_); >+ EVP_MD_CTX_free(mdctx_); >+ mdctx_ = nullptr; > > if (fatal) > return kSignPrivateKey; >@@ -4291,21 +4490,6 @@ > } > > >-SignBase::Error Verify::VerifyInit(const char* verify_type) { >- CHECK_EQ(initialised_, false); >- const EVP_MD* md = EVP_get_digestbyname(verify_type); >- if (md == nullptr) >- return kSignUnknownDigest; >- >- EVP_MD_CTX_init(&mdctx_); >- if (!EVP_DigestInit_ex(&mdctx_, md, nullptr)) >- return kSignInit; >- initialised_ = true; >- >- return kSignOk; >-} >- >- > void Verify::VerifyInit(const FunctionCallbackInfo<Value>& args) { > Verify* verify; > ASSIGN_OR_RETURN_UNWRAP(&verify, args.Holder()); >@@ -4318,18 +4502,7 @@ > THROW_AND_RETURN_IF_NOT_STRING(args[0], "Verify type"); > > const node::Utf8Value verify_type(args.GetIsolate(), args[0]); >- verify->CheckThrow(verify->VerifyInit(*verify_type)); >-} >- >- >-SignBase::Error Verify::VerifyUpdate(const char* data, int len) { >- if (!initialised_) >- return kSignNotInitialised; >- >- if (!EVP_DigestUpdate(&mdctx_, data, len)) >- return kSignUpdate; >- >- return kSignOk; >+ verify->CheckThrow(verify->Init(*verify_type)); > } > > >@@ -4347,11 +4520,11 @@ > StringBytes::InlineDecoder decoder; > if (!decoder.Decode(env, args[0].As<String>(), args[1], UTF8)) > return; >- err = verify->VerifyUpdate(decoder.out(), decoder.size()); >+ err = verify->Update(decoder.out(), decoder.size()); > } else { > char* buf = Buffer::Data(args[0]); > size_t buflen = Buffer::Length(args[0]); >- err = verify->VerifyUpdate(buf, buflen); >+ err = verify->Update(buf, buflen); > } > > verify->CheckThrow(err); >@@ -4365,7 +4538,7 @@ > int padding, > int saltlen, > bool* verify_result) { >- if (!initialised_) >+ if (!mdctx_) > return kSignNotInitialised; > > EVP_PKEY* pkey = nullptr; >@@ -4410,7 +4583,7 @@ > goto exit; > } > >- if (!EVP_DigestFinal_ex(&mdctx_, m, &m_len)) { >+ if (!EVP_DigestFinal_ex(mdctx_, m, &m_len)) { > goto exit; > } > >@@ -4423,7 +4596,7 @@ > goto err; > if (!ApplyRSAOptions(pkey, pkctx, padding, saltlen)) > goto err; >- if (EVP_PKEY_CTX_set_signature_md(pkctx, mdctx_.digest) <= 0) >+ if (EVP_PKEY_CTX_set_signature_md(pkctx, EVP_MD_CTX_md(mdctx_)) <= 0) > goto err; > r = EVP_PKEY_verify(pkctx, > reinterpret_cast<const unsigned char*>(sig), >@@ -4442,8 +4615,8 @@ > if (x509 != nullptr) > X509_free(x509); > >- EVP_MD_CTX_cleanup(&mdctx_); >- initialised_ = false; >+ EVP_MD_CTX_free(mdctx_); >+ mdctx_ = nullptr; > > if (fatal) > return kSignPublicKey; >@@ -4695,10 +4868,15 @@ > > bool DiffieHellman::Init(const char* p, int p_len, int g) { > dh = DH_new(); >- dh->p = BN_bin2bn(reinterpret_cast<const unsigned char*>(p), p_len, 0); >- dh->g = BN_new(); >- if (!BN_set_word(dh->g, g)) >+ BIGNUM* bn_p = >+ BN_bin2bn(reinterpret_cast<const unsigned char*>(p), p_len, nullptr); >+ BIGNUM* bn_g = BN_new(); >+ if (!BN_set_word(bn_g, g) || >+ !DH_set0_pqg(dh, bn_p, nullptr, bn_g)) { >+ BN_free(bn_p); >+ BN_free(bn_g); > return false; >+ } > bool result = VerifyContext(); > if (!result) > return false; >@@ -4709,8 +4887,13 @@ > > bool DiffieHellman::Init(const char* p, int p_len, const char* g, int g_len) { > dh = DH_new(); >- dh->p = BN_bin2bn(reinterpret_cast<const unsigned char*>(p), p_len, 0); >- dh->g = BN_bin2bn(reinterpret_cast<const unsigned char*>(g), g_len, 0); >+ BIGNUM *bn_p = BN_bin2bn(reinterpret_cast<const unsigned char*>(p), p_len, 0); >+ BIGNUM *bn_g = BN_bin2bn(reinterpret_cast<const unsigned char*>(g), g_len, 0); >+ if (!DH_set0_pqg(dh, bn_p, nullptr, bn_g)) { >+ BN_free(bn_p); >+ BN_free(bn_g); >+ return false; >+ } > bool result = VerifyContext(); > if (!result) > return false; >@@ -4798,22 +4981,25 @@ > return ThrowCryptoError(env, ERR_get_error(), "Key generation failed"); > } > >- size_t size = BN_num_bytes(diffieHellman->dh->pub_key); >+ const BIGNUM* pub_key; >+ DH_get0_key(diffieHellman->dh, &pub_key, nullptr); >+ size_t size = BN_num_bytes(pub_key); > char* data = Malloc(size); >- BN_bn2bin(diffieHellman->dh->pub_key, reinterpret_cast<unsigned char*>(data)); >+ BN_bn2bin(pub_key, reinterpret_cast<unsigned char*>(data)); > args.GetReturnValue().Set(Buffer::New(env, data, size).ToLocalChecked()); > } > > > void DiffieHellman::GetField(const FunctionCallbackInfo<Value>& args, >- BIGNUM* (DH::*field), const char* err_if_null) { >+ const BIGNUM* (*get_field)(const DH*), >+ const char* err_if_null) { > Environment* env = Environment::GetCurrent(args); > > DiffieHellman* dh; > ASSIGN_OR_RETURN_UNWRAP(&dh, args.Holder()); > if (!dh->initialised_) return env->ThrowError("Not initialized"); > >- const BIGNUM* num = (dh->dh)->*field; >+ const BIGNUM* num = get_field(dh->dh); > if (num == nullptr) return env->ThrowError(err_if_null); > > size_t size = BN_num_bytes(num); >@@ -4823,24 +5009,38 @@ > } > > void DiffieHellman::GetPrime(const FunctionCallbackInfo<Value>& args) { >- GetField(args, &DH::p, "p is null"); >+ GetField(args, [](const DH* dh) -> const BIGNUM* { >+ const BIGNUM* p; >+ DH_get0_pqg(dh, &p, nullptr, nullptr); >+ return p; >+ }, "p is null"); > } > > > void DiffieHellman::GetGenerator(const FunctionCallbackInfo<Value>& args) { >- GetField(args, &DH::g, "g is null"); >+ GetField(args, [](const DH* dh) -> const BIGNUM* { >+ const BIGNUM* g; >+ DH_get0_pqg(dh, nullptr, nullptr, &g); >+ return g; >+ }, "g is null"); > } > > > void DiffieHellman::GetPublicKey(const FunctionCallbackInfo<Value>& args) { >- GetField(args, &DH::pub_key, >- "No public key - did you forget to generate one?"); >+ GetField(args, [](const DH* dh) -> const BIGNUM* { >+ const BIGNUM* pub_key; >+ DH_get0_key(dh, &pub_key, nullptr); >+ return pub_key; >+ }, "No public key - did you forget to generate one?"); > } > > > void DiffieHellman::GetPrivateKey(const FunctionCallbackInfo<Value>& args) { >- GetField(args, &DH::priv_key, >- "No private key - did you forget to generate one?"); >+ GetField(args, [](const DH* dh) -> const BIGNUM* { >+ const BIGNUM* priv_key; >+ DH_get0_key(dh, nullptr, &priv_key); >+ return priv_key; >+ }, "No private key - did you forget to generate one?"); > } > > >@@ -4916,16 +5116,14 @@ > args.GetReturnValue().Set(rc); > } > >- > void DiffieHellman::SetKey(const v8::FunctionCallbackInfo<v8::Value>& args, >- BIGNUM* (DH::*field), const char* what) { >+ void (*set_field)(DH*, BIGNUM*), const char* what) { > Environment* env = Environment::GetCurrent(args); > > DiffieHellman* dh; > ASSIGN_OR_RETURN_UNWRAP(&dh, args.Holder()); > if (!dh->initialised_) return env->ThrowError("Not initialized"); > >- BIGNUM** num = &((dh->dh)->*field); > char errmsg[64]; > > if (args.Length() == 0) { >@@ -4938,19 +5136,28 @@ > return env->ThrowTypeError(errmsg); > } > >- *num = BN_bin2bn(reinterpret_cast<unsigned char*>(Buffer::Data(args[0])), >- Buffer::Length(args[0]), *num); >- CHECK_NE(*num, nullptr); >+ BIGNUM* num = >+ BN_bin2bn(reinterpret_cast<unsigned char*>(Buffer::Data(args[0])), >+ Buffer::Length(args[0]), nullptr); >+ CHECK_NE(num, nullptr); >+ set_field(dh->dh, num); > } > > > void DiffieHellman::SetPublicKey(const FunctionCallbackInfo<Value>& args) { >- SetKey(args, &DH::pub_key, "Public key"); >+ SetKey(args, [](DH* dh, BIGNUM* num) { DH_set0_key(dh, num, nullptr); }, >+ "Public key"); > } > >- > void DiffieHellman::SetPrivateKey(const FunctionCallbackInfo<Value>& args) { >- SetKey(args, &DH::priv_key, "Private key"); >+#if OPENSSL_VERSION_NUMBER >= 0x10100000L && \ >+ OPENSSL_VERSION_NUMBER < 0x10100070L >+// Older versions of OpenSSL 1.1.0 have a DH_set0_key which does not work for >+// Node. See https://github.com/openssl/openssl/pull/4384. >+#error "OpenSSL 1.1.0 revisions before 1.1.0g are not supported" >+#endif >+ SetKey(args, [](DH* dh, BIGNUM* num) { DH_set0_key(dh, nullptr, num); }, >+ "Private key"); > } > > >@@ -5738,7 +5945,7 @@ > void GetSSLCiphers(const FunctionCallbackInfo<Value>& args) { > Environment* env = Environment::GetCurrent(args); > >- SSL_CTX* ctx = SSL_CTX_new(TLSv1_server_method()); >+ SSL_CTX* ctx = SSL_CTX_new(TLS_method()); > if (ctx == nullptr) { > return env->ThrowError("SSL_CTX_new() failed."); > } >@@ -6028,9 +6235,11 @@ > SSL_library_init(); > OpenSSL_add_all_algorithms(); > >+#if OPENSSL_VERSION_NUMBER < 0x10100000L > crypto_lock_init(); > CRYPTO_set_locking_callback(crypto_lock_cb); > CRYPTO_THREADID_set_callback(crypto_threadid_cb); >+#endif > > #ifdef NODE_FIPS_MODE > /* Override FIPS settings in cnf file, if needed. */ >--- node-v8.8.1-orig/src/node_crypto_bio.cc 2017-10-26 07:10:33.000000000 +1100 >+++ node-v8.8.1/src/node_crypto_bio.cc 2017-10-29 11:51:11.003518215 +1100 >@@ -29,24 +29,20 @@ > namespace node { > namespace crypto { > >-const BIO_METHOD NodeBIO::method = { >- BIO_TYPE_MEM, >- "node.js SSL buffer", >- NodeBIO::Write, >- NodeBIO::Read, >- NodeBIO::Puts, >- NodeBIO::Gets, >- NodeBIO::Ctrl, >- NodeBIO::New, >- NodeBIO::Free, >- nullptr >-}; >+#if OPENSSL_VERSION_NUMBER < 0x10100000L >+#define BIO_set_data(bio, data) bio->ptr = data >+#define BIO_get_data(bio) bio->ptr >+#define BIO_set_shutdown(bio, shutdown_) bio->shutdown = shutdown_ >+#define BIO_get_shutdown(bio) bio->shutdown >+#define BIO_set_init(bio, init_) bio->init = init_ >+#define BIO_get_init(bio) bio->init >+#endif > > > BIO* NodeBIO::New() { > // The const_cast doesn't violate const correctness. OpenSSL's usage of > // BIO_METHOD is effectively const but BIO_new() takes a non-const argument. >- return BIO_new(const_cast<BIO_METHOD*>(&method)); >+ return BIO_new(const_cast<BIO_METHOD*>(GetMethod())); > } > > >@@ -71,12 +67,11 @@ > > > int NodeBIO::New(BIO* bio) { >- bio->ptr = new NodeBIO(); >+ BIO_set_data(bio, new NodeBIO()); > > // XXX Why am I doing it?! >- bio->shutdown = 1; >- bio->init = 1; >- bio->num = -1; >+ BIO_set_shutdown(bio, 1); >+ BIO_set_init(bio, 1); > > return 1; > } >@@ -86,10 +81,10 @@ > if (bio == nullptr) > return 0; > >- if (bio->shutdown) { >- if (bio->init && bio->ptr != nullptr) { >+ if (BIO_get_shutdown(bio)) { >+ if (BIO_get_init(bio) && BIO_get_data(bio) != nullptr) { > delete FromBIO(bio); >- bio->ptr = nullptr; >+ BIO_set_data(bio, nullptr); > } > } > >@@ -98,13 +93,13 @@ > > > int NodeBIO::Read(BIO* bio, char* out, int len) { >- int bytes; > BIO_clear_retry_flags(bio); > >- bytes = FromBIO(bio)->Read(out, len); >+ NodeBIO* nbio = FromBIO(bio); >+ int bytes = nbio->Read(out, len); > > if (bytes == 0) { >- bytes = bio->num; >+ bytes = nbio->eof_return(); > if (bytes != 0) { > BIO_set_retry_read(bio); > } >@@ -162,7 +157,7 @@ > > > int NodeBIO::Gets(BIO* bio, char* out, int size) { >- NodeBIO* nbio = FromBIO(bio); >+ NodeBIO* nbio = FromBIO(bio); > > if (nbio->Length() == 0) > return 0; >@@ -202,7 +197,7 @@ > ret = nbio->Length() == 0; > break; > case BIO_C_SET_BUF_MEM_EOF_RETURN: >- bio->num = num; >+ nbio->set_eof_return(num); > break; > case BIO_CTRL_INFO: > ret = nbio->Length(); >@@ -217,10 +212,10 @@ > ret = 0; > break; > case BIO_CTRL_GET_CLOSE: >- ret = bio->shutdown; >+ ret = BIO_get_shutdown(bio); > break; > case BIO_CTRL_SET_CLOSE: >- bio->shutdown = num; >+ BIO_set_shutdown(bio, num); > break; > case BIO_CTRL_WPENDING: > ret = 0; >@@ -242,6 +237,41 @@ > } > > >+const BIO_METHOD* NodeBIO::GetMethod() { >+#if OPENSSL_VERSION_NUMBER < 0x10100000L >+ static const BIO_METHOD method = { >+ BIO_TYPE_MEM, >+ "node.js SSL buffer", >+ Write, >+ Read, >+ Puts, >+ Gets, >+ Ctrl, >+ New, >+ Free, >+ nullptr >+ }; >+ >+ return &method; >+#else >+ static BIO_METHOD* method = nullptr; >+ >+ if (method == nullptr) { >+ method = BIO_meth_new(BIO_TYPE_MEM, "node.js SSL buffer"); >+ BIO_meth_set_write(method, Write); >+ BIO_meth_set_read(method, Read); >+ BIO_meth_set_puts(method, Puts); >+ BIO_meth_set_gets(method, Gets); >+ BIO_meth_set_ctrl(method, Ctrl); >+ BIO_meth_set_create(method, New); >+ BIO_meth_set_destroy(method, Free); >+ } >+ >+ return method; >+#endif >+} >+ >+ > void NodeBIO::TryMoveReadHead() { > // `read_pos_` and `write_pos_` means the position of the reader and writer > // inside the buffer, respectively. When they're equal - its safe to reset >@@ -489,5 +519,12 @@ > write_head_ = nullptr; > } > >+ >+NodeBIO* NodeBIO::FromBIO(BIO* bio) { >+ CHECK_NE(BIO_get_data(bio), nullptr); >+ return static_cast<NodeBIO*>(BIO_get_data(bio)); >+} >+ >+ > } // namespace crypto > } // namespace node >--- node-v8.8.1-orig/src/node_crypto_bio.h 2017-10-26 07:10:33.000000000 +1100 >+++ node-v8.8.1/src/node_crypto_bio.h 2017-10-29 11:51:11.004518215 +1100 >@@ -39,6 +39,7 @@ > NodeBIO() : env_(nullptr), > initial_(kInitialBufferLength), > length_(0), >+ eof_return_(-1), > read_head_(nullptr), > write_head_(nullptr) { > } >@@ -97,14 +98,19 @@ > return length_; > } > >+ inline void set_eof_return(int num) { >+ eof_return_ = num; >+ } >+ >+ inline int eof_return() { >+ return eof_return_; >+ } >+ > inline void set_initial(size_t initial) { > initial_ = initial; > } > >- static inline NodeBIO* FromBIO(BIO* bio) { >- CHECK_NE(bio->ptr, nullptr); >- return static_cast<NodeBIO*>(bio->ptr); >- } >+ static NodeBIO* FromBIO(BIO* bio); > > private: > static int New(BIO* bio); >@@ -116,12 +122,12 @@ > static long Ctrl(BIO* bio, int cmd, long num, // NOLINT(runtime/int) > void* ptr); > >+ static const BIO_METHOD* GetMethod(); >+ > // Enough to handle the most of the client hellos > static const size_t kInitialBufferLength = 1024; > static const size_t kThroughputBufferLength = 16384; > >- static const BIO_METHOD method; >- > class Buffer { > public: > Buffer(Environment* env, size_t len) : env_(env), >@@ -153,6 +159,7 @@ > Environment* env_; > size_t initial_; > size_t length_; >+ int eof_return_; > Buffer* read_head_; > Buffer* write_head_; > }; >--- node-v8.8.1-orig/src/node_crypto.h 2017-10-26 07:10:32.000000000 +1100 >+++ node-v8.8.1/src/node_crypto.h 2017-10-29 14:06:40.775558946 +1100 >@@ -53,8 +53,6 @@ > #include <openssl/rand.h> > #include <openssl/pkcs12.h> > >-#define EVP_F_EVP_DECRYPTFINAL 101 >- > #if !defined(OPENSSL_NO_TLSEXT) && defined(SSL_CTX_set_tlsext_status_cb) > # define NODE__HAVE_TLSEXT_STATUS_CB > #endif // !defined(OPENSSL_NO_TLSEXT) && defined(SSL_CTX_set_tlsext_status_cb) >@@ -107,8 +105,20 @@ > static const int kTicketKeyNameIndex = 3; > static const int kTicketKeyIVIndex = 4; > >+#if OPENSSL_VERSION_NUMBER >= 0x10100000L >+ unsigned char ticket_key_name_[16]; >+ unsigned char ticket_key_aes_[16]; >+ unsigned char ticket_key_hmac_[16]; >+#endif >+ > protected: >+#if OPENSSL_VERSION_NUMBER < 0x10100000L > static const int64_t kExternalSize = sizeof(SSL_CTX); >+#else >+ // OpenSSL 1.1.0 has opaque structures. This is an estimate based on the size >+ // as of OpenSSL 1.1.0f. >+ static const int64_t kExternalSize = 872; >+#endif > > static void New(const v8::FunctionCallbackInfo<v8::Value>& args); > static void Init(const v8::FunctionCallbackInfo<v8::Value>& args); >@@ -146,6 +156,15 @@ > HMAC_CTX* hctx, > int enc); > >+#if OPENSSL_VERSION_NUMBER >= 0x10100000L >+ static int TicketCompatibilityCallback(SSL* ssl, >+ unsigned char* name, >+ unsigned char* iv, >+ EVP_CIPHER_CTX* ectx, >+ HMAC_CTX* hctx, >+ int enc); >+#endif >+ > SecureContext(Environment* env, v8::Local<v8::Object> wrap) > : BaseObject(env, wrap), > ctx_(nullptr), >@@ -222,19 +241,32 @@ > protected: > typedef void (*CertCb)(void* arg); > >+#if OPENSSL_VERSION_NUMBER < 0x10100000L > // Size allocated by OpenSSL: one for SSL structure, one for SSL3_STATE and > // some for buffers. > // NOTE: Actually it is much more than this > static const int64_t kExternalSize = > sizeof(SSL) + sizeof(SSL3_STATE) + 42 * 1024; >+#else >+ // OpenSSL 1.1.0 has opaque structures. This is an estimate based on the size >+ // as of OpenSSL 1.1.0f. >+ static const int64_t kExternalSize = 4448 + 1024 + 42 * 1024; >+#endif > > static void InitNPN(SecureContext* sc); > static void AddMethods(Environment* env, v8::Local<v8::FunctionTemplate> t); > >+#if OPENSSL_VERSION_NUMBER < 0x10100000L > static SSL_SESSION* GetSessionCallback(SSL* s, > unsigned char* key, > int len, > int* copy); >+#else >+ static SSL_SESSION* GetSessionCallback(SSL* s, >+ const unsigned char* key, >+ int len, >+ int* copy); >+#endif > static int NewSessionCallback(SSL* s, SSL_SESSION* sess); > static void OnClientHello(void* arg, > const ClientHelloParser::ClientHello& hello); >@@ -425,9 +457,7 @@ > class CipherBase : public BaseObject { > public: > ~CipherBase() override { >- if (!initialised_) >- return; >- EVP_CIPHER_CTX_cleanup(&ctx_); >+ EVP_CIPHER_CTX_free(ctx_); > } > > static void Initialize(Environment* env, v8::Local<v8::Object> target); >@@ -466,15 +496,14 @@ > v8::Local<v8::Object> wrap, > CipherKind kind) > : BaseObject(env, wrap), >- initialised_(false), >+ ctx_(nullptr), > kind_(kind), > auth_tag_len_(0) { > MakeWeak<CipherBase>(this); > } > > private: >- EVP_CIPHER_CTX ctx_; /* coverity[member_decl] */ >- bool initialised_; >+ EVP_CIPHER_CTX* ctx_; > const CipherKind kind_; > unsigned int auth_tag_len_; > char auth_tag_[EVP_GCM_TLS_TAG_LEN]; >@@ -482,11 +511,7 @@ > > class Hmac : public BaseObject { > public: >- ~Hmac() override { >- if (!initialised_) >- return; >- HMAC_CTX_cleanup(&ctx_); >- } >+ ~Hmac() override; > > static void Initialize(Environment* env, v8::Local<v8::Object> target); > >@@ -501,22 +526,17 @@ > > Hmac(Environment* env, v8::Local<v8::Object> wrap) > : BaseObject(env, wrap), >- initialised_(false) { >+ ctx_(nullptr) { > MakeWeak<Hmac>(this); > } > > private: >- HMAC_CTX ctx_; /* coverity[member_decl] */ >- bool initialised_; >+ HMAC_CTX* ctx_; > }; > > class Hash : public BaseObject { > public: >- ~Hash() override { >- if (!initialised_) >- return; >- EVP_MD_CTX_cleanup(&mdctx_); >- } >+ ~Hash() override; > > static void Initialize(Environment* env, v8::Local<v8::Object> target); > >@@ -530,13 +550,13 @@ > > Hash(Environment* env, v8::Local<v8::Object> wrap) > : BaseObject(env, wrap), >- initialised_(false) { >+ mdctx_(nullptr), >+ finalized_(false) { > MakeWeak<Hash>(this); > } > > private: >- EVP_MD_CTX mdctx_; /* coverity[member_decl] */ >- bool initialised_; >+ EVP_MD_CTX* mdctx_; > bool finalized_; > }; > >@@ -554,28 +574,24 @@ > > SignBase(Environment* env, v8::Local<v8::Object> wrap) > : BaseObject(env, wrap), >- initialised_(false) { >+ mdctx_(nullptr) { > } > >- ~SignBase() override { >- if (!initialised_) >- return; >- EVP_MD_CTX_cleanup(&mdctx_); >- } >+ ~SignBase() override; >+ >+ Error Init(const char* sign_type); >+ Error Update(const char* data, int len); > > protected: > void CheckThrow(Error error); > >- EVP_MD_CTX mdctx_; /* coverity[member_decl] */ >- bool initialised_; >+ EVP_MD_CTX* mdctx_; > }; > > class Sign : public SignBase { > public: > static void Initialize(Environment* env, v8::Local<v8::Object> target); > >- Error SignInit(const char* sign_type); >- Error SignUpdate(const char* data, int len); > Error SignFinal(const char* key_pem, > int key_pem_len, > const char* passphrase, >@@ -599,8 +615,6 @@ > public: > static void Initialize(Environment* env, v8::Local<v8::Object> target); > >- Error VerifyInit(const char* verify_type); >- Error VerifyUpdate(const char* data, int len); > Error VerifyFinal(const char* key_pem, > int key_pem_len, > const char* sig, >@@ -690,9 +704,10 @@ > > private: > static void GetField(const v8::FunctionCallbackInfo<v8::Value>& args, >- BIGNUM* (DH::*field), const char* err_if_null); >+ const BIGNUM* (*get_field)(const DH*), >+ const char* err_if_null); > static void SetKey(const v8::FunctionCallbackInfo<v8::Value>& args, >- BIGNUM* (DH::*field), const char* what); >+ void (*set_field)(DH*, BIGNUM*), const char* what); > bool VerifyContext(); > > bool initialised_; >--- node-v8.8.1-orig/test/parallel/test-crypto-dh.js 2017-10-26 07:10:33.000000000 +1100 >+++ node-v8.8.1/test/parallel/test-crypto-dh.js 2017-10-29 11:51:11.008518215 +1100 >@@ -58,6 +58,19 @@ > > assert.strictEqual(secret1, secret3); > >+// computeSecret works without a public key set at all. >+const dh4 = crypto.createDiffieHellman(p1, 'buffer'); >+dh4.setPrivateKey(privkey1); >+ >+assert.deepStrictEqual(dh1.getPrime(), dh4.getPrime()); >+assert.deepStrictEqual(dh1.getGenerator(), dh4.getGenerator()); >+assert.deepStrictEqual(dh1.getPrivateKey(), dh4.getPrivateKey()); >+assert.strictEqual(dh4.verifyError, 0); >+ >+const secret4 = dh4.computeSecret(key2, 'hex', 'base64'); >+ >+assert.strictEqual(secret1, secret4); >+ > const wrongBlockLength = > /^Error: error:0606506D:digital envelope routines:EVP_DecryptFinal_ex:wrong final block length$/; > >--- node-v8.8.1-orig/doc/api/tls.md 2017-10-26 07:10:31.000000000 +1100 >+++ node-v8.8.1/doc/api/tls.md 2017-10-29 11:51:11.023518215 +1100 >@@ -575,12 +575,12 @@ > added: v0.11.4 > --> > >-Returns an object representing the cipher name and the SSL/TLS protocol version >-that first defined the cipher. >+Returns an object representing the cipher name. The `version` key is a legacy >+field which always contains the value `'TLSv1/SSLv3'`. > > For example: `{ name: 'AES256-SHA', version: 'TLSv1/SSLv3' }` > >-See `SSL_CIPHER_get_name()` and `SSL_CIPHER_get_version()` in >+See `SSL_CIPHER_get_name()` in > https://www.openssl.org/docs/man1.0.2/ssl/SSL_CIPHER_get_name.html for more > information. > >--- node-v8.8.1-orig/test/parallel/test-crypto.js 2017-10-26 07:10:33.000000000 +1100 >+++ node-v8.8.1/test/parallel/test-crypto.js 2017-10-29 11:51:11.027518215 +1100 >@@ -129,12 +129,12 @@ > assert(tlsCiphers.every((value) => noCapitals.test(value))); > validateList(tlsCiphers); > >-// Assert that we have sha and sha1 but not SHA and SHA1. >+// Assert that we have sha1 and sha256 but not SHA1 and SHA256. > assert.notStrictEqual(0, crypto.getHashes().length); > assert(crypto.getHashes().includes('sha1')); >-assert(crypto.getHashes().includes('sha')); >+assert(crypto.getHashes().includes('sha256')); > assert(!crypto.getHashes().includes('SHA1')); >-assert(!crypto.getHashes().includes('SHA')); >+assert(!crypto.getHashes().includes('SHA156')); > assert(crypto.getHashes().includes('RSA-SHA1')); > assert(!crypto.getHashes().includes('rsa-sha1')); > validateList(crypto.getHashes()); >@@ -257,7 +257,7 @@ > // Throws crypto error, so there is an opensslErrorStack property. > // The openSSL stack should have content. > if ((err instanceof Error) && >- /asn1 encoding routines:ASN1_CHECK_TLEN:wrong tag/.test(err) && >+ /asn1 encoding routines:[^:]*:wrong tag/.test(err) && > err.opensslErrorStack !== undefined && > Array.isArray(err.opensslErrorStack) && > err.opensslErrorStack.length > 0) { >--- node-v8.8.1-orig/test/parallel/test-tls-junk-server.js 2017-10-26 07:10:34.000000000 +1100 >+++ node-v8.8.1/test/parallel/test-tls-junk-server.js 2017-10-29 11:51:11.026518215 +1100 >@@ -21,7 +21,9 @@ > req.end(); > > req.once('error', common.mustCall(function(err) { >- assert(/unknown protocol/.test(err.message)); >+ // OpenSSL 1.0.x and 1.1.x use different error messages for junk inputs. >+ assert(/unknown protocol/.test(err.message) || >+ /wrong version number/.test(err.message)); > server.close(); > })); > }); >--- node-v8.8.1-orig/test/parallel/test-tls-no-sslv3.js 2017-10-26 07:10:34.000000000 +1100 >+++ node-v8.8.1/test/parallel/test-tls-no-sslv3.js 2017-10-29 11:51:11.026518215 +1100 >@@ -46,6 +46,8 @@ > common.printSkipMessage('`openssl s_client -ssl3` not supported.'); > } else { > assert.strictEqual(errors.length, 1); >- assert(/:wrong version number/.test(errors[0].message)); >+ // OpenSSL 1.0.x and 1.1.x report invalid client versions differently. >+ assert(/:wrong version number/.test(errors[0].message) || >+ /:version too low/.test(errors[0].message)); > } > }); >--- node-v8.8.1-orig/test/parallel/test-tls-server-failed-handshake-emits-clienterror.js 2017-10-26 07:10:34.000000000 +1100 >+++ node-v8.8.1/test/parallel/test-tls-server-failed-handshake-emits-clienterror.js 2017-10-29 11:51:11.026518215 +1100 >@@ -20,8 +20,10 @@ > }).on('tlsClientError', common.mustCall(function(e) { > assert.ok(e instanceof Error, > 'Instance of Error should be passed to error handler'); >+ // OpenSSL 1.0.x and 1.1.x use different error codes for junk inputs. > assert.ok( >- /SSL routines:SSL23_GET_CLIENT_HELLO:unknown protocol/.test(e.message), >+ /SSL routines:[^:]*:(unknown protocol|wrong version number)/.test( >+ e.message), > 'Expecting SSL unknown protocol'); > > server.close(); >--- node-v8.8.1-orig/test/parallel/test-tls-socket-failed-handshake-emits-error.js 2017-10-26 07:10:34.000000000 +1100 >+++ node-v8.8.1/test/parallel/test-tls-socket-failed-handshake-emits-error.js 2017-10-29 11:51:11.027518215 +1100 >@@ -20,8 +20,10 @@ > s.on('error', common.mustCall(function(e) { > assert.ok(e instanceof Error, > 'Instance of Error should be passed to error handler'); >+ // OpenSSL 1.0.x and 1.1.x use different error codes for junk inputs. > assert.ok( >- /SSL routines:SSL23_GET_CLIENT_HELLO:unknown protocol/.test(e.message), >+ /SSL routines:[^:]*:(unknown protocol|wrong version number)/.test( >+ e.message), > 'Expecting SSL unknown protocol'); > })); > >--- node-v8.8.1-orig/test/parallel/test-tls-cert-regression.js 2017-10-26 07:10:34.000000000 +1100 >+++ node-v8.8.1/test/parallel/test-tls-cert-regression.js 2017-10-29 11:51:11.030518215 +1100 >@@ -27,29 +27,43 @@ > > const tls = require('tls'); > >- > const cert = > `-----BEGIN CERTIFICATE----- >-MIIBfjCCASgCCQDmmNjAojbDQjANBgkqhkiG9w0BAQUFADBFMQswCQYDVQQGEwJB >-VTETMBEGA1UECBMKU29tZS1TdGF0ZTEhMB8GA1UEChMYSW50ZXJuZXQgV2lkZ2l0 >-cyBQdHkgTHRkMCAXDTE0MDExNjE3NTMxM1oYDzIyODcxMDMxMTc1MzEzWjBFMQsw >-CQYDVQQGEwJBVTETMBEGA1UECBMKU29tZS1TdGF0ZTEhMB8GA1UEChMYSW50ZXJu >-ZXQgV2lkZ2l0cyBQdHkgTHRkMFwwDQYJKoZIhvcNAQEBBQADSwAwSAJBAPKwlfMX >-6HGZIt1xm7fna72eWcOYfUfSxSugghvqYgJt2Oi3lH+wsU1O9FzRIVmpeIjDXhbp >-Mjsa1HtzSiccPXsCAwEAATANBgkqhkiG9w0BAQUFAANBAHOoKy0NkyfiYH7Ne5ka >-uvCyndyeB4d24FlfqEUlkfaWCZlNKRaV9YhLDiEg3BcIreFo4brtKQfZzTRs0GVm >-KHg= >+MIIDNDCCAp2gAwIBAgIJAJvXLQpGPpm7MA0GCSqGSIb3DQEBBQUAMHAxCzAJBgNV >+BAYTAkdCMRAwDgYDVQQIEwdHd3luZWRkMREwDwYDVQQHEwhXYXVuZmF3cjEUMBIG >+A1UEChMLQWNrbmFjayBMdGQxEjAQBgNVBAsTCVRlc3QgQ2VydDESMBAGA1UEAxMJ >+bG9jYWxob3N0MB4XDTA5MTEwMjE5MzMwNVoXDTEwMTEwMjE5MzMwNVowcDELMAkG >+A1UEBhMCR0IxEDAOBgNVBAgTB0d3eW5lZGQxETAPBgNVBAcTCFdhdW5mYXdyMRQw >+EgYDVQQKEwtBY2tuYWNrIEx0ZDESMBAGA1UECxMJVGVzdCBDZXJ0MRIwEAYDVQQD >+Ewlsb2NhbGhvc3QwgZ8wDQYJKoZIhvcNAQEBBQADgY0AMIGJAoGBANdym7nGe2yw >+6LlJfJrQtC5TmKOGrSXiyolYCbGOy4xZI4KD31d3097jhlQFJyF+10gwkE62DuJe >+fLvBZDUsvLe1R8bzlVhZnBVn+3QJyUIWQAL+DsRj8P3KoD7k363QN5dIaA1GOAg2 >+vZcPy1HCUsvOgvDXGRUCZqNLAyt+h/cpAgMBAAGjgdUwgdIwHQYDVR0OBBYEFK4s >+VBV4shKUj3UX/fvSJnFaaPBjMIGiBgNVHSMEgZowgZeAFK4sVBV4shKUj3UX/fvS >+JnFaaPBjoXSkcjBwMQswCQYDVQQGEwJHQjEQMA4GA1UECBMHR3d5bmVkZDERMA8G >+A1UEBxMIV2F1bmZhd3IxFDASBgNVBAoTC0Fja25hY2sgTHRkMRIwEAYDVQQLEwlU >+ZXN0IENlcnQxEjAQBgNVBAMTCWxvY2FsaG9zdIIJAJvXLQpGPpm7MAwGA1UdEwQF >+MAMBAf8wDQYJKoZIhvcNAQEFBQADgYEAFxR7BA1mUlsYqPiogtxSIfLzHWh+s0bJ >+SBuhNrHes4U8QxS8+x/KWjd/81gzsf9J1C2VzTlFaydAgigz3SkQYgs+TMnFkT2o >+9jqoJrcdf4WpZ2DQXUALaZgwNzPumMUSx8Ac5gO+BY/RHyP6fCodYvdNwyKslnI3 >+US7eCSHZsVo= > -----END CERTIFICATE-----`; > > const key = > `-----BEGIN RSA PRIVATE KEY----- >-MIIBPQIBAAJBAPKwlfMX6HGZIt1xm7fna72eWcOYfUfSxSugghvqYgJt2Oi3lH+w >-sU1O9FzRIVmpeIjDXhbpMjsa1HtzSiccPXsCAwEAAQJBAM4uU9aJE0OfdE1p/X+K >-LrCT3XMdFCJ24GgmHyOURtwDy18upQJecDVdcZp16fjtOPmaW95GoYRyifB3R4I5 >-RxECIQD7jRM9slCSVV8xp9kOJQNpHjhRQYVGBn+pyllS2sb+RQIhAPb7Y+BIccri >-NWnuhwCW8hA7Fkj/kaBdAwyW7L3Tvui/AiEAiqLCovMecre4Yi6GcsQ1b/6mvSmm >-IOS+AT6zIfXPTB0CIQCJKGR3ymN/Qw5crL1GQ41cHCQtF9ickOq/lBUW+j976wIh >-AOaJnkQrmurlRdePX6LvN/LgGAQoxwovfjcOYNnZsIVY >+MIICXgIBAAKBgQDXcpu5xntssOi5SXya0LQuU5ijhq0l4sqJWAmxjsuMWSOCg99X >+d9Pe44ZUBSchftdIMJBOtg7iXny7wWQ1LLy3tUfG85VYWZwVZ/t0CclCFkAC/g7E >+Y/D9yqA+5N+t0DeXSGgNRjgINr2XD8tRwlLLzoLw1xkVAmajSwMrfof3KQIDAQAB >+AoGBAIBHR/tT93ce2mJAJAXV0AJpWc+7x2pwX2FpXtQujnlxNZhnRlrBCRCD7h4m >+t0bVS/86kyGaesBDvAbavfx/N5keYzzmmSp5Ht8IPqKPydGWdigk4x90yWvktai7 >+dWuRKF94FXr0GUuBONb/dfHdp4KBtzN7oIF9WydYGGXA9ZmBAkEA8/k01bfwQZIu >+AgcdNEM94Zcug1gSspXtUu8exNQX4+PNVbadghZb1+OnUO4d3gvWfqvAnaXD3KV6 >+N4OtUhQQ0QJBAOIRbKMfaymQ9yE3CQQxYfKmEhHXWARXVwuYqIFqjmhSjSXx0l/P >+7mSHz1I9uDvxkJev8sQgu1TKIyTOdqPH1tkCQQDPa6H1yYoj1Un0Q2Qa2Mg1kTjk >+Re6vkjPQ/KcmJEOjZjtekgFbZfLzmwLXFXqjG2FjFFaQMSxR3QYJSJQEYjbhAkEA >+sy7OZcjcXnjZeEkv61Pc57/7qIp/6Aj2JGnefZ1gvI1Z9Q5kCa88rA/9Iplq8pA4 >+ZBKAoDW1ZbJGAsFmxc/6mQJAdPilhci0qFN86IGmf+ZBnwsDflIwHKDaVofti4wQ >+sPWhSOb9VQjMXekI4Y2l8fqAVTS2Fn6+8jkVKxXBywSVCw== > -----END RSA PRIVATE KEY-----`; > > function test(cert, key, cb) { >--- node-v8.8.1-orig/test/parallel/test-tls-econnreset.js 2017-10-26 07:10:34.000000000 +1100 >+++ node-v8.8.1/test/parallel/test-tls-econnreset.js 2017-10-29 11:51:11.030518215 +1100 >@@ -25,72 +25,28 @@ > common.skip('missing crypto'); > > const assert = require('assert'); >+const fixtures = require('../common/fixtures'); >+const net = require('net'); > const tls = require('tls'); > >-const cacert = >-`-----BEGIN CERTIFICATE----- >-MIIBxTCCAX8CAnXnMA0GCSqGSIb3DQEBBQUAMH0xCzAJBgNVBAYTAlVTMQswCQYD >-VQQIEwJDQTEWMBQGA1UEBxMNU2FuIEZyYW5jaXNjbzEZMBcGA1UEChMQU3Ryb25n >-TG9vcCwgSW5jLjESMBAGA1UECxMJU3Ryb25nT3BzMRowGAYDVQQDExFjYS5zdHJv >-bmdsb29wLmNvbTAeFw0xNDAxMTcyMjE1MDdaFw00MTA2MDMyMjE1MDdaMH0xCzAJ >-BgNVBAYTAlVTMQswCQYDVQQIEwJDQTEWMBQGA1UEBxMNU2FuIEZyYW5jaXNjbzEZ >-MBcGA1UEChMQU3Ryb25nTG9vcCwgSW5jLjESMBAGA1UECxMJU3Ryb25nT3BzMRow >-GAYDVQQDExFjYS5zdHJvbmdsb29wLmNvbTBMMA0GCSqGSIb3DQEBAQUAAzsAMDgC >-MQDKbQ6rIR5t1q1v4Ha36jrq0IkyUohy9EYNvLnXUly1PGqxby0ILlAVJ8JawpY9 >-AVkCAwEAATANBgkqhkiG9w0BAQUFAAMxALA1uS4CqQXRSAyYTfio5oyLGz71a+NM >-+0AFLBwh5AQjhGd0FcenU4OfHxyDEOJT/Q== >------END CERTIFICATE-----`; >- >-const cert = >-`-----BEGIN CERTIFICATE----- >-MIIBfDCCATYCAgQaMA0GCSqGSIb3DQEBBQUAMH0xCzAJBgNVBAYTAlVTMQswCQYD >-VQQIEwJDQTEWMBQGA1UEBxMNU2FuIEZyYW5jaXNjbzEZMBcGA1UEChMQU3Ryb25n >-TG9vcCwgSW5jLjESMBAGA1UECxMJU3Ryb25nT3BzMRowGAYDVQQDExFjYS5zdHJv >-bmdsb29wLmNvbTAeFw0xNDAxMTcyMjE1MDdaFw00MTA2MDMyMjE1MDdaMBkxFzAV >-BgNVBAMTDnN0cm9uZ2xvb3AuY29tMEwwDQYJKoZIhvcNAQEBBQADOwAwOAIxAMfk >-I0LWU15pPUwIQNMnRVhhOibi0TQmAau8FBtgwEfGK01WpfGUaJr1a41K8Uq7xwID >-AQABoxkwFzAVBgNVHREEDjAMhwQAAAAAhwR/AAABMA0GCSqGSIb3DQEBBQUAAzEA >-cGpYrhkrb7mIh9DNhV0qp7pGjqBzlHqB7KQXw2luLDp//6dyHBMexDCQznkhZKRU >------END CERTIFICATE-----`; >- >-const key = >-`-----BEGIN RSA PRIVATE KEY----- >-MIH0AgEAAjEAx+QjQtZTXmk9TAhA0ydFWGE6JuLRNCYBq7wUG2DAR8YrTVal8ZRo >-mvVrjUrxSrvHAgMBAAECMBCGccvSwC2r8Z9Zh1JtirQVxaL1WWpAQfmVwLe0bAgg >-/JWMU/6hS36TsYyZMxwswQIZAPTAfht/zDLb7Hwgu2twsS1Ra9w/yyvtlwIZANET >-26votwJAHK1yUrZGA5nnp5qcmQ/JUQIZAII5YV/UUZvF9D/fUplJ7puENPWNY9bN >-pQIZAMMwxuS3XiO7two2sQF6W+JTYyX1DPCwAQIZAOYg1TvEGT38k8e8jygv8E8w >-YqrWTeQFNQ== >------END RSA PRIVATE KEY-----`; >- >-const ca = [ cert, cacert ]; >- > let clientError = null; >-let connectError = null; > >-const server = tls.createServer({ ca: ca, cert: cert, key: key }, () => { >- assert.fail('should be unreachable'); >-}).on('tlsClientError', function(err, conn) { >+const server = tls.createServer({ >+ cert: fixtures.readKey('agent1-cert.pem'), >+ key: fixtures.readKey('agent1-key.pem'), >+}, common.mustNotCall()).on('tlsClientError', function(err, conn) { > assert(!clientError && conn); > clientError = err; >+ server.close(); > }).listen(0, function() { >- const options = { >- ciphers: 'AES128-GCM-SHA256', >- port: this.address().port, >- ca: ca >- }; >- tls.connect(options).on('error', function(err) { >- assert(!connectError); >- >- connectError = err; >+ net.connect(this.address().port, function() { >+ // Destroy the socket once it is connected, so the server sees ECONNRESET. > this.destroy(); >- server.close(); >- }).write('123'); >+ }).on('error', common.mustNotCall()); > }); > > process.on('exit', function() { > assert(clientError); >- assert(connectError); > assert(/socket hang up/.test(clientError.message)); > assert(/ECONNRESET/.test(clientError.code)); > }); >--- node-v8.8.1-orig/test/parallel/test-https-connect-address-family.js 2017-10-26 07:10:34.000000000 +1100 >+++ node-v8.8.1/test/parallel/test-https-connect-address-family.js 2017-10-29 11:51:11.032518215 +1100 >@@ -7,12 +7,15 @@ > common.skip('no IPv6 support'); > > const assert = require('assert'); >+const fixtures = require('../common/fixtures'); > const https = require('https'); > const dns = require('dns'); > > function runTest() { >- const ciphers = 'AECDH-NULL-SHA'; >- https.createServer({ ciphers }, common.mustCall(function(req, res) { >+ https.createServer({ >+ cert: fixtures.readKey('agent1-cert.pem'), >+ key: fixtures.readKey('agent1-key.pem'), >+ }, common.mustCall(function(req, res) { > this.close(); > res.end(); > })).listen(0, '::1', common.mustCall(function() { >@@ -20,7 +23,6 @@ > host: 'localhost', > port: this.address().port, > family: 6, >- ciphers: ciphers, > rejectUnauthorized: false, > }; > // Will fail with ECONNREFUSED if the address family is not honored. >--- node-v8.8.1-orig/test/parallel/test-tls-connect-address-family.js 2017-10-26 07:10:34.000000000 +1100 >+++ node-v8.8.1/test/parallel/test-tls-connect-address-family.js 2017-10-29 11:51:11.033518215 +1100 >@@ -7,19 +7,21 @@ > common.skip('no IPv6 support'); > > const assert = require('assert'); >+const fixtures = require('../common/fixtures'); > const tls = require('tls'); > const dns = require('dns'); > > function runTest() { >- const ciphers = 'AECDH-NULL-SHA'; >- tls.createServer({ ciphers }, common.mustCall(function() { >+ tls.createServer({ >+ cert: fixtures.readKey('agent1-cert.pem'), >+ key: fixtures.readKey('agent1-key.pem'), >+ }, common.mustCall(function() { > this.close(); > })).listen(0, '::1', common.mustCall(function() { > const options = { > host: 'localhost', > port: this.address().port, > family: 6, >- ciphers: ciphers, > rejectUnauthorized: false, > }; > // Will fail with ECONNREFUSED if the address family is not honored. >--- node-v8.8.1-orig/src/node_constants.cc 2017-10-26 07:10:32.000000000 +1100 >+++ node-v8.8.1/src/node_constants.cc 2017-10-29 11:51:11.033518215 +1100 >@@ -755,6 +755,10 @@ > } > > void DefineOpenSSLConstants(Local<Object> target) { >+#ifdef OPENSSL_VERSION_NUMBER >+ NODE_DEFINE_CONSTANT(target, OPENSSL_VERSION_NUMBER); >+#endif >+ > #ifdef SSL_OP_ALL > NODE_DEFINE_CONSTANT(target, SSL_OP_ALL); > #endif >--- node-v8.8.1-orig/test/parallel/test-https-agent-session-eviction.js 2017-10-26 07:10:34.000000000 +1100 >+++ node-v8.8.1/test/parallel/test-https-agent-session-eviction.js 2017-10-29 11:51:11.034518215 +1100 >@@ -8,7 +8,8 @@ > > const assert = require('assert'); > const https = require('https'); >-const SSL_OP_NO_TICKET = require('crypto').constants.SSL_OP_NO_TICKET; >+const { OPENSSL_VERSION_NUMBER, SSL_OP_NO_TICKET } = >+ require('crypto').constants; > > const options = { > key: readKey('agent1-key.pem'), >@@ -58,14 +59,25 @@ > res.resume(); > }); > >- // Let it fail >- req.on('error', common.mustCall(function(err) { >- assert(/wrong version number/.test(err.message)); >- >- req.on('close', function() { >- third(server); >- }); >- })); >+ if (OPENSSL_VERSION_NUMBER >= 0x10100000) { >+ // Although we have a TLS 1.2 session to offer to the TLS 1.0 server, >+ // connection to the TLS 1.0 server should work. >+ req.on('response', common.mustCall(function(res) { >+ // The test is now complete for OpenSSL 1.1.0. >+ server.close(); >+ })); >+ } else { >+ // OpenSSL 1.0.x mistakenly locked versions based on the session it was >+ // offering. This causes this sequent request to fail. Let it fail, but >+ // test that this is mitigated on the next try by invalidating the session. >+ req.on('error', common.mustCall(function(err) { >+ assert(/wrong version number/.test(err.message)); >+ >+ req.on('close', function() { >+ third(server); >+ }); >+ })); >+ } > req.end(); > } > >--- node-v8.8.1-orig/test/parallel/test-http2-create-client-connect.js 2017-10-26 07:10:33.000000000 +1100 >+++ node-v8.8.1/test/parallel/test-http2-create-client-connect.js 2017-10-29 11:51:11.037518215 +1100 >@@ -3,6 +3,7 @@ > // Tests http2.connect() > > const common = require('../common'); >+const Countdown = require('../common/countdown'); > if (!common.hasCrypto) > common.skip('missing crypto'); > const fixtures = require('../common/fixtures'); >@@ -25,13 +26,12 @@ > [{ port: port, hostname: '127.0.0.1' }, { protocol: 'http:' }] > ]; > >- let count = items.length; >+ const serverClose = new Countdown(items.length + 1, >+ () => setImmediate(() => server.close())); > > const maybeClose = common.mustCall((client) => { > client.destroy(); >- if (--count === 0) { >- setImmediate(() => server.close()); >- } >+ serverClose.dec(); > }, items.length); > > items.forEach((i) => { >@@ -42,7 +42,7 @@ > > // Will fail because protocol does not match the server. > h2.connect({ port: port, protocol: 'https:' }) >- .on('socketError', common.mustCall()); >+ .on('socketError', common.mustCall(() => serverClose.dec())); > })); > } > >@@ -70,13 +70,12 @@ > [{ port: port, hostname: '127.0.0.1', protocol: 'https:' }, opts] > ]; > >- let count = items.length; >+ const serverClose = new Countdown(items.length, >+ () => setImmediate(() => server.close())); > > const maybeClose = common.mustCall((client) => { > client.destroy(); >- if (--count === 0) { >- setImmediate(() => server.close()); >- } >+ serverClose.dec(); > }, items.length); > > items.forEach((i) => { >--- node-v8.8.1-orig/test/parallel/test-tls-ecdh-disable.js 2017-10-26 07:10:34.000000000 +1100 >+++ node-v8.8.1/test/parallel/test-tls-ecdh-disable.js 2017-10-29 11:51:11.038518215 +1100 >@@ -27,6 +27,11 @@ > if (!common.opensslCli) > common.skip('missing openssl-cli'); > >+const OPENSSL_VERSION_NUMBER = >+ require('crypto').constants.OPENSSL_VERSION_NUMBER; >+if (OPENSSL_VERSION_NUMBER >= 0x10100000) >+ common.skip('false ecdhCurve not supported in OpenSSL 1.1.0') >+ > const assert = require('assert'); > const tls = require('tls'); > const exec = require('child_process').exec;
You cannot view the attachment while viewing its details because your browser does not support IFRAMEs.
View the attachment on a separate page
.
View Attachment As Diff
View Attachment As Raw
Actions:
View
|
Diff
Attachments on
bug 604978
:
459110
| 500618 |
500620
|
507810
|
510424