C ++电子邮件客户端中的OpenSSL - 服务器关闭与TLSv1警报消息的连接

时间:2012-03-24 11:23:37

标签: c++ client openssl ssl

我的应用程序连接到IMAP电子邮件服务器。一个客户端将其服务器配置为拒绝SSLv2证书,现在我的应用程序无法连接到服务器。所有其他电子邮件客户端都成功连接到此服我的应用使用openssl。

我通过创建最小的openssl客户端并尝试连接到服务器进行调试。下面是连接到邮件服务器的代码(使用Windows套接字,但unix套接字也有同样的问题)。

服务器发送其初始IMAP问候消息,但在客户端发送第1个命令后,服务器关闭连接。在Wireshark中,我看到在向服务器发送命令后,它返回TLSv1错误消息21(加密警报)并且连接已经消失。

我正在寻找适当的OpenSSL设置,以使此连接成功。 感谢

#include <stdio.h>
#include <memory.h>
#include <errno.h>
#include <sys/types.h>
#include <winsock2.h>
#include <openssl/crypto.h>
#include <openssl/x509.h>
#include <openssl/pem.h>
#include <openssl/ssl.h>
#include <openssl/err.h>

#define CHK_NULL(x) if((x)==NULL) exit(1)
#define CHK_ERR(err,s) if((err)==-1) { perror(s); exit(1); }
#define CHK_SSL(err) if((err)==-1) { ERR_print_errors_fp(stderr); exit(2); }

SSL *ssl;
char buf[4096];

void write(const char *s){
   int err = SSL_write(ssl, s, strlen(s));
   printf("> %s\n", s);
   CHK_SSL(err);
}

void read(){
   int n = SSL_read(ssl, buf, sizeof(buf) - 1);
   CHK_SSL(n);
   if(n==0){
      int e = SSL_get_error(ssl, 0);
      printf("Read error %i\n", e);
      exit(1);
   }
   buf[n] = 0;
   printf("%s\n", buf);
}

void main(){
   int err=0;

   SSLeay_add_ssl_algorithms();
   SSL_METHOD *meth = SSLv23_client_method();
   SSL_load_error_strings();
   SSL_CTX *ctx = SSL_CTX_new(meth);
   CHK_NULL(ctx);

   WSADATA data;
   WSAStartup(0x202, &data);

   int sd = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
   CHK_ERR(sd, "socket");

   struct sockaddr_in sa;
   memset(&sa, 0, sizeof(sa));
   sa.sin_family      = AF_INET;
   sa.sin_addr.s_addr = inet_addr("195.137.27.14");
   sa.sin_port = htons(993);

   err = connect(sd,(struct sockaddr*) &sa, sizeof(sa));
   CHK_ERR(err, "connect");

   /* ----------------------------------------------- */
   /* Now we have TCP connection. Start SSL negotiation. */

   ssl = SSL_new(ctx);                         CHK_NULL(ssl);    
   SSL_set_fd(ssl, sd);
   err = SSL_connect(ssl); CHK_SSL(err);

   // Following two steps are optional and not required for data exchange to be successful.
   /*
   printf("SSL connection using %s\n", SSL_get_cipher(ssl));

   X509 *server_cert = SSL_get_peer_certificate(ssl);       CHK_NULL(server_cert);
   printf("Server certificate:\n");

   char *str = X509_NAME_oneline(X509_get_subject_name(server_cert),0,0);
   CHK_NULL(str);
   printf(" subject: %s\n", str);
   OPENSSL_free(str);

   str = X509_NAME_oneline(X509_get_issuer_name (server_cert),0,0);
   CHK_NULL(str);
   printf(" issuer: %s\n", str);
   OPENSSL_free(str);

   // We could do all sorts of certificate verification stuff here before deallocating the certificate.
   X509_free(server_cert);
   */

   printf("\n\n");

   read(); // get initial IMAP greeting
   write("1 CAPABILITY\r\n"); // send 1st command
   read(); // get reply to cmd; server closes connection here
   write("2 LOGIN a b\r\n");
   read();

   SSL_shutdown(ssl);

   closesocket(sd);
   SSL_free(ssl);
   SSL_CTX_free(ctx);
}

1 个答案:

答案 0 :(得分:4)

您尝试连接的主机似乎有一个错误的TLS实现。使用openssl命令行工具,我发现了以下内容。

首先,文件imap包含一个愚蠢的IMAP会话:

A1 CAPABILITY
A2 LOGIN foo bar

然后,命令:

openssl s_client -ign_eof -crlf -pause -connect 195.137.27.14:993 < imap

失败如下:

CONNECTED(00000003)
depth=2 /C=US/O=GeoTrust Inc./CN=GeoTrust Global CA
verify error:num=20:unable to get local issuer certificate
verify return:0
---
Certificate chain
 0 s:/serialNumber=iGXzgDJpD6t8m5jQNY0xwwcCiwwlXzET/C=GB/O=mail1.firedupgroup.co.uk/OU=GT57369617/OU=See www.rapidssl.com/resources/cps (c)11/OU=Domain Control Validated - RapidSSL(R)/CN=mail1.firedupgroup.co.uk
   i:/C=US/O=GeoTrust, Inc./CN=RapidSSL CA
 1 s:/C=US/O=GeoTrust, Inc./CN=RapidSSL CA
   i:/C=US/O=GeoTrust Inc./CN=GeoTrust Global CA
 2 s:/C=US/O=GeoTrust Inc./CN=GeoTrust Global CA
   i:/C=US/O=Equifax/OU=Equifax Secure Certificate Authority
---
Server certificate
-----BEGIN CERTIFICATE-----
MIIE6TCCA9GgAwIBAgIDA+NwMA0GCSqGSIb3DQEBBQUAMDwxCzAJBgNVBAYTAlVT
MRcwFQYDVQQKEw5HZW9UcnVzdCwgSW5jLjEUMBIGA1UEAxMLUmFwaWRTU0wgQ0Ew
HhcNMTExMTA2MTQ1MDQwWhcNMTQxMTA4MTUwNTIwWjCB9zEpMCcGA1UEBRMgaUdY
emdESnBENnQ4bTVqUU5ZMHh3d2NDaXd3bFh6RVQxCzAJBgNVBAYTAkdCMSEwHwYD
VQQKExhtYWlsMS5maXJlZHVwZ3JvdXAuY28udWsxEzARBgNVBAsTCkdUNTczNjk2
MTcxMTAvBgNVBAsTKFNlZSB3d3cucmFwaWRzc2wuY29tL3Jlc291cmNlcy9jcHMg
KGMpMTExLzAtBgNVBAsTJkRvbWFpbiBDb250cm9sIFZhbGlkYXRlZCAtIFJhcGlk
U1NMKFIpMSEwHwYDVQQDExhtYWlsMS5maXJlZHVwZ3JvdXAuY28udWswggEiMA0G
CSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQC80HlFa86b8C4N9NEpu904iluVyYEH
rwZaIYNR6cvfHl/QXut+h4080UoIxxFmSsuVI9YBJBf/J6ZnJoFTZsJITuoI89G/
4/nmcuGPOeJIrlMnWHZE56N5bVNDFDsNeroE2ieQKiJN2IT9lUA7uZHtJuokXlfz
Xg6DEWBXokAjPc3VeS2eBDfajY2SLZNdRxGYzyQkaW43pMaz4FR9WKljsRvvvKUI
G0Hnsy1vpjCDw3io4C+IY8tClZFVnLthQQEbceD93LS/AUsaZEZWf4pppFviYHze
HuiZ6IlYvLzLaYtCurNaJhs2Yf6kNPDbfCFSWbCrfdf86feQxt/JyR4HAgMBAAGj
ggE2MIIBMjAfBgNVHSMEGDAWgBRraT1qGEJK3Y8CZTn9NSSGeJEWMDAOBgNVHQ8B
Af8EBAMCBaAwHQYDVR0lBBYwFAYIKwYBBQUHAwEGCCsGAQUFBwMCMCMGA1UdEQQc
MBqCGG1haWwxLmZpcmVkdXBncm91cC5jby51azBDBgNVHR8EPDA6MDigNqA0hjJo
dHRwOi8vcmFwaWRzc2wtY3JsLmdlb3RydXN0LmNvbS9jcmxzL3JhcGlkc3NsLmNy
bDAdBgNVHQ4EFgQUC0oWYx2XW3qtt3Xq6mUljQlYb+UwDAYDVR0TAQH/BAIwADBJ
BggrBgEFBQcBAQQ9MDswOQYIKwYBBQUHMAKGLWh0dHA6Ly9yYXBpZHNzbC1haWEu
Z2VvdHJ1c3QuY29tL3JhcGlkc3NsLmNydDANBgkqhkiG9w0BAQUFAAOCAQEAXX5N
EYNlVqiu8LIn39JODWCUbqZQOHOSquC+VxTyLRaUjrkrnU0oCDqKTs/C6qGBqiqC
7gaZKn2k+KjTMu2rTtgO/BHve6y9kKz7oLgXqfjZp6965O+x4BV5/GyVbwmV5gyU
dRZ5U83Vhwut5MxbiMyxnZHtuz9jGMC08O3Gc84N1Ox18FwOE8HpQIHOO99ISxOi
8TgVe/NJvd4f/nn7GPTyVDQpGOJ2dqHYUNpAMMVXKmCeNq+u0nXXZFXUkkkVxmrC
aINtUJuelF6V4vxtyERwReviAct9vcIrg3011p7NYbZ5fVA8thSYcnacfe1jyp5Z
XSPY6tC26zmbIPmHHg==
-----END CERTIFICATE-----
subject=/serialNumber=iGXzgDJpD6t8m5jQNY0xwwcCiwwlXzET/C=GB/O=mail1.firedupgroup.co.uk/OU=GT57369617/OU=See www.rapidssl.com/resources/cps (c)11/OU=Domain Control Validated - RapidSSL(R)/CN=mail1.firedupgroup.co.uk
issuer=/C=US/O=GeoTrust, Inc./CN=RapidSSL CA
---
No client certificate CA names sent
---
SSL handshake has read 3300 bytes and written 439 bytes
---
New, TLSv1/SSLv3, Cipher is DES-CBC3-SHA
Server public key is 2048 bit
Secure Renegotiation IS supported
Compression: NONE
Expansion: NONE
SSL-Session:
    Protocol  : TLSv1
    Cipher    : DES-CBC3-SHA
    Session-ID: 9F1200004D888506211A976BF1CC755C873789D8256936638BF9C9E66DAA9438
    Session-ID-ctx: 
    Master-Key: A67DE8C76371B8034AA60447ECB97ED631E55E4E713F64FAA49D2DBAC07A6339719F4C4DD4E1FD2BC5E41EDCC2CF22FE
    Key-Arg   : None
    Start Time: 1332595025
    Timeout   : 300 (sec)
    Verify return code: 20 (unable to get local issuer certificate)
---
* OK firedupgroup.co.uk IMAP4rev1 MDaemon 9.6.2 ready
closed

但命令:

openssl s_client -bugs -ign_eof -crlf -pause -connect 195.137.27.14:993 < imap

成功:

CONNECTED(00000003)
depth=2 /C=US/O=GeoTrust Inc./CN=GeoTrust Global CA
verify error:num=20:unable to get local issuer certificate
verify return:0
---
Certificate chain
 0 s:/serialNumber=iGXzgDJpD6t8m5jQNY0xwwcCiwwlXzET/C=GB/O=mail1.firedupgroup.co.uk/OU=GT57369617/OU=See www.rapidssl.com/resources/cps (c)11/OU=Domain Control Validated - RapidSSL(R)/CN=mail1.firedupgroup.co.uk
   i:/C=US/O=GeoTrust, Inc./CN=RapidSSL CA
 1 s:/C=US/O=GeoTrust, Inc./CN=RapidSSL CA
   i:/C=US/O=GeoTrust Inc./CN=GeoTrust Global CA
 2 s:/C=US/O=GeoTrust Inc./CN=GeoTrust Global CA
   i:/C=US/O=Equifax/OU=Equifax Secure Certificate Authority
---
Server certificate
-----BEGIN CERTIFICATE-----
MIIE6TCCA9GgAwIBAgIDA+NwMA0GCSqGSIb3DQEBBQUAMDwxCzAJBgNVBAYTAlVT
MRcwFQYDVQQKEw5HZW9UcnVzdCwgSW5jLjEUMBIGA1UEAxMLUmFwaWRTU0wgQ0Ew
HhcNMTExMTA2MTQ1MDQwWhcNMTQxMTA4MTUwNTIwWjCB9zEpMCcGA1UEBRMgaUdY
emdESnBENnQ4bTVqUU5ZMHh3d2NDaXd3bFh6RVQxCzAJBgNVBAYTAkdCMSEwHwYD
VQQKExhtYWlsMS5maXJlZHVwZ3JvdXAuY28udWsxEzARBgNVBAsTCkdUNTczNjk2
MTcxMTAvBgNVBAsTKFNlZSB3d3cucmFwaWRzc2wuY29tL3Jlc291cmNlcy9jcHMg
KGMpMTExLzAtBgNVBAsTJkRvbWFpbiBDb250cm9sIFZhbGlkYXRlZCAtIFJhcGlk
U1NMKFIpMSEwHwYDVQQDExhtYWlsMS5maXJlZHVwZ3JvdXAuY28udWswggEiMA0G
CSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQC80HlFa86b8C4N9NEpu904iluVyYEH
rwZaIYNR6cvfHl/QXut+h4080UoIxxFmSsuVI9YBJBf/J6ZnJoFTZsJITuoI89G/
4/nmcuGPOeJIrlMnWHZE56N5bVNDFDsNeroE2ieQKiJN2IT9lUA7uZHtJuokXlfz
Xg6DEWBXokAjPc3VeS2eBDfajY2SLZNdRxGYzyQkaW43pMaz4FR9WKljsRvvvKUI
G0Hnsy1vpjCDw3io4C+IY8tClZFVnLthQQEbceD93LS/AUsaZEZWf4pppFviYHze
HuiZ6IlYvLzLaYtCurNaJhs2Yf6kNPDbfCFSWbCrfdf86feQxt/JyR4HAgMBAAGj
ggE2MIIBMjAfBgNVHSMEGDAWgBRraT1qGEJK3Y8CZTn9NSSGeJEWMDAOBgNVHQ8B
Af8EBAMCBaAwHQYDVR0lBBYwFAYIKwYBBQUHAwEGCCsGAQUFBwMCMCMGA1UdEQQc
MBqCGG1haWwxLmZpcmVkdXBncm91cC5jby51azBDBgNVHR8EPDA6MDigNqA0hjJo
dHRwOi8vcmFwaWRzc2wtY3JsLmdlb3RydXN0LmNvbS9jcmxzL3JhcGlkc3NsLmNy
bDAdBgNVHQ4EFgQUC0oWYx2XW3qtt3Xq6mUljQlYb+UwDAYDVR0TAQH/BAIwADBJ
BggrBgEFBQcBAQQ9MDswOQYIKwYBBQUHMAKGLWh0dHA6Ly9yYXBpZHNzbC1haWEu
Z2VvdHJ1c3QuY29tL3JhcGlkc3NsLmNydDANBgkqhkiG9w0BAQUFAAOCAQEAXX5N
EYNlVqiu8LIn39JODWCUbqZQOHOSquC+VxTyLRaUjrkrnU0oCDqKTs/C6qGBqiqC
7gaZKn2k+KjTMu2rTtgO/BHve6y9kKz7oLgXqfjZp6965O+x4BV5/GyVbwmV5gyU
dRZ5U83Vhwut5MxbiMyxnZHtuz9jGMC08O3Gc84N1Ox18FwOE8HpQIHOO99ISxOi
8TgVe/NJvd4f/nn7GPTyVDQpGOJ2dqHYUNpAMMVXKmCeNq+u0nXXZFXUkkkVxmrC
aINtUJuelF6V4vxtyERwReviAct9vcIrg3011p7NYbZ5fVA8thSYcnacfe1jyp5Z
XSPY6tC26zmbIPmHHg==
-----END CERTIFICATE-----
subject=/serialNumber=iGXzgDJpD6t8m5jQNY0xwwcCiwwlXzET/C=GB/O=mail1.firedupgroup.co.uk/OU=GT57369617/OU=See www.rapidssl.com/resources/cps (c)11/OU=Domain Control Validated - RapidSSL(R)/CN=mail1.firedupgroup.co.uk
issuer=/C=US/O=GeoTrust, Inc./CN=RapidSSL CA
---
No client certificate CA names sent
---
SSL handshake has read 3300 bytes and written 423 bytes
---
New, TLSv1/SSLv3, Cipher is DES-CBC3-SHA
Server public key is 2048 bit
Secure Renegotiation IS supported
Compression: NONE
Expansion: NONE
SSL-Session:
    Protocol  : TLSv1
    Cipher    : DES-CBC3-SHA
    Session-ID: 261200008CB526A49A014E97D510AA7FDA08DDAC797B8B78B3ABEEF4A64B3228
    Session-ID-ctx: 
    Master-Key: 457E9FFB43C77E028211A0FDB9915FCB374A55445ED15498E2C5AFDBEA52C9A413CC8D79EE29ECA823E038A93363B9D6
    Key-Arg   : None
    Start Time: 1332595088
    Timeout   : 300 (sec)
    Verify return code: 20 (unable to get local issuer certificate)
---
* OK firedupgroup.co.uk IMAP4rev1 MDaemon 9.6.2 ready
* CAPABILITY IMAP4rev1 NAMESPACE AUTH=CRAM-MD5 AUTH=LOGIN AUTH=PLAIN IDLE ACL UNSELECT UIDPLUS
A1 OK CAPABILITY completed
A2 NO LOGIN failed

这意味着您需要启用OpenSSL的错误解决方法,如SSL_CTX_set_options(3)手册页中所述。