Seastar
High performance C++ framework for concurrent servers
tls.hh
1 /*
2  * This file is open source software, licensed to you under the terms
3  * of the Apache License, Version 2.0 (the "License"). See the NOTICE file
4  * distributed with this work for additional information regarding copyright
5  * ownership. You may not use this file except in compliance with the License.
6  *
7  * You may obtain a copy of the License at
8  *
9  * http://www.apache.org/licenses/LICENSE-2.0
10  *
11  * Unless required by applicable law or agreed to in writing,
12  * software distributed under the License is distributed on an
13  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
14  * KIND, either express or implied. See the License for the
15  * specific language governing permissions and limitations
16  * under the License.
17  */
18 /*
19  * Copyright 2015 Cloudius Systems
20  */
21 #pragma once
22 
23 #ifndef SEASTAR_MODULE
24 #include <functional>
25 #include <unordered_set>
26 #include <map>
27 #include <boost/any.hpp>
28 #endif
29 
30 #include <seastar/core/future.hh>
31 #include <seastar/core/internal/api-level.hh>
32 #include <seastar/core/sstring.hh>
33 #include <seastar/core/shared_ptr.hh>
34 #include <seastar/net/socket_defs.hh>
35 #include <seastar/net/inet_address.hh>
36 #include <seastar/util/std-compat.hh>
37 #include <seastar/util/modules.hh>
38 #include <seastar/net/api.hh>
39 
40 namespace seastar {
41 
42 class socket;
43 
44 class server_socket;
45 class connected_socket;
46 class socket_address;
47 
58 SEASTAR_MODULE_EXPORT
59 namespace tls {
60 
61  enum class x509_crt_format {
62  DER,
63  PEM,
64  };
65 
66  typedef std::basic_string_view<char> blob;
67 
68  class session;
69  class server_session;
70  class server_credentials;
71  class certificate_credentials;
72  class credentials_builder;
73 
78  class dh_params {
79  public:
80  // Key strength
81  enum class level {
82  LEGACY = 2,
83  MEDIUM = 3,
84  HIGH = 4,
85  ULTRA = 5
86  };
87  dh_params(level = level::LEGACY);
88  // loads a key from data
89  dh_params(const blob&, x509_crt_format);
90  ~dh_params();
91 
92  dh_params(dh_params&&) noexcept;
93  dh_params& operator=(dh_params&&) noexcept;
94 
95  dh_params(const dh_params&) = delete;
96  dh_params& operator=(const dh_params&) = delete;
97 
99  static future<dh_params> from_file(const sstring&, x509_crt_format);
100  private:
101  class impl;
102  friend class server_credentials;
103  friend class certificate_credentials;
104  std::unique_ptr<impl> _impl;
105  };
106 
107  class x509_cert {
108  x509_cert(const blob&, x509_crt_format);
109 
110  static future<x509_cert> from_file(const sstring&, x509_crt_format);
111  private:
112  class impl;
114  shared_ptr<impl> _impl;
115  };
116 
118  protected:
119  abstract_credentials() = default;
120  abstract_credentials(const abstract_credentials&) = default;
121  abstract_credentials& operator=(abstract_credentials&) = default;
122  abstract_credentials& operator=(abstract_credentials&&) = default;
123  virtual ~abstract_credentials() {};
124  public:
125  virtual void set_x509_trust(const blob&, x509_crt_format) = 0;
126  virtual void set_x509_crl(const blob&, x509_crt_format) = 0;
127  virtual void set_x509_key(const blob& cert, const blob& key, x509_crt_format) = 0;
128 
129  virtual void set_simple_pkcs12(const blob&, x509_crt_format, const sstring& password) = 0;
130 
131  virtual future<> set_x509_trust_file(const sstring& cafile, x509_crt_format);
132  virtual future<> set_x509_crl_file(const sstring& crlfile, x509_crt_format);
133  virtual future<> set_x509_key_file(const sstring& cf, const sstring& kf, x509_crt_format);
134 
135  virtual future<> set_simple_pkcs12_file(const sstring& pkcs12file, x509_crt_format, const sstring& password);
136  };
137 
138  template<typename Base>
140 
146  enum class session_type {
147  CLIENT, SERVER,
148  };
149 
157  using dn_callback = noncopyable_function<void(session_type type, sstring subject, sstring issuer)>;
158 
169  public:
172 
174  certificate_credentials& operator=(certificate_credentials&&) noexcept;
175 
177  certificate_credentials& operator=(const certificate_credentials&) = delete;
178 
179  void set_x509_trust(const blob&, x509_crt_format) override;
180  void set_x509_crl(const blob&, x509_crt_format) override;
181  void set_x509_key(const blob& cert, const blob& key, x509_crt_format) override;
182  void set_simple_pkcs12(const blob&, x509_crt_format, const sstring& password) override;
183 
189 
190  // TODO add methods for certificate verification
191 
198  void set_priority_string(const sstring&);
199 
222 
223  private:
224  class impl;
225  friend class session;
226  friend class server_session;
227  friend class server_credentials;
228  friend class credentials_builder;
229  template<typename Base>
230  friend class reloadable_credentials;
231  shared_ptr<impl> _impl;
232  };
233 
235  class verification_error : public std::runtime_error {
236  public:
237  using runtime_error::runtime_error;
238  };
239 
240  enum class client_auth {
241  NONE, REQUEST, REQUIRE
242  };
243 
249  public:
253 
255  server_credentials& operator=(server_credentials&&) noexcept;
256 
257  server_credentials(const server_credentials&) = delete;
258  server_credentials& operator=(const server_credentials&) = delete;
259 
260  void set_client_auth(client_auth);
261  };
262 
263  class reloadable_credentials_base;
264 
265  using reload_callback = std::function<void(const std::unordered_set<sstring>&, std::exception_ptr)>;
266 
278  public:
279  void set_dh_level(dh_params::level = dh_params::level::LEGACY);
280 
281  void set_x509_trust(const blob&, x509_crt_format) override ;
282  void set_x509_crl(const blob&, x509_crt_format) override;
283  void set_x509_key(const blob& cert, const blob& key, x509_crt_format) override;
284  void set_simple_pkcs12(const blob&, x509_crt_format, const sstring& password) override;
285 
286  future<> set_x509_trust_file(const sstring& cafile, x509_crt_format) override;
287  future<> set_x509_crl_file(const sstring& crlfile, x509_crt_format) override;
288  future<> set_x509_key_file(const sstring& cf, const sstring& kf, x509_crt_format) override;
289  future<> set_simple_pkcs12_file(const sstring& pkcs12file, x509_crt_format, const sstring& password) override;
290 
291  future<> set_system_trust();
292  void set_client_auth(client_auth);
293  void set_priority_string(const sstring&);
294 
295  void apply_to(certificate_credentials&) const;
296 
297  shared_ptr<certificate_credentials> build_certificate_credentials() const;
298  shared_ptr<server_credentials> build_server_credentials() const;
299 
300  // same as above, but any files used for certs/keys etc will be watched
301  // for modification and reloaded if changed
302  future<shared_ptr<certificate_credentials>> build_reloadable_certificate_credentials(reload_callback = {}, std::optional<std::chrono::milliseconds> tolerance = {}) const;
303  future<shared_ptr<server_credentials>> build_reloadable_server_credentials(reload_callback = {}, std::optional<std::chrono::milliseconds> tolerance = {}) const;
304  private:
305  friend class reloadable_credentials_base;
306 
307  std::multimap<sstring, boost::any> _blobs;
308  client_auth _client_auth = client_auth::NONE;
309  sstring _priority;
310  };
311 
313  struct tls_options {
317  sstring server_name = {};
318  };
319 
331  [[deprecated("Use overload with tls_options parameter")]]
333  [[deprecated("Use overload with tls_options parameter")]]
336 
349 
361  [[deprecated("Use overload with tls_options parameter")]]
364 
376 
385  [[deprecated("Use overload with tls_options parameter")]]
389 
398 
407  // Wraps an existing server socket in SSL
410 
422 
427  dnsname = 1, // string value representing a 'DNS' entry
428  rfc822name, // string value representing an 'email' entry
429  uri, // string value representing an 'uri' entry
430  ipaddress, // inet_address value representing an 'IP' entry
431  othername, // string value
432  dn, // string value
433  };
434 
435  // Subject alt name entry
437  using value_type = std::variant<
438  sstring,
440  >;
442  value_type value;
443  };
444 
453  future<std::vector<subject_alt_name>> get_alt_name_information(connected_socket& socket, std::unordered_set<subject_alt_name_type> types = {});
454 
455  std::ostream& operator<<(std::ostream&, const subject_alt_name::value_type&);
456  std::ostream& operator<<(std::ostream&, const subject_alt_name&);
457 
472  std::string_view format_as(subject_alt_name_type);
473  std::ostream& operator<<(std::ostream&, subject_alt_name_type);
474 
480  const std::error_category& error_category();
481 
486  extern const int ERROR_UNKNOWN_COMPRESSION_ALGORITHM;
487  extern const int ERROR_UNKNOWN_CIPHER_TYPE;
488  extern const int ERROR_INVALID_SESSION;
489  extern const int ERROR_UNEXPECTED_HANDSHAKE_PACKET;
490  extern const int ERROR_UNKNOWN_CIPHER_SUITE;
491  extern const int ERROR_UNKNOWN_ALGORITHM;
492  extern const int ERROR_UNSUPPORTED_SIGNATURE_ALGORITHM;
493  extern const int ERROR_SAFE_RENEGOTIATION_FAILED;
494  extern const int ERROR_UNSAFE_RENEGOTIATION_DENIED;
495  extern const int ERROR_UNKNOWN_SRP_USERNAME;
496  extern const int ERROR_PREMATURE_TERMINATION;
497 }
498 }
Definition: api.hh:182
A representation of a possibly not-yet-computed value.
Definition: future.hh:1238
Definition: inet_address.hh:49
A listening socket, waiting to accept incoming network connections.
Definition: api.hh:325
Definition: socket_defs.hh:47
Definition: api.hh:282
void set_priority_string(const sstring &)
void set_dn_verification_callback(dn_callback)
Definition: tls.hh:277
Definition: tls.hh:78
static future< dh_params > from_file(const sstring &, x509_crt_format)
Definition: tls.hh:248
Definition: tls.hh:235
Definition: tls.hh:107
holds the implementation parts of the metrics layer, do not use directly.
sstring server_name
server name to be used for the SNI TLS extension
Definition: tls.hh:317
session_type
Definition: tls.hh:146
std::string_view format_as(subject_alt_name_type)
const std::error_category & error_category()
future< connected_socket > connect(shared_ptr< certificate_credentials >, socket_address, sstring name)
subject_alt_name_type
Definition: tls.hh:426
future< std::optional< session_dn > > get_dn_information(connected_socket &socket)
bool wait_for_eof_on_shutdown
whether to wait for EOF from server on session termination
Definition: tls.hh:315
::seastar::socket socket(shared_ptr< certificate_credentials >, sstring name)
future< connected_socket > wrap_client(shared_ptr< certificate_credentials >, connected_socket &&, sstring name)
future< std::vector< subject_alt_name > > get_alt_name_information(connected_socket &socket, std::unordered_set< subject_alt_name_type > types={})
server_socket listen(shared_ptr< server_credentials >, socket_address sa, listen_options opts=listen_options())
const int ERROR_UNKNOWN_COMPRESSION_ALGORITHM
Definition: tls.hh:436
TLS configuration options.
Definition: tls.hh:313
Seastar API namespace.
Definition: abort_on_ebadf.hh:26
Definition: noncopyable_function.hh:37
Definition: api.hh:391