[libnet-ssleay-perl] 01/04: Imported Upstream version 1.77
dom at earth.li
dom at earth.li
Tue Aug 9 01:07:45 UTC 2016
This is an automated email from the git hooks/post-receive script.
dom pushed a commit to branch master
in repository libnet-ssleay-perl.
commit e669abf0dd8ca93f3d14079cfc398062a96e2315
Author: Dominic Hargreaves <dom at earth.li>
Date: Mon Aug 8 23:25:32 2016 +0100
Imported Upstream version 1.77
---
Changes | 43 +++
MANIFEST | 2 +
META.yml | 11 +-
Makefile.PL | 2 +-
README | 14 +-
SSLeay.xs | 444 ++++++++++++++++++++++++++-----
inc/Module/Install.pm | 22 +-
inc/Module/Install/Base.pm | 2 +-
inc/Module/Install/Can.pm | 2 +-
inc/Module/Install/External.pm | 2 +-
inc/Module/Install/Fetch.pm | 2 +-
inc/Module/Install/Makefile.pm | 4 +-
inc/Module/Install/Metadata.pm | 6 +-
inc/Module/Install/PRIVATE/Net/SSLeay.pm | 1 -
inc/Module/Install/Win32.pm | 2 +-
inc/Module/Install/WriteAll.pm | 2 +-
lib/Net/SSLeay.pm | 4 +-
lib/Net/SSLeay.pod | 148 ++++++++++-
t/local/32_x509_get_cert_info.t | 2 +-
t/local/35_ephemeral.t | 2 +-
t/local/63_ec_key_generate_key.t | 35 +++
t/local/64_ticket_sharing.t | 270 +++++++++++++++++++
22 files changed, 917 insertions(+), 105 deletions(-)
diff --git a/Changes b/Changes
index 7d19fb1..876482e 100644
--- a/Changes
+++ b/Changes
@@ -1,5 +1,48 @@
Revision history for Perl extension Net::SSLeay.
+1.77 2016-08-01
+ Fixed incorrect size to memset in tlsext_ticket_key_cb_invoke.
+
+1.76 2016-07-31
+ Replaced bzero with memset. Bzero not present on windows.
+
+1.75 2016-07-31
+ Compatibility with OpenSSL 1.1, tested with openssl-1.1.0-pre5:
+ - Conditionally remove threading locking code, not needed in 1.1
+ - Rewrite code that accesses inside X509_ATTRIBUTE struct.
+ - SSL_CTX_need_tmp_RSA, SSL_CTX_set_tmp_rsa,
+ SSL_CTX_set_tmp_rsa_callback, SSL_set_tmp_rsa_callback support
+ not available in 1.1.
+ - SSL_session_reused is now native
+ - SSL_get_keyblock_size modifed to use new API
+ - OCSP functions modified to use new API under 1.1
+ - SSL_set_state removed with 1.1
+ - SSL_get_state and SSL_state are now equivalent and available in all
+ versions
+ - SSL_CTX_v2_new removed
+ - SESSION_set_master_key removed with 1.1. Code that previously used
+ SESSION_set_master_key must now set $secret in the session_secret
+ callback set with SSL_set_session_secret_cb
+ - With 1.1, $secret in the session_secret
+ callback set with SSL_set_session_secret_cb can be changed to alter
+ the master key (required by EAP-FAST).
+ Added a function EC_KEY_generate_key similar to RSA_generate_key and a
+ function EVP_PKEY_assign_EC_KEY similar to EVP_PKEY_assign_RSA. Using
+ these functions it is easy to create and use EC keys in the same way as
+ RSA keys. Patch provided by Steffen Ullrich. Thanks Steffen.
+ Testing with LibreSSL 2.4.1, with compatibility patch from Steffen
+ Ullrich. Thanks Steffen.
+ Patch from Steffen Ulrich provides support for cross context (and cross process)
+ session sharing using the stateless TLS session tickets. It uses the
+ SSL_CTX_set_tlsext_ticket_key_cb function to manage the encryption and
+ decryption of the tickets but provides a more simplified
+ interface. Includes new function CTX_set_tlsext_ticket_getkey_cb.
+ To not conflict with the OpenSSL name in case the more complex interface
+ will be implemented ever the current simplified interface is called
+ slightly different: CTX_set_tlsext_ticket_*get*key_cb.
+ Added documentation about downloading latest version from SVN.
+ Added missing Module/install files to SVN.
+
1.74 2016-04-12
README.OSX was missing from the distribution
diff --git a/MANIFEST b/MANIFEST
index ae92ebb..5e99e6e 100644
--- a/MANIFEST
+++ b/MANIFEST
@@ -113,5 +113,7 @@ t/local/42_info_callback.t
t/local/50_digest.t
t/local/61_threads-cb-crash.t
t/local/62_threads-ctx_new-deadlock.t
+t/local/63_ec_key_generate_key.t
+t/local/64_ticket_sharing.t
t/local/kwalitee.t
typemap
diff --git a/META.yml b/META.yml
index 34adafd..413cc48 100644
--- a/META.yml
+++ b/META.yml
@@ -1,5 +1,4 @@
---
-name: Net-SSLeay
abstract: 'Perl extension for using OpenSSL'
author:
- 'Maintained by Mike McCauley and Florian Ragwitz since November 2005'
@@ -9,11 +8,12 @@ configure_requires:
ExtUtils::MakeMaker: 6.36
distribution_type: module
dynamic_config: 1
-generated_by: 'Module::Install version 1.06'
+generated_by: 'Module::Install version 1.16'
license: perl
meta-spec:
url: http://module-build.sourceforge.net/META-spec-v1.4.html
version: 1.4
+name: Net-SSLeay
no_index:
directory:
- examples
@@ -24,8 +24,9 @@ no_index:
requires:
MIME::Base64: 0
Test::More: 0.60_01
- perl: 5.005
+ perl: '5.005'
resources:
bugtracker: https://rt.cpan.org/Public/Dist/Display.html?Name=net-ssleay
- repository: svn://svn.debian.org/svn/net-ssleay
-version: '1.74'
+ license: http://dev.perl.org/licenses/
+ repository: http://svn.debian.org/wsvn/net-ssleay
+version: '1.77'
diff --git a/Makefile.PL b/Makefile.PL
index bfd98b6..c841cef 100644
--- a/Makefile.PL
+++ b/Makefile.PL
@@ -8,7 +8,7 @@ use Config;
use File::Spec;
name('Net-SSLeay');
-license 'perl';
+license('perl');
all_from('lib/Net/SSLeay.pm');
ssleay();
diff --git a/README b/README
index 43e4029..608eb72 100644
--- a/README
+++ b/README
@@ -1,17 +1,23 @@
README - Net::SSLeay Perl module for using OpenSSL
-$Id: README 461 2016-04-04 03:32:38Z mikem-guest $
+$Id: README 472 2016-07-28 09:14:26Z mikem-guest $
By popular demand...
--------------------
perl -MNet::SSLeay -e '($p)=Net::SSLeay::get_https("www.openssl.org", 443, "/"); print $p'
+for the latest and possibly unstable version from SVN:
+
+ svn co svn://svn.debian.org/svn/net-ssleay
+
+
Prerequisites
-------------
-perl-5.6.1 though anything starting from perl5.003 probably works.
+perl-5.6.1 though anything starting from perl5.003 probably works. Later
+ versions are OK.
-OpenSSL-0.9.6j through to at least OpenSSL-1.0.2 and probably later
+OpenSSL-0.9.6j through to at least OpenSSL-1.1 and probably later
http://www.openssl.org/ - On Linux, you can either build and
install OpenSSL from scratch (its very portable) or you can
install the appropriate OpenSSL 'devel' package for your Linux
@@ -25,6 +31,8 @@ Note: SSLeay is no longer supported. If you want to use Net::SSLeay with
in OpenSSL-0.9.2b. OpenSSL-0.9.1c support has also been dropped,
version 1.03 was the last one to support that.
+LibreSSL is also supported.
+
You should use the same C compiler and options to compile OpenSSL,
perl, and Net::SSLeay. This is the only supported configuration.
If you insist on using different compilers (perhaps because you
diff --git a/SSLeay.xs b/SSLeay.xs
index 9d0494c..9b86989 100644
--- a/SSLeay.xs
+++ b/SSLeay.xs
@@ -8,7 +8,7 @@
*
* Change data removed. See Changes
*
- * $Id: SSLeay.xs 458 2015-12-15 21:23:48Z mikem-guest $
+ * $Id: SSLeay.xs 477 2016-07-31 20:24:00Z mikem-guest $
*
* The distribution and use of this module are subject to the conditions
* listed in LICENSE file at the root of the Net-SSLeay
@@ -237,8 +237,10 @@ START_MY_CXT
#ifdef USE_ITHREADS
static perl_mutex LIB_init_mutex;
+#if OPENSSL_VERSION_NUMBER < 0x10100000L
static perl_mutex *GLOBAL_openssl_mutex = NULL;
#endif
+#endif
static int LIB_initialized;
UV get_my_thread_id(void) /* returns threads->tid() value */
@@ -277,6 +279,8 @@ UV get_my_thread_id(void) /* returns threads->tid() value */
*/
#if defined(USE_ITHREADS) && defined(OPENSSL_THREADS)
+
+#if OPENSSL_VERSION_NUMBER < 0x10100000L
static void openssl_locking_function(int mode, int type, const char *file, int line)
{
PR3("openssl_locking_function %d %d\n", mode, type);
@@ -331,6 +335,7 @@ void openssl_dynlocking_destroy_function (struct CRYPTO_dynlock_value *l, const
MUTEX_DESTROY(&l->mutex);
Safefree(l);
}
+#endif
void openssl_threads_init(void)
{
@@ -338,6 +343,7 @@ void openssl_threads_init(void)
PR1("STARTED: openssl_threads_init\n");
+#if OPENSSL_VERSION_NUMBER < 0x10100000L
/* initialize static locking */
if ( !CRYPTO_get_locking_callback() ) {
#if OPENSSL_VERSION_NUMBER < 0x10000000L
@@ -371,6 +377,7 @@ void openssl_threads_init(void)
CRYPTO_set_dynlock_lock_callback(openssl_dynlocking_lock_function);
CRYPTO_set_dynlock_destroy_callback(openssl_dynlocking_destroy_function);
}
+#endif
}
#endif
@@ -395,7 +402,9 @@ static void handler_list_md_fn(const EVP_MD *m, const char *from, const char *to
if (!m) return; /* Skip aliases */
mname = OBJ_nid2ln(EVP_MD_type(m));
if (strcmp(from, mname)) return; /* Skip shortnames */
+#if OPENSSL_VERSION_NUMBER < 0x10100000L
if (EVP_MD_flags(m) & EVP_MD_FLAG_PKEY_DIGEST) return; /* Skip clones */
+#endif
if (strchr(mname, ' ')) mname= EVP_MD_name(m);
av_push(arg, newSVpv(mname,0));
}
@@ -799,6 +808,7 @@ int ssleay_session_secret_cb_invoke(SSL* s, void* secret, int *secret_len,
AV *ciphers = newAV();
SV *pref_cipher = sv_newmortal();
SV * cb_func, *cb_data;
+ SV * secretsv;
PR1("STARTED: ssleay_session_secret_cb_invoke\n");
cb_func = cb_data_advanced_get(arg, "ssleay_session_secret_cb!!func");
@@ -811,8 +821,8 @@ int ssleay_session_secret_cb_invoke(SSL* s, void* secret, int *secret_len,
SAVETMPS;
PUSHMARK(SP);
-
- XPUSHs( sv_2mortal( newSVpv(secret, *secret_len)) );
+ secretsv = sv_2mortal( newSVpv(secret, *secret_len));
+ XPUSHs(secretsv);
for (i=0; i<sk_SSL_CIPHER_num(peer_ciphers); i++) {
SSL_CIPHER *c = sk_SSL_CIPHER_value(peer_ciphers,i);
av_store(ciphers, i, sv_2mortal(newSVpv(SSL_CIPHER_get_name(c), 0)));
@@ -835,6 +845,13 @@ int ssleay_session_secret_cb_invoke(SSL* s, void* secret, int *secret_len,
/* See if there is a preferred cipher selected, if so it is an index into the stack */
if (SvIOK(pref_cipher))
*cipher = sk_SSL_CIPHER_value(peer_ciphers, SvIV(pref_cipher));
+
+#if OPENSSL_VERSION_NUMBER >= 0x10100000L
+ /* Use any new master secret set by the callback function in secret */
+ STRLEN newsecretlen;
+ char* newsecretdata = SvPV(secretsv, newsecretlen);
+ memcpy(secret, newsecretdata, newsecretlen);
+#endif
}
PUTBACK;
@@ -1221,6 +1238,100 @@ void ssleay_ctx_info_cb_invoke(const SSL *ssl, int where, int ret)
LEAVE;
}
+/*
+ * Support for tlsext_ticket_key_cb_invoke was already in 0.9.8 but it was
+ * broken in various ways during the various 1.0.0* versions.
+ * Better enable it only starting with 1.0.1.
+*/
+#if defined(SSL_CTRL_SET_TLSEXT_TICKET_KEY_CB) && OPENSSL_VERSION_NUMBER >= 0x10001000L && !defined(OPENSSL_NO_TLSEXT)
+#define NET_SSLEAY_CAN_TICKET_KEY_CB
+
+int tlsext_ticket_key_cb_invoke(
+ SSL *ssl,
+ unsigned char *key_name,
+ unsigned char *iv,
+ EVP_CIPHER_CTX *ectx,
+ HMAC_CTX *hctx,
+ int enc
+){
+
+ dSP;
+ int count;
+ SV *cb_func, *cb_data;
+ SV *sv_name, *sv_key;
+ STRLEN svlen;
+ unsigned char *key; /* key[0..15] aes, key[16..32] hmac */
+ unsigned char *name;
+ SSL_CTX *ctx = SSL_get_SSL_CTX(ssl);
+
+ PR1("STARTED: tlsext_ticket_key_cb_invoke\n");
+ cb_func = cb_data_advanced_get(ctx, "tlsext_ticket_key_cb!!func");
+ cb_data = cb_data_advanced_get(ctx, "tlsext_ticket_key_cb!!data");
+
+ if (!SvROK(cb_func) || (SvTYPE(SvRV(cb_func)) != SVt_PVCV))
+ croak("callback must be a code reference");
+
+ ENTER;
+ SAVETMPS;
+ PUSHMARK(SP);
+ XPUSHs(sv_2mortal(newSVsv(cb_data)));
+
+ if (!enc) {
+ /* call as getkey(data,this_name) -> (key,current_name) */
+ XPUSHs(sv_2mortal(newSVpv(key_name,16)));
+ } else {
+ /* call as getkey(data) -> (key,current_name) */
+ }
+
+
+ PUTBACK;
+ count = call_sv( cb_func, G_ARRAY );
+
+ SPAGAIN;
+ if (count>0) sv_name = POPs;
+ if (count>1) sv_key = POPs;
+
+ if (!enc && ( !count || !SvOK(sv_key) )) {
+ TRACE(2,"no key returned for ticket");
+ return 0;
+ }
+
+ if (count != 2)
+ croak("key functions needs to return (key,name)");
+ key = SvPV(sv_key,svlen);
+ if (svlen < 32)
+ croak("key must be at least 32 random bytes, got %d",svlen);
+ name = SvPV(sv_name,svlen);
+ if (svlen != 16)
+ croak("name should be exactly 16 characters, got %d",svlen);
+ if (svlen == 0)
+ croak("name should not be empty");
+
+ if (enc) {
+ /* encrypt ticket information with given key */
+ RAND_bytes(iv, 16);
+ EVP_EncryptInit_ex(ectx, EVP_aes_128_cbc(), NULL, key, iv);
+ HMAC_Init_ex(hctx,key+16,16,EVP_sha256(),NULL);
+ memset(key_name, 0, 16);
+ memcpy(key_name,name,svlen);
+ return 1;
+ } else {
+ unsigned char new_name[16];
+ memset(new_name, 0, sizeof(new_name));
+ memcpy(new_name,name,svlen);
+
+ HMAC_Init_ex(hctx,key+16,16,EVP_sha256(),NULL);
+ EVP_DecryptInit_ex(ectx, EVP_aes_128_cbc(), NULL, key, iv);
+
+ if (memcmp(new_name,key_name,16) == 0)
+ return 1; /* current key was used */
+ else
+ return 2; /* different key was used, need to be renewed */
+ }
+}
+
+#endif
+
/* ============= end of callback stuff, begin helper functions ============== */
@@ -1404,7 +1515,9 @@ SSL_CTX_new()
OUTPUT:
RETVAL
-#ifndef OPENSSL_NO_SSL2
+
+#if OPENSSL_VERSION_NUMBER < 0x10100000L
+#ifndef OPENSSL_NO_SSL2
SSL_CTX *
SSL_CTX_v2_new()
@@ -1414,7 +1527,7 @@ SSL_CTX_v2_new()
RETVAL
#endif
-
+#endif
#ifndef OPENSSL_NO_SSL3
SSL_CTX *
@@ -2105,10 +2218,35 @@ int
SSL_want(s)
SSL * s
+#if OPENSSL_VERSION_NUMBER < 0x10100000L
+int
+SSL_state(s)
+ SSL * s
+
+int
+SSL_get_state(ssl)
+ SSL * ssl
+ CODE:
+ RETVAL = SSL_state(ssl);
+ OUTPUT:
+ RETVAL
+
+
+#else
int
SSL_state(s)
SSL * s
+ CODE:
+ RETVAL = SSL_get_state(s);
+ OUTPUT:
+ RETVAL
+
+
+int
+SSL_get_state(s)
+ SSL * s
+#endif
#if OPENSSL_VERSION_NUMBER >= 0x0090806fL && !defined(OPENSSL_NO_TLSEXT)
long
@@ -2734,19 +2872,15 @@ P_X509_REQ_get_attr(req,n)
X509_ATTRIBUTE * att;
int count, i;
ASN1_STRING * s;
+ ASN1_TYPE * t;
PPCODE:
att = X509_REQ_get_attr(req,n);
- if (att->single) {
- s = (att->value.single->value.asn1_string);
+ count = X509_ATTRIBUTE_count(att);
+ for (i=0; i<count; i++) {
+ t = X509_ATTRIBUTE_get0_type(att, i);
+ s = t->value.asn1_string;
XPUSHs(sv_2mortal(newSViv(PTR2IV(s))));
- }
- else {
- count = sk_ASN1_TYPE_num(att->value.set);
- for (i=0; i<count; i++) {
- s = (sk_ASN1_TYPE_value(att->value.set, i)->value.asn1_string);
- XPUSHs(sv_2mortal(newSViv(PTR2IV(s))));
- }
- }
+ }
#endif
@@ -4439,6 +4573,7 @@ SSL_set_session_id_context(ssl,sid_ctx,sid_ctx_len)
const unsigned char * sid_ctx
unsigned int sid_ctx_len
+#if OPENSSL_VERSION_NUMBER < 0x10100000L
void
SSL_CTX_set_tmp_rsa_callback(ctx, cb)
SSL_CTX * ctx
@@ -4449,6 +4584,8 @@ SSL_set_tmp_rsa_callback(ssl, cb)
SSL * ssl
cb_ssl_int_int_ret_RSA * cb
+#endif
+
void
SSL_CTX_set_tmp_dh_callback(ctx, dh)
SSL_CTX * ctx
@@ -4526,6 +4663,7 @@ SSL_CTX_get_session_cache_mode(ctx)
OUTPUT:
RETVAL
+#if OPENSSL_VERSION_NUMBER < 0x10100000L
long
SSL_CTX_need_tmp_RSA(ctx)
SSL_CTX * ctx
@@ -4534,6 +4672,8 @@ SSL_CTX_need_tmp_RSA(ctx)
OUTPUT:
RETVAL
+#endif
+
int
SSL_CTX_set_app_data(ctx,arg)
SSL_CTX * ctx
@@ -4575,11 +4715,14 @@ SSL_CTX_set_tmp_dh(ctx,dh)
SSL_CTX * ctx
DH * dh
+#if OPENSSL_VERSION_NUMBER < 0x10100000L
long
SSL_CTX_set_tmp_rsa(ctx,rsa)
SSL_CTX * ctx
RSA * rsa
+#endif
+
#if OPENSSL_VERSION_NUMBER > 0x10000000L && !defined OPENSSL_NO_EC
EC_KEY *
@@ -4591,10 +4734,53 @@ EC_KEY_free(key)
EC_KEY * key
long
-SSL_CTX_set_tmp_ecdh(ctx,ecdh);
+SSL_CTX_set_tmp_ecdh(ctx,ecdh)
SSL_CTX * ctx
EC_KEY * ecdh
+int
+EVP_PKEY_assign_EC_KEY(pkey,key)
+ EVP_PKEY * pkey
+ EC_KEY * key
+
+
+EC_KEY *
+EC_KEY_generate_key(curve)
+ SV *curve;
+ CODE:
+ EC_GROUP *group = NULL;
+ EC_KEY *eckey = NULL;
+ int nid;
+
+ RETVAL = 0;
+ if (SvIOK(curve)) {
+ nid = SvIV(curve);
+ } else {
+ nid = OBJ_sn2nid(SvPV_nolen(curve));
+#if OPENSSL_VERSION_NUMBER > 0x10002000L
+ if (!nid) nid = EC_curve_nist2nid(SvPV_nolen(curve));
+#endif
+ if (!nid) croak("unknown curve %s",SvPV_nolen(curve));
+ }
+
+ group = EC_GROUP_new_by_curve_name(nid);
+ if (!group) croak("unknown curve nid=%d",nid);
+ EC_GROUP_set_asn1_flag(group,OPENSSL_EC_NAMED_CURVE);
+
+ eckey = EC_KEY_new();
+ if ( eckey
+ && EC_KEY_set_group(eckey, group)
+ && EC_KEY_generate_key(eckey)) {
+ RETVAL = eckey;
+ } else {
+ if (eckey) EC_KEY_free(eckey);
+ }
+ if (group) EC_GROUP_free(group);
+
+ OUTPUT:
+ RETVAL
+
+
#endif
void *
@@ -4622,25 +4808,20 @@ SSL_get_mode(ssl)
OUTPUT:
RETVAL
-int
-SSL_get_state(ssl)
- SSL * ssl
- CODE:
- RETVAL = SSL_state(ssl);
- OUTPUT:
- RETVAL
-
void
SSL_set_state(ssl,state)
SSL * ssl
int state
CODE:
-#ifdef OPENSSL_NO_SSL_INTERN
+#if OPENSSL_VERSION_NUMBER >= 0x10100000L
+ /* not available */
+#elif defined(OPENSSL_NO_SSL_INTERN)
SSL_set_state(ssl,state);
#else
ssl->state = state;
#endif
+#if OPENSSL_VERSION_NUMBER < 0x10100000L
long
SSL_need_tmp_RSA(ssl)
SSL * ssl
@@ -4649,6 +4830,9 @@ SSL_need_tmp_RSA(ssl)
OUTPUT:
RETVAL
+
+#endif
+
long
SSL_num_renegotiations(ssl)
SSL * ssl
@@ -4668,10 +4852,6 @@ SSL_SESSION_get_app_data(ses)
long
SSL_session_reused(ssl)
SSL * ssl
- CODE:
- RETVAL = SSL_ctrl(ssl,SSL_CTRL_GET_SESSION_REUSED,0,NULL);
- OUTPUT:
- RETVAL
int
SSL_SESSION_set_app_data(s,a)
@@ -4714,6 +4894,7 @@ SSL_set_tmp_dh(ssl,dh)
SSL * ssl
DH * dh
+#if OPENSSL_VERSION_NUMBER < 0x10100000L
long
SSL_set_tmp_rsa(ssl,rsa)
SSL * ssl
@@ -4723,6 +4904,7 @@ SSL_set_tmp_rsa(ssl,rsa)
OUTPUT:
RETVAL
+#endif
#ifdef __ANDROID__
@@ -4855,6 +5037,22 @@ SSL_total_renegotiations(ssl)
OUTPUT:
RETVAL
+#if OPENSSL_VERSION_NUMBER >= 0x10100000L && !defined(LIBRESSL_VERSION_NUMBER)
+void
+SSL_SESSION_get_master_key(s)
+ SSL_SESSION * s
+ PREINIT:
+ size_t master_key_length;
+ unsigned char* master_key;
+ CODE:
+ ST(0) = sv_newmortal(); /* Undefined to start with */
+ master_key_length = SSL_SESSION_get_master_key(s, 0, 0); /* get the length */
+ New(0, master_key, master_key_length, unsigned char);
+ SSL_SESSION_get_master_key(s, master_key, master_key_length);
+ sv_setpvn(ST(0), (const char*)master_key, master_key_length);
+ Safefree(master_key);
+
+#else
void
SSL_SESSION_get_master_key(s)
SSL_SESSION * s
@@ -4862,6 +5060,10 @@ SSL_SESSION_get_master_key(s)
ST(0) = sv_newmortal(); /* Undefined to start with */
sv_setpvn(ST(0), (const char*)s->master_key, s->master_key_length);
+#endif
+
+#if OPENSSL_VERSION_NUMBER < 0x10100000L
+
void
SSL_SESSION_set_master_key(s,key)
SSL_SESSION * s
@@ -4873,6 +5075,26 @@ SSL_SESSION_set_master_key(s,key)
memcpy(s->master_key, key, len);
s->master_key_length = len;
+#endif
+
+#if OPENSSL_VERSION_NUMBER >= 0x10100000L && !defined(LIBRESSL_VERSION_NUMBER)
+
+void
+SSL_get_client_random(s)
+ SSL * s
+ PREINIT:
+ size_t random_length;
+ unsigned char* random_data;
+ CODE:
+ ST(0) = sv_newmortal(); /* Undefined to start with */
+ random_length = SSL_get_client_random(s, 0, 0); /* get the length */
+ New(0, random_data, random_length, unsigned char);
+ SSL_get_client_random(s, random_data, random_length);
+ sv_setpvn(ST(0), (const char*)random_data, random_length);
+ Safefree(random_data);
+
+#else
+
void
SSL_get_client_random(s)
SSL * s
@@ -4880,6 +5102,26 @@ SSL_get_client_random(s)
ST(0) = sv_newmortal(); /* Undefined to start with */
sv_setpvn(ST(0), (const char*)s->s3->client_random, SSL3_RANDOM_SIZE);
+#endif
+
+#if OPENSSL_VERSION_NUMBER >= 0x10100000L && !defined(LIBRESSL_VERSION_NUMBER)
+
+void
+SSL_get_server_random(s)
+ SSL * s
+ PREINIT:
+ size_t random_length;
+ unsigned char* random_data;
+ CODE:
+ ST(0) = sv_newmortal(); /* Undefined to start with */
+ random_length = SSL_get_server_random(s, 0, 0); /* get the length */
+ New(0, random_data, random_length, unsigned char);
+ SSL_get_server_random(s, random_data, random_length);
+ sv_setpvn(ST(0), (const char*)random_data, random_length);
+ Safefree(random_data);
+
+#else
+
void
SSL_get_server_random(s)
SSL * s
@@ -4887,10 +5129,26 @@ SSL_get_server_random(s)
ST(0) = sv_newmortal(); /* Undefined to start with */
sv_setpvn(ST(0), (const char*)s->s3->server_random, SSL3_RANDOM_SIZE);
+#endif
+
int
SSL_get_keyblock_size(s)
SSL * s
CODE:
+#if OPENSSL_VERSION_NUMBER >= 0x10100000L && !defined(LIBRESSL_VERSION_NUMBER)
+ const SSL_CIPHER *ssl_cipher;
+ int cipher, digest;
+ const EVP_CIPHER *c;
+ const EVP_MD *h;
+
+ ssl_cipher = SSL_get_current_cipher(s);
+ cipher = SSL_CIPHER_get_cipher_nid(ssl_cipher);
+ digest = SSL_CIPHER_get_digest_nid(ssl_cipher);
+ c = EVP_get_cipherbynid(cipher);
+ h = EVP_get_digestbynid(digest);
+ RETVAL = 2 * (EVP_CIPHER_key_length(c) + EVP_MD_size(h) +
+ EVP_CIPHER_iv_length(c));
+#else
if (s == NULL ||
s->enc_read_ctx == NULL ||
s->enc_read_ctx->cipher == NULL ||
@@ -4919,6 +5177,8 @@ SSL_get_keyblock_size(s)
EVP_CIPHER_iv_length(c)))
: -1;
}
+#endif
+
OUTPUT:
RETVAL
@@ -4956,13 +5216,34 @@ SSL_set_session_secret_cb(s,callback=&PL_sv_undef,data=&PL_sv_undef)
else {
cb_data_advanced_put(s, "ssleay_session_secret_cb!!func", newSVsv(callback));
cb_data_advanced_put(s, "ssleay_session_secret_cb!!data", newSVsv(data));
- SSL_set_session_secret_cb(s, (int (*)(SSL *s, void *secret, int *secret_len,
- STACK_OF(SSL_CIPHER) *peer_ciphers,
- SSL_CIPHER **cipher, void *arg))&ssleay_session_secret_cb_invoke, s);
+ SSL_set_session_secret_cb(s, (tls_session_secret_cb_fn)&ssleay_session_secret_cb_invoke, s);
+ }
+
+#endif
+
+#ifdef NET_SSLEAY_CAN_TICKET_KEY_CB
+
+void
+SSL_CTX_set_tlsext_ticket_getkey_cb(ctx,callback=&PL_sv_undef,data=&PL_sv_undef)
+ SSL_CTX * ctx
+ SV * callback
+ SV * data
+ CODE:
+ if (callback==NULL || !SvOK(callback)) {
+ SSL_CTX_set_tlsext_ticket_key_cb(ctx, NULL);
+ cb_data_advanced_put(ctx, "tlsext_ticket_key_cb!!func", NULL);
+ cb_data_advanced_put(ctx, "tlsext_ticket_key_cb!!data", NULL);
+ }
+ else {
+ cb_data_advanced_put(ctx, "tlsext_ticket_key_cb!!func", newSVsv(callback));
+ cb_data_advanced_put(ctx, "tlsext_ticket_key_cb!!data", newSVsv(data));
+ SSL_CTX_set_tlsext_ticket_key_cb(ctx, &tlsext_ticket_key_cb_invoke);
}
+
#endif
+
#if OPENSSL_VERSION_NUMBER < 0x0090700fL
#define REM11 "NOTE: before 0.9.7"
@@ -5382,15 +5663,28 @@ ASN1_OBJECT *
P_X509_get_signature_alg(x)
X509 * x
CODE:
+#if OPENSSL_VERSION_NUMBER >= 0x10100000L && !defined(LIBRESSL_VERSION_NUMBER)
+ RETVAL = (X509_get0_tbs_sigalg(x)->algorithm);
+#else
RETVAL = (x->cert_info->signature->algorithm);
+#endif
OUTPUT:
RETVAL
ASN1_OBJECT *
P_X509_get_pubkey_alg(x)
X509 * x
+ PREINIT:
CODE:
+#if OPENSSL_VERSION_NUMBER >= 0x10100000L
+ {
+ X509_ALGOR * algor;
+ X509_PUBKEY_get0_param(0, 0, 0, &algor, X509_get_X509_PUBKEY(x));
+ RETVAL = (algor->algorithm);
+ }
+#else
RETVAL = (x->cert_info->key->algor->algorithm);
+#endif
OUTPUT:
RETVAL
@@ -5705,8 +5999,7 @@ SSL_OCSP_response_verify(ssl,rsp,svreq=NULL,flags=0)
* response does not contain the chain up to the trusted root */
STACK_OF(X509) *chain = SSL_get_peer_cert_chain(ssl);
for(i=0;i<sk_X509_num(chain);i++) {
- if (!bsr->certs) bsr->certs = sk_X509_new_null();
- sk_X509_push(bsr->certs,X509_dup(sk_X509_value(chain,i)));
+ OCSP_basic_add1_cert(bsr, sk_X509_value(chain,i));
}
TRACE(1,"run basic verify");
RETVAL = OCSP_basic_verify(bsr, NULL, store, flags);
@@ -5718,7 +6011,7 @@ SSL_OCSP_response_verify(ssl,rsp,svreq=NULL,flags=0)
X509 *issuer;
X509 *last = sk_X509_value(chain,sk_X509_num(chain)-1);
if ( (issuer = find_issuer(last,store,chain))) {
- sk_X509_push(bsr->certs,X509_dup(issuer));
+ OCSP_basic_add1_cert(bsr, X509_dup(issuer));
TRACE(1,"run OCSP_basic_verify with issuer for last chain element");
RETVAL = OCSP_basic_verify(bsr, NULL, store, flags);
}
@@ -5736,7 +6029,6 @@ OCSP_response_results(rsp,...)
OCSP_BASICRESP *bsr;
int i,want_array;
time_t nextupd = 0;
- STACK_OF(OCSP_SINGLERESP) *sks;
int getall,sksn;
bsr = OCSP_response_get1_basic(rsp);
@@ -5744,8 +6036,7 @@ OCSP_response_results(rsp,...)
want_array = (GIMME == G_ARRAY);
getall = (items <= 1);
- sks = bsr->tbsResponseData->responses;
- sksn = sk_OCSP_SINGLERESP_num(sks);
+ sksn = OCSP_resp_count(bsr);
for(i=0; i < (getall ? sksn : items-1); i++) {
const char *error = NULL;
@@ -5754,9 +6045,8 @@ OCSP_response_results(rsp,...)
SV *idsv = NULL;
if(getall) {
- sir = sk_OCSP_SINGLERESP_value(sks,i);
+ sir = OCSP_resp_get0(bsr,i);
} else {
- int k;
STRLEN len;
const unsigned char *p;
@@ -5767,22 +6057,36 @@ OCSP_response_results(rsp,...)
error = "failed to get OCSP certid from string";
goto end;
}
- for(k=0;k<sksn;k++) {
- if (!OCSP_id_cmp(certid,sk_OCSP_SINGLERESP_value(sks,k)->certId)) {
- sir = sk_OCSP_SINGLERESP_value(sks,k);
- break;
- }
+ int first = OCSP_resp_find(bsr, certid, -1); /* Find the first matching */
+ if (first >= 0)
+ {
+ sir = OCSP_resp_get0(bsr,first);
+ break;
}
}
- if (!sir) {
- error = "cannot find entry for certificate in OCSP response";
- } else if (!OCSP_check_validity(sir->thisUpdate,sir->nextUpdate,0,-1)) {
- error = "response not yet valid or expired";
- } else if (sir->certStatus->type == V_OCSP_CERTSTATUS_REVOKED) {
- error = "certificate status is revoked";
- } else if (sir->certStatus->type != V_OCSP_CERTSTATUS_GOOD) {
- error = "certificate status is unknown";
+ int status, revocationReason;
+ ASN1_GENERALIZEDTIME *revocationTime, *thisupdate, *nextupdate;
+ if (sir)
+ {
+#if OPENSSL_VERSION_NUMBER >= 0x10100000L
+ status = OCSP_single_get0_status(sir, &revocationReason, &revocationTime, &thisupdate, &nextupdate);
+#else
+ status = sir->certStatus->type;
+ revocationTime = sir->certStatus->value.revoked->revocationTime;
+ thisupdate = sir->thisUpdate;
+ nextupdate = sir->nextUpdate;
+#endif
+ if (status == V_OCSP_CERTSTATUS_REVOKED) {
+ error = "certificate status is revoked";
+ } else if (status != V_OCSP_CERTSTATUS_GOOD) {
+ error = "certificate status is unknown";
+ }
+ else if (!OCSP_check_validity(thisupdate, nextupdate, 0, -1)) {
+ error = "response not yet valid or expired";
+ }
+ } else {
+ error = "cannot find entry for certificate in OCSP response";
}
end:
@@ -5791,12 +6095,20 @@ OCSP_response_results(rsp,...)
if (!idsv) {
/* getall: create new SV with OCSP_CERTID */
unsigned char *pi,*pc;
+#if OPENSSL_VERSION_NUMBER >= 0x10100000L && !defined(LIBRESSL_VERSION_NUMBER)
+ int len = i2d_OCSP_CERTID(OCSP_SINGLERESP_get0_id(sir),NULL);
+#else
int len = i2d_OCSP_CERTID(sir->certId,NULL);
+#endif
if(!len) continue;
Newx(pc,len,unsigned char);
if (!pc) croak("out of memory");
pi = pc;
+#if OPENSSL_VERSION_NUMBER >= 0x10100000L && !defined(LIBRESSL_VERSION_NUMBER)
+ i2d_OCSP_CERTID(OCSP_SINGLERESP_get0_id(sir),&pi);
+#else
i2d_OCSP_CERTID(sir->certId,&pi);
+#endif
idsv = newSVpv((char*)pc,len);
Safefree(pc);
} else {
@@ -5809,26 +6121,26 @@ OCSP_response_results(rsp,...)
HV *details = newHV();
av_push(idav,newRV_noinc((SV*)details));
hv_store(details,"statusType",10,
- newSViv(sir->certStatus->type),0);
- if (sir->nextUpdate) hv_store(details,"nextUpdate",10,
- newSViv(ASN1_TIME_timet(sir->nextUpdate)),0);
- if (sir->thisUpdate) hv_store(details,"thisUpdate",10,
- newSViv(ASN1_TIME_timet(sir->thisUpdate)),0);
- if (sir->certStatus->type == V_OCSP_CERTSTATUS_REVOKED) {
+ newSViv(status),0);
+ if (nextupdate) hv_store(details,"nextUpdate",10,
+ newSViv(ASN1_TIME_timet(nextupdate)),0);
+ if (thisupdate) hv_store(details,"thisUpdate",10,
+ newSViv(ASN1_TIME_timet(thisupdate)),0);
+ if (status == V_OCSP_CERTSTATUS_REVOKED) {
+#if OPENSSL_VERSION_NUMBER < 0x10100000L
OCSP_REVOKEDINFO *rev = sir->certStatus->value.revoked;
- hv_store(details,"revocationTime",14,newSViv(
- ASN1_TIME_timet(rev->revocationTime)),0);
- hv_store(details,"revocationReason",16,newSViv(
- ASN1_ENUMERATED_get(rev->revocationReason)),0);
+ revocationReason = ASN1_ENUMERATED_get(rev->revocationReason);
+#endif
+ hv_store(details,"revocationTime",14,newSViv(ASN1_TIME_timet(revocationTime)),0);
+ hv_store(details,"revocationReason",16,newSViv(revocationReason),0);
hv_store(details,"revocationReason_str",20,newSVpv(
- OCSP_crl_reason_str(ASN1_ENUMERATED_get(
- rev->revocationReason)),0),0);
+ OCSP_crl_reason_str(revocationReason),0),0);
}
}
XPUSHs(sv_2mortal(newRV_noinc((SV*)idav)));
} else if (!error) {
/* compute lowest nextUpdate */
- time_t nu = ASN1_TIME_timet(sir->nextUpdate);
+ time_t nu = ASN1_TIME_timet(nextupdate);
if (!nextupd || nextupd>nu) nextupd = nu;
}
diff --git a/inc/Module/Install.pm b/inc/Module/Install.pm
index 4ecf46b..f44ab4d 100644
--- a/inc/Module/Install.pm
+++ b/inc/Module/Install.pm
@@ -17,7 +17,7 @@ package Module::Install;
# 3. The ./inc/ version of Module::Install loads
# }
-use 5.005;
+use 5.006;
use strict 'vars';
use Cwd ();
use File::Find ();
@@ -31,7 +31,7 @@ BEGIN {
# This is not enforced yet, but will be some time in the next few
# releases once we can make sure it won't clash with custom
# Module::Install extensions.
- $VERSION = '1.06';
+ $VERSION = '1.16';
# Storage for the pseudo-singleton
$MAIN = undef;
@@ -156,10 +156,10 @@ END_DIE
sub autoload {
my $self = shift;
my $who = $self->_caller;
- my $cwd = Cwd::cwd();
+ my $cwd = Cwd::getcwd();
my $sym = "${who}::AUTOLOAD";
$sym->{$cwd} = sub {
- my $pwd = Cwd::cwd();
+ my $pwd = Cwd::getcwd();
if ( my $code = $sym->{$pwd} ) {
# Delegate back to parent dirs
goto &$code unless $cwd eq $pwd;
@@ -239,7 +239,7 @@ sub new {
# ignore the prefix on extension modules built from top level.
my $base_path = Cwd::abs_path($FindBin::Bin);
- unless ( Cwd::abs_path(Cwd::cwd()) eq $base_path ) {
+ unless ( Cwd::abs_path(Cwd::getcwd()) eq $base_path ) {
delete $args{prefix};
}
return $args{_self} if $args{_self};
@@ -338,7 +338,7 @@ sub find_extensions {
if ( $subpath eq lc($subpath) || $subpath eq uc($subpath) ) {
my $content = Module::Install::_read($subpath . '.pm');
my $in_pod = 0;
- foreach ( split //, $content ) {
+ foreach ( split /\n/, $content ) {
$in_pod = 1 if /^=\w/;
$in_pod = 0 if /^=cut/;
next if ($in_pod || /^=cut/); # skip pod text
@@ -378,6 +378,7 @@ eval( $] >= 5.006 ? <<'END_NEW' : <<'END_OLD' ); die $@ if $@;
sub _read {
local *FH;
open( FH, '<', $_[0] ) or die "open($_[0]): $!";
+ binmode FH;
my $string = do { local $/; <FH> };
close FH or die "close($_[0]): $!";
return $string;
@@ -386,6 +387,7 @@ END_NEW
sub _read {
local *FH;
open( FH, "< $_[0]" ) or die "open($_[0]): $!";
+ binmode FH;
my $string = do { local $/; <FH> };
close FH or die "close($_[0]): $!";
return $string;
@@ -416,6 +418,7 @@ eval( $] >= 5.006 ? <<'END_NEW' : <<'END_OLD' ); die $@ if $@;
sub _write {
local *FH;
open( FH, '>', $_[0] ) or die "open($_[0]): $!";
+ binmode FH;
foreach ( 1 .. $#_ ) {
print FH $_[$_] or die "print($_[0]): $!";
}
@@ -425,6 +428,7 @@ END_NEW
sub _write {
local *FH;
open( FH, "> $_[0]" ) or die "open($_[0]): $!";
+ binmode FH;
foreach ( 1 .. $#_ ) {
print FH $_[$_] or die "print($_[0]): $!";
}
@@ -434,7 +438,7 @@ END_OLD
# _version is for processing module versions (eg, 1.03_05) not
# Perl versions (eg, 5.8.1).
-sub _version ($) {
+sub _version {
my $s = shift || 0;
my $d =()= $s =~ /(\.)/g;
if ( $d >= 2 ) {
@@ -450,12 +454,12 @@ sub _version ($) {
return $l + 0;
}
-sub _cmp ($$) {
+sub _cmp {
_version($_[1]) <=> _version($_[2]);
}
# Cloned from Params::Util::_CLASS
-sub _CLASS ($) {
+sub _CLASS {
(
defined $_[0]
and
diff --git a/inc/Module/Install/Base.pm b/inc/Module/Install/Base.pm
index 802844a..5762a74 100644
--- a/inc/Module/Install/Base.pm
+++ b/inc/Module/Install/Base.pm
@@ -4,7 +4,7 @@ package Module::Install::Base;
use strict 'vars';
use vars qw{$VERSION};
BEGIN {
- $VERSION = '1.06';
+ $VERSION = '1.16';
}
# Suspend handler for "redefined" warnings
diff --git a/inc/Module/Install/Can.pm b/inc/Module/Install/Can.pm
index 22167b8..d859276 100644
--- a/inc/Module/Install/Can.pm
+++ b/inc/Module/Install/Can.pm
@@ -8,7 +8,7 @@ use Module::Install::Base ();
use vars qw{$VERSION @ISA $ISCORE};
BEGIN {
- $VERSION = '1.06';
+ $VERSION = '1.16';
@ISA = 'Module::Install::Base';
$ISCORE = 1;
}
diff --git a/inc/Module/Install/External.pm b/inc/Module/Install/External.pm
index 53522d6..88ed718 100644
--- a/inc/Module/Install/External.pm
+++ b/inc/Module/Install/External.pm
@@ -8,7 +8,7 @@ use Module::Install::Base ();
use vars qw{$VERSION $ISCORE @ISA};
BEGIN {
- $VERSION = '1.06';
+ $VERSION = '1.16';
$ISCORE = 1;
@ISA = qw{Module::Install::Base};
}
diff --git a/inc/Module/Install/Fetch.pm b/inc/Module/Install/Fetch.pm
index bee0c4f..41d3517 100644
--- a/inc/Module/Install/Fetch.pm
+++ b/inc/Module/Install/Fetch.pm
@@ -6,7 +6,7 @@ use Module::Install::Base ();
use vars qw{$VERSION @ISA $ISCORE};
BEGIN {
- $VERSION = '1.06';
+ $VERSION = '1.16';
@ISA = 'Module::Install::Base';
$ISCORE = 1;
}
diff --git a/inc/Module/Install/Makefile.pm b/inc/Module/Install/Makefile.pm
index 7052f36..e9918d2 100644
--- a/inc/Module/Install/Makefile.pm
+++ b/inc/Module/Install/Makefile.pm
@@ -8,7 +8,7 @@ use Fcntl qw/:flock :seek/;
use vars qw{$VERSION @ISA $ISCORE};
BEGIN {
- $VERSION = '1.06';
+ $VERSION = '1.16';
@ISA = 'Module::Install::Base';
$ISCORE = 1;
}
@@ -133,7 +133,7 @@ sub makemaker_args {
return $args;
}
-# For mm args that take multiple space-seperated args,
+# For mm args that take multiple space-separated args,
# append an argument to the current list.
sub makemaker_append {
my $self = shift;
diff --git a/inc/Module/Install/Metadata.pm b/inc/Module/Install/Metadata.pm
index 58430f3..9792685 100644
--- a/inc/Module/Install/Metadata.pm
+++ b/inc/Module/Install/Metadata.pm
@@ -6,7 +6,7 @@ use Module::Install::Base ();
use vars qw{$VERSION @ISA $ISCORE};
BEGIN {
- $VERSION = '1.06';
+ $VERSION = '1.16';
@ISA = 'Module::Install::Base';
$ISCORE = 1;
}
@@ -347,7 +347,7 @@ sub name_from {
^ \s*
package \s*
([\w:]+)
- \s* ;
+ [\s|;]*
/ixms
) {
my ($name, $module_name) = ($1, $1);
@@ -705,7 +705,7 @@ sub _write_mymeta_data {
my @yaml = Parse::CPAN::Meta::LoadFile('META.yml');
my $meta = $yaml[0];
- # Overwrite the non-configure dependency hashs
+ # Overwrite the non-configure dependency hashes
delete $meta->{requires};
delete $meta->{build_requires};
delete $meta->{recommends};
diff --git a/inc/Module/Install/PRIVATE/Net/SSLeay.pm b/inc/Module/Install/PRIVATE/Net/SSLeay.pm
index 8f73647..d6fbdf6 100644
--- a/inc/Module/Install/PRIVATE/Net/SSLeay.pm
+++ b/inc/Module/Install/PRIVATE/Net/SSLeay.pm
@@ -1,5 +1,4 @@
#line 1
-#line 1
package Module::Install::PRIVATE::Net::SSLeay;
use strict;
diff --git a/inc/Module/Install/Win32.pm b/inc/Module/Install/Win32.pm
index eeaa3fe..218a66b 100644
--- a/inc/Module/Install/Win32.pm
+++ b/inc/Module/Install/Win32.pm
@@ -6,7 +6,7 @@ use Module::Install::Base ();
use vars qw{$VERSION @ISA $ISCORE};
BEGIN {
- $VERSION = '1.06';
+ $VERSION = '1.16';
@ISA = 'Module::Install::Base';
$ISCORE = 1;
}
diff --git a/inc/Module/Install/WriteAll.pm b/inc/Module/Install/WriteAll.pm
index 85d8018..530749b 100644
--- a/inc/Module/Install/WriteAll.pm
+++ b/inc/Module/Install/WriteAll.pm
@@ -6,7 +6,7 @@ use Module::Install::Base ();
use vars qw{$VERSION @ISA $ISCORE};
BEGIN {
- $VERSION = '1.06';
+ $VERSION = '1.16';
@ISA = qw{Module::Install::Base};
$ISCORE = 1;
}
diff --git a/lib/Net/SSLeay.pm b/lib/Net/SSLeay.pm
index 4968e15..88886ee 100644
--- a/lib/Net/SSLeay.pm
+++ b/lib/Net/SSLeay.pm
@@ -4,7 +4,7 @@
# Copyright (C) 2005 Florian Ragwitz <rafl at debian.org>, All Rights Reserved.
# Copyright (C) 2005 Mike McCauley <mikem at airspayce.com>, All Rights Reserved.
#
-# $Id: SSLeay.pm 464 2016-04-11 00:16:31Z mikem-guest $
+# $Id: SSLeay.pm 477 2016-07-31 20:24:00Z mikem-guest $
#
# Change data removed from here. See Changes
# The distribution and use of this module are subject to the conditions
@@ -63,7 +63,7 @@ $Net::SSLeay::slowly = 0;
$Net::SSLeay::random_device = '/dev/urandom';
$Net::SSLeay::how_random = 512;
-$VERSION = '1.74'; # Dont forget to set version in META.yml too
+$VERSION = '1.77'; # Dont forget to set version in META.yml too
@ISA = qw(Exporter);
#BEWARE:
diff --git a/lib/Net/SSLeay.pod b/lib/Net/SSLeay.pod
index e494541..efb8243 100644
--- a/lib/Net/SSLeay.pod
+++ b/lib/Net/SSLeay.pod
@@ -44,6 +44,8 @@ B<COMPATIBILITY NOTE:> L<Net::SSLeay> cannot be built with pre-0.9.3 openssl. It
to use at least 0.9.7 (as older versions are not tested during development). Some low level API functions
may be available with certain openssl versions.
+It is compatible with OpenSSL 1.0 and 1.1. Some functions are not available under OpenSSL 1.1.
+
L<Net::SSLeay> module basically comprise of:
=over
@@ -1393,8 +1395,8 @@ B<COMPATIBILITY:> not available in Net-SSLeay-1.45 and before
Set the key referenced by $pkey to $key
-B<NOTE:> In accordance with the OpenSSL naming convention the $key assigned
-to the $pkey using the "1" functions must be freed as well as $pkey.
+B<NOTE:> No reference counter will be increased, i.e. $key will be freed if
+$pkey is freed.
my $rv = Net::SSLeay::EVP_PKEY_assign_RSA($pkey, $key);
# $pkey - value corresponding to openssl's EVP_PKEY structure
@@ -1402,7 +1404,24 @@ to the $pkey using the "1" functions must be freed as well as $pkey.
#
# returns: 1 on success, 0 on failure
-Check openssl doc L<http://www.openssl.org/docs/crypto/EVP_PKEY_set1_RSA.html|http://www.openssl.org/docs/crypto/EVP_PKEY_set1_RSA.html>
+Check openssl doc L<http://www.openssl.org/docs/crypto/EVP_PKEY_assign_RSA.html|http://www.openssl.org/docs/crypto/EVP_PKEY_assign_RSA.html>
+
+=item * EVP_PKEY_assign_EC_KEY
+
+B<COMPATIBILITY:> not available in Net-SSLeay-1.74 and before
+
+Set the key referenced by $pkey to $key
+
+B<NOTE:> No reference counter will be increased, i.e. $key will be freed if
+$pkey is freed.
+
+ my $rv = Net::SSLeay::EVP_PKEY_assign_EC_KEY($pkey, $key);
+ # $pkey - value corresponding to openssl's EVP_PKEY structure
+ # $key - value corresponding to openssl's EC_KEY structure
+ #
+ # returns: 1 on success, 0 on failure
+
+Check openssl doc L<http://www.openssl.org/docs/crypto/EVP_PKEY_assign_EC_KEY.html|http://www.openssl.org/docs/crypto/EVP_PKEY_assign_EC_KEY.html>
=item * EVP_PKEY_bits
@@ -1844,6 +1863,11 @@ Sets 'master_key' value for SSL_SESSION structure $s
#
# returns: no return value
+Not available with OpenSSL 1.1 and later.
+Code that previously used
+ SESSION_set_master_key must now set $secret in the session_secret
+ callback set with SSL_set_session_secret_cb.
+
=item * SESSION_get_time
Returns the time at which the session s was established.
@@ -2447,6 +2471,8 @@ Return the result of C<SSL_CTX_ctrl(ctx,SSL_CTRL_NEED_TMP_RSA,0,NULL)>
#
# returns: result of SSL_CTRL_NEED_TMP_RSA command
+Not available with OpenSSL 1.1 and later.
+
=item * CTX_new
The same as L</CTX_v23_new>
@@ -2457,6 +2483,8 @@ The same as L</CTX_v23_new>
Check openssl doc L<http://www.openssl.org/docs/ssl/SSL_CTX_new.html|http://www.openssl.org/docs/ssl/SSL_CTX_new.html>
+Not available with OpenSSL 1.1 and later.
+
=item * CTX_v2_new
Creates a new SSL_CTX object - based on SSLv2_method() - as framework to establish TLS/SSL enabled connections.
@@ -2906,6 +2934,8 @@ Sets the temporary/ephemeral RSA key to be used to be $rsa.
Check openssl doc L<http://www.openssl.org/docs/ssl/SSL_CTX_set_tmp_rsa_callback.html|http://www.openssl.org/docs/ssl/SSL_CTX_set_tmp_rsa_callback.html>
+Not available with OpenSSL 1.1 and later.
+
=item * CTX_set_tmp_rsa_callback
Sets the callback function for ctx to be used when a temporary/ephemeral RSA key is required to $tmp_rsa_callback.
@@ -2920,6 +2950,8 @@ Sets the callback function for ctx to be used when a temporary/ephemeral RSA key
Check openssl doc L<http://www.openssl.org/docs/ssl/SSL_CTX_set_tmp_rsa_callback.html|http://www.openssl.org/docs/ssl/SSL_CTX_set_tmp_rsa_callback.html>
+Not available with OpenSSL 1.1 and later.
+
=item * CTX_set_trust
my $rv = Net::SSLeay::CTX_set_trust($s, $trust);
@@ -3436,9 +3468,9 @@ Obtains the latest 'Finished' message expected from the peer.
=item * get_keyblock_size
-B<NOTE:> Does not exactly correspond to any low level API function.
+Gets the length of the TLS keyblock.
-??? (more info needed)
+B<NOTE:> Does not exactly correspond to any low level API function.
my $rv = Net::SSLeay::get_keyblock_size($ssl);
# $ssl - value corresponding to openssl's SSL structure
@@ -3680,6 +3712,8 @@ Sets the SSL connection state.
Net::SSLeay::set_state($ssl,Net::SSLeay::SSL_ST_ACCEPT());
+Not available with OpenSSL 1.1 and later.
+
=item * get_verify_depth
Returns the verification depth limit currently set in $ssl.
@@ -3829,6 +3863,8 @@ Executes SSL_CTRL_NEED_TMP_RSA command on $ssl.
#
# returns: command result
+Not available with OpenSSL 1.1 and later.
+
=item * num_renegotiations
Executes SSL_CTRL_GET_NUM_RENEGOTIATIONS command on $ssl.
@@ -4131,6 +4167,91 @@ Setup pre-shared secret session resumption function.
#
# returns: no return value
+The callback function will be called like:
+callback_function($secret, $ciphers, $pref_cipher, $data);
+
+# $secret is the current master session key, usually all 0s at the beginning of a session
+# $ciphers is ref to an array of peer cipher names
+# $pref_cipher is a ref to an index into the list of cipher names of
+# the preferred cipher. Set it if you want to specify a preferred cipher
+# $data is the data passed to set_session_secret_cb
+
+The callback function should return 1 if it likes the suggested cipher (or has selected an alternative
+by setting pref_cipher), else it should return 0 (in which case OpenSSL will select its own preferred cipher).
+
+With OpenSSL 1.1 and later, callback_function can change the master key for the session by
+altering $secret and returning 1.
+
+=item * CTX_set_tlsext_ticket_getkey_cb
+
+Setup encryption for TLS session tickets (stateless session reuse).
+
+ Net::SSLeay::CTX_set_tlsext_ticket_getkey_cb($ctx, $func, $data);
+ # $ctx - value corresponding to openssl's SSL_CTX structure
+ # $func - perl reference to callback function
+ # $data - [optional] data that will be passed to callback function when invoked
+ #
+ # returns: no return value
+
+The callback function will be called like:
+getkey($data,[$key_name]) -> ($key,$current_key_name)
+
+# $data is the data passed to set_session_secret_cb
+# $key_name is the name of the key OpenSSL has extracted from the session ticket
+# $key is the requested key for ticket encryption + HMAC
+# $current_key_name is the name for the currently valid key
+
+OpenSSL will call the function without a key name if it generates a new ticket.
+It then needs the callback to return the encryption+HMAC key and an identifier
+(key name) for this key.
+
+When OpenSSL gets a session ticket from the client it extracts the key name and
+calls the callback with this name as argument. It then expects the callback to
+return the encryption+HMAC key matching the requested key name and and also the
+key name which should be used at the moment. If the requested key name and the
+returned key name differ it means that this session ticket was created with an
+expired key and need to be renewed. In this case OpenSSL will call the callback
+again with no key name to create a new session ticket based on the old one.
+
+The key must be at least 32 byte of random data which can be created with
+RAND_bytes. Internally the first 16 byte are used as key in AES-128 encryption
+while the next 16 byte are used for the SHA-256 HMAC.
+The key name are binary data and must be exactly 16 byte long.
+
+Example:
+
+ Net::SSLeay::RAND_bytes(my $oldkey,32);
+ Net::SSLeay::RAND_bytes(my $newkey,32);
+ my $oldkey_name = pack("a16",'oldsecret');
+ my $newkey_name = pack("a16",'newsecret');
+
+ my @keys = (
+ [ $newkey_name, $newkey ], # current active key
+ [ $oldkey_name, $oldkey ], # already expired
+ );
+
+ Net::SSLeay::CTX_set_tlsext_ticket_getkey_cb($server2->_ctx, sub {
+ my ($mykeys,$name) = @_;
+
+ # return (current_key, current_key_name) if no name given
+ return ($mykeys->[0][1],$mykeys->[0][0]) if ! $name;
+
+ # return (matching_key, current_key_name) if we find a key matching
+ # the given name
+ for(my $i = 0; $i<@$mykeys; $i++) {
+ next if $name ne $mykeys->[$i][0];
+ return ($mykeys->[$i][1],$mykeys->[0][0]);
+ }
+
+ # no matching key found
+ return;
+ },\@keys);
+
+
+This function is based on the OpenSSL function SSL_CTX_set_tlsext_ticket_key_cb
+but provides a simpler to use interface. For more information see
+L<http://www.openssl.org/docs/ssl/SSL_CTX_set_tlsext_ticket_key_cb.html|http://www.openssl.org/docs/ssl/SSL_CTX_set_tlsext_ticket_key_cb.html>
+
=item * set_shutdown
Sets the shutdown state of $ssl to $mode.
@@ -7961,6 +8082,23 @@ TBA
TBA
+=item * EC_KEY_generate_key
+
+Generates a EC key and returns it in a newly allocated EC_KEY structure.
+The EC key then can be used to create a PKEY which can be used in calls
+like X509_set_pubkey.
+
+ my $key = Net::SSLeay::EVP_PKEY_new();
+ my $ec = Net::SSLeay::EC_KEY_generate_key($curve);
+ Net::SSLeay::EVP_PKEY_assign_EC_KEY($key,$ec);
+
+ # $curve - curve name like 'secp521r1' or the matching Id (integer) of the curve
+ #
+ # returns: value corresponding to openssl's EC_KEY structure (0 on failure)
+
+This function has no equivalent in OpenSSL but combines multiple OpenSSL
+functions for an easier interface.
+
=back
diff --git a/t/local/32_x509_get_cert_info.t b/t/local/32_x509_get_cert_info.t
index d7079f9..80bf9d3 100755
--- a/t/local/32_x509_get_cert_info.t
+++ b/t/local/32_x509_get_cert_info.t
@@ -175,7 +175,7 @@ for my $f (keys (%$dump)) {
}
SKIP: {
- skip('crl_distribution_points requires 0.9.7+', scalar(@{$dump->{$f}->{cdp}})+1) unless Net::SSLeay::SSLeay >= 0x0090700f;
+ skip('crl_distribution_points requires 0.9.7+', int(@{$dump->{$f}->{cdp}})+1) unless Net::SSLeay::SSLeay >= 0x0090700f;
my @cdp = Net::SSLeay::P_X509_get_crl_distribution_points($x509);
is(scalar(@cdp), scalar(@{$dump->{$f}->{cdp}}), "cdp size\t$f");
for my $i (0..$#cdp) {
diff --git a/t/local/35_ephemeral.t b/t/local/35_ephemeral.t
index ce4b3dc..86e1d78 100644
--- a/t/local/35_ephemeral.t
+++ b/t/local/35_ephemeral.t
@@ -6,7 +6,7 @@ use Test::More;
use Net::SSLeay;
BEGIN {
- plan skip_all => "libressl removed support for ephemeral/temporary RSA private keys" if Net::SSLeay::constant("LIBRESSL_VERSION_NUMBER");
+ plan skip_all => "libressl and OpenSSL 1.1 removed support for ephemeral/temporary RSA private keys" if Net::SSLeay::constant("LIBRESSL_VERSION_NUMBER") || Net::SSLeay::constant("OPENSSL_VERSION_NUMBER") >= 0x10100000;
}
plan tests => 3;
diff --git a/t/local/63_ec_key_generate_key.t b/t/local/63_ec_key_generate_key.t
new file mode 100644
index 0000000..8c8375b
--- /dev/null
+++ b/t/local/63_ec_key_generate_key.t
@@ -0,0 +1,35 @@
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+use Test::More;
+use Net::SSLeay;
+
+if (!defined &Net::SSLeay::EC_KEY_generate_key) {
+ plan skip_all => "no suport for ECC in your OpenSSL";
+ exit(0);
+}
+
+plan tests => 4;
+
+Net::SSLeay::randomize();
+Net::SSLeay::load_error_strings();
+Net::SSLeay::ERR_load_crypto_strings();
+Net::SSLeay::SSLeay_add_ssl_algorithms();
+
+my $ec = Net::SSLeay::EC_KEY_generate_key('prime256v1');
+ok($ec,'EC key created');
+
+if ($ec) {
+ my $key = Net::SSLeay::EVP_PKEY_new();
+ my $rv = Net::SSLeay::EVP_PKEY_assign_EC_KEY($key,$ec);
+ ok($rv,'EC key assigned to PKEY');
+
+ my $pem = Net::SSLeay::PEM_get_string_PrivateKey($key);
+ ok( $pem =~m{^---.* PRIVATE KEY}m, "output key as PEM");
+
+ my $bio = Net::SSLeay::BIO_new( Net::SSLeay::BIO_s_mem());
+ Net::SSLeay::BIO_write($bio,$pem);
+ my $newkey = Net::SSLeay::PEM_read_bio_PrivateKey($bio);
+ ok($newkey,"read key again from PEM");
+}
diff --git a/t/local/64_ticket_sharing.t b/t/local/64_ticket_sharing.t
new file mode 100644
index 0000000..2db2077
--- /dev/null
+++ b/t/local/64_ticket_sharing.t
@@ -0,0 +1,270 @@
+#!/usr/bin/perl
+
+use strict;
+use warnings;
+use Test::More;
+use Socket;
+use File::Spec;
+use Net::SSLeay;
+use Config;
+
+# for debugging only
+my $DEBUG = 0;
+my $PCAP = 0;
+require Net::PcapWriter if $PCAP;
+
+plan skip_all => "no support for tlsext_ticket_key_cb"
+ if ! defined &Net::SSLeay::CTX_set_tlsext_ticket_getkey_cb;
+plan tests => 15;
+
+Net::SSLeay::randomize();
+Net::SSLeay::load_error_strings();
+Net::SSLeay::ERR_load_crypto_strings();
+Net::SSLeay::SSLeay_add_ssl_algorithms();
+
+my $SSL_ERROR; # set in _minSSL
+my %TRANSFER; # set in _handshake
+
+my $client = _minSSL->new();
+my $server = _minSSL->new( cert => [
+ File::Spec->catfile('t','data','cert.pem'),
+ File::Spec->catfile('t','data','key.pem')
+]);
+
+
+# initial tests without reuse
+# ----------------------------------------------
+is( _handshake($client,$server), 'full', "initial handshake is full");
+is( _handshake($client,$server), 'full', "another full handshake");
+
+# explicitly reuse session in client to check that server accepts it
+# ----------------------------------------------
+my $sess = Net::SSLeay::get1_session($client->_ssl);
+my $reuse = sub { Net::SSLeay::set_session($client->_ssl,$sess) };
+is( _handshake($client,$server,$reuse),'reuse',"handshake with reuse");
+is( _handshake($client,$server,$reuse),'reuse',"handshake again with reuse");
+
+# create another server and connect client with session from old server
+# should not be reused
+# ----------------------------------------------
+my $server2 = _minSSL->new( cert => [
+ File::Spec->catfile('t','data','cert.pem'),
+ File::Spec->catfile('t','data','key.pem')
+]);
+is( _handshake($client,$server2,$reuse),'full',"handshake with server2 is full");
+
+# now attach the same ticket key callback to both servers
+# ----------------------------------------------
+Net::SSLeay::RAND_bytes(my $key,32);
+my $key_name = pack("a16",'secret');
+my $keycb = sub {
+ my ($mykey,$name) = @_;
+ return ($mykey,$key_name) if ! $name or $key_name eq $name;
+ return; # unknown key
+};
+Net::SSLeay::CTX_set_tlsext_ticket_getkey_cb($server->_ctx, $keycb,$key);
+Net::SSLeay::CTX_set_tlsext_ticket_getkey_cb($server2->_ctx,$keycb,$key);
+is( _handshake($client,$server),'full',"initial full handshake with server1");
+$sess = Net::SSLeay::get1_session($client->_ssl);
+is( _handshake($client,$server,$reuse), 'reuse',"reuse session with server1");
+is( _handshake($client,$server2,$reuse),'reuse',"reuse session with server2");
+
+# simulate rotation for $key: the callback returns now the right key, but
+# has a different current_name. It is expected that the callback is called again
+# for encryption with the new key and that a new session ticket gets sent to
+# the client
+# ----------------------------------------------
+Net::SSLeay::RAND_bytes(my $newkey,32);
+my $newkey_name = pack("a16",'newsecret');
+my @keys = (
+ [ $newkey_name, $newkey ], # current default key
+ [ $key_name, $key ], # already expired
+);
+my @was_called_with;
+my %old_transfer = %TRANSFER;
+Net::SSLeay::CTX_set_tlsext_ticket_getkey_cb($server2->_ctx, sub {
+ my (undef,$name) = @_;
+ push @was_called_with,$name || '<undef>';
+ return ($keys[0][1],$keys[0][0]) if ! $name;
+ for(my $i = 0; $i<@keys; $i++) {
+ return ($keys[$i][1],$keys[0][0]) if $name eq $keys[$i][0];
+ }
+ return;
+});
+
+my $expect_reuse = _handshake($client,$server2,$reuse);
+if ($expect_reuse eq '> < > <') {
+ # broken handshake seen with openssl 1.0.0 when a ticket was used where
+ # the key is still known but expired. It will do
+ # Encrypted Handshake Message, Change Cipher Spec, Encrypted Handshake Message
+ # in the last packet from server to client
+ is($expect_reuse,'> < > <',"(slightly broken) reuse session with old key with server2");
+ ok( @was_called_with >= 2,'callback was called at least 2 times');
+} else {
+ is($expect_reuse,'reuse',"reuse session with old key with server2");
+ is( 0+ at was_called_with,2,'callback was called 2 times');
+}
+
+is( $was_called_with[0],$key_name, 'first with the old key name');
+is( $was_called_with[1],"<undef>", 'then with undef to get the current key');
+ok( $TRANSFER{client} == $old_transfer{client}, 'no more data from client to server');
+ok( $TRANSFER{server} > $old_transfer{server}, 'but more data from server (new ticket)');
+
+# finally try to reuse the session created with new key against server1
+# this should result in a full handshake since server1 does not know newkey
+# ----------------------------------------------
+$sess = Net::SSLeay::get1_session($client->_ssl);
+is( _handshake($client,$server,$reuse),'full',"full handshake with new ticker on server1");
+
+
+
+my $i;
+sub _handshake {
+ my ($client,$server,$after_init) = @_;
+ $client->state_connect;
+ $server->state_accept;
+ &$after_init if $after_init;
+
+ my $pcap = $PCAP && do {
+ my $fname = 'test'.(++$i).'.pcap';
+ open(my $fh,'>',$fname);
+ diag("pcap in $fname");
+ $fh->autoflush;
+ Net::PcapWriter->new($fh)->tcp_conn('1.1.1.1',1000,'2.2.2.2',443);
+ };
+
+ my ($client_done,$server_done, at hs);
+ %TRANSFER = ();
+ for(my $tries = 0; $tries < 10 and !$client_done || !$server_done; $tries++ ) {
+ $client_done ||= $client->handshake || 0;
+ $server_done ||= $server->handshake || 0;
+
+ my $transfer = 0;
+ if (defined(my $data = $client->bio_read())) {
+ $pcap && $pcap->write(0,$data);
+ $DEBUG && warn "client -> server: ".length($data)." bytes\n";
+ $server->bio_write($data);
+ push @hs,'>';
+ $TRANSFER{client} += length($data);
+ $transfer++;
+ }
+ if (defined(my $data = $server->bio_read())) {
+ $pcap && $pcap->write(1,$data);
+ $DEBUG && warn "server -> client: ".length($data)." bytes\n";
+ $client->bio_write($data);
+ # assume certificate was sent if length>700
+ push @hs, length($data) > 700 ? '<[C]':'<';
+ $TRANSFER{server} += length($data);
+ $transfer++;
+ }
+ if (!$transfer) {
+ # no more data to transfer - assume we are done
+ $client_done = $server_done = 1;
+ }
+ }
+
+ return
+ !$client_done || !$server_done ? 'failed' :
+ "@hs" eq '> <[C] > <' ? 'full' :
+ "@hs" eq '> < >' ? 'reuse' :
+ "@hs";
+}
+
+
+{
+ package _minSSL;
+ sub new {
+ my ($class,%args) = @_;
+ my $ctx = Net::SSLeay::CTX_tlsv1_new();
+ Net::SSLeay::CTX_set_options($ctx,Net::SSLeay::OP_ALL());
+ Net::SSLeay::CTX_set_cipher_list($ctx,'AES128-SHA');
+ my $id = 'client';
+ if ($args{cert}) {
+ my ($cert,$key) = @{ delete $args{cert} };
+ Net::SSLeay::set_cert_and_key($ctx, $cert, $key)
+ || die "failed to use cert file $cert,$key";
+ $id = 'server';
+ }
+
+ my $self = bless { id => $id, ctx => $ctx }, $class;
+ return $self;
+ }
+
+ sub state_accept {
+ my $self = shift;
+ _reset($self);
+ Net::SSLeay::set_accept_state($self->{ssl});
+ }
+
+ sub state_connect {
+ my $self = shift;
+ _reset($self);
+ Net::SSLeay::set_connect_state($self->{ssl});
+ }
+
+ sub handshake {
+ my $self = shift;
+ my $rv = Net::SSLeay::do_handshake($self->{ssl});
+ $rv = _error($self,$rv);
+ return $rv;
+ }
+
+ sub ssl_read {
+ my ($self) = @_;
+ my ($data,$rv) = Net::SSLeay::read($self->{ssl});
+ return _error($self,$rv || -1) if !$rv || $rv<0;
+ return $data;
+ }
+
+ sub bio_write {
+ my ($self,$data) = @_;
+ defined $data and $data ne '' or return;
+ Net::SSLeay::BIO_write($self->{rbio},$data);
+ }
+
+ sub ssl_write {
+ my ($self,$data) = @_;
+ my $rv = Net::SSLeay::write($self->{ssl},$data);
+ return _error($self,$rv || -1) if !$rv || $rv<0;
+ return $rv;
+ }
+
+ sub bio_read {
+ my ($self) = @_;
+ return Net::SSLeay::BIO_read($self->{wbio});
+ }
+
+ sub _ssl { shift->{ssl} }
+ sub _ctx { shift->{ctx} }
+
+ sub _reset {
+ my $self = shift;
+ my $ssl = Net::SSLeay::new($self->{ctx});
+ my @bio = (
+ Net::SSLeay::BIO_new(Net::SSLeay::BIO_s_mem()),
+ Net::SSLeay::BIO_new(Net::SSLeay::BIO_s_mem()),
+ );
+ Net::SSLeay::set_bio($ssl,$bio[0],$bio[1]);
+ $self->{ssl} = $ssl;
+ $self->{rbio} = $bio[0];
+ $self->{wbio} = $bio[1];
+ }
+
+ sub _error {
+ my ($self,$rv) = @_;
+ if ($rv>0) {
+ $SSL_ERROR = undef;
+ return $rv;
+ }
+ my $err = Net::SSLeay::get_error($self->{ssl},$rv);
+ if ($err == Net::SSLeay::ERROR_WANT_READ()
+ || $err == Net::SSLeay::ERROR_WANT_WRITE()) {
+ $SSL_ERROR = $err;
+ $DEBUG && warn "[$self->{id}] rw:$err\n";
+ return;
+ }
+ $DEBUG && warn "[$self->{id}] ".Net::SSLeay::ERR_error_string($err)."\n";
+ return;
+ }
+
+}
--
Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/pkg-perl/packages/libnet-ssleay-perl.git
More information about the Pkg-perl-cvs-commits
mailing list