14 #define numberof(ary) (int)(sizeof(ary)/sizeof((ary)[0]))    17 #  define TO_SOCKET(s) _get_osfhandle(s)    19 #  define TO_SOCKET(s) (s)    22 #define GetSSLCTX(obj, ctx) do { \    23         TypedData_Get_Struct((obj), SSL_CTX, &ossl_sslctx_type, (ctx)); \    27 static VALUE mSSLExtConfig;
    28 static VALUE eSSLError;
    32 static VALUE eSSLErrorWaitReadable;
    33 static VALUE eSSLErrorWaitWritable;
    35 static ID ID_callback_state, id_tmp_dh_callback, id_tmp_ecdh_callback,
    36           id_npn_protocols_encoded;
    37 static VALUE sym_exception, sym_wait_readable, sym_wait_writable;
    39 static ID id_i_cert_store, id_i_ca_file, id_i_ca_path, id_i_verify_mode,
    40           id_i_verify_depth, id_i_verify_callback, id_i_client_ca,
    41           id_i_renegotiation_cb, id_i_cert, id_i_key, id_i_extra_chain_cert,
    42           id_i_client_cert_cb, id_i_tmp_ecdh_callback, id_i_timeout,
    43           id_i_session_id_context, id_i_session_get_cb, id_i_session_new_cb,
    44           id_i_session_remove_cb, id_i_npn_select_cb, id_i_npn_protocols,
    45           id_i_alpn_select_cb, id_i_alpn_protocols, id_i_servername_cb,
    47 static ID id_i_io, id_i_context, id_i_hostname;
    49 static int ossl_ssl_ex_vcb_idx;
    50 static int ossl_ssl_ex_ptr_idx;
    51 static int ossl_sslctx_ex_ptr_idx;
    52 #if !defined(HAVE_X509_STORE_UP_REF)    53 static int ossl_sslctx_ex_store_p;
    57 ossl_sslctx_free(
void *ptr)
    60 #if !defined(HAVE_X509_STORE_UP_REF)    61     if (ctx && SSL_CTX_get_ex_data(ctx, ossl_sslctx_ex_store_p))
    62         ctx->cert_store = 
NULL;
    76 ossl_sslctx_s_alloc(
VALUE klass)
    80         SSL_MODE_ENABLE_PARTIAL_WRITE |
    81         SSL_MODE_ACCEPT_MOVING_WRITE_BUFFER |
    82         SSL_MODE_RELEASE_BUFFERS;
    86 #if OPENSSL_VERSION_NUMBER >= 0x10100000 && !defined(LIBRESSL_VERSION_NUMBER)    87     ctx = SSL_CTX_new(TLS_method());
    89     ctx = SSL_CTX_new(SSLv23_method());
    94     SSL_CTX_set_mode(ctx, mode);
    96     SSL_CTX_set_ex_data(ctx, ossl_sslctx_ex_ptr_idx, (
void *)obj);
    98 #if !defined(OPENSSL_NO_EC) && defined(HAVE_SSL_CTX_SET_ECDH_AUTO)   106     if (!SSL_CTX_set_ecdh_auto(ctx, 1))
   107         ossl_raise(eSSLError, 
"SSL_CTX_set_ecdh_auto");
   114 parse_proto_version(
VALUE str)
   117     static const struct {
   121         { 
"SSL2", SSL2_VERSION },
   122         { 
"SSL3", SSL3_VERSION },
   123         { 
"TLS1", TLS1_VERSION },
   124         { 
"TLS1_1", TLS1_1_VERSION },
   125         { 
"TLS1_2", TLS1_2_VERSION },
   126 #ifdef TLS1_3_VERSION   127         { 
"TLS1_3", TLS1_3_VERSION },
   141             return map[i].version;
   153 ossl_sslctx_set_minmax_proto_version(
VALUE self, 
VALUE min_v, 
VALUE max_v)
   159     min = parse_proto_version(min_v);
   160     max = parse_proto_version(max_v);
   162 #ifdef HAVE_SSL_CTX_SET_MIN_PROTO_VERSION   163     if (!SSL_CTX_set_min_proto_version(ctx, min))
   164         ossl_raise(eSSLError, 
"SSL_CTX_set_min_proto_version");
   165     if (!SSL_CTX_set_max_proto_version(ctx, max))
   166         ossl_raise(eSSLError, 
"SSL_CTX_set_max_proto_version");
   169         unsigned long sum = 0, opts = 0;
   171         static const struct {
   175             { SSL2_VERSION, SSL_OP_NO_SSLv2 },
   176             { SSL3_VERSION, SSL_OP_NO_SSLv3 },
   177             { TLS1_VERSION, SSL_OP_NO_TLSv1 },
   178             { TLS1_1_VERSION, SSL_OP_NO_TLSv1_1 },
   179             { TLS1_2_VERSION, SSL_OP_NO_TLSv1_2 },
   180 # if defined(TLS1_3_VERSION)   181             { TLS1_3_VERSION, SSL_OP_NO_TLSv1_3 },
   185         for (i = 0; i < 
numberof(options_map); i++) {
   186             sum |= options_map[i].opts;
   187             if (min && min > options_map[i].ver || max && max < options_map[i].ver)
   188                 opts |= options_map[i].opts;
   190         SSL_CTX_clear_options(ctx, sum);
   191         SSL_CTX_set_options(ctx, opts);
   199 ossl_call_client_cert_cb(
VALUE obj)
   217 ossl_client_cert_cb(SSL *ssl, X509 **x509, EVP_PKEY **pkey)
   221     obj = (
VALUE)SSL_get_ex_data(ssl, ossl_ssl_ex_ptr_idx);
   232 #if !defined(OPENSSL_NO_DH) || \   233     !defined(OPENSSL_NO_EC) && defined(HAVE_SSL_CTX_SET_TMP_ECDH_CALLBACK)   254     if (EVP_PKEY_base_id(pkey) != args->
type)
   261 #if !defined(OPENSSL_NO_DH)   263 ossl_tmp_dh_callback(SSL *ssl, 
int is_export, 
int keylength)
   270     rb_ssl = (
VALUE)SSL_get_ex_data(ssl, ossl_ssl_ex_ptr_idx);
   272     args.
id = id_tmp_dh_callback;
   275     args.
type = EVP_PKEY_DH;
   278                                   (
VALUE)&args, &state);
   286     return EVP_PKEY_get0_DH(pkey);
   290 #if !defined(OPENSSL_NO_EC) && defined(HAVE_SSL_CTX_SET_TMP_ECDH_CALLBACK)   299     rb_ssl = (
VALUE)SSL_get_ex_data(ssl, ossl_ssl_ex_ptr_idx);
   301     args.
id = id_tmp_ecdh_callback;
   304     args.
type = EVP_PKEY_EC;
   307                                   (
VALUE)&args, &state);
   315     return EVP_PKEY_get0_EC_KEY(pkey);
   320 call_verify_certificate_identity(
VALUE ctx_v)
   322     X509_STORE_CTX *ctx = (X509_STORE_CTX *)ctx_v;
   326     ssl = X509_STORE_CTX_get_ex_data(ctx, SSL_get_ex_data_X509_STORE_CTX_idx());
   327     ssl_obj = (
VALUE)SSL_get_ex_data(ssl, ossl_ssl_ex_ptr_idx);
   330     if (!
RTEST(hostname)) {
   331         rb_warning(
"verify_hostname requires hostname to be set");
   335     cert_obj = 
ossl_x509_new(X509_STORE_CTX_get_current_cert(ctx));
   341 ossl_ssl_verify_callback(
int preverify_ok, X509_STORE_CTX *ctx)
   347     ssl = X509_STORE_CTX_get_ex_data(ctx, SSL_get_ex_data_X509_STORE_CTX_idx());
   348     cb = (
VALUE)SSL_get_ex_data(ssl, ossl_ssl_ex_vcb_idx);
   349     ssl_obj = (
VALUE)SSL_get_ex_data(ssl, ossl_ssl_ex_ptr_idx);
   351     verify_hostname = 
rb_attr_get(sslctx_obj, id_i_verify_hostname);
   354         !X509_STORE_CTX_get_error_depth(ctx)) {
   355         ret = 
rb_protect(call_verify_certificate_identity, (
VALUE)ctx, &status);
   360         preverify_ok = ret == 
Qtrue;
   367 ossl_call_session_get_cb(
VALUE ary)
   382 #if OPENSSL_VERSION_NUMBER >= 0x10100000L && !defined(LIBRESSL_VERSION_NUMBER)   383 ossl_sslctx_session_get_cb(SSL *ssl, 
const unsigned char *
buf, 
int len, 
int *copy)
   385 ossl_sslctx_session_get_cb(SSL *ssl, 
unsigned char *
buf, 
int len, 
int *copy)
   392     OSSL_Debug(
"SSL SESSION get callback entered");
   393     ssl_obj = (
VALUE)SSL_get_ex_data(ssl, ossl_ssl_ex_ptr_idx);
   398     ret_obj = 
rb_protect(ossl_call_session_get_cb, ary, &state);
   413 ossl_call_session_new_cb(
VALUE ary)
   428 ossl_sslctx_session_new_cb(SSL *ssl, SSL_SESSION *sess)
   433     OSSL_Debug(
"SSL SESSION new callback entered");
   435     ssl_obj = (
VALUE)SSL_get_ex_data(ssl, ossl_ssl_ex_ptr_idx);
   444     rb_protect(ossl_call_session_new_cb, ary, &state);
   460 ossl_call_session_remove_cb(
VALUE ary)
   467     cb = 
rb_attr_get(sslctx_obj, id_i_session_remove_cb);
   474 ossl_sslctx_session_remove_cb(SSL_CTX *ctx, SSL_SESSION *sess)
   476     VALUE ary, sslctx_obj, sess_obj;
   486     OSSL_Debug(
"SSL SESSION remove callback entered");
   488     sslctx_obj = (
VALUE)SSL_CTX_get_ex_data(ctx, ossl_sslctx_ex_ptr_idx);
   497     rb_protect(ossl_call_session_remove_cb, ary, &state);
   515     if(!SSL_CTX_add_extra_chain_cert(ctx, x509)){
   525 ossl_call_servername_cb(
VALUE ary)
   541         ossl_sslctx_setup(ret_obj);
   544         SSL_set_SSL_CTX(ssl, ctx2);
   546     } 
else if (!
NIL_P(ret_obj)) {
   548                    "OpenSSL::SSL::SSLContext object or nil");
   555 ssl_servername_cb(SSL *ssl, 
int *ad, 
void *arg)
   559     const char *servername = SSL_get_servername(ssl, TLSEXT_NAMETYPE_host_name);
   562         return SSL_TLSEXT_ERR_OK;
   564     ssl_obj = (
VALUE)SSL_get_ex_data(ssl, ossl_ssl_ex_ptr_idx);
   569     rb_protect(ossl_call_servername_cb, ary, &state);
   572         return SSL_TLSEXT_ERR_ALERT_FATAL;
   575     return SSL_TLSEXT_ERR_OK;
   579 ssl_renegotiation_cb(
const SSL *ssl)
   583     ssl_obj = (
VALUE)SSL_get_ex_data(ssl, ossl_ssl_ex_ptr_idx);
   585     cb = 
rb_attr_get(sslctx_obj, id_i_renegotiation_cb);
   586     if (
NIL_P(cb)) 
return;
   591 #if !defined(OPENSSL_NO_NEXTPROTONEG) || \   592     defined(HAVE_SSL_CTX_SET_ALPN_SELECT_CB)   594 ssl_npn_encode_protocol_i(
VALUE cur, 
VALUE encoded)
   598     if (len < 1 || len > 255)
   599         ossl_raise(eSSLError, 
"Advertised protocol must have length 1..255");
   608 ssl_encode_npn_protocols(
VALUE protocols)
   617     const unsigned char *
in;
   622 npn_select_cb_common_i(
VALUE tmp)
   625     const unsigned char *
in = args->
in, *in_end = in + args->
inlen;
   632     while (in < in_end) {
   641     if (len < 1 || len >= 256) {
   642         ossl_raise(eSSLError, 
"Selected protocol name must have length 1..255");
   649 ssl_npn_select_cb_common(SSL *ssl, 
VALUE cb, 
const unsigned char **out,
   650                          unsigned char *outlen, 
const unsigned char *
in,
   663         VALUE ssl_obj = (
VALUE)SSL_get_ex_data(ssl, ossl_ssl_ex_ptr_idx);
   666         return SSL_TLSEXT_ERR_ALERT_FATAL;
   672     return SSL_TLSEXT_ERR_OK;
   676 #ifndef OPENSSL_NO_NEXTPROTONEG   678 ssl_npn_advertise_cb(SSL *ssl, 
const unsigned char **out, 
unsigned int *outlen,
   683     *out = (
const unsigned char *) 
RSTRING_PTR(protocols);
   686     return SSL_TLSEXT_ERR_OK;
   690 ssl_npn_select_cb(SSL *ssl, 
unsigned char **out, 
unsigned char *outlen,
   691                   const unsigned char *
in, 
unsigned int inlen, 
void *arg)
   695     sslctx_obj = (
VALUE) arg;
   698     return ssl_npn_select_cb_common(ssl, cb, (
const unsigned char **)out,
   703 #ifdef HAVE_SSL_CTX_SET_ALPN_SELECT_CB   705 ssl_alpn_select_cb(SSL *ssl, 
const unsigned char **out, 
unsigned char *outlen,
   706                    const unsigned char *
in, 
unsigned int inlen, 
void *arg)
   710     sslctx_obj = (
VALUE) arg;
   713     return ssl_npn_select_cb_common(ssl, cb, out, outlen, 
in, 
inlen);
   719 ssl_info_cb(
const SSL *ssl, 
int where, 
int val)
   723     if (is_server && where & SSL_CB_HANDSHAKE_START) {
   724         ssl_renegotiation_cb(ssl);
   732 ossl_sslctx_get_options(
VALUE self)
   740     return ULONG2NUM((
unsigned long)SSL_CTX_get_options(ctx));
   747 ossl_sslctx_set_options(
VALUE self, 
VALUE options)
   754     SSL_CTX_clear_options(ctx, SSL_CTX_get_options(ctx));
   756     if (
NIL_P(options)) {
   757         SSL_CTX_set_options(ctx, SSL_OP_ALL);
   759         SSL_CTX_set_options(ctx, 
NUM2ULONG(options));
   775 ossl_sslctx_setup(
VALUE self)
   778     X509 *cert = 
NULL, *client_ca = 
NULL;
   780     char *ca_path = 
NULL, *ca_file = 
NULL;
   788 #if !defined(OPENSSL_NO_DH)   789     SSL_CTX_set_tmp_dh_callback(ctx, ossl_tmp_dh_callback);
   792 #if !defined(OPENSSL_NO_EC)   796 # if defined(HAVE_SSL_CTX_SET_TMP_ECDH_CALLBACK)   797         rb_warn(
"#tmp_ecdh_callback= is deprecated; use #ecdh_curves= instead");
   798         SSL_CTX_set_tmp_ecdh_callback(ctx, ossl_tmp_ecdh_callback);
   799 #  if defined(HAVE_SSL_CTX_SET_ECDH_AUTO)   802         if (!SSL_CTX_set_ecdh_auto(ctx, 0))
   803             ossl_raise(eSSLError, 
"SSL_CTX_set_ecdh_auto");
   806         ossl_raise(eSSLError, 
"OpenSSL does not support tmp_ecdh_callback; "   807                    "use #ecdh_curves= instead");
   815         SSL_CTX_set_cert_store(ctx, store);
   816 #if !defined(HAVE_X509_STORE_UP_REF)   823         SSL_CTX_set_ex_data(ctx, ossl_sslctx_ex_store_p, ctx);
   840         if (!SSL_CTX_use_certificate(ctx, cert)) {
   842             ossl_raise(eSSLError, 
"SSL_CTX_use_certificate");
   844         if (!SSL_CTX_use_PrivateKey(ctx, key)) {
   846             ossl_raise(eSSLError, 
"SSL_CTX_use_PrivateKey");
   848         if (!SSL_CTX_check_private_key(ctx)) {
   849             ossl_raise(eSSLError, 
"SSL_CTX_check_private_key");
   858                 if (!SSL_CTX_add_client_CA(ctx, client_ca)){
   860                     ossl_raise(eSSLError, 
"SSL_CTX_add_client_CA");
   866             if (!SSL_CTX_add_client_CA(ctx, client_ca)){
   868                 ossl_raise(eSSLError, 
"SSL_CTX_add_client_CA");
   877     if(ca_file || ca_path){
   878         if (!SSL_CTX_load_verify_locations(ctx, ca_file, ca_path))
   883     verify_mode = 
NIL_P(val) ? SSL_VERIFY_NONE : 
NUM2INT(val);
   884     SSL_CTX_set_verify(ctx, verify_mode, ossl_ssl_verify_callback);
   886         SSL_CTX_set_client_cert_cb(ctx, ossl_client_cert_cb);
   892     if(!
NIL_P(val)) SSL_CTX_set_verify_depth(ctx, 
NUM2INT(val));
   894 #ifndef OPENSSL_NO_NEXTPROTONEG   897         VALUE encoded = ssl_encode_npn_protocols(val);
   898         rb_ivar_set(
self, id_npn_protocols_encoded, encoded);
   899         SSL_CTX_set_next_protos_advertised_cb(ctx, ssl_npn_advertise_cb, (
void *)encoded);
   900         OSSL_Debug(
"SSL NPN advertise callback added");
   903         SSL_CTX_set_next_proto_select_cb(ctx, ssl_npn_select_cb, (
void *) 
self);
   908 #ifdef HAVE_SSL_CTX_SET_ALPN_SELECT_CB   911         VALUE rprotos = ssl_encode_npn_protocols(val);
   914         if (SSL_CTX_set_alpn_protos(ctx, (
unsigned char *)
RSTRING_PTR(rprotos),
   916             ossl_raise(eSSLError, 
"SSL_CTX_set_alpn_protos");
   920         SSL_CTX_set_alpn_select_cb(ctx, ssl_alpn_select_cb, (
void *) 
self);
   930         if (!SSL_CTX_set_session_id_context(ctx, (
unsigned char *)
RSTRING_PTR(val),
   932             ossl_raise(eSSLError, 
"SSL_CTX_set_session_id_context");
   937         SSL_CTX_sess_set_get_cb(ctx, ossl_sslctx_session_get_cb);
   941         SSL_CTX_sess_set_new_cb(ctx, ossl_sslctx_session_new_cb);
   945         SSL_CTX_sess_set_remove_cb(ctx, ossl_sslctx_session_remove_cb);
   946         OSSL_Debug(
"SSL SESSION remove callback added");
   951         SSL_CTX_set_tlsext_servername_callback(ctx, ssl_servername_cb);
   952         OSSL_Debug(
"SSL TLSEXT servername callback added");
   959 ossl_ssl_cipher_to_ary(
const SSL_CIPHER *cipher)
   967     bits = SSL_CIPHER_get_bits(cipher, &alg_bits);
   981 ossl_sslctx_get_ciphers(
VALUE self)
   985     const SSL_CIPHER *cipher;
   994     num = sk_SSL_CIPHER_num(ciphers);
   996     for(i = 0; i < num; i++){
   997         cipher = sk_SSL_CIPHER_value(ciphers, i);
  1039         ossl_raise(eSSLError, 
"SSL_CTX is not initialized.");
  1043         ossl_raise(eSSLError, 
"SSL_CTX_set_cipher_list");
  1049 #if !defined(OPENSSL_NO_EC)  1078 ossl_sslctx_set_ecdh_curves(
VALUE self, 
VALUE arg)
  1086 #if defined(HAVE_SSL_CTX_SET1_CURVES_LIST)  1087     if (!SSL_CTX_set1_curves_list(ctx, 
RSTRING_PTR(arg)))
  1093         VALUE curve, splitted;
  1099             ossl_raise(eSSLError, 
"invalid input format");
  1105         if (nid == NID_undef)
  1107         if (nid == NID_undef)
  1110         ec = EC_KEY_new_by_curve_name(nid);
  1113         EC_KEY_set_asn1_flag(ec, OPENSSL_EC_NAMED_CURVE);
  1114         if (!SSL_CTX_set_tmp_ecdh(ctx, ec)) {
  1116             ossl_raise(eSSLError, 
"SSL_CTX_set_tmp_ecdh");
  1119 # if defined(HAVE_SSL_CTX_SET_ECDH_AUTO)  1122         if (!SSL_CTX_set_ecdh_auto(ctx, 0))
  1123             ossl_raise(eSSLError, 
"SSL_CTX_set_ecdh_auto");
  1131 #define ossl_sslctx_set_ecdh_curves rb_f_notimplement  1143 ossl_sslctx_get_security_level(
VALUE self)
  1149 #if defined(HAVE_SSL_CTX_GET_SECURITY_LEVEL)  1150     return INT2NUM(SSL_CTX_get_security_level(ctx));
  1177 ossl_sslctx_set_security_level(
VALUE self, 
VALUE value)
  1184 #if defined(HAVE_SSL_CTX_GET_SECURITY_LEVEL)  1185     SSL_CTX_set_security_level(ctx, 
NUM2INT(value));
  1190                    "not supported in this version of OpenSSL");
  1203 ossl_sslctx_session_add(
VALUE self, 
VALUE arg)
  1211     return SSL_CTX_add_session(ctx, sess) == 1 ? 
Qtrue : 
Qfalse;
  1221 ossl_sslctx_session_remove(
VALUE self, 
VALUE arg)
  1229     return SSL_CTX_remove_session(ctx, sess) == 1 ? 
Qtrue : 
Qfalse;
  1239 ossl_sslctx_get_session_cache_mode(
VALUE self)
  1245     return LONG2NUM(SSL_CTX_get_session_cache_mode(ctx));
  1257 ossl_sslctx_set_session_cache_mode(
VALUE self, 
VALUE arg)
  1263     SSL_CTX_set_session_cache_mode(ctx, 
NUM2LONG(arg));
  1276 ossl_sslctx_get_session_cache_size(
VALUE self)
  1282     return LONG2NUM(SSL_CTX_sess_get_cache_size(ctx));
  1293 ossl_sslctx_set_session_cache_size(
VALUE self, 
VALUE arg)
  1299     SSL_CTX_sess_set_cache_size(ctx, 
NUM2LONG(arg));
  1327 ossl_sslctx_get_session_cache_stats(
VALUE self)
  1377     SSL_CTX_flush_sessions(ctx, (
long)tm);
  1385 #ifndef OPENSSL_NO_SOCK  1387 ssl_started(SSL *ssl)
  1390     return SSL_get_fd(ssl) >= 0;
  1394 ossl_ssl_free(
void *ssl)
  1408 ossl_ssl_s_alloc(
VALUE klass)
  1432     VALUE io, v_ctx, verify_cb;
  1438         ossl_raise(eSSLError, 
"SSL already initialized");
  1445     ossl_sslctx_setup(v_ctx);
  1456     SSL_set_ex_data(ssl, ossl_ssl_ex_ptr_idx, (
void *)
self);
  1457     SSL_set_info_callback(ssl, ssl_info_cb);
  1458     verify_cb = 
rb_attr_get(v_ctx, id_i_verify_callback);
  1459     SSL_set_ex_data(ssl, ossl_ssl_ex_vcb_idx, (
void *)verify_cb);
  1467 ossl_ssl_setup(
VALUE self)
  1474     if (ssl_started(ssl))
  1488 #define ssl_get_error(ssl, ret) (errno = rb_w32_map_errno(WSAGetLastError()), SSL_get_error((ssl), (ret)))  1490 #define ssl_get_error(ssl, ret) SSL_get_error((ssl), (ret))  1494 write_would_block(
int nonblock)
  1497         ossl_raise(eSSLErrorWaitWritable, 
"write would block");
  1501 read_would_block(
int nonblock)
  1504         ossl_raise(eSSLErrorWaitReadable, 
"read would block");
  1508 no_exception_p(
VALUE opts)
  1517 ossl_start_ssl(
VALUE self, 
int (*func)(), 
const char *funcname, 
VALUE opts)
  1523     int nonblock = opts != 
Qfalse;
  1524 #if defined(SSL_R_CERTIFICATE_VERIFY_FAILED)  1537         if (!
NIL_P(cb_state)) {
  1547         case SSL_ERROR_WANT_WRITE:
  1548             if (no_exception_p(opts)) { 
return sym_wait_writable; }
  1549             write_would_block(nonblock);
  1552         case SSL_ERROR_WANT_READ:
  1553             if (no_exception_p(opts)) { 
return sym_wait_readable; }
  1554             read_would_block(nonblock);
  1557         case SSL_ERROR_SYSCALL:
  1559             ossl_raise(eSSLError, 
"%s SYSCALL returned=%d errno=%d state=%s", funcname, ret2, 
errno, SSL_state_string_long(ssl));
  1560 #if defined(SSL_R_CERTIFICATE_VERIFY_FAILED)  1562             err = ERR_peek_last_error();
  1563             if (ERR_GET_LIB(err) == ERR_LIB_SSL &&
  1564                 ERR_GET_REASON(err) == SSL_R_CERTIFICATE_VERIFY_FAILED) {
  1565                 const char *err_msg = ERR_reason_error_string(err),
  1566                       *verify_msg = X509_verify_cert_error_string(SSL_get_verify_result(ssl));
  1570                     verify_msg = 
"(null)";
  1572                 ossl_raise(eSSLError, 
"%s returned=%d errno=%d state=%s: %s (%s)",
  1573                            funcname, ret2, 
errno, SSL_state_string_long(ssl),
  1574                            err_msg, verify_msg);
  1578             ossl_raise(eSSLError, 
"%s returned=%d errno=%d state=%s", funcname, ret2, 
errno, SSL_state_string_long(ssl));
  1593 ossl_ssl_connect(
VALUE self)
  1595     ossl_ssl_setup(
self);
  1597     return ossl_start_ssl(
self, SSL_connect, 
"SSL_connect", 
Qfalse);
  1628     ossl_ssl_setup(
self);
  1630     return ossl_start_ssl(
self, SSL_connect, 
"SSL_connect", opts);
  1641 ossl_ssl_accept(
VALUE self)
  1643     ossl_ssl_setup(
self);
  1645     return ossl_start_ssl(
self, SSL_accept, 
"SSL_accept", 
Qfalse);
  1676     ossl_ssl_setup(
self);
  1678     return ossl_start_ssl(
self, SSL_accept, 
"SSL_accept", opts);
  1685     int ilen, nread = 0;
  1714     if (ssl_started(ssl)) {
  1718             case SSL_ERROR_NONE:
  1720             case SSL_ERROR_ZERO_RETURN:
  1721                 if (no_exception_p(opts)) { 
return Qnil; }
  1723             case SSL_ERROR_WANT_WRITE:
  1724                 if (no_exception_p(opts)) { 
return sym_wait_writable; }
  1725                 write_would_block(nonblock);
  1728             case SSL_ERROR_WANT_READ:
  1729                 if (no_exception_p(opts)) { 
return sym_wait_readable; }
  1730                 read_would_block(nonblock);
  1733             case SSL_ERROR_SYSCALL:
  1734                 if (!ERR_peek_error()) {
  1745                         if (no_exception_p(opts)) { 
return Qnil; }
  1757         rb_warning(
"SSL session is not started yet.");
  1759             return rb_funcall(io, meth, 3, len, str, opts);
  1780     return ossl_ssl_read_internal(
argc, 
argv, 
self, 0);
  1799     return ossl_ssl_read_internal(
argc, 
argv, 
self, 1);
  1808     int nonblock = opts != 
Qfalse;
  1815     if (ssl_started(ssl)) {
  1825             case SSL_ERROR_NONE:
  1827             case SSL_ERROR_WANT_WRITE:
  1828                 if (no_exception_p(opts)) { 
return sym_wait_writable; }
  1829                 write_would_block(nonblock);
  1832             case SSL_ERROR_WANT_READ:
  1833                 if (no_exception_p(opts)) { 
return sym_wait_readable; }
  1834                 read_would_block(nonblock);
  1837             case SSL_ERROR_SYSCALL:
  1845         ID meth = nonblock ?
  1848         rb_warning(
"SSL session is not started yet.");
  1868     return ossl_ssl_write_internal(
self, str, 
Qfalse);
  1885     return ossl_ssl_write_internal(
self, str, opts);
  1896 ossl_ssl_stop(
VALUE self)
  1902     if (!ssl_started(ssl))
  1904     ret = SSL_shutdown(ssl);
  1927 ossl_ssl_get_cert(
VALUE self)
  1938     cert = SSL_get_certificate(ssl); 
  1953 ossl_ssl_get_peer_cert(
VALUE self)
  1961     cert = SSL_get_peer_certificate(ssl); 
  1979 ossl_ssl_get_peer_cert_chain(
VALUE self)
  1989     chain = SSL_get_peer_cert_chain(ssl);
  1990     if(!chain) 
return Qnil;
  1991     num = sk_X509_num(chain);
  1993     for (i = 0; i < num; i++){
  1994         cert = sk_X509_value(chain, i);
  2009 ossl_ssl_get_version(
VALUE self)
  2026 ossl_ssl_get_cipher(
VALUE self)
  2029     const SSL_CIPHER *cipher;
  2032     cipher = SSL_get_current_cipher(ssl);
  2033     return cipher ? ossl_ssl_cipher_to_ary(cipher) : 
Qnil;
  2044 ossl_ssl_get_state(
VALUE self)
  2066 ossl_ssl_pending(
VALUE self)
  2072     return INT2NUM(SSL_pending(ssl));
  2082 ossl_ssl_session_reused(
VALUE self)
  2106     if (SSL_set_session(ssl, sess) != 1)
  2123     char *hostname = 
NULL;
  2130     if (!SSL_set_tlsext_host_name(ssl, hostname))
  2149 ossl_ssl_get_verify_result(
VALUE self)
  2155     return INT2NUM(SSL_get_verify_result(ssl));
  2170 ossl_ssl_get_client_ca_list(
VALUE self)
  2177     ca = SSL_get_client_CA_list(ssl);
  2181 # ifndef OPENSSL_NO_NEXTPROTONEG  2190 ossl_ssl_npn_protocol(
VALUE self)
  2193     const unsigned char *out;
  2194     unsigned int outlen;
  2198     SSL_get0_next_proto_negotiated(ssl, &out, &outlen);
  2202         return rb_str_new((
const char *) out, outlen);
  2206 # ifdef HAVE_SSL_CTX_SET_ALPN_SELECT_CB  2215 ossl_ssl_alpn_protocol(
VALUE self)
  2218     const unsigned char *out;
  2219     unsigned int outlen;
  2223     SSL_get0_alpn_selected(ssl, &out, &outlen);
  2227         return rb_str_new((
const char *) out, outlen);
  2231 # ifdef HAVE_SSL_GET_SERVER_TMP_KEY  2239 ossl_ssl_tmp_key(
VALUE self)
  2245     if (!SSL_get_server_tmp_key(ssl, &key))
  2253 #define rb_intern(s) rb_intern_const(s)  2264     ID_callback_state = 
rb_intern(
"callback_state");
  2266     ossl_ssl_ex_vcb_idx = SSL_get_ex_new_index(0, (
void *)
"ossl_ssl_ex_vcb_idx", 0, 0, 0);
  2267     if (ossl_ssl_ex_vcb_idx < 0)
  2269     ossl_ssl_ex_ptr_idx = SSL_get_ex_new_index(0, (
void *)
"ossl_ssl_ex_ptr_idx", 0, 0, 0);
  2270     if (ossl_ssl_ex_ptr_idx < 0)
  2272     ossl_sslctx_ex_ptr_idx = SSL_CTX_get_ex_new_index(0, (
void *)
"ossl_sslctx_ex_ptr_idx", 0, 0, 0);
  2273     if (ossl_sslctx_ex_ptr_idx < 0)
  2275 #if !defined(HAVE_X509_STORE_UP_REF)  2276     ossl_sslctx_ex_store_p = SSL_CTX_get_ex_new_index(0, (
void *)
"ossl_sslctx_ex_store_p", 0, 0, 0);
  2277     if (ossl_sslctx_ex_store_p < 0)
  2418 #if !defined(OPENSSL_NO_EC) && defined(HAVE_SSL_CTX_SET_TMP_ECDH_CALLBACK)  2491 #ifndef OPENSSL_NO_NEXTPROTONEG  2523 #ifdef HAVE_SSL_CTX_SET_ALPN_SELECT_CB  2558                              ossl_sslctx_set_minmax_proto_version, 2);
  2630 #ifdef OPENSSL_NO_SOCK  2661 # ifdef HAVE_SSL_GET_SERVER_TMP_KEY  2664 # ifdef HAVE_SSL_CTX_SET_ALPN_SELECT_CB  2667 # ifndef OPENSSL_NO_NEXTPROTONEG  2679 #ifdef SSL_OP_TLSEXT_PADDING   2682 #ifdef SSL_OP_SAFARI_ECDHE_ECDSA_BUG   2685 #ifdef SSL_OP_ALLOW_NO_DHE_KEX   2693 #ifdef SSL_OP_NO_ENCRYPT_THEN_MAC   2698 #ifdef SSL_OP_NO_RENEGOTIATION   2707 #ifdef SSL_OP_NO_TLSv1_3   2768 #ifdef TLS1_3_VERSION   2778     id_tmp_dh_callback = 
rb_intern(
"tmp_dh_callback");
  2779     id_tmp_ecdh_callback = 
rb_intern(
"tmp_ecdh_callback");
  2780     id_npn_protocols_encoded = 
rb_intern(
"npn_protocols_encoded");
  2782 #define DefIVarID(name) do \  2783     id_i_##name = rb_intern("@"#name); while (0) 
VALUE rb_protect(VALUE(*proc)(VALUE), VALUE data, int *pstate)
Protects a function call from potential global escapes from the function. 
 
void rb_warn(const char *fmt,...)
 
VALUE rb_ary_entry(VALUE ary, long offset)
 
#define RUBY_TYPED_FREE_IMMEDIATELY
 
#define ssl_get_error(ssl, ret)
 
void rb_io_check_readable(rb_io_t *)
 
const rb_data_type_t ossl_ssl_type
 
void rb_raise(VALUE exc, const char *fmt,...)
 
void rb_jump_tag(int tag)
Continues the exception caught by rb_protect() and rb_eval_string_protect(). 
 
EVP_PKEY * GetPrivPKeyPtr(VALUE obj)
 
#define TypedData_Wrap_Struct(klass, data_type, sval)
 
#define TypedData_Get_Struct(obj, type, data_type, sval)
 
void rb_define_private_method(VALUE klass, const char *name, VALUE(*func)(ANYARGS), int argc)
 
VALUE rb_iterate(VALUE(*)(VALUE), VALUE, VALUE(*)(ANYARGS), VALUE)
 
VALUE rb_ary_push(VALUE ary, VALUE item)
 
VALUE rb_String(VALUE)
Equivalent to Kernel#String in Ruby. 
 
VALUE rb_funcall(VALUE, ID, int,...)
Calls a method. 
 
VALUE ossl_x509name_sk2ary(const STACK_OF(X509_NAME) *names)
 
void rb_str_set_len(VALUE, long)
 
VALUE rb_define_class_under(VALUE outer, const char *name, VALUE super)
Defines a class under the namespace of outer. 
 
void rb_define_alloc_func(VALUE, rb_alloc_func_t)
 
VALUE rb_obj_alloc(VALUE)
Allocates an instance of klass. 
 
#define SSL_SESSION_up_ref(x)
 
void rb_include_module(VALUE klass, VALUE module)
 
VALUE rb_block_call(VALUE, ID, int, const VALUE *, rb_block_call_func_t, VALUE)
 
VALUE ossl_pkey_new(EVP_PKEY *pkey)
 
void rb_undef_method(VALUE klass, const char *name)
 
#define GetSSLCTX(obj, ctx)
 
VALUE rb_f_notimplement(int argc, const VALUE *argv, VALUE obj)
 
#define GetOpenFile(obj, fp)
 
VALUE rb_str_buf_cat(VALUE, const char *, long)
 
#define RB_BLOCK_CALL_FUNC_ARGLIST(yielded_arg, callback_arg)
 
void Init_ossl_ssl_session(void)
 
#define RB_TYPE_P(obj, type)
 
VALUE rb_obj_is_kind_of(VALUE, VALUE)
call-seq: obj.is_a?(class) -> true or false obj.kind_of?(class) -> true or false 
 
#define EC_curve_nist2nid
 
X509 * GetX509CertPtr(VALUE)
 
RUBY_EXTERN VALUE rb_mWaitReadable
 
void ossl_clear_error(void)
 
VALUE rb_hash_aset(VALUE hash, VALUE key, VALUE val)
 
RUBY_EXTERN VALUE rb_cObject
 
STACK_OF(X509) *ossl_x509_ary2sk(VALUE)
 
void rb_attr(VALUE, ID, int, int, int)
 
VALUE rb_str_cat2(VALUE, const char *)
 
void rb_define_const(VALUE, const char *, VALUE)
 
int rb_io_wait_writable(int)
 
VALUE ossl_x509_new(X509 *)
 
VALUE rb_obj_is_instance_of(VALUE, VALUE)
call-seq: obj.instance_of?(class) -> true or false 
 
VALUE rb_str_split(VALUE, const char *)
 
#define GetSSLSession(obj, sess)
 
void rb_sys_fail(const char *mesg)
 
void rb_define_alias(VALUE klass, const char *name1, const char *name2)
Defines an alias of a method. 
 
VALUE rb_obj_freeze(VALUE)
call-seq: obj.freeze -> obj 
 
RUBY_EXTERN VALUE rb_mWaitWritable
 
int rb_scan_args(int argc, const VALUE *argv, const char *fmt,...)
 
void rb_str_modify_expand(VALUE, long)
 
int ossl_verify_cb_call(VALUE, int, X509_STORE_CTX *)
 
VALUE rb_ivar_set(VALUE, ID, VALUE)
 
unsigned char buf[MIME_BUF_SIZE]
 
VALUE rb_call_super(int, const VALUE *)
 
X509_STORE * GetX509StorePtr(VALUE)
 
int rb_respond_to(VALUE, ID)
 
register unsigned int len
 
VALUE rb_define_module_under(VALUE outer, const char *name)
 
#define X509_STORE_up_ref(x)
 
#define StringValueCStr(v)
 
void rb_str_modify(VALUE)
 
VALUE rb_hash_lookup2(VALUE hash, VALUE key, VALUE def)
 
#define RARRAY_AREF(a, i)
 
void rb_warning(const char *fmt,...)
 
void ossl_raise(VALUE exc, const char *fmt,...)
 
EVP_PKEY * GetPKeyPtr(VALUE obj)
 
EVP_PKEY * DupPKeyPtr(VALUE obj)
 
X509 * DupX509CertPtr(VALUE)
 
void rb_io_check_writable(rb_io_t *)
 
#define SSL_CTX_get_ciphers(ctx)
 
#define RTYPEDDATA_DATA(v)
 
#define RSTRING_LENINT(str)
 
#define rb_check_frozen(obj)
 
VALUE rb_define_module(const char *name)
 
#define RB_INTEGER_TYPE_P(obj)
 
int rb_io_wait_readable(int)
 
RUBY_EXTERN VALUE rb_cTime
 
void rb_define_method(VALUE klass, const char *name, VALUE(*func)(ANYARGS), int argc)
 
VALUE rb_str_append(VALUE, VALUE)
 
VALUE rb_attr_get(VALUE, ID)
 
VALUE rb_str_new(const char *, long)