bcd4d9e7897ea24005d76c6034de801772b9bc38
[umurmur.git] / src / ssli_openssl.c
1 /* Copyright (C) 2009-2014, Martin Johansson <martin@fatbob.nu>
2    Copyright (C) 2005-2014, Thorvald Natvig <thorvald@natvig.com>
3
4    All rights reserved.
5
6    Redistribution and use in source and binary forms, with or without
7    modification, are permitted provided that the following conditions
8    are met:
9
10    - Redistributions of source code must retain the above copyright notice,
11      this list of conditions and the following disclaimer.
12    - Redistributions in binary form must reproduce the above copyright notice,
13      this list of conditions and the following disclaimer in the documentation
14      and/or other materials provided with the distribution.
15    - Neither the name of the Developers nor the names of its contributors may
16      be used to endorse or promote products derived from this software without
17      specific prior written permission.
18
19    THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
20    ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
21    LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
22    A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR
23    CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
24    EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
25    PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
26    PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
27    LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
28    NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
29    SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30 */
31 #include <stdlib.h>
32 #include <fcntl.h>
33
34 #include "conf.h"
35 #include "log.h"
36 #include "memory.h"
37 #include "ssl.h"
38
39 /*
40  * OpenSSL interface
41  */
42
43 #include <openssl/x509v3.h>
44 #include <openssl/ssl.h>
45 #include <openssl/err.h>
46 #include <openssl/safestack.h>
47 static X509 *x509;
48 static RSA *rsa;
49 static SSL_CTX *context;
50 static EVP_PKEY *pkey;
51
52 static int verify_callback(int preverify_ok, X509_STORE_CTX *ctx);
53
54 static int SSL_add_ext(X509 * crt, int nid, char *value) {
55         X509_EXTENSION *ex;
56         X509V3_CTX ctx;
57         X509V3_set_ctx_nodb(&ctx);
58         X509V3_set_ctx(&ctx, crt, crt, NULL, NULL, 0);
59         ex = X509V3_EXT_conf_nid(NULL, &ctx, nid, value);
60         if (!ex)
61                 return 0;
62
63         X509_add_ext(crt, ex, -1);
64         X509_EXTENSION_free(ex);
65         return 1;
66 }
67
68 static X509 *SSL_readcert(char *certfile)
69 {
70         FILE *fp;
71         X509 *x509;
72
73         /* open the certificate file */
74         fp = fopen(certfile, "r");
75         if (fp == NULL) {
76                 Log_warn("Unable to open the X509 file %s for reading.", certfile);
77                 return NULL;
78         }
79
80         /* allocate memory for the cert structure */
81         x509 = X509_new();
82
83         if (PEM_read_X509(fp, &x509, NULL, NULL) == 0) {
84                 /* error reading the x509 information - check the error stack */
85                 Log_warn("Error trying to read X509 info.");
86                 fclose(fp);
87                 X509_free(x509);
88                 return NULL;
89         }
90         fclose(fp);
91         return x509;
92 }
93
94 static RSA *SSL_readprivatekey(char *keyfile)
95 {
96         FILE *fp;
97         RSA *rsa;
98
99 /* open the private key file for reading */
100         fp = fopen(keyfile, "r");
101         if (fp == NULL) {
102                 Log_warn("Unable to open the private key file %s for reading.", keyfile);
103                 return NULL;
104         }
105
106 /* allocate memory for the RSA structure */
107         rsa = RSA_new();
108
109         /* assign a callback function for the password */
110
111         /* read a private key from file */
112         if (PEM_read_RSAPrivateKey(fp, &rsa, NULL, NULL) <= 0) {
113                 /* error reading the key - check the error stack */
114                 Log_warn("Error trying to read private key.");
115                 RSA_free(rsa);
116                 fclose(fp);
117                 return NULL;
118         }
119         fclose(fp);
120         return rsa;
121 }
122
123 static void SSL_writecert(char *certfile, X509 *x509)
124 {
125         FILE *fp;
126
127         /* open the private key file */
128         fp = fopen(certfile, "w");
129         if (fp == NULL) {
130                 Log_warn("Unable to open the X509 file %s for writing", certfile);
131                 return;
132         }
133         if (PEM_write_X509(fp, x509) == 0) {
134                 Log_warn("Error trying to write X509 info.");
135         }
136         fclose(fp);
137 }
138
139 static void SSL_writekey(char *keyfile, RSA *rsa)
140 {
141         FILE *fp;
142
143         /* open the private key file for reading */
144         fp = fopen(keyfile, "w");
145         if (fp == NULL) {
146                 Log_warn("Unable to open the private key file %s for writing.", keyfile);
147                 return;
148         }
149
150         if (PEM_write_RSAPrivateKey(fp, rsa, NULL, NULL, 0, NULL, NULL) == 0) {
151                 Log_warn("Error trying to write private key");
152         }
153         fclose(fp);
154 }
155
156 static void SSL_initializeCert() {
157
158         char *crt = (char *)getStrConf(CERTIFICATE);
159         char *key = (char *)getStrConf(KEY);
160
161         if (context) {
162                 bool_t did_load_cert = SSL_CTX_use_certificate_chain_file(context, crt);
163                 rsa = SSL_readprivatekey(key);
164
165                 if (!rsa || !did_load_cert) {
166                         Log_info("Generating new server certificate.");
167
168
169                         CRYPTO_mem_ctrl(CRYPTO_MEM_CHECK_ON);
170
171                         x509 = X509_new();
172                         pkey = EVP_PKEY_new();
173                         rsa = RSA_generate_key(4096,RSA_F4,NULL,NULL);
174                         EVP_PKEY_assign_RSA(pkey, rsa);
175
176                         X509_set_version(x509, 2);
177                         ASN1_INTEGER_set(X509_get_serialNumber(x509),1);
178                         X509_gmtime_adj(X509_get_notBefore(x509),0);
179                         X509_gmtime_adj(X509_get_notAfter(x509),60*60*24*365);
180                         X509_set_pubkey(x509, pkey);
181
182                         X509_NAME *name=X509_get_subject_name(x509);
183
184                         X509_NAME_add_entry_by_txt(name, "CN", MBSTRING_ASC, (const uint8_t *)"Murmur Autogenerated Certificate v2", -1, -1, 0);
185                         X509_set_issuer_name(x509, name);
186                         SSL_add_ext(x509, NID_basic_constraints, "critical,CA:FALSE");
187                         SSL_add_ext(x509, NID_ext_key_usage, "serverAuth,clientAuth");
188                         SSL_add_ext(x509, NID_subject_key_identifier, "hash");
189                         SSL_add_ext(x509, NID_netscape_comment, "Generated from umurmur");
190
191                         X509_sign(x509, pkey, EVP_md5());
192
193                         SSL_writecert(crt, x509);
194                         SSL_writekey(key, rsa);
195
196                         SSL_CTX_use_certificate(context, x509);
197                 } else {
198                   pkey = EVP_PKEY_new();
199                   EVP_PKEY_assign_RSA(pkey, rsa);
200                 }
201
202                 SSL_CTX_use_PrivateKey(context, pkey);
203
204         } else {
205                 Log_fatal("Failed to initialize TLS context.");
206         }
207
208 }
209
210 void SSLi_init(void)
211 {
212         SSL *ssl;
213         int i, offset = 0, cipherstringlen = 0;
214         STACK_OF(SSL_CIPHER) *cipherlist = NULL, *cipherlist_new = NULL;
215         SSL_CIPHER *cipher;
216         char *cipherstring;
217
218         SSL_library_init();
219         OpenSSL_add_all_algorithms();
220         SSL_load_error_strings();
221         ERR_load_crypto_strings();
222
223         context = SSL_CTX_new(SSLv23_server_method());
224         if (context == NULL)
225         {
226                 ERR_print_errors_fp(stderr);
227                 abort();
228         }
229
230         char const * sslCAPath = getStrConf(CAPATH);
231         if(sslCAPath != NULL)
232         {
233                 SSL_CTX_load_verify_locations(context, NULL, sslCAPath);
234         }
235
236         SSL_initializeCert();
237
238         /* Set cipher list */
239         ssl = SSL_new(context);
240         cipherlist = (STACK_OF(SSL_CIPHER) *) SSL_get_ciphers(ssl);
241         cipherlist_new = (STACK_OF(SSL_CIPHER) *) sk_SSL_CIPHER_new_null();
242
243         for ( i = 0; (cipher = sk_SSL_CIPHER_value(cipherlist, i)) != NULL; i++) {
244                 if (SSL_CIPHER_get_bits(cipher, NULL) >= 128) {
245                         sk_SSL_CIPHER_push(cipherlist_new, cipher);
246                 }
247         }
248         Log_debug("List of ciphers:");
249         if (cipherlist_new) {
250                 for (i = 0; (cipher = sk_SSL_CIPHER_value(cipherlist_new, i)) != NULL; i++) {
251                         Log_debug("%s", SSL_CIPHER_get_name(cipher));
252                         cipherstringlen += strlen(SSL_CIPHER_get_name(cipher)) + 1;
253                 }
254                 cipherstring = Memory_safeMalloc(1, cipherstringlen + 1);
255                 for (i = 0; (cipher = sk_SSL_CIPHER_value(cipherlist_new, i)) != NULL; i++) {
256                         offset += sprintf(cipherstring + offset, "%s:", SSL_CIPHER_get_name(cipher));
257                 }
258         }
259
260         if (cipherlist_new)
261                 sk_SSL_CIPHER_free(cipherlist_new);
262
263         if (strlen(cipherstring) == 0)
264                 Log_fatal("No suitable ciphers found!");
265
266         if (SSL_CTX_set_cipher_list(context, cipherstring) == 0)
267                 Log_fatal("Failed to set cipher list!");
268
269         free(cipherstring);
270
271         SSL_CTX_set_verify(context, SSL_VERIFY_PEER|SSL_VERIFY_CLIENT_ONCE,
272                            verify_callback);
273
274         SSL_free(ssl);
275         Log_info("OpenSSL library initialized");
276
277 }
278
279 void SSLi_deinit(void)
280 {
281         SSL_CTX_free(context);
282         EVP_cleanup();
283 }
284
285 int SSLi_nonblockaccept(SSL_handle_t *ssl, bool_t *SSLready)
286 {
287         int rc;
288         rc = SSL_accept(ssl);
289         if (rc < 0) {
290                 if (SSL_get_error(ssl, rc) == SSL_ERROR_WANT_READ ||
291                         SSL_get_error(ssl, rc) == SSL_ERROR_WANT_WRITE) {
292                         Log_debug("SSL not ready");
293                         return 0;
294                 } else {
295                         Log_warn("SSL error: %s", ERR_error_string(SSL_get_error(ssl, rc), NULL));
296                         return -1;
297                 }
298         }
299         *SSLready = true;
300         return 0;
301 }
302
303 SSL_handle_t *SSLi_newconnection(int *fd, bool_t *SSLready)
304 {
305         SSL *ssl;
306
307         *SSLready = false;
308         ssl = SSL_new(context);
309         SSL_set_fd(ssl, *fd);
310         if (SSLi_nonblockaccept(ssl, SSLready) < 0) {
311                 SSL_free(ssl);
312                 return NULL;
313         }
314         return ssl;
315 }
316
317 /* Create SHA1 of last certificate in the peer's chain. */
318 bool_t SSLi_getSHA1Hash(SSL_handle_t *ssl, uint8_t *hash)
319 {
320         X509 *x509;
321         uint8_t *buf, *p;
322         int len;
323
324         x509 = SSL_get_peer_certificate(ssl);
325         if (!x509) {
326                 return false;
327         }
328
329         len = i2d_X509(x509, NULL);
330         buf = Memory_safeMalloc(1, len);
331
332         p = buf;
333         i2d_X509(x509, &p);
334
335         SHA1(buf, len, hash);
336         free(buf);
337         return true;
338 }
339
340 void SSLi_closeconnection(SSL_handle_t *ssl)
341 {
342         SSL_free(ssl);
343 }
344
345 void SSLi_shutdown(SSL_handle_t *ssl)
346 {
347         SSL_shutdown(ssl);
348 }
349
350 int SSLi_read(SSL_handle_t *ssl, uint8_t *buf, int len)
351 {
352         return SSL_read(ssl, buf, len);
353 }
354
355 int SSLi_write(SSL_handle_t *ssl, uint8_t *buf, int len)
356 {
357         return SSL_write(ssl, buf, len);
358 }
359
360 int SSLi_get_error(SSL_handle_t *ssl, int code)
361 {
362         return SSL_get_error(ssl, code);
363 }
364
365 bool_t SSLi_data_pending(SSL_handle_t *ssl)
366 {
367         return SSL_pending(ssl);
368 }
369
370 void SSLi_free(SSL_handle_t *ssl)
371 {
372         SSL_free(ssl);
373 }
374
375 static int verify_callback(int preverify_ok, X509_STORE_CTX *ctx)
376 {
377         char    buf[256];
378         X509   *err_cert;
379         int     err, depth;
380         SSL    *ssl;
381
382     err_cert = X509_STORE_CTX_get_current_cert(ctx);
383     err = X509_STORE_CTX_get_error(ctx);
384     depth = X509_STORE_CTX_get_error_depth(ctx);
385
386     ssl = X509_STORE_CTX_get_ex_data(ctx, SSL_get_ex_data_X509_STORE_CTX_idx());
387     X509_NAME_oneline(X509_get_subject_name(err_cert), buf, 256);
388
389     if (depth > 5) {
390         preverify_ok = 0;
391         err = X509_V_ERR_CERT_CHAIN_TOO_LONG;
392         X509_STORE_CTX_set_error(ctx, err);
393     }
394     if (!preverify_ok) {
395             Log_warn("SSL: verify error:num=%d:%s:depth=%d:%s\n", err,
396                      X509_verify_cert_error_string(err), depth, buf);
397     }
398     /*
399      * At this point, err contains the last verification error. We can use
400      * it for something special
401      */
402     if (!preverify_ok && (err == X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT)) {
403             X509_NAME_oneline(X509_get_issuer_name(ctx->current_cert), buf, 256);
404             Log_warn("issuer= %s", buf);
405     }
406     return 1;
407 }