security/manager/ssl/tests/unit/tlsserver/cmd/OCSPStaplingServer.cpp

Thu, 22 Jan 2015 13:21:57 +0100

author
Michael Schloh von Bennewitz <michael@schloh.com>
date
Thu, 22 Jan 2015 13:21:57 +0100
branch
TOR_BUG_9701
changeset 15
b8a032363ba2
permissions
-rw-r--r--

Incorporate requested changes from Mozilla in review:
https://bugzilla.mozilla.org/show_bug.cgi?id=1123480#c6

     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/. */
     5 // This is a standalone server that delivers various stapled OCSP responses.
     6 // The client is expected to connect, initiate an SSL handshake (with SNI
     7 // to indicate which "server" to connect to), and verify the OCSP response.
     8 // If all is good, the client then sends one encrypted byte and receives that
     9 // same byte back.
    10 // This server also has the ability to "call back" another process waiting on
    11 // it. That is, when the server is all set up and ready to receive connections,
    12 // it will connect to a specified port and issue a simple HTTP request.
    14 #include <stdio.h>
    16 #include "OCSPCommon.h"
    17 #include "TLSServer.h"
    19 using namespace mozilla;
    20 using namespace mozilla::test;
    22 const OCSPHost sOCSPHosts[] =
    23 {
    24   { "ocsp-stapling-good.example.com", ORTGood, nullptr },
    25   { "ocsp-stapling-revoked.example.com", ORTRevoked, nullptr },
    26   { "ocsp-stapling-revoked-old.example.com", ORTRevokedOld, nullptr },
    27   { "ocsp-stapling-unknown.example.com", ORTUnknown, nullptr },
    28   { "ocsp-stapling-unknown-old.example.com", ORTUnknownOld, nullptr },
    29   { "ocsp-stapling-good-other.example.com", ORTGoodOtherCert, "ocspOtherEndEntity" },
    30   { "ocsp-stapling-good-other-ca.example.com", ORTGoodOtherCA, "otherCA" },
    31   { "ocsp-stapling-expired.example.com", ORTExpired, nullptr },
    32   { "ocsp-stapling-expired-fresh-ca.example.com", ORTExpiredFreshCA, nullptr },
    33   { "ocsp-stapling-none.example.com", ORTNone, nullptr },
    34   { "ocsp-stapling-empty.example.com", ORTEmpty, nullptr },
    35   { "ocsp-stapling-malformed.example.com", ORTMalformed, nullptr },
    36   { "ocsp-stapling-srverr.example.com", ORTSrverr, nullptr },
    37   { "ocsp-stapling-trylater.example.com", ORTTryLater, nullptr },
    38   { "ocsp-stapling-needssig.example.com", ORTNeedsSig, nullptr },
    39   { "ocsp-stapling-unauthorized.example.com", ORTUnauthorized, nullptr },
    40   { "ocsp-stapling-with-intermediate.example.com", ORTGood, "ocspEEWithIntermediate" },
    41   { "ocsp-stapling-bad-signature.example.com", ORTBadSignature, nullptr },
    42   { "ocsp-stapling-skip-responseBytes.example.com", ORTSkipResponseBytes, nullptr },
    43   { "ocsp-stapling-critical-extension.example.com", ORTCriticalExtension, nullptr },
    44   { "ocsp-stapling-noncritical-extension.example.com", ORTNoncriticalExtension, nullptr },
    45   { "ocsp-stapling-empty-extensions.example.com", ORTEmptyExtensions, nullptr },
    46   { "ocsp-stapling-delegated-included.example.com", ORTDelegatedIncluded, "delegatedSigner" },
    47   { "ocsp-stapling-delegated-included-last.example.com", ORTDelegatedIncludedLast, "delegatedSigner" },
    48   { "ocsp-stapling-delegated-missing.example.com", ORTDelegatedMissing, "delegatedSigner" },
    49   { "ocsp-stapling-delegated-missing-multiple.example.com", ORTDelegatedMissingMultiple, "delegatedSigner" },
    50   { "ocsp-stapling-delegated-no-extKeyUsage.example.com", ORTDelegatedIncluded, "invalidDelegatedSignerNoExtKeyUsage" },
    51   { "ocsp-stapling-delegated-from-intermediate.example.com", ORTDelegatedIncluded, "invalidDelegatedSignerFromIntermediate" },
    52   { "ocsp-stapling-delegated-keyUsage-crlSigning.example.com", ORTDelegatedIncluded, "invalidDelegatedSignerKeyUsageCrlSigning" },
    53   { "ocsp-stapling-delegated-wrong-extKeyUsage.example.com", ORTDelegatedIncluded, "invalidDelegatedSignerWrongExtKeyUsage" },
    54   { "ocsp-stapling-ancient-valid.example.com", ORTAncientAlmostExpired, nullptr},
    55   { nullptr, ORTNull, nullptr }
    56 };
    58 int32_t
    59 DoSNISocketConfig(PRFileDesc *aFd, const SECItem *aSrvNameArr,
    60                   uint32_t aSrvNameArrSize, void *aArg)
    61 {
    62   const OCSPHost *host = GetHostForSNI(aSrvNameArr, aSrvNameArrSize,
    63                                        sOCSPHosts);
    64   if (!host) {
    65     return SSL_SNI_SEND_ALERT;
    66   }
    68   if (gDebugLevel >= DEBUG_VERBOSE) {
    69     fprintf(stderr, "found pre-defined host '%s'\n", host->mHostName);
    70   }
    72   const char *certNickname;
    73   if (strcmp(host->mHostName,
    74              "ocsp-stapling-with-intermediate.example.com") == 0) {
    75     certNickname = host->mAdditionalCertName;
    76   } else {
    77     certNickname = DEFAULT_CERT_NICKNAME;
    78   }
    80   ScopedCERTCertificate cert;
    81   SSLKEAType certKEA;
    82   if (SECSuccess != ConfigSecureServerWithNamedCert(aFd, certNickname,
    83                                                     &cert, &certKEA)) {
    84     return SSL_SNI_SEND_ALERT;
    85   }
    87   // If the OCSP response type is "none", don't staple a response.
    88   if (host->mORT == ORTNone) {
    89     return 0;
    90   }
    92   PLArenaPool *arena = PORT_NewArena(1024);
    93   if (!arena) {
    94     PrintPRError("PORT_NewArena failed");
    95     return SSL_SNI_SEND_ALERT;
    96   }
    98   // response is contained by the arena - freeing the arena will free it
    99   SECItemArray *response = GetOCSPResponseForType(host->mORT, cert, arena,
   100                                                   host->mAdditionalCertName);
   101   if (!response) {
   102     PORT_FreeArena(arena, PR_FALSE);
   103     return SSL_SNI_SEND_ALERT;
   104   }
   106   // SSL_SetStapledOCSPResponses makes a deep copy of response
   107   SECStatus st = SSL_SetStapledOCSPResponses(aFd, response, certKEA);
   108   PORT_FreeArena(arena, PR_FALSE);
   109   if (st != SECSuccess) {
   110     PrintPRError("SSL_SetStapledOCSPResponses failed");
   111     return SSL_SNI_SEND_ALERT;
   112   }
   114   return 0;
   115 }
   117 int
   118 main(int argc, char *argv[])
   119 {
   120   if (argc != 2) {
   121     fprintf(stderr, "usage: %s <NSS DB directory>\n", argv[0]);
   122     return 1;
   123   }
   125   return StartServer(argv[1], DoSNISocketConfig, nullptr);
   126 }

mercurial