Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

SSL3_GET_SERVER_CERTIFICATE:certificate verify failed:.\ssl\s3_clnt.c:984

347 views
Skip to first unread message

Hamid....@sungard.com

unread,
Jan 17, 2012, 9:00:33 AM1/17/12
to

Hi,

 

I am trying to create SSL connection with a remote server using OpenSSL in visual C++ (Visual Studio-2008, Win-7). I am getting the following errors. Please let me know, what does this error indicates, and how can it be rectified.

 

Please reply me on my email address as well, because I asked one question few weeks back and I never saw its reply until today when I was searching for this new problem.

 

Thank you.

Kind Regards,

Hamid Shahid

 

 

//=========================================

//  Error Log

//=========================================

.... Establishing SSL Connection ....

Socket bound with server

Starting SSL HandShake on tcp connection

SSL error # 1 in accept, program terminated 0

12256:error:14090086:SSL routines:SSL3_GET_SERVER_CERTIFICATE:certificate verify failed:.\ssl\s3_clnt.c:984:

 

//=========================================

//  Code

//=========================================

 

ConnectSSL(string serverIP, string serverPort)

{

       m_serverIP = serverIP;

       m_serverPort = serverPort;

 

       std::cout<<".... Establishing SSL Connection .... \n";

 

       // Binding Socket IP and Port

       memset(&socketaddr,0, sizeof(socketaddr));

       socketaddr.sin_family = AF_INET;

       socketaddr.sin_addr.s_addr = inet_addr((char *)m_serverIP.c_str() );

       socketaddr.sin_port = htons(atoi((char *)m_serverPort.c_str()));

       std::cout<<"Socket bound with server \n";

 

       myssl;

       myssl=SSL_new(ctx);  // Create new ssl object

       if(!myssl)

       {

              std::cout<<"Error creating SSL Object, error # "<<GetLastError()<<"\n";

              ERR_print_errors_fp(stderr);

              return -1;

       }

 

       err = connect(socketfd,(SOCKADDR *)&socketaddr,sizeof(SOCKADDR_IN)); // Connect to the server on TCP/IP layer

       if(err<0)

       {

              std::cout<<"Error creating connection on Tcp/ip socket, error # "<<GetLastError()<<"\n";

              ERR_print_errors_fp(stderr);

              //SSL_free(myssl);

              //SSL_CTX_free(ctx);

              return -1;

       }

 

       std::cout<<"Starting SSL HandShake on tcp connection\n";

 

       SSL_set_fd(myssl,(int)socketfd); //Bind the socket to the SSL Object

       err=SSL_connect(myssl);    // Connect to the server, SSL layer

       // Check for error in SSL connection

       if (err<1)

       {

              err=SSL_get_error(myssl,err);

              std::cout<<"SSL error # "<<err<<" in accept, program terminated "<<GetLastError()<<"\n";

              ERR_print_errors_fp(stderr);

              if(err==5)

              {

                     std::cout<<"SockErr - LastError is: "<<err<<", "<<GetLastError();

                     ERR_print_errors_fp(stderr);

              }

 

              closesocket(socketfd);

              //SSL_free(myssl);

              //SSL_CTX_free(ctx);

              return -1;

       }

 

       //Printing out connection details, when a connection is created

       cout<<"SSL connection on socket: "<<socketfd<<", Version: "<<SSL_get_version(myssl)<<", Cipher: "<<SSL_get_cipher(myssl)<<"\n";

       return 1;

}

 

//=========================================

 

LoadCertificates()

{

       std::cout<<".... Loading Certificates .... \n";

 

       cout<<"Accessing CERT_FILE : "<<m_certFileName.c_str()<<"\n";

       if (SSL_CTX_use_certificate_file(ctx,(char *)m_certFileName.c_str(), SSL_FILETYPE_PEM) <= 0)    // Indicate the certificate file to be used

       {

              std::cout<<"Error setting the certificate file, error # "<<GetLastError()<<"\n";

              ERR_print_errors_fp(stderr);

              return;

       }

       std::cout<<"~~Certificate file loaded~~\n";

 

       std::cout<<"setting the password for the Private Key\n"; // setting the password for the Private Key

       SSL_CTX_set_default_passwd_cb_userdata(ctx,(char *)m_privKeyPassword.c_str());

 

       std::cout<<"Accessing PrivateKey_file :"<< m_certPrivKeyFileName.c_str()<<"\n";   // Indicate the key file to be used

       if (SSL_CTX_use_PrivateKey_file(ctx,(char *)m_certPrivKeyFileName.c_str() , SSL_FILETYPE_PEM) <= 0)

       {

              std::cout<<"Error loading the private key, error # "<<GetLastError()<<"\n";

              ERR_print_errors_fp(stderr);

              return;

       }

       std::cout<<"~~Certificate PrivateKey_file loaded~~\n";

 

       if (SSL_CTX_check_private_key(ctx) == 0) // Make sure the key and certificate file match

       {

              std::cout<<"Private key does not match the certificate public key, error # "<<GetLastError()<<"\n";

              ERR_print_errors_fp(stderr);

              return;;

       }

       std::cout<<"~~Certificate and private key matched~~\n";

 

std::cout<<"Accessing Trusted CAs file : "<<m_trustedCAFileName.c_str()<<"\n";    // Set the list of trusted CAs based on the file and/or directory provided*/

       if(SSL_CTX_load_verify_locations(ctx,(char *)m_trustedCAFileName.c_str(),CA_DIR)<1)

       {

              std::cout<<"Error setting verify location, error # "<<GetLastError()<<"\n";

              ERR_print_errors_fp(stderr);

              return;

       }

       std::cout<<"~~CAs file loaded~~\n";

 

       SSL_CTX_set_verify(ctx,SSL_VERIFY_PEER,NULL);   // Set for server verification

 

       std::cout<<".... Certificates loaded .... \n\n";

}

 

//=========================================

Dave Thompson

unread,
Jan 17, 2012, 6:18:23 PM1/17/12
to
> From: owner-ope...@openssl.org On Behalf Of
Hamid....@sungard.com
> Sent: Tuesday, 17 January, 2012 09:01

> I am trying to create SSL connection with a remote server
> using OpenSSL in visual C++ (Visual Studio-2008, Win-7). I am
> getting the following errors. Please let me know, what does
> this error indicates, and how can it be rectified.

> Please reply me on my email address as well, because I asked
> one question few weeks back and I never saw its reply until today
> when I was searching for this new problem.

CCed. Note http://marc.info/?l=openssl-users&w=2&r=1&s=hamid&q=b
http://www.mail-archive.com/search?q=hamid.shahid&l=openssl-users%40openssl.
org
both shows three posts from you:
2011/12/12-13 error:14077410 --- sslv3 alert handshake failure
2011/12/03,05 Problems with a setting certificates via OpenSSL in C++
(Windows)
all with replies. (Although for some reason searching your full name
in marc gives incomplete results.) If you didn't get those replies,
check your incoming email isn't blocking/filtering the list.

> // Error Log
> .... Establishing SSL Connection ....
> Socket bound with server
> Starting SSL HandShake on tcp connection
> SSL error # 1 in accept, program terminated 0
> 12256:error:14090086:SSL routines:SSL3_GET_SERVER_CERTIFICATE:
> certificate verify failed:.\ssl\s3_clnt.c:984:

It means exactly what it says; the client logic failed
to verify the server certifcate. Either:
- you've connected to the wrong server
- the server is using an invalid certificate
- you aren't using the correct CA cert(s) (root,
and possibly chain if server doesn't supply it/them).
In particular your log excerpt doesn't indicate
if you executed your LoadCertificates() before
you executed ConnectSSL(). If not (and you don't
have the CA cert(s) in the default truststore)
client verify of server will fail; since your
LoadCertificates() also loads the client key&cert,
it would also cause server verify of client if used
to fail, but the handshake doesn't get that far.

If you are doing LoadCertificates first and with
the correct cert(s), then to get a more detailed
error you can add a verify callback (perhaps only
temporarily for debugging), or probably easier you
can do the same connection attempt with commandline
openssl s_client (which already displays the
verify callback events in readable form).

Several other comments on your code:

- your log message says "error # in accept" when
it's actually in SSL_connect.

- functions of the form
ConnectSSL(args...){...}
are not valid C++. The return type is required in C++
except for ctors (and dtors), and not only would that
be a stupid name for a class and (thus) ctor, but the
two functions you show must share data but can't
possibly be ctors of one class. My VC++08Express
gives error C4430, as it should; there may be some
option to crank this down, but you shouldn't.

- except for _passwd_cb_userdata, all of your (char*)
casts are unneeded clutter because they are in places
that accept const char *. And in the one place you do
need it, good C++ style is to use the least powerful
new-style cast needed, here const_cast<>.

- your error cleanup is inconsistent and probably wrong
in some places depending on how these functions are used,
but I'll assume you just haven't gotten to that yet.


______________________________________________________________________
OpenSSL Project http://www.openssl.org
User Support Mailing List openss...@openssl.org
Automated List Manager majo...@openssl.org

Dave Thompson

unread,
Jan 18, 2012, 10:38:56 PM1/18/12
to
> From: Hamid....@sungard.com [mailto:Hamid....@sungard.com]
> Sent: Wednesday, 18 January, 2012 10:36

> - Yes, I am calling load certificates before the trying to
> make a connection. According to your suggestion, I have tried
> to used openssl s_client to see the callback events and got
> the following log. But how can I add verify callback in my code?
>
See below.

> - Also, I tried by commenting the code which is loading the
> CA file, and in that case "SSL_connect" gives no error and
> works fine. Does that mean CA is not needed at all?
>
Did you keep the set_verify(,SSL_VERIFY_PEER,)? If not,
then no verification is done and no trust entries at all
are needed. If so, the needed CA cert is apparently in the
default truststore used by your OpenSSL. The base distro
has nothing in the default truststore, but some packaged
builds include various well-known public CAs, and if so
and the server you connect to is using one of them
then verification succeeds.

> -------------------------------------
> Regarding code:
> -------------------------------------
> - Actually both those functions are members of a class and
> they have return types but that got skipped when I pasted the
> code here.
> - Type casting to char * was indeed not needed.

Fine.

> - I am using the class destructor to free the memory.
> However, please elaborate your point about error-cleanup.
>
That might do it. I didn't know that when I was reading
before so I'd have to go through again and don't have time
right now. And it's your code anyway. :-)

> -------------------------------------
> openssl s_client Log:
> -------------------------------------

With what arguments, in particular were -CAfile (or -CApath)
and -cert and -key same as your code uses?

> Loading 'screen' into random state - done
> CONNECTED(00000100)
> depth=0 /C=DE/ST=Hessen/L=Frankfurt/O=SIX Swiss Exchange
> AG/OU=DBAG-a-2011/CN=fixml2.eurexchange.com
> verify error:num=20:unable to get local issuer certificate
> verify return:1

s_client didn't find the issuer cert in whatever you
supplied for -CAfile/-CApath. And due to the error below
s_client didn't tell you the needed issuer. If you have or
can get a separate copy of the server cert you can look at
that, otherwise use -debug on s_client and decode manually
or get a wire trace with wireshark or equivalent which can
decode the server-Cert message. Or write a callback, see
below, that displays the issuer for 20 and not just 2.

> depth=0 /C=DE/ST=Hessen/L=Frankfurt/O=SIX Swiss Exchange
> AG/OU=DBAG-a-2011/CN=fixml2.eurexchange.com
> verify error:num=27:certificate not trusted
> verify return:1
> depth=0 /C=DE/ST=Hessen/L=Frankfurt/O=SIX Swiss Exchange
> AG/OU=DBAG-a-2011/CN=fixml2.eurexchange.com
> verify error:num=21:unable to verify the first certificate
> verify return:1

s_client continues in spite of the verify failure, unlike
your code with set_verify_mode(,SSL_VERIFY_PEER,).

> 10720:error:14094412:SSL routines:SSL3_READ_BYTES:sslv3 alert
> bad certificate:.\ssl\s3_pkt.c:1102:SSL alert number 42
> 10720:error:140790E5:SSL routines:SSL23_WRITE:ssl handshake
> failure:.\ssl\s23_lib.c:182:
>
And either you did not give s_client the client key+cert, or
the one you gave it is not acceptable to the server. And
because the handshake fails, s_client doesn't get to the
point of displaying the known part of the cert chain.

If you want to write a verify callback, man SSL_set_verify
specifies the API, which is simple except that it gives you
the cert (in fact the whole cert chain) and X.509 certs are
moderately complex. The callback used by s_client (and also
s_server) is in apps/s_cb.c and gives some ideas on what you
can do. Like displaying the issuer name for verify error 20.

Good luck.

Hamid....@sungard.com

unread,
Jan 18, 2012, 10:35:48 AM1/18/12
to
Hi Dave,

Thank you so much for a detailed reply and the code review.

-------------------------------------
Regarding the problem:
-------------------------------------
- Yes, I am calling load certificates before the trying to make a connection. According to your suggestion, I have tried to used openssl s_client to see the callback events and got the following log. But how can I add verify callback in my code?

- Also, I tried by commenting the code which is loading the CA file, and in that case "SSL_connect" gives no error and works fine. Does that mean CA is not needed at all?

-------------------------------------
Regarding code:
-------------------------------------
- Actually both those functions are members of a class and they have return types but that got skipped when I pasted the code here.
- Type casting to char * was indeed not needed.
- I am using the class destructor to free the memory. However, please elaborate your point about error-cleanup.

Thanks again.

Kind Regards,
Hamid Shahid

-------------------------------------
openssl s_client Log:
-------------------------------------
Loading 'screen' into random state - done
CONNECTED(00000100)
depth=0 /C=DE/ST=Hessen/L=Frankfurt/O=SIX Swiss Exchange AG/OU=DBAG-a-2011/CN=fixml2.eurexchange.com
verify error:num=20:unable to get local issuer certificate
verify return:1
depth=0 /C=DE/ST=Hessen/L=Frankfurt/O=SIX Swiss Exchange AG/OU=DBAG-a-2011/CN=fixml2.eurexchange.com
verify error:num=27:certificate not trusted
verify return:1
depth=0 /C=DE/ST=Hessen/L=Frankfurt/O=SIX Swiss Exchange AG/OU=DBAG-a-2011/CN=fixml2.eurexchange.com
verify error:num=21:unable to verify the first certificate
verify return:1
10720:error:14094412:SSL routines:SSL3_READ_BYTES:sslv3 alert bad certificate:.\ssl\s3_pkt.c:1102:SSL alert number 42
10720:error:140790E5:SSL routines:SSL23_WRITE:ssl handshake failure:.\ssl\s23_lib.c:182:

============================================================================
LoadCertificates() also loads the client key&cert, it would also cause server verify of client if used to fail, but the handshake doesn't get that far______________________________________________________________________

jaynes...@gmail.com

unread,
Jun 3, 2014, 3:31:02 AM6/3/14
to
hello sir,

i am working in wm6. for that i am compile wcecompat and openssl but i can not know how to use this libs in my application.can you tell me the steps for that

Thank you
jaynesh
0 new messages