tstclnt.c (84959B)
1 /* This Source Code Form is subject to the terms of the Mozilla Public 2 * License, v. 2.0. If a copy of the MPL was not distributed with this 3 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ 4 5 /* 6 ** 7 ** Sample client side test program that uses SSL and NSS 8 ** 9 */ 10 11 #include "secutil.h" 12 #include "basicutil.h" 13 14 #if defined(XP_UNIX) 15 #include <unistd.h> 16 #else 17 #include <ctype.h> /* for isalpha() */ 18 #endif 19 20 #include <stdio.h> 21 #include <string.h> 22 #include <stdlib.h> 23 #include <errno.h> 24 #include <fcntl.h> 25 #include <stdarg.h> 26 27 #include "nspr.h" 28 #include "prio.h" 29 #include "prnetdb.h" 30 #include "nss.h" 31 #include "nssb64.h" 32 #include "ocsp.h" 33 #include "ssl.h" 34 #include "sslproto.h" 35 #include "sslexp.h" 36 #include "pk11func.h" 37 #include "secmod.h" 38 #include "plgetopt.h" 39 #include "plstr.h" 40 #include "zlib.h" 41 42 #if defined(WIN32) 43 #include <fcntl.h> 44 #include <io.h> 45 #endif 46 47 #define PRINTF \ 48 if (verbose) \ 49 printf 50 #define FPRINTF \ 51 if (verbose) \ 52 fprintf 53 54 #define MAX_WAIT_FOR_SERVER 600 55 #define WAIT_INTERVAL 100 56 #define ZERO_RTT_MAX (2 << 16) 57 58 #define EXIT_CODE_HANDSHAKE_FAILED 254 59 60 #define EXIT_CODE_SIDECHANNELTEST_GOOD 0 61 #define EXIT_CODE_SIDECHANNELTEST_BADCERT 1 62 #define EXIT_CODE_SIDECHANNELTEST_NODATA 2 63 #define EXIT_CODE_SIDECHANNELTEST_REVOKED 3 64 65 PRIntervalTime maxInterval = PR_INTERVAL_NO_TIMEOUT; 66 67 int ssl3CipherSuites[] = { 68 -1, /* SSL_FORTEZZA_DMS_WITH_FORTEZZA_CBC_SHA* a */ 69 -1, /* SSL_FORTEZZA_DMS_WITH_RC4_128_SHA * b */ 70 TLS_RSA_WITH_RC4_128_MD5, /* c */ 71 TLS_RSA_WITH_3DES_EDE_CBC_SHA, /* d */ 72 TLS_RSA_WITH_DES_CBC_SHA, /* e */ 73 -1, /* TLS_RSA_EXPORT_WITH_RC4_40_MD5 * f */ 74 -1, /* TLS_RSA_EXPORT_WITH_RC2_CBC_40_MD5 * g */ 75 -1, /* SSL_FORTEZZA_DMS_WITH_NULL_SHA * h */ 76 TLS_RSA_WITH_NULL_MD5, /* i */ 77 -1, /* SSL_RSA_FIPS_WITH_3DES_EDE_CBC_SHA * j */ 78 -1, /* SSL_RSA_FIPS_WITH_DES_CBC_SHA * k */ 79 -1, /* TLS_RSA_EXPORT1024_WITH_DES_CBC_SHA * l */ 80 -1, /* TLS_RSA_EXPORT1024_WITH_RC4_56_SHA * m */ 81 TLS_RSA_WITH_RC4_128_SHA, /* n */ 82 TLS_DHE_DSS_WITH_RC4_128_SHA, /* o */ 83 TLS_DHE_RSA_WITH_3DES_EDE_CBC_SHA, /* p */ 84 TLS_DHE_DSS_WITH_3DES_EDE_CBC_SHA, /* q */ 85 TLS_DHE_RSA_WITH_DES_CBC_SHA, /* r */ 86 TLS_DHE_DSS_WITH_DES_CBC_SHA, /* s */ 87 TLS_DHE_DSS_WITH_AES_128_CBC_SHA, /* t */ 88 TLS_DHE_RSA_WITH_AES_128_CBC_SHA, /* u */ 89 TLS_RSA_WITH_AES_128_CBC_SHA, /* v */ 90 TLS_DHE_DSS_WITH_AES_256_CBC_SHA, /* w */ 91 TLS_DHE_RSA_WITH_AES_256_CBC_SHA, /* x */ 92 TLS_RSA_WITH_AES_256_CBC_SHA, /* y */ 93 TLS_RSA_WITH_NULL_SHA, /* z */ 94 0 95 }; 96 97 unsigned long __cmp_umuls; 98 PRBool verbose; 99 int dumpServerChain = 0; 100 int renegotiationsToDo = 0; 101 int renegotiationsDone = 0; 102 PRBool initializedServerSessionCache = PR_FALSE; 103 104 static char *progName; 105 static const char *requestFile; 106 107 secuPWData pwdata = { PW_NONE, 0 }; 108 109 SSLNamedGroup *enabledGroups = NULL; 110 unsigned int enabledGroupsCount = 0; 111 const SSLSignatureScheme *enabledSigSchemes = NULL; 112 unsigned int enabledSigSchemeCount = 0; 113 SECItem psk = { siBuffer, NULL, 0 }; 114 SECItem pskLabel = { siBuffer, NULL, 0 }; 115 116 void 117 printSecurityInfo(PRFileDesc *fd) 118 { 119 CERTCertificate *cert; 120 const SECItemArray *csa; 121 const SECItem *scts; 122 SSL3Statistics *ssl3stats = SSL_GetStatistics(); 123 SECStatus result; 124 SSLChannelInfo channel; 125 SSLCipherSuiteInfo suite; 126 127 result = SSL_GetChannelInfo(fd, &channel, sizeof channel); 128 if (result == SECSuccess && 129 channel.length == sizeof channel && 130 channel.cipherSuite) { 131 result = SSL_GetCipherSuiteInfo(channel.cipherSuite, 132 &suite, sizeof suite); 133 if (result == SECSuccess) { 134 FPRINTF(stderr, 135 "tstclnt: SSL version %d.%d using %d-bit %s with %d-bit %s MAC%s\n", 136 channel.protocolVersion >> 8, channel.protocolVersion & 0xff, 137 suite.effectiveKeyBits, suite.symCipherName, 138 suite.macBits, suite.macAlgorithmName, 139 channel.isFIPS ? " FIPS" : ""); 140 FPRINTF(stderr, 141 "tstclnt: Server Auth: %d-bit %s, Key Exchange: %d-bit %s\n" 142 " Key Exchange Group: %s\n" 143 " Compression: %s, Extended Master Secret: %s\n" 144 " Signature Scheme: %s\n", 145 channel.authKeyBits, suite.authAlgorithmName, 146 channel.keaKeyBits, suite.keaTypeName, 147 SECU_NamedGroupToGroupName(channel.keaGroup), 148 channel.compressionMethodName, 149 channel.extendedMasterSecretUsed ? "Yes" : "No", 150 SECU_SignatureSchemeName(channel.signatureScheme)); 151 } 152 } 153 cert = SSL_RevealCert(fd); 154 if (cert) { 155 char *ip = CERT_NameToAscii(&cert->issuer); 156 char *sp = CERT_NameToAscii(&cert->subject); 157 if (sp) { 158 fprintf(stderr, "subject DN: %s\n", sp); 159 PORT_Free(sp); 160 } 161 if (ip) { 162 fprintf(stderr, "issuer DN: %s\n", ip); 163 PORT_Free(ip); 164 } 165 CERT_DestroyCertificate(cert); 166 cert = NULL; 167 } 168 fprintf(stderr, 169 "%ld cache hits; %ld cache misses, %ld cache not reusable\n" 170 "%ld stateless resumes\n", 171 ssl3stats->hsh_sid_cache_hits, ssl3stats->hsh_sid_cache_misses, 172 ssl3stats->hsh_sid_cache_not_ok, ssl3stats->hsh_sid_stateless_resumes); 173 174 csa = SSL_PeerStapledOCSPResponses(fd); 175 if (csa) { 176 fprintf(stderr, "Received %d Cert Status items (OCSP stapled data)\n", 177 csa->len); 178 } 179 scts = SSL_PeerSignedCertTimestamps(fd); 180 if (scts && scts->len) { 181 fprintf(stderr, "Received a Signed Certificate Timestamp of length" 182 " %u\n", 183 scts->len); 184 } 185 if (channel.peerDelegCred) { 186 fprintf(stderr, "Received a Delegated Credential\n"); 187 } 188 } 189 190 static void 191 PrintUsageHeader() 192 { 193 fprintf(stderr, 194 "Usage: %s -h host [-a 1st_hs_name ] [-a 2nd_hs_name ] [-p port]\n" 195 " [-D | -d certdir] [-C] [-b | -R root-module] \n" 196 " [-n nickname] [-Bafosvx] [-c ciphers] [-Y] [-Z] [-E]\n" 197 " [-V [min-version]:[max-version]] [-K] [-T] [-U]\n" 198 " [-r N] [-w passwd] [-W pwfile] [-q [-t seconds]]\n" 199 " [-I groups] [-J signatureschemes]\n" 200 " [-A requestfile] [-L totalconnections] [-P {client,server}]\n" 201 " [-N echConfigs] [-Q] [-z externalPsk]\n" 202 " [-i echGreaseSize]\n" 203 " [--enable-rfc8701-grease] [--enable-ch-extension-permutation]\n" 204 " [--zlib-certificate-compression] \n" 205 "\n", 206 progName); 207 } 208 209 static void 210 PrintParameterUsage() 211 { 212 fprintf(stderr, "%-20s Send different SNI name. 1st_hs_name - at first\n" 213 "%-20s handshake, 2nd_hs_name - at second handshake.\n" 214 "%-20s Default is host from the -h argument.\n", 215 "-a name", 216 "", ""); 217 fprintf(stderr, "%-20s Hostname to connect with\n", "-h host"); 218 fprintf(stderr, "%-20s Port number for SSL server\n", "-p port"); 219 fprintf(stderr, 220 "%-20s Directory with cert database (default is ~/.netscape)\n", 221 "-d certdir"); 222 fprintf(stderr, "%-20s Run without a cert database\n", "-D"); 223 fprintf(stderr, "%-20s Load the default \"builtins\" root CA module\n", "-b"); 224 fprintf(stderr, "%-20s Load the given root CA module\n", "-R"); 225 fprintf(stderr, "%-20s Print certificate chain information\n", "-C"); 226 fprintf(stderr, "%-20s (use -C twice to print more certificate details)\n", ""); 227 fprintf(stderr, "%-20s (use -C three times to include PEM format certificate dumps)\n", ""); 228 fprintf(stderr, "%-20s Nickname of key and cert\n", 229 "-n nickname"); 230 fprintf(stderr, 231 "%-20s Restricts the set of enabled SSL/TLS protocols versions.\n" 232 "%-20s All versions are enabled by default.\n" 233 "%-20s Possible values for min/max: ssl3 tls1.0 tls1.1 tls1.2 tls1.3\n" 234 "%-20s Example: \"-V ssl3:\" enables SSL 3 and newer.\n", 235 "-V [min]:[max]", "", "", ""); 236 fprintf(stderr, "%-20s Send TLS_FALLBACK_SCSV\n", "-K"); 237 fprintf(stderr, "%-20s Prints only payload data. Skips HTTP header.\n", "-S"); 238 fprintf(stderr, "%-20s Client speaks first. \n", "-f"); 239 fprintf(stderr, "%-20s Use synchronous certificate selection & validation\n", "-O"); 240 fprintf(stderr, "%-20s Override bad server cert. Make it OK.\n", "-o"); 241 fprintf(stderr, "%-20s Disable SSL socket locking.\n", "-s"); 242 fprintf(stderr, "%-20s Verbose progress reporting.\n", "-v"); 243 fprintf(stderr, "%-20s Ping the server and then exit.\n", "-q"); 244 fprintf(stderr, "%-20s Timeout for server ping (default: no timeout).\n", "-t seconds"); 245 fprintf(stderr, "%-20s Renegotiate N times (resuming session if N>1).\n", "-r N"); 246 fprintf(stderr, "%-20s Enable the session ticket extension.\n", "-u"); 247 fprintf(stderr, "%-20s Enable false start.\n", "-g"); 248 fprintf(stderr, "%-20s Enable the cert_status extension (OCSP stapling).\n", "-T"); 249 fprintf(stderr, "%-20s Enable the signed_certificate_timestamp extension.\n", "-U"); 250 fprintf(stderr, "%-20s Enable the delegated credentials extension.\n", "-B"); 251 fprintf(stderr, "%-20s Require fresh revocation info from side channel.\n" 252 "%-20s -F once means: require for server cert only\n" 253 "%-20s -F twice means: require for intermediates, too\n" 254 "%-20s (Connect, handshake with server, disable dynamic download\n" 255 "%-20s of OCSP/CRL, verify cert using CERT_PKIXVerifyCert.)\n" 256 "%-20s Exit code:\n" 257 "%-20s 0: have fresh and valid revocation data, status good\n" 258 "%-20s 1: cert failed to verify, prior to revocation checking\n" 259 "%-20s 2: missing, old or invalid revocation data\n" 260 "%-20s 3: have fresh and valid revocation data, status revoked\n", 261 "-F", "", "", "", "", "", "", "", "", ""); 262 fprintf(stderr, "%-20s Test -F allows 0=any (default), 1=only OCSP, 2=only CRL\n", "-M"); 263 fprintf(stderr, "%-20s Restrict ciphers\n", "-c ciphers"); 264 fprintf(stderr, "%-20s Print cipher values allowed for parameter -c and exit\n", "-Y"); 265 fprintf(stderr, "%-20s Enforce using an IPv4 destination address\n", "-4"); 266 fprintf(stderr, "%-20s Enforce using an IPv6 destination address\n", "-6"); 267 fprintf(stderr, "%-20s (Options -4 and -6 cannot be combined.)\n", ""); 268 fprintf(stderr, "%-20s Enable the extended master secret extension [RFC7627]\n", "-G"); 269 fprintf(stderr, "%-20s Require the use of FFDHE supported groups [RFC7919]\n", "-H"); 270 fprintf(stderr, "%-20s Read from a file instead of stdin\n", "-A"); 271 fprintf(stderr, "%-20s Allow 0-RTT data (TLS 1.3 only)\n", "-Z"); 272 fprintf(stderr, "%-20s Disconnect and reconnect up to N times total\n", "-L"); 273 fprintf(stderr, "%-20s Comma separated list of enabled groups for TLS key exchange.\n" 274 "%-20s The following values are valid", 275 "-I", ""); 276 char comma = ':'; 277 const char *groupName; 278 int total = SECU_MAX_COL_LEN; 279 for (size_t i = 0; (groupName = SECU_NamedGroupGetNextName(i)) != NULL; i++) { 280 int len = strlen(groupName); 281 /* 2 represents a comma and a space */ 282 if ((total + len + 2) > SECU_MAX_COL_LEN) { 283 fprintf(stderr, "%c\n%-20s %s", comma, "", groupName); 284 /* 21 represents 21 spaces */ 285 total = len + 21; 286 } else { 287 fprintf(stderr, "%c %s", comma, groupName); 288 /* 2 represents a comma and a space */ 289 total += len + 2; 290 } 291 comma = ','; 292 } 293 fprintf(stderr, "\n"); 294 fprintf(stderr, "%-20s Comma separated list of signature schemes in preference order.\n" 295 "%-20s The following values are valid", 296 "-J", ""); 297 298 comma = ':'; 299 const char *schemeName; 300 total = SECU_MAX_COL_LEN; 301 for (size_t i = 0; (schemeName = SECU_SignatureSchemeGetNextScheme(i)) != NULL; i++) { 302 int len = strlen(schemeName); 303 /* 2 represents a comma and a space */ 304 if ((total + len + 2) > SECU_MAX_COL_LEN) { 305 fprintf(stderr, "%c\n%-20s %s", comma, "", schemeName); 306 /* 21 represents 21 spaces */ 307 total = len + 21; 308 } else { 309 fprintf(stderr, "%c %s", comma, schemeName); 310 /* 2 represents a comma and a space */ 311 total += len + 2; 312 } 313 comma = ','; 314 } 315 fprintf(stderr, "\n"); 316 fprintf(stderr, "%-20s Use DTLS\n", "-P {client, server}"); 317 fprintf(stderr, "%-20s Exit after handshake\n", "-Q"); 318 fprintf(stderr, "%-20s Use Encrypted Client Hello with the given Base64-encoded ECHConfigs\n", "-N"); 319 fprintf(stderr, "%-20s Enable Encrypted Client Hello GREASEing with the given padding size (0-255) \n", "-i"); 320 fprintf(stderr, "%-20s Enable post-handshake authentication\n" 321 "%-20s for TLS 1.3; need to specify -n\n", 322 "-E", ""); 323 fprintf(stderr, "%-20s Export and print keying material after successful handshake.\n" 324 "%-20s The argument is a comma separated list of exporters in the form:\n" 325 "%-20s LABEL[:OUTPUT-LENGTH[:CONTEXT]]\n" 326 "%-20s where LABEL and CONTEXT can be either a free-form string or\n" 327 "%-20s a hex string if it is preceded by \"0x\"; OUTPUT-LENGTH\n" 328 "%-20s is a decimal integer.\n", 329 "-x", "", "", "", "", ""); 330 fprintf(stderr, 331 "%-20s Configure a TLS 1.3 External PSK with the given hex string for a key\n" 332 "%-20s To specify a label, use ':' as a delimiter. For example\n" 333 "%-20s 0xAAAABBBBCCCCDDDD:mylabel. Otherwise, the default label of\n" 334 "%-20s 'Client_identity' will be used.\n", 335 "-z externalPsk", "", "", ""); 336 fprintf(stderr, "%-20s Enable middlebox compatibility mode (TLS 1.3 only)\n", "-e"); 337 } 338 339 static void 340 Usage() 341 { 342 PrintUsageHeader(); 343 PrintParameterUsage(); 344 exit(1); 345 } 346 347 static void 348 PrintCipherUsage() 349 { 350 PrintUsageHeader(); 351 fprintf(stderr, "%-20s Letter(s) chosen from the following list\n", 352 "-c ciphers"); 353 fprintf(stderr, 354 "c SSL3 RSA WITH RC4 128 MD5\n" 355 "d SSL3 RSA WITH 3DES EDE CBC SHA\n" 356 "e SSL3 RSA WITH DES CBC SHA\n" 357 "i SSL3 RSA WITH NULL MD5\n" 358 "n SSL3 RSA WITH RC4 128 SHA\n" 359 "o SSL3 DHE DSS WITH RC4 128 SHA\n" 360 "p SSL3 DHE RSA WITH 3DES EDE CBC SHA\n" 361 "q SSL3 DHE DSS WITH 3DES EDE CBC SHA\n" 362 "r SSL3 DHE RSA WITH DES CBC SHA\n" 363 "s SSL3 DHE DSS WITH DES CBC SHA\n" 364 "t SSL3 DHE DSS WITH AES 128 CBC SHA\n" 365 "u SSL3 DHE RSA WITH AES 128 CBC SHA\n" 366 "v SSL3 RSA WITH AES 128 CBC SHA\n" 367 "w SSL3 DHE DSS WITH AES 256 CBC SHA\n" 368 "x SSL3 DHE RSA WITH AES 256 CBC SHA\n" 369 "y SSL3 RSA WITH AES 256 CBC SHA\n" 370 "z SSL3 RSA WITH NULL SHA\n" 371 "\n" 372 ":WXYZ Use cipher with hex code { 0xWX , 0xYZ } in TLS\n"); 373 exit(1); 374 } 375 376 void 377 milliPause(PRUint32 milli) 378 { 379 PRIntervalTime ticks = PR_MillisecondsToInterval(milli); 380 PR_Sleep(ticks); 381 } 382 383 void 384 disableAllSSLCiphers() 385 { 386 const PRUint16 *cipherSuites = SSL_GetImplementedCiphers(); 387 int i = SSL_GetNumImplementedCiphers(); 388 SECStatus rv; 389 390 /* disable all the SSL3 cipher suites */ 391 while (--i >= 0) { 392 PRUint16 suite = cipherSuites[i]; 393 rv = SSL_CipherPrefSetDefault(suite, PR_FALSE); 394 if (rv != SECSuccess) { 395 PRErrorCode err = PR_GetError(); 396 fprintf(stderr, 397 "SSL_CipherPrefSet didn't like value 0x%04x (i = %d): %s\n", 398 suite, i, SECU_Strerror(err)); 399 exit(2); 400 } 401 } 402 } 403 404 typedef struct 405 { 406 PRBool shouldPause; /* PR_TRUE if we should use asynchronous peer cert 407 * authentication */ 408 PRBool isPaused; /* PR_TRUE if libssl is waiting for us to validate the 409 * peer's certificate and restart the handshake. */ 410 void *dbHandle; /* Certificate database handle to use while 411 * authenticating the peer's certificate. */ 412 PRBool testFreshStatusFromSideChannel; 413 PRErrorCode sideChannelRevocationTestResultCode; 414 PRBool requireDataForIntermediates; 415 PRBool allowOCSPSideChannelData; 416 PRBool allowCRLSideChannelData; 417 } ServerCertAuth; 418 419 /* 420 * Callback is called when incoming certificate is not valid. 421 * Returns SECSuccess to accept the cert anyway, SECFailure to reject. 422 */ 423 static SECStatus 424 ownBadCertHandler(void *arg, PRFileDesc *socket) 425 { 426 PRErrorCode err = PR_GetError(); 427 /* can log invalid cert here */ 428 fprintf(stderr, "Bad server certificate: %d, %s\n", err, 429 SECU_Strerror(err)); 430 return SECSuccess; /* override, say it's OK. */ 431 } 432 433 #define EXIT_CODE_SIDECHANNELTEST_GOOD 0 434 #define EXIT_CODE_SIDECHANNELTEST_BADCERT 1 435 #define EXIT_CODE_SIDECHANNELTEST_NODATA 2 436 #define EXIT_CODE_SIDECHANNELTEST_REVOKED 3 437 438 static void 439 verifyFromSideChannel(CERTCertificate *cert, ServerCertAuth *sca) 440 { 441 PRUint64 revDoNotUse = 442 CERT_REV_M_DO_NOT_TEST_USING_THIS_METHOD; 443 444 PRUint64 revUseLocalOnlyAndSoftFail = 445 CERT_REV_M_TEST_USING_THIS_METHOD | 446 CERT_REV_M_FORBID_NETWORK_FETCHING | 447 CERT_REV_M_REQUIRE_INFO_ON_MISSING_SOURCE | 448 CERT_REV_M_IGNORE_MISSING_FRESH_INFO | 449 CERT_REV_M_STOP_TESTING_ON_FRESH_INFO; 450 451 PRUint64 revUseLocalOnlyAndHardFail = 452 CERT_REV_M_TEST_USING_THIS_METHOD | 453 CERT_REV_M_FORBID_NETWORK_FETCHING | 454 CERT_REV_M_REQUIRE_INFO_ON_MISSING_SOURCE | 455 CERT_REV_M_FAIL_ON_MISSING_FRESH_INFO | 456 CERT_REV_M_STOP_TESTING_ON_FRESH_INFO; 457 458 PRUint64 methodFlagsDoNotUse[2]; 459 PRUint64 methodFlagsCheckSoftFail[2]; 460 PRUint64 methodFlagsCheckHardFail[2]; 461 CERTRevocationTests revTestsDoNotCheck; 462 CERTRevocationTests revTestsOverallSoftFail; 463 CERTRevocationTests revTestsOverallHardFail; 464 CERTRevocationFlags rev; 465 CERTValInParam cvin[2]; 466 CERTValOutParam cvout[1]; 467 SECStatus rv; 468 469 methodFlagsDoNotUse[cert_revocation_method_crl] = revDoNotUse; 470 methodFlagsDoNotUse[cert_revocation_method_ocsp] = revDoNotUse; 471 472 methodFlagsCheckSoftFail[cert_revocation_method_crl] = 473 sca->allowCRLSideChannelData ? revUseLocalOnlyAndSoftFail : revDoNotUse; 474 methodFlagsCheckSoftFail[cert_revocation_method_ocsp] = 475 sca->allowOCSPSideChannelData ? revUseLocalOnlyAndSoftFail : revDoNotUse; 476 477 methodFlagsCheckHardFail[cert_revocation_method_crl] = 478 sca->allowCRLSideChannelData ? revUseLocalOnlyAndHardFail : revDoNotUse; 479 methodFlagsCheckHardFail[cert_revocation_method_ocsp] = 480 sca->allowOCSPSideChannelData ? revUseLocalOnlyAndHardFail : revDoNotUse; 481 482 revTestsDoNotCheck.cert_rev_flags_per_method = methodFlagsDoNotUse; 483 revTestsDoNotCheck.number_of_defined_methods = 2; 484 revTestsDoNotCheck.number_of_preferred_methods = 0; 485 revTestsDoNotCheck.cert_rev_method_independent_flags = 486 CERT_REV_MI_TEST_ALL_LOCAL_INFORMATION_FIRST | 487 CERT_REV_MI_NO_OVERALL_INFO_REQUIREMENT; 488 489 revTestsOverallSoftFail.cert_rev_flags_per_method = 0; /* must define later */ 490 revTestsOverallSoftFail.number_of_defined_methods = 2; 491 revTestsOverallSoftFail.number_of_preferred_methods = 0; 492 revTestsOverallSoftFail.cert_rev_method_independent_flags = 493 CERT_REV_MI_TEST_ALL_LOCAL_INFORMATION_FIRST | 494 CERT_REV_MI_NO_OVERALL_INFO_REQUIREMENT; 495 496 revTestsOverallHardFail.cert_rev_flags_per_method = 0; /* must define later */ 497 revTestsOverallHardFail.number_of_defined_methods = 2; 498 revTestsOverallHardFail.number_of_preferred_methods = 0; 499 revTestsOverallHardFail.cert_rev_method_independent_flags = 500 CERT_REV_MI_TEST_ALL_LOCAL_INFORMATION_FIRST | 501 CERT_REV_MI_REQUIRE_SOME_FRESH_INFO_AVAILABLE; 502 503 rev.chainTests = revTestsDoNotCheck; 504 rev.leafTests = revTestsDoNotCheck; 505 506 cvin[0].type = cert_pi_revocationFlags; 507 cvin[0].value.pointer.revocation = &rev; 508 cvin[1].type = cert_pi_end; 509 510 cvout[0].type = cert_po_end; 511 512 /* Strategy: 513 * 514 * Verify with revocation checking disabled. 515 * On failure return 1. 516 * 517 * if result if "good", then continue testing. 518 * 519 * Verify with CERT_REV_M_FAIL_ON_MISSING_FRESH_INFO. 520 * If result is good, return 0. 521 * 522 * On failure continue testing, find out why it failed. 523 * 524 * Verify with CERT_REV_M_IGNORE_MISSING_FRESH_INFO 525 * 526 * If result is "good", then our previous test failed, 527 * because we don't have fresh revocation info, return 2. 528 * 529 * If result is still bad, we do have revocation info, 530 * and it says "revoked" or something equivalent, return 3. 531 */ 532 533 /* revocation checking disabled */ 534 rv = CERT_PKIXVerifyCert(cert, certificateUsageSSLServer, 535 cvin, cvout, NULL); 536 if (rv != SECSuccess) { 537 sca->sideChannelRevocationTestResultCode = 538 EXIT_CODE_SIDECHANNELTEST_BADCERT; 539 return; 540 } 541 542 /* revocation checking, hard fail */ 543 if (sca->allowOCSPSideChannelData && sca->allowCRLSideChannelData) { 544 /* any method is allowed. use soft fail on individual checks, 545 * but use hard fail on the overall check 546 */ 547 revTestsOverallHardFail.cert_rev_flags_per_method = methodFlagsCheckSoftFail; 548 } else { 549 /* only one method is allowed. use hard fail on the individual checks. 550 * hard/soft fail is irrelevant on overall flags. 551 */ 552 revTestsOverallHardFail.cert_rev_flags_per_method = methodFlagsCheckHardFail; 553 } 554 rev.leafTests = revTestsOverallHardFail; 555 rev.chainTests = 556 sca->requireDataForIntermediates ? revTestsOverallHardFail : revTestsDoNotCheck; 557 rv = CERT_PKIXVerifyCert(cert, certificateUsageSSLServer, 558 cvin, cvout, NULL); 559 if (rv == SECSuccess) { 560 sca->sideChannelRevocationTestResultCode = 561 EXIT_CODE_SIDECHANNELTEST_GOOD; 562 return; 563 } 564 565 /* revocation checking, soft fail */ 566 revTestsOverallSoftFail.cert_rev_flags_per_method = methodFlagsCheckSoftFail; 567 rev.leafTests = revTestsOverallSoftFail; 568 rev.chainTests = 569 sca->requireDataForIntermediates ? revTestsOverallSoftFail : revTestsDoNotCheck; 570 rv = CERT_PKIXVerifyCert(cert, certificateUsageSSLServer, 571 cvin, cvout, NULL); 572 if (rv == SECSuccess) { 573 sca->sideChannelRevocationTestResultCode = 574 EXIT_CODE_SIDECHANNELTEST_NODATA; 575 return; 576 } 577 578 sca->sideChannelRevocationTestResultCode = 579 EXIT_CODE_SIDECHANNELTEST_REVOKED; 580 } 581 582 static void 583 dumpCertificatePEM(CERTCertificate *cert) 584 { 585 char *asciiDER = BTOA_DataToAscii(cert->derCert.data, cert->derCert.len); 586 if (asciiDER) { 587 fprintf(stderr, "%s\n%s\n%s\n", NS_CERT_HEADER, asciiDER, NS_CERT_TRAILER); 588 PORT_Free(asciiDER); 589 } 590 } 591 592 static void 593 dumpServerCertificateChain(PRFileDesc *fd) 594 { 595 CERTCertList *peerCertChain = NULL; 596 CERTCertListNode *node = NULL; 597 CERTCertificate *peerCert = NULL; 598 CERTCertificateList *foundChain = NULL; 599 SECU_PPFunc dumpFunction = NULL; 600 PRBool dumpCertPEM = PR_FALSE; 601 602 if (!dumpServerChain) { 603 return; 604 } else if (dumpServerChain == 1) { 605 dumpFunction = SECU_PrintCertificateBasicInfo; 606 } else { 607 dumpFunction = SECU_PrintCertificate; 608 if (dumpServerChain > 2) { 609 dumpCertPEM = PR_TRUE; 610 } 611 } 612 613 SECU_EnableWrap(PR_FALSE); 614 615 fprintf(stderr, "==== certificate(s) sent by server: ====\n"); 616 peerCertChain = SSL_PeerCertificateChain(fd); 617 if (peerCertChain) { 618 node = CERT_LIST_HEAD(peerCertChain); 619 while (!CERT_LIST_END(node, peerCertChain)) { 620 CERTCertificate *cert = node->cert; 621 SECU_PrintSignedContent(stderr, &cert->derCert, "Certificate", 0, 622 dumpFunction); 623 if (dumpCertPEM) { 624 dumpCertificatePEM(cert); 625 } 626 node = CERT_LIST_NEXT(node); 627 } 628 } 629 630 if (peerCertChain) { 631 peerCert = SSL_RevealCert(fd); 632 if (peerCert) { 633 foundChain = CERT_CertChainFromCert(peerCert, certificateUsageSSLServer, 634 PR_TRUE); 635 } 636 if (foundChain) { 637 unsigned int count = 0; 638 fprintf(stderr, "==== locally found issuer certificate(s): ====\n"); 639 for (count = 0; count < (unsigned int)foundChain->len; count++) { 640 CERTCertificate *c; 641 PRBool wasSentByServer = PR_FALSE; 642 c = CERT_FindCertByDERCert(CERT_GetDefaultCertDB(), &foundChain->certs[count]); 643 644 node = CERT_LIST_HEAD(peerCertChain); 645 while (!CERT_LIST_END(node, peerCertChain)) { 646 CERTCertificate *cert = node->cert; 647 if (CERT_CompareCerts(cert, c)) { 648 wasSentByServer = PR_TRUE; 649 break; 650 } 651 node = CERT_LIST_NEXT(node); 652 } 653 654 if (!wasSentByServer) { 655 SECU_PrintSignedContent(stderr, &c->derCert, "Certificate", 0, 656 dumpFunction); 657 if (dumpCertPEM) { 658 dumpCertificatePEM(c); 659 } 660 } 661 CERT_DestroyCertificate(c); 662 } 663 CERT_DestroyCertificateList(foundChain); 664 } 665 if (peerCert) { 666 CERT_DestroyCertificate(peerCert); 667 } 668 669 CERT_DestroyCertList(peerCertChain); 670 peerCertChain = NULL; 671 } 672 673 fprintf(stderr, "==== end of certificate chain information ====\n"); 674 fflush(stderr); 675 } 676 677 static SECStatus 678 ownAuthCertificate(void *arg, PRFileDesc *fd, PRBool checkSig, 679 PRBool isServer) 680 { 681 ServerCertAuth *serverCertAuth = (ServerCertAuth *)arg; 682 683 if (dumpServerChain) { 684 dumpServerCertificateChain(fd); 685 } 686 687 if (!serverCertAuth->shouldPause) { 688 CERTCertificate *cert; 689 unsigned int i; 690 const SECItemArray *csa; 691 692 if (!serverCertAuth->testFreshStatusFromSideChannel) { 693 return SSL_AuthCertificate(serverCertAuth->dbHandle, 694 fd, checkSig, isServer); 695 } 696 697 /* No verification attempt must have happened before now, 698 * to ensure revocation data has been actively retrieved yet, 699 * or our test will produce incorrect results. 700 */ 701 702 cert = SSL_RevealCert(fd); 703 if (!cert) { 704 exit(254); 705 } 706 707 csa = SSL_PeerStapledOCSPResponses(fd); 708 if (csa) { 709 for (i = 0; i < csa->len; ++i) { 710 PORT_SetError(0); 711 if (CERT_CacheOCSPResponseFromSideChannel( 712 serverCertAuth->dbHandle, cert, PR_Now(), 713 &csa->items[i], arg) != SECSuccess) { 714 PORT_Assert(PR_GetError() != 0); 715 } 716 } 717 } 718 719 verifyFromSideChannel(cert, serverCertAuth); 720 CERT_DestroyCertificate(cert); 721 /* return success to ensure our caller will continue and we will 722 * reach the code that handles 723 * serverCertAuth->sideChannelRevocationTestResultCode 724 */ 725 return SECSuccess; 726 } 727 728 FPRINTF(stderr, "%s: using asynchronous certificate validation\n", 729 progName); 730 731 PORT_Assert(!serverCertAuth->isPaused); 732 serverCertAuth->isPaused = PR_TRUE; 733 return SECWouldBlock; 734 } 735 736 struct clientCertAsyncParamsStr { 737 void *arg; /* The nickname used for selection, not owned */ 738 struct CERTDistNamesStr *caNames; /* CA Names specified by Server, owned. */ 739 }; 740 741 /* tstclnt can only have a single handshake in progress at any instant. */ 742 PRBool clientCertAsyncSelect = PR_TRUE; /* Async by default */ 743 PRBool clientCertIsBlocked = PR_FALSE; /* Whether we waiting to finish ClientAuth */ 744 struct clientCertAsyncParamsStr *clientCertParams = NULL; 745 746 SECStatus 747 own_CompleteClientAuthData(PRFileDesc *fd, struct clientCertAsyncParamsStr *args) 748 { 749 SECStatus rv; 750 CERTCertificate *pRetCert = NULL; 751 SECKEYPrivateKey *pRetKey = NULL; 752 rv = NSS_GetClientAuthData(args->arg, fd, args->caNames, &pRetCert, &pRetKey); 753 if (rv != SECSuccess) { 754 fprintf(stderr, "Failed to load a suitable client certificate \n"); 755 } 756 return SSL_ClientCertCallbackComplete(fd, rv, pRetKey, pRetCert); 757 } 758 759 SECStatus 760 restartHandshakeAfterClientCertIfNeeded(PRFileDesc *fd) 761 { 762 if (!clientCertIsBlocked) { 763 return SECFailure; 764 } 765 clientCertIsBlocked = PR_FALSE; 766 own_CompleteClientAuthData(fd, clientCertParams); 767 CERT_FreeDistNames(clientCertParams->caNames); 768 PORT_Free(clientCertParams); 769 clientCertParams = NULL; 770 return SECSuccess; 771 } 772 773 SECStatus 774 own_GetClientAuthData(void *arg, 775 PRFileDesc *socket, 776 struct CERTDistNamesStr *caNames, 777 struct CERTCertificateStr **pRetCert, 778 struct SECKEYPrivateKeyStr **pRetKey) 779 { 780 if (clientCertAsyncSelect) { 781 PR_ASSERT(!clientCertIsBlocked); 782 PR_ASSERT(!clientCertParams); 783 784 clientCertIsBlocked = PR_TRUE; 785 clientCertParams = PORT_Alloc(sizeof(struct clientCertAsyncParamsStr)); 786 if (!clientCertParams) { 787 fprintf(stderr, "Unable to allocate buffer for client cert callback\n"); 788 exit(1); 789 } 790 791 clientCertParams->arg = arg; 792 clientCertParams->caNames = caNames ? CERT_DupDistNames(caNames) : NULL; 793 if (caNames && !clientCertParams->caNames) { 794 fprintf(stderr, "Unable to allocate buffer for client cert callback\n"); 795 exit(1); 796 } 797 return SECWouldBlock; 798 } 799 800 if (verbose > 1) { 801 SECStatus rv; 802 fprintf(stderr, "Server requested Client Authentication\n"); 803 if (caNames && caNames->nnames > 0) { 804 PLArenaPool *arena = caNames->arena; 805 if (!arena) 806 arena = PORT_NewArena(2048); 807 if (arena) { 808 int i; 809 for (i = 0; i < caNames->nnames; ++i) { 810 char *nameString; 811 CERTName dn; 812 rv = SEC_QuickDERDecodeItem(arena, 813 &dn, 814 SEC_ASN1_GET(CERT_NameTemplate), 815 caNames->names + i); 816 if (rv != SECSuccess) 817 continue; 818 nameString = CERT_NameToAscii(&dn); 819 if (!nameString) 820 continue; 821 fprintf(stderr, "CA[%d]: %s\n", i + 1, nameString); 822 PORT_Free(nameString); 823 } 824 if (!caNames->arena) { 825 PORT_FreeArena(arena, PR_FALSE); 826 } 827 } 828 } 829 rv = NSS_GetClientAuthData(arg, socket, caNames, pRetCert, pRetKey); 830 if (rv == SECSuccess && *pRetCert) { 831 char *nameString = CERT_NameToAscii(&((*pRetCert)->subject)); 832 if (nameString) { 833 fprintf(stderr, "sent cert: %s\n", nameString); 834 PORT_Free(nameString); 835 } 836 } else { 837 fprintf(stderr, "send no cert\n"); 838 } 839 return rv; 840 } 841 return NSS_GetClientAuthData(arg, socket, caNames, pRetCert, pRetKey); 842 } 843 844 #if defined(WIN32) 845 void 846 thread_main(void *arg) 847 { 848 PRFileDesc *ps = (PRFileDesc *)arg; 849 PRFileDesc *std_in; 850 int wc, rc; 851 char buf[256]; 852 853 if (requestFile) { 854 std_in = PR_Open(requestFile, PR_RDONLY, 0); 855 } else { 856 std_in = PR_GetSpecialFD(PR_StandardInput); 857 } 858 859 #ifdef WIN32 860 if (!requestFile) { 861 /* Put stdin into O_BINARY mode 862 ** or else incoming \r\n's will become \n's. 863 */ 864 int smrv = _setmode(_fileno(stdin), _O_BINARY); 865 if (smrv == -1) { 866 fprintf(stderr, 867 "%s: Cannot change stdin to binary mode. Use -i option instead.\n", 868 progName); 869 /* plow ahead anyway */ 870 } 871 } 872 #endif 873 874 do { 875 rc = PR_Read(std_in, buf, sizeof buf); 876 if (rc <= 0) 877 break; 878 wc = PR_Send(ps, buf, rc, 0, maxInterval); 879 } while (wc == rc); 880 PR_Close(ps); 881 if (requestFile) { 882 PR_Close(std_in); 883 } 884 } 885 886 #endif 887 888 static void 889 printHostNameAndAddr(const char *host, const PRNetAddr *addr) 890 { 891 PRUint16 port = PR_NetAddrInetPort(addr); 892 char addrBuf[80]; 893 PRStatus st = PR_NetAddrToString(addr, addrBuf, sizeof addrBuf); 894 895 if (st == PR_SUCCESS) { 896 port = PR_ntohs(port); 897 FPRINTF(stderr, "%s: connecting to %s:%hu (address=%s)\n", 898 progName, host, port, addrBuf); 899 } 900 } 901 902 /* 903 * Prints output according to skipProtoHeader flag. If skipProtoHeader 904 * is not set, prints without any changes, otherwise looking 905 * for \n\r\n(empty line sequence: HTTP header separator) and 906 * prints everything after it. 907 */ 908 static void 909 separateReqHeader(const PRFileDesc *outFd, const char *buf, const int nb, 910 PRBool *wrStarted, int *ptrnMatched) 911 { 912 913 /* it is sufficient to look for only "\n\r\n". Hopping that 914 * HTTP response format satisfies the standard */ 915 char *ptrnStr = "\n\r\n"; 916 char *resPtr; 917 918 if (nb == 0) { 919 return; 920 } 921 922 if (*ptrnMatched > 0) { 923 /* Get here only if previous separateReqHeader call found 924 * only a fragment of "\n\r\n" in previous buffer. */ 925 PORT_Assert(*ptrnMatched < 3); 926 927 /* the size of fragment of "\n\r\n" what we want to find in this 928 * buffer is equal to *ptrnMatched */ 929 if (*ptrnMatched <= nb) { 930 /* move the pointer to the beginning of the fragment */ 931 int strSize = *ptrnMatched; 932 char *tmpPtrn = ptrnStr + (3 - strSize); 933 if (PL_strncmp(buf, tmpPtrn, strSize) == 0) { 934 /* print the rest of the buffer(without the fragment) */ 935 PR_Write((void *)outFd, buf + strSize, nb - strSize); 936 *wrStarted = PR_TRUE; 937 return; 938 } 939 } else { 940 /* we are here only when nb == 1 && *ptrnMatched == 2 */ 941 if (*buf == '\r') { 942 *ptrnMatched = 1; 943 } else { 944 *ptrnMatched = 0; 945 } 946 return; 947 } 948 } 949 resPtr = PL_strnstr(buf, ptrnStr, nb); 950 if (resPtr != NULL) { 951 /* if "\n\r\n" was found in the buffer, calculate offset 952 * and print the rest of the buffer */ 953 int newBn = nb - (resPtr - buf + 3); /* 3 is the length of "\n\r\n" */ 954 955 PR_Write((void *)outFd, resPtr + 3, newBn); 956 *wrStarted = PR_TRUE; 957 return; 958 } else { 959 /* try to find a fragment of "\n\r\n" at the end of the buffer. 960 * if found, set *ptrnMatched to the number of chars left to find 961 * in the next buffer.*/ 962 int i; 963 for (i = 1; i < 3; i++) { 964 char *bufPrt; 965 int strSize = 3 - i; 966 967 if (strSize > nb) { 968 continue; 969 } 970 bufPrt = (char *)(buf + nb - strSize); 971 972 if (PL_strncmp(bufPrt, ptrnStr, strSize) == 0) { 973 *ptrnMatched = i; 974 return; 975 } 976 } 977 } 978 } 979 980 #define SSOCK_FD 0 981 #define STDIN_FD 1 982 983 #define HEXCHAR_TO_INT(c, i) \ 984 if (((c) >= '0') && ((c) <= '9')) { \ 985 i = (c) - '0'; \ 986 } else if (((c) >= 'a') && ((c) <= 'f')) { \ 987 i = (c) - 'a' + 10; \ 988 } else if (((c) >= 'A') && ((c) <= 'F')) { \ 989 i = (c) - 'A' + 10; \ 990 } else { \ 991 Usage(); \ 992 } 993 994 static SECStatus 995 restartHandshakeAfterServerCertIfNeeded(PRFileDesc *fd, 996 ServerCertAuth *serverCertAuth, 997 PRBool override) 998 { 999 SECStatus rv; 1000 PRErrorCode error = 0; 1001 1002 if (!serverCertAuth->isPaused || clientCertIsBlocked) 1003 return SECSuccess; 1004 1005 FPRINTF(stderr, "%s: handshake was paused by auth certificate hook\n", 1006 progName); 1007 1008 serverCertAuth->isPaused = PR_FALSE; 1009 rv = SSL_AuthCertificate(serverCertAuth->dbHandle, fd, PR_TRUE, PR_FALSE); 1010 if (rv != SECSuccess) { 1011 error = PR_GetError(); 1012 if (error == 0) { 1013 PR_NOT_REACHED("SSL_AuthCertificate return SECFailure without " 1014 "setting error code."); 1015 error = PR_INVALID_STATE_ERROR; 1016 } else if (override) { 1017 rv = ownBadCertHandler(NULL, fd); 1018 } 1019 } 1020 if (rv == SECSuccess) { 1021 error = 0; 1022 } 1023 1024 if (SSL_AuthCertificateComplete(fd, error) != SECSuccess) { 1025 rv = SECFailure; 1026 } else { 1027 /* restore the original error code, which could be reset by 1028 * SSL_AuthCertificateComplete */ 1029 PORT_SetError(error); 1030 } 1031 1032 return rv; 1033 } 1034 1035 char *host = NULL; 1036 char *nickname = NULL; 1037 char *cipherString = NULL; 1038 int multiplier = 0; 1039 SSLVersionRange enabledVersions; 1040 int disableLocking = 0; 1041 int enableSessionTickets = 0; 1042 int enableFalseStart = 0; 1043 int enableCertStatus = 0; 1044 int enableSignedCertTimestamps = 0; 1045 int forceFallbackSCSV = 0; 1046 int enableExtendedMasterSecret = 0; 1047 PRBool requireDHNamedGroups = 0; 1048 PRBool middleboxCompatMode = 0; 1049 PRSocketOptionData opt; 1050 PRNetAddr addr; 1051 PRBool allowIPv4 = PR_TRUE; 1052 PRBool allowIPv6 = PR_TRUE; 1053 PRBool pingServerFirst = PR_FALSE; 1054 int pingTimeoutSeconds = -1; 1055 PRBool clientSpeaksFirst = PR_FALSE; 1056 PRBool skipProtoHeader = PR_FALSE; 1057 ServerCertAuth serverCertAuth; 1058 char *hs1SniHostName = NULL; 1059 char *hs2SniHostName = NULL; 1060 PRUint16 portno = 443; 1061 int override = 0; 1062 PRBool enableZeroRtt = PR_FALSE; 1063 PRUint8 *zeroRttData; 1064 unsigned int zeroRttLen = 0; 1065 PRBool enableAltServerHello = PR_FALSE; 1066 PRBool useDTLS = PR_FALSE; 1067 PRBool actAsServer = PR_FALSE; 1068 PRBool stopAfterHandshake = PR_FALSE; 1069 PRBool requestToExit = PR_FALSE; 1070 char *versionString = NULL; 1071 PRBool handshakeComplete = PR_FALSE; 1072 char *echConfigs = NULL; 1073 PRUint16 echGreaseSize = 0; 1074 PRBool enablePostHandshakeAuth = PR_FALSE; 1075 PRBool enableDelegatedCredentials = PR_FALSE; 1076 const secuExporter *enabledExporters = NULL; 1077 unsigned int enabledExporterCount = 0; 1078 PRBool enableRfc8701Grease = PR_FALSE; 1079 PRBool enableCHExtensionPermuation = PR_FALSE; 1080 PRBool zlibCertificateCompression = PR_FALSE; 1081 1082 static int 1083 writeBytesToServer(PRFileDesc *s, const PRUint8 *buf, int nb) 1084 { 1085 SECStatus rv; 1086 const PRUint8 *bufp = buf; 1087 PRPollDesc pollDesc; 1088 1089 pollDesc.in_flags = PR_POLL_WRITE | PR_POLL_EXCEPT; 1090 pollDesc.out_flags = 0; 1091 pollDesc.fd = s; 1092 1093 FPRINTF(stderr, "%s: Writing %d bytes to server\n", 1094 progName, nb); 1095 do { 1096 PRInt32 cc = PR_Send(s, bufp, nb, 0, maxInterval); 1097 if (cc < 0) { 1098 PRErrorCode err = PR_GetError(); 1099 if (err != PR_WOULD_BLOCK_ERROR) { 1100 SECU_PrintError(progName, "write to SSL socket failed"); 1101 return 254; 1102 } 1103 cc = 0; 1104 } 1105 FPRINTF(stderr, "%s: %d bytes written\n", progName, cc); 1106 if (enableZeroRtt && !handshakeComplete) { 1107 if (zeroRttLen + cc > ZERO_RTT_MAX) { 1108 SECU_PrintError(progName, "too much early data to save"); 1109 return -1; 1110 } 1111 PORT_Memcpy(zeroRttData + zeroRttLen, bufp, cc); 1112 zeroRttLen += cc; 1113 } 1114 bufp += cc; 1115 nb -= cc; 1116 if (nb <= 0) 1117 break; 1118 1119 rv = restartHandshakeAfterServerCertIfNeeded(s, 1120 &serverCertAuth, override); 1121 if (rv != SECSuccess) { 1122 SECU_PrintError(progName, "authentication of server cert failed"); 1123 return EXIT_CODE_HANDSHAKE_FAILED; 1124 } 1125 1126 rv = restartHandshakeAfterClientCertIfNeeded(s); 1127 if (rv == SECSuccess) { 1128 continue; 1129 } 1130 1131 pollDesc.in_flags = PR_POLL_WRITE | PR_POLL_EXCEPT; 1132 pollDesc.out_flags = 0; 1133 FPRINTF(stderr, 1134 "%s: about to call PR_Poll on writable socket !\n", 1135 progName); 1136 cc = PR_Poll(&pollDesc, 1, PR_INTERVAL_NO_TIMEOUT); 1137 if (cc < 0) { 1138 SECU_PrintError(progName, "PR_Poll failed"); 1139 return -1; 1140 } 1141 FPRINTF(stderr, 1142 "%s: PR_Poll returned with writable socket !\n", 1143 progName); 1144 } while (1); 1145 1146 return 0; 1147 } 1148 1149 void 1150 handshakeCallback(PRFileDesc *fd, void *client_data) 1151 { 1152 const char *secondHandshakeName = (char *)client_data; 1153 if (secondHandshakeName) { 1154 SSL_SetURL(fd, secondHandshakeName); 1155 } 1156 printSecurityInfo(fd); 1157 if (renegotiationsDone < renegotiationsToDo) { 1158 SSL_ReHandshake(fd, (renegotiationsToDo < 2)); 1159 ++renegotiationsDone; 1160 } 1161 if (zeroRttLen) { 1162 /* This data was sent in 0-RTT. */ 1163 SSLChannelInfo info; 1164 SECStatus rv; 1165 1166 rv = SSL_GetChannelInfo(fd, &info, sizeof(info)); 1167 if (rv != SECSuccess) 1168 return; 1169 1170 if (!info.earlyDataAccepted) { 1171 FPRINTF(stderr, "Early data rejected. Re-sending %d bytes\n", 1172 zeroRttLen); 1173 writeBytesToServer(fd, zeroRttData, zeroRttLen); 1174 zeroRttLen = 0; 1175 } 1176 } 1177 if (stopAfterHandshake) { 1178 requestToExit = PR_TRUE; 1179 } 1180 handshakeComplete = PR_TRUE; 1181 1182 if (enabledExporters) { 1183 SECStatus rv; 1184 1185 rv = exportKeyingMaterials(fd, enabledExporters, enabledExporterCount); 1186 if (rv != SECSuccess) { 1187 PRErrorCode err = PR_GetError(); 1188 FPRINTF(stderr, 1189 "couldn't export keying material: %s\n", 1190 SECU_Strerror(err)); 1191 } 1192 } 1193 } 1194 1195 static SECStatus 1196 installServerCertificate(PRFileDesc *s, char *nick) 1197 { 1198 CERTCertificate *cert; 1199 SECKEYPrivateKey *privKey = NULL; 1200 1201 if (!nick) { 1202 PORT_SetError(SEC_ERROR_INVALID_ARGS); 1203 return SECFailure; 1204 } 1205 1206 cert = PK11_FindCertFromNickname(nick, &pwdata); 1207 if (cert == NULL) { 1208 return SECFailure; 1209 } 1210 1211 privKey = PK11_FindKeyByAnyCert(cert, &pwdata); 1212 if (privKey == NULL) { 1213 return SECFailure; 1214 } 1215 if (SSL_ConfigServerCert(s, cert, privKey, NULL, 0) != SECSuccess) { 1216 return SECFailure; 1217 } 1218 SECKEY_DestroyPrivateKey(privKey); 1219 CERT_DestroyCertificate(cert); 1220 1221 return SECSuccess; 1222 } 1223 1224 static SECStatus 1225 bindToClient(PRFileDesc *s) 1226 { 1227 PRStatus status; 1228 status = PR_Bind(s, &addr); 1229 if (status != PR_SUCCESS) { 1230 return SECFailure; 1231 } 1232 1233 for (;;) { 1234 /* Bind the remote address on first packet. This must happen 1235 * before we SSL-ize the socket because we need to get the 1236 * peer's address before SSLizing. Recvfrom gives us that 1237 * while not consuming any data. */ 1238 unsigned char tmp; 1239 PRNetAddr remote; 1240 int nb; 1241 1242 nb = PR_RecvFrom(s, &tmp, 1, PR_MSG_PEEK, 1243 &remote, PR_INTERVAL_NO_TIMEOUT); 1244 if (nb != 1) 1245 continue; 1246 1247 status = PR_Connect(s, &remote, PR_INTERVAL_NO_TIMEOUT); 1248 if (status != PR_SUCCESS) { 1249 SECU_PrintError(progName, "server bind to remote end failed"); 1250 return SECFailure; 1251 } 1252 return SECSuccess; 1253 } 1254 1255 /* Unreachable. */ 1256 } 1257 1258 static SECStatus 1259 connectToServer(PRFileDesc *s, PRPollDesc *pollset) 1260 { 1261 PRStatus status; 1262 PRInt32 filesReady; 1263 1264 status = PR_Connect(s, &addr, PR_INTERVAL_NO_TIMEOUT); 1265 if (status != PR_SUCCESS) { 1266 if (PR_GetError() == PR_IN_PROGRESS_ERROR) { 1267 if (verbose) 1268 SECU_PrintError(progName, "connect"); 1269 milliPause(50 * multiplier); 1270 pollset[SSOCK_FD].in_flags = PR_POLL_WRITE | PR_POLL_EXCEPT; 1271 pollset[SSOCK_FD].out_flags = 0; 1272 pollset[SSOCK_FD].fd = s; 1273 while (1) { 1274 FPRINTF(stderr, 1275 "%s: about to call PR_Poll for connect completion!\n", 1276 progName); 1277 filesReady = PR_Poll(pollset, 1, PR_INTERVAL_NO_TIMEOUT); 1278 if (filesReady < 0) { 1279 SECU_PrintError(progName, "unable to connect (poll)"); 1280 return SECFailure; 1281 } 1282 FPRINTF(stderr, 1283 "%s: PR_Poll returned 0x%02x for socket out_flags.\n", 1284 progName, pollset[SSOCK_FD].out_flags); 1285 if (filesReady == 0) { /* shouldn't happen! */ 1286 SECU_PrintError(progName, "%s: PR_Poll returned zero!\n"); 1287 return SECFailure; 1288 } 1289 status = PR_GetConnectStatus(pollset); 1290 if (status == PR_SUCCESS) { 1291 break; 1292 } 1293 if (PR_GetError() != PR_IN_PROGRESS_ERROR) { 1294 SECU_PrintError(progName, "unable to connect (poll)"); 1295 return SECFailure; 1296 } 1297 SECU_PrintError(progName, "poll"); 1298 milliPause(50 * multiplier); 1299 } 1300 } else { 1301 SECU_PrintError(progName, "unable to connect"); 1302 return SECFailure; 1303 } 1304 } 1305 1306 return SECSuccess; 1307 } 1308 1309 static SECStatus 1310 importPsk(PRFileDesc *s) 1311 { 1312 SECU_PrintAsHex(stdout, &psk, "Using External PSK", 0); 1313 PK11SlotInfo *slot = NULL; 1314 PK11SymKey *symKey = NULL; 1315 slot = PK11_GetInternalSlot(); 1316 if (!slot) { 1317 SECU_PrintError(progName, "PK11_GetInternalSlot failed"); 1318 return SECFailure; 1319 } 1320 symKey = PK11_ImportSymKey(slot, CKM_HKDF_KEY_GEN, PK11_OriginUnwrap, 1321 CKA_DERIVE, &psk, NULL); 1322 PK11_FreeSlot(slot); 1323 if (!symKey) { 1324 SECU_PrintError(progName, "PK11_ImportSymKey failed"); 1325 return SECFailure; 1326 } 1327 1328 SECStatus rv = SSL_AddExternalPsk(s, symKey, (const PRUint8 *)pskLabel.data, 1329 pskLabel.len, ssl_hash_sha256); 1330 PK11_FreeSymKey(symKey); 1331 return rv; 1332 } 1333 1334 static SECStatus 1335 printEchRetryConfigs(PRFileDesc *s) 1336 { 1337 if (PORT_GetError() == SSL_ERROR_ECH_RETRY_WITH_ECH) { 1338 SECItem retries = { siBuffer, NULL, 0 }; 1339 SECStatus rv = SSL_GetEchRetryConfigs(s, &retries); 1340 if (rv != SECSuccess) { 1341 SECU_PrintError(progName, "SSL_GetEchRetryConfigs failed"); 1342 return SECFailure; 1343 } 1344 char *retriesBase64 = NSSBase64_EncodeItem(NULL, NULL, 0, &retries); 1345 if (!retriesBase64) { 1346 SECU_PrintError(progName, "NSSBase64_EncodeItem on retry_configs failed"); 1347 SECITEM_FreeItem(&retries, PR_FALSE); 1348 return SECFailure; 1349 } 1350 1351 // Remove the newline characters that NSSBase64_EncodeItem unhelpfully inserts. 1352 char *newline = strstr(retriesBase64, "\r\n"); 1353 if (newline) { 1354 memmove(newline, newline + 2, strlen(newline + 2) + 1); 1355 } 1356 fprintf(stderr, "Received ECH retry_configs: \n%s\n", retriesBase64); 1357 PORT_Free(retriesBase64); 1358 SECITEM_FreeItem(&retries, PR_FALSE); 1359 } 1360 return SECSuccess; 1361 } 1362 1363 static SECStatus 1364 zlibCertificateEncode(const SECItem *input, SECItem *output) 1365 { 1366 if (!input || !input->data || input->len == 0 || !output) { 1367 PR_SetError(SEC_ERROR_INVALID_ARGS, 0); 1368 return SECFailure; 1369 } 1370 1371 unsigned long maxCompressedLen = compressBound(input->len); 1372 SECITEM_AllocItem(NULL, output, maxCompressedLen); 1373 1374 unsigned long outputLenUL = output->len; 1375 int ret = compress(output->data, &outputLenUL, input->data, input->len); 1376 output->len = outputLenUL; 1377 if (ret != Z_OK) { 1378 PR_SetError(SEC_ERROR_LIBRARY_FAILURE, 0); 1379 return SECFailure; 1380 } 1381 1382 return SECSuccess; 1383 } 1384 1385 static SECStatus 1386 zlibCertificateDecode(const SECItem *input, 1387 unsigned char *output, size_t outputLen, 1388 size_t *usedLen) 1389 { 1390 if (!input || !input->data || input->len == 0 || !output || outputLen == 0) { 1391 PR_SetError(SEC_ERROR_INVALID_ARGS, 0); 1392 return SECFailure; 1393 } 1394 1395 unsigned long outputLenUL = outputLen; 1396 int ret = uncompress(output, &outputLenUL, input->data, input->len); 1397 *usedLen = outputLenUL; 1398 if (ret != Z_OK) { 1399 PR_SetError(SEC_ERROR_BAD_DATA, 0); 1400 return SECFailure; 1401 } 1402 1403 return SECSuccess; 1404 } 1405 1406 static int 1407 run() 1408 { 1409 int headerSeparatorPtrnId = 0; 1410 int error = 0; 1411 SECStatus rv; 1412 PRStatus status; 1413 PRInt32 filesReady; 1414 PRFileDesc *s = NULL; 1415 PRFileDesc *std_out; 1416 PRPollDesc pollset[2] = { { 0 }, { 0 } }; 1417 PRBool wrStarted = PR_FALSE; 1418 SSLCertificateCompressionAlgorithm zlibCompressionAlg = { 1, "zlib", zlibCertificateEncode, zlibCertificateDecode }; 1419 1420 handshakeComplete = PR_FALSE; 1421 1422 /* Create socket */ 1423 if (useDTLS) { 1424 s = PR_OpenUDPSocket(addr.raw.family); 1425 } else { 1426 s = PR_OpenTCPSocket(addr.raw.family); 1427 } 1428 1429 if (s == NULL) { 1430 SECU_PrintError(progName, "error creating socket"); 1431 error = 1; 1432 goto done; 1433 } 1434 1435 if (actAsServer) { 1436 if (bindToClient(s) != SECSuccess) { 1437 return 1; 1438 } 1439 } 1440 opt.option = PR_SockOpt_Nonblocking; 1441 opt.value.non_blocking = PR_TRUE; /* default */ 1442 if (serverCertAuth.testFreshStatusFromSideChannel) { 1443 opt.value.non_blocking = PR_FALSE; 1444 } 1445 status = PR_SetSocketOption(s, &opt); 1446 if (status != PR_SUCCESS) { 1447 SECU_PrintError(progName, "error setting socket options"); 1448 error = 1; 1449 goto done; 1450 } 1451 1452 if (useDTLS) { 1453 s = DTLS_ImportFD(NULL, s); 1454 } else { 1455 s = SSL_ImportFD(NULL, s); 1456 } 1457 if (s == NULL) { 1458 SECU_PrintError(progName, "error importing socket"); 1459 error = 1; 1460 goto done; 1461 } 1462 SSL_SetPKCS11PinArg(s, &pwdata); 1463 1464 rv = SSL_OptionSet(s, SSL_SECURITY, 1); 1465 if (rv != SECSuccess) { 1466 SECU_PrintError(progName, "error enabling socket"); 1467 error = 1; 1468 goto done; 1469 } 1470 1471 rv = SSL_OptionSet(s, actAsServer ? SSL_HANDSHAKE_AS_SERVER : SSL_HANDSHAKE_AS_CLIENT, 1); 1472 if (rv != SECSuccess) { 1473 SECU_PrintError(progName, "error enabling client handshake"); 1474 error = 1; 1475 goto done; 1476 } 1477 1478 /* all SSL3 cipher suites are enabled by default. */ 1479 if (cipherString) { 1480 char *cstringSaved = cipherString; 1481 int ndx; 1482 1483 while (0 != (ndx = *cipherString++)) { 1484 int cipher = 0; 1485 1486 if (ndx == ':') { 1487 int ctmp = 0; 1488 1489 HEXCHAR_TO_INT(*cipherString, ctmp) 1490 cipher |= (ctmp << 12); 1491 cipherString++; 1492 HEXCHAR_TO_INT(*cipherString, ctmp) 1493 cipher |= (ctmp << 8); 1494 cipherString++; 1495 HEXCHAR_TO_INT(*cipherString, ctmp) 1496 cipher |= (ctmp << 4); 1497 cipherString++; 1498 HEXCHAR_TO_INT(*cipherString, ctmp) 1499 cipher |= ctmp; 1500 cipherString++; 1501 } else { 1502 if (!isalpha((unsigned char)ndx)) 1503 Usage(); 1504 ndx = tolower((unsigned char)ndx) - 'a'; 1505 if (ndx < PR_ARRAY_SIZE(ssl3CipherSuites)) { 1506 cipher = ssl3CipherSuites[ndx]; 1507 } 1508 } 1509 if (cipher > 0) { 1510 rv = SSL_CipherPrefSet(s, cipher, SSL_ALLOWED); 1511 if (rv != SECSuccess) { 1512 SECU_PrintError(progName, "SSL_CipherPrefSet()"); 1513 error = 1; 1514 goto done; 1515 } 1516 } else { 1517 Usage(); 1518 } 1519 } 1520 PORT_Free(cstringSaved); 1521 } 1522 1523 rv = SSL_VersionRangeSet(s, &enabledVersions); 1524 if (rv != SECSuccess) { 1525 SECU_PrintError(progName, "error setting SSL/TLS version range "); 1526 error = 1; 1527 goto done; 1528 } 1529 1530 /* disable SSL socket locking */ 1531 rv = SSL_OptionSet(s, SSL_NO_LOCKS, disableLocking); 1532 if (rv != SECSuccess) { 1533 SECU_PrintError(progName, "error disabling SSL socket locking"); 1534 error = 1; 1535 goto done; 1536 } 1537 1538 /* enable Session Ticket extension. */ 1539 rv = SSL_OptionSet(s, SSL_ENABLE_SESSION_TICKETS, enableSessionTickets); 1540 if (rv != SECSuccess) { 1541 SECU_PrintError(progName, "error enabling Session Ticket extension"); 1542 error = 1; 1543 goto done; 1544 } 1545 1546 /* enable false start. */ 1547 rv = SSL_OptionSet(s, SSL_ENABLE_FALSE_START, enableFalseStart); 1548 if (rv != SECSuccess) { 1549 SECU_PrintError(progName, "error enabling false start"); 1550 error = 1; 1551 goto done; 1552 } 1553 1554 if (forceFallbackSCSV) { 1555 rv = SSL_OptionSet(s, SSL_ENABLE_FALLBACK_SCSV, PR_TRUE); 1556 if (rv != SECSuccess) { 1557 SECU_PrintError(progName, "error forcing fallback scsv"); 1558 error = 1; 1559 goto done; 1560 } 1561 } 1562 1563 /* enable cert status (OCSP stapling). */ 1564 rv = SSL_OptionSet(s, SSL_ENABLE_OCSP_STAPLING, enableCertStatus); 1565 if (rv != SECSuccess) { 1566 SECU_PrintError(progName, "error enabling cert status (OCSP stapling)"); 1567 error = 1; 1568 goto done; 1569 } 1570 1571 /* enable negotiation of delegated credentials (draft-ietf-tls-subcerts) */ 1572 rv = SSL_OptionSet(s, SSL_ENABLE_DELEGATED_CREDENTIALS, enableDelegatedCredentials); 1573 if (rv != SECSuccess) { 1574 SECU_PrintError(progName, "error enabling delegated credentials"); 1575 error = 1; 1576 goto done; 1577 } 1578 1579 /* enable extended master secret mode */ 1580 if (enableExtendedMasterSecret) { 1581 rv = SSL_OptionSet(s, SSL_ENABLE_EXTENDED_MASTER_SECRET, PR_TRUE); 1582 if (rv != SECSuccess) { 1583 SECU_PrintError(progName, "error enabling extended master secret"); 1584 error = 1; 1585 goto done; 1586 } 1587 } 1588 1589 /* enable 0-RTT (TLS 1.3 only) */ 1590 if (enableZeroRtt) { 1591 rv = SSL_OptionSet(s, SSL_ENABLE_0RTT_DATA, PR_TRUE); 1592 if (rv != SECSuccess) { 1593 SECU_PrintError(progName, "error enabling 0-RTT"); 1594 error = 1; 1595 goto done; 1596 } 1597 } 1598 1599 /* Alternate ServerHello content type (TLS 1.3 only) */ 1600 if (enableAltServerHello) { 1601 rv = SSL_UseAltServerHelloType(s, PR_TRUE); 1602 if (rv != SECSuccess) { 1603 SECU_PrintError(progName, "error enabling alternate ServerHello type"); 1604 error = 1; 1605 goto done; 1606 } 1607 } 1608 1609 /* Middlebox compatibility mode (TLS 1.3 only) */ 1610 if (middleboxCompatMode) { 1611 rv = SSL_OptionSet(s, SSL_ENABLE_TLS13_COMPAT_MODE, PR_TRUE); 1612 if (rv != SECSuccess) { 1613 SECU_PrintError(progName, "error enabling middlebox compatibility mode"); 1614 error = 1; 1615 goto done; 1616 } 1617 } 1618 1619 /* require the use of fixed finite-field DH groups */ 1620 if (requireDHNamedGroups) { 1621 rv = SSL_OptionSet(s, SSL_REQUIRE_DH_NAMED_GROUPS, PR_TRUE); 1622 if (rv != SECSuccess) { 1623 SECU_PrintError(progName, "error in requiring the use of fixed finite-field DH groups"); 1624 error = 1; 1625 goto done; 1626 } 1627 } 1628 1629 /* enable Signed Certificate Timestamps. */ 1630 rv = SSL_OptionSet(s, SSL_ENABLE_SIGNED_CERT_TIMESTAMPS, 1631 enableSignedCertTimestamps); 1632 if (rv != SECSuccess) { 1633 SECU_PrintError(progName, "error enabling signed cert timestamps"); 1634 error = 1; 1635 goto done; 1636 } 1637 1638 if (enablePostHandshakeAuth) { 1639 rv = SSL_OptionSet(s, SSL_ENABLE_POST_HANDSHAKE_AUTH, PR_TRUE); 1640 if (rv != SECSuccess) { 1641 SECU_PrintError(progName, "error enabling post-handshake auth"); 1642 error = 1; 1643 goto done; 1644 } 1645 } 1646 1647 if (enableRfc8701Grease) { 1648 rv = SSL_OptionSet(s, SSL_ENABLE_GREASE, PR_TRUE); 1649 if (rv != SECSuccess) { 1650 SECU_PrintError(progName, "error enabling grease"); 1651 error = 1; 1652 goto done; 1653 } 1654 } 1655 1656 if (enableCHExtensionPermuation) { 1657 rv = SSL_OptionSet(s, SSL_ENABLE_CH_EXTENSION_PERMUTATION, PR_TRUE); 1658 if (rv != SECSuccess) { 1659 SECU_PrintError(progName, "error enabling ch extension permutation"); 1660 error = 1; 1661 goto done; 1662 } 1663 } 1664 1665 if (zlibCertificateCompression) { 1666 rv = SSL_SetCertificateCompressionAlgorithm(s, zlibCompressionAlg); 1667 if (rv != SECSuccess) { 1668 SECU_PrintError(progName, "error setting zlib certificate compression algorithm"); 1669 error = 1; 1670 goto done; 1671 } 1672 } 1673 1674 if (enabledGroups) { 1675 rv = SSL_NamedGroupConfig(s, enabledGroups, enabledGroupsCount); 1676 if (rv < 0) { 1677 SECU_PrintError(progName, "SSL_NamedGroupConfig failed"); 1678 error = 1; 1679 goto done; 1680 } 1681 } 1682 1683 if (enabledSigSchemes) { 1684 rv = SSL_SignatureSchemePrefSet(s, enabledSigSchemes, enabledSigSchemeCount); 1685 if (rv < 0) { 1686 SECU_PrintError(progName, "SSL_SignatureSchemePrefSet failed"); 1687 error = 1; 1688 goto done; 1689 } 1690 } 1691 1692 if (echConfigs) { 1693 SECItem echConfigsBin = { siBuffer, NULL, 0 }; 1694 1695 if (!NSSBase64_DecodeBuffer(NULL, &echConfigsBin, echConfigs, 1696 strlen(echConfigs))) { 1697 SECU_PrintError(progName, "ECHConfigs record is invalid base64"); 1698 error = 1; 1699 goto done; 1700 } 1701 1702 rv = SSL_SetClientEchConfigs(s, echConfigsBin.data, echConfigsBin.len); 1703 SECITEM_FreeItem(&echConfigsBin, PR_FALSE); 1704 if (rv < 0) { 1705 SECU_PrintError(progName, "SSL_SetClientEchConfigs failed"); 1706 error = 1; 1707 goto done; 1708 } 1709 } 1710 1711 if (echGreaseSize) { 1712 rv = SSL_EnableTls13GreaseEch(s, PR_TRUE); 1713 if (rv != SECSuccess) { 1714 SECU_PrintError(progName, "SSL_EnableTls13GreaseEch failed"); 1715 error = 1; 1716 goto done; 1717 } 1718 rv = SSL_SetTls13GreaseEchSize(s, echGreaseSize); 1719 if (rv != SECSuccess) { 1720 SECU_PrintError(progName, "SSL_SetTls13GreaseEchSize failed"); 1721 error = 1; 1722 goto done; 1723 } 1724 } 1725 1726 if (psk.data) { 1727 rv = importPsk(s); 1728 if (rv != SECSuccess) { 1729 SECU_PrintError(progName, "importPsk failed"); 1730 error = 1; 1731 goto done; 1732 } 1733 } 1734 1735 serverCertAuth.dbHandle = CERT_GetDefaultCertDB(); 1736 1737 SSL_AuthCertificateHook(s, ownAuthCertificate, &serverCertAuth); 1738 if (override) { 1739 SSL_BadCertHook(s, ownBadCertHandler, NULL); 1740 } 1741 if (actAsServer) { 1742 rv = installServerCertificate(s, nickname); 1743 if (rv != SECSuccess) { 1744 SECU_PrintError(progName, "error installing server cert"); 1745 return 1; 1746 } 1747 rv = SSL_ConfigServerSessionIDCache(1024, 0, 0, "."); 1748 if (rv != SECSuccess) { 1749 SECU_PrintError(progName, "error configuring session cache"); 1750 return 1; 1751 } 1752 initializedServerSessionCache = PR_TRUE; 1753 } else { 1754 SSL_GetClientAuthDataHook(s, own_GetClientAuthData, (void *)nickname); 1755 } 1756 SSL_HandshakeCallback(s, handshakeCallback, hs2SniHostName); 1757 if (hs1SniHostName) { 1758 SSL_SetURL(s, hs1SniHostName); 1759 } else { 1760 SSL_SetURL(s, host); 1761 } 1762 1763 if (actAsServer) { 1764 rv = SSL_ResetHandshake(s, PR_TRUE /* server */); 1765 if (rv != SECSuccess) { 1766 return 1; 1767 } 1768 } else { 1769 /* Try to connect to the server */ 1770 rv = connectToServer(s, pollset); 1771 if (rv != SECSuccess) { 1772 error = 1; 1773 goto done; 1774 } 1775 } 1776 1777 pollset[SSOCK_FD].fd = s; 1778 pollset[SSOCK_FD].in_flags = PR_POLL_EXCEPT; 1779 if (!actAsServer) 1780 pollset[SSOCK_FD].in_flags |= (clientSpeaksFirst ? 0 : PR_POLL_READ); 1781 else 1782 pollset[SSOCK_FD].in_flags |= PR_POLL_READ; 1783 if (requestFile) { 1784 pollset[STDIN_FD].fd = PR_Open(requestFile, PR_RDONLY, 0); 1785 if (!pollset[STDIN_FD].fd) { 1786 fprintf(stderr, "%s: unable to open input file: %s\n", 1787 progName, requestFile); 1788 error = 1; 1789 goto done; 1790 } 1791 } else { 1792 pollset[STDIN_FD].fd = PR_GetSpecialFD(PR_StandardInput); 1793 } 1794 pollset[STDIN_FD].in_flags = PR_POLL_READ; 1795 std_out = PR_GetSpecialFD(PR_StandardOutput); 1796 1797 #if defined(WIN32) 1798 /* PR_Poll cannot be used with stdin on Windows or OS/2. (sigh). 1799 ** But use of PR_Poll and non-blocking sockets is a major feature 1800 ** of this program. So, we simulate a pollable stdin with a 1801 ** TCP socket pair and a thread that reads stdin and writes to 1802 ** that socket pair. 1803 */ 1804 { 1805 PRFileDesc *fds[2]; 1806 PRThread *thread; 1807 1808 int nspr_rv = PR_NewTCPSocketPair(fds); 1809 if (nspr_rv != PR_SUCCESS) { 1810 SECU_PrintError(progName, "PR_NewTCPSocketPair failed"); 1811 error = 1; 1812 goto done; 1813 } 1814 pollset[STDIN_FD].fd = fds[1]; 1815 1816 thread = PR_CreateThread(PR_USER_THREAD, thread_main, fds[0], 1817 PR_PRIORITY_NORMAL, PR_GLOBAL_THREAD, 1818 PR_UNJOINABLE_THREAD, 0); 1819 if (!thread) { 1820 SECU_PrintError(progName, "PR_CreateThread failed"); 1821 error = 1; 1822 goto done; 1823 } 1824 } 1825 #endif 1826 1827 if (serverCertAuth.testFreshStatusFromSideChannel) { 1828 SSL_ForceHandshake(s); 1829 error = serverCertAuth.sideChannelRevocationTestResultCode; 1830 goto done; 1831 } 1832 1833 /* 1834 ** Select on stdin and on the socket. Write data from stdin to 1835 ** socket, read data from socket and write to stdout. 1836 */ 1837 requestToExit = PR_FALSE; 1838 FPRINTF(stderr, "%s: ready...\n", progName); 1839 while (!requestToExit && 1840 (pollset[SSOCK_FD].in_flags || pollset[STDIN_FD].in_flags)) { 1841 PRUint8 buf[4000]; /* buffer for stdin */ 1842 int nb; /* num bytes read from stdin. */ 1843 1844 rv = restartHandshakeAfterServerCertIfNeeded(s, &serverCertAuth, 1845 override); 1846 if (rv != SECSuccess) { 1847 error = EXIT_CODE_HANDSHAKE_FAILED; 1848 SECU_PrintError(progName, "authentication of server cert failed"); 1849 goto done; 1850 } 1851 1852 rv = restartHandshakeAfterClientCertIfNeeded(s); 1853 if (rv == SECSuccess) { 1854 continue; 1855 } 1856 1857 pollset[SSOCK_FD].out_flags = 0; 1858 pollset[STDIN_FD].out_flags = 0; 1859 1860 FPRINTF(stderr, "%s: about to call PR_Poll !\n", progName); 1861 filesReady = PR_Poll(pollset, PR_ARRAY_SIZE(pollset), 1862 PR_INTERVAL_NO_TIMEOUT); 1863 if (filesReady < 0) { 1864 SECU_PrintError(progName, "select failed"); 1865 error = 1; 1866 goto done; 1867 } 1868 if (filesReady == 0) { /* shouldn't happen! */ 1869 FPRINTF(stderr, "%s: PR_Poll returned zero!\n", progName); 1870 error = 1; 1871 goto done; 1872 } 1873 FPRINTF(stderr, "%s: PR_Poll returned!\n", progName); 1874 if (pollset[STDIN_FD].in_flags) { 1875 FPRINTF(stderr, 1876 "%s: PR_Poll returned 0x%02x for stdin out_flags.\n", 1877 progName, pollset[STDIN_FD].out_flags); 1878 } 1879 if (pollset[SSOCK_FD].in_flags) { 1880 FPRINTF(stderr, 1881 "%s: PR_Poll returned 0x%02x for socket out_flags.\n", 1882 progName, pollset[SSOCK_FD].out_flags); 1883 } 1884 if (pollset[STDIN_FD].out_flags & PR_POLL_READ) { 1885 /* Read from stdin and write to socket */ 1886 nb = PR_Read(pollset[STDIN_FD].fd, buf, sizeof(buf)); 1887 FPRINTF(stderr, "%s: stdin read %d bytes\n", progName, nb); 1888 if (nb < 0) { 1889 if (PR_GetError() != PR_WOULD_BLOCK_ERROR) { 1890 SECU_PrintError(progName, "read from stdin failed"); 1891 error = 1; 1892 break; 1893 } 1894 } else if (nb == 0) { 1895 /* EOF on stdin, stop polling stdin for read. */ 1896 pollset[STDIN_FD].in_flags = 0; 1897 if (actAsServer) 1898 requestToExit = PR_TRUE; 1899 } else { 1900 error = writeBytesToServer(s, buf, nb); 1901 if (error) { 1902 if (echConfigs) { 1903 (void)printEchRetryConfigs(s); 1904 } 1905 goto done; 1906 } 1907 pollset[SSOCK_FD].in_flags = PR_POLL_READ; 1908 } 1909 } 1910 1911 if (pollset[SSOCK_FD].in_flags) { 1912 FPRINTF(stderr, 1913 "%s: PR_Poll returned 0x%02x for socket out_flags.\n", 1914 progName, pollset[SSOCK_FD].out_flags); 1915 } 1916 #ifdef PR_POLL_HUP 1917 #define POLL_RECV_FLAGS (PR_POLL_READ | PR_POLL_ERR | PR_POLL_HUP) 1918 #else 1919 #define POLL_RECV_FLAGS (PR_POLL_READ | PR_POLL_ERR) 1920 #endif 1921 if (pollset[SSOCK_FD].out_flags & POLL_RECV_FLAGS) { 1922 /* Read from socket and write to stdout */ 1923 nb = PR_Recv(pollset[SSOCK_FD].fd, buf, sizeof buf, 0, maxInterval); 1924 FPRINTF(stderr, "%s: Read from server %d bytes\n", progName, nb); 1925 if (nb < 0) { 1926 if (PR_GetError() != PR_WOULD_BLOCK_ERROR) { 1927 SECU_PrintError(progName, "read from socket failed"); 1928 error = 1; 1929 goto done; 1930 } 1931 } else if (nb == 0) { 1932 /* EOF from socket... stop polling socket for read */ 1933 pollset[SSOCK_FD].in_flags = 0; 1934 } else { 1935 if (skipProtoHeader != PR_TRUE || wrStarted == PR_TRUE) { 1936 PR_Write(std_out, buf, nb); 1937 } else { 1938 separateReqHeader(std_out, (char *)buf, nb, &wrStarted, 1939 &headerSeparatorPtrnId); 1940 } 1941 if (verbose) 1942 fputs("\n\n", stderr); 1943 } 1944 } 1945 milliPause(50 * multiplier); 1946 } 1947 1948 done: 1949 if (s) { 1950 PR_Close(s); 1951 } 1952 if (requestFile && pollset[STDIN_FD].fd) { 1953 PR_Close(pollset[STDIN_FD].fd); 1954 } 1955 return error; 1956 } 1957 1958 const char *cmdLineOptions = "46A:BCDEFGHI:J:KL:M:N:OP:QR:STUV:W:X:YZa:bc:d:efgh:i:m:n:op:qr:st:uvw:x:z:"; 1959 const PLLongOpt cmdLineLongOpts[] = { 1960 { .longOptName = "enable-rfc8701-grease", .longOption = 0, .valueRequired = PR_FALSE }, 1961 { .longOptName = "enable-ch-extension-permutation", .longOption = 1, .valueRequired = PR_FALSE }, 1962 { .longOptName = "zlib-certificate-compression", .longOption = 2, .valueRequired = PR_FALSE }, 1963 { .longOptName = NULL }, 1964 }; 1965 1966 int 1967 main(int argc, char **argv) 1968 { 1969 PLOptState *optstate; 1970 PLOptStatus optstatus; 1971 PRStatus status; 1972 PRStatus prStatus; 1973 int error = 0; 1974 char *tmp; 1975 SECStatus rv; 1976 char *certDir = NULL; 1977 PRBool openDB = PR_TRUE; 1978 PRBool loadDefaultRootCAs = PR_FALSE; 1979 char *rootModule = NULL; 1980 int numConnections = 1; 1981 PRFileDesc *s = NULL; 1982 1983 serverCertAuth.shouldPause = PR_TRUE; 1984 serverCertAuth.isPaused = PR_FALSE; 1985 serverCertAuth.dbHandle = NULL; 1986 serverCertAuth.testFreshStatusFromSideChannel = PR_FALSE; 1987 serverCertAuth.sideChannelRevocationTestResultCode = EXIT_CODE_HANDSHAKE_FAILED; 1988 serverCertAuth.requireDataForIntermediates = PR_FALSE; 1989 serverCertAuth.allowOCSPSideChannelData = PR_TRUE; 1990 serverCertAuth.allowCRLSideChannelData = PR_TRUE; 1991 1992 progName = strrchr(argv[0], '/'); 1993 if (!progName) 1994 progName = strrchr(argv[0], '\\'); 1995 progName = progName ? progName + 1 : argv[0]; 1996 1997 tmp = PR_GetEnvSecure("NSS_DEBUG_TIMEOUT"); 1998 if (tmp && tmp[0]) { 1999 int sec = PORT_Atoi(tmp); 2000 if (sec > 0) { 2001 maxInterval = PR_SecondsToInterval(sec); 2002 } 2003 } 2004 2005 optstate = PL_CreateLongOptState(argc, argv, cmdLineOptions, cmdLineLongOpts); 2006 while ((optstatus = PL_GetNextOpt(optstate)) == PL_OPT_OK) { 2007 switch (optstate->longOption) { 2008 case '?': 2009 default: 2010 Usage(); 2011 break; 2012 2013 case 0: 2014 enableRfc8701Grease = PR_TRUE; 2015 break; 2016 2017 case 1: 2018 enableCHExtensionPermuation = PR_TRUE; 2019 break; 2020 2021 case 2: 2022 zlibCertificateCompression = PR_TRUE; 2023 break; 2024 2025 case '4': 2026 allowIPv6 = PR_FALSE; 2027 if (!allowIPv4) 2028 Usage(); 2029 break; 2030 case '6': 2031 allowIPv4 = PR_FALSE; 2032 if (!allowIPv6) 2033 Usage(); 2034 break; 2035 2036 case 'A': 2037 requestFile = PORT_Strdup(optstate->value); 2038 break; 2039 2040 case 'B': 2041 enableDelegatedCredentials = PR_TRUE; 2042 break; 2043 2044 case 'C': 2045 ++dumpServerChain; 2046 break; 2047 2048 case 'D': 2049 openDB = PR_FALSE; 2050 break; 2051 2052 case 'E': 2053 enablePostHandshakeAuth = PR_TRUE; 2054 break; 2055 2056 case 'F': 2057 if (serverCertAuth.testFreshStatusFromSideChannel) { 2058 /* parameter given twice or more */ 2059 serverCertAuth.requireDataForIntermediates = PR_TRUE; 2060 } 2061 serverCertAuth.testFreshStatusFromSideChannel = PR_TRUE; 2062 break; 2063 2064 case 'G': 2065 enableExtendedMasterSecret = PR_TRUE; 2066 break; 2067 2068 case 'H': 2069 requireDHNamedGroups = PR_TRUE; 2070 break; 2071 2072 case 'O': 2073 clientCertAsyncSelect = PR_FALSE; 2074 serverCertAuth.shouldPause = PR_FALSE; 2075 break; 2076 2077 case 'K': 2078 forceFallbackSCSV = PR_TRUE; 2079 break; 2080 2081 case 'L': 2082 numConnections = atoi(optstate->value); 2083 break; 2084 2085 case 'M': 2086 switch (atoi(optstate->value)) { 2087 case 1: 2088 serverCertAuth.allowOCSPSideChannelData = PR_TRUE; 2089 serverCertAuth.allowCRLSideChannelData = PR_FALSE; 2090 break; 2091 case 2: 2092 serverCertAuth.allowOCSPSideChannelData = PR_FALSE; 2093 serverCertAuth.allowCRLSideChannelData = PR_TRUE; 2094 break; 2095 case 0: 2096 default: 2097 serverCertAuth.allowOCSPSideChannelData = PR_TRUE; 2098 serverCertAuth.allowCRLSideChannelData = PR_TRUE; 2099 break; 2100 }; 2101 break; 2102 2103 case 'N': 2104 echConfigs = PORT_Strdup(optstate->value); 2105 break; 2106 2107 case 'i': 2108 echGreaseSize = PORT_Atoi(optstate->value); 2109 if (!echGreaseSize || echGreaseSize > 255) { 2110 fprintf(stderr, "ECH Grease size must be within 1..255 (inclusive).\n"); 2111 exit(-1); 2112 } 2113 break; 2114 2115 case 'P': 2116 useDTLS = PR_TRUE; 2117 if (!strcmp(optstate->value, "server")) { 2118 actAsServer = 1; 2119 } else { 2120 if (strcmp(optstate->value, "client")) { 2121 Usage(); 2122 } 2123 } 2124 break; 2125 2126 case 'Q': 2127 stopAfterHandshake = PR_TRUE; 2128 break; 2129 2130 case 'R': 2131 rootModule = PORT_Strdup(optstate->value); 2132 break; 2133 2134 case 'S': 2135 skipProtoHeader = PR_TRUE; 2136 break; 2137 2138 case 'T': 2139 enableCertStatus = 1; 2140 break; 2141 2142 case 'U': 2143 enableSignedCertTimestamps = 1; 2144 break; 2145 2146 case 'V': 2147 versionString = PORT_Strdup(optstate->value); 2148 break; 2149 2150 case 'X': 2151 if (!strcmp(optstate->value, "alt-server-hello")) { 2152 enableAltServerHello = PR_TRUE; 2153 } else { 2154 Usage(); 2155 } 2156 break; 2157 case 'Y': 2158 PrintCipherUsage(); 2159 exit(0); 2160 break; 2161 2162 case 'Z': 2163 enableZeroRtt = PR_TRUE; 2164 zeroRttData = PORT_ZAlloc(ZERO_RTT_MAX); 2165 if (!zeroRttData) { 2166 fprintf(stderr, "Unable to allocate buffer for 0-RTT\n"); 2167 exit(1); 2168 } 2169 break; 2170 2171 case 'a': 2172 if (!hs1SniHostName) { 2173 hs1SniHostName = PORT_Strdup(optstate->value); 2174 } else if (!hs2SniHostName) { 2175 hs2SniHostName = PORT_Strdup(optstate->value); 2176 } else { 2177 Usage(); 2178 } 2179 break; 2180 2181 case 'b': 2182 loadDefaultRootCAs = PR_TRUE; 2183 break; 2184 2185 case 'c': 2186 cipherString = PORT_Strdup(optstate->value); 2187 break; 2188 2189 case 'g': 2190 enableFalseStart = 1; 2191 break; 2192 2193 case 'd': 2194 certDir = PORT_Strdup(optstate->value); 2195 break; 2196 2197 case 'e': 2198 middleboxCompatMode = PR_TRUE; 2199 break; 2200 2201 case 'f': 2202 clientSpeaksFirst = PR_TRUE; 2203 break; 2204 2205 case 'h': 2206 host = PORT_Strdup(optstate->value); 2207 break; 2208 2209 case 'm': 2210 multiplier = atoi(optstate->value); 2211 if (multiplier < 0) 2212 multiplier = 0; 2213 break; 2214 2215 case 'n': 2216 nickname = PORT_Strdup(optstate->value); 2217 break; 2218 2219 case 'o': 2220 override = 1; 2221 break; 2222 2223 case 'p': 2224 portno = (PRUint16)atoi(optstate->value); 2225 break; 2226 2227 case 'q': 2228 pingServerFirst = PR_TRUE; 2229 break; 2230 2231 case 's': 2232 disableLocking = 1; 2233 break; 2234 2235 case 't': 2236 pingTimeoutSeconds = atoi(optstate->value); 2237 break; 2238 2239 case 'u': 2240 enableSessionTickets = PR_TRUE; 2241 break; 2242 2243 case 'v': 2244 verbose++; 2245 break; 2246 2247 case 'r': 2248 renegotiationsToDo = atoi(optstate->value); 2249 break; 2250 2251 case 'w': 2252 pwdata.source = PW_PLAINTEXT; 2253 pwdata.data = PORT_Strdup(optstate->value); 2254 break; 2255 2256 case 'W': 2257 pwdata.source = PW_FROMFILE; 2258 pwdata.data = PORT_Strdup(optstate->value); 2259 break; 2260 2261 case 'I': 2262 rv = parseGroupList(optstate->value, &enabledGroups, &enabledGroupsCount); 2263 if (rv != SECSuccess) { 2264 PL_DestroyOptState(optstate); 2265 fprintf(stderr, "Bad group specified.\n"); 2266 Usage(); 2267 } 2268 break; 2269 2270 case 'J': 2271 rv = parseSigSchemeList(optstate->value, &enabledSigSchemes, &enabledSigSchemeCount); 2272 if (rv != SECSuccess) { 2273 PL_DestroyOptState(optstate); 2274 fprintf(stderr, "Bad signature scheme specified.\n"); 2275 Usage(); 2276 } 2277 break; 2278 2279 case 'x': 2280 rv = parseExporters(optstate->value, 2281 &enabledExporters, 2282 &enabledExporterCount); 2283 if (rv != SECSuccess) { 2284 PL_DestroyOptState(optstate); 2285 fprintf(stderr, "Bad exporter specified.\n"); 2286 Usage(); 2287 } 2288 break; 2289 2290 case 'z': 2291 rv = readPSK(optstate->value, &psk, &pskLabel); 2292 if (rv != SECSuccess) { 2293 PL_DestroyOptState(optstate); 2294 fprintf(stderr, "Bad PSK specified.\n"); 2295 Usage(); 2296 } 2297 break; 2298 } 2299 } 2300 PL_DestroyOptState(optstate); 2301 2302 SSL_VersionRangeGetSupported(useDTLS ? ssl_variant_datagram : ssl_variant_stream, &enabledVersions); 2303 2304 if (versionString) { 2305 if (SECU_ParseSSLVersionRangeString(versionString, 2306 enabledVersions, &enabledVersions) != 2307 SECSuccess) { 2308 fprintf(stderr, "Bad version specified.\n"); 2309 Usage(); 2310 } 2311 PORT_Free(versionString); 2312 } 2313 2314 if (optstatus == PL_OPT_BAD) { 2315 Usage(); 2316 } 2317 2318 if (!host || !portno) { 2319 fprintf(stderr, "%s: parameters -h and -p are mandatory\n", progName); 2320 Usage(); 2321 } 2322 2323 if (serverCertAuth.testFreshStatusFromSideChannel && 2324 serverCertAuth.shouldPause) { 2325 fprintf(stderr, "%s: -F requires the use of -O\n", progName); 2326 exit(1); 2327 } 2328 2329 if (certDir && !openDB) { 2330 fprintf(stderr, "%s: Cannot combine parameters -D and -d\n", progName); 2331 exit(1); 2332 } 2333 2334 if (rootModule && loadDefaultRootCAs) { 2335 fprintf(stderr, "%s: Cannot combine parameters -b and -R\n", progName); 2336 exit(1); 2337 } 2338 2339 if (enablePostHandshakeAuth && !nickname) { 2340 fprintf(stderr, "%s: -E requires the use of -n\n", progName); 2341 exit(1); 2342 } 2343 2344 PR_Init(PR_SYSTEM_THREAD, PR_PRIORITY_NORMAL, 1); 2345 2346 PK11_SetPasswordFunc(SECU_GetModulePassword); 2347 memset(&addr, 0, sizeof(addr)); 2348 status = PR_StringToNetAddr(host, &addr); 2349 if (status == PR_SUCCESS) { 2350 addr.inet.port = PR_htons(portno); 2351 } else { 2352 PRBool gotLoopbackIP = PR_FALSE; 2353 if ((!strcmp(host, "localhost") || !strcmp(host, "localhost.localdomain")) 2354 /* only check for preference if both types are allowed */ 2355 && allowIPv4 && allowIPv6) { 2356 /* make a decision which IP to prefer */ 2357 status = PR_GetPrefLoopbackAddrInfo(&addr, portno); 2358 if (status != PR_FAILURE) { 2359 gotLoopbackIP = PR_TRUE; 2360 } 2361 } 2362 2363 if (!gotLoopbackIP) { 2364 /* Lookup host */ 2365 PRAddrInfo *addrInfo; 2366 void *enumPtr = NULL; 2367 2368 addrInfo = PR_GetAddrInfoByName(host, PR_AF_UNSPEC, 2369 PR_AI_ADDRCONFIG | PR_AI_NOCANONNAME); 2370 if (!addrInfo) { 2371 fprintf(stderr, "HOSTNAME=%s\n", host); 2372 SECU_PrintError(progName, "error looking up host"); 2373 error = 1; 2374 goto done; 2375 } 2376 for (;;) { 2377 enumPtr = PR_EnumerateAddrInfo(enumPtr, addrInfo, portno, &addr); 2378 if (enumPtr == NULL) 2379 break; 2380 if (addr.raw.family == PR_AF_INET && allowIPv4) 2381 break; 2382 if (addr.raw.family == PR_AF_INET6 && allowIPv6) 2383 break; 2384 } 2385 PR_FreeAddrInfo(addrInfo); 2386 if (enumPtr == NULL) { 2387 SECU_PrintError(progName, "error looking up host address"); 2388 error = 1; 2389 goto done; 2390 } 2391 } 2392 } 2393 2394 printHostNameAndAddr(host, &addr); 2395 2396 if (!certDir) { 2397 certDir = SECU_DefaultSSLDir(); /* Look in $SSL_DIR */ 2398 certDir = SECU_ConfigDirectory(certDir); 2399 } else { 2400 char *certDirTmp = certDir; 2401 certDir = SECU_ConfigDirectory(certDirTmp); 2402 PORT_Free(certDirTmp); 2403 } 2404 2405 if (pingServerFirst) { 2406 int iter = 0; 2407 PRErrorCode err; 2408 2409 int max_attempts = MAX_WAIT_FOR_SERVER; 2410 if (pingTimeoutSeconds >= 0) { 2411 /* If caller requested a timeout, let's try just twice. */ 2412 max_attempts = 2; 2413 } 2414 do { 2415 PRIntervalTime timeoutInterval = PR_INTERVAL_NO_TIMEOUT; 2416 s = PR_OpenTCPSocket(addr.raw.family); 2417 if (s == NULL) { 2418 SECU_PrintError(progName, "Failed to create a TCP socket"); 2419 error = 1; 2420 goto done; 2421 } 2422 opt.option = PR_SockOpt_Nonblocking; 2423 opt.value.non_blocking = PR_FALSE; 2424 prStatus = PR_SetSocketOption(s, &opt); 2425 if (prStatus != PR_SUCCESS) { 2426 SECU_PrintError(progName, 2427 "Failed to set blocking socket option"); 2428 error = 1; 2429 goto done; 2430 } 2431 if (pingTimeoutSeconds >= 0) { 2432 timeoutInterval = PR_SecondsToInterval(pingTimeoutSeconds); 2433 } 2434 prStatus = PR_Connect(s, &addr, timeoutInterval); 2435 if (prStatus == PR_SUCCESS) { 2436 PR_Shutdown(s, PR_SHUTDOWN_BOTH); 2437 goto done; 2438 } 2439 err = PR_GetError(); 2440 if ((err != PR_CONNECT_REFUSED_ERROR) && 2441 (err != PR_CONNECT_RESET_ERROR)) { 2442 SECU_PrintError(progName, "TCP Connection failed"); 2443 error = 1; 2444 goto done; 2445 } 2446 PR_Close(s); 2447 s = NULL; 2448 PR_Sleep(PR_MillisecondsToInterval(WAIT_INTERVAL)); 2449 } while (++iter < max_attempts); 2450 SECU_PrintError(progName, 2451 "Client timed out while waiting for connection to server"); 2452 error = 1; 2453 goto done; 2454 } 2455 2456 /* open the cert DB, the key DB, and the secmod DB. */ 2457 if (openDB) { 2458 rv = NSS_Init(certDir); 2459 if (rv != SECSuccess) { 2460 SECU_PrintError(progName, "unable to open cert database"); 2461 error = 1; 2462 goto done; 2463 } 2464 } else { 2465 rv = NSS_NoDB_Init(NULL); 2466 if (rv != SECSuccess) { 2467 SECU_PrintError(progName, "failed to initialize NSS"); 2468 error = 1; 2469 goto done; 2470 } 2471 } 2472 2473 if (loadDefaultRootCAs) { 2474 SECMOD_AddNewModule("Builtins", 2475 DLL_PREFIX "nssckbi." DLL_SUFFIX, 0, 0); 2476 } else if (rootModule) { 2477 SECMOD_AddNewModule("Builtins", rootModule, 0, 0); 2478 } 2479 2480 /* all SSL3 cipher suites are enabled by default. */ 2481 if (cipherString) { 2482 /* disable all the ciphers, then enable the ones we want. */ 2483 disableAllSSLCiphers(); 2484 } 2485 2486 while (numConnections--) { 2487 error = run(); 2488 if (error) { 2489 goto done; 2490 } 2491 } 2492 2493 done: 2494 if (s) { 2495 PR_Close(s); 2496 } 2497 2498 PORT_Free((void *)requestFile); 2499 PORT_Free(hs1SniHostName); 2500 PORT_Free(hs2SniHostName); 2501 PORT_Free(nickname); 2502 PORT_Free(pwdata.data); 2503 PORT_Free(host); 2504 PORT_Free(zeroRttData); 2505 PORT_Free(echConfigs); 2506 SECITEM_ZfreeItem(&psk, PR_FALSE); 2507 SECITEM_ZfreeItem(&pskLabel, PR_FALSE); 2508 2509 if (enabledGroups) { 2510 PORT_Free(enabledGroups); 2511 } 2512 if (NSS_IsInitialized()) { 2513 SSL_ClearSessionCache(); 2514 if (initializedServerSessionCache) { 2515 if (SSL_ShutdownServerSessionIDCache() != SECSuccess) { 2516 error = 1; 2517 } 2518 } 2519 2520 if (NSS_Shutdown() != SECSuccess) { 2521 error = 1; 2522 } 2523 } 2524 2525 FPRINTF(stderr, "tstclnt: exiting with return code %d\n", error); 2526 PR_Cleanup(); 2527 return error; 2528 }