diff options
Diffstat (limited to 'src')
| -rw-r--r-- | src/usr.bin/openssl/s_client.c | 1220 |
1 files changed, 770 insertions, 450 deletions
diff --git a/src/usr.bin/openssl/s_client.c b/src/usr.bin/openssl/s_client.c index cc886b11e6..2b47bf7ff9 100644 --- a/src/usr.bin/openssl/s_client.c +++ b/src/usr.bin/openssl/s_client.c | |||
| @@ -1,4 +1,4 @@ | |||
| 1 | /* $OpenBSD: s_client.c,v 1.46 2020/05/23 12:52:54 tb Exp $ */ | 1 | /* $OpenBSD: s_client.c,v 1.47 2020/07/09 12:48:19 inoguchi Exp $ */ |
| 2 | /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) | 2 | /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) |
| 3 | * All rights reserved. | 3 | * All rights reserved. |
| 4 | * | 4 | * |
| @@ -170,87 +170,674 @@ | |||
| 170 | 170 | ||
| 171 | #define BUFSIZZ 1024*8 | 171 | #define BUFSIZZ 1024*8 |
| 172 | 172 | ||
| 173 | static int c_nbio = 0; | ||
| 174 | static int c_Pause = 0; | ||
| 175 | static int c_debug = 0; | ||
| 176 | static int c_tlsextdebug = 0; | ||
| 177 | static int c_status_req = 0; | ||
| 178 | static int c_msg = 0; | ||
| 179 | static int c_showcerts = 0; | ||
| 180 | |||
| 181 | static char *keymatexportlabel = NULL; | ||
| 182 | static int keymatexportlen = 20; | ||
| 183 | |||
| 184 | static void sc_usage(void); | 173 | static void sc_usage(void); |
| 185 | static void print_stuff(BIO * berr, SSL * con, int full); | 174 | static void print_stuff(BIO * berr, SSL * con, int full); |
| 186 | static int ocsp_resp_cb(SSL * s, void *arg); | 175 | static int ocsp_resp_cb(SSL * s, void *arg); |
| 187 | static BIO *bio_c_out = NULL; | 176 | static BIO *bio_c_out = NULL; |
| 188 | static int c_quiet = 0; | ||
| 189 | static int c_ign_eof = 0; | ||
| 190 | 177 | ||
| 178 | enum { | ||
| 179 | PROTO_OFF = 0, | ||
| 180 | PROTO_SMTP, | ||
| 181 | PROTO_LMTP, | ||
| 182 | PROTO_POP3, | ||
| 183 | PROTO_IMAP, | ||
| 184 | PROTO_FTP, | ||
| 185 | PROTO_XMPP, | ||
| 186 | }; | ||
| 191 | 187 | ||
| 192 | static void | 188 | static struct { |
| 193 | sc_usage(void) | 189 | int af; |
| 190 | char *alpn_in; | ||
| 191 | int bugs; | ||
| 192 | char *CAfile; | ||
| 193 | char *CApath; | ||
| 194 | int c_debug; | ||
| 195 | int c_ign_eof; | ||
| 196 | int c_msg; | ||
| 197 | int c_nbio; | ||
| 198 | int c_Pause; | ||
| 199 | int c_quiet; | ||
| 200 | int c_showcerts; | ||
| 201 | int c_status_req; | ||
| 202 | int c_tlsextdebug; | ||
| 203 | char *cert_file; | ||
| 204 | int cert_format; | ||
| 205 | char *cipher; | ||
| 206 | unsigned int clr; | ||
| 207 | char *connect; | ||
| 208 | int crlf; | ||
| 209 | int enable_timeouts; | ||
| 210 | const char *errstr; | ||
| 211 | char *groups_in; | ||
| 212 | char *host; | ||
| 213 | char *key_file; | ||
| 214 | int key_format; | ||
| 215 | char *keymatexportlabel; | ||
| 216 | int keymatexportlen; | ||
| 217 | uint16_t max_version; | ||
| 218 | uint16_t min_version; | ||
| 219 | const SSL_METHOD *meth; | ||
| 220 | int nbio_test; | ||
| 221 | char *npn_in; | ||
| 222 | unsigned int off; | ||
| 223 | char *passarg; | ||
| 224 | int peekaboo; | ||
| 225 | char *port; | ||
| 226 | int prexit; | ||
| 227 | char *proxy; | ||
| 228 | int reconnect; | ||
| 229 | char *servername; | ||
| 230 | char *sess_in; | ||
| 231 | char *sess_out; | ||
| 232 | int socket_type; | ||
| 233 | long socket_mtu; | ||
| 234 | #ifndef OPENSSL_NO_SRTP | ||
| 235 | char *srtp_profiles; | ||
| 236 | #endif | ||
| 237 | int starttls_proto; | ||
| 238 | int state; | ||
| 239 | int verify; | ||
| 240 | X509_VERIFY_PARAM *vpm; | ||
| 241 | char *xmpphost; | ||
| 242 | } s_client_config; | ||
| 243 | |||
| 244 | static int | ||
| 245 | s_client_opt_keymatexportlen(char *arg) | ||
| 194 | { | 246 | { |
| 195 | BIO_printf(bio_err, "usage: s_client args\n"); | 247 | s_client_config.keymatexportlen = strtonum(arg, 1, INT_MAX, |
| 196 | BIO_printf(bio_err, "\n"); | 248 | &s_client_config.errstr); |
| 197 | BIO_printf(bio_err, " -4 - Force IPv4\n"); | 249 | if (s_client_config.errstr != NULL) { |
| 198 | BIO_printf(bio_err, " -6 - Force IPv6\n"); | 250 | BIO_printf(bio_err, "invalid argument %s: %s\n", |
| 199 | BIO_printf(bio_err, " -host host - use -connect instead\n"); | 251 | arg, s_client_config.errstr); |
| 200 | BIO_printf(bio_err, " -port port - use -connect instead\n"); | 252 | return (1); |
| 201 | BIO_printf(bio_err, " -connect host:port - who to connect to (default is %s:%s)\n", SSL_HOST_NAME, PORT_STR); | 253 | } |
| 202 | BIO_printf(bio_err, " -proxy host:port - connect to http proxy\n"); | 254 | return (0); |
| 203 | 255 | } | |
| 204 | BIO_printf(bio_err, " -verify arg - turn on peer certificate verification\n"); | 256 | |
| 205 | BIO_printf(bio_err, " -cert arg - certificate file to use, PEM format assumed\n"); | 257 | #ifndef OPENSSL_NO_DTLS1 |
| 206 | BIO_printf(bio_err, " -certform arg - certificate format (PEM or DER) PEM default\n"); | 258 | static int |
| 207 | BIO_printf(bio_err, " -key arg - Private key file to use, in cert file if\n"); | 259 | s_client_opt_mtu(char *arg) |
| 208 | BIO_printf(bio_err, " not specified but cert file is.\n"); | 260 | { |
| 209 | BIO_printf(bio_err, " -keyform arg - key format (PEM or DER) PEM default\n"); | 261 | s_client_config.socket_mtu = strtonum(arg, 0, LONG_MAX, |
| 210 | BIO_printf(bio_err, " -pass arg - private key file pass phrase source\n"); | 262 | &s_client_config.errstr); |
| 211 | BIO_printf(bio_err, " -CApath arg - PEM format directory of CA's\n"); | 263 | if (s_client_config.errstr != NULL) { |
| 212 | BIO_printf(bio_err, " -CAfile arg - PEM format file of CA's\n"); | 264 | BIO_printf(bio_err, "invalid argument %s: %s\n", |
| 213 | BIO_printf(bio_err, " -reconnect - Drop and re-make the connection with the same Session-ID\n"); | 265 | arg, s_client_config.errstr); |
| 214 | BIO_printf(bio_err, " -pause - sleep(1) after each read(2) and write(2) system call\n"); | 266 | return (1); |
| 215 | BIO_printf(bio_err, " -showcerts - show all certificates in the chain\n"); | 267 | } |
| 216 | BIO_printf(bio_err, " -debug - extra output\n"); | 268 | return (0); |
| 217 | BIO_printf(bio_err, " -msg - Show protocol messages\n"); | 269 | } |
| 218 | BIO_printf(bio_err, " -nbio_test - more ssl protocol testing\n"); | 270 | #endif |
| 219 | BIO_printf(bio_err, " -state - print the 'ssl' states\n"); | 271 | |
| 220 | BIO_printf(bio_err, " -nbio - Run with non-blocking IO\n"); | 272 | static int |
| 221 | BIO_printf(bio_err, " -crlf - convert LF from terminal into CRLF\n"); | 273 | s_client_opt_port(char *arg) |
| 222 | BIO_printf(bio_err, " -quiet - no s_client output\n"); | 274 | { |
| 223 | BIO_printf(bio_err, " -ign_eof - ignore input eof (default when -quiet)\n"); | 275 | if (*arg == '\0') |
| 224 | BIO_printf(bio_err, " -no_ign_eof - don't ignore input eof\n"); | 276 | return (1); |
| 225 | BIO_printf(bio_err, " -tls1_3 - just use TLSv1.3\n"); | 277 | |
| 226 | BIO_printf(bio_err, " -tls1_2 - just use TLSv1.2\n"); | 278 | s_client_config.port = arg; |
| 227 | BIO_printf(bio_err, " -tls1_1 - just use TLSv1.1\n"); | 279 | return (0); |
| 228 | BIO_printf(bio_err, " -tls1 - just use TLSv1\n"); | 280 | } |
| 229 | BIO_printf(bio_err, " -dtls1 - just use DTLSv1\n"); | 281 | |
| 230 | BIO_printf(bio_err, " -mtu - set the link layer MTU\n"); | 282 | #ifndef OPENSSL_NO_DTLS1 |
| 231 | BIO_printf(bio_err, " -no_tls1_3/-no_tls1_2/-no_tls1_1/-no_tls1 - turn off that protocol\n"); | 283 | static int |
| 232 | BIO_printf(bio_err, " -bugs - Switch on all SSL implementation bug workarounds\n"); | 284 | s_client_opt_protocol_version_dtls1(void) |
| 233 | BIO_printf(bio_err, " -cipher - preferred cipher to use, use the 'openssl ciphers'\n"); | 285 | { |
| 234 | BIO_printf(bio_err, " command to see what is available\n"); | 286 | s_client_config.meth = DTLS_client_method(); |
| 235 | BIO_printf(bio_err, " -starttls prot - use the STARTTLS command before starting TLS\n"); | 287 | s_client_config.socket_type = SOCK_DGRAM; |
| 236 | BIO_printf(bio_err, " for those protocols that support it, where\n"); | 288 | return (0); |
| 237 | BIO_printf(bio_err, " 'prot' defines which one to assume. Currently,\n"); | 289 | } |
| 238 | BIO_printf(bio_err, " only \"smtp\", \"lmtp\", \"pop3\", \"imap\", \"ftp\" and \"xmpp\"\n"); | 290 | #endif |
| 239 | BIO_printf(bio_err, " are supported.\n"); | 291 | |
| 240 | BIO_printf(bio_err, " -xmpphost host - connect to this virtual host on the xmpp server\n"); | 292 | static int |
| 241 | BIO_printf(bio_err, " -sess_out arg - file to write SSL session to\n"); | 293 | s_client_opt_protocol_version_tls1(void) |
| 242 | BIO_printf(bio_err, " -sess_in arg - file to read SSL session from\n"); | 294 | { |
| 243 | BIO_printf(bio_err, " -servername host - Set TLS extension servername in ClientHello\n"); | 295 | s_client_config.min_version = TLS1_VERSION; |
| 244 | BIO_printf(bio_err, " -tlsextdebug - hex dump of all TLS extensions received\n"); | 296 | s_client_config.max_version = TLS1_VERSION; |
| 245 | BIO_printf(bio_err, " -status - request certificate status from server\n"); | 297 | return (0); |
| 246 | BIO_printf(bio_err, " -no_ticket - disable use of RFC4507bis session tickets\n"); | 298 | } |
| 247 | BIO_printf(bio_err, " -alpn arg - enable ALPN extension, considering named protocols supported (comma-separated list)\n"); | 299 | |
| 248 | BIO_printf(bio_err, " -groups arg - specify EC groups (colon-separated list)\n"); | 300 | static int |
| 301 | s_client_opt_protocol_version_tls1_1(void) | ||
| 302 | { | ||
| 303 | s_client_config.min_version = TLS1_1_VERSION; | ||
| 304 | s_client_config.max_version = TLS1_1_VERSION; | ||
| 305 | return (0); | ||
| 306 | } | ||
| 307 | |||
| 308 | static int | ||
| 309 | s_client_opt_protocol_version_tls1_2(void) | ||
| 310 | { | ||
| 311 | s_client_config.min_version = TLS1_2_VERSION; | ||
| 312 | s_client_config.max_version = TLS1_2_VERSION; | ||
| 313 | return (0); | ||
| 314 | } | ||
| 315 | |||
| 316 | static int | ||
| 317 | s_client_opt_protocol_version_tls1_3(void) | ||
| 318 | { | ||
| 319 | s_client_config.min_version = TLS1_3_VERSION; | ||
| 320 | s_client_config.max_version = TLS1_3_VERSION; | ||
| 321 | return (0); | ||
| 322 | } | ||
| 323 | |||
| 324 | static int | ||
| 325 | s_client_opt_quiet(void) | ||
| 326 | { | ||
| 327 | s_client_config.c_quiet = 1; | ||
| 328 | s_client_config.c_ign_eof = 1; | ||
| 329 | return (0); | ||
| 330 | } | ||
| 331 | |||
| 332 | static int | ||
| 333 | s_client_opt_starttls(char *arg) | ||
| 334 | { | ||
| 335 | if (strcmp(arg, "smtp") == 0) | ||
| 336 | s_client_config.starttls_proto = PROTO_SMTP; | ||
| 337 | else if (strcmp(arg, "lmtp") == 0) | ||
| 338 | s_client_config.starttls_proto = PROTO_LMTP; | ||
| 339 | else if (strcmp(arg, "pop3") == 0) | ||
| 340 | s_client_config.starttls_proto = PROTO_POP3; | ||
| 341 | else if (strcmp(arg, "imap") == 0) | ||
| 342 | s_client_config.starttls_proto = PROTO_IMAP; | ||
| 343 | else if (strcmp(arg, "ftp") == 0) | ||
| 344 | s_client_config.starttls_proto = PROTO_FTP; | ||
| 345 | else if (strcmp(arg, "xmpp") == 0) | ||
| 346 | s_client_config.starttls_proto = PROTO_XMPP; | ||
| 347 | else | ||
| 348 | return (1); | ||
| 349 | return (0); | ||
| 350 | } | ||
| 351 | |||
| 352 | static int | ||
| 353 | s_client_opt_verify(char *arg) | ||
| 354 | { | ||
| 355 | s_client_config.verify = SSL_VERIFY_PEER; | ||
| 356 | |||
| 357 | verify_depth = strtonum(arg, 0, INT_MAX, &s_client_config.errstr); | ||
| 358 | if (s_client_config.errstr != NULL) { | ||
| 359 | BIO_printf(bio_err, "invalid argument %s: %s\n", | ||
| 360 | arg, s_client_config.errstr); | ||
| 361 | return (1); | ||
| 362 | } | ||
| 363 | BIO_printf(bio_err, "verify depth is %d\n", verify_depth); | ||
| 364 | return (0); | ||
| 365 | } | ||
| 366 | |||
| 367 | static int | ||
| 368 | s_client_opt_verify_param(int argc, char **argv, int *argsused) | ||
| 369 | { | ||
| 370 | char **pargs = argv; | ||
| 371 | int pargc = argc; | ||
| 372 | int badarg = 0; | ||
| 373 | |||
| 374 | if (!args_verify(&pargs, &pargc, &badarg, bio_err, | ||
| 375 | &s_client_config.vpm)) { | ||
| 376 | BIO_printf(bio_err, "unknown option %s\n", *argv); | ||
| 377 | return (1); | ||
| 378 | } | ||
| 379 | if (badarg) | ||
| 380 | return (1); | ||
| 381 | |||
| 382 | *argsused = argc - pargc; | ||
| 383 | return (0); | ||
| 384 | } | ||
| 385 | |||
| 386 | static const struct option s_client_options[] = { | ||
| 387 | { | ||
| 388 | .name = "4", | ||
| 389 | .desc = "Use IPv4 only", | ||
| 390 | .type = OPTION_VALUE, | ||
| 391 | .opt.value = &s_client_config.af, | ||
| 392 | .value = AF_INET, | ||
| 393 | }, | ||
| 394 | { | ||
| 395 | .name = "6", | ||
| 396 | .desc = "Use IPv6 only", | ||
| 397 | .type = OPTION_VALUE, | ||
| 398 | .opt.value = &s_client_config.af, | ||
| 399 | .value = AF_INET6, | ||
| 400 | }, | ||
| 401 | { | ||
| 402 | .name = "alpn", | ||
| 403 | .argname = "protocols", | ||
| 404 | .desc = "Set the advertised protocols for ALPN" | ||
| 405 | " (comma-separated list)", | ||
| 406 | .type = OPTION_ARG, | ||
| 407 | .opt.arg = &s_client_config.alpn_in, | ||
| 408 | }, | ||
| 409 | { | ||
| 410 | .name = "bugs", | ||
| 411 | .desc = "Enable various workarounds for buggy implementations", | ||
| 412 | .type = OPTION_FLAG, | ||
| 413 | .opt.flag = &s_client_config.bugs, | ||
| 414 | }, | ||
| 415 | { | ||
| 416 | .name = "CAfile", | ||
| 417 | .argname = "file", | ||
| 418 | .desc = "PEM format file of CA certificates", | ||
| 419 | .type = OPTION_ARG, | ||
| 420 | .opt.arg = &s_client_config.CAfile, | ||
| 421 | }, | ||
| 422 | { | ||
| 423 | .name = "CApath", | ||
| 424 | .argname = "directory", | ||
| 425 | .desc = "PEM format directory of CA certificates", | ||
| 426 | .type = OPTION_ARG, | ||
| 427 | .opt.arg = &s_client_config.CApath, | ||
| 428 | }, | ||
| 429 | { | ||
| 430 | .name = "cert", | ||
| 431 | .argname = "file", | ||
| 432 | .desc = "Certificate file to use, PEM format assumed", | ||
| 433 | .type = OPTION_ARG, | ||
| 434 | .opt.arg = &s_client_config.cert_file, | ||
| 435 | }, | ||
| 436 | { | ||
| 437 | .name = "certform", | ||
| 438 | .argname = "fmt", | ||
| 439 | .desc = "Certificate format (PEM or DER) PEM default", | ||
| 440 | .type = OPTION_ARG_FORMAT, | ||
| 441 | .opt.value = &s_client_config.cert_format, | ||
| 442 | }, | ||
| 443 | { | ||
| 444 | .name = "cipher", | ||
| 445 | .argname = "cipherlist", | ||
| 446 | .desc = "Preferred cipher to use (see 'openssl ciphers')", | ||
| 447 | .type = OPTION_ARG, | ||
| 448 | .opt.arg = &s_client_config.cipher, | ||
| 449 | }, | ||
| 450 | { | ||
| 451 | .name = "connect", | ||
| 452 | .argname = "host:port", | ||
| 453 | .desc = "Who to connect to (default is localhost:4433)", | ||
| 454 | .type = OPTION_ARG, | ||
| 455 | .opt.arg = &s_client_config.connect, | ||
| 456 | }, | ||
| 457 | { | ||
| 458 | .name = "crlf", | ||
| 459 | .desc = "Convert LF from terminal into CRLF", | ||
| 460 | .type = OPTION_FLAG, | ||
| 461 | .opt.flag = &s_client_config.crlf, | ||
| 462 | }, | ||
| 463 | { | ||
| 464 | .name = "debug", | ||
| 465 | .desc = "Print extensive debugging information", | ||
| 466 | .type = OPTION_FLAG, | ||
| 467 | .opt.flag = &s_client_config.c_debug, | ||
| 468 | }, | ||
| 469 | #ifndef OPENSSL_NO_DTLS1 | ||
| 470 | { | ||
| 471 | .name = "dtls1", | ||
| 472 | .desc = "Just use DTLSv1", | ||
| 473 | .type = OPTION_FUNC, | ||
| 474 | .opt.func = s_client_opt_protocol_version_dtls1, | ||
| 475 | }, | ||
| 476 | #endif | ||
| 477 | { | ||
| 478 | .name = "groups", | ||
| 479 | .argname = "list", | ||
| 480 | .desc = "Specify EC groups (colon-separated list)", | ||
| 481 | .type = OPTION_ARG, | ||
| 482 | .opt.arg = &s_client_config.groups_in, | ||
| 483 | }, | ||
| 484 | { | ||
| 485 | .name = "host", | ||
| 486 | .argname = "host", | ||
| 487 | .desc = "Use -connect instead", | ||
| 488 | .type = OPTION_ARG, | ||
| 489 | .opt.arg = &s_client_config.host, | ||
| 490 | }, | ||
| 491 | { | ||
| 492 | .name = "ign_eof", | ||
| 493 | .desc = "Ignore input EOF (default when -quiet)", | ||
| 494 | .type = OPTION_VALUE, | ||
| 495 | .opt.value = &s_client_config.c_ign_eof, | ||
| 496 | .value = 1, | ||
| 497 | }, | ||
| 498 | { | ||
| 499 | .name = "key", | ||
| 500 | .argname = "file", | ||
| 501 | .desc = "Private key file to use, if not, -cert file is used", | ||
| 502 | .type = OPTION_ARG, | ||
| 503 | .opt.arg = &s_client_config.key_file, | ||
| 504 | }, | ||
| 505 | { | ||
| 506 | .name = "keyform", | ||
| 507 | .argname = "fmt", | ||
| 508 | .desc = "Key format (PEM or DER) PEM default", | ||
| 509 | .type = OPTION_ARG_FORMAT, | ||
| 510 | .opt.value = &s_client_config.key_format, | ||
| 511 | }, | ||
| 512 | { | ||
| 513 | .name = "keymatexport", | ||
| 514 | .argname = "label", | ||
| 515 | .desc = "Export keying material using label", | ||
| 516 | .type = OPTION_ARG, | ||
| 517 | .opt.arg = &s_client_config.keymatexportlabel, | ||
| 518 | }, | ||
| 519 | { | ||
| 520 | .name = "keymatexportlen", | ||
| 521 | .argname = "len", | ||
| 522 | .desc = "Export len bytes of keying material (default 20)", | ||
| 523 | .type = OPTION_ARG_FUNC, | ||
| 524 | .opt.argfunc = s_client_opt_keymatexportlen, | ||
| 525 | }, | ||
| 526 | { | ||
| 527 | .name = "legacy_renegotiation", | ||
| 528 | .type = OPTION_DISCARD, | ||
| 529 | }, | ||
| 530 | { | ||
| 531 | .name = "legacy_server_connect", | ||
| 532 | .desc = "Allow initial connection to servers that don't support RI", | ||
| 533 | .type = OPTION_VALUE_OR, | ||
| 534 | .opt.value = &s_client_config.off, | ||
| 535 | .value = SSL_OP_LEGACY_SERVER_CONNECT, | ||
| 536 | }, | ||
| 537 | { | ||
| 538 | .name = "msg", | ||
| 539 | .desc = "Show all protocol messages with hex dump", | ||
| 540 | .type = OPTION_FLAG, | ||
| 541 | .opt.flag = &s_client_config.c_msg, | ||
| 542 | }, | ||
| 543 | #ifndef OPENSSL_NO_DTLS1 | ||
| 544 | { | ||
| 545 | .name = "mtu", | ||
| 546 | .argname = "mtu", | ||
| 547 | .desc = "Set the link layer MTU on DTLS connections", | ||
| 548 | .type = OPTION_ARG_FUNC, | ||
| 549 | .opt.argfunc = s_client_opt_mtu, | ||
| 550 | }, | ||
| 551 | #endif | ||
| 552 | { | ||
| 553 | .name = "nbio", | ||
| 554 | .desc = "Turn on non-blocking I/O", | ||
| 555 | .type = OPTION_FLAG, | ||
| 556 | .opt.flag = &s_client_config.c_nbio, | ||
| 557 | }, | ||
| 558 | { | ||
| 559 | .name = "nbio_test", | ||
| 560 | .desc = "Test non-blocking I/O", | ||
| 561 | .type = OPTION_FLAG, | ||
| 562 | .opt.flag = &s_client_config.nbio_test, | ||
| 563 | }, | ||
| 564 | { | ||
| 565 | .name = "nextprotoneg", | ||
| 566 | .argname = "protocols", | ||
| 567 | .type = OPTION_ARG, | ||
| 568 | .opt.arg = &s_client_config.npn_in, /* Ignored. */ | ||
| 569 | }, | ||
| 570 | { | ||
| 571 | .name = "no_comp", | ||
| 572 | .type = OPTION_VALUE_OR, | ||
| 573 | .opt.value = &s_client_config.off, | ||
| 574 | .value = SSL_OP_NO_COMPRESSION, | ||
| 575 | }, | ||
| 576 | { | ||
| 577 | .name = "no_ign_eof", | ||
| 578 | .desc = "Don't ignore input EOF", | ||
| 579 | .type = OPTION_VALUE, | ||
| 580 | .opt.value = &s_client_config.c_ign_eof, | ||
| 581 | .value = 0, | ||
| 582 | }, | ||
| 583 | { | ||
| 584 | .name = "no_legacy_server_connect", | ||
| 585 | .desc = "Disallow initial connection to servers that don't support RI", | ||
| 586 | .type = OPTION_VALUE_OR, | ||
| 587 | .opt.value = &s_client_config.clr, | ||
| 588 | .value = SSL_OP_LEGACY_SERVER_CONNECT, | ||
| 589 | }, | ||
| 590 | { | ||
| 591 | .name = "no_ssl2", | ||
| 592 | .type = OPTION_VALUE_OR, | ||
| 593 | .opt.value = &s_client_config.off, | ||
| 594 | .value = SSL_OP_NO_SSLv2, | ||
| 595 | }, | ||
| 596 | { | ||
| 597 | .name = "no_ssl3", | ||
| 598 | .type = OPTION_VALUE_OR, | ||
| 599 | .opt.value = &s_client_config.off, | ||
| 600 | .value = SSL_OP_NO_SSLv3, | ||
| 601 | }, | ||
| 602 | { | ||
| 603 | .name = "no_ticket", | ||
| 604 | .desc = "Disable use of RFC4507 session ticket support", | ||
| 605 | .type = OPTION_VALUE_OR, | ||
| 606 | .opt.value = &s_client_config.off, | ||
| 607 | .value = SSL_OP_NO_TICKET, | ||
| 608 | }, | ||
| 609 | { | ||
| 610 | .name = "no_tls1", | ||
| 611 | .desc = "Disable the use of TLSv1", | ||
| 612 | .type = OPTION_VALUE_OR, | ||
| 613 | .opt.value = &s_client_config.off, | ||
| 614 | .value = SSL_OP_NO_TLSv1, | ||
| 615 | }, | ||
| 616 | { | ||
| 617 | .name = "no_tls1_1", | ||
| 618 | .desc = "Disable the use of TLSv1.1", | ||
| 619 | .type = OPTION_VALUE_OR, | ||
| 620 | .opt.value = &s_client_config.off, | ||
| 621 | .value = SSL_OP_NO_TLSv1_1, | ||
| 622 | }, | ||
| 623 | { | ||
| 624 | .name = "no_tls1_2", | ||
| 625 | .desc = "Disable the use of TLSv1.2", | ||
| 626 | .type = OPTION_VALUE_OR, | ||
| 627 | .opt.value = &s_client_config.off, | ||
| 628 | .value = SSL_OP_NO_TLSv1_2, | ||
| 629 | }, | ||
| 630 | { | ||
| 631 | .name = "no_tls1_3", | ||
| 632 | .desc = "Disable the use of TLSv1.3", | ||
| 633 | .type = OPTION_VALUE_OR, | ||
| 634 | .opt.value = &s_client_config.off, | ||
| 635 | .value = SSL_OP_NO_TLSv1_3, | ||
| 636 | }, | ||
| 637 | { | ||
| 638 | .name = "pass", | ||
| 639 | .argname = "arg", | ||
| 640 | .desc = "Private key file pass phrase source", | ||
| 641 | .type = OPTION_ARG, | ||
| 642 | .opt.arg = &s_client_config.passarg, | ||
| 643 | }, | ||
| 644 | { | ||
| 645 | .name = "pause", | ||
| 646 | .desc = "Pause 1 second between each read and write call", | ||
| 647 | .type = OPTION_FLAG, | ||
| 648 | .opt.flag = &s_client_config.c_Pause, | ||
| 649 | }, | ||
| 650 | { | ||
| 651 | .name = "peekaboo", | ||
| 652 | .type = OPTION_FLAG, | ||
| 653 | .opt.flag = &s_client_config.peekaboo, | ||
| 654 | }, | ||
| 655 | { | ||
| 656 | .name = "port", | ||
| 657 | .argname = "port", | ||
| 658 | .desc = "Use -connect instead", | ||
| 659 | .type = OPTION_ARG_FUNC, | ||
| 660 | .opt.argfunc = s_client_opt_port, | ||
| 661 | }, | ||
| 662 | { | ||
| 663 | .name = "prexit", | ||
| 664 | .desc = "Print session information when the program exits", | ||
| 665 | .type = OPTION_FLAG, | ||
| 666 | .opt.flag = &s_client_config.prexit, | ||
| 667 | }, | ||
| 668 | { | ||
| 669 | .name = "proxy", | ||
| 670 | .argname = "host:port", | ||
| 671 | .desc = "Connect to http proxy", | ||
| 672 | .type = OPTION_ARG, | ||
| 673 | .opt.arg = &s_client_config.proxy, | ||
| 674 | }, | ||
| 675 | { | ||
| 676 | .name = "quiet", | ||
| 677 | .desc = "Inhibit printing of session and certificate info", | ||
| 678 | .type = OPTION_FUNC, | ||
| 679 | .opt.func = s_client_opt_quiet, | ||
| 680 | }, | ||
| 681 | { | ||
| 682 | .name = "reconnect", | ||
| 683 | .desc = "Drop and re-make the connection with the same Session-ID", | ||
| 684 | .type = OPTION_VALUE, | ||
| 685 | .opt.value = &s_client_config.reconnect, | ||
| 686 | .value = 5, | ||
| 687 | }, | ||
| 688 | { | ||
| 689 | .name = "servername", | ||
| 690 | .argname = "name", | ||
| 691 | .desc = "Set TLS extension servername in ClientHello (SNI)", | ||
| 692 | .type = OPTION_ARG, | ||
| 693 | .opt.arg = &s_client_config.servername, | ||
| 694 | }, | ||
| 695 | { | ||
| 696 | .name = "serverpref", | ||
| 697 | .desc = "Use server's cipher preferences", | ||
| 698 | .type = OPTION_VALUE_OR, | ||
| 699 | .opt.value = &s_client_config.off, | ||
| 700 | .value = SSL_OP_CIPHER_SERVER_PREFERENCE, | ||
| 701 | }, | ||
| 702 | { | ||
| 703 | .name = "sess_in", | ||
| 704 | .argname = "file", | ||
| 705 | .desc = "File to read TLS session from", | ||
| 706 | .type = OPTION_ARG, | ||
| 707 | .opt.arg = &s_client_config.sess_in, | ||
| 708 | }, | ||
| 709 | { | ||
| 710 | .name = "sess_out", | ||
| 711 | .argname = "file", | ||
| 712 | .desc = "File to write TLS session to", | ||
| 713 | .type = OPTION_ARG, | ||
| 714 | .opt.arg = &s_client_config.sess_out, | ||
| 715 | }, | ||
| 716 | { | ||
| 717 | .name = "showcerts", | ||
| 718 | .desc = "Show all server certificates in the chain", | ||
| 719 | .type = OPTION_FLAG, | ||
| 720 | .opt.flag = &s_client_config.c_showcerts, | ||
| 721 | }, | ||
| 722 | { | ||
| 723 | .name = "starttls", | ||
| 724 | .argname = "protocol", | ||
| 725 | .desc = "Use the STARTTLS command before starting TLS,\n" | ||
| 726 | "smtp, lmtp, pop3, imap, ftp and xmpp are supported.", | ||
| 727 | .type = OPTION_ARG_FUNC, | ||
| 728 | .opt.argfunc = s_client_opt_starttls, | ||
| 729 | }, | ||
| 730 | { | ||
| 731 | .name = "state", | ||
| 732 | .desc = "Print the TLS session states", | ||
| 733 | .type = OPTION_FLAG, | ||
| 734 | .opt.flag = &s_client_config.state, | ||
| 735 | }, | ||
| 736 | { | ||
| 737 | .name = "status", | ||
| 738 | .desc = "Send a certificate status request to the server (OCSP)", | ||
| 739 | .type = OPTION_FLAG, | ||
| 740 | .opt.flag = &s_client_config.c_status_req, | ||
| 741 | }, | ||
| 742 | #ifndef OPENSSL_NO_DTLS1 | ||
| 743 | { | ||
| 744 | .name = "timeout", | ||
| 745 | .desc = "Enable send/receive timeout on DTLS connections", | ||
| 746 | .type = OPTION_FLAG, | ||
| 747 | .opt.flag = &s_client_config.enable_timeouts, | ||
| 748 | }, | ||
| 749 | #endif | ||
| 750 | { | ||
| 751 | .name = "tls1", | ||
| 752 | .desc = "Just use TLSv1", | ||
| 753 | .type = OPTION_FUNC, | ||
| 754 | .opt.func = s_client_opt_protocol_version_tls1, | ||
| 755 | }, | ||
| 756 | { | ||
| 757 | .name = "tls1_1", | ||
| 758 | .desc = "Just use TLSv1.1", | ||
| 759 | .type = OPTION_FUNC, | ||
| 760 | .opt.func = s_client_opt_protocol_version_tls1_1, | ||
| 761 | }, | ||
| 762 | { | ||
| 763 | .name = "tls1_2", | ||
| 764 | .desc = "Just use TLSv1.2", | ||
| 765 | .type = OPTION_FUNC, | ||
| 766 | .opt.func = s_client_opt_protocol_version_tls1_2, | ||
| 767 | }, | ||
| 768 | { | ||
| 769 | .name = "tls1_3", | ||
| 770 | .desc = "Just use TLSv1.3", | ||
| 771 | .type = OPTION_FUNC, | ||
| 772 | .opt.func = s_client_opt_protocol_version_tls1_3, | ||
| 773 | }, | ||
| 774 | { | ||
| 775 | .name = "tlsextdebug", | ||
| 776 | .desc = "Hex dump of all TLS extensions received", | ||
| 777 | .type = OPTION_FLAG, | ||
| 778 | .opt.flag = &s_client_config.c_tlsextdebug, | ||
| 779 | }, | ||
| 249 | #ifndef OPENSSL_NO_SRTP | 780 | #ifndef OPENSSL_NO_SRTP |
| 250 | BIO_printf(bio_err, " -use_srtp profiles - Offer SRTP key management with a colon-separated profile list\n"); | 781 | { |
| 782 | .name = "use_srtp", | ||
| 783 | .argname = "profiles", | ||
| 784 | .desc = "Offer SRTP key management with a colon-separated profiles", | ||
| 785 | .type = OPTION_ARG, | ||
| 786 | .opt.arg = &s_client_config.srtp_profiles, | ||
| 787 | }, | ||
| 251 | #endif | 788 | #endif |
| 252 | BIO_printf(bio_err, " -keymatexport label - Export keying material using label\n"); | 789 | { |
| 253 | BIO_printf(bio_err, " -keymatexportlen len - Export len bytes of keying material (default 20)\n"); | 790 | .name = "verify", |
| 791 | .argname = "depth", | ||
| 792 | .desc = "Turn on peer certificate verification, with a max of depth", | ||
| 793 | .type = OPTION_ARG_FUNC, | ||
| 794 | .opt.argfunc = s_client_opt_verify, | ||
| 795 | }, | ||
| 796 | { | ||
| 797 | .name = "verify_return_error", | ||
| 798 | .desc = "Return verification error", | ||
| 799 | .type = OPTION_FLAG, | ||
| 800 | .opt.flag = &verify_return_error, | ||
| 801 | }, | ||
| 802 | { | ||
| 803 | .name = "xmpphost", | ||
| 804 | .argname = "host", | ||
| 805 | .desc = "Connect to this virtual host on the xmpp server", | ||
| 806 | .type = OPTION_ARG, | ||
| 807 | .opt.arg = &s_client_config.xmpphost, | ||
| 808 | }, | ||
| 809 | { | ||
| 810 | .name = NULL, | ||
| 811 | .desc = "", | ||
| 812 | .type = OPTION_ARGV_FUNC, | ||
| 813 | .opt.argvfunc = s_client_opt_verify_param, | ||
| 814 | }, | ||
| 815 | { NULL }, | ||
| 816 | }; | ||
| 817 | |||
| 818 | static void | ||
| 819 | sc_usage(void) | ||
| 820 | { | ||
| 821 | fprintf(stderr, "usage: s_client " | ||
| 822 | "[-4 | -6] [-alpn protocols] [-bugs] [-CAfile file]\n" | ||
| 823 | " [-CApath directory] [-cert file] [-certform der | pem] [-check_ss_sig]\n" | ||
| 824 | " [-cipher cipherlist] [-connect host[:port]] [-crl_check]\n" | ||
| 825 | " [-crl_check_all] [-crlf] [-debug] [-dtls1] [-extended_crl]\n" | ||
| 826 | " [-groups list] [-host host] [-ign_eof] [-ignore_critical]\n" | ||
| 827 | " [-issuer_checks] [-key keyfile] [-keyform der | pem]\n" | ||
| 828 | " [-keymatexport label] [-keymatexportlen len] [-legacy_server_connect]\n" | ||
| 829 | " [-msg] [-mtu mtu] [-nbio] [-nbio_test] [-no_comp] [-no_ign_eof]\n" | ||
| 830 | " [-no_legacy_server_connect] [-no_ticket] [-no_tls1] [-no_tls1_1]\n" | ||
| 831 | " [-no_tls1_2] [-no_tls1_3] [-pass arg] [-pause] [-policy_check]\n" | ||
| 832 | " [-port port] [-prexit] [-proxy host:port] [-quiet] [-reconnect]\n" | ||
| 833 | " [-servername name] [-serverpref] [-sess_in file] [-sess_out file]\n" | ||
| 834 | " [-showcerts] [-starttls protocol] [-state] [-status] [-timeout]\n" | ||
| 835 | " [-tls1] [-tls1_1] [-tls1_2] [-tls1_3] [-tlsextdebug]\n" | ||
| 836 | " [-use_srtp profiles] [-verify depth] [-verify_return_error]\n" | ||
| 837 | " [-x509_strict] [-xmpphost host]\n"); | ||
| 838 | fprintf(stderr, "\n"); | ||
| 839 | options_usage(s_client_options); | ||
| 840 | fprintf(stderr, "\n"); | ||
| 254 | } | 841 | } |
| 255 | 842 | ||
| 256 | 843 | ||
| @@ -274,68 +861,29 @@ ssl_servername_cb(SSL * s, int *ad, void *arg) | |||
| 274 | return SSL_TLSEXT_ERR_OK; | 861 | return SSL_TLSEXT_ERR_OK; |
| 275 | } | 862 | } |
| 276 | 863 | ||
| 277 | #ifndef OPENSSL_NO_SRTP | ||
| 278 | char *srtp_profiles = NULL; | ||
| 279 | #endif | ||
| 280 | |||
| 281 | enum { | ||
| 282 | PROTO_OFF = 0, | ||
| 283 | PROTO_SMTP, | ||
| 284 | PROTO_LMTP, | ||
| 285 | PROTO_POP3, | ||
| 286 | PROTO_IMAP, | ||
| 287 | PROTO_FTP, | ||
| 288 | PROTO_XMPP | ||
| 289 | }; | ||
| 290 | |||
| 291 | int | 864 | int |
| 292 | s_client_main(int argc, char **argv) | 865 | s_client_main(int argc, char **argv) |
| 293 | { | 866 | { |
| 294 | unsigned int off = 0, clr = 0; | ||
| 295 | SSL *con = NULL; | 867 | SSL *con = NULL; |
| 296 | int s, k, p = 0, pending = 0, state = 0, af = AF_UNSPEC; | 868 | int s, k, p = 0, pending = 0; |
| 297 | char *cbuf = NULL, *sbuf = NULL, *mbuf = NULL, *pbuf = NULL; | 869 | char *cbuf = NULL, *sbuf = NULL, *mbuf = NULL, *pbuf = NULL; |
| 298 | int cbuf_len, cbuf_off; | 870 | int cbuf_len, cbuf_off; |
| 299 | int sbuf_len, sbuf_off; | 871 | int sbuf_len, sbuf_off; |
| 300 | int pbuf_len, pbuf_off; | 872 | int pbuf_len, pbuf_off; |
| 301 | char *port = PORT_STR; | ||
| 302 | int full_log = 1; | 873 | int full_log = 1; |
| 303 | char *host = SSL_HOST_NAME; | 874 | char *pass = NULL; |
| 304 | char *xmpphost = NULL; | ||
| 305 | char *proxy = NULL, *connect = NULL; | ||
| 306 | char *cert_file = NULL, *key_file = NULL; | ||
| 307 | int cert_format = FORMAT_PEM, key_format = FORMAT_PEM; | ||
| 308 | char *passarg = NULL, *pass = NULL; | ||
| 309 | X509 *cert = NULL; | 875 | X509 *cert = NULL; |
| 310 | EVP_PKEY *key = NULL; | 876 | EVP_PKEY *key = NULL; |
| 311 | char *CApath = NULL, *CAfile = NULL, *cipher = NULL; | 877 | int badop = 0; |
| 312 | int reconnect = 0, badop = 0, verify = SSL_VERIFY_NONE, bugs = 0; | ||
| 313 | int crlf = 0; | ||
| 314 | int write_tty, read_tty, write_ssl, read_ssl, tty_on, ssl_pending; | 878 | int write_tty, read_tty, write_ssl, read_ssl, tty_on, ssl_pending; |
| 315 | SSL_CTX *ctx = NULL; | 879 | SSL_CTX *ctx = NULL; |
| 316 | int ret = 1, in_init = 1, i, nbio_test = 0; | 880 | int ret = 1, in_init = 1, i; |
| 317 | int starttls_proto = PROTO_OFF; | ||
| 318 | int prexit = 0; | ||
| 319 | int peekaboo = 0; | ||
| 320 | X509_VERIFY_PARAM *vpm = NULL; | ||
| 321 | int badarg = 0; | ||
| 322 | const SSL_METHOD *meth = NULL; | ||
| 323 | int socket_type = SOCK_STREAM; | ||
| 324 | BIO *sbio; | 881 | BIO *sbio; |
| 325 | int mbuf_len = 0; | 882 | int mbuf_len = 0; |
| 326 | struct timeval timeout; | 883 | struct timeval timeout; |
| 327 | const char *errstr = NULL; | ||
| 328 | char *servername = NULL; | ||
| 329 | tlsextctx tlsextcbp = {NULL, 0}; | 884 | tlsextctx tlsextcbp = {NULL, 0}; |
| 330 | const char *alpn_in = NULL; | ||
| 331 | const char *groups_in = NULL; | ||
| 332 | char *sess_in = NULL; | ||
| 333 | char *sess_out = NULL; | ||
| 334 | struct sockaddr_storage peer; | 885 | struct sockaddr_storage peer; |
| 335 | int peerlen = sizeof(peer); | 886 | int peerlen = sizeof(peer); |
| 336 | int enable_timeouts = 0; | ||
| 337 | long socket_mtu = 0; | ||
| 338 | uint16_t min_version = 0, max_version = 0; | ||
| 339 | 887 | ||
| 340 | if (single_execution) { | 888 | if (single_execution) { |
| 341 | if (pledge("stdio cpath wpath rpath inet dns tty", NULL) == -1) { | 889 | if (pledge("stdio cpath wpath rpath inet dns tty", NULL) == -1) { |
| @@ -344,14 +892,17 @@ s_client_main(int argc, char **argv) | |||
| 344 | } | 892 | } |
| 345 | } | 893 | } |
| 346 | 894 | ||
| 347 | meth = TLS_client_method(); | 895 | memset(&s_client_config, 0, sizeof(s_client_config)); |
| 348 | 896 | s_client_config.af = AF_UNSPEC; | |
| 349 | c_Pause = 0; | 897 | s_client_config.cert_format = FORMAT_PEM; |
| 350 | c_quiet = 0; | 898 | s_client_config.host = SSL_HOST_NAME; |
| 351 | c_ign_eof = 0; | 899 | s_client_config.key_format = FORMAT_PEM; |
| 352 | c_debug = 0; | 900 | s_client_config.keymatexportlen = 20; |
| 353 | c_msg = 0; | 901 | s_client_config.meth = TLS_client_method(); |
| 354 | c_showcerts = 0; | 902 | s_client_config.port = PORT_STR; |
| 903 | s_client_config.socket_type = SOCK_STREAM; | ||
| 904 | s_client_config.starttls_proto = PROTO_OFF; | ||
| 905 | s_client_config.verify = SSL_VERIFY_NONE; | ||
| 355 | 906 | ||
| 356 | if (((cbuf = malloc(BUFSIZZ)) == NULL) || | 907 | if (((cbuf = malloc(BUFSIZZ)) == NULL) || |
| 357 | ((sbuf = malloc(BUFSIZZ)) == NULL) || | 908 | ((sbuf = malloc(BUFSIZZ)) == NULL) || |
| @@ -361,277 +912,46 @@ s_client_main(int argc, char **argv) | |||
| 361 | goto end; | 912 | goto end; |
| 362 | } | 913 | } |
| 363 | verify_depth = 0; | 914 | verify_depth = 0; |
| 364 | c_nbio = 0; | 915 | |
| 365 | 916 | if (options_parse(argc, argv, s_client_options, NULL, NULL) != 0) { | |
| 366 | argc--; | 917 | badop = 1; |
| 367 | argv++; | 918 | goto bad; |
| 368 | while (argc >= 1) { | ||
| 369 | if (strcmp(*argv, "-host") == 0) { | ||
| 370 | if (--argc < 1) | ||
| 371 | goto bad; | ||
| 372 | host = *(++argv); | ||
| 373 | } else if (strcmp(*argv, "-port") == 0) { | ||
| 374 | if (--argc < 1) | ||
| 375 | goto bad; | ||
| 376 | port = *(++argv); | ||
| 377 | if (port == NULL || *port == '\0') | ||
| 378 | goto bad; | ||
| 379 | } else if (strcmp(*argv, "-connect") == 0) { | ||
| 380 | if (--argc < 1) | ||
| 381 | goto bad; | ||
| 382 | connect = *(++argv); | ||
| 383 | } else if (strcmp(*argv, "-proxy") == 0) { | ||
| 384 | if (--argc < 1) | ||
| 385 | goto bad; | ||
| 386 | proxy = *(++argv); | ||
| 387 | } else if (strcmp(*argv,"-xmpphost") == 0) { | ||
| 388 | if (--argc < 1) | ||
| 389 | goto bad; | ||
| 390 | xmpphost= *(++argv); | ||
| 391 | } else if (strcmp(*argv, "-verify") == 0) { | ||
| 392 | verify = SSL_VERIFY_PEER; | ||
| 393 | if (--argc < 1) | ||
| 394 | goto bad; | ||
| 395 | verify_depth = strtonum(*(++argv), 0, INT_MAX, &errstr); | ||
| 396 | if (errstr) | ||
| 397 | goto bad; | ||
| 398 | BIO_printf(bio_err, "verify depth is %d\n", verify_depth); | ||
| 399 | } else if (strcmp(*argv, "-cert") == 0) { | ||
| 400 | if (--argc < 1) | ||
| 401 | goto bad; | ||
| 402 | cert_file = *(++argv); | ||
| 403 | } else if (strcmp(*argv, "-sess_out") == 0) { | ||
| 404 | if (--argc < 1) | ||
| 405 | goto bad; | ||
| 406 | sess_out = *(++argv); | ||
| 407 | } else if (strcmp(*argv, "-sess_in") == 0) { | ||
| 408 | if (--argc < 1) | ||
| 409 | goto bad; | ||
| 410 | sess_in = *(++argv); | ||
| 411 | } else if (strcmp(*argv, "-certform") == 0) { | ||
| 412 | if (--argc < 1) | ||
| 413 | goto bad; | ||
| 414 | cert_format = str2fmt(*(++argv)); | ||
| 415 | } else if (args_verify(&argv, &argc, &badarg, bio_err, &vpm)) { | ||
| 416 | if (badarg) | ||
| 417 | goto bad; | ||
| 418 | continue; | ||
| 419 | } else if (strcmp(*argv, "-verify_return_error") == 0) | ||
| 420 | verify_return_error = 1; | ||
| 421 | else if (strcmp(*argv, "-prexit") == 0) | ||
| 422 | prexit = 1; | ||
| 423 | else if (strcmp(*argv, "-peekaboo") == 0) | ||
| 424 | peekaboo = 1; | ||
| 425 | else if (strcmp(*argv, "-crlf") == 0) | ||
| 426 | crlf = 1; | ||
| 427 | else if (strcmp(*argv, "-quiet") == 0) { | ||
| 428 | c_quiet = 1; | ||
| 429 | c_ign_eof = 1; | ||
| 430 | } else if (strcmp(*argv, "-ign_eof") == 0) | ||
| 431 | c_ign_eof = 1; | ||
| 432 | else if (strcmp(*argv, "-no_ign_eof") == 0) | ||
| 433 | c_ign_eof = 0; | ||
| 434 | else if (strcmp(*argv, "-pause") == 0) | ||
| 435 | c_Pause = 1; | ||
| 436 | else if (strcmp(*argv, "-debug") == 0) | ||
| 437 | c_debug = 1; | ||
| 438 | else if (strcmp(*argv, "-tlsextdebug") == 0) | ||
| 439 | c_tlsextdebug = 1; | ||
| 440 | else if (strcmp(*argv, "-status") == 0) | ||
| 441 | c_status_req = 1; | ||
| 442 | else if (strcmp(*argv, "-msg") == 0) | ||
| 443 | c_msg = 1; | ||
| 444 | else if (strcmp(*argv, "-showcerts") == 0) | ||
| 445 | c_showcerts = 1; | ||
| 446 | else if (strcmp(*argv, "-nbio_test") == 0) | ||
| 447 | nbio_test = 1; | ||
| 448 | else if (strcmp(*argv, "-state") == 0) | ||
| 449 | state = 1; | ||
| 450 | else if (strcmp(*argv, "-tls1_3") == 0) { | ||
| 451 | min_version = TLS1_3_VERSION; | ||
| 452 | max_version = TLS1_3_VERSION; | ||
| 453 | } else if (strcmp(*argv, "-tls1_2") == 0) { | ||
| 454 | min_version = TLS1_2_VERSION; | ||
| 455 | max_version = TLS1_2_VERSION; | ||
| 456 | } else if (strcmp(*argv, "-tls1_1") == 0) { | ||
| 457 | min_version = TLS1_1_VERSION; | ||
| 458 | max_version = TLS1_1_VERSION; | ||
| 459 | } else if (strcmp(*argv, "-tls1") == 0) { | ||
| 460 | min_version = TLS1_VERSION; | ||
| 461 | max_version = TLS1_VERSION; | ||
| 462 | #ifndef OPENSSL_NO_DTLS1 | ||
| 463 | } else if (strcmp(*argv, "-dtls1") == 0) { | ||
| 464 | meth = DTLS_client_method(); | ||
| 465 | socket_type = SOCK_DGRAM; | ||
| 466 | } else if (strcmp(*argv, "-timeout") == 0) | ||
| 467 | enable_timeouts = 1; | ||
| 468 | else if (strcmp(*argv, "-mtu") == 0) { | ||
| 469 | if (--argc < 1) | ||
| 470 | goto bad; | ||
| 471 | socket_mtu = strtonum(*(++argv), 0, LONG_MAX, &errstr); | ||
| 472 | if (errstr) | ||
| 473 | goto bad; | ||
| 474 | } | ||
| 475 | #endif | ||
| 476 | else if (strcmp(*argv, "-bugs") == 0) | ||
| 477 | bugs = 1; | ||
| 478 | else if (strcmp(*argv, "-keyform") == 0) { | ||
| 479 | if (--argc < 1) | ||
| 480 | goto bad; | ||
| 481 | key_format = str2fmt(*(++argv)); | ||
| 482 | } else if (strcmp(*argv, "-pass") == 0) { | ||
| 483 | if (--argc < 1) | ||
| 484 | goto bad; | ||
| 485 | passarg = *(++argv); | ||
| 486 | } else if (strcmp(*argv, "-key") == 0) { | ||
| 487 | if (--argc < 1) | ||
| 488 | goto bad; | ||
| 489 | key_file = *(++argv); | ||
| 490 | } else if (strcmp(*argv, "-reconnect") == 0) { | ||
| 491 | reconnect = 5; | ||
| 492 | } else if (strcmp(*argv, "-CApath") == 0) { | ||
| 493 | if (--argc < 1) | ||
| 494 | goto bad; | ||
| 495 | CApath = *(++argv); | ||
| 496 | } else if (strcmp(*argv, "-CAfile") == 0) { | ||
| 497 | if (--argc < 1) | ||
| 498 | goto bad; | ||
| 499 | CAfile = *(++argv); | ||
| 500 | } else if (strcmp(*argv, "-no_tls1_3") == 0) | ||
| 501 | off |= SSL_OP_NO_TLSv1_3; | ||
| 502 | else if (strcmp(*argv, "-no_tls1_2") == 0) | ||
| 503 | off |= SSL_OP_NO_TLSv1_2; | ||
| 504 | else if (strcmp(*argv, "-no_tls1_1") == 0) | ||
| 505 | off |= SSL_OP_NO_TLSv1_1; | ||
| 506 | else if (strcmp(*argv, "-no_tls1") == 0) | ||
| 507 | off |= SSL_OP_NO_TLSv1; | ||
| 508 | else if (strcmp(*argv, "-no_ssl3") == 0) | ||
| 509 | off |= SSL_OP_NO_SSLv3; | ||
| 510 | else if (strcmp(*argv, "-no_ssl2") == 0) | ||
| 511 | off |= SSL_OP_NO_SSLv2; | ||
| 512 | else if (strcmp(*argv, "-no_comp") == 0) { | ||
| 513 | off |= SSL_OP_NO_COMPRESSION; | ||
| 514 | } else if (strcmp(*argv, "-no_ticket") == 0) { | ||
| 515 | off |= SSL_OP_NO_TICKET; | ||
| 516 | } else if (strcmp(*argv, "-nextprotoneg") == 0) { | ||
| 517 | /* Ignored. */ | ||
| 518 | if (--argc < 1) | ||
| 519 | goto bad; | ||
| 520 | ++argv; | ||
| 521 | } else if (strcmp(*argv, "-alpn") == 0) { | ||
| 522 | if (--argc < 1) | ||
| 523 | goto bad; | ||
| 524 | alpn_in = *(++argv); | ||
| 525 | } else if (strcmp(*argv, "-groups") == 0) { | ||
| 526 | if (--argc < 1) | ||
| 527 | goto bad; | ||
| 528 | groups_in = *(++argv); | ||
| 529 | } else if (strcmp(*argv, "-serverpref") == 0) | ||
| 530 | off |= SSL_OP_CIPHER_SERVER_PREFERENCE; | ||
| 531 | else if (strcmp(*argv, "-legacy_renegotiation") == 0) | ||
| 532 | ; /* no-op */ | ||
| 533 | else if (strcmp(*argv, "-legacy_server_connect") == 0) { | ||
| 534 | off |= SSL_OP_LEGACY_SERVER_CONNECT; | ||
| 535 | } else if (strcmp(*argv, "-no_legacy_server_connect") == 0) { | ||
| 536 | clr |= SSL_OP_LEGACY_SERVER_CONNECT; | ||
| 537 | } else if (strcmp(*argv, "-cipher") == 0) { | ||
| 538 | if (--argc < 1) | ||
| 539 | goto bad; | ||
| 540 | cipher = *(++argv); | ||
| 541 | } | ||
| 542 | else if (strcmp(*argv, "-nbio") == 0) { | ||
| 543 | c_nbio = 1; | ||
| 544 | } | ||
| 545 | else if (strcmp(*argv, "-starttls") == 0) { | ||
| 546 | if (--argc < 1) | ||
| 547 | goto bad; | ||
| 548 | ++argv; | ||
| 549 | if (strcmp(*argv, "smtp") == 0) | ||
| 550 | starttls_proto = PROTO_SMTP; | ||
| 551 | else if (strcmp(*argv, "lmtp") == 0) | ||
| 552 | starttls_proto = PROTO_LMTP; | ||
| 553 | else if (strcmp(*argv, "pop3") == 0) | ||
| 554 | starttls_proto = PROTO_POP3; | ||
| 555 | else if (strcmp(*argv, "imap") == 0) | ||
| 556 | starttls_proto = PROTO_IMAP; | ||
| 557 | else if (strcmp(*argv, "ftp") == 0) | ||
| 558 | starttls_proto = PROTO_FTP; | ||
| 559 | else if (strcmp(*argv, "xmpp") == 0) | ||
| 560 | starttls_proto = PROTO_XMPP; | ||
| 561 | else | ||
| 562 | goto bad; | ||
| 563 | } else if (strcmp(*argv, "-4") == 0) { | ||
| 564 | af = AF_INET; | ||
| 565 | } else if (strcmp(*argv, "-6") == 0) { | ||
| 566 | af = AF_INET6; | ||
| 567 | } else if (strcmp(*argv, "-servername") == 0) { | ||
| 568 | if (--argc < 1) | ||
| 569 | goto bad; | ||
| 570 | servername = *(++argv); | ||
| 571 | } | ||
| 572 | #ifndef OPENSSL_NO_SRTP | ||
| 573 | else if (strcmp(*argv, "-use_srtp") == 0) { | ||
| 574 | if (--argc < 1) | ||
| 575 | goto bad; | ||
| 576 | srtp_profiles = *(++argv); | ||
| 577 | } | ||
| 578 | #endif | ||
| 579 | else if (strcmp(*argv, "-keymatexport") == 0) { | ||
| 580 | if (--argc < 1) | ||
| 581 | goto bad; | ||
| 582 | keymatexportlabel = *(++argv); | ||
| 583 | } else if (strcmp(*argv, "-keymatexportlen") == 0) { | ||
| 584 | if (--argc < 1) | ||
| 585 | goto bad; | ||
| 586 | keymatexportlen = strtonum(*(++argv), 1, INT_MAX, &errstr); | ||
| 587 | if (errstr) | ||
| 588 | goto bad; | ||
| 589 | } else { | ||
| 590 | BIO_printf(bio_err, "unknown option %s\n", *argv); | ||
| 591 | badop = 1; | ||
| 592 | break; | ||
| 593 | } | ||
| 594 | argc--; | ||
| 595 | argv++; | ||
| 596 | } | 919 | } |
| 597 | if (proxy != NULL) { | 920 | if (s_client_config.proxy != NULL) { |
| 598 | if (!extract_host_port(proxy, &host, NULL, &port)) | 921 | if (!extract_host_port(s_client_config.proxy, &s_client_config.host, NULL, &s_client_config.port)) |
| 599 | goto bad; | 922 | goto bad; |
| 600 | if (connect == NULL) | 923 | if (s_client_config.connect == NULL) |
| 601 | connect = SSL_HOST_NAME; | 924 | s_client_config.connect = SSL_HOST_NAME; |
| 602 | } else if (connect != NULL) { | 925 | } else if (s_client_config.connect != NULL) { |
| 603 | if (!extract_host_port(connect, &host, NULL, &port)) | 926 | if (!extract_host_port(s_client_config.connect, &s_client_config.host, NULL, &s_client_config.port)) |
| 604 | goto bad; | 927 | goto bad; |
| 605 | } | 928 | } |
| 606 | if (badop) { | 929 | if (badop) { |
| 607 | bad: | 930 | bad: |
| 608 | if (errstr) | 931 | if (s_client_config.errstr == NULL) |
| 609 | BIO_printf(bio_err, "invalid argument %s: %s\n", | ||
| 610 | *argv, errstr); | ||
| 611 | else | ||
| 612 | sc_usage(); | 932 | sc_usage(); |
| 613 | goto end; | 933 | goto end; |
| 614 | } | 934 | } |
| 615 | 935 | ||
| 616 | if (!app_passwd(bio_err, passarg, NULL, &pass, NULL)) { | 936 | if (!app_passwd(bio_err, s_client_config.passarg, NULL, &pass, NULL)) { |
| 617 | BIO_printf(bio_err, "Error getting password\n"); | 937 | BIO_printf(bio_err, "Error getting password\n"); |
| 618 | goto end; | 938 | goto end; |
| 619 | } | 939 | } |
| 620 | if (key_file == NULL) | 940 | if (s_client_config.key_file == NULL) |
| 621 | key_file = cert_file; | 941 | s_client_config.key_file = s_client_config.cert_file; |
| 622 | 942 | ||
| 623 | 943 | ||
| 624 | if (key_file) { | 944 | if (s_client_config.key_file) { |
| 625 | 945 | ||
| 626 | key = load_key(bio_err, key_file, key_format, 0, pass, | 946 | key = load_key(bio_err, s_client_config.key_file, s_client_config.key_format, 0, pass, |
| 627 | "client certificate private key file"); | 947 | "client certificate private key file"); |
| 628 | if (!key) { | 948 | if (!key) { |
| 629 | ERR_print_errors(bio_err); | 949 | ERR_print_errors(bio_err); |
| 630 | goto end; | 950 | goto end; |
| 631 | } | 951 | } |
| 632 | } | 952 | } |
| 633 | if (cert_file) { | 953 | if (s_client_config.cert_file) { |
| 634 | cert = load_cert(bio_err, cert_file, cert_format, | 954 | cert = load_cert(bio_err, s_client_config.cert_file, s_client_config.cert_format, |
| 635 | NULL, "client certificate file"); | 955 | NULL, "client certificate file"); |
| 636 | 956 | ||
| 637 | if (!cert) { | 957 | if (!cert) { |
| @@ -640,7 +960,7 @@ s_client_main(int argc, char **argv) | |||
| 640 | } | 960 | } |
| 641 | } | 961 | } |
| 642 | if (bio_c_out == NULL) { | 962 | if (bio_c_out == NULL) { |
| 643 | if (c_quiet && !c_debug && !c_msg) { | 963 | if (s_client_config.c_quiet && !s_client_config.c_debug && !s_client_config.c_msg) { |
| 644 | bio_c_out = BIO_new(BIO_s_null()); | 964 | bio_c_out = BIO_new(BIO_s_null()); |
| 645 | } else { | 965 | } else { |
| 646 | if (bio_c_out == NULL) | 966 | if (bio_c_out == NULL) |
| @@ -648,7 +968,7 @@ s_client_main(int argc, char **argv) | |||
| 648 | } | 968 | } |
| 649 | } | 969 | } |
| 650 | 970 | ||
| 651 | ctx = SSL_CTX_new(meth); | 971 | ctx = SSL_CTX_new(s_client_config.meth); |
| 652 | if (ctx == NULL) { | 972 | if (ctx == NULL) { |
| 653 | ERR_print_errors(bio_err); | 973 | ERR_print_errors(bio_err); |
| 654 | goto end; | 974 | goto end; |
| @@ -656,35 +976,35 @@ s_client_main(int argc, char **argv) | |||
| 656 | 976 | ||
| 657 | SSL_CTX_clear_mode(ctx, SSL_MODE_AUTO_RETRY); | 977 | SSL_CTX_clear_mode(ctx, SSL_MODE_AUTO_RETRY); |
| 658 | 978 | ||
| 659 | if (vpm) | 979 | if (s_client_config.vpm) |
| 660 | SSL_CTX_set1_param(ctx, vpm); | 980 | SSL_CTX_set1_param(ctx, s_client_config.vpm); |
| 661 | 981 | ||
| 662 | if (!SSL_CTX_set_min_proto_version(ctx, min_version)) | 982 | if (!SSL_CTX_set_min_proto_version(ctx, s_client_config.min_version)) |
| 663 | goto end; | 983 | goto end; |
| 664 | if (!SSL_CTX_set_max_proto_version(ctx, max_version)) | 984 | if (!SSL_CTX_set_max_proto_version(ctx, s_client_config.max_version)) |
| 665 | goto end; | 985 | goto end; |
| 666 | 986 | ||
| 667 | #ifndef OPENSSL_NO_SRTP | 987 | #ifndef OPENSSL_NO_SRTP |
| 668 | if (srtp_profiles != NULL) | 988 | if (s_client_config.srtp_profiles != NULL) |
| 669 | SSL_CTX_set_tlsext_use_srtp(ctx, srtp_profiles); | 989 | SSL_CTX_set_tlsext_use_srtp(ctx, s_client_config.srtp_profiles); |
| 670 | #endif | 990 | #endif |
| 671 | if (bugs) | 991 | if (s_client_config.bugs) |
| 672 | SSL_CTX_set_options(ctx, SSL_OP_ALL | off); | 992 | SSL_CTX_set_options(ctx, SSL_OP_ALL | s_client_config.off); |
| 673 | else | 993 | else |
| 674 | SSL_CTX_set_options(ctx, off); | 994 | SSL_CTX_set_options(ctx, s_client_config.off); |
| 675 | 995 | ||
| 676 | if (clr) | 996 | if (s_client_config.clr) |
| 677 | SSL_CTX_clear_options(ctx, clr); | 997 | SSL_CTX_clear_options(ctx, s_client_config.clr); |
| 678 | /* | 998 | /* |
| 679 | * DTLS: partial reads end up discarding unread UDP bytes :-( Setting | 999 | * DTLS: partial reads end up discarding unread UDP bytes :-( Setting |
| 680 | * read ahead solves this problem. | 1000 | * read ahead solves this problem. |
| 681 | */ | 1001 | */ |
| 682 | if (socket_type == SOCK_DGRAM) | 1002 | if (s_client_config.socket_type == SOCK_DGRAM) |
| 683 | SSL_CTX_set_read_ahead(ctx, 1); | 1003 | SSL_CTX_set_read_ahead(ctx, 1); |
| 684 | 1004 | ||
| 685 | if (alpn_in) { | 1005 | if (s_client_config.alpn_in) { |
| 686 | unsigned short alpn_len; | 1006 | unsigned short alpn_len; |
| 687 | unsigned char *alpn = next_protos_parse(&alpn_len, alpn_in); | 1007 | unsigned char *alpn = next_protos_parse(&alpn_len, s_client_config.alpn_in); |
| 688 | 1008 | ||
| 689 | if (alpn == NULL) { | 1009 | if (alpn == NULL) { |
| 690 | BIO_printf(bio_err, "Error parsing -alpn argument\n"); | 1010 | BIO_printf(bio_err, "Error parsing -alpn argument\n"); |
| @@ -693,47 +1013,47 @@ s_client_main(int argc, char **argv) | |||
| 693 | SSL_CTX_set_alpn_protos(ctx, alpn, alpn_len); | 1013 | SSL_CTX_set_alpn_protos(ctx, alpn, alpn_len); |
| 694 | free(alpn); | 1014 | free(alpn); |
| 695 | } | 1015 | } |
| 696 | if (groups_in != NULL) { | 1016 | if (s_client_config.groups_in != NULL) { |
| 697 | if (SSL_CTX_set1_groups_list(ctx, groups_in) != 1) { | 1017 | if (SSL_CTX_set1_groups_list(ctx, s_client_config.groups_in) != 1) { |
| 698 | BIO_printf(bio_err, "Failed to set groups '%s'\n", | 1018 | BIO_printf(bio_err, "Failed to set groups '%s'\n", |
| 699 | groups_in); | 1019 | s_client_config.groups_in); |
| 700 | goto end; | 1020 | goto end; |
| 701 | } | 1021 | } |
| 702 | } | 1022 | } |
| 703 | 1023 | ||
| 704 | if (state) | 1024 | if (s_client_config.state) |
| 705 | SSL_CTX_set_info_callback(ctx, apps_ssl_info_callback); | 1025 | SSL_CTX_set_info_callback(ctx, apps_ssl_info_callback); |
| 706 | if (cipher != NULL) | 1026 | if (s_client_config.cipher != NULL) |
| 707 | if (!SSL_CTX_set_cipher_list(ctx, cipher)) { | 1027 | if (!SSL_CTX_set_cipher_list(ctx, s_client_config.cipher)) { |
| 708 | BIO_printf(bio_err, "error setting cipher list\n"); | 1028 | BIO_printf(bio_err, "error setting cipher list\n"); |
| 709 | ERR_print_errors(bio_err); | 1029 | ERR_print_errors(bio_err); |
| 710 | goto end; | 1030 | goto end; |
| 711 | } | 1031 | } |
| 712 | 1032 | ||
| 713 | SSL_CTX_set_verify(ctx, verify, verify_callback); | 1033 | SSL_CTX_set_verify(ctx, s_client_config.verify, verify_callback); |
| 714 | if (!set_cert_key_stuff(ctx, cert, key)) | 1034 | if (!set_cert_key_stuff(ctx, cert, key)) |
| 715 | goto end; | 1035 | goto end; |
| 716 | 1036 | ||
| 717 | if ((CAfile || CApath) | 1037 | if ((s_client_config.CAfile || s_client_config.CApath) |
| 718 | && !SSL_CTX_load_verify_locations(ctx, CAfile, CApath)) | 1038 | && !SSL_CTX_load_verify_locations(ctx, s_client_config.CAfile, s_client_config.CApath)) |
| 719 | ERR_print_errors(bio_err); | 1039 | ERR_print_errors(bio_err); |
| 720 | 1040 | ||
| 721 | if (!SSL_CTX_set_default_verify_paths(ctx)) | 1041 | if (!SSL_CTX_set_default_verify_paths(ctx)) |
| 722 | ERR_print_errors(bio_err); | 1042 | ERR_print_errors(bio_err); |
| 723 | 1043 | ||
| 724 | if (servername != NULL) { | 1044 | if (s_client_config.servername != NULL) { |
| 725 | tlsextcbp.biodebug = bio_err; | 1045 | tlsextcbp.biodebug = bio_err; |
| 726 | SSL_CTX_set_tlsext_servername_callback(ctx, ssl_servername_cb); | 1046 | SSL_CTX_set_tlsext_servername_callback(ctx, ssl_servername_cb); |
| 727 | SSL_CTX_set_tlsext_servername_arg(ctx, &tlsextcbp); | 1047 | SSL_CTX_set_tlsext_servername_arg(ctx, &tlsextcbp); |
| 728 | } | 1048 | } |
| 729 | 1049 | ||
| 730 | con = SSL_new(ctx); | 1050 | con = SSL_new(ctx); |
| 731 | if (sess_in) { | 1051 | if (s_client_config.sess_in) { |
| 732 | SSL_SESSION *sess; | 1052 | SSL_SESSION *sess; |
| 733 | BIO *stmp = BIO_new_file(sess_in, "r"); | 1053 | BIO *stmp = BIO_new_file(s_client_config.sess_in, "r"); |
| 734 | if (!stmp) { | 1054 | if (!stmp) { |
| 735 | BIO_printf(bio_err, "Can't open session file %s\n", | 1055 | BIO_printf(bio_err, "Can't open session file %s\n", |
| 736 | sess_in); | 1056 | s_client_config.sess_in); |
| 737 | ERR_print_errors(bio_err); | 1057 | ERR_print_errors(bio_err); |
| 738 | goto end; | 1058 | goto end; |
| 739 | } | 1059 | } |
| @@ -741,15 +1061,15 @@ s_client_main(int argc, char **argv) | |||
| 741 | BIO_free(stmp); | 1061 | BIO_free(stmp); |
| 742 | if (!sess) { | 1062 | if (!sess) { |
| 743 | BIO_printf(bio_err, "Can't open session file %s\n", | 1063 | BIO_printf(bio_err, "Can't open session file %s\n", |
| 744 | sess_in); | 1064 | s_client_config.sess_in); |
| 745 | ERR_print_errors(bio_err); | 1065 | ERR_print_errors(bio_err); |
| 746 | goto end; | 1066 | goto end; |
| 747 | } | 1067 | } |
| 748 | SSL_set_session(con, sess); | 1068 | SSL_set_session(con, sess); |
| 749 | SSL_SESSION_free(sess); | 1069 | SSL_SESSION_free(sess); |
| 750 | } | 1070 | } |
| 751 | if (servername != NULL) { | 1071 | if (s_client_config.servername != NULL) { |
| 752 | if (!SSL_set_tlsext_host_name(con, servername)) { | 1072 | if (!SSL_set_tlsext_host_name(con, s_client_config.servername)) { |
| 753 | BIO_printf(bio_err, "Unable to set TLS servername extension.\n"); | 1073 | BIO_printf(bio_err, "Unable to set TLS servername extension.\n"); |
| 754 | ERR_print_errors(bio_err); | 1074 | ERR_print_errors(bio_err); |
| 755 | goto end; | 1075 | goto end; |
| @@ -759,21 +1079,21 @@ s_client_main(int argc, char **argv) | |||
| 759 | 1079 | ||
| 760 | re_start: | 1080 | re_start: |
| 761 | 1081 | ||
| 762 | if (init_client(&s, host, port, socket_type, af) == 0) { | 1082 | if (init_client(&s, s_client_config.host, s_client_config.port, s_client_config.socket_type, s_client_config.af) == 0) { |
| 763 | BIO_printf(bio_err, "connect:errno=%d\n", errno); | 1083 | BIO_printf(bio_err, "connect:errno=%d\n", errno); |
| 764 | goto end; | 1084 | goto end; |
| 765 | } | 1085 | } |
| 766 | BIO_printf(bio_c_out, "CONNECTED(%08X)\n", s); | 1086 | BIO_printf(bio_c_out, "CONNECTED(%08X)\n", s); |
| 767 | 1087 | ||
| 768 | if (c_nbio) { | 1088 | if (s_client_config.c_nbio) { |
| 769 | if (!c_quiet) | 1089 | if (!s_client_config.c_quiet) |
| 770 | BIO_printf(bio_c_out, "turning on non blocking io\n"); | 1090 | BIO_printf(bio_c_out, "turning on non blocking io\n"); |
| 771 | if (!BIO_socket_nbio(s, 1)) { | 1091 | if (!BIO_socket_nbio(s, 1)) { |
| 772 | ERR_print_errors(bio_err); | 1092 | ERR_print_errors(bio_err); |
| 773 | goto end; | 1093 | goto end; |
| 774 | } | 1094 | } |
| 775 | } | 1095 | } |
| 776 | if (c_Pause & 0x01) | 1096 | if (s_client_config.c_Pause & 0x01) |
| 777 | SSL_set_debug(con, 1); | 1097 | SSL_set_debug(con, 1); |
| 778 | 1098 | ||
| 779 | if (SSL_version(con) == DTLS1_VERSION) { | 1099 | if (SSL_version(con) == DTLS1_VERSION) { |
| @@ -789,7 +1109,7 @@ re_start: | |||
| 789 | } | 1109 | } |
| 790 | (void) BIO_ctrl_set_connected(sbio, 1, &peer); | 1110 | (void) BIO_ctrl_set_connected(sbio, 1, &peer); |
| 791 | 1111 | ||
| 792 | if (enable_timeouts) { | 1112 | if (s_client_config.enable_timeouts) { |
| 793 | timeout.tv_sec = 0; | 1113 | timeout.tv_sec = 0; |
| 794 | timeout.tv_usec = DGRAM_RCV_TIMEOUT; | 1114 | timeout.tv_usec = DGRAM_RCV_TIMEOUT; |
| 795 | BIO_ctrl(sbio, BIO_CTRL_DGRAM_SET_RECV_TIMEOUT, 0, &timeout); | 1115 | BIO_ctrl(sbio, BIO_CTRL_DGRAM_SET_RECV_TIMEOUT, 0, &timeout); |
| @@ -798,35 +1118,35 @@ re_start: | |||
| 798 | timeout.tv_usec = DGRAM_SND_TIMEOUT; | 1118 | timeout.tv_usec = DGRAM_SND_TIMEOUT; |
| 799 | BIO_ctrl(sbio, BIO_CTRL_DGRAM_SET_SEND_TIMEOUT, 0, &timeout); | 1119 | BIO_ctrl(sbio, BIO_CTRL_DGRAM_SET_SEND_TIMEOUT, 0, &timeout); |
| 800 | } | 1120 | } |
| 801 | if (socket_mtu > 28) { | 1121 | if (s_client_config.socket_mtu > 28) { |
| 802 | SSL_set_options(con, SSL_OP_NO_QUERY_MTU); | 1122 | SSL_set_options(con, SSL_OP_NO_QUERY_MTU); |
| 803 | SSL_set_mtu(con, socket_mtu - 28); | 1123 | SSL_set_mtu(con, s_client_config.socket_mtu - 28); |
| 804 | } else | 1124 | } else |
| 805 | /* want to do MTU discovery */ | 1125 | /* want to do MTU discovery */ |
| 806 | BIO_ctrl(sbio, BIO_CTRL_DGRAM_MTU_DISCOVER, 0, NULL); | 1126 | BIO_ctrl(sbio, BIO_CTRL_DGRAM_MTU_DISCOVER, 0, NULL); |
| 807 | } else | 1127 | } else |
| 808 | sbio = BIO_new_socket(s, BIO_NOCLOSE); | 1128 | sbio = BIO_new_socket(s, BIO_NOCLOSE); |
| 809 | 1129 | ||
| 810 | if (nbio_test) { | 1130 | if (s_client_config.nbio_test) { |
| 811 | BIO *test; | 1131 | BIO *test; |
| 812 | 1132 | ||
| 813 | test = BIO_new(BIO_f_nbio_test()); | 1133 | test = BIO_new(BIO_f_nbio_test()); |
| 814 | sbio = BIO_push(test, sbio); | 1134 | sbio = BIO_push(test, sbio); |
| 815 | } | 1135 | } |
| 816 | if (c_debug) { | 1136 | if (s_client_config.c_debug) { |
| 817 | SSL_set_debug(con, 1); | 1137 | SSL_set_debug(con, 1); |
| 818 | BIO_set_callback(sbio, bio_dump_callback); | 1138 | BIO_set_callback(sbio, bio_dump_callback); |
| 819 | BIO_set_callback_arg(sbio, (char *) bio_c_out); | 1139 | BIO_set_callback_arg(sbio, (char *) bio_c_out); |
| 820 | } | 1140 | } |
| 821 | if (c_msg) { | 1141 | if (s_client_config.c_msg) { |
| 822 | SSL_set_msg_callback(con, msg_cb); | 1142 | SSL_set_msg_callback(con, msg_cb); |
| 823 | SSL_set_msg_callback_arg(con, bio_c_out); | 1143 | SSL_set_msg_callback_arg(con, bio_c_out); |
| 824 | } | 1144 | } |
| 825 | if (c_tlsextdebug) { | 1145 | if (s_client_config.c_tlsextdebug) { |
| 826 | SSL_set_tlsext_debug_callback(con, tlsext_cb); | 1146 | SSL_set_tlsext_debug_callback(con, tlsext_cb); |
| 827 | SSL_set_tlsext_debug_arg(con, bio_c_out); | 1147 | SSL_set_tlsext_debug_arg(con, bio_c_out); |
| 828 | } | 1148 | } |
| 829 | if (c_status_req) { | 1149 | if (s_client_config.c_status_req) { |
| 830 | SSL_set_tlsext_status_type(con, TLSEXT_STATUSTYPE_ocsp); | 1150 | SSL_set_tlsext_status_type(con, TLSEXT_STATUSTYPE_ocsp); |
| 831 | SSL_CTX_set_tlsext_status_cb(ctx, ocsp_resp_cb); | 1151 | SSL_CTX_set_tlsext_status_cb(ctx, ocsp_resp_cb); |
| 832 | SSL_CTX_set_tlsext_status_arg(ctx, bio_c_out); | 1152 | SSL_CTX_set_tlsext_status_arg(ctx, bio_c_out); |
| @@ -857,7 +1177,7 @@ re_start: | |||
| 857 | * push a buffering BIO into the chain that is removed again later on | 1177 | * push a buffering BIO into the chain that is removed again later on |
| 858 | * to not disturb the rest of the s_client operation. | 1178 | * to not disturb the rest of the s_client operation. |
| 859 | */ | 1179 | */ |
| 860 | if (starttls_proto == PROTO_SMTP || starttls_proto == PROTO_LMTP) { | 1180 | if (s_client_config.starttls_proto == PROTO_SMTP || s_client_config.starttls_proto == PROTO_LMTP) { |
| 861 | int foundit = 0; | 1181 | int foundit = 0; |
| 862 | BIO *fbio = BIO_new(BIO_f_buffer()); | 1182 | BIO *fbio = BIO_new(BIO_f_buffer()); |
| 863 | BIO_push(fbio, sbio); | 1183 | BIO_push(fbio, sbio); |
| @@ -868,7 +1188,7 @@ re_start: | |||
| 868 | while (mbuf_len > 3 && mbuf[3] == '-'); | 1188 | while (mbuf_len > 3 && mbuf[3] == '-'); |
| 869 | /* STARTTLS command requires EHLO... */ | 1189 | /* STARTTLS command requires EHLO... */ |
| 870 | BIO_printf(fbio, "%cHLO openssl.client.net\r\n", | 1190 | BIO_printf(fbio, "%cHLO openssl.client.net\r\n", |
| 871 | starttls_proto == PROTO_SMTP ? 'E' : 'L'); | 1191 | s_client_config.starttls_proto == PROTO_SMTP ? 'E' : 'L'); |
| 872 | (void) BIO_flush(fbio); | 1192 | (void) BIO_flush(fbio); |
| 873 | /* wait for multi-line response to end EHLO SMTP response */ | 1193 | /* wait for multi-line response to end EHLO SMTP response */ |
| 874 | do { | 1194 | do { |
| @@ -886,7 +1206,7 @@ re_start: | |||
| 886 | " try anyway...\n"); | 1206 | " try anyway...\n"); |
| 887 | BIO_printf(sbio, "STARTTLS\r\n"); | 1207 | BIO_printf(sbio, "STARTTLS\r\n"); |
| 888 | BIO_read(sbio, sbuf, BUFSIZZ); | 1208 | BIO_read(sbio, sbuf, BUFSIZZ); |
| 889 | } else if (starttls_proto == PROTO_POP3) { | 1209 | } else if (s_client_config.starttls_proto == PROTO_POP3) { |
| 890 | mbuf_len = BIO_read(sbio, mbuf, BUFSIZZ); | 1210 | mbuf_len = BIO_read(sbio, mbuf, BUFSIZZ); |
| 891 | if (mbuf_len == -1) { | 1211 | if (mbuf_len == -1) { |
| 892 | BIO_printf(bio_err, "BIO_read failed\n"); | 1212 | BIO_printf(bio_err, "BIO_read failed\n"); |
| @@ -894,7 +1214,7 @@ re_start: | |||
| 894 | } | 1214 | } |
| 895 | BIO_printf(sbio, "STLS\r\n"); | 1215 | BIO_printf(sbio, "STLS\r\n"); |
| 896 | BIO_read(sbio, sbuf, BUFSIZZ); | 1216 | BIO_read(sbio, sbuf, BUFSIZZ); |
| 897 | } else if (starttls_proto == PROTO_IMAP) { | 1217 | } else if (s_client_config.starttls_proto == PROTO_IMAP) { |
| 898 | int foundit = 0; | 1218 | int foundit = 0; |
| 899 | BIO *fbio = BIO_new(BIO_f_buffer()); | 1219 | BIO *fbio = BIO_new(BIO_f_buffer()); |
| 900 | BIO_push(fbio, sbio); | 1220 | BIO_push(fbio, sbio); |
| @@ -918,7 +1238,7 @@ re_start: | |||
| 918 | " try anyway...\n"); | 1238 | " try anyway...\n"); |
| 919 | BIO_printf(sbio, ". STARTTLS\r\n"); | 1239 | BIO_printf(sbio, ". STARTTLS\r\n"); |
| 920 | BIO_read(sbio, sbuf, BUFSIZZ); | 1240 | BIO_read(sbio, sbuf, BUFSIZZ); |
| 921 | } else if (starttls_proto == PROTO_FTP) { | 1241 | } else if (s_client_config.starttls_proto == PROTO_FTP) { |
| 922 | BIO *fbio = BIO_new(BIO_f_buffer()); | 1242 | BIO *fbio = BIO_new(BIO_f_buffer()); |
| 923 | BIO_push(fbio, sbio); | 1243 | BIO_push(fbio, sbio); |
| 924 | /* wait for multi-line response to end from FTP */ | 1244 | /* wait for multi-line response to end from FTP */ |
| @@ -931,11 +1251,11 @@ re_start: | |||
| 931 | BIO_free(fbio); | 1251 | BIO_free(fbio); |
| 932 | BIO_printf(sbio, "AUTH TLS\r\n"); | 1252 | BIO_printf(sbio, "AUTH TLS\r\n"); |
| 933 | BIO_read(sbio, sbuf, BUFSIZZ); | 1253 | BIO_read(sbio, sbuf, BUFSIZZ); |
| 934 | } else if (starttls_proto == PROTO_XMPP) { | 1254 | } else if (s_client_config.starttls_proto == PROTO_XMPP) { |
| 935 | int seen = 0; | 1255 | int seen = 0; |
| 936 | BIO_printf(sbio, "<stream:stream " | 1256 | BIO_printf(sbio, "<stream:stream " |
| 937 | "xmlns:stream='http://etherx.jabber.org/streams' " | 1257 | "xmlns:stream='http://etherx.jabber.org/streams' " |
| 938 | "xmlns='jabber:client' to='%s' version='1.0'>", xmpphost ? xmpphost : host); | 1258 | "xmlns='jabber:client' to='%s' version='1.0'>", s_client_config.xmpphost ? s_client_config.xmpphost : s_client_config.host); |
| 939 | seen = BIO_read(sbio, mbuf, BUFSIZZ); | 1259 | seen = BIO_read(sbio, mbuf, BUFSIZZ); |
| 940 | 1260 | ||
| 941 | if (seen <= 0) | 1261 | if (seen <= 0) |
| @@ -957,8 +1277,8 @@ re_start: | |||
| 957 | if (!strstr(sbuf, "<proceed")) | 1277 | if (!strstr(sbuf, "<proceed")) |
| 958 | goto shut; | 1278 | goto shut; |
| 959 | mbuf[0] = 0; | 1279 | mbuf[0] = 0; |
| 960 | } else if (proxy != NULL) { | 1280 | } else if (s_client_config.proxy != NULL) { |
| 961 | BIO_printf(sbio, "CONNECT %s HTTP/1.0\r\n\r\n", connect); | 1281 | BIO_printf(sbio, "CONNECT %s HTTP/1.0\r\n\r\n", s_client_config.connect); |
| 962 | mbuf_len = BIO_read(sbio, mbuf, BUFSIZZ); | 1282 | mbuf_len = BIO_read(sbio, mbuf, BUFSIZZ); |
| 963 | if (mbuf_len == -1) { | 1283 | if (mbuf_len == -1) { |
| 964 | BIO_printf(bio_err, "BIO_read failed\n"); | 1284 | BIO_printf(bio_err, "BIO_read failed\n"); |
| @@ -980,25 +1300,25 @@ re_start: | |||
| 980 | tty_on = 1; | 1300 | tty_on = 1; |
| 981 | if (in_init) { | 1301 | if (in_init) { |
| 982 | in_init = 0; | 1302 | in_init = 0; |
| 983 | if (sess_out) { | 1303 | if (s_client_config.sess_out) { |
| 984 | BIO *stmp = BIO_new_file(sess_out, "w"); | 1304 | BIO *stmp = BIO_new_file(s_client_config.sess_out, "w"); |
| 985 | if (stmp) { | 1305 | if (stmp) { |
| 986 | PEM_write_bio_SSL_SESSION(stmp, SSL_get_session(con)); | 1306 | PEM_write_bio_SSL_SESSION(stmp, SSL_get_session(con)); |
| 987 | BIO_free(stmp); | 1307 | BIO_free(stmp); |
| 988 | } else | 1308 | } else |
| 989 | BIO_printf(bio_err, "Error writing session file %s\n", sess_out); | 1309 | BIO_printf(bio_err, "Error writing session file %s\n", s_client_config.sess_out); |
| 990 | } | 1310 | } |
| 991 | print_stuff(bio_c_out, con, full_log); | 1311 | print_stuff(bio_c_out, con, full_log); |
| 992 | if (full_log > 0) | 1312 | if (full_log > 0) |
| 993 | full_log--; | 1313 | full_log--; |
| 994 | 1314 | ||
| 995 | if (starttls_proto) { | 1315 | if (s_client_config.starttls_proto) { |
| 996 | BIO_write(bio_err, mbuf, mbuf_len); | 1316 | BIO_write(bio_err, mbuf, mbuf_len); |
| 997 | /* We don't need to know any more */ | 1317 | /* We don't need to know any more */ |
| 998 | starttls_proto = PROTO_OFF; | 1318 | s_client_config.starttls_proto = PROTO_OFF; |
| 999 | } | 1319 | } |
| 1000 | if (reconnect) { | 1320 | if (s_client_config.reconnect) { |
| 1001 | reconnect--; | 1321 | s_client_config.reconnect--; |
| 1002 | BIO_printf(bio_c_out, "drop connection and then reconnect\n"); | 1322 | BIO_printf(bio_c_out, "drop connection and then reconnect\n"); |
| 1003 | SSL_shutdown(con); | 1323 | SSL_shutdown(con); |
| 1004 | SSL_set_connect_state(con); | 1324 | SSL_set_connect_state(con); |
| @@ -1137,7 +1457,7 @@ re_start: | |||
| 1137 | } | 1457 | } |
| 1138 | } | 1458 | } |
| 1139 | #endif | 1459 | #endif |
| 1140 | if (peekaboo) { | 1460 | if (s_client_config.peekaboo) { |
| 1141 | k = p = SSL_peek(con, pbuf, 1024 /* BUFSIZZ */ ); | 1461 | k = p = SSL_peek(con, pbuf, 1024 /* BUFSIZZ */ ); |
| 1142 | pending = SSL_pending(con); | 1462 | pending = SSL_pending(con); |
| 1143 | if (SSL_get_error(con, p) == SSL_ERROR_NONE) { | 1463 | if (SSL_get_error(con, p) == SSL_ERROR_NONE) { |
| @@ -1158,7 +1478,7 @@ re_start: | |||
| 1158 | goto end; | 1478 | goto end; |
| 1159 | sbuf_off = 0; | 1479 | sbuf_off = 0; |
| 1160 | sbuf_len = k; | 1480 | sbuf_len = k; |
| 1161 | if (peekaboo) { | 1481 | if (s_client_config.peekaboo) { |
| 1162 | if (p != pending) { | 1482 | if (p != pending) { |
| 1163 | ret = -1; | 1483 | ret = -1; |
| 1164 | BIO_printf(bio_err, | 1484 | BIO_printf(bio_err, |
| @@ -1215,7 +1535,7 @@ re_start: | |||
| 1215 | BIO_printf(bio_err, "poll error"); | 1535 | BIO_printf(bio_err, "poll error"); |
| 1216 | goto shut; | 1536 | goto shut; |
| 1217 | } | 1537 | } |
| 1218 | if (crlf) { | 1538 | if (s_client_config.crlf) { |
| 1219 | int j, lf_num; | 1539 | int j, lf_num; |
| 1220 | 1540 | ||
| 1221 | i = read(fileno(stdin), cbuf, BUFSIZZ / 2); | 1541 | i = read(fileno(stdin), cbuf, BUFSIZZ / 2); |
| @@ -1236,12 +1556,12 @@ re_start: | |||
| 1236 | } else | 1556 | } else |
| 1237 | i = read(fileno(stdin), cbuf, BUFSIZZ); | 1557 | i = read(fileno(stdin), cbuf, BUFSIZZ); |
| 1238 | 1558 | ||
| 1239 | if ((!c_ign_eof) && ((i <= 0) || (cbuf[0] == 'Q'))) { | 1559 | if ((!s_client_config.c_ign_eof) && ((i <= 0) || (cbuf[0] == 'Q'))) { |
| 1240 | BIO_printf(bio_err, "DONE\n"); | 1560 | BIO_printf(bio_err, "DONE\n"); |
| 1241 | ret = 0; | 1561 | ret = 0; |
| 1242 | goto shut; | 1562 | goto shut; |
| 1243 | } | 1563 | } |
| 1244 | if ((!c_ign_eof) && (cbuf[0] == 'R')) { | 1564 | if ((!s_client_config.c_ign_eof) && (cbuf[0] == 'R')) { |
| 1245 | BIO_printf(bio_err, "RENEGOTIATING\n"); | 1565 | BIO_printf(bio_err, "RENEGOTIATING\n"); |
| 1246 | SSL_renegotiate(con); | 1566 | SSL_renegotiate(con); |
| 1247 | cbuf_len = 0; | 1567 | cbuf_len = 0; |
| @@ -1264,7 +1584,7 @@ re_start: | |||
| 1264 | close(SSL_get_fd(con)); | 1584 | close(SSL_get_fd(con)); |
| 1265 | end: | 1585 | end: |
| 1266 | if (con != NULL) { | 1586 | if (con != NULL) { |
| 1267 | if (prexit != 0) | 1587 | if (s_client_config.prexit != 0) |
| 1268 | print_stuff(bio_c_out, con, 1); | 1588 | print_stuff(bio_c_out, con, 1); |
| 1269 | SSL_free(con); | 1589 | SSL_free(con); |
| 1270 | } | 1590 | } |
| @@ -1272,7 +1592,7 @@ re_start: | |||
| 1272 | X509_free(cert); | 1592 | X509_free(cert); |
| 1273 | EVP_PKEY_free(key); | 1593 | EVP_PKEY_free(key); |
| 1274 | free(pass); | 1594 | free(pass); |
| 1275 | X509_VERIFY_PARAM_free(vpm); | 1595 | X509_VERIFY_PARAM_free(s_client_config.vpm); |
| 1276 | freezero(cbuf, BUFSIZZ); | 1596 | freezero(cbuf, BUFSIZZ); |
| 1277 | freezero(sbuf, BUFSIZZ); | 1597 | freezero(sbuf, BUFSIZZ); |
| 1278 | freezero(mbuf, BUFSIZZ); | 1598 | freezero(mbuf, BUFSIZZ); |
| @@ -1315,7 +1635,7 @@ print_stuff(BIO * bio, SSL * s, int full) | |||
| 1315 | X509_NAME_oneline(X509_get_issuer_name( | 1635 | X509_NAME_oneline(X509_get_issuer_name( |
| 1316 | sk_X509_value(sk, i)), buf, sizeof buf); | 1636 | sk_X509_value(sk, i)), buf, sizeof buf); |
| 1317 | BIO_printf(bio, " i:%s\n", buf); | 1637 | BIO_printf(bio, " i:%s\n", buf); |
| 1318 | if (c_showcerts) | 1638 | if (s_client_config.c_showcerts) |
| 1319 | PEM_write_bio_X509(bio, sk_X509_value(sk, i)); | 1639 | PEM_write_bio_X509(bio, sk_X509_value(sk, i)); |
| 1320 | } | 1640 | } |
| 1321 | } | 1641 | } |
| @@ -1323,7 +1643,7 @@ print_stuff(BIO * bio, SSL * s, int full) | |||
| 1323 | peer = SSL_get_peer_certificate(s); | 1643 | peer = SSL_get_peer_certificate(s); |
| 1324 | if (peer != NULL) { | 1644 | if (peer != NULL) { |
| 1325 | BIO_printf(bio, "Server certificate\n"); | 1645 | BIO_printf(bio, "Server certificate\n"); |
| 1326 | if (!(c_showcerts && got_a_chain)) /* Redundant if we | 1646 | if (!(s_client_config.c_showcerts && got_a_chain)) /* Redundant if we |
| 1327 | * showed the whole | 1647 | * showed the whole |
| 1328 | * chain */ | 1648 | * chain */ |
| 1329 | PEM_write_bio_X509(bio, peer); | 1649 | PEM_write_bio_X509(bio, peer); |
| @@ -1434,21 +1754,21 @@ print_stuff(BIO * bio, SSL * s, int full) | |||
| 1434 | #endif | 1754 | #endif |
| 1435 | 1755 | ||
| 1436 | SSL_SESSION_print(bio, SSL_get_session(s)); | 1756 | SSL_SESSION_print(bio, SSL_get_session(s)); |
| 1437 | if (keymatexportlabel != NULL) { | 1757 | if (s_client_config.keymatexportlabel != NULL) { |
| 1438 | BIO_printf(bio, "Keying material exporter:\n"); | 1758 | BIO_printf(bio, "Keying material exporter:\n"); |
| 1439 | BIO_printf(bio, " Label: '%s'\n", keymatexportlabel); | 1759 | BIO_printf(bio, " Label: '%s'\n", s_client_config.keymatexportlabel); |
| 1440 | BIO_printf(bio, " Length: %i bytes\n", keymatexportlen); | 1760 | BIO_printf(bio, " Length: %i bytes\n", s_client_config.keymatexportlen); |
| 1441 | exportedkeymat = malloc(keymatexportlen); | 1761 | exportedkeymat = malloc(s_client_config.keymatexportlen); |
| 1442 | if (exportedkeymat != NULL) { | 1762 | if (exportedkeymat != NULL) { |
| 1443 | if (!SSL_export_keying_material(s, exportedkeymat, | 1763 | if (!SSL_export_keying_material(s, exportedkeymat, |
| 1444 | keymatexportlen, | 1764 | s_client_config.keymatexportlen, |
| 1445 | keymatexportlabel, | 1765 | s_client_config.keymatexportlabel, |
| 1446 | strlen(keymatexportlabel), | 1766 | strlen(s_client_config.keymatexportlabel), |
| 1447 | NULL, 0, 0)) { | 1767 | NULL, 0, 0)) { |
| 1448 | BIO_printf(bio, " Error\n"); | 1768 | BIO_printf(bio, " Error\n"); |
| 1449 | } else { | 1769 | } else { |
| 1450 | BIO_printf(bio, " Keying material: "); | 1770 | BIO_printf(bio, " Keying material: "); |
| 1451 | for (i = 0; i < keymatexportlen; i++) | 1771 | for (i = 0; i < s_client_config.keymatexportlen; i++) |
| 1452 | BIO_printf(bio, "%02X", | 1772 | BIO_printf(bio, "%02X", |
| 1453 | exportedkeymat[i]); | 1773 | exportedkeymat[i]); |
| 1454 | BIO_printf(bio, "\n"); | 1774 | BIO_printf(bio, "\n"); |
