Index: net/cert/internal/path_builder.h |
diff --git a/net/cert/internal/path_builder.h b/net/cert/internal/path_builder.h |
new file mode 100644 |
index 0000000000000000000000000000000000000000..77150bc329466d1722d6bec6a0c1b4748ea54289 |
--- /dev/null |
+++ b/net/cert/internal/path_builder.h |
@@ -0,0 +1,165 @@ |
+// Copyright 2016 The Chromium Authors. All rights reserved. |
+// Use of this source code is governed by a BSD-style license that can be |
+// found in the LICENSE file. |
+ |
+#ifndef NET_CERT_INTERNAL_PATH_BUILDER_H_ |
+#define NET_CERT_INTERNAL_PATH_BUILDER_H_ |
+ |
+#include <memory> |
+#include <string> |
+#include <unordered_map> |
+#include <vector> |
+ |
+#include "base/callback.h" |
+#include "net/base/completion_callback.h" |
+#include "net/base/net_errors.h" |
+#include "net/base/net_export.h" |
+#include "net/cert/internal/verify_certificate_chain.h" |
+#include "net/der/input.h" |
+ |
+namespace net { |
+ |
+using CertVector = std::vector<std::unique_ptr<CertThing>>; |
+ |
+class NET_EXPORT CertSource { |
+ public: |
+ using IssuerCallback = base::Callback<void(CertVector)>; |
+ |
+ class Request { |
+ public: |
+ Request() {} |
+ // Destruction of the Request cancels it. |
+ virtual ~Request() {} |
+ |
+ private: |
+ DISALLOW_COPY_AND_ASSIGN(Request); |
+ }; |
+ |
+ virtual ~CertSource() {} |
+ |
+ // Append certs to |issuers|. Any existing contents of |issuers| will not be |
+ // modified. |
+ virtual bool SyncGetIssuersOf(const CertThing& cert, CertVector* issuers) = 0; |
+ // Returns ERR_IO_PENDING if async callback will be made, or OK if no async |
+ // results are available from this source. |
+ // If |*out_req| is destroyed, the callback will not be run. |
+ virtual int AsyncGetIssuersOf(const CertThing& cert, |
+ const IssuerCallback& issuers_callback, |
+ std::unique_ptr<Request>* out_req) = 0; |
+}; |
+ |
+class NET_EXPORT StaticCertsSource : public CertSource { |
+ public: |
+ StaticCertsSource(); |
+ ~StaticCertsSource() override; |
+ |
+ // Initialize the StaticCertsSource with the given certificates. The data |
+ // referred to by |certs| must outlive the StaticCertsSource object. |
+ // XXX Should this just take a CertVector? |
+ bool Init(std::vector<der::Input> certs); |
+ |
+ // CertSource implementation: |
+ bool SyncGetIssuersOf(const CertThing& cert, CertVector* issuers) override; |
+ int AsyncGetIssuersOf(const CertThing& cert, |
+ const IssuerCallback& issuers_callback, |
+ std::unique_ptr<Request>* out_req) override; |
+ |
+ private: |
+ // The certificates that the StaticCertsSource can return, keyed on the |
+ // normalized subject value. |
+ // XXX key using StringPiece to avoid copy? |
+ std::unordered_multimap<std::string, std::unique_ptr<CertThing>> |
+ intermediates_; |
+}; |
+ |
+// XXX possible cert sources: |
+// * intermediates supplied by server (synchronous) |
+// * AIA fetch (async) |
+// * intermediates in OS cert store (async?) |
+// * certs cached from previous requests (sync?) |
+ |
+class CertPathIter; |
+ |
+class NET_EXPORT CertPathBuilder { |
+ public: |
+ using CertSources = std::vector<CertSource*>; |
+ |
+ struct ResultPath { |
+ ResultPath(); |
+ ~ResultPath(); |
+ |
+ std::vector<std::unique_ptr<CertThing>> path; |
+ int rv; |
+ }; |
+ |
+ struct Result { |
+ Result(); |
+ ~Result(); |
+ |
+ // Returns the overall result. This is the same value that was returned by |
+ // Run (if synchronous) or by the CompletionCallback (if asynchronous). |
+ int result() { |
+ if (paths.empty()) |
+ return ERR_CERT_AUTHORITY_INVALID; |
+ return paths[best_result_index]->rv; |
+ } |
+ |
+ // List of paths that were attempted and the result for each. |
+ std::vector<std::unique_ptr<ResultPath>> paths; |
+ // Index into |paths|. |
+ size_t best_result_index = 0; |
+ }; |
+ |
+ // TODO: allow caller specified filters / checkers, initial values of name |
+ // constraints, etc |
+ // |
+ // Creates a CertPathBuilder that attempts to find a path from |cert| to a |
+ // trust anchor in |trust_store|, using intermediates from |cert_sources| if |
+ // necessary, which satisfies |signature_policy| and is valid at |time|. |
+ // Details of attempted path(s) are stored in |*result|. |
+ CertPathBuilder(std::unique_ptr<CertThing> cert, |
+ const CertSources& cert_sources, |
+ const TrustStore& trust_store, |
+ const SignaturePolicy* signature_policy, |
+ const der::GeneralizedTime& time, |
+ Result* result); |
+ ~CertPathBuilder(); |
+ |
+ // Begins verification of |cert|. If the return value is ERR_IO_PENDING, |
+ // |callback| will be called asynchronously with the result. Otherwise, the |
+ // result is returned synchronously and |callback| is not called. |
+ int Run(const CompletionCallback& callback); |
+ |
+ private: |
+ enum State { |
+ STATE_NONE, |
+ STATE_GET_NEXT_PATH, |
+ STATE_GET_NEXT_PATH_COMPLETE, |
+ }; |
+ |
+ int DoLoop(int result); |
+ |
+ int DoGetNextPath(); |
+ void HandleGotNextPath(int result); |
+ int DoGetNextPathComplete(int result); |
+ |
+ void AddResultPath(const CertVector& path, bool result); |
+ |
+ CompletionCallback callback_; |
+ |
+ std::unique_ptr<CertPathIter> cert_path_iter_; |
+ const TrustStore& trust_store_; |
+ const SignaturePolicy* signature_policy_; |
+ const der::GeneralizedTime& time_; |
eroman
2016/04/26 22:10:11
Why a const reference? This seems like a problem s
mattm
2016/04/26 22:54:16
Good catch. Just a bad copy/paste.
|
+ |
+ CertVector next_path_; |
+ State next_state_; |
+ |
+ Result* out_result_; |
+ |
+ DISALLOW_COPY_AND_ASSIGN(CertPathBuilder); |
+}; |
+ |
+} // namespace net |
+ |
+#endif // NET_CERT_INTERNAL_PATH_BUILDER_H_ |