• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  *  Copyright 2004 The WebRTC Project Authors. All rights reserved.
3  *
4  *  Use of this source code is governed by a BSD-style license
5  *  that can be found in the LICENSE file in the root of the source
6  *  tree. An additional intellectual property rights grant can be found
7  *  in the file PATENTS.  All contributing project authors may
8  *  be found in the AUTHORS file in the root of the source tree.
9  */
10 
11 // Handling of certificates and keypairs for SSLStreamAdapter's peer mode.
12 
13 #ifndef RTC_BASE_SSL_IDENTITY_H_
14 #define RTC_BASE_SSL_IDENTITY_H_
15 
16 #include <stdint.h>
17 
18 #include <ctime>
19 #include <memory>
20 #include <string>
21 
22 #include "absl/strings/string_view.h"
23 #include "rtc_base/system/rtc_export.h"
24 
25 namespace rtc {
26 
27 class SSLCertChain;
28 class SSLCertificate;
29 
30 // KT_LAST is intended for vector declarations and loops over all key types;
31 // it does not represent any key type in itself.
32 // KT_DEFAULT is used as the default KeyType for KeyParams.
33 enum KeyType { KT_RSA, KT_ECDSA, KT_LAST, KT_DEFAULT = KT_ECDSA };
34 
35 static const int kRsaDefaultModSize = 1024;
36 static const int kRsaDefaultExponent = 0x10001;  // = 2^16+1 = 65537
37 static const int kRsaMinModSize = 1024;
38 static const int kRsaMaxModSize = 8192;
39 
40 // Certificate default validity lifetime.
41 static const int kDefaultCertificateLifetimeInSeconds =
42     60 * 60 * 24 * 30;  // 30 days
43 // Certificate validity window.
44 // This is to compensate for slightly incorrect system clocks.
45 static const int kCertificateWindowInSeconds = -60 * 60 * 24;
46 
47 struct RSAParams {
48   unsigned int mod_size;
49   unsigned int pub_exp;
50 };
51 
52 enum ECCurve { EC_NIST_P256, /* EC_FANCY, */ EC_LAST };
53 
54 class RTC_EXPORT KeyParams {
55  public:
56   // Generate a KeyParams object from a simple KeyType, using default params.
57   explicit KeyParams(KeyType key_type = KT_DEFAULT);
58 
59   // Generate a a KeyParams for RSA with explicit parameters.
60   static KeyParams RSA(int mod_size = kRsaDefaultModSize,
61                        int pub_exp = kRsaDefaultExponent);
62 
63   // Generate a a KeyParams for ECDSA specifying the curve.
64   static KeyParams ECDSA(ECCurve curve = EC_NIST_P256);
65 
66   // Check validity of a KeyParams object. Since the factory functions have
67   // no way of returning errors, this function can be called after creation
68   // to make sure the parameters are OK.
69   bool IsValid() const;
70 
71   RSAParams rsa_params() const;
72 
73   ECCurve ec_curve() const;
74 
type()75   KeyType type() const { return type_; }
76 
77  private:
78   KeyType type_;
79   union {
80     RSAParams rsa;
81     ECCurve curve;
82   } params_;
83 };
84 
85 // TODO(hbos): Remove once rtc::KeyType (to be modified) and
86 // blink::WebRTCKeyType (to be landed) match. By using this function in Chromium
87 // appropriately we can change KeyType enum -> class without breaking Chromium.
88 KeyType IntKeyTypeFamilyToKeyType(int key_type_family);
89 
90 // Parameters for generating a certificate. If `common_name` is non-empty, it
91 // will be used for the certificate's subject and issuer name, otherwise a
92 // random string will be used.
93 struct SSLIdentityParams {
94   std::string common_name;
95   time_t not_before;  // Absolute time since epoch in seconds.
96   time_t not_after;   // Absolute time since epoch in seconds.
97   KeyParams key_params;
98 };
99 
100 // Our identity in an SSL negotiation: a keypair and certificate (both
101 // with the same public key).
102 // This too is pretty much immutable once created.
103 class RTC_EXPORT SSLIdentity {
104  public:
105   // Generates an identity (keypair and self-signed certificate). If
106   // `common_name` is non-empty, it will be used for the certificate's subject
107   // and issuer name, otherwise a random string will be used. The key type and
108   // parameters are defined in `key_param`. The certificate's lifetime in
109   // seconds from the current time is defined in `certificate_lifetime`; it
110   // should be a non-negative number.
111   // Returns null on failure.
112   // Caller is responsible for freeing the returned object.
113   static std::unique_ptr<SSLIdentity> Create(absl::string_view common_name,
114                                              const KeyParams& key_param,
115                                              time_t certificate_lifetime);
116   static std::unique_ptr<SSLIdentity> Create(absl::string_view common_name,
117                                              const KeyParams& key_param);
118   static std::unique_ptr<SSLIdentity> Create(absl::string_view common_name,
119                                              KeyType key_type);
120 
121   // Allows fine-grained control over expiration time.
122   static std::unique_ptr<SSLIdentity> CreateForTest(
123       const SSLIdentityParams& params);
124 
125   // Construct an identity from a private key and a certificate.
126   static std::unique_ptr<SSLIdentity> CreateFromPEMStrings(
127       absl::string_view private_key,
128       absl::string_view certificate);
129 
130   // Construct an identity from a private key and a certificate chain.
131   static std::unique_ptr<SSLIdentity> CreateFromPEMChainStrings(
132       absl::string_view private_key,
133       absl::string_view certificate_chain);
134 
~SSLIdentity()135   virtual ~SSLIdentity() {}
136 
137   // Returns a new SSLIdentity object instance wrapping the same
138   // identity information.
Clone()139   std::unique_ptr<SSLIdentity> Clone() const { return CloneInternal(); }
140 
141   // Returns a temporary reference to the end-entity (leaf) certificate.
142   virtual const SSLCertificate& certificate() const = 0;
143   // Returns a temporary reference to the entire certificate chain.
144   virtual const SSLCertChain& cert_chain() const = 0;
145   virtual std::string PrivateKeyToPEMString() const = 0;
146   virtual std::string PublicKeyToPEMString() const = 0;
147 
148   // Helpers for parsing converting between PEM and DER format.
149   static bool PemToDer(absl::string_view pem_type,
150                        absl::string_view pem_string,
151                        std::string* der);
152   static std::string DerToPem(absl::string_view pem_type,
153                               const unsigned char* data,
154                               size_t length);
155 
156  protected:
157   virtual std::unique_ptr<SSLIdentity> CloneInternal() const = 0;
158 };
159 
160 bool operator==(const SSLIdentity& a, const SSLIdentity& b);
161 bool operator!=(const SSLIdentity& a, const SSLIdentity& b);
162 
163 // Convert from ASN1 time as restricted by RFC 5280 to seconds from 1970-01-01
164 // 00.00 ("epoch").  If the ASN1 time cannot be read, return -1.  The data at
165 // `s` is not 0-terminated; its char count is defined by `length`.
166 int64_t ASN1TimeToSec(const unsigned char* s, size_t length, bool long_format);
167 
168 extern const char kPemTypeCertificate[];
169 extern const char kPemTypeRsaPrivateKey[];
170 extern const char kPemTypeEcPrivateKey[];
171 
172 }  // namespace rtc
173 
174 #endif  // RTC_BASE_SSL_IDENTITY_H_
175