예제 #1
0
int ipfix_ssl_init_con( SSL *con )
{
    extern FILE *mlog_fp; // todo: see if this is working
    int i;
    char *str;
    long verify_error;
    char buf[100];

    if ((i=SSL_accept(con)) <= 0) {
        if (BIO_sock_should_retry(i)) {
            mlogf( 0, "[ipfix_ssl_init] DELAY\n");
            return -1;
        }

        mlogf( 0, "[ipfix_ssl_init] ERROR\n");
        verify_error=SSL_get_verify_result( con );
        if (verify_error != X509_V_OK) {
            mlogf( 0, "[ipfix_ssl_init] verify error: %s\n",
                   X509_verify_cert_error_string(verify_error));
        }
        else
            ERR_print_errors_fp( mlog_fp );

        return -1;
    }

    if ( 1 <= mlog_get_vlevel() ) {
        PEM_write_SSL_SESSION( mlog_fp, SSL_get_session(con));

        if ( SSL_get_shared_ciphers(con, buf, sizeof buf) != NULL) {
            mlogf( 3, "[ipfix] Shared ciphers:%s\n", buf);
        }
        str=(char*)SSL_CIPHER_get_name( SSL_get_current_cipher(con) );
        mlogf( 3,  "[ipfix] CIPHER is %s\n",(str != NULL)?str:"(NONE)");
        if (SSL_ctrl(con,SSL_CTRL_GET_FLAGS,0,NULL) &
            TLS1_FLAGS_TLS_PADDING_BUG) {
            mlogf( 1, "[ipfix] Peer has incorrect TLSv1 block padding\n");
        }
    }

    return 0;
}
예제 #2
0
파일: p_memory.c 프로젝트: gandaro/piebnc
void logsslstats(SSL *reference)
{
    char sglobal[1024];
    p_log(LOG_INFO,-1, lngtxt(613));
    if(reference==NULL)
        p_log(LOG_INFO,-1,lngtxt(614));
    else
    {
        if(SSL_get_shared_ciphers(reference,sglobal,1023)==NULL)
            strmncpy(sglobal,lngtxt(615),sizeof(sglobal));
        p_log(LOG_INFO,-1,lngtxt(616),sglobal);
    }
    p_log(LOG_INFO,-1, lngtxt(617),
          SSL_CTX_sess_number(srvctx)+SSL_CTX_sess_number(clnctx));
    p_log(LOG_INFO,-1, lngtxt(618),
          SSL_CTX_sess_connect(srvctx)+SSL_CTX_sess_connect(clnctx));
    p_log(LOG_INFO,-1, lngtxt(619),
          SSL_CTX_sess_connect_good(srvctx)+SSL_CTX_sess_connect_good(clnctx));
#if SSLEAY_VERSION_NUMBER >= 0x0922
    p_log(LOG_INFO,-1, lngtxt(620),
          SSL_CTX_sess_connect_renegotiate(srvctx)+SSL_CTX_sess_connect_renegotiate(clnctx));
#endif
    p_log(LOG_INFO,-1, lngtxt(621),
          SSL_CTX_sess_accept(srvctx)+SSL_CTX_sess_accept(clnctx));
    p_log(LOG_INFO,-1, lngtxt(622),
          SSL_CTX_sess_accept_good(srvctx)+SSL_CTX_sess_accept_good(clnctx));
#if SSLEAY_VERSION_NUMBER >= 0x0922
    p_log(LOG_INFO,-1, lngtxt(623),
          SSL_CTX_sess_accept_renegotiate(srvctx)+SSL_CTX_sess_accept_renegotiate(clnctx));
#endif
    p_log(LOG_INFO,-1, lngtxt(624), SSL_CTX_sess_hits(srvctx)+SSL_CTX_sess_hits(clnctx));
    p_log(LOG_INFO,-1, lngtxt(625), SSL_CTX_sess_misses(srvctx)+SSL_CTX_sess_misses(clnctx));
    p_log(LOG_INFO,-1, lngtxt(626), SSL_CTX_sess_timeouts(srvctx)+SSL_CTX_sess_timeouts(clnctx));
    p_log(LOG_INFO,-1, lngtxt(627));
    return;
}
예제 #3
0
static void print_stuff(BIO *bio, SSL *s, int full)
{
    X509 *peer=NULL;
    char *p;
    static const char *space="                ";
    char buf[BUFSIZ];
    STACK_OF(X509) *sk;
    STACK_OF(X509_NAME) *sk2;
    SSL_CIPHER *c;
    X509_NAME *xn;
    int j,i;
#ifndef OPENSSL_NO_COMP
    const COMP_METHOD *comp, *expansion;
#endif

    if (full)
    {
        int got_a_chain = 0;

        sk=SSL_get_peer_cert_chain(s);
        if (sk != NULL)
        {
            got_a_chain = 1; /* we don't have it for SSL2 (yet) */

            BIO_printf(bio,"---\nCertificate chain\n");
            for (i=0; i<sk_X509_num(sk); i++)
            {
                X509_NAME_oneline(X509_get_subject_name(
                                      sk_X509_value(sk,i)),buf,sizeof buf);
                BIO_printf(bio,"%2d s:%s\n",i,buf);
                X509_NAME_oneline(X509_get_issuer_name(
                                      sk_X509_value(sk,i)),buf,sizeof buf);
                BIO_printf(bio,"   i:%s\n",buf);
                if (c_showcerts)
                    PEM_write_bio_X509(bio,sk_X509_value(sk,i));
            }
        }

        BIO_printf(bio,"---\n");
        peer=SSL_get_peer_certificate(s);
        if (peer != NULL)
        {
            BIO_printf(bio,"Server certificate\n");
            if (!(c_showcerts && got_a_chain)) /* Redundant if we showed the whole chain */
                PEM_write_bio_X509(bio,peer);
            X509_NAME_oneline(X509_get_subject_name(peer),
                              buf,sizeof buf);
            BIO_printf(bio,"subject=%s\n",buf);
            X509_NAME_oneline(X509_get_issuer_name(peer),
                              buf,sizeof buf);
            BIO_printf(bio,"issuer=%s\n",buf);
        }
        else
            BIO_printf(bio,"no peer certificate available\n");

        sk2=SSL_get_client_CA_list(s);
        if ((sk2 != NULL) && (sk_X509_NAME_num(sk2) > 0))
        {
            BIO_printf(bio,"---\nAcceptable client certificate CA names\n");
            for (i=0; i<sk_X509_NAME_num(sk2); i++)
            {
                xn=sk_X509_NAME_value(sk2,i);
                X509_NAME_oneline(xn,buf,sizeof(buf));
                BIO_write(bio,buf,strlen(buf));
                BIO_write(bio,"\n",1);
            }
        }
        else
        {
            BIO_printf(bio,"---\nNo client certificate CA names sent\n");
        }
        p=SSL_get_shared_ciphers(s,buf,sizeof buf);
        if (p != NULL)
        {
            /* This works only for SSL 2.  In later protocol
             * versions, the client does not know what other
             * ciphers (in addition to the one to be used
             * in the current connection) the server supports. */

            BIO_printf(bio,"---\nCiphers common between both SSL endpoints:\n");
            j=i=0;
            while (*p)
            {
                if (*p == ':')
                {
                    BIO_write(bio,space,15-j%25);
                    i++;
                    j=0;
                    BIO_write(bio,((i%3)?" ":"\n"),1);
                }
                else
                {
                    BIO_write(bio,p,1);
                    j++;
                }
                p++;
            }
            BIO_write(bio,"\n",1);
        }

        BIO_printf(bio,"---\nSSL handshake has read %ld bytes and written %ld bytes\n",
                   BIO_number_read(SSL_get_rbio(s)),
                   BIO_number_written(SSL_get_wbio(s)));
    }
    BIO_printf(bio,((s->hit)?"---\nReused, ":"---\nNew, "));
    c=SSL_get_current_cipher(s);
    BIO_printf(bio,"%s, Cipher is %s\n",
               SSL_CIPHER_get_version(c),
               SSL_CIPHER_get_name(c));
    if (peer != NULL) {
        EVP_PKEY *pktmp;
        pktmp = X509_get_pubkey(peer);
        BIO_printf(bio,"Server public key is %d bit\n",
                   EVP_PKEY_bits(pktmp));
        EVP_PKEY_free(pktmp);
    }
#ifndef OPENSSL_NO_COMP
    comp=SSL_get_current_compression(s);
    expansion=SSL_get_current_expansion(s);
    BIO_printf(bio,"Compression: %s\n",
               comp ? SSL_COMP_get_name(comp) : "NONE");
    BIO_printf(bio,"Expansion: %s\n",
               expansion ? SSL_COMP_get_name(expansion) : "NONE");
#endif
    SSL_SESSION_print(bio,SSL_get_session(s));
    BIO_printf(bio,"---\n");
    if (peer != NULL)
        X509_free(peer);
    /* flush, or debugging output gets mixed with http response */
    (void)BIO_flush(bio);
}
예제 #4
0
static int ssl_do(struct st_VioSSLFd *ptr, Vio *vio, long timeout,
                  ssl_handshake_func_t func,
                  unsigned long *ssl_errno_holder)
{
  int r;
  SSL *ssl;
  my_socket sd= mysql_socket_getfd(vio->mysql_socket);
  DBUG_ENTER("ssl_do");
  DBUG_PRINT("enter", ("ptr: 0x%lx, sd: %d  ctx: 0x%lx",
                       (long) ptr, sd, (long) ptr->ssl_context));

  if (!(ssl= SSL_new(ptr->ssl_context)))
  {
    DBUG_PRINT("error", ("SSL_new failure"));
    *ssl_errno_holder= ERR_get_error();
    DBUG_RETURN(1);
  }
  DBUG_PRINT("info", ("ssl: 0x%lx timeout: %ld", (long) ssl, timeout));
  SSL_clear(ssl);
  SSL_SESSION_set_timeout(SSL_get_session(ssl), timeout);
  SSL_set_fd(ssl, sd);
#ifndef HAVE_YASSL
  SSL_set_options(ssl, SSL_OP_NO_COMPRESSION);
#endif

  /*
    Since yaSSL does not support non-blocking send operations, use
    special transport functions that properly handles non-blocking
    sockets. These functions emulate the behavior of blocking I/O
    operations by waiting for I/O to become available.
  */
#ifdef HAVE_YASSL
  /* Set first argument of the transport functions. */
  yaSSL_transport_set_ptr(ssl, vio);
  /* Set functions to use in order to send and receive data. */
  yaSSL_transport_set_recv_function(ssl, yassl_recv);
  yaSSL_transport_set_send_function(ssl, yassl_send);
#endif

  if ((r= ssl_handshake_loop(vio, ssl, func, ssl_errno_holder)) < 1)
  {
    DBUG_PRINT("error", ("SSL_connect/accept failure"));
    SSL_free(ssl);
    DBUG_RETURN(1);
  }

  /*
    Connection succeeded. Install new function handlers,
    change type, set sd to the fd used when connecting
    and set pointer to the SSL structure
  */
  if (vio_reset(vio, VIO_TYPE_SSL, SSL_get_fd(ssl), ssl, 0))
    DBUG_RETURN(1);

#ifndef DBUG_OFF
  {
    /* Print some info about the peer */
    X509 *cert;
    char buf[512];

    DBUG_PRINT("info",("SSL connection succeeded"));
    DBUG_PRINT("info",("Using cipher: '%s'" , SSL_get_cipher_name(ssl)));

    if ((cert= SSL_get_peer_certificate (ssl)))
    {
      DBUG_PRINT("info",("Peer certificate:"));
      X509_NAME_oneline(X509_get_subject_name(cert), buf, sizeof(buf));
      DBUG_PRINT("info",("\t subject: '%s'", buf));
      X509_NAME_oneline(X509_get_issuer_name(cert), buf, sizeof(buf));
      DBUG_PRINT("info",("\t issuer: '%s'", buf));
      X509_free(cert);
    }
    else
      DBUG_PRINT("info",("Peer does not have certificate."));

    if (SSL_get_shared_ciphers(ssl, buf, sizeof(buf)))
    {
      DBUG_PRINT("info",("shared_ciphers: '%s'", buf));
    }
    else
      DBUG_PRINT("info",("no shared ciphers!"));
  }
#endif

  DBUG_RETURN(0);
}
예제 #5
0
파일: viossl.c 프로젝트: AllenWeb/mariadb
static int ssl_do(struct st_VioSSLFd *ptr, Vio *vio, long timeout,
                  int (*connect_accept_func)(SSL*), unsigned long *errptr)
{
  int r;
  SSL *ssl;
  my_bool unused;
  my_bool was_blocking;
  DBUG_ENTER("ssl_do");
  DBUG_PRINT("enter", ("ptr: 0x%lx, sd: %d  ctx: 0x%lx",
                       (long) ptr, vio->sd, (long) ptr->ssl_context));

  /* Set socket to blocking if not already set */
  vio_blocking(vio, 1, &was_blocking);

  if (!(ssl= SSL_new(ptr->ssl_context)))
  {
    DBUG_PRINT("error", ("SSL_new failure"));
    *errptr= ERR_get_error();
    vio_blocking(vio, was_blocking, &unused);
    DBUG_RETURN(1);
  }
  DBUG_PRINT("info", ("ssl: 0x%lx timeout: %ld", (long) ssl, timeout));
  SSL_clear(ssl);
  SSL_SESSION_set_timeout(SSL_get_session(ssl), timeout);
  SSL_set_fd(ssl, vio->sd);
#if  !defined(HAVE_YASSL) && defined(SSL_OP_NO_COMPRESSION)
  SSL_set_options(ssl, SSL_OP_NO_COMPRESSION);
#endif

  if ((r= connect_accept_func(ssl)) < 1)
  {
    DBUG_PRINT("error", ("SSL_connect/accept failure"));
    *errptr= SSL_get_error(ssl, r);
    SSL_free(ssl);
    vio_blocking(vio, was_blocking, &unused);
    DBUG_RETURN(1);
  }

  /*
    Connection succeeded. Install new function handlers,
    change type, set sd to the fd used when connecting
    and set pointer to the SSL structure
  */
  vio_reset(vio, VIO_TYPE_SSL, SSL_get_fd(ssl), 0, 0);
  vio->ssl_arg= (void*)ssl;

#ifndef DBUG_OFF
  {
    /* Print some info about the peer */
    X509 *cert;
    char buf[512];

    DBUG_PRINT("info",("SSL connection succeeded"));
    DBUG_PRINT("info",("Using cipher: '%s'" , SSL_get_cipher_name(ssl)));

    if ((cert= SSL_get_peer_certificate (ssl)))
    {
      DBUG_PRINT("info",("Peer certificate:"));
      X509_NAME_oneline(X509_get_subject_name(cert), buf, sizeof(buf));
      DBUG_PRINT("info",("\t subject: '%s'", buf));
      X509_NAME_oneline(X509_get_issuer_name(cert), buf, sizeof(buf));
      DBUG_PRINT("info",("\t issuer: '%s'", buf));
      X509_free(cert);
    }
    else
      DBUG_PRINT("info",("Peer does not have certificate."));

    if (SSL_get_shared_ciphers(ssl, buf, sizeof(buf)))
    {
      DBUG_PRINT("info",("shared_ciphers: '%s'", buf));
    }
    else
      DBUG_PRINT("info",("no shared ciphers!"));
  }
#endif

  DBUG_RETURN(0);
}
예제 #6
0
/* Switch on a filedescriptor */
int ggz_tls_enable_fd(int fd, GGZTLSType mode, GGZTLSVerificationType verify)
{
	int ret, ret2;
	STACK_OF(SSL_CIPHER) *stack;
	SSL_CIPHER *cipher;
	int bits;
	char *cipherlist;
	SSL *_tls;
	int _tls_active;
	struct list_entry *entry;

	_state = 1;
	_tls_active = 0;
	if((mode != GGZ_TLS_CLIENT) && (mode != GGZ_TLS_SERVER))
	{
		TLSERROR("Wrong mode.");
		return 0;
	}

	if(!_tlsctx) tls_init(verify);
		
	_tls = SSL_new(_tlsctx);
	if(_tls)
	{
		cipherlist = NULL;
		stack = SSL_get_ciphers(_tls);
		while((cipher = (SSL_CIPHER*)sk_pop(stack)) != NULL)
		{
			printf("* Cipher: %s\n", SSL_CIPHER_get_name(cipher));
			printf("  Bits: %i\n", SSL_CIPHER_get_bits(cipher, &bits));
			printf("  Used bits: %i\n", bits);
			printf("  Version: %s\n", SSL_CIPHER_get_version(cipher));
			printf("  Description: %s\n", SSL_CIPHER_description(cipher, NULL, 0));
			if(cipherlist)
			{
				cipherlist = (char*)realloc(cipherlist, (strlen(cipherlist) + 1) + strlen(SSL_CIPHER_get_name(cipher)) + 1);
				strcat(cipherlist, ":");
				strcat(cipherlist, SSL_CIPHER_get_name(cipher));
			}
			else
			{
				cipherlist = (char*)malloc(strlen(SSL_CIPHER_get_name(cipher)) + 1);
				strcpy(cipherlist, SSL_CIPHER_get_name(cipher));
			}
		}
		printf("Available ciphers: %s\n", cipherlist);
		ret = SSL_set_cipher_list(_tls, cipherlist);
		if(!ret) TLSERROR("Cipher selection failed.");
		ret = SSL_set_fd(_tls, fd);
		if(!ret) TLSERROR("Assignment to connection failed.");
		else
		{
			SSL_set_read_ahead(_tls, 1);
			if(mode == GGZ_TLS_SERVER)
			{
				tls_certkey(_tls);
				if(_state)
				{
					SSL_set_accept_state(_tls);
					ret = SSL_accept(_tls);
				}
			}
			else
			{
				SSL_set_connect_state(_tls);
				ret = SSL_connect(_tls);
			}
			if((ret != 1) || (!_state))
			{
				printf("Ret: %i, State: %i\n", ret, _state);
				TLSERROR("Handshake failed.");
				ret2 = ERR_get_error();
				printf("EXT: %s\n%s\n%s\n%s\n%s\n", tls_exterror(_tls, ret), ERR_error_string(ret2, NULL),
					ERR_lib_error_string(ret2), ERR_func_error_string(ret2), ERR_reason_error_string(ret2));
			}
			else
			{
				printf(">>>>> Handshake successful.\n");
				if((mode == GGZ_TLS_SERVER) || (verify == GGZ_TLS_VERIFY_NONE)) _tls_active = 1;
				else
				{
					printf(">>>>> Client side, thus checking Certificate.\n");
					printf("Negotiated cipher: %s\n", SSL_get_cipher(_tls));
					printf("Shared ciphers: %s\n", SSL_get_shared_ciphers(_tls, NULL, 0));
					if(SSL_get_peer_certificate(_tls))
					{
						if(SSL_get_verify_result(_tls) == X509_V_OK)
						{
							_tls_active = 1;
						}
						else
						{
							printf("Error code: %li\n", SSL_get_verify_result(_tls));
							TLSERROR("Invalid certificate, or certificate is not self-signed.");
						}
					}
					else TLSERROR("Couldn't get certificate.");
				}
			}
			entry = (struct list_entry*)ggz_malloc(sizeof(struct list_entry));
			entry->tls = _tls;
			entry->fd = fd;
			entry->active = _tls_active;
			ggz_list_insert(openssllist, entry);
			return 1;
		}
	}
	return 0;
}
예제 #7
0
파일: ssl.c 프로젝트: witchu/lua-openssl
static int openssl_ssl_get(lua_State*L)
{
  SSL* s = CHECK_OBJECT(1, SSL, "openssl.ssl");
  int i;
  int top = lua_gettop(L);
  for (i = 2; i <= top; i++)
  {
    const char* what = luaL_checklstring(L, i, NULL);
    if (strcmp(what, "fd") == 0)
    {
      lua_pushinteger(L, SSL_get_fd(s));
    }
    else if (strcmp(what, "rfd") == 0)
    {
      lua_pushinteger(L, SSL_get_rfd(s));
    }
    else if (strcmp(what, "wfd") == 0)
    {
      lua_pushinteger(L, SSL_get_wfd(s));
    }
    else if (strcmp(what, "client_CA_list") == 0)
    {
      STACK_OF(X509_NAME)* sn = SSL_get_client_CA_list(s);
      PUSH_OBJECT(sn, "openssl.sk_x509_name");
    }
    else if (strcmp(what, "read_ahead") == 0)
    {
      lua_pushboolean(L, SSL_get_read_ahead(s));
    }
    else if (strcmp(what, "shared_ciphers") == 0)
    {
      char buf[LUAL_BUFFERSIZE] = {0};
      lua_pushstring(L, SSL_get_shared_ciphers(s, buf, sizeof(buf)));
    }
    else if (strcmp(what, "cipher_list") == 0)
    {
      //TODO FIX
      lua_pushstring(L, SSL_get_cipher_list(s, 0));
    }
    else if (strcmp(what, "verify_mode") == 0)
    {
      //FIX
      lua_pushinteger(L, SSL_get_verify_mode(s));
    }
    else if (strcmp(what, "verify_depth") == 0)
    {
      lua_pushinteger(L, SSL_get_verify_depth(s));
    }
    else if (strcmp(what, "state_string") == 0)
    {
      lua_pushstring(L, SSL_state_string(s));
    }
    else if (strcmp(what, "state_string_long") == 0)
    {
      lua_pushstring(L, SSL_state_string_long(s));
    }
    else if (strcmp(what, "rstate_string") == 0)
    {
      lua_pushstring(L, SSL_rstate_string(s));
    }
    else if (strcmp(what, "rstate_string_long") == 0)
    {
      lua_pushstring(L, SSL_rstate_string_long(s));
    }
    else if (strcmp(what, "version") == 0)
    {
      lua_pushstring(L, SSL_get_version(s));
    }
    else if (strcmp(what, "iversion") == 0)
    {
      lua_pushinteger(L, SSL_version(s));
    }
    else if (strcmp(what, "default_timeout") == 0)
    {
      lua_pushinteger(L, SSL_get_default_timeout(s));
    }
    else if (strcmp(what, "certificate") == 0)
    {
      X509* cert = SSL_get_certificate(s);
      PUSH_OBJECT(cert, "openssl.x509");
    }
    else if (strcmp(what, "verify_result") == 0)
    {
      long l = SSL_get_verify_result(s);
      lua_pushinteger(L, l);
    }
    else if (strcmp(what, "version") == 0)
    {
      lua_pushstring(L, SSL_get_version(s));
    }
    else if (strcmp(what, "state") == 0)
    {
      lua_pushinteger(L, SSL_state(s));
    }
    else if (strcmp(what, "hostname") == 0)
    {
      lua_pushstring(L, SSL_get_servername(s, TLSEXT_NAMETYPE_host_name));
    }
    else
      luaL_argerror(L, i, "can't understant");
  }
  return top - 1;
}
예제 #8
0
static void
print_stuff(BIO * bio, SSL * s, int full)
{
	X509 *peer = NULL;
	char *p;
	static const char *space = "                ";
	char buf[BUFSIZ];
	STACK_OF(X509) * sk;
	STACK_OF(X509_NAME) * sk2;
	const SSL_CIPHER *c;
	X509_NAME *xn;
	int j, i;
	unsigned char *exportedkeymat;

	if (full) {
		int got_a_chain = 0;

		sk = SSL_get_peer_cert_chain(s);
		if (sk != NULL) {
			got_a_chain = 1;	/* we don't have it for SSL2
						 * (yet) */

			BIO_printf(bio, "---\nCertificate chain\n");
			for (i = 0; i < sk_X509_num(sk); i++) {
				X509_NAME_oneline(X509_get_subject_name(
					sk_X509_value(sk, i)), buf, sizeof buf);
				BIO_printf(bio, "%2d s:%s\n", i, buf);
				X509_NAME_oneline(X509_get_issuer_name(
					sk_X509_value(sk, i)), buf, sizeof buf);
				BIO_printf(bio, "   i:%s\n", buf);
				if (c_showcerts)
					PEM_write_bio_X509(bio, sk_X509_value(sk, i));
			}
		}
		BIO_printf(bio, "---\n");
		peer = SSL_get_peer_certificate(s);
		if (peer != NULL) {
			BIO_printf(bio, "Server certificate\n");
			if (!(c_showcerts && got_a_chain))	/* Redundant if we
								 * showed the whole
								 * chain */
				PEM_write_bio_X509(bio, peer);
			X509_NAME_oneline(X509_get_subject_name(peer),
			    buf, sizeof buf);
			BIO_printf(bio, "subject=%s\n", buf);
			X509_NAME_oneline(X509_get_issuer_name(peer),
			    buf, sizeof buf);
			BIO_printf(bio, "issuer=%s\n", buf);
		} else
			BIO_printf(bio, "no peer certificate available\n");

		sk2 = SSL_get_client_CA_list(s);
		if ((sk2 != NULL) && (sk_X509_NAME_num(sk2) > 0)) {
			BIO_printf(bio, "---\nAcceptable client certificate CA names\n");
			for (i = 0; i < sk_X509_NAME_num(sk2); i++) {
				xn = sk_X509_NAME_value(sk2, i);
				X509_NAME_oneline(xn, buf, sizeof(buf));
				BIO_write(bio, buf, strlen(buf));
				BIO_write(bio, "\n", 1);
			}
		} else {
			BIO_printf(bio, "---\nNo client certificate CA names sent\n");
		}
		p = SSL_get_shared_ciphers(s, buf, sizeof buf);
		if (p != NULL) {
			/*
			 * This works only for SSL 2.  In later protocol
			 * versions, the client does not know what other
			 * ciphers (in addition to the one to be used in the
			 * current connection) the server supports.
			 */

			BIO_printf(bio, "---\nCiphers common between both SSL endpoints:\n");
			j = i = 0;
			while (*p) {
				if (*p == ':') {
					BIO_write(bio, space, 15 - j % 25);
					i++;
					j = 0;
					BIO_write(bio, ((i % 3) ? " " : "\n"), 1);
				} else {
					BIO_write(bio, p, 1);
					j++;
				}
				p++;
			}
			BIO_write(bio, "\n", 1);
		}
		BIO_printf(bio, "---\nSSL handshake has read %ld bytes and written %ld bytes\n",
		    BIO_number_read(SSL_get_rbio(s)),
		    BIO_number_written(SSL_get_wbio(s)));
	}
	BIO_printf(bio, (SSL_cache_hit(s) ? "---\nReused, " : "---\nNew, "));
	c = SSL_get_current_cipher(s);
	BIO_printf(bio, "%s, Cipher is %s\n",
	    SSL_CIPHER_get_version(c),
	    SSL_CIPHER_get_name(c));
	if (peer != NULL) {
		EVP_PKEY *pktmp;
		pktmp = X509_get_pubkey(peer);
		BIO_printf(bio, "Server public key is %d bit\n",
		    EVP_PKEY_bits(pktmp));
		EVP_PKEY_free(pktmp);
	}
	BIO_printf(bio, "Secure Renegotiation IS%s supported\n",
	    SSL_get_secure_renegotiation_support(s) ? "" : " NOT");

	/* Compression is not supported and will always be none. */
	BIO_printf(bio, "Compression: NONE\n");
	BIO_printf(bio, "Expansion: NONE\n");

#ifdef SSL_DEBUG
	{
		/* Print out local port of connection: useful for debugging */
		int sock;
		struct sockaddr_in ladd;
		socklen_t ladd_size = sizeof(ladd);
		sock = SSL_get_fd(s);
		getsockname(sock, (struct sockaddr *) & ladd, &ladd_size);
		BIO_printf(bio_c_out, "LOCAL PORT is %u\n", ntohs(ladd.sin_port));
	}
#endif

#if !defined(OPENSSL_NO_TLSEXT) && !defined(OPENSSL_NO_NEXTPROTONEG)
	if (next_proto.status != -1) {
		const unsigned char *proto;
		unsigned int proto_len;
		SSL_get0_next_proto_negotiated(s, &proto, &proto_len);
		BIO_printf(bio, "Next protocol: (%d) ", next_proto.status);
		BIO_write(bio, proto, proto_len);
		BIO_write(bio, "\n", 1);
	}
#endif

#ifndef OPENSSL_NO_SRTP
	{
		SRTP_PROTECTION_PROFILE *srtp_profile = SSL_get_selected_srtp_profile(s);

		if (srtp_profile)
			BIO_printf(bio, "SRTP Extension negotiated, profile=%s\n",
			    srtp_profile->name);
	}
#endif

	SSL_SESSION_print(bio, SSL_get_session(s));
	if (keymatexportlabel != NULL) {
		BIO_printf(bio, "Keying material exporter:\n");
		BIO_printf(bio, "    Label: '%s'\n", keymatexportlabel);
		BIO_printf(bio, "    Length: %i bytes\n", keymatexportlen);
		exportedkeymat = malloc(keymatexportlen);
		if (exportedkeymat != NULL) {
			if (!SSL_export_keying_material(s, exportedkeymat,
				keymatexportlen,
				keymatexportlabel,
				strlen(keymatexportlabel),
				NULL, 0, 0)) {
				BIO_printf(bio, "    Error\n");
			} else {
				BIO_printf(bio, "    Keying material: ");
				for (i = 0; i < keymatexportlen; i++)
					BIO_printf(bio, "%02X",
					    exportedkeymat[i]);
				BIO_printf(bio, "\n");
			}
			free(exportedkeymat);
		}
	}
	BIO_printf(bio, "---\n");
	if (peer != NULL)
		X509_free(peer);
	/* flush, or debugging output gets mixed with http response */
	(void) BIO_flush(bio);
}
예제 #9
0
파일: viossl.c 프로젝트: GitHub9527/easysql
static int ssl_do(struct st_VioSSLFd *ptr, Vio *vio, long timeout,
                  ssl_handshake_func_t func,
                  unsigned long *ssl_errno_holder)
{
  int r;
  SSL *ssl;
  my_socket sd= mysql_socket_getfd(vio->mysql_socket);

  /* Declared here to make compiler happy */
#if !defined(HAVE_YASSL) && !defined(DBUG_OFF)
  int j, n;
#endif

  DBUG_ENTER("ssl_do");
  DBUG_PRINT("enter", ("ptr: 0x%lx, sd: %d  ctx: 0x%lx",
                       (long) ptr, sd, (long) ptr->ssl_context));

  if (!(ssl= SSL_new(ptr->ssl_context)))
  {
    DBUG_PRINT("error", ("SSL_new failure"));
    *ssl_errno_holder= ERR_get_error();
    DBUG_RETURN(1);
  }
  DBUG_PRINT("info", ("ssl: 0x%lx timeout: %ld", (long) ssl, timeout));
  SSL_clear(ssl);
  SSL_SESSION_set_timeout(SSL_get_session(ssl), timeout);
  SSL_set_fd(ssl, sd);
#if !defined(HAVE_YASSL) && defined(SSL_OP_NO_COMPRESSION)
  SSL_set_options(ssl, SSL_OP_NO_COMPRESSION); /* OpenSSL >= 1.0 only */
#elif OPENSSL_VERSION_NUMBER >= 0x00908000L /* workaround for OpenSSL 0.9.8 */
  sk_SSL_COMP_zero(SSL_COMP_get_compression_methods());
#endif

#if !defined(HAVE_YASSL) && !defined(DBUG_OFF)
  {
    STACK_OF(SSL_COMP) *ssl_comp_methods = NULL;
    ssl_comp_methods = SSL_COMP_get_compression_methods();
    n= sk_SSL_COMP_num(ssl_comp_methods);
    DBUG_PRINT("info", ("Available compression methods:\n"));
    if (n == 0)
      DBUG_PRINT("info", ("NONE\n"));
    else
      for (j = 0; j < n; j++)
      {
        SSL_COMP *c = sk_SSL_COMP_value(ssl_comp_methods, j);
        DBUG_PRINT("info", ("  %d: %s\n", c->id, c->name));
      }
  }
#endif

  /*
    Since yaSSL does not support non-blocking send operations, use
    special transport functions that properly handles non-blocking
    sockets. These functions emulate the behavior of blocking I/O
    operations by waiting for I/O to become available.
  */
#ifdef HAVE_YASSL
  /* Set first argument of the transport functions. */
  yaSSL_transport_set_ptr(ssl, vio);
  /* Set functions to use in order to send and receive data. */
  yaSSL_transport_set_recv_function(ssl, yassl_recv);
  yaSSL_transport_set_send_function(ssl, yassl_send);
#endif

  if ((r= ssl_handshake_loop(vio, ssl, func, ssl_errno_holder)) < 1)
  {
    DBUG_PRINT("error", ("SSL_connect/accept failure"));
    SSL_free(ssl);
    DBUG_RETURN(1);
  }

  /*
    Connection succeeded. Install new function handlers,
    change type, set sd to the fd used when connecting
    and set pointer to the SSL structure
  */
  if (vio_reset(vio, VIO_TYPE_SSL, SSL_get_fd(ssl), ssl, 0))
    DBUG_RETURN(1);

#ifndef DBUG_OFF
  {
    /* Print some info about the peer */
    X509 *cert;
    char buf[512];

    DBUG_PRINT("info",("SSL connection succeeded"));
    DBUG_PRINT("info",("Using cipher: '%s'" , SSL_get_cipher_name(ssl)));

    if ((cert= SSL_get_peer_certificate (ssl)))
    {
      DBUG_PRINT("info",("Peer certificate:"));
      X509_NAME_oneline(X509_get_subject_name(cert), buf, sizeof(buf));
      DBUG_PRINT("info",("\t subject: '%s'", buf));
      X509_NAME_oneline(X509_get_issuer_name(cert), buf, sizeof(buf));
      DBUG_PRINT("info",("\t issuer: '%s'", buf));
      X509_free(cert);
    }
    else
      DBUG_PRINT("info",("Peer does not have certificate."));

    if (SSL_get_shared_ciphers(ssl, buf, sizeof(buf)))
    {
      DBUG_PRINT("info",("shared_ciphers: '%s'", buf));
    }
    else
      DBUG_PRINT("info",("no shared ciphers!"));
  }
#endif

  DBUG_RETURN(0);
}
예제 #10
0
int sslconnect(struct st_VioSSLFd *ptr, Vio *vio, long timeout)
{
  SSL *ssl;
  my_bool unused;
  my_bool was_blocking;

  DBUG_ENTER("sslconnect");
  DBUG_PRINT("enter", ("ptr: 0x%lx, sd: %d  ctx: 0x%lx",
                       (long) ptr, vio->sd, (long) ptr->ssl_context));

  /* Set socket to blocking if not already set */
  vio_blocking(vio, 1, &was_blocking);

  if (!(ssl= SSL_new(ptr->ssl_context)))
  {
    DBUG_PRINT("error", ("SSL_new failure"));
    report_errors(ssl);
    vio_blocking(vio, was_blocking, &unused);
    DBUG_RETURN(1);
  }
  DBUG_PRINT("info", ("ssl: 0x%lx timeout: %ld", (long) ssl, timeout));
  SSL_clear(ssl);
  SSL_SESSION_set_timeout(SSL_get_session(ssl), timeout);
  SSL_set_fd(ssl, vio->sd);

  /*
    SSL_do_handshake will select between SSL_connect
    or SSL_accept depending on server or client side
  */
  if (SSL_do_handshake(ssl) < 1)
  {
    DBUG_PRINT("error", ("SSL_do_handshake failure"));
    report_errors(ssl);
    SSL_free(ssl);
    vio_blocking(vio, was_blocking, &unused);
    DBUG_RETURN(1);
  }

  /*
    Connection succeeded. Install new function handlers,
    change type, set sd to the fd used when connecting
    and set pointer to the SSL structure
  */
  vio_reset(vio, VIO_TYPE_SSL, SSL_get_fd(ssl), 0, 0);
  vio->ssl_arg= (void*)ssl;

#ifndef DBUG_OFF
  {
    /* Print some info about the peer */
    X509 *cert;
    char buf[512];

    DBUG_PRINT("info",("SSL connection succeeded"));
    DBUG_PRINT("info",("Using cipher: '%s'" , SSL_get_cipher_name(ssl)));

    if ((cert= SSL_get_peer_certificate (ssl)))
    {
      DBUG_PRINT("info",("Peer certificate:"));
      X509_NAME_oneline(X509_get_subject_name(cert), buf, sizeof(buf));
      DBUG_PRINT("info",("\t subject: '%s'", buf));
      X509_NAME_oneline(X509_get_issuer_name(cert), buf, sizeof(buf));
      DBUG_PRINT("info",("\t issuer: '%s'", buf));
      X509_free(cert);
    }
    else
      DBUG_PRINT("info",("Peer does not have certificate."));

    if (SSL_get_shared_ciphers(ssl, buf, sizeof(buf)))
    {
      DBUG_PRINT("info",("shared_ciphers: '%s'", buf));
    }
    else
      DBUG_PRINT("info",("no shared ciphers!"));
  }
#endif

  DBUG_RETURN(0);
}
예제 #11
0
void ssl_barf_out(Socket_t S) {
	BIO *ebio;
	char buf[BUFSIZ], *p;
	sock_ssl_t m = XSsl(S);

  if (tb_errorlevel >= TB_NOTICE) {
		STACK      * sk;

    if ((ebio=BIO_new(BIO_s_file())) == NULL) {
      tb_warn("Cannot create new BIO\n");
      ERR_print_errors_fp(stderr);
      return;
    }
    BIO_set_fp(ebio,stderr,BIO_NOCLOSE);
    if ((sk=(STACK *)SSL_get_peer_cert_chain(m->cx)) != NULL) {
			int i;
      BIO_printf(ebio,"---\nCertificate chain\n");
      for (i=0; i<sk_num(sk); i++) {
        X509_NAME_oneline(X509_get_subject_name((X509*)sk_value(sk,i)),buf,BUFSIZ);
        BIO_printf(ebio,"%2d s:%s\n",i,buf);
        X509_NAME_oneline(X509_get_issuer_name((X509 *)sk_value(sk,i)),buf,BUFSIZ);
        BIO_printf(ebio,"   i:%s\n",buf);
      }
    }
    BIO_printf(ebio,"---\n");
    if ((m->peer=SSL_get_peer_certificate(m->cx)) != NULL) {
      BIO_printf(ebio,"Peer certificate\n");
      PEM_write_bio_X509(ebio,m->peer);
      X509_NAME_oneline(X509_get_subject_name(m->peer),buf,BUFSIZ);
      BIO_printf(ebio,"subject=%s\n",buf);
      X509_NAME_oneline(X509_get_issuer_name(m->peer),buf,BUFSIZ);
      BIO_printf(ebio,"issuer=%s\n",buf);
    }
    else
      BIO_printf(ebio,"no peer certificate available\n");
    if (((sk=SSL_get_client_CA_list(m->cx)) != NULL) && (sk_num(sk) > 0)) {
			int i;
      BIO_printf(ebio,"---\nAcceptable peer certificate CA names\n");
      for (i=0; i<sk_num(sk); i++) {
        m->xn=(X509_NAME *)sk_value(sk,i);
        X509_NAME_oneline(m->xn,buf,sizeof(buf));
        BIO_write(ebio,buf,strlen(buf));
        BIO_write(ebio,"\n",1);
      }
    }
    else {
      BIO_printf(ebio,"---\nNo peer certificate CA names sent\n");
    }
    if ((p=SSL_get_shared_ciphers(m->cx,buf,BUFSIZ)) != NULL) {
			int i, j;
      BIO_printf(ebio,"---\nCiphers common between both SSL endpoints:\n");
      j=i=0;
      while (*p) {
        if (*p != ':') {
          BIO_write(ebio,p,1);j++;
        } else {
          BIO_write(ebio,"                ",15-j%25);i++;j=0;
          BIO_write(ebio,((i%3)?" ":"\n"),1);
        }
        p++;
      }
      BIO_write(ebio,"\n",1);
    }
    BIO_printf(ebio,
               "---\nSSL handshake has read %ld bytes and written %ld bytes\n",
               BIO_number_read(SSL_get_rbio(m->cx)),
               BIO_number_written(SSL_get_wbio(m->cx)));
    BIO_printf(ebio,((m->cx->hit)?"---\nReused, ":"---\nNew, "));
    m->sc=SSL_get_current_cipher(m->cx);
    BIO_printf(ebio,"%s, Cipher is %s\n",
               SSL_CIPHER_get_version(m->sc),SSL_CIPHER_get_name(m->sc));
    if(m->peer != NULL) {
      EVP_PKEY *pktmp;
      pktmp = X509_get_pubkey(m->peer);
      BIO_printf(ebio,"Server public key is %d bit\n", EVP_PKEY_bits(pktmp));
      EVP_PKEY_free(pktmp);
    }
    SSL_SESSION_print(ebio,SSL_get_session(m->cx));
    BIO_printf(ebio,"---\n");
    if(m->peer != NULL)
      X509_free(m->peer);
    BIO_free(ebio);
  }
}
예제 #12
0
static int init_ssl_connection(SSL *con)
{
	int i;
#ifdef DEBUG
	const char *str;
	X509 *peer;
	static char buf[BUFSIZ];
#endif
	long verify_error;
	int err = 0;

	if ((i = SSL_accept(con)) <= 0)
	{
		err = SSL_get_error (con, i);
		if ((SSL_ERROR_WANT_READ == err) || (SSL_ERROR_WANT_WRITE == err))
			fprintf (stderr, "%s: %s(): Error [SSL_ERROR_WANT_READ or SSL_ERROR_WANT_WRITE]\n", \
				__FILE__, __func__);

		if (BIO_sock_should_retry (i))
		{
			BIO_printf(bio_s_out, "DELAY\n");
			return 1;
		}

		
		BIO_printf(bio_err, "ERROR\n");
		verify_error = SSL_get_verify_result (con);
		if (verify_error != X509_V_OK)
		{
			BIO_printf(bio_err,"verify error:%s\n",
				X509_verify_cert_error_string(verify_error));
		}
		else
		{
			fprintf (stderr, "%s: %s(): X509_V_OK but error\n", __FILE__, __func__);
			ERR_print_errors (bio_err);
		}
		return 0;
	}

#ifdef DEBUG
	PEM_write_bio_SSL_SESSION (bio_s_out, SSL_get_session (con));

	peer = SSL_get_peer_certificate (con);
	if (NULL != peer)
	{
		BIO_printf (bio_s_out, "Client certificate\n");
		PEM_write_bio_X509 (bio_s_out, peer);
		X509_NAME_oneline (X509_get_subject_name (peer), buf, sizeof buf);
		BIO_printf (bio_s_out, "subject = %s\n", buf);
		X509_NAME_oneline (X509_get_issuer_name (peer), buf, sizeof buf);
		BIO_printf (bio_s_out, "issuer = %s\n", buf);
		X509_free(peer);
	}

	if (SSL_get_shared_ciphers (con, buf, sizeof buf) != NULL)
		BIO_printf (bio_s_out, "Shared ciphers: %s\n", buf);
	str = SSL_CIPHER_get_name (SSL_get_current_cipher (con));
	BIO_printf (bio_s_out, "CIPHER is %s\n", (str != NULL) ? str : "(NONE)");
#endif
	if (con->hit) BIO_printf (bio_s_out, "Reused session-id\n");
	if (SSL_ctrl (con, SSL_CTRL_GET_FLAGS, 0, NULL) & TLS1_FLAGS_TLS_PADDING_BUG)
		BIO_printf (bio_s_out, "Peer has incorrect TLSv1 block padding\n");

	return 1;
}