hi all i'm a newbie to the openssl and plan to integrate SSL to my server. my server is developed based on IO completion port. so i want to separate the SSL engine from the socket object totally. after googled in mail list, i found it is possible by using BIO pair mechanism . after almost two weeks paining, i decide to turn to you.(i know this topic was discussed many times in the mail list,but i still cannot figure out) please help me out of it. i think i was trapped by some wrong things.
to make you better understand, i wrote a simple server and past below. My idea is: 1.make the bio pair.bioInternal,bioNetwork 2.got client accept. 3.receive data from client (eg.client hello) 4.feed the data(eg.client hello) to bioNetwork 5. waiting data(eg.server hello) in bioNetwork and send back to client. 6.(repeat the step 3,4,5 until the handshake process finish) ----code.(writed by VS2008)----------------------- #include "openssl/ssl.h" #include <winsock2.h> #include <stdlib.h> #include <stdio.h> int _tmain(int argc, _TCHAR* argv[]) { SSL_load_error_strings(); SSL_library_init(); OpenSSL_add_all_algorithms(); SSL_CTX* pCTX=SSL_CTX_new(TLSv1_server_method()); /*INIT*/ { char cCurDir[255]; ::GetCurrentDirectory( 255,cCurDir ); char cTmp[1024]; sprintf( cTmp,"%s\\pem\\ca.cer",cCurDir ); if(!SSL_CTX_load_verify_locations(pCTX, cTmp, NULL) ) goto bad_ssl; sprintf( cTmp,"%s\\pem\\ns.cer",cCurDir ); if(!SSL_CTX_use_certificate_file(pCTX, cTmp, SSL_FILETYPE_PEM)) goto bad_ssl; sprintf( cTmp,"%s\\pem\\ns.key",cCurDir ); if(!SSL_CTX_use_PrivateKey_file(pCTX, cTmp, SSL_FILETYPE_PEM)) goto bad_ssl; if (!SSL_CTX_check_private_key(pCTX)) goto bad_ssl; } SOCKET sktAccepted = INVALID_SOCKET; /*windows network*/ { WSADATA neto; if (WSAStartup(MAKEWORD(2,2), &neto)!=0) goto bad_ssl; SOCKET sk = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP); if(sk == SOCKET_ERROR) goto bad_ssl; SOCKADDR_IN sa; sa.sin_addr.S_un.S_addr = INADDR_ANY; sa.sin_family = AF_INET; sa.sin_port = htons(8001); if(bind(sk, (SOCKADDR*)&sa, sizeof(sa))== SOCKET_ERROR) goto bad_ssl; if(listen(sk,5)== SOCKET_ERROR) goto bad_ssl; sktAccepted = accept(sk, (struct sockaddr *)&sa, NULL); if(sktAccepted == INVALID_SOCKET) goto bad_ssl; } //after got client accept,prepare for handshake SSL* pSSL = SSL_new( pCTX ); if( pSSL == NULL ) goto bad_ssl; BIO* pBIOnet = BIO_new( BIO_s_mem() ); BIO* pBIOint = BIO_new( BIO_s_mem() ); //BIO* pBIO_SSL = BIO_new(BIO_f_ssl()); BIO_make_bio_pair( pBIOint,pBIOnet ); //long lOptions = SSL_ctrl( pSSL, SSL_CTRL_OPTIONS, 0, 0) | SSL_OP_ALL; //SSL_ctrl(pSSL, SSL_CTRL_OPTIONS, lOptions, 0); SSL_set_accept_state( pSSL ); SSL_set_bio( pSSL,pBIOint,pBIOint ); //BIO_set_ssl( pBIO_SSL, pSSL, BIO_NOCLOSE); SSL_set_mode(pSSL, SSL_MODE_AUTO_RETRY); char cTmp[4*1024]; //waitting data from client while( true ) { //(here.always got 124 len data from client.i use client tool 'openssl s_client -connect 127.0.0.1:8001' ) int iRe = recv( sktAccepted,cTmp,4*1024,0); if( iRe == 0 || iRe == SOCKET_ERROR ) break; //data got from network. send to SSL int iWritedLen = BIO_write( pBIOnet,cTmp,iRe ); BIO_flush( pBIOnet ); if( SSL_in_init( pSSL ) ) { int iRe = SSL_accept( pSSL );// SSL_do_handshake( pSSL ); if( iRe <= 0 ) { int iErrCode = SSL_get_error( pSSL,iRe ); printf("Error happen during BIO_do_handshake(..).err:%d\n",iErrCode ); switch( iErrCode ) { case SSL_ERROR_WANT_READ: {//where can i got data to feed SSL? } break; case SSL_ERROR_WANT_WRITE: break; } } //if( 0 ) { //in handshake process, after data got from network,there should be data needed sending back to client.for example."Server Hello" int iPendingLen = BIO_pending( pBIOnet ); if( iPendingLen > 0 ) { int iReadedDataLen = BIO_read( pBIOnet,cTmp,iPendingLen );//(the data is exactly the same with the data recived from client.??!) //send to client send( sktAccepted,cTmp,iReadedDataLen,0 ); } } } else {//handshake is done.then the data is application logic data. //got plain application data. if( BIO_pending( pBIOint ) > 0 ) { //read and dealing... //(...) } } } bad_ssl: //destroy all resource... //(...) return 0; } many thanks. anakin.jin