1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 /* vim: set sw=2 ts=8 et tw=80 : */
4 /* This Source Code Form is subject to the terms of the Mozilla Public
5 * License, v. 2.0. If a copy of the MPL was not distributed with this
6 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
8 #include "VerifySSLServerCertChild.h"
10 #include "CertVerifier.h"
11 #include "mozilla/ipc/Endpoint.h"
12 #include "mozilla/net/SocketProcessBackgroundChild.h"
13 #include "mozilla/psm/PVerifySSLServerCertParent.h"
14 #include "mozilla/psm/PVerifySSLServerCertChild.h"
15 #include "nsNSSIOLayer.h"
16 #include "nsSerializationHelper.h"
20 extern mozilla::LazyLogModule gPIPNSSLog
;
25 VerifySSLServerCertChild::VerifySSLServerCertChild(
26 SSLServerCertVerificationResult
* aResultTask
,
27 nsTArray
<nsTArray
<uint8_t>>&& aPeerCertChain
, uint32_t aProviderFlags
)
28 : mResultTask(aResultTask
),
29 mPeerCertChain(std::move(aPeerCertChain
)),
30 mProviderFlags(aProviderFlags
) {}
32 ipc::IPCResult
VerifySSLServerCertChild::RecvOnVerifySSLServerCertFinished(
33 nsTArray
<ByteArray
>&& aBuiltCertChain
,
34 const uint16_t& aCertTransparencyStatus
, const EVStatus
& aEVStatus
,
35 const bool& aSucceeded
, int32_t aFinalError
,
36 const nsITransportSecurityInfo::OverridableErrorCategory
&
37 aOverridableErrorCategory
,
38 const bool& aIsBuiltCertChainRootBuiltInRoot
,
39 const bool& aMadeOCSPRequests
) {
40 MOZ_LOG(gPIPNSSLog
, LogLevel::Debug
,
41 ("[%p] VerifySSLServerCertChild::RecvOnVerifySSLServerCertFinished",
44 nsTArray
<nsTArray
<uint8_t>> certBytesArray
;
45 for (auto& cert
: aBuiltCertChain
) {
46 certBytesArray
.AppendElement(std::move(cert
.data()));
49 nsresult rv
= mResultTask
->Dispatch(
50 std::move(certBytesArray
), std::move(mPeerCertChain
),
51 aCertTransparencyStatus
, aEVStatus
, aSucceeded
, aFinalError
,
52 aOverridableErrorCategory
, aIsBuiltCertChainRootBuiltInRoot
,
53 mProviderFlags
, aMadeOCSPRequests
);
55 // We can't release this off the STS thread because some parts of it are
56 // not threadsafe. Just leak mResultTask.
57 Unused
<< mResultTask
.forget();
62 SECStatus
RemoteProcessCertVerification(
63 nsTArray
<nsTArray
<uint8_t>>&& aPeerCertChain
, const nsACString
& aHostName
,
64 int32_t aPort
, const OriginAttributes
& aOriginAttributes
,
65 Maybe
<nsTArray
<uint8_t>>& aStapledOCSPResponse
,
66 Maybe
<nsTArray
<uint8_t>>& aSctsFromTLSExtension
,
67 Maybe
<DelegatedCredentialInfo
>& aDcInfo
, uint32_t aProviderFlags
,
68 uint32_t aCertVerifierFlags
, SSLServerCertVerificationResult
* aResultTask
) {
70 PR_SetError(SEC_ERROR_INVALID_ARGS
, 0);
74 nsTArray
<ByteArray
> peerCertBytes
;
75 for (auto& certBytes
: aPeerCertChain
) {
76 peerCertBytes
.AppendElement(ByteArray(certBytes
));
79 Maybe
<ByteArray
> stapledOCSPResponse
;
80 if (aStapledOCSPResponse
) {
81 stapledOCSPResponse
.emplace();
82 stapledOCSPResponse
->data().Assign(*aStapledOCSPResponse
);
85 Maybe
<ByteArray
> sctsFromTLSExtension
;
86 if (aSctsFromTLSExtension
) {
87 sctsFromTLSExtension
.emplace();
88 sctsFromTLSExtension
->data().Assign(*aSctsFromTLSExtension
);
91 Maybe
<DelegatedCredentialInfoArg
> dcInfo
;
94 dcInfo
.ref().scheme() = static_cast<uint32_t>(aDcInfo
->scheme
);
95 dcInfo
.ref().authKeyBits() = static_cast<uint32_t>(aDcInfo
->authKeyBits
);
98 ipc::Endpoint
<PVerifySSLServerCertParent
> parentEndpoint
;
99 ipc::Endpoint
<PVerifySSLServerCertChild
> childEndpoint
;
100 PVerifySSLServerCert::CreateEndpoints(&parentEndpoint
, &childEndpoint
);
102 // Create a dedicated nsCString, so that our lambda below can take an
103 // ownership stake in the underlying string buffer:
104 nsCString
hostName(aHostName
);
106 if (NS_FAILED(net::SocketProcessBackgroundChild::WithActor(
107 "SendInitVerifySSLServerCert",
108 [endpoint
= std::move(parentEndpoint
),
109 peerCertBytes
= std::move(peerCertBytes
),
110 hostName
= std::move(hostName
), port(aPort
),
111 originAttributes(aOriginAttributes
),
112 stapledOCSPResponse
= std::move(stapledOCSPResponse
),
113 sctsFromTLSExtension
= std::move(sctsFromTLSExtension
),
114 dcInfo
= std::move(dcInfo
), providerFlags(aProviderFlags
),
115 certVerifierFlags(aCertVerifierFlags
)](
116 net::SocketProcessBackgroundChild
* aActor
) mutable {
117 Unused
<< aActor
->SendInitVerifySSLServerCert(
118 std::move(endpoint
), peerCertBytes
, hostName
, port
,
119 originAttributes
, stapledOCSPResponse
, sctsFromTLSExtension
,
120 dcInfo
, providerFlags
, certVerifierFlags
);
122 PR_SetError(SEC_ERROR_LIBRARY_FAILURE
, 0);
126 RefPtr
<VerifySSLServerCertChild
> authCert
= new VerifySSLServerCertChild(
127 aResultTask
, std::move(aPeerCertChain
), aProviderFlags
);
128 if (!childEndpoint
.Bind(authCert
)) {
129 PR_SetError(SEC_ERROR_LIBRARY_FAILURE
, 0);
133 PR_SetError(PR_WOULD_BLOCK_ERROR
, 0);
134 return SECWouldBlock
;
138 } // namespace mozilla