Annotation of src/usr.bin/openssl/s_server.c, Revision 1.44
1.44 ! tb 1: /* $OpenBSD: s_server.c,v 1.43 2020/07/27 13:46:48 inoguchi Exp $ */
1.1 jsing 2: /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com)
3: * All rights reserved.
4: *
5: * This package is an SSL implementation written
6: * by Eric Young (eay@cryptsoft.com).
7: * The implementation was written so as to conform with Netscapes SSL.
8: *
9: * This library is free for commercial and non-commercial use as long as
10: * the following conditions are aheared to. The following conditions
11: * apply to all code found in this distribution, be it the RC4, RSA,
12: * lhash, DES, etc., code; not just the SSL code. The SSL documentation
13: * included with this distribution is covered by the same copyright terms
14: * except that the holder is Tim Hudson (tjh@cryptsoft.com).
15: *
16: * Copyright remains Eric Young's, and as such any Copyright notices in
17: * the code are not to be removed.
18: * If this package is used in a product, Eric Young should be given attribution
19: * as the author of the parts of the library used.
20: * This can be in the form of a textual message at program startup or
21: * in documentation (online or textual) provided with the package.
22: *
23: * Redistribution and use in source and binary forms, with or without
24: * modification, are permitted provided that the following conditions
25: * are met:
26: * 1. Redistributions of source code must retain the copyright
27: * notice, this list of conditions and the following disclaimer.
28: * 2. Redistributions in binary form must reproduce the above copyright
29: * notice, this list of conditions and the following disclaimer in the
30: * documentation and/or other materials provided with the distribution.
31: * 3. All advertising materials mentioning features or use of this software
32: * must display the following acknowledgement:
33: * "This product includes cryptographic software written by
34: * Eric Young (eay@cryptsoft.com)"
35: * The word 'cryptographic' can be left out if the rouines from the library
36: * being used are not cryptographic related :-).
37: * 4. If you include any Windows specific code (or a derivative thereof) from
38: * the apps directory (application code) you must include an acknowledgement:
39: * "This product includes software written by Tim Hudson (tjh@cryptsoft.com)"
40: *
41: * THIS SOFTWARE IS PROVIDED BY ERIC YOUNG ``AS IS'' AND
42: * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
43: * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
44: * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
45: * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
46: * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
47: * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
48: * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
49: * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
50: * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
51: * SUCH DAMAGE.
52: *
53: * The licence and distribution terms for any publically available version or
54: * derivative of this code cannot be changed. i.e. this code cannot simply be
55: * copied and put under another distribution licence
56: * [including the GNU Public Licence.]
57: */
58: /* ====================================================================
59: * Copyright (c) 1998-2006 The OpenSSL Project. All rights reserved.
60: *
61: * Redistribution and use in source and binary forms, with or without
62: * modification, are permitted provided that the following conditions
63: * are met:
64: *
65: * 1. Redistributions of source code must retain the above copyright
66: * notice, this list of conditions and the following disclaimer.
67: *
68: * 2. Redistributions in binary form must reproduce the above copyright
69: * notice, this list of conditions and the following disclaimer in
70: * the documentation and/or other materials provided with the
71: * distribution.
72: *
73: * 3. All advertising materials mentioning features or use of this
74: * software must display the following acknowledgment:
75: * "This product includes software developed by the OpenSSL Project
76: * for use in the OpenSSL Toolkit. (http://www.openssl.org/)"
77: *
78: * 4. The names "OpenSSL Toolkit" and "OpenSSL Project" must not be used to
79: * endorse or promote products derived from this software without
80: * prior written permission. For written permission, please contact
81: * openssl-core@openssl.org.
82: *
83: * 5. Products derived from this software may not be called "OpenSSL"
84: * nor may "OpenSSL" appear in their names without prior written
85: * permission of the OpenSSL Project.
86: *
87: * 6. Redistributions of any form whatsoever must retain the following
88: * acknowledgment:
89: * "This product includes software developed by the OpenSSL Project
90: * for use in the OpenSSL Toolkit (http://www.openssl.org/)"
91: *
92: * THIS SOFTWARE IS PROVIDED BY THE OpenSSL PROJECT ``AS IS'' AND ANY
93: * EXPRESSED OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
94: * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
95: * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE OpenSSL PROJECT OR
96: * ITS CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
97: * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
98: * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
99: * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
100: * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
101: * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
102: * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED
103: * OF THE POSSIBILITY OF SUCH DAMAGE.
104: * ====================================================================
105: *
106: * This product includes cryptographic software written by Eric Young
107: * (eay@cryptsoft.com). This product includes software written by Tim
108: * Hudson (tjh@cryptsoft.com).
109: *
110: */
111: /* ====================================================================
112: * Copyright 2002 Sun Microsystems, Inc. ALL RIGHTS RESERVED.
113: * ECC cipher suite support in OpenSSL originally developed by
114: * SUN MICROSYSTEMS, INC., and contributed to the OpenSSL project.
115: */
116: /* ====================================================================
117: * Copyright 2005 Nokia. All rights reserved.
118: *
119: * The portions of the attached software ("Contribution") is developed by
120: * Nokia Corporation and is licensed pursuant to the OpenSSL open source
121: * license.
122: *
123: * The Contribution, originally written by Mika Kousa and Pasi Eronen of
124: * Nokia Corporation, consists of the "PSK" (Pre-Shared Key) ciphersuites
125: * support (see RFC 4279) to OpenSSL.
126: *
127: * No patent licenses or other rights except those expressly stated in
128: * the OpenSSL open source license shall be deemed granted or received
129: * expressly, by implication, estoppel, or otherwise.
130: *
131: * No assurances are provided by Nokia that the Contribution does not
132: * infringe the patent or other intellectual property rights of any third
133: * party or that the license provides you with all the necessary rights
134: * to make use of the Contribution.
135: *
136: * THE SOFTWARE IS PROVIDED "AS IS" WITHOUT WARRANTY OF ANY KIND. IN
137: * ADDITION TO THE DISCLAIMERS INCLUDED IN THE LICENSE, NOKIA
138: * SPECIFICALLY DISCLAIMS ANY LIABILITY FOR CLAIMS BROUGHT BY YOU OR ANY
139: * OTHER ENTITY BASED ON INFRINGEMENT OF INTELLECTUAL PROPERTY RIGHTS OR
140: * OTHERWISE.
141: */
142:
143: /* Until the key-gen callbacks are modified to use newer prototypes, we allow
144: * deprecated functions for openssl-internal code */
145: #ifdef OPENSSL_NO_DEPRECATED
146: #undef OPENSSL_NO_DEPRECATED
147: #endif
148:
149: #include <sys/types.h>
150: #include <sys/socket.h>
151:
152: #include <assert.h>
153: #include <ctype.h>
154: #include <stdio.h>
155: #include <stdlib.h>
156: #include <limits.h>
157: #include <string.h>
158: #include <unistd.h>
1.7 deraadt 159: #include <poll.h>
1.1 jsing 160:
161: #include "apps.h"
162:
163: #include <openssl/bn.h>
164: #include <openssl/err.h>
165: #include <openssl/lhash.h>
166: #include <openssl/ocsp.h>
167: #include <openssl/pem.h>
168: #include <openssl/ssl.h>
169: #include <openssl/x509.h>
170:
171: #ifndef OPENSSL_NO_DH
172: #include <openssl/dh.h>
173: #endif
174:
175: #include <openssl/rsa.h>
176:
177: #include "s_apps.h"
178: #include "timeouts.h"
179:
1.42 inoguchi 180: static void s_server_init(void);
181: static void sv_usage(void);
182: static void print_stats(BIO *bp, SSL_CTX *ctx);
1.1 jsing 183: static int sv_body(char *hostname, int s, unsigned char *context);
184: static void close_accept_socket(void);
1.41 inoguchi 185: static int init_ssl_connection(SSL *s);
1.1 jsing 186: #ifndef OPENSSL_NO_DH
187: static DH *load_dh_param(const char *dhfile);
188: #endif
1.42 inoguchi 189: static int www_body(char *hostname, int s, unsigned char *context);
190: static int generate_session_id(const SSL *ssl, unsigned char *id,
191: unsigned int *id_len);
192: static int ssl_servername_cb(SSL *s, int *ad, void *arg);
193: static int cert_status_cb(SSL * s, void *arg);
194: static int alpn_cb(SSL *s, const unsigned char **out, unsigned char *outlen,
195: const unsigned char *in, unsigned int inlen, void *arg);
1.1 jsing 196: /* static int load_CA(SSL_CTX *ctx, char *file);*/
197:
198: #define BUFSIZZ 16*1024
199: static int bufsize = BUFSIZZ;
200: static int accept_socket = -1;
201:
202: #define TEST_CERT "server.pem"
203: #define TEST_CERT2 "server2.pem"
204:
205: static int s_server_session_id_context = 1; /* anything will do */
206: static SSL_CTX *ctx = NULL;
207: static SSL_CTX *ctx2 = NULL;
208: static BIO *bio_s_out = NULL;
1.42 inoguchi 209:
210: static int local_argc = 0;
211: static char **local_argv;
1.1 jsing 212:
1.39 inoguchi 213: /* This is a context that we pass to callbacks */
214: typedef struct tlsextctx_st {
215: char *servername;
216: BIO *biodebug;
217: int extension_error;
218: } tlsextctx;
1.1 jsing 219:
1.39 inoguchi 220: /* Structure passed to cert status callback */
221: typedef struct tlsextstatusctx_st {
222: /* Default responder to use */
223: char *host, *path, *port;
224: int use_ssl;
225: int timeout;
226: BIO *err;
227: int verbose;
228: } tlsextstatusctx;
229:
1.42 inoguchi 230: /* This the context that we pass to alpn_cb */
231: typedef struct tlsextalpnctx_st {
232: unsigned char *data;
233: unsigned short len;
234: } tlsextalpnctx;
235:
1.39 inoguchi 236: static struct {
237: char *alpn_in;
238: char *npn_in; /* Ignored. */
239: int bugs;
240: char *CAfile;
241: char *CApath;
242: #ifndef OPENSSL_NO_DTLS1
243: int cert_chain;
244: #endif
1.40 inoguchi 245: char *cert_file;
246: char *cert_file2;
247: int cert_format;
1.39 inoguchi 248: char *cipher;
249: unsigned char *context;
1.40 inoguchi 250: int crlf;
251: char *dcert_file;
252: int dcert_format;
253: int debug;
1.39 inoguchi 254: char *dhfile;
1.40 inoguchi 255: char *dkey_file;
256: int dkey_format;
1.39 inoguchi 257: char *dpassarg;
258: int enable_timeouts;
259: const char *errstr;
260: char *groups_in;
1.40 inoguchi 261: char *key_file;
262: char *key_file2;
263: int key_format;
1.39 inoguchi 264: char *keymatexportlabel;
265: int keymatexportlen;
266: uint16_t max_version;
267: uint16_t min_version;
268: const SSL_METHOD *meth;
1.40 inoguchi 269: int msg;
1.39 inoguchi 270: char *named_curve;
1.40 inoguchi 271: int nbio;
272: int nbio_test;
1.39 inoguchi 273: int no_cache;
274: int nocert;
275: int no_dhe;
276: int no_ecdhe;
277: int no_tmp_rsa; /* No-op. */
278: int off;
279: char *passarg;
280: short port;
1.40 inoguchi 281: int quiet;
282: int server_verify;
1.39 inoguchi 283: char *session_id_prefix;
284: long socket_mtu;
285: int socket_type;
286: #ifndef OPENSSL_NO_SRTP
287: char *srtp_profiles;
288: #endif
289: int state;
290: tlsextstatusctx tlscstatp;
291: tlsextctx tlsextcbp;
1.40 inoguchi 292: int tlsextdebug;
293: int tlsextstatus;
1.39 inoguchi 294: X509_VERIFY_PARAM *vpm;
295: int www;
296: } s_server_config;
297:
298: static int
299: s_server_opt_context(char *arg)
300: {
301: s_server_config.context = (unsigned char *) arg;
302: return (0);
303: }
304:
305: static int
306: s_server_opt_keymatexportlen(char *arg)
307: {
308: s_server_config.keymatexportlen = strtonum(arg, 1, INT_MAX,
309: &s_server_config.errstr);
310: if (s_server_config.errstr != NULL) {
311: BIO_printf(bio_err, "invalid argument %s: %s\n",
312: arg, s_server_config.errstr);
313: return (1);
314: }
315: return (0);
316: }
1.1 jsing 317:
318: #ifndef OPENSSL_NO_DTLS1
1.39 inoguchi 319: static int
320: s_server_opt_mtu(char *arg)
321: {
322: s_server_config.socket_mtu = strtonum(arg, 0, LONG_MAX,
323: &s_server_config.errstr);
324: if (s_server_config.errstr != NULL) {
325: BIO_printf(bio_err, "invalid argument %s: %s\n",
326: arg, s_server_config.errstr);
327: return (1);
328: }
329: return (0);
330: }
331:
332: static int
333: s_server_protocol_version_dtls1(void)
334: {
335: s_server_config.meth = DTLS_server_method();
336: s_server_config.socket_type = SOCK_DGRAM;
337: return (0);
338: }
1.1 jsing 339: #endif
340:
1.39 inoguchi 341: static int
342: s_server_protocol_version_tls1(void)
343: {
344: s_server_config.min_version = TLS1_VERSION;
345: s_server_config.max_version = TLS1_VERSION;
346: return (0);
347: }
348:
349: static int
350: s_server_protocol_version_tls1_1(void)
351: {
352: s_server_config.min_version = TLS1_1_VERSION;
353: s_server_config.max_version = TLS1_1_VERSION;
354: return (0);
355: }
356:
357: static int
358: s_server_protocol_version_tls1_2(void)
359: {
360: s_server_config.min_version = TLS1_2_VERSION;
361: s_server_config.max_version = TLS1_2_VERSION;
362: return (0);
363: }
364:
365: static int
366: s_server_protocol_version_tls1_3(void)
367: {
368: s_server_config.min_version = TLS1_3_VERSION;
369: s_server_config.max_version = TLS1_3_VERSION;
370: return (0);
371: }
372:
373: static int
374: s_server_opt_nbio_test(void)
375: {
1.40 inoguchi 376: s_server_config.nbio = 1;
377: s_server_config.nbio_test = 1;
1.39 inoguchi 378: return (0);
379: }
380:
381: static int
382: s_server_opt_port(char *arg)
383: {
384: if (!extract_port(arg, &s_server_config.port))
385: return (1);
386: return (0);
387: }
388:
389: static int
390: s_server_opt_status_timeout(char *arg)
391: {
1.40 inoguchi 392: s_server_config.tlsextstatus = 1;
1.39 inoguchi 393: s_server_config.tlscstatp.timeout = strtonum(arg, 0, INT_MAX,
394: &s_server_config.errstr);
395: if (s_server_config.errstr != NULL) {
396: BIO_printf(bio_err, "invalid argument %s: %s\n",
397: arg, s_server_config.errstr);
398: return (1);
399: }
400: return (0);
401: }
402:
403: static int
404: s_server_opt_status_url(char *arg)
405: {
1.40 inoguchi 406: s_server_config.tlsextstatus = 1;
1.39 inoguchi 407: if (!OCSP_parse_url(arg, &s_server_config.tlscstatp.host,
408: &s_server_config.tlscstatp.port, &s_server_config.tlscstatp.path,
409: &s_server_config.tlscstatp.use_ssl)) {
410: BIO_printf(bio_err, "Error parsing URL\n");
411: return (1);
412: }
413: return (0);
414: }
415:
416: static int
417: s_server_opt_status_verbose(void)
418: {
1.40 inoguchi 419: s_server_config.tlsextstatus = 1;
1.39 inoguchi 420: s_server_config.tlscstatp.verbose = 1;
421: return (0);
422: }
423:
424: static int
425: s_server_opt_verify(char *arg)
426: {
1.40 inoguchi 427: s_server_config.server_verify = SSL_VERIFY_PEER |
1.39 inoguchi 428: SSL_VERIFY_CLIENT_ONCE;
429: verify_depth = strtonum(arg, 0, INT_MAX, &s_server_config.errstr);
430: if (s_server_config.errstr != NULL) {
431: BIO_printf(bio_err, "invalid argument %s: %s\n",
432: arg, s_server_config.errstr);
433: return (1);
434: }
435: BIO_printf(bio_err, "verify depth is %d\n", verify_depth);
436: return (0);
437: }
438:
439: static int
440: s_server_opt_verify_fail(char *arg)
441: {
1.40 inoguchi 442: s_server_config.server_verify = SSL_VERIFY_PEER |
1.39 inoguchi 443: SSL_VERIFY_FAIL_IF_NO_PEER_CERT | SSL_VERIFY_CLIENT_ONCE;
444: verify_depth = strtonum(arg, 0, INT_MAX, &s_server_config.errstr);
445: if (s_server_config.errstr != NULL) {
446: BIO_printf(bio_err, "invalid argument %s: %s\n",
447: arg, s_server_config.errstr);
448: return (1);
449: }
450: BIO_printf(bio_err, "verify depth is %d, must return a certificate\n",
451: verify_depth);
452: return (0);
453: }
454:
455: static int
456: s_server_opt_verify_param(int argc, char **argv, int *argsused)
457: {
458: char **pargs = argv;
459: int pargc = argc;
460: int badarg = 0;
1.1 jsing 461:
1.39 inoguchi 462: if (!args_verify(&pargs, &pargc, &badarg, bio_err,
463: &s_server_config.vpm)) {
464: BIO_printf(bio_err, "unknown option %s\n", *argv);
465: return (1);
466: }
467: if (badarg)
468: return (1);
469:
470: *argsused = argc - pargc;
471: return (0);
472: }
1.1 jsing 473:
1.39 inoguchi 474: static const struct option s_server_options[] = {
1.44 ! tb 475: {
! 476: .name = "4",
! 477: .type = OPTION_DISCARD,
! 478: },
! 479: {
! 480: .name = "6",
! 481: .type = OPTION_DISCARD,
! 482: },
1.39 inoguchi 483: {
484: .name = "accept",
485: .argname = "port",
486: .desc = "Port to accept on (default is 4433)",
487: .type = OPTION_ARG_FUNC,
488: .opt.argfunc = s_server_opt_port,
489: },
490: {
491: .name = "alpn",
492: .argname = "protocols",
493: .desc = "Set the advertised protocols for the ALPN extension"
494: " (comma-separated list)",
495: .type = OPTION_ARG,
496: .opt.arg = &s_server_config.alpn_in,
497: },
498: {
499: .name = "bugs",
500: .desc = "Turn on SSL bug compatibility",
501: .type = OPTION_FLAG,
502: .opt.flag = &s_server_config.bugs,
503: },
504: {
505: .name = "CAfile",
506: .argname = "file",
507: .desc = "PEM format file of CA certificates",
508: .type = OPTION_ARG,
509: .opt.arg = &s_server_config.CAfile,
510: },
511: {
512: .name = "CApath",
513: .argname = "directory",
514: .desc = "PEM format directory of CA certificates",
515: .type = OPTION_ARG,
516: .opt.arg = &s_server_config.CApath,
517: },
518: {
519: .name = "cert",
520: .argname = "file",
521: .desc = "Certificate file to use\n"
522: "(default is " TEST_CERT ")",
523: .type = OPTION_ARG,
1.40 inoguchi 524: .opt.arg = &s_server_config.cert_file,
1.39 inoguchi 525: },
526: {
527: .name = "cert2",
528: .argname = "file",
529: .desc = "Certificate file to use for servername\n"
530: "(default is " TEST_CERT2 ")",
531: .type = OPTION_ARG,
1.40 inoguchi 532: .opt.arg = &s_server_config.cert_file2,
1.39 inoguchi 533: },
534: {
535: .name = "certform",
536: .argname = "fmt",
537: .desc = "Certificate format (PEM or DER) PEM default",
538: .type = OPTION_ARG_FORMAT,
1.40 inoguchi 539: .opt.value = &s_server_config.cert_format,
1.39 inoguchi 540: },
541: #ifndef OPENSSL_NO_DTLS1
542: {
543: .name = "chain",
544: .type = OPTION_FLAG,
545: .opt.flag = &s_server_config.cert_chain,
546: },
547: #endif
548: {
549: .name = "cipher",
550: .argname = "list",
551: .desc = "List of ciphers to enable (see `openssl ciphers`)",
552: .type = OPTION_ARG,
553: .opt.arg = &s_server_config.cipher,
554: },
555: {
556: .name = "context",
557: .argname = "id",
558: .desc = "Set session ID context",
559: .type = OPTION_ARG_FUNC,
560: .opt.argfunc = s_server_opt_context,
561: },
562: {
563: .name = "crlf",
564: .desc = "Convert LF from terminal into CRLF",
565: .type = OPTION_FLAG,
1.40 inoguchi 566: .opt.flag = &s_server_config.crlf,
1.39 inoguchi 567: },
568: {
569: .name = "dcert",
570: .argname = "file",
571: .desc = "Second certificate file to use (usually for DSA)",
572: .type = OPTION_ARG,
1.40 inoguchi 573: .opt.arg = &s_server_config.dcert_file,
1.39 inoguchi 574: },
575: {
576: .name = "dcertform",
577: .argname = "fmt",
578: .desc = "Second certificate format (PEM or DER) PEM default",
579: .type = OPTION_ARG_FORMAT,
1.40 inoguchi 580: .opt.value = &s_server_config.dcert_format,
1.39 inoguchi 581: },
582: {
583: .name = "debug",
584: .desc = "Print more output",
585: .type = OPTION_FLAG,
1.40 inoguchi 586: .opt.flag = &s_server_config.debug,
1.39 inoguchi 587: },
588: {
589: .name = "dhparam",
590: .argname = "file",
591: .desc = "DH parameter file to use, in cert file if not specified",
592: .type = OPTION_ARG,
593: .opt.arg = &s_server_config.dhfile,
594: },
595: {
596: .name = "dkey",
597: .argname = "file",
598: .desc = "Second private key file to use (usually for DSA)",
599: .type = OPTION_ARG,
1.40 inoguchi 600: .opt.arg = &s_server_config.dkey_file,
1.39 inoguchi 601: },
602: {
603: .name = "dkeyform",
604: .argname = "fmt",
605: .desc = "Second key format (PEM or DER) PEM default",
606: .type = OPTION_ARG_FORMAT,
1.40 inoguchi 607: .opt.value = &s_server_config.dkey_format,
1.39 inoguchi 608: },
609: {
610: .name = "dpass",
611: .argname = "arg",
612: .desc = "Second private key file pass phrase source",
613: .type = OPTION_ARG,
614: .opt.arg = &s_server_config.dpassarg,
615: },
616: #ifndef OPENSSL_NO_DTLS1
617: {
618: .name = "dtls1",
619: .desc = "Just talk DTLSv1",
620: .type = OPTION_FUNC,
621: .opt.func = s_server_protocol_version_dtls1,
622: },
623: #endif
624: {
625: .name = "groups",
626: .argname = "list",
627: .desc = "Specify EC groups (colon-separated list)",
628: .type = OPTION_ARG,
629: .opt.arg = &s_server_config.groups_in,
630: },
631: {
632: .name = "HTTP",
633: .desc = "Respond to a 'GET /<path> HTTP/1.0' with file ./<path>",
634: .type = OPTION_VALUE,
635: .opt.value = &s_server_config.www,
636: .value = 3,
637: },
638: {
639: .name = "id_prefix",
640: .argname = "arg",
641: .desc = "Generate SSL/TLS session IDs prefixed by 'arg'",
642: .type = OPTION_ARG,
643: .opt.arg = &s_server_config.session_id_prefix,
644: },
645: {
646: .name = "key",
647: .argname = "file",
648: .desc = "Private Key file to use, in cert file if\n"
649: "not specified (default is " TEST_CERT ")",
650: .type = OPTION_ARG,
1.40 inoguchi 651: .opt.arg = &s_server_config.key_file,
1.39 inoguchi 652: },
653: {
654: .name = "key2",
655: .argname = "file",
656: .desc = "Private Key file to use for servername, in cert file if\n"
657: "not specified (default is " TEST_CERT2 ")",
658: .type = OPTION_ARG,
1.40 inoguchi 659: .opt.arg = &s_server_config.key_file2,
1.39 inoguchi 660: },
661: {
662: .name = "keyform",
663: .argname = "fmt",
664: .desc = "Key format (PEM or DER) PEM default",
665: .type = OPTION_ARG_FORMAT,
1.40 inoguchi 666: .opt.value = &s_server_config.key_format,
1.39 inoguchi 667: },
668: {
669: .name = "keymatexport",
670: .argname = "label",
671: .desc = "Export keying material using label",
672: .type = OPTION_ARG,
673: .opt.arg = &s_server_config.keymatexportlabel,
674: },
675: {
676: .name = "keymatexportlen",
677: .argname = "len",
678: .desc = "Export len bytes of keying material (default 20)",
679: .type = OPTION_ARG_FUNC,
680: .opt.argfunc = s_server_opt_keymatexportlen,
681: },
682: {
683: .name = "legacy_renegotiation",
684: .type = OPTION_DISCARD,
685: },
686: {
687: .name = "msg",
688: .desc = "Show protocol messages",
689: .type = OPTION_FLAG,
1.40 inoguchi 690: .opt.flag = &s_server_config.msg,
1.39 inoguchi 691: },
692: #ifndef OPENSSL_NO_DTLS1
693: {
694: .name = "mtu",
695: .argname = "mtu",
696: .desc = "Set link layer MTU",
697: .type = OPTION_ARG_FUNC,
698: .opt.argfunc = s_server_opt_mtu,
699: },
700: #endif
701: {
702: .name = "named_curve",
703: .argname = "arg",
704: .type = OPTION_ARG,
705: .opt.arg = &s_server_config.named_curve,
706: },
707: {
708: .name = "nbio",
709: .desc = "Run with non-blocking I/O",
710: .type = OPTION_FLAG,
1.40 inoguchi 711: .opt.flag = &s_server_config.nbio,
1.39 inoguchi 712: },
713: {
714: .name = "nbio_test",
715: .desc = "Test with the non-blocking test bio",
716: .type = OPTION_FUNC,
717: .opt.func = s_server_opt_nbio_test,
718: },
719: {
720: .name = "nextprotoneg",
721: .argname = "arg",
722: .type = OPTION_ARG,
723: .opt.arg = &s_server_config.npn_in, /* Ignored. */
724: },
725: {
726: .name = "no_cache",
727: .desc = "Disable session cache",
728: .type = OPTION_FLAG,
729: .opt.flag = &s_server_config.no_cache,
730: },
731: {
732: .name = "no_comp",
733: .desc = "Disable SSL/TLS compression",
734: .type = OPTION_VALUE_OR,
735: .opt.value = &s_server_config.off,
736: .value = SSL_OP_NO_COMPRESSION,
737: },
738: {
739: .name = "no_dhe",
740: .desc = "Disable ephemeral DH",
741: .type = OPTION_FLAG,
742: .opt.flag = &s_server_config.no_dhe,
743: },
744: {
745: .name = "no_ecdhe",
746: .desc = "Disable ephemeral ECDH",
747: .type = OPTION_FLAG,
748: .opt.flag = &s_server_config.no_ecdhe,
749: },
750: {
751: .name = "no_ticket",
752: .desc = "Disable use of RFC4507bis session tickets",
753: .type = OPTION_VALUE_OR,
754: .opt.value = &s_server_config.off,
755: .value = SSL_OP_NO_TICKET,
756: },
757: {
758: .name = "no_ssl2",
759: .type = OPTION_VALUE_OR,
760: .opt.value = &s_server_config.off,
761: .value = SSL_OP_NO_SSLv2,
762: },
763: {
764: .name = "no_ssl3",
765: .type = OPTION_VALUE_OR,
766: .opt.value = &s_server_config.off,
767: .value = SSL_OP_NO_SSLv3,
768: },
769: {
770: .name = "no_tls1",
771: .desc = "Just disable TLSv1",
772: .type = OPTION_VALUE_OR,
773: .opt.value = &s_server_config.off,
774: .value = SSL_OP_NO_TLSv1,
775: },
776: {
777: .name = "no_tls1_1",
778: .desc = "Just disable TLSv1.1",
779: .type = OPTION_VALUE_OR,
780: .opt.value = &s_server_config.off,
781: .value = SSL_OP_NO_TLSv1_1,
782: },
783: {
784: .name = "no_tls1_2",
785: .desc = "Just disable TLSv1.2",
786: .type = OPTION_VALUE_OR,
787: .opt.value = &s_server_config.off,
788: .value = SSL_OP_NO_TLSv1_2,
789: },
790: {
791: .name = "no_tls1_3",
792: .desc = "Just disable TLSv1.3",
793: .type = OPTION_VALUE_OR,
794: .opt.value = &s_server_config.off,
795: .value = SSL_OP_NO_TLSv1_3,
796: },
797: {
798: .name = "no_tmp_rsa",
799: .type = OPTION_DISCARD,
800: },
801: {
802: .name = "nocert",
803: .desc = "Don't use any certificates (Anon-DH)",
804: .type = OPTION_FLAG,
805: .opt.flag = &s_server_config.nocert,
806: },
807: {
808: .name = "pass",
809: .argname = "arg",
810: .desc = "Private key file pass phrase source",
811: .type = OPTION_ARG,
812: .opt.arg = &s_server_config.passarg,
813: },
814: {
815: .name = "port",
816: .argname = "port",
817: .type = OPTION_ARG_FUNC,
818: .opt.argfunc = s_server_opt_port,
819: },
820: {
821: .name = "quiet",
822: .desc = "Inhibit printing of session and certificate information",
823: .type = OPTION_FLAG,
1.40 inoguchi 824: .opt.flag = &s_server_config.quiet,
1.39 inoguchi 825: },
826: {
827: .name = "servername",
828: .argname = "name",
829: .desc = "Servername for HostName TLS extension",
830: .type = OPTION_ARG,
831: .opt.arg = &s_server_config.tlsextcbp.servername,
832: },
833: {
834: .name = "servername_fatal",
835: .desc = "On mismatch send fatal alert (default warning alert)",
836: .type = OPTION_VALUE,
837: .opt.value = &s_server_config.tlsextcbp.extension_error,
838: .value = SSL_TLSEXT_ERR_ALERT_FATAL,
839: },
840: {
841: .name = "serverpref",
842: .desc = "Use server's cipher preferences",
843: .type = OPTION_VALUE_OR,
844: .opt.value = &s_server_config.off,
845: .value = SSL_OP_CIPHER_SERVER_PREFERENCE,
846: },
847: {
848: .name = "state",
849: .desc = "Print the SSL states",
850: .type = OPTION_FLAG,
851: .opt.flag = &s_server_config.state,
852: },
853: {
854: .name = "status",
855: .desc = "Respond to certificate status requests",
856: .type = OPTION_FLAG,
1.40 inoguchi 857: .opt.flag = &s_server_config.tlsextstatus,
1.39 inoguchi 858: },
859: {
860: .name = "status_timeout",
861: .argname = "nsec",
862: .desc = "Status request responder timeout",
863: .type = OPTION_ARG_FUNC,
864: .opt.argfunc = s_server_opt_status_timeout,
865: },
866: {
867: .name = "status_url",
868: .argname = "url",
869: .desc = "Status request fallback URL",
870: .type = OPTION_ARG_FUNC,
871: .opt.argfunc = s_server_opt_status_url,
872: },
873: {
874: .name = "status_verbose",
875: .desc = "Enable status request verbose printout",
876: .type = OPTION_FUNC,
877: .opt.func = s_server_opt_status_verbose,
878: },
879: #ifndef OPENSSL_NO_DTLS1
880: {
881: .name = "timeout",
882: .desc = "Enable timeouts",
883: .type = OPTION_FLAG,
884: .opt.flag = &s_server_config.enable_timeouts,
885: },
886: #endif
887: {
888: .name = "tls1",
889: .desc = "Just talk TLSv1",
890: .type = OPTION_FUNC,
891: .opt.func = s_server_protocol_version_tls1,
892: },
893: {
894: .name = "tls1_1",
895: .desc = "Just talk TLSv1.1",
896: .type = OPTION_FUNC,
897: .opt.func = s_server_protocol_version_tls1_1,
898: },
899: {
900: .name = "tls1_2",
901: .desc = "Just talk TLSv1.2",
902: .type = OPTION_FUNC,
903: .opt.func = s_server_protocol_version_tls1_2,
904: },
905: {
906: .name = "tls1_3",
907: .desc = "Just talk TLSv1.3",
908: .type = OPTION_FUNC,
909: .opt.func = s_server_protocol_version_tls1_3,
910: },
911: {
912: .name = "tlsextdebug",
913: .desc = "Hex dump of all TLS extensions received",
914: .type = OPTION_FLAG,
1.40 inoguchi 915: .opt.flag = &s_server_config.tlsextdebug,
1.39 inoguchi 916: },
917: #ifndef OPENSSL_NO_SRTP
918: {
919: .name = "use_srtp",
920: .argname = "profiles",
921: .desc = "Offer SRTP key management with a colon-separated profile list",
922: .type = OPTION_ARG,
923: .opt.arg = &s_server_config.srtp_profiles,
924: },
925: #endif
926: {
927: .name = "Verify",
928: .argname = "depth",
929: .desc = "Turn on peer certificate verification, must have a cert",
930: .type = OPTION_ARG_FUNC,
931: .opt.argfunc = s_server_opt_verify_fail,
932: },
933: {
934: .name = "verify",
935: .argname = "depth",
936: .desc = "Turn on peer certificate verification",
937: .type = OPTION_ARG_FUNC,
938: .opt.argfunc = s_server_opt_verify,
939: },
940: {
941: .name = "verify_return_error",
942: .desc = "Return verification error",
943: .type = OPTION_FLAG,
944: .opt.flag = &verify_return_error,
945: },
946: {
947: .name = "WWW",
948: .desc = "Respond to a 'GET /<path> HTTP/1.0' with file ./<path>",
949: .type = OPTION_VALUE,
950: .opt.value = &s_server_config.www,
951: .value = 2,
952: },
953: {
954: .name = "www",
955: .desc = "Respond to a 'GET /' with a status page",
956: .type = OPTION_VALUE,
957: .opt.value = &s_server_config.www,
958: .value = 1,
959: },
960: {
961: .name = NULL,
962: .desc = "",
963: .type = OPTION_ARGV_FUNC,
964: .opt.argvfunc = s_server_opt_verify_param,
965: },
966: { NULL },
967: };
1.1 jsing 968:
969: static void
970: s_server_init(void)
971: {
972: accept_socket = -1;
1.39 inoguchi 973: s_server_config.cipher = NULL;
1.40 inoguchi 974: s_server_config.server_verify = SSL_VERIFY_NONE;
975: s_server_config.dcert_file = NULL;
976: s_server_config.dkey_file = NULL;
977: s_server_config.cert_file = TEST_CERT;
978: s_server_config.key_file = NULL;
979: s_server_config.cert_file2 = TEST_CERT2;
980: s_server_config.key_file2 = NULL;
1.1 jsing 981: ctx2 = NULL;
1.40 inoguchi 982: s_server_config.nbio = 0;
983: s_server_config.nbio_test = 0;
1.1 jsing 984: ctx = NULL;
1.39 inoguchi 985: s_server_config.www = 0;
1.1 jsing 986:
987: bio_s_out = NULL;
1.40 inoguchi 988: s_server_config.debug = 0;
989: s_server_config.msg = 0;
990: s_server_config.quiet = 0;
1.1 jsing 991: }
992:
993: static void
994: sv_usage(void)
995: {
1.39 inoguchi 996: fprintf(stderr, "usage: s_server "
997: "[-accept port] [-alpn protocols] [-bugs] [-CAfile file]\n"
998: " [-CApath directory] [-cert file] [-cert2 file]\n"
999: " [-certform der | pem] [-cipher cipherlist]\n"
1000: " [-context id] [-crl_check] [-crl_check_all] [-crlf]\n"
1001: " [-dcert file] [-dcertform der | pem] [-debug]\n"
1002: " [-dhparam file] [-dkey file] [-dkeyform der | pem]\n"
1003: " [-dpass arg] [-dtls1] [-groups list] [-HTTP]\n"
1004: " [-id_prefix arg] [-key keyfile] [-key2 keyfile]\n"
1005: " [-keyform der | pem] [-keymatexport label]\n"
1006: " [-keymatexportlen len] [-msg] [-mtu mtu]\n"
1007: " [-named_curve arg] [-nbio] [-nbio_test] [-no_cache]\n"
1008: " [-no_dhe] [-no_ecdhe] [-no_ticket] [-no_tls1]\n"
1009: " [-no_tls1_1] [-no_tls1_2] [-no_tls1_3] [-no_tmp_rsa]\n"
1010: " [-nocert] [-pass arg] [-quiet] [-servername name]\n"
1011: " [-servername_fatal] [-serverpref] [-state] [-status]\n"
1012: " [-status_timeout nsec] [-status_url url]\n"
1013: " [-status_verbose] [-timeout] [-tls1] [-tls1_1]\n"
1014: " [-tls1_2] [-tls1_3] [-tlsextdebug] [-use_srtp profiles]\n"
1015: " [-Verify depth] [-verify depth] [-verify_return_error]\n"
1016: " [-WWW] [-www]\n");
1017: fprintf(stderr, "\n");
1018: options_usage(s_server_options);
1019: fprintf(stderr, "\n");
1.1 jsing 1020: }
1021:
1022: int
1023: s_server_main(int argc, char *argv[])
1024: {
1.39 inoguchi 1025: int badop = 0;
1.1 jsing 1026: int ret = 1;
1.39 inoguchi 1027: char *pass = NULL;
1028: char *dpass = NULL;
1.1 jsing 1029: X509 *s_cert = NULL, *s_dcert = NULL;
1030: EVP_PKEY *s_key = NULL, *s_dkey = NULL;
1031: EVP_PKEY *s_key2 = NULL;
1032: X509 *s_cert2 = NULL;
1.8 jsing 1033: tlsextalpnctx alpn_ctx = { NULL, 0 };
1.20 doug 1034:
1035: if (single_execution) {
1.25 deraadt 1036: if (pledge("stdio rpath inet dns tty", NULL) == -1) {
1.20 doug 1037: perror("pledge");
1.22 doug 1038: exit(1);
1039: }
1.20 doug 1040: }
1041:
1.39 inoguchi 1042: memset(&s_server_config, 0, sizeof(s_server_config));
1043: s_server_config.keymatexportlen = 20;
1044: s_server_config.meth = TLS_server_method();
1045: s_server_config.port = PORT;
1.40 inoguchi 1046: s_server_config.cert_file = TEST_CERT;
1047: s_server_config.cert_file2 = TEST_CERT2;
1048: s_server_config.cert_format = FORMAT_PEM;
1049: s_server_config.dcert_format = FORMAT_PEM;
1050: s_server_config.dkey_format = FORMAT_PEM;
1051: s_server_config.key_format = FORMAT_PEM;
1052: s_server_config.server_verify = SSL_VERIFY_NONE;
1.39 inoguchi 1053: s_server_config.socket_type = SOCK_STREAM;
1054: s_server_config.tlscstatp.timeout = -1;
1.43 inoguchi 1055: s_server_config.tlsextcbp.extension_error =
1056: SSL_TLSEXT_ERR_ALERT_WARNING;
1.1 jsing 1057:
1058: local_argc = argc;
1059: local_argv = argv;
1060:
1061: s_server_init();
1062:
1063: verify_depth = 0;
1064:
1.39 inoguchi 1065: if (options_parse(argc, argv, s_server_options, NULL, NULL) != 0) {
1066: badop = 1;
1067: goto bad;
1.1 jsing 1068: }
1069: if (badop) {
1.30 jsing 1070: bad:
1.39 inoguchi 1071: if (s_server_config.errstr == NULL)
1.1 jsing 1072: sv_usage();
1073: goto end;
1074: }
1075:
1.43 inoguchi 1076: if (!app_passwd(bio_err, s_server_config.passarg,
1077: s_server_config.dpassarg, &pass, &dpass)) {
1.1 jsing 1078: BIO_printf(bio_err, "Error getting password\n");
1079: goto end;
1080: }
1.40 inoguchi 1081: if (s_server_config.key_file == NULL)
1082: s_server_config.key_file = s_server_config.cert_file;
1083: if (s_server_config.key_file2 == NULL)
1084: s_server_config.key_file2 = s_server_config.cert_file2;
1.1 jsing 1085:
1.39 inoguchi 1086: if (s_server_config.nocert == 0) {
1.43 inoguchi 1087: s_key = load_key(bio_err, s_server_config.key_file,
1088: s_server_config.key_format, 0, pass,
1.1 jsing 1089: "server certificate private key file");
1090: if (!s_key) {
1091: ERR_print_errors(bio_err);
1092: goto end;
1093: }
1.43 inoguchi 1094: s_cert = load_cert(bio_err, s_server_config.cert_file,
1095: s_server_config.cert_format,
1.17 bcook 1096: NULL, "server certificate file");
1.1 jsing 1097:
1098: if (!s_cert) {
1099: ERR_print_errors(bio_err);
1100: goto end;
1101: }
1.39 inoguchi 1102: if (s_server_config.tlsextcbp.servername) {
1.43 inoguchi 1103: s_key2 = load_key(bio_err, s_server_config.key_file2,
1104: s_server_config.key_format, 0, pass,
1.1 jsing 1105: "second server certificate private key file");
1106: if (!s_key2) {
1107: ERR_print_errors(bio_err);
1108: goto end;
1109: }
1.43 inoguchi 1110: s_cert2 = load_cert(bio_err, s_server_config.cert_file2,
1111: s_server_config.cert_format,
1.17 bcook 1112: NULL, "second server certificate file");
1.1 jsing 1113:
1114: if (!s_cert2) {
1115: ERR_print_errors(bio_err);
1116: goto end;
1117: }
1118: }
1119: }
1.8 jsing 1120: alpn_ctx.data = NULL;
1.39 inoguchi 1121: if (s_server_config.alpn_in) {
1.8 jsing 1122: unsigned short len;
1.43 inoguchi 1123: alpn_ctx.data = next_protos_parse(&len,
1124: s_server_config.alpn_in);
1.8 jsing 1125: if (alpn_ctx.data == NULL)
1126: goto end;
1127: alpn_ctx.len = len;
1128: }
1.1 jsing 1129:
1.40 inoguchi 1130: if (s_server_config.dcert_file) {
1.1 jsing 1131:
1.40 inoguchi 1132: if (s_server_config.dkey_file == NULL)
1133: s_server_config.dkey_file = s_server_config.dcert_file;
1.1 jsing 1134:
1.43 inoguchi 1135: s_dkey = load_key(bio_err, s_server_config.dkey_file,
1136: s_server_config.dkey_format,
1.17 bcook 1137: 0, dpass, "second certificate private key file");
1.1 jsing 1138: if (!s_dkey) {
1139: ERR_print_errors(bio_err);
1140: goto end;
1141: }
1.43 inoguchi 1142: s_dcert = load_cert(bio_err, s_server_config.dcert_file,
1143: s_server_config.dcert_format,
1.17 bcook 1144: NULL, "second server certificate file");
1.1 jsing 1145:
1146: if (!s_dcert) {
1147: ERR_print_errors(bio_err);
1148: goto end;
1149: }
1150: }
1151: if (bio_s_out == NULL) {
1.43 inoguchi 1152: if (s_server_config.quiet && !s_server_config.debug &&
1153: !s_server_config.msg) {
1.1 jsing 1154: bio_s_out = BIO_new(BIO_s_null());
1155: } else {
1156: if (bio_s_out == NULL)
1157: bio_s_out = BIO_new_fp(stdout, BIO_NOCLOSE);
1158: }
1159: }
1.39 inoguchi 1160: if (s_server_config.nocert) {
1.40 inoguchi 1161: s_server_config.cert_file = NULL;
1162: s_server_config.key_file = NULL;
1163: s_server_config.dcert_file = NULL;
1164: s_server_config.dkey_file = NULL;
1165: s_server_config.cert_file2 = NULL;
1166: s_server_config.key_file2 = NULL;
1.1 jsing 1167: }
1.39 inoguchi 1168: ctx = SSL_CTX_new(s_server_config.meth);
1.1 jsing 1169: if (ctx == NULL) {
1170: ERR_print_errors(bio_err);
1171: goto end;
1172: }
1.37 tb 1173:
1174: SSL_CTX_clear_mode(ctx, SSL_MODE_AUTO_RETRY);
1.35 inoguchi 1175:
1.39 inoguchi 1176: if (!SSL_CTX_set_min_proto_version(ctx, s_server_config.min_version))
1.35 inoguchi 1177: goto end;
1.39 inoguchi 1178: if (!SSL_CTX_set_max_proto_version(ctx, s_server_config.max_version))
1.35 inoguchi 1179: goto end;
1180:
1.39 inoguchi 1181: if (s_server_config.session_id_prefix) {
1182: if (strlen(s_server_config.session_id_prefix) >= 32)
1.1 jsing 1183: BIO_printf(bio_err,
1184: "warning: id_prefix is too long, only one new session will be possible\n");
1.39 inoguchi 1185: else if (strlen(s_server_config.session_id_prefix) >= 16)
1.1 jsing 1186: BIO_printf(bio_err,
1187: "warning: id_prefix is too long if you use SSLv2\n");
1188: if (!SSL_CTX_set_generate_session_id(ctx, generate_session_id)) {
1189: BIO_printf(bio_err, "error setting 'id_prefix'\n");
1190: ERR_print_errors(bio_err);
1191: goto end;
1192: }
1.43 inoguchi 1193: BIO_printf(bio_err, "id_prefix '%s' set.\n",
1194: s_server_config.session_id_prefix);
1.1 jsing 1195: }
1196: SSL_CTX_set_quiet_shutdown(ctx, 1);
1.39 inoguchi 1197: if (s_server_config.bugs)
1.1 jsing 1198: SSL_CTX_set_options(ctx, SSL_OP_ALL);
1.39 inoguchi 1199: SSL_CTX_set_options(ctx, s_server_config.off);
1.1 jsing 1200: /*
1201: * DTLS: partial reads end up discarding unread UDP bytes :-( Setting
1202: * read ahead solves this problem.
1203: */
1.39 inoguchi 1204: if (s_server_config.socket_type == SOCK_DGRAM)
1.1 jsing 1205: SSL_CTX_set_read_ahead(ctx, 1);
1206:
1.39 inoguchi 1207: if (s_server_config.state)
1.1 jsing 1208: SSL_CTX_set_info_callback(ctx, apps_ssl_info_callback);
1.39 inoguchi 1209: if (s_server_config.no_cache)
1.1 jsing 1210: SSL_CTX_set_session_cache_mode(ctx, SSL_SESS_CACHE_OFF);
1211: else
1212: SSL_CTX_sess_set_cache_size(ctx, 128);
1213:
1214: #ifndef OPENSSL_NO_SRTP
1.39 inoguchi 1215: if (s_server_config.srtp_profiles != NULL)
1216: SSL_CTX_set_tlsext_use_srtp(ctx, s_server_config.srtp_profiles);
1.1 jsing 1217: #endif
1218:
1.43 inoguchi 1219: if ((!SSL_CTX_load_verify_locations(ctx, s_server_config.CAfile,
1220: s_server_config.CApath)) ||
1.1 jsing 1221: (!SSL_CTX_set_default_verify_paths(ctx))) {
1222: /* BIO_printf(bio_err,"X509_load_verify_locations\n"); */
1223: ERR_print_errors(bio_err);
1224: /* goto end; */
1225: }
1.39 inoguchi 1226: if (s_server_config.vpm)
1227: SSL_CTX_set1_param(ctx, s_server_config.vpm);
1.1 jsing 1228:
1229: if (s_cert2) {
1.39 inoguchi 1230: ctx2 = SSL_CTX_new(s_server_config.meth);
1.1 jsing 1231: if (ctx2 == NULL) {
1232: ERR_print_errors(bio_err);
1233: goto end;
1234: }
1.35 inoguchi 1235:
1.43 inoguchi 1236: if (!SSL_CTX_set_min_proto_version(ctx2,
1237: s_server_config.min_version))
1.35 inoguchi 1238: goto end;
1.43 inoguchi 1239: if (!SSL_CTX_set_max_proto_version(ctx2,
1240: s_server_config.max_version))
1.35 inoguchi 1241: goto end;
1.38 tb 1242: SSL_CTX_clear_mode(ctx2, SSL_MODE_AUTO_RETRY);
1.1 jsing 1243: }
1244: if (ctx2) {
1245: BIO_printf(bio_s_out, "Setting secondary ctx parameters\n");
1246:
1.39 inoguchi 1247: if (s_server_config.session_id_prefix) {
1248: if (strlen(s_server_config.session_id_prefix) >= 32)
1.1 jsing 1249: BIO_printf(bio_err,
1250: "warning: id_prefix is too long, only one new session will be possible\n");
1.39 inoguchi 1251: else if (strlen(s_server_config.session_id_prefix) >= 16)
1.1 jsing 1252: BIO_printf(bio_err,
1253: "warning: id_prefix is too long if you use SSLv2\n");
1.43 inoguchi 1254: if (!SSL_CTX_set_generate_session_id(ctx2,
1255: generate_session_id)) {
1256: BIO_printf(bio_err,
1257: "error setting 'id_prefix'\n");
1.1 jsing 1258: ERR_print_errors(bio_err);
1259: goto end;
1260: }
1.43 inoguchi 1261: BIO_printf(bio_err, "id_prefix '%s' set.\n",
1262: s_server_config.session_id_prefix);
1.1 jsing 1263: }
1264: SSL_CTX_set_quiet_shutdown(ctx2, 1);
1.39 inoguchi 1265: if (s_server_config.bugs)
1.1 jsing 1266: SSL_CTX_set_options(ctx2, SSL_OP_ALL);
1.39 inoguchi 1267: SSL_CTX_set_options(ctx2, s_server_config.off);
1.1 jsing 1268: /*
1269: * DTLS: partial reads end up discarding unread UDP bytes :-(
1270: * Setting read ahead solves this problem.
1271: */
1.39 inoguchi 1272: if (s_server_config.socket_type == SOCK_DGRAM)
1.1 jsing 1273: SSL_CTX_set_read_ahead(ctx2, 1);
1274:
1.39 inoguchi 1275: if (s_server_config.state)
1.1 jsing 1276: SSL_CTX_set_info_callback(ctx2, apps_ssl_info_callback);
1277:
1.39 inoguchi 1278: if (s_server_config.no_cache)
1.1 jsing 1279: SSL_CTX_set_session_cache_mode(ctx2, SSL_SESS_CACHE_OFF);
1280: else
1281: SSL_CTX_sess_set_cache_size(ctx2, 128);
1282:
1.43 inoguchi 1283: if ((!SSL_CTX_load_verify_locations(ctx2,
1284: s_server_config.CAfile, s_server_config.CApath)) ||
1.1 jsing 1285: (!SSL_CTX_set_default_verify_paths(ctx2))) {
1286: ERR_print_errors(bio_err);
1287: }
1.39 inoguchi 1288: if (s_server_config.vpm)
1289: SSL_CTX_set1_param(ctx2, s_server_config.vpm);
1.1 jsing 1290: }
1.8 jsing 1291: if (alpn_ctx.data)
1292: SSL_CTX_set_alpn_select_cb(ctx, alpn_cb, &alpn_ctx);
1.1 jsing 1293:
1.39 inoguchi 1294: if (s_server_config.groups_in != NULL) {
1295: if (SSL_CTX_set1_groups_list(ctx, s_server_config.groups_in) != 1) {
1.33 jsing 1296: BIO_printf(bio_err, "Failed to set groups '%s'\n",
1.39 inoguchi 1297: s_server_config.groups_in);
1.33 jsing 1298: goto end;
1299: }
1300: }
1301:
1.1 jsing 1302: #ifndef OPENSSL_NO_DH
1.39 inoguchi 1303: if (!s_server_config.no_dhe) {
1.1 jsing 1304: DH *dh = NULL;
1305:
1.39 inoguchi 1306: if (s_server_config.dhfile)
1307: dh = load_dh_param(s_server_config.dhfile);
1.40 inoguchi 1308: else if (s_server_config.cert_file)
1309: dh = load_dh_param(s_server_config.cert_file);
1.1 jsing 1310:
1.4 jsing 1311: if (dh != NULL)
1.1 jsing 1312: BIO_printf(bio_s_out, "Setting temp DH parameters\n");
1.4 jsing 1313: else
1314: BIO_printf(bio_s_out, "Using auto DH parameters\n");
1315: (void) BIO_flush(bio_s_out);
1316:
1317: if (dh == NULL)
1318: SSL_CTX_set_dh_auto(ctx, 1);
1319: else if (!SSL_CTX_set_tmp_dh(ctx, dh)) {
1320: BIO_printf(bio_err,
1321: "Error setting temp DH parameters\n");
1322: ERR_print_errors(bio_err);
1323: DH_free(dh);
1324: goto end;
1.1 jsing 1325: }
1326:
1327: if (ctx2) {
1.39 inoguchi 1328: if (!s_server_config.dhfile) {
1.14 doug 1329: DH *dh2 = NULL;
1330:
1.40 inoguchi 1331: if (s_server_config.cert_file2 != NULL)
1.43 inoguchi 1332: dh2 = load_dh_param(
1333: s_server_config.cert_file2);
1.1 jsing 1334: if (dh2 != NULL) {
1.43 inoguchi 1335: BIO_printf(bio_s_out,
1336: "Setting temp DH parameters\n");
1.1 jsing 1337: (void) BIO_flush(bio_s_out);
1338:
1339: DH_free(dh);
1340: dh = dh2;
1341: }
1342: }
1.4 jsing 1343: if (dh == NULL)
1344: SSL_CTX_set_dh_auto(ctx2, 1);
1345: else if (!SSL_CTX_set_tmp_dh(ctx2, dh)) {
1346: BIO_printf(bio_err,
1347: "Error setting temp DH parameters\n");
1348: ERR_print_errors(bio_err);
1349: DH_free(dh);
1350: goto end;
1351: }
1.1 jsing 1352: }
1353: DH_free(dh);
1354: }
1355: #endif
1356:
1.39 inoguchi 1357: if (!s_server_config.no_ecdhe && s_server_config.named_curve != NULL) {
1.1 jsing 1358: EC_KEY *ecdh = NULL;
1.33 jsing 1359: int nid;
1.1 jsing 1360:
1.39 inoguchi 1361: if ((nid = OBJ_sn2nid(s_server_config.named_curve)) == 0) {
1.33 jsing 1362: BIO_printf(bio_err, "unknown curve name (%s)\n",
1.39 inoguchi 1363: s_server_config.named_curve);
1.33 jsing 1364: goto end;
1.39 inoguchi 1365: }
1.33 jsing 1366: if ((ecdh = EC_KEY_new_by_curve_name(nid)) == NULL) {
1367: BIO_printf(bio_err, "unable to create curve (%s)\n",
1.39 inoguchi 1368: s_server_config.named_curve);
1.33 jsing 1369: goto end;
1.39 inoguchi 1370: }
1.33 jsing 1371: BIO_printf(bio_s_out, "Setting temp ECDH parameters\n");
1.1 jsing 1372: (void) BIO_flush(bio_s_out);
1373:
1374: SSL_CTX_set_tmp_ecdh(ctx, ecdh);
1375: if (ctx2)
1376: SSL_CTX_set_tmp_ecdh(ctx2, ecdh);
1377: EC_KEY_free(ecdh);
1378: }
1379:
1380: if (!set_cert_key_stuff(ctx, s_cert, s_key))
1381: goto end;
1382: if (ctx2 && !set_cert_key_stuff(ctx2, s_cert2, s_key2))
1383: goto end;
1384: if (s_dcert != NULL) {
1385: if (!set_cert_key_stuff(ctx, s_dcert, s_dkey))
1386: goto end;
1387: }
1388:
1.39 inoguchi 1389: if (s_server_config.cipher != NULL) {
1390: if (!SSL_CTX_set_cipher_list(ctx, s_server_config.cipher)) {
1.1 jsing 1391: BIO_printf(bio_err, "error setting cipher list\n");
1392: ERR_print_errors(bio_err);
1393: goto end;
1394: }
1.43 inoguchi 1395: if (ctx2 && !SSL_CTX_set_cipher_list(ctx2,
1396: s_server_config.cipher)) {
1.1 jsing 1397: BIO_printf(bio_err, "error setting cipher list\n");
1398: ERR_print_errors(bio_err);
1399: goto end;
1400: }
1401: }
1.40 inoguchi 1402: SSL_CTX_set_verify(ctx, s_server_config.server_verify, verify_callback);
1.43 inoguchi 1403: SSL_CTX_set_session_id_context(ctx,
1404: (void *) &s_server_session_id_context,
1.1 jsing 1405: sizeof s_server_session_id_context);
1406:
1407: /* Set DTLS cookie generation and verification callbacks */
1408: SSL_CTX_set_cookie_generate_cb(ctx, generate_cookie_callback);
1409: SSL_CTX_set_cookie_verify_cb(ctx, verify_cookie_callback);
1410:
1411: if (ctx2) {
1.43 inoguchi 1412: SSL_CTX_set_verify(ctx2, s_server_config.server_verify,
1413: verify_callback);
1414: SSL_CTX_set_session_id_context(ctx2,
1415: (void *) &s_server_session_id_context,
1.1 jsing 1416: sizeof s_server_session_id_context);
1417:
1.39 inoguchi 1418: s_server_config.tlsextcbp.biodebug = bio_s_out;
1.1 jsing 1419: SSL_CTX_set_tlsext_servername_callback(ctx2, ssl_servername_cb);
1.43 inoguchi 1420: SSL_CTX_set_tlsext_servername_arg(ctx2,
1421: &s_server_config.tlsextcbp);
1.1 jsing 1422: SSL_CTX_set_tlsext_servername_callback(ctx, ssl_servername_cb);
1.43 inoguchi 1423: SSL_CTX_set_tlsext_servername_arg(ctx,
1424: &s_server_config.tlsextcbp);
1.1 jsing 1425: }
1426:
1.39 inoguchi 1427: if (s_server_config.CAfile != NULL) {
1.43 inoguchi 1428: SSL_CTX_set_client_CA_list(ctx,
1429: SSL_load_client_CA_file(s_server_config.CAfile));
1.1 jsing 1430: if (ctx2)
1.43 inoguchi 1431: SSL_CTX_set_client_CA_list(ctx2,
1432: SSL_load_client_CA_file(s_server_config.CAfile));
1.1 jsing 1433: }
1434: BIO_printf(bio_s_out, "ACCEPT\n");
1435: (void) BIO_flush(bio_s_out);
1.39 inoguchi 1436: if (s_server_config.www)
1.43 inoguchi 1437: do_server(s_server_config.port, s_server_config.socket_type,
1438: &accept_socket, www_body, s_server_config.context);
1.1 jsing 1439: else
1.43 inoguchi 1440: do_server(s_server_config.port, s_server_config.socket_type,
1441: &accept_socket, sv_body, s_server_config.context);
1.1 jsing 1442: print_stats(bio_s_out, ctx);
1443: ret = 0;
1.30 jsing 1444: end:
1.29 jsing 1445: SSL_CTX_free(ctx);
1446: X509_free(s_cert);
1447: X509_free(s_dcert);
1448: EVP_PKEY_free(s_key);
1449: EVP_PKEY_free(s_dkey);
1.1 jsing 1450: free(pass);
1451: free(dpass);
1.39 inoguchi 1452: X509_VERIFY_PARAM_free(s_server_config.vpm);
1453: free(s_server_config.tlscstatp.host);
1454: free(s_server_config.tlscstatp.port);
1455: free(s_server_config.tlscstatp.path);
1.29 jsing 1456: SSL_CTX_free(ctx2);
1457: X509_free(s_cert2);
1458: EVP_PKEY_free(s_key2);
1.8 jsing 1459: free(alpn_ctx.data);
1.1 jsing 1460: if (bio_s_out != NULL) {
1461: BIO_free(bio_s_out);
1462: bio_s_out = NULL;
1463: }
1464:
1465: return (ret);
1466: }
1467:
1468: static void
1.41 inoguchi 1469: print_stats(BIO *bio, SSL_CTX *ssl_ctx)
1.1 jsing 1470: {
1471: BIO_printf(bio, "%4ld items in the session cache\n",
1472: SSL_CTX_sess_number(ssl_ctx));
1473: BIO_printf(bio, "%4ld client connects (SSL_connect())\n",
1474: SSL_CTX_sess_connect(ssl_ctx));
1475: BIO_printf(bio, "%4ld client renegotiates (SSL_connect())\n",
1476: SSL_CTX_sess_connect_renegotiate(ssl_ctx));
1477: BIO_printf(bio, "%4ld client connects that finished\n",
1478: SSL_CTX_sess_connect_good(ssl_ctx));
1479: BIO_printf(bio, "%4ld server accepts (SSL_accept())\n",
1480: SSL_CTX_sess_accept(ssl_ctx));
1481: BIO_printf(bio, "%4ld server renegotiates (SSL_accept())\n",
1482: SSL_CTX_sess_accept_renegotiate(ssl_ctx));
1483: BIO_printf(bio, "%4ld server accepts that finished\n",
1484: SSL_CTX_sess_accept_good(ssl_ctx));
1.43 inoguchi 1485: BIO_printf(bio, "%4ld session cache hits\n",
1486: SSL_CTX_sess_hits(ssl_ctx));
1487: BIO_printf(bio, "%4ld session cache misses\n",
1488: SSL_CTX_sess_misses(ssl_ctx));
1489: BIO_printf(bio, "%4ld session cache timeouts\n",
1490: SSL_CTX_sess_timeouts(ssl_ctx));
1491: BIO_printf(bio, "%4ld callback cache hits\n",
1492: SSL_CTX_sess_cb_hits(ssl_ctx));
1.1 jsing 1493: BIO_printf(bio, "%4ld cache full overflows (%ld allowed)\n",
1494: SSL_CTX_sess_cache_full(ssl_ctx),
1495: SSL_CTX_sess_get_cache_size(ssl_ctx));
1496: }
1497:
1498: static int
1499: sv_body(char *hostname, int s, unsigned char *context)
1500: {
1501: char *buf = NULL;
1.7 deraadt 1502: int ret = 1;
1.1 jsing 1503: int k, i;
1504: unsigned long l;
1505: SSL *con = NULL;
1506: BIO *sbio;
1507: struct timeval timeout;
1508:
1509: if ((buf = malloc(bufsize)) == NULL) {
1510: BIO_printf(bio_err, "out of memory\n");
1511: goto err;
1512: }
1.40 inoguchi 1513: if (s_server_config.nbio) {
1514: if (!s_server_config.quiet)
1.1 jsing 1515: BIO_printf(bio_err, "turning on non blocking io\n");
1.2 bcook 1516: if (!BIO_socket_nbio(s, 1))
1.1 jsing 1517: ERR_print_errors(bio_err);
1518: }
1519:
1520: if (con == NULL) {
1521: con = SSL_new(ctx);
1.40 inoguchi 1522: if (s_server_config.tlsextdebug) {
1.1 jsing 1523: SSL_set_tlsext_debug_callback(con, tlsext_cb);
1524: SSL_set_tlsext_debug_arg(con, bio_s_out);
1525: }
1.40 inoguchi 1526: if (s_server_config.tlsextstatus) {
1.1 jsing 1527: SSL_CTX_set_tlsext_status_cb(ctx, cert_status_cb);
1.39 inoguchi 1528: s_server_config.tlscstatp.err = bio_err;
1.43 inoguchi 1529: SSL_CTX_set_tlsext_status_arg(ctx,
1530: &s_server_config.tlscstatp);
1.1 jsing 1531: }
1532: if (context)
1533: SSL_set_session_id_context(con, context,
1534: strlen((char *) context));
1535: }
1536: SSL_clear(con);
1537:
1538: if (SSL_version(con) == DTLS1_VERSION) {
1539:
1540: sbio = BIO_new_dgram(s, BIO_NOCLOSE);
1541:
1.39 inoguchi 1542: if (s_server_config.enable_timeouts) {
1.1 jsing 1543: timeout.tv_sec = 0;
1544: timeout.tv_usec = DGRAM_RCV_TIMEOUT;
1.43 inoguchi 1545: BIO_ctrl(sbio, BIO_CTRL_DGRAM_SET_RECV_TIMEOUT, 0,
1546: &timeout);
1.1 jsing 1547:
1548: timeout.tv_sec = 0;
1549: timeout.tv_usec = DGRAM_SND_TIMEOUT;
1.43 inoguchi 1550: BIO_ctrl(sbio, BIO_CTRL_DGRAM_SET_SEND_TIMEOUT, 0,
1551: &timeout);
1.1 jsing 1552: }
1.39 inoguchi 1553: if (s_server_config.socket_mtu > 28) {
1.1 jsing 1554: SSL_set_options(con, SSL_OP_NO_QUERY_MTU);
1.39 inoguchi 1555: SSL_set_mtu(con, s_server_config.socket_mtu - 28);
1.1 jsing 1556: } else
1557: /* want to do MTU discovery */
1558: BIO_ctrl(sbio, BIO_CTRL_DGRAM_MTU_DISCOVER, 0, NULL);
1559:
1560: /* turn on cookie exchange */
1561: SSL_set_options(con, SSL_OP_COOKIE_EXCHANGE);
1562: } else
1563: sbio = BIO_new_socket(s, BIO_NOCLOSE);
1564:
1.40 inoguchi 1565: if (s_server_config.nbio_test) {
1.1 jsing 1566: BIO *test;
1567:
1568: test = BIO_new(BIO_f_nbio_test());
1569: sbio = BIO_push(test, sbio);
1570: }
1571:
1572: SSL_set_bio(con, sbio, sbio);
1573: SSL_set_accept_state(con);
1574: /* SSL_set_fd(con,s); */
1575:
1.40 inoguchi 1576: if (s_server_config.debug) {
1.1 jsing 1577: SSL_set_debug(con, 1);
1578: BIO_set_callback(SSL_get_rbio(con), bio_dump_callback);
1579: BIO_set_callback_arg(SSL_get_rbio(con), (char *) bio_s_out);
1580: }
1.40 inoguchi 1581: if (s_server_config.msg) {
1.1 jsing 1582: SSL_set_msg_callback(con, msg_cb);
1583: SSL_set_msg_callback_arg(con, bio_s_out);
1584: }
1.40 inoguchi 1585: if (s_server_config.tlsextdebug) {
1.1 jsing 1586: SSL_set_tlsext_debug_callback(con, tlsext_cb);
1587: SSL_set_tlsext_debug_arg(con, bio_s_out);
1588: }
1589:
1590: for (;;) {
1591: int read_from_terminal;
1592: int read_from_sslcon;
1.7 deraadt 1593: struct pollfd pfd[2];
1594: int ptimeout;
1.1 jsing 1595:
1596: read_from_terminal = 0;
1597: read_from_sslcon = SSL_pending(con);
1598:
1599: if (!read_from_sslcon) {
1.7 deraadt 1600: pfd[0].fd = fileno(stdin);
1601: pfd[0].events = POLLIN;
1602: pfd[1].fd = s;
1603: pfd[1].events = POLLIN;
1604:
1.1 jsing 1605: if ((SSL_version(con) == DTLS1_VERSION) &&
1606: DTLSv1_get_timeout(con, &timeout))
1.7 deraadt 1607: ptimeout = timeout.tv_sec * 1000 +
1608: timeout.tv_usec / 1000;
1.1 jsing 1609: else
1.7 deraadt 1610: ptimeout = -1;
1.1 jsing 1611:
1.7 deraadt 1612: i = poll(pfd, 2, ptimeout);
1.1 jsing 1613:
1.43 inoguchi 1614: if ((SSL_version(con) == DTLS1_VERSION) &&
1615: DTLSv1_handle_timeout(con) > 0) {
1.1 jsing 1616: BIO_printf(bio_err, "TIMEOUT occured\n");
1617: }
1618: if (i <= 0)
1619: continue;
1.7 deraadt 1620: if (pfd[0].revents) {
1621: if ((pfd[0].revents & (POLLERR|POLLNVAL)))
1622: continue;
1.1 jsing 1623: read_from_terminal = 1;
1.7 deraadt 1624: }
1625: if (pfd[1].revents) {
1626: if ((pfd[1].revents & (POLLERR|POLLNVAL)))
1627: continue;
1.1 jsing 1628: read_from_sslcon = 1;
1.7 deraadt 1629: }
1.1 jsing 1630: }
1631: if (read_from_terminal) {
1.40 inoguchi 1632: if (s_server_config.crlf) {
1.1 jsing 1633: int j, lf_num;
1634:
1635: i = read(fileno(stdin), buf, bufsize / 2);
1636: lf_num = 0;
1637: /* both loops are skipped when i <= 0 */
1638: for (j = 0; j < i; j++)
1639: if (buf[j] == '\n')
1640: lf_num++;
1641: for (j = i - 1; j >= 0; j--) {
1642: buf[j + lf_num] = buf[j];
1643: if (buf[j] == '\n') {
1644: lf_num--;
1645: i++;
1646: buf[j + lf_num] = '\r';
1647: }
1648: }
1649: assert(lf_num == 0);
1650: } else
1651: i = read(fileno(stdin), buf, bufsize);
1.40 inoguchi 1652: if (!s_server_config.quiet) {
1.1 jsing 1653: if ((i <= 0) || (buf[0] == 'Q')) {
1654: BIO_printf(bio_s_out, "DONE\n");
1655: shutdown(s, SHUT_RD);
1656: close(s);
1657: close_accept_socket();
1658: ret = -11;
1659: goto err;
1660: }
1661: if ((i <= 0) || (buf[0] == 'q')) {
1662: BIO_printf(bio_s_out, "DONE\n");
1663: if (SSL_version(con) != DTLS1_VERSION) {
1664: shutdown(s, SHUT_RD);
1665: close(s);
1666: }
1667: /*
1668: * close_accept_socket(); ret= -11;
1669: */
1670: goto err;
1671: }
1672: if ((buf[0] == 'r') &&
1673: ((buf[1] == '\n') || (buf[1] == '\r'))) {
1674: SSL_renegotiate(con);
1675: i = SSL_do_handshake(con);
1676: printf("SSL_do_handshake -> %d\n", i);
1677: i = 0; /* 13; */
1678: continue;
1679: /*
1680: * RE-NEGOTIATE\n");
1681: */
1682: }
1683: if ((buf[0] == 'R') &&
1684: ((buf[1] == '\n') || (buf[1] == '\r'))) {
1685: SSL_set_verify(con,
1.43 inoguchi 1686: SSL_VERIFY_PEER |
1687: SSL_VERIFY_CLIENT_ONCE,
1688: NULL);
1.1 jsing 1689: SSL_renegotiate(con);
1690: i = SSL_do_handshake(con);
1691: printf("SSL_do_handshake -> %d\n", i);
1692: i = 0; /* 13; */
1693: continue;
1694: /*
1695: * RE-NEGOTIATE asking for client
1696: * cert\n");
1697: */
1698: }
1699: if (buf[0] == 'P') {
1.43 inoguchi 1700: static const char *str =
1701: "Lets print some clear text\n";
1702: BIO_write(SSL_get_wbio(con), str,
1703: strlen(str));
1.1 jsing 1704: }
1705: if (buf[0] == 'S') {
1.43 inoguchi 1706: print_stats(bio_s_out,
1707: SSL_get_SSL_CTX(con));
1.1 jsing 1708: }
1709: }
1710: l = k = 0;
1711: for (;;) {
1712: /* should do a select for the write */
1713: #ifdef RENEG
1714: {
1715: static count = 0;
1716: if (++count == 100) {
1717: count = 0;
1718: SSL_renegotiate(con);
1719: }
1720: }
1721: #endif
1722: k = SSL_write(con, &(buf[l]), (unsigned int) i);
1723: switch (SSL_get_error(con, k)) {
1724: case SSL_ERROR_NONE:
1725: break;
1726: case SSL_ERROR_WANT_WRITE:
1727: case SSL_ERROR_WANT_READ:
1728: case SSL_ERROR_WANT_X509_LOOKUP:
1729: BIO_printf(bio_s_out, "Write BLOCK\n");
1730: break;
1731: case SSL_ERROR_SYSCALL:
1732: case SSL_ERROR_SSL:
1733: BIO_printf(bio_s_out, "ERROR\n");
1734: ERR_print_errors(bio_err);
1735: ret = 1;
1736: goto err;
1737: /* break; */
1738: case SSL_ERROR_ZERO_RETURN:
1739: BIO_printf(bio_s_out, "DONE\n");
1740: ret = 1;
1741: goto err;
1742: }
1.36 tb 1743: if (k <= 0)
1744: continue;
1.1 jsing 1745: l += k;
1746: i -= k;
1747: if (i <= 0)
1748: break;
1749: }
1750: }
1751: if (read_from_sslcon) {
1752: if (!SSL_is_init_finished(con)) {
1753: i = init_ssl_connection(con);
1754:
1755: if (i < 0) {
1756: ret = 0;
1757: goto err;
1758: } else if (i == 0) {
1759: ret = 1;
1760: goto err;
1761: }
1762: } else {
1763: again:
1764: i = SSL_read(con, (char *) buf, bufsize);
1765: switch (SSL_get_error(con, i)) {
1766: case SSL_ERROR_NONE: {
1767: int len, n;
1768: for (len = 0; len < i;) {
1769: do {
1770: n = write(fileno(stdout), buf + len, i - len);
1771: } while (n == -1 && errno == EINTR);
1772:
1.31 deraadt 1773: if (n == -1) {
1.1 jsing 1774: BIO_printf(bio_s_out, "ERROR\n");
1775: goto err;
1776: }
1777: len += n;
1778: }
1779: }
1780: if (SSL_pending(con))
1781: goto again;
1782: break;
1783: case SSL_ERROR_WANT_WRITE:
1784: case SSL_ERROR_WANT_READ:
1785: BIO_printf(bio_s_out, "Read BLOCK\n");
1786: break;
1787: case SSL_ERROR_SYSCALL:
1788: case SSL_ERROR_SSL:
1789: BIO_printf(bio_s_out, "ERROR\n");
1790: ERR_print_errors(bio_err);
1791: ret = 1;
1792: goto err;
1793: case SSL_ERROR_ZERO_RETURN:
1794: BIO_printf(bio_s_out, "DONE\n");
1795: ret = 1;
1796: goto err;
1797: }
1798: }
1799: }
1800: }
1.30 jsing 1801: err:
1.1 jsing 1802: if (con != NULL) {
1803: BIO_printf(bio_s_out, "shutting down SSL\n");
1.43 inoguchi 1804: SSL_set_shutdown(con,
1805: SSL_SENT_SHUTDOWN | SSL_RECEIVED_SHUTDOWN);
1.1 jsing 1806: SSL_free(con);
1807: }
1808: BIO_printf(bio_s_out, "CONNECTION CLOSED\n");
1.26 deraadt 1809: freezero(buf, bufsize);
1.1 jsing 1810: if (ret >= 0)
1811: BIO_printf(bio_s_out, "ACCEPT\n");
1812: return (ret);
1813: }
1814:
1815: static void
1816: close_accept_socket(void)
1817: {
1818: BIO_printf(bio_err, "shutdown accept socket\n");
1819: if (accept_socket >= 0) {
1820: shutdown(accept_socket, SHUT_RDWR);
1821: close(accept_socket);
1822: }
1823: }
1824:
1825: static int
1.41 inoguchi 1826: init_ssl_connection(SSL *con)
1.1 jsing 1827: {
1828: int i;
1829: const char *str;
1830: X509 *peer;
1831: long verify_error;
1832: char buf[BUFSIZ];
1833: unsigned char *exportedkeymat;
1834:
1835: i = SSL_accept(con);
1836: if (i <= 0) {
1837: if (BIO_sock_should_retry(i)) {
1838: BIO_printf(bio_s_out, "DELAY\n");
1839: return (1);
1840: }
1841: BIO_printf(bio_err, "ERROR\n");
1842: verify_error = SSL_get_verify_result(con);
1843: if (verify_error != X509_V_OK) {
1844: BIO_printf(bio_err, "verify error:%s\n",
1845: X509_verify_cert_error_string(verify_error));
1846: } else
1847: ERR_print_errors(bio_err);
1848: return (0);
1849: }
1850: PEM_write_bio_SSL_SESSION(bio_s_out, SSL_get_session(con));
1851:
1852: peer = SSL_get_peer_certificate(con);
1853: if (peer != NULL) {
1854: BIO_printf(bio_s_out, "Client certificate\n");
1855: PEM_write_bio_X509(bio_s_out, peer);
1856: X509_NAME_oneline(X509_get_subject_name(peer), buf, sizeof buf);
1857: BIO_printf(bio_s_out, "subject=%s\n", buf);
1858: X509_NAME_oneline(X509_get_issuer_name(peer), buf, sizeof buf);
1859: BIO_printf(bio_s_out, "issuer=%s\n", buf);
1860: X509_free(peer);
1861: }
1862: if (SSL_get_shared_ciphers(con, buf, sizeof buf) != NULL)
1863: BIO_printf(bio_s_out, "Shared ciphers:%s\n", buf);
1864: str = SSL_CIPHER_get_name(SSL_get_current_cipher(con));
1865: BIO_printf(bio_s_out, "CIPHER is %s\n", (str != NULL) ? str : "(NONE)");
1866:
1867: #ifndef OPENSSL_NO_SRTP
1868: {
1869: SRTP_PROTECTION_PROFILE *srtp_profile
1870: = SSL_get_selected_srtp_profile(con);
1871:
1872: if (srtp_profile)
1.43 inoguchi 1873: BIO_printf(bio_s_out,
1874: "SRTP Extension negotiated, profile=%s\n",
1.1 jsing 1875: srtp_profile->name);
1876: }
1877: #endif
1878: if (SSL_cache_hit(con))
1879: BIO_printf(bio_s_out, "Reused session-id\n");
1880: BIO_printf(bio_s_out, "Secure Renegotiation IS%s supported\n",
1881: SSL_get_secure_renegotiation_support(con) ? "" : " NOT");
1.39 inoguchi 1882: if (s_server_config.keymatexportlabel != NULL) {
1.1 jsing 1883: BIO_printf(bio_s_out, "Keying material exporter:\n");
1.43 inoguchi 1884: BIO_printf(bio_s_out, " Label: '%s'\n",
1885: s_server_config.keymatexportlabel);
1.1 jsing 1886: BIO_printf(bio_s_out, " Length: %i bytes\n",
1.39 inoguchi 1887: s_server_config.keymatexportlen);
1888: exportedkeymat = malloc(s_server_config.keymatexportlen);
1.1 jsing 1889: if (exportedkeymat != NULL) {
1890: if (!SSL_export_keying_material(con, exportedkeymat,
1.39 inoguchi 1891: s_server_config.keymatexportlen,
1892: s_server_config.keymatexportlabel,
1893: strlen(s_server_config.keymatexportlabel),
1.1 jsing 1894: NULL, 0, 0)) {
1895: BIO_printf(bio_s_out, " Error\n");
1896: } else {
1897: BIO_printf(bio_s_out, " Keying material: ");
1.39 inoguchi 1898: for (i = 0; i < s_server_config.keymatexportlen; i++)
1.1 jsing 1899: BIO_printf(bio_s_out, "%02X",
1900: exportedkeymat[i]);
1901: BIO_printf(bio_s_out, "\n");
1902: }
1903: free(exportedkeymat);
1904: }
1905: }
1906: return (1);
1907: }
1908:
1909: #ifndef OPENSSL_NO_DH
1910: static DH *
1911: load_dh_param(const char *dhfile)
1912: {
1913: DH *ret = NULL;
1914: BIO *bio;
1915:
1916: if ((bio = BIO_new_file(dhfile, "r")) == NULL)
1917: goto err;
1918: ret = PEM_read_bio_DHparams(bio, NULL, NULL, NULL);
1.30 jsing 1919: err:
1.1 jsing 1920: BIO_free(bio);
1921: return (ret);
1922: }
1923: #endif
1924:
1925: static int
1926: www_body(char *hostname, int s, unsigned char *context)
1927: {
1928: char *buf = NULL;
1929: int ret = 1;
1930: int i, j, k, dot;
1931: SSL *con;
1932: const SSL_CIPHER *c;
1933: BIO *io, *ssl_bio, *sbio;
1934:
1935: buf = malloc(bufsize);
1936: if (buf == NULL)
1937: return (0);
1938: io = BIO_new(BIO_f_buffer());
1939: ssl_bio = BIO_new(BIO_f_ssl());
1940: if ((io == NULL) || (ssl_bio == NULL))
1941: goto err;
1942:
1.40 inoguchi 1943: if (s_server_config.nbio) {
1944: if (!s_server_config.quiet)
1.1 jsing 1945: BIO_printf(bio_err, "turning on non blocking io\n");
1.2 bcook 1946: if (!BIO_socket_nbio(s, 1))
1.1 jsing 1947: ERR_print_errors(bio_err);
1948: }
1949:
1950: /* lets make the output buffer a reasonable size */
1951: if (!BIO_set_write_buffer_size(io, bufsize))
1952: goto err;
1953:
1954: if ((con = SSL_new(ctx)) == NULL)
1955: goto err;
1.40 inoguchi 1956: if (s_server_config.tlsextdebug) {
1.1 jsing 1957: SSL_set_tlsext_debug_callback(con, tlsext_cb);
1958: SSL_set_tlsext_debug_arg(con, bio_s_out);
1959: }
1960: if (context)
1961: SSL_set_session_id_context(con, context,
1962: strlen((char *) context));
1963:
1964: sbio = BIO_new_socket(s, BIO_NOCLOSE);
1.40 inoguchi 1965: if (s_server_config.nbio_test) {
1.1 jsing 1966: BIO *test;
1967:
1968: test = BIO_new(BIO_f_nbio_test());
1969: sbio = BIO_push(test, sbio);
1970: }
1971: SSL_set_bio(con, sbio, sbio);
1972: SSL_set_accept_state(con);
1973:
1974: /* SSL_set_fd(con,s); */
1975: BIO_set_ssl(ssl_bio, con, BIO_CLOSE);
1976: BIO_push(io, ssl_bio);
1977:
1.40 inoguchi 1978: if (s_server_config.debug) {
1.1 jsing 1979: SSL_set_debug(con, 1);
1980: BIO_set_callback(SSL_get_rbio(con), bio_dump_callback);
1981: BIO_set_callback_arg(SSL_get_rbio(con), (char *) bio_s_out);
1982: }
1.40 inoguchi 1983: if (s_server_config.msg) {
1.1 jsing 1984: SSL_set_msg_callback(con, msg_cb);
1985: SSL_set_msg_callback_arg(con, bio_s_out);
1986: }
1987: for (;;) {
1988: i = BIO_gets(io, buf, bufsize - 1);
1989: if (i < 0) { /* error */
1990: if (!BIO_should_retry(io)) {
1.40 inoguchi 1991: if (!s_server_config.quiet)
1.1 jsing 1992: ERR_print_errors(bio_err);
1993: goto err;
1994: } else {
1.40 inoguchi 1995: if (s_server_config.debug) {
1.34 beck 1996: BIO_printf(bio_s_out, "read R BLOCK\n");
1997: sleep(1);
1998: }
1.1 jsing 1999: continue;
2000: }
2001: } else if (i == 0) { /* end of input */
2002: ret = 1;
2003: goto end;
2004: }
2005: /* else we have data */
1.43 inoguchi 2006: if (((s_server_config.www == 1) &&
2007: (strncmp("GET ", buf, 4) == 0)) ||
2008: ((s_server_config.www == 2) &&
2009: (strncmp("GET /stats ", buf, 11) == 0))) {
1.1 jsing 2010: char *p;
2011: X509 *peer;
1.41 inoguchi 2012: STACK_OF(SSL_CIPHER) *sk;
1.1 jsing 2013: static const char *space = " ";
2014:
2015: BIO_puts(io, "HTTP/1.0 200 ok\r\nContent-type: text/html\r\n\r\n");
2016: BIO_puts(io, "<HTML><BODY BGCOLOR=\"#ffffff\">\n");
2017: BIO_puts(io, "<pre>\n");
2018: /* BIO_puts(io,SSLeay_version(SSLEAY_VERSION));*/
2019: BIO_puts(io, "\n");
2020: for (i = 0; i < local_argc; i++) {
2021: BIO_puts(io, local_argv[i]);
2022: BIO_write(io, " ", 1);
2023: }
2024: BIO_puts(io, "\n");
2025:
2026: BIO_printf(io,
2027: "Secure Renegotiation IS%s supported\n",
2028: SSL_get_secure_renegotiation_support(con) ?
2029: "" : " NOT");
2030:
2031: /*
2032: * The following is evil and should not really be
2033: * done
2034: */
1.43 inoguchi 2035: BIO_printf(io,
2036: "Ciphers supported in s_server binary\n");
1.1 jsing 2037: sk = SSL_get_ciphers(con);
2038: j = sk_SSL_CIPHER_num(sk);
2039: for (i = 0; i < j; i++) {
2040: c = sk_SSL_CIPHER_value(sk, i);
2041: BIO_printf(io, "%-11s:%-25s",
2042: SSL_CIPHER_get_version(c),
2043: SSL_CIPHER_get_name(c));
2044: if ((((i + 1) % 2) == 0) && (i + 1 != j))
2045: BIO_puts(io, "\n");
2046: }
2047: BIO_puts(io, "\n");
2048: p = SSL_get_shared_ciphers(con, buf, bufsize);
2049: if (p != NULL) {
1.43 inoguchi 2050: BIO_printf(io,
2051: "---\nCiphers common between both SSL end points:\n");
1.1 jsing 2052: j = i = 0;
2053: while (*p) {
2054: if (*p == ':') {
2055: BIO_write(io, space, 26 - j);
2056: i++;
2057: j = 0;
1.43 inoguchi 2058: BIO_write(io,
2059: ((i % 3) ? " " : "\n"), 1);
1.1 jsing 2060: } else {
2061: BIO_write(io, p, 1);
2062: j++;
2063: }
2064: p++;
2065: }
2066: BIO_puts(io, "\n");
2067: }
2068: BIO_printf(io, (SSL_cache_hit(con)
2069: ? "---\nReused, "
2070: : "---\nNew, "));
2071: c = SSL_get_current_cipher(con);
2072: BIO_printf(io, "%s, Cipher is %s\n",
2073: SSL_CIPHER_get_version(c),
2074: SSL_CIPHER_get_name(c));
2075: SSL_SESSION_print(io, SSL_get_session(con));
2076: BIO_printf(io, "---\n");
2077: print_stats(io, SSL_get_SSL_CTX(con));
2078: BIO_printf(io, "---\n");
2079: peer = SSL_get_peer_certificate(con);
2080: if (peer != NULL) {
2081: BIO_printf(io, "Client certificate\n");
2082: X509_print(io, peer);
2083: PEM_write_bio_X509(io, peer);
2084: } else
1.43 inoguchi 2085: BIO_puts(io,
2086: "no client certificate available\n");
1.1 jsing 2087: BIO_puts(io, "</BODY></HTML>\r\n\r\n");
2088: break;
1.43 inoguchi 2089: } else if ((s_server_config.www == 2 ||
2090: s_server_config.www == 3) &&
2091: (strncmp("GET /", buf, 5) == 0)) {
1.1 jsing 2092: BIO *file;
2093: char *p, *e;
2094: static const char *text = "HTTP/1.0 200 ok\r\nContent-type: text/plain\r\n\r\n";
2095:
2096: /* skip the '/' */
2097: p = &(buf[5]);
2098:
2099: dot = 1;
2100: for (e = p; *e != '\0'; e++) {
2101: if (e[0] == ' ')
2102: break;
2103:
2104: switch (dot) {
2105: case 1:
2106: dot = (e[0] == '.') ? 2 : 0;
2107: break;
2108: case 2:
2109: dot = (e[0] == '.') ? 3 : 0;
2110: break;
2111: case 3:
1.43 inoguchi 2112: dot = (e[0] == '/' || e[0] == '\\') ?
2113: -1 : 0;
1.1 jsing 2114: break;
2115: }
2116: if (dot == 0)
1.43 inoguchi 2117: dot = (e[0] == '/' || e[0] == '\\') ?
2118: 1 : 0;
1.1 jsing 2119: }
1.43 inoguchi 2120: dot = (dot == 3) || (dot == -1); /* filename contains
2121: * ".." component */
1.1 jsing 2122:
2123: if (*e == '\0') {
2124: BIO_puts(io, text);
1.43 inoguchi 2125: BIO_printf(io,
2126: "'%s' is an invalid file name\r\n", p);
1.1 jsing 2127: break;
2128: }
2129: *e = '\0';
2130:
2131: if (dot) {
2132: BIO_puts(io, text);
1.43 inoguchi 2133: BIO_printf(io,
2134: "'%s' contains '..' reference\r\n", p);
1.1 jsing 2135: break;
2136: }
2137: if (*p == '/') {
2138: BIO_puts(io, text);
1.43 inoguchi 2139: BIO_printf(io,
2140: "'%s' is an invalid path\r\n", p);
1.1 jsing 2141: break;
2142: }
2143: /* if a directory, do the index thang */
2144: if (app_isdir(p) > 0) {
2145: BIO_puts(io, text);
2146: BIO_printf(io, "'%s' is a directory\r\n", p);
2147: break;
2148: }
2149: if ((file = BIO_new_file(p, "r")) == NULL) {
2150: BIO_puts(io, text);
2151: BIO_printf(io, "Error opening '%s'\r\n", p);
2152: ERR_print_errors(io);
2153: break;
2154: }
1.40 inoguchi 2155: if (!s_server_config.quiet)
1.1 jsing 2156: BIO_printf(bio_err, "FILE:%s\n", p);
2157:
1.39 inoguchi 2158: if (s_server_config.www == 2) {
1.1 jsing 2159: i = strlen(p);
2160: if (((i > 5) && (strcmp(&(p[i - 5]), ".html") == 0)) ||
2161: ((i > 4) && (strcmp(&(p[i - 4]), ".php") == 0)) ||
2162: ((i > 4) && (strcmp(&(p[i - 4]), ".htm") == 0)))
2163: BIO_puts(io, "HTTP/1.0 200 ok\r\nContent-type: text/html\r\n\r\n");
2164: else
2165: BIO_puts(io, "HTTP/1.0 200 ok\r\nContent-type: text/plain\r\n\r\n");
2166: }
2167: /* send the file */
2168: for (;;) {
2169: i = BIO_read(file, buf, bufsize);
2170: if (i <= 0)
2171: break;
2172:
2173: #ifdef RENEG
2174: total_bytes += i;
2175: fprintf(stderr, "%d\n", i);
2176: if (total_bytes > 3 * 1024) {
2177: total_bytes = 0;
2178: fprintf(stderr, "RENEGOTIATE\n");
2179: SSL_renegotiate(con);
2180: }
2181: #endif
2182:
2183: for (j = 0; j < i;) {
2184: #ifdef RENEG
2185: {
2186: static count = 0;
2187: if (++count == 13) {
2188: SSL_renegotiate(con);
2189: }
2190: }
2191: #endif
2192: k = BIO_write(io, &(buf[j]), i - j);
2193: if (k <= 0) {
2194: if (!BIO_should_retry(io))
2195: goto write_error;
2196: else {
1.43 inoguchi 2197: BIO_printf(bio_s_out,
2198: "rwrite W BLOCK\n");
1.1 jsing 2199: }
2200: } else {
2201: j += k;
2202: }
2203: }
2204: }
2205: write_error:
2206: BIO_free(file);
2207: break;
2208: }
2209: }
2210:
2211: for (;;) {
2212: i = (int) BIO_flush(io);
2213: if (i <= 0) {
2214: if (!BIO_should_retry(io))
2215: break;
2216: } else
2217: break;
2218: }
1.30 jsing 2219: end:
1.1 jsing 2220: /* make sure we re-use sessions */
2221: SSL_set_shutdown(con, SSL_SENT_SHUTDOWN | SSL_RECEIVED_SHUTDOWN);
2222:
1.30 jsing 2223: err:
1.1 jsing 2224:
2225: if (ret >= 0)
2226: BIO_printf(bio_s_out, "ACCEPT\n");
2227:
1.24 mmcc 2228: free(buf);
1.29 jsing 2229: BIO_free_all(io);
1.1 jsing 2230: /* if (ssl_bio != NULL) BIO_free(ssl_bio);*/
2231: return (ret);
2232: }
2233:
2234: #define MAX_SESSION_ID_ATTEMPTS 10
2235: static int
1.42 inoguchi 2236: generate_session_id(const SSL *ssl, unsigned char *id, unsigned int *id_len)
1.1 jsing 2237: {
2238: unsigned int count = 0;
2239: do {
1.3 jsing 2240: arc4random_buf(id, *id_len);
1.1 jsing 2241: /*
2242: * Prefix the session_id with the required prefix. NB: If our
2243: * prefix is too long, clip it - but there will be worse
2244: * effects anyway, eg. the server could only possibly create
2245: * 1 session ID (ie. the prefix!) so all future session
2246: * negotiations will fail due to conflicts.
2247: */
1.39 inoguchi 2248: memcpy(id, s_server_config.session_id_prefix,
2249: (strlen(s_server_config.session_id_prefix) < *id_len) ?
2250: strlen(s_server_config.session_id_prefix) : *id_len);
1.1 jsing 2251: }
2252: while (SSL_has_matching_session_id(ssl, id, *id_len) &&
2253: (++count < MAX_SESSION_ID_ATTEMPTS));
2254: if (count >= MAX_SESSION_ID_ATTEMPTS)
2255: return 0;
2256: return 1;
1.42 inoguchi 2257: }
2258:
2259: static int
2260: ssl_servername_cb(SSL *s, int *ad, void *arg)
2261: {
2262: tlsextctx *p = (tlsextctx *) arg;
1.43 inoguchi 2263: const char *servername = SSL_get_servername(s,
2264: TLSEXT_NAMETYPE_host_name);
2265:
1.42 inoguchi 2266: if (servername && p->biodebug)
1.43 inoguchi 2267: BIO_printf(p->biodebug, "Hostname in TLS extension: \"%s\"\n",
2268: servername);
1.42 inoguchi 2269:
2270: if (!p->servername)
2271: return SSL_TLSEXT_ERR_NOACK;
2272:
2273: if (servername) {
2274: if (strcmp(servername, p->servername))
2275: return p->extension_error;
2276: if (ctx2) {
2277: BIO_printf(p->biodebug, "Switching server context.\n");
2278: SSL_set_SSL_CTX(s, ctx2);
2279: }
2280: }
2281: return SSL_TLSEXT_ERR_OK;
2282: }
2283:
2284: /* Certificate Status callback. This is called when a client includes a
2285: * certificate status request extension.
2286: *
2287: * This is a simplified version. It examines certificates each time and
2288: * makes one OCSP responder query for each request.
2289: *
2290: * A full version would store details such as the OCSP certificate IDs and
2291: * minimise the number of OCSP responses by caching them until they were
2292: * considered "expired".
2293: */
2294:
2295: static int
2296: cert_status_cb(SSL *s, void *arg)
2297: {
2298: tlsextstatusctx *srctx = arg;
2299: BIO *err = srctx->err;
2300: char *host = NULL, *port = NULL, *path = NULL;
2301: int use_ssl;
2302: unsigned char *rspder = NULL;
2303: int rspderlen;
2304: STACK_OF(OPENSSL_STRING) *aia = NULL;
2305: X509 *x = NULL;
2306: X509_STORE_CTX inctx;
2307: X509_OBJECT obj;
2308: OCSP_REQUEST *req = NULL;
2309: OCSP_RESPONSE *resp = NULL;
2310: OCSP_CERTID *id = NULL;
2311: STACK_OF(X509_EXTENSION) *exts;
2312: int ret = SSL_TLSEXT_ERR_NOACK;
2313: int i;
2314:
2315: if (srctx->verbose)
2316: BIO_puts(err, "cert_status: callback called\n");
2317: /* Build up OCSP query from server certificate */
2318: x = SSL_get_certificate(s);
2319: aia = X509_get1_ocsp(x);
2320: if (aia) {
2321: if (!OCSP_parse_url(sk_OPENSSL_STRING_value(aia, 0),
2322: &host, &port, &path, &use_ssl)) {
2323: BIO_puts(err, "cert_status: can't parse AIA URL\n");
2324: goto err;
2325: }
2326: if (srctx->verbose)
2327: BIO_printf(err, "cert_status: AIA URL: %s\n",
2328: sk_OPENSSL_STRING_value(aia, 0));
2329: } else {
2330: if (!srctx->host) {
1.43 inoguchi 2331: BIO_puts(srctx->err,
2332: "cert_status: no AIA and no default responder URL\n");
1.42 inoguchi 2333: goto done;
2334: }
2335: host = srctx->host;
2336: path = srctx->path;
2337: port = srctx->port;
2338: use_ssl = srctx->use_ssl;
2339: }
2340:
2341: if (!X509_STORE_CTX_init(&inctx,
2342: SSL_CTX_get_cert_store(SSL_get_SSL_CTX(s)),
2343: NULL, NULL))
2344: goto err;
2345: if (X509_STORE_get_by_subject(&inctx, X509_LU_X509,
2346: X509_get_issuer_name(x), &obj) <= 0) {
1.43 inoguchi 2347: BIO_puts(err,
2348: "cert_status: Can't retrieve issuer certificate.\n");
1.42 inoguchi 2349: X509_STORE_CTX_cleanup(&inctx);
2350: goto done;
2351: }
2352: req = OCSP_REQUEST_new();
2353: if (!req)
2354: goto err;
2355: id = OCSP_cert_to_id(NULL, x, obj.data.x509);
2356: X509_free(obj.data.x509);
2357: X509_STORE_CTX_cleanup(&inctx);
2358: if (!id)
2359: goto err;
2360: if (!OCSP_request_add0_id(req, id))
2361: goto err;
2362: id = NULL;
2363: /* Add any extensions to the request */
2364: SSL_get_tlsext_status_exts(s, &exts);
2365: for (i = 0; i < sk_X509_EXTENSION_num(exts); i++) {
2366: X509_EXTENSION *ext = sk_X509_EXTENSION_value(exts, i);
2367: if (!OCSP_REQUEST_add_ext(req, ext, -1))
2368: goto err;
2369: }
2370: resp = process_responder(err, req, host, path, port, use_ssl, NULL,
2371: srctx->timeout);
2372: if (!resp) {
2373: BIO_puts(err, "cert_status: error querying responder\n");
2374: goto done;
2375: }
2376: rspderlen = i2d_OCSP_RESPONSE(resp, &rspder);
2377: if (rspderlen <= 0)
2378: goto err;
2379: SSL_set_tlsext_status_ocsp_resp(s, rspder, rspderlen);
2380: if (srctx->verbose) {
2381: BIO_puts(err, "cert_status: ocsp response sent:\n");
2382: OCSP_RESPONSE_print(err, resp, 2);
2383: }
2384: ret = SSL_TLSEXT_ERR_OK;
2385: done:
2386: if (ret != SSL_TLSEXT_ERR_OK)
2387: ERR_print_errors(err);
2388: if (aia) {
2389: free(host);
2390: free(path);
2391: free(port);
2392: X509_email_free(aia);
2393: }
2394: if (id)
2395: OCSP_CERTID_free(id);
2396: if (req)
2397: OCSP_REQUEST_free(req);
2398: if (resp)
2399: OCSP_RESPONSE_free(resp);
2400: return ret;
2401: err:
2402: ret = SSL_TLSEXT_ERR_ALERT_FATAL;
2403: goto done;
2404: }
2405:
2406: static int
2407: alpn_cb(SSL *s, const unsigned char **out, unsigned char *outlen,
2408: const unsigned char *in, unsigned int inlen, void *arg)
2409: {
2410: tlsextalpnctx *alpn_ctx = arg;
2411:
2412: if (!s_server_config.quiet) {
2413: /* We can assume that in is syntactically valid. */
2414: unsigned i;
2415:
2416: BIO_printf(bio_s_out,
2417: "ALPN protocols advertised by the client: ");
2418: for (i = 0; i < inlen; ) {
2419: if (i)
2420: BIO_write(bio_s_out, ", ", 2);
2421: BIO_write(bio_s_out, &in[i + 1], in[i]);
2422: i += in[i] + 1;
2423: }
2424: BIO_write(bio_s_out, "\n", 1);
2425: }
2426:
2427: if (SSL_select_next_proto((unsigned char**)out, outlen, alpn_ctx->data,
2428: alpn_ctx->len, in, inlen) != OPENSSL_NPN_NEGOTIATED)
2429: return (SSL_TLSEXT_ERR_NOACK);
2430:
2431: if (!s_server_config.quiet) {
2432: BIO_printf(bio_s_out, "ALPN protocols selected: ");
2433: BIO_write(bio_s_out, *out, *outlen);
2434: BIO_write(bio_s_out, "\n", 1);
2435: }
2436:
2437: return (SSL_TLSEXT_ERR_OK);
1.1 jsing 2438: }