Invoke AC_PROG_CPP.
[elisp/starttls.git] / openssl.c
1 #include <stdio.h>
2 #include <stdlib.h>
3 #include <openssl/lhash.h>
4 #include <openssl/bn.h>
5 #include <openssl/err.h>
6 #include <openssl/pem.h>
7 #include <openssl/x509.h>
8 #include <openssl/ssl.h>
9
10 static SSL_CTX *tls_ctx = NULL;
11 static SSL *tls_conn = NULL;
12
13 static int
14 tls_ssl_ctx_new (cert_file, key_file)
15   const char *cert_file, *key_file;
16 {
17   SSL_load_error_strings ();
18   SSLeay_add_ssl_algorithms ();
19
20   tls_ctx = SSL_CTX_new (TLSv1_client_method());
21   if (!tls_ctx)
22     return -1;
23
24   SSL_CTX_set_options (tls_ctx, SSL_OP_ALL /* Work around all known bugs */); 
25
26   if (cert_file)
27     {
28       if (SSL_CTX_use_certificate_file (tls_ctx, cert_file, 
29                                         SSL_FILETYPE_PEM) <= 0)
30         return -1;
31       if (!key_file)
32         key_file = cert_file;
33       if (SSL_CTX_use_PrivateKey_file (tls_ctx, key_file, 
34                                        SSL_FILETYPE_PEM) <= 0)
35         return -1;
36       if (!SSL_CTX_check_private_key (tls_ctx))
37         return -1;
38     }
39
40   SSL_CTX_set_verify (tls_ctx, SSL_VERIFY_NONE, NULL);
41
42   return 0;
43 }
44
45 static int
46 tls_ssl_new(ctx, s)
47   SSL_CTX *ctx;
48   int s;
49 {
50   SSL_SESSION *session;
51   SSL_CIPHER *cipher;
52   X509   *peer;
53
54   tls_conn = (SSL *) SSL_new (ctx);
55   if (!tls_conn)
56     return -1;
57   SSL_clear(tls_conn);
58
59   if (!SSL_set_fd (tls_conn, s))
60     return -1;
61
62   SSL_set_connect_state (tls_conn);
63
64   if (SSL_connect (tls_conn) <= 0)
65     {
66       session = SSL_get_session (tls_conn);
67       if (session)
68         SSL_CTX_remove_session (ctx, session);
69       if (tls_conn)
70         SSL_free (tls_conn);
71       return -1;
72     }
73
74   return 0;
75 }
76
77 void
78 tls_negotiate (fd, cert_file, key_file)
79      int fd;
80      const char *cert_file, *key_file;
81 {
82   if (tls_ssl_ctx_new (cert_file, key_file) == -1)
83     return;
84
85   (void) tls_ssl_new (tls_ctx, fd); /* Negotiation has done. */
86 }
87
88 int
89 tls_write(fd, buf, num)
90      const char *buf;
91      int fd, num;
92 {
93   if (tls_conn) 
94     return SSL_write (tls_conn, buf, num);
95   return write (fd, buf, num);
96 }
97
98 int
99 tls_read(fd, buf, num)
100      char *buf;
101      int fd, num;
102 {
103   if (tls_conn)
104     return SSL_read (tls_conn, buf, num);
105   return read (fd, buf, num);
106 }
107
108 int
109 tls_pending()
110 {
111   return tls_conn && SSL_pending (tls_conn);
112 }