2016-02-23 20:19:11 +00:00
|
|
|
/*
|
|
|
|
* sslEcdsa.cpp - test SSL connections to a number of known servers.
|
|
|
|
*
|
|
|
|
* Note this uses the keychain ecdsa.keychain in cwd; it contains an
|
|
|
|
* SSL client auth identity. To avoid ACL hassles and to allow this
|
|
|
|
* program to run hands-off, the identity is imported into this keychain
|
|
|
|
* with no ACL on the private key. This is done with the kcImport tool
|
|
|
|
* like so:
|
|
|
|
*
|
|
|
|
* % kcImport ecc-secp256r1-client.pfx -k ___path_to_cwd___/ecdsa.keychain -f pkcs12 -z password -n
|
|
|
|
*/
|
|
|
|
#include <Security/SecureTransport.h>
|
|
|
|
#include <Security/SecureTransportPriv.h>
|
|
|
|
#include <Security/Security.h>
|
|
|
|
#include "sslAppUtils.h"
|
|
|
|
#include "ioSock.h"
|
|
|
|
//#include <utilLib/common.h>
|
|
|
|
|
|
|
|
#include <Security/SecBase.h>
|
|
|
|
|
|
|
|
#include <stdio.h>
|
|
|
|
#include <stdlib.h>
|
|
|
|
#include <unistd.h>
|
|
|
|
#include <string.h>
|
|
|
|
#include <time.h>
|
|
|
|
#include <ctype.h>
|
|
|
|
#include <sys/param.h>
|
|
|
|
|
|
|
|
#if NO_SERVER
|
2020-07-06 11:59:58 +00:00
|
|
|
#include "keychain/securityd/spi.h"
|
2016-02-23 20:19:11 +00:00
|
|
|
#endif
|
|
|
|
|
|
|
|
|
|
|
|
static void usage(char **argv)
|
|
|
|
{
|
|
|
|
printf("Usage: %s [options]\n", argv[0]);
|
|
|
|
printf("options:\n");
|
|
|
|
printf(" -t testNum -- only do test testNum; default is all\n");
|
|
|
|
printf(" -q -- quiet\n");
|
|
|
|
printf(" -b -- non blocking I/O\n");
|
|
|
|
printf(" -p -- pause for malloc debug\n");
|
|
|
|
exit(1);
|
|
|
|
}
|
|
|
|
|
|
|
|
#define IGNORE_SIGPIPE 1
|
|
|
|
#if IGNORE_SIGPIPE
|
|
|
|
#include <signal.h>
|
|
|
|
|
|
|
|
static void sigpipe(int sig)
|
|
|
|
{
|
|
|
|
}
|
|
|
|
#endif /* IGNORE_SIGPIPE */
|
|
|
|
|
|
|
|
/* Test params */
|
|
|
|
typedef struct {
|
|
|
|
const char *hostName;
|
|
|
|
int port;
|
|
|
|
|
|
|
|
/* We enable exacly one CipherSuite and require that to work */
|
|
|
|
SSLCipherSuite cipherSuite;
|
|
|
|
|
|
|
|
/* Curve to specify; SSL_Curve_None means use default */
|
|
|
|
SSL_ECDSA_NamedCurve specCurve;
|
|
|
|
|
|
|
|
/* Curve to verify; SSL_Curve_None means don't check */
|
|
|
|
SSL_ECDSA_NamedCurve expCurve;
|
|
|
|
|
|
|
|
/*
|
|
|
|
* keychain containing client-side cert, located in LOCAL_BUILD_DIR.
|
|
|
|
* NULL means no keychain.
|
|
|
|
*/
|
|
|
|
const char *keychain;
|
|
|
|
|
|
|
|
/* password for above keychain */
|
|
|
|
const char *kcPassword;
|
|
|
|
} EcdsaTestParams;
|
|
|
|
|
|
|
|
static const EcdsaTestParams ecdsaTestParams[] =
|
|
|
|
{
|
|
|
|
/* client auth */
|
|
|
|
{
|
|
|
|
"tls.secg.org", 8443, TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_None,
|
|
|
|
"ecdsa.keychain", "password"
|
|
|
|
},
|
|
|
|
/* tla.secg.org -- port 40023 - secp256r1 */
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40023, TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40023, TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA,
|
|
|
|
SSL_Curve_secp256r1, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40023, TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40023, TLS_ECDHE_ECDSA_WITH_RC4_128_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40023, TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40023, TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40023, TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40023, TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA,
|
|
|
|
SSL_Curve_secp256r1, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40023, TLS_ECDH_ECDSA_WITH_RC4_128_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40023, TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40023, TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA,
|
|
|
|
SSL_Curve_secp256r1, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
|
|
|
|
/* tla.secg.org -- port 40024 - secp384r1 */
|
|
|
|
/* This one doesn't let you specify a curve */
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40024, TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp384r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40024, TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp384r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40024, TLS_ECDHE_ECDSA_WITH_RC4_128_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp384r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40024, TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp384r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40024, TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp384r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40024, TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp384r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40024, TLS_ECDH_ECDSA_WITH_RC4_128_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp384r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40024, TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp384r1
|
|
|
|
},
|
|
|
|
|
|
|
|
/* tla.secg.org -- port 40025 - secp521r1 */
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40025, TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp521r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40025, TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp521r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40025, TLS_ECDHE_ECDSA_WITH_RC4_128_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp521r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40025, TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp521r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40025, TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp521r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40025, TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp521r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40025, TLS_ECDH_ECDSA_WITH_RC4_128_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp521r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"tls.secg.org", 40025, TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp521r1
|
|
|
|
},
|
|
|
|
|
|
|
|
|
|
|
|
/* ecc.fedora.redhat.com - port 8443 - secp256r1 */
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 8443, TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 8443, TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA,
|
|
|
|
SSL_Curve_secp256r1, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 8443, TLS_ECDHE_ECDSA_WITH_RC4_128_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 8443, TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA,
|
|
|
|
SSL_Curve_secp256r1, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 8443, TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA,
|
|
|
|
SSL_Curve_secp256r1, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 8443, TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 8443, TLS_ECDH_ECDSA_WITH_RC4_128_SHA,
|
|
|
|
SSL_Curve_secp256r1, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 8443, TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA,
|
|
|
|
SSL_Curve_secp256r1, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
|
|
|
|
/* ecc.fedora.redhat.com - port 8444 - SSL_Curve_secp384r1 */
|
|
|
|
/* This doesn't work, the server requires a redirect ...
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 8444, TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp384r1
|
|
|
|
},
|
|
|
|
*/
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 8445, TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp521r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 8444, TLS_ECDHE_ECDSA_WITH_RC4_128_SHA,
|
|
|
|
SSL_Curve_secp384r1, SSL_Curve_secp384r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 8444, TLS_ECDHE_ECDSA_WITH_3DES_EDE_CBC_SHA,
|
|
|
|
SSL_Curve_secp384r1, SSL_Curve_secp384r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 8444, TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp384r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 8444, TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp384r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 8444, TLS_ECDH_ECDSA_WITH_RC4_128_SHA,
|
|
|
|
SSL_Curve_secp384r1, SSL_Curve_secp384r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 8444, TLS_ECDH_ECDSA_WITH_3DES_EDE_CBC_SHA,
|
|
|
|
SSL_Curve_secp384r1, SSL_Curve_secp384r1
|
|
|
|
},
|
|
|
|
|
|
|
|
/* ecc.fedora.redhat.com - port 8445 - SSL_Curve_secp521r1 */
|
|
|
|
/* This one can't do RC4_128 without some HTTP redirection */
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 8445, TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp521r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 8445, TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA,
|
|
|
|
SSL_Curve_secp521r1, SSL_Curve_secp521r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 8445, TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA,
|
|
|
|
SSL_Curve_secp521r1, SSL_Curve_secp521r1
|
|
|
|
},
|
|
|
|
|
|
|
|
/* ecc.fedora.redhat.com - port 443 - secp256r1 with RSA authentication */
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 443, TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA,
|
|
|
|
SSL_Curve_secp256r1, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 443, TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA,
|
|
|
|
SSL_Curve_secp256r1, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 443, TLS_ECDHE_RSA_WITH_RC4_128_SHA,
|
|
|
|
SSL_Curve_secp256r1, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 443, TLS_ECDHE_RSA_WITH_3DES_EDE_CBC_SHA,
|
|
|
|
SSL_Curve_secp256r1, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 443, TLS_ECDH_RSA_WITH_AES_128_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 443, TLS_ECDH_RSA_WITH_AES_256_CBC_SHA,
|
|
|
|
SSL_Curve_secp256r1, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 443, TLS_ECDH_RSA_WITH_RC4_128_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
{
|
|
|
|
"ecc.fedora.redhat.com", 443, TLS_ECDH_RSA_WITH_3DES_EDE_CBC_SHA,
|
|
|
|
SSL_Curve_None, SSL_Curve_secp256r1
|
|
|
|
},
|
|
|
|
|
|
|
|
/* etc. */
|
|
|
|
};
|
|
|
|
#define NUM_TEST_PARAMS (sizeof(ecdsaTestParams) / sizeof(ecdsaTestParams[0]))
|
|
|
|
|
|
|
|
static void dumpParams(
|
|
|
|
const EcdsaTestParams *testParams)
|
|
|
|
{
|
|
|
|
printf("%s:%d %-33s ",
|
|
|
|
testParams->hostName, testParams->port,
|
|
|
|
/* skip leading "TLS_" */
|
|
|
|
sslGetCipherSuiteString(testParams->cipherSuite)+4);
|
|
|
|
if(testParams->expCurve != SSL_Curve_None) {
|
|
|
|
printf("expCurve = %s ", sslCurveString(testParams->expCurve));
|
|
|
|
}
|
|
|
|
if(testParams->specCurve != SSL_Curve_None) {
|
|
|
|
printf("specCurve = %s ", sslCurveString(testParams->specCurve));
|
|
|
|
}
|
|
|
|
if(testParams->keychain) {
|
|
|
|
printf("Client Auth Enabled");
|
|
|
|
}
|
|
|
|
putchar('\n');
|
|
|
|
}
|
|
|
|
|
|
|
|
static void dumpErrInfo(
|
|
|
|
const char *op,
|
|
|
|
const EcdsaTestParams *testParams,
|
|
|
|
OSStatus ortn)
|
|
|
|
{
|
|
|
|
printf("***%s failed for ", op);
|
|
|
|
dumpParams(testParams);
|
|
|
|
printf(" error: %s\n", sslGetSSLErrString(ortn));
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Custom ping for this test.
|
|
|
|
*/
|
|
|
|
#define RCV_BUF_SIZE 256
|
|
|
|
|
|
|
|
static int doSslPing(
|
|
|
|
const EcdsaTestParams *testParams,
|
|
|
|
bool quiet,
|
|
|
|
int nonBlocking)
|
|
|
|
{
|
|
|
|
PeerSpec peerId;
|
|
|
|
otSocket sock = 0;
|
|
|
|
OSStatus ortn;
|
|
|
|
SSLContextRef ctx = NULL;
|
|
|
|
SSLCipherSuite negCipher;
|
|
|
|
|
|
|
|
/* first make sure requested server is there */
|
|
|
|
ortn = MakeServerConnection(testParams->hostName, testParams->port,
|
|
|
|
nonBlocking, &sock, &peerId);
|
|
|
|
if(ortn) {
|
|
|
|
printf("MakeServerConnection(%s) returned %d\n",
|
|
|
|
testParams->hostName, (int)ortn);
|
|
|
|
return -1;
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Set up a SecureTransport session.
|
|
|
|
* First the standard calls.
|
|
|
|
*/
|
2020-07-06 11:59:58 +00:00
|
|
|
#pragma clang diagnostic push
|
|
|
|
#pragma clang diagnostic ignored "-Wdeprecated-declarations"
|
2016-02-23 20:19:11 +00:00
|
|
|
ortn = SSLNewContext(false, &ctx);
|
|
|
|
if(ortn) {
|
|
|
|
printSslErrStr("SSLNewContext", ortn);
|
|
|
|
goto cleanup;
|
|
|
|
}
|
|
|
|
ortn = SSLSetIOFuncs(ctx, SocketRead, SocketWrite);
|
|
|
|
if(ortn) {
|
|
|
|
printSslErrStr("SSLSetIOFuncs", ortn);
|
|
|
|
goto cleanup;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Restrict to only TLSv1 - we have to do this because of Radar 6133465 */
|
|
|
|
ortn = SSLSetProtocolVersionEnabled(ctx, kSSLProtocolAll, false);
|
|
|
|
if(ortn) {
|
|
|
|
printSslErrStr("SSLSetProtocolVersionEnabled", ortn);
|
|
|
|
goto cleanup;
|
|
|
|
}
|
|
|
|
ortn = SSLSetProtocolVersionEnabled(ctx, kTLSProtocol1, true);
|
|
|
|
if(ortn) {
|
|
|
|
printSslErrStr("SSLSetProtocolVersionEnabled", ortn);
|
|
|
|
goto cleanup;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* Restrict to only one CipherSuite */
|
|
|
|
ortn = SSLSetEnabledCiphers(ctx, &testParams->cipherSuite, 1);
|
|
|
|
if(ortn) {
|
|
|
|
printSslErrStr("SSLSetEnabledCiphers", ortn);
|
|
|
|
goto cleanup;
|
|
|
|
}
|
|
|
|
|
|
|
|
ortn = SSLSetConnection(ctx, (SSLConnectionRef)(intptr_t)sock);
|
|
|
|
if(ortn) {
|
|
|
|
printSslErrStr("SSLSetConnection", ortn);
|
|
|
|
goto cleanup;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* These test servers have custom roots, just allow any roots for this test */
|
|
|
|
ortn = SSLSetAllowsExpiredCerts(ctx, true);
|
|
|
|
if(ortn) {
|
|
|
|
printSslErrStr("SSLSetAllowExpiredCerts", ortn);
|
|
|
|
goto cleanup;
|
|
|
|
}
|
|
|
|
ortn = SSLSetAllowsAnyRoot(ctx, true);
|
|
|
|
if(ortn) {
|
|
|
|
printSslErrStr("SSLSetAllowAnyRoot", ortn);
|
|
|
|
goto cleanup;
|
|
|
|
}
|
|
|
|
|
|
|
|
if(testParams->specCurve != SSL_Curve_None) {
|
|
|
|
ortn = SSLSetECDSACurves(ctx, &testParams->specCurve, 1);
|
|
|
|
if(ortn) {
|
|
|
|
printSslErrStr("SSLSetAllowAnyRoot", ortn);
|
|
|
|
goto cleanup;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
do {
|
|
|
|
ortn = SSLHandshake(ctx);
|
|
|
|
} while (ortn == errSSLWouldBlock);
|
|
|
|
|
|
|
|
/* convert normal "shutdown" into zero err rtn */
|
|
|
|
switch(ortn) {
|
|
|
|
case errSecSuccess:
|
|
|
|
break;
|
|
|
|
case errSSLClosedGraceful:
|
|
|
|
case errSSLClosedNoNotify:
|
|
|
|
ortn = errSecSuccess;
|
|
|
|
goto cleanup;
|
|
|
|
default:
|
|
|
|
dumpErrInfo("SSLHandshake", testParams, ortn);
|
|
|
|
goto cleanup;
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Unlike other ping tests we don't bother with a GET - just validate
|
|
|
|
* the handshake
|
|
|
|
*/
|
|
|
|
ortn = SSLGetNegotiatedCipher(ctx, &negCipher);
|
|
|
|
if(ortn) {
|
|
|
|
dumpErrInfo("SSLHandshake", testParams, ortn);
|
|
|
|
goto cleanup;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* here is really what we're testing */
|
|
|
|
if(negCipher != testParams->cipherSuite) {
|
|
|
|
printf("***Cipher mismatch for ");
|
|
|
|
dumpParams(testParams);
|
|
|
|
printf("Negotiated cipher: %s\n", sslGetCipherSuiteString(negCipher));
|
|
|
|
ortn = errSecIO;
|
|
|
|
goto cleanup;
|
|
|
|
}
|
|
|
|
if(testParams->expCurve != SSL_Curve_None) {
|
|
|
|
SSL_ECDSA_NamedCurve actNegCurve;
|
|
|
|
ortn = SSLGetNegotiatedCurve(ctx, &actNegCurve);
|
|
|
|
if(ortn) {
|
|
|
|
printSslErrStr("SSLGetNegotiatedCurve", ortn);
|
|
|
|
goto cleanup;
|
|
|
|
}
|
|
|
|
if(actNegCurve != testParams->expCurve) {
|
|
|
|
printf("***Negotiated curve error\n");
|
|
|
|
printf("Specified curve: %s\n", sslCurveString(testParams->specCurve));
|
|
|
|
printf("Expected curve: %s\n", sslCurveString(testParams->expCurve));
|
|
|
|
printf("Obtained curve: %s\n", sslCurveString(actNegCurve));
|
|
|
|
ortn = errSecIO;
|
|
|
|
goto cleanup;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
if(testParams->keychain) {
|
|
|
|
/* Verify client auth */
|
|
|
|
SSLClientCertificateState authState;
|
|
|
|
ortn = SSLGetClientCertificateState(ctx, &authState);
|
|
|
|
if(ortn) {
|
|
|
|
printSslErrStr("SSLGetClientCertificateState", ortn);
|
|
|
|
goto cleanup;
|
|
|
|
}
|
|
|
|
if(authState != kSSLClientCertSent) {
|
|
|
|
printf("***Unexpected ClientCertificateState\n");
|
|
|
|
printf(" Expected: ClientCertSent\n");
|
|
|
|
printf(" Received: %s\n", sslGetClientCertStateString(authState));
|
|
|
|
ortn = errSecIO;
|
|
|
|
goto cleanup;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
ortn = SSLClose(ctx);
|
|
|
|
|
2020-07-06 11:59:58 +00:00
|
|
|
#pragma clang diagnostic pop
|
|
|
|
|
2016-02-23 20:19:11 +00:00
|
|
|
cleanup:
|
|
|
|
if(sock) {
|
|
|
|
endpointShutdown(sock);
|
|
|
|
}
|
|
|
|
if(ctx) {
|
|
|
|
SSLDisposeContext(ctx);
|
|
|
|
}
|
|
|
|
return (int)ortn;
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
int main(int argc, char **argv)
|
|
|
|
{
|
|
|
|
int ourRtn = 0;
|
|
|
|
bool quiet = false;
|
|
|
|
int nonBlocking = false;
|
|
|
|
unsigned minDex = 0;
|
|
|
|
unsigned maxDex = NUM_TEST_PARAMS-1;
|
|
|
|
bool doPause = false;
|
|
|
|
|
|
|
|
extern char *optarg;
|
|
|
|
int arg;
|
|
|
|
while ((arg = getopt(argc, argv, "t:bpqh")) != -1) {
|
|
|
|
switch (arg) {
|
|
|
|
case 't':
|
|
|
|
minDex = maxDex = atoi(optarg);
|
|
|
|
if(minDex > (NUM_TEST_PARAMS - 1)) {
|
|
|
|
printf("***max test number is %u.\n", (unsigned)NUM_TEST_PARAMS);
|
|
|
|
exit(1);
|
|
|
|
}
|
|
|
|
break;
|
|
|
|
case 'q':
|
|
|
|
quiet = true;
|
|
|
|
break;
|
|
|
|
case 'b':
|
|
|
|
nonBlocking = true;
|
|
|
|
break;
|
|
|
|
case 'p':
|
|
|
|
doPause = true;
|
|
|
|
break;
|
|
|
|
default:
|
|
|
|
usage(argv);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
if(optind != argc) {
|
|
|
|
usage(argv);
|
|
|
|
}
|
|
|
|
|
|
|
|
#if NO_SERVER
|
|
|
|
# if DEBUG
|
|
|
|
securityd_init(NULL);
|
|
|
|
# endif
|
|
|
|
#endif
|
|
|
|
|
|
|
|
#if IGNORE_SIGPIPE
|
|
|
|
signal(SIGPIPE, sigpipe);
|
|
|
|
#endif
|
|
|
|
|
|
|
|
//testStartBanner("sslEcdsa", argc, argv);
|
|
|
|
|
|
|
|
if(doPause) {
|
|
|
|
fpurge(stdin);
|
|
|
|
printf("Pausing at top of loop; CR to continue: ");
|
|
|
|
fflush(stdout);
|
|
|
|
getchar();
|
|
|
|
}
|
|
|
|
|
|
|
|
for(unsigned dex=minDex; dex<=maxDex; dex++) {
|
|
|
|
const EcdsaTestParams *testParams = &ecdsaTestParams[dex];
|
|
|
|
if(!quiet) {
|
|
|
|
printf("[%u]: ", dex);
|
|
|
|
dumpParams(testParams);
|
|
|
|
}
|
|
|
|
ourRtn = doSslPing(testParams, quiet, nonBlocking);
|
|
|
|
if(ourRtn) {
|
|
|
|
//printf("** Test %u failed **\n", dex);
|
|
|
|
//if(testError(quiet)) {
|
|
|
|
// break;
|
|
|
|
//}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
if(doPause) {
|
|
|
|
fpurge(stdin);
|
|
|
|
printf("Pausing at end of loop; CR to continue: ");
|
|
|
|
fflush(stdout);
|
|
|
|
getchar();
|
|
|
|
}
|
|
|
|
|
|
|
|
if(!quiet) {
|
|
|
|
if(ourRtn == 0) {
|
|
|
|
printf("===== sslEcdsa test PASSED =====\n");
|
|
|
|
}
|
|
|
|
else {
|
|
|
|
printf("****sslEcdsa test FAILED\n");
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return ourRtn;
|
|
|
|
}
|