Context.h 14 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405
  1. //
  2. // Context.h
  3. //
  4. // Library: NetSSL_OpenSSL
  5. // Package: SSLCore
  6. // Module: Context
  7. //
  8. // Definition of the Context class.
  9. //
  10. // Copyright (c) 2006-2010, Applied Informatics Software Engineering GmbH.
  11. // and Contributors.
  12. //
  13. // SPDX-License-Identifier: BSL-1.0
  14. //
  15. #ifndef NetSSL_Context_INCLUDED
  16. #define NetSSL_Context_INCLUDED
  17. #include "Poco/Net/NetSSL.h"
  18. #include "Poco/Net/SocketDefs.h"
  19. #include "Poco/Crypto/X509Certificate.h"
  20. #include "Poco/Crypto/RSAKey.h"
  21. #include "Poco/RefCountedObject.h"
  22. #include "Poco/AutoPtr.h"
  23. #include <openssl/ssl.h>
  24. #include <cstdlib>
  25. namespace Poco {
  26. namespace Net {
  27. class NetSSL_API Context: public Poco::RefCountedObject
  28. /// This class encapsulates context information for
  29. /// an SSL server or client, such as the certificate
  30. /// verification mode and the location of certificates
  31. /// and private key files, as well as the list of
  32. /// supported ciphers.
  33. ///
  34. /// The Context class is also used to control
  35. /// SSL session caching on the server and client side.
  36. {
  37. public:
  38. typedef Poco::AutoPtr<Context> Ptr;
  39. enum Usage
  40. {
  41. CLIENT_USE, /// Context is used by a client.
  42. SERVER_USE, /// Context is used by a server.
  43. TLSV1_CLIENT_USE, /// Context is used by a client requiring TLSv1.
  44. TLSV1_SERVER_USE, /// Context is used by a server requiring TLSv1.
  45. TLSV1_1_CLIENT_USE, /// Context is used by a client requiring TLSv1.1 (OpenSSL 1.0.0 or newer).
  46. TLSV1_1_SERVER_USE, /// Context is used by a server requiring TLSv1.1 (OpenSSL 1.0.0 or newer).
  47. TLSV1_2_CLIENT_USE, /// Context is used by a client requiring TLSv1.2 (OpenSSL 1.0.1 or newer).
  48. TLSV1_2_SERVER_USE /// Context is used by a server requiring TLSv1.2 (OpenSSL 1.0.1 or newer).
  49. };
  50. enum VerificationMode
  51. {
  52. VERIFY_NONE = SSL_VERIFY_NONE,
  53. /// Server: The server will not send a client certificate
  54. /// request to the client, so the client will not send a certificate.
  55. ///
  56. /// Client: If not using an anonymous cipher (by default disabled),
  57. /// the server will send a certificate which will be checked, but
  58. /// the result of the check will be ignored.
  59. VERIFY_RELAXED = SSL_VERIFY_PEER,
  60. /// Server: The server sends a client certificate request to the
  61. /// client. The certificate returned (if any) is checked.
  62. /// If the verification process fails, the TLS/SSL handshake is
  63. /// immediately terminated with an alert message containing the
  64. /// reason for the verification failure.
  65. ///
  66. /// Client: The server certificate is verified, if one is provided.
  67. /// If the verification process fails, the TLS/SSL handshake is
  68. /// immediately terminated with an alert message containing the
  69. /// reason for the verification failure.
  70. VERIFY_STRICT = SSL_VERIFY_PEER | SSL_VERIFY_FAIL_IF_NO_PEER_CERT,
  71. /// Server: If the client did not return a certificate, the TLS/SSL
  72. /// handshake is immediately terminated with a handshake failure
  73. /// alert.
  74. ///
  75. /// Client: Same as VERIFY_RELAXED.
  76. VERIFY_ONCE = SSL_VERIFY_PEER | SSL_VERIFY_CLIENT_ONCE
  77. /// Server: Only request a client certificate on the initial
  78. /// TLS/SSL handshake. Do not ask for a client certificate
  79. /// again in case of a renegotiation.
  80. ///
  81. /// Client: Same as VERIFY_RELAXED.
  82. };
  83. enum Protocols
  84. {
  85. PROTO_SSLV2 = 0x01,
  86. PROTO_SSLV3 = 0x02,
  87. PROTO_TLSV1 = 0x04,
  88. PROTO_TLSV1_1 = 0x08,
  89. PROTO_TLSV1_2 = 0x10
  90. };
  91. struct NetSSL_API Params
  92. {
  93. Params();
  94. /// Initializes the struct with default values.
  95. std::string privateKeyFile;
  96. /// Path to the private key file used for encryption.
  97. /// Can be empty if no private key file is used.
  98. std::string certificateFile;
  99. /// Path to the certificate file (in PEM format).
  100. /// If the private key and the certificate are stored in the same file, this
  101. /// can be empty if privateKeyFile is given.
  102. std::string caLocation;
  103. /// Path to the file or directory containing the CA/root certificates.
  104. /// Can be empty if the OpenSSL builtin CA certificates
  105. /// are used (see loadDefaultCAs).
  106. VerificationMode verificationMode;
  107. /// Specifies whether and how peer certificates are validated.
  108. /// Defaults to VERIFY_RELAXED.
  109. int verificationDepth;
  110. /// Sets the upper limit for verification chain sizes. Verification
  111. /// will fail if a certificate chain larger than this is encountered.
  112. /// Defaults to 9.
  113. bool loadDefaultCAs;
  114. /// Specifies whether the builtin CA certificates from OpenSSL are used.
  115. /// Defaults to false.
  116. std::string cipherList;
  117. /// Specifies the supported ciphers in OpenSSL notation.
  118. /// Defaults to "ALL:!ADH:!LOW:!EXP:!MD5:@STRENGTH".
  119. std::string dhParamsFile;
  120. /// Specifies a file containing Diffie-Hellman parameters.
  121. /// If empty, the default parameters are used.
  122. std::string ecdhCurve;
  123. /// Specifies the name of the curve to use for ECDH, based
  124. /// on the curve names specified in RFC 4492.
  125. /// Defaults to "prime256v1".
  126. };
  127. Context(Usage usage, const Params& params);
  128. /// Creates a Context using the given parameters.
  129. ///
  130. /// * usage specifies whether the context is used by a client or server.
  131. /// * params specifies the context parameters.
  132. Context(
  133. Usage usage,
  134. const std::string& privateKeyFile,
  135. const std::string& certificateFile,
  136. const std::string& caLocation,
  137. VerificationMode verificationMode = VERIFY_RELAXED,
  138. int verificationDepth = 9,
  139. bool loadDefaultCAs = false,
  140. const std::string& cipherList = "ALL:!ADH:!LOW:!EXP:!MD5:@STRENGTH");
  141. /// Creates a Context.
  142. ///
  143. /// * usage specifies whether the context is used by a client or server.
  144. /// * privateKeyFile contains the path to the private key file used for encryption.
  145. /// Can be empty if no private key file is used.
  146. /// * certificateFile contains the path to the certificate file (in PEM format).
  147. /// If the private key and the certificate are stored in the same file, this
  148. /// can be empty if privateKeyFile is given.
  149. /// * caLocation contains the path to the file or directory containing the
  150. /// CA/root certificates. Can be empty if the OpenSSL builtin CA certificates
  151. /// are used (see loadDefaultCAs).
  152. /// * verificationMode specifies whether and how peer certificates are validated.
  153. /// * verificationDepth sets the upper limit for verification chain sizes. Verification
  154. /// will fail if a certificate chain larger than this is encountered.
  155. /// * loadDefaultCAs specifies whether the builtin CA certificates from OpenSSL are used.
  156. /// * cipherList specifies the supported ciphers in OpenSSL notation.
  157. ///
  158. /// Note: If the private key is protected by a passphrase, a PrivateKeyPassphraseHandler
  159. /// must have been setup with the SSLManager, or the SSLManager's PrivateKeyPassphraseRequired
  160. /// event must be handled.
  161. Context(
  162. Usage usage,
  163. const std::string& caLocation,
  164. VerificationMode verificationMode = VERIFY_RELAXED,
  165. int verificationDepth = 9,
  166. bool loadDefaultCAs = false,
  167. const std::string& cipherList = "ALL:!ADH:!LOW:!EXP:!MD5:@STRENGTH");
  168. /// Creates a Context.
  169. ///
  170. /// * usage specifies whether the context is used by a client or server.
  171. /// * caLocation contains the path to the file or directory containing the
  172. /// CA/root certificates. Can be empty if the OpenSSL builtin CA certificates
  173. /// are used (see loadDefaultCAs).
  174. /// * verificationMode specifies whether and how peer certificates are validated.
  175. /// * verificationDepth sets the upper limit for verification chain sizes. Verification
  176. /// will fail if a certificate chain larger than this is encountered.
  177. /// * loadDefaultCAs specifies whether the builtin CA certificates from OpenSSL are used.
  178. /// * cipherList specifies the supported ciphers in OpenSSL notation.
  179. ///
  180. /// Note that a private key and/or certificate must be specified with
  181. /// usePrivateKey()/useCertificate() before the Context can be used.
  182. ~Context();
  183. /// Destroys the Context.
  184. void useCertificate(const Poco::Crypto::X509Certificate& certificate);
  185. /// Sets the certificate to be used by the Context.
  186. ///
  187. /// To set-up a complete certificate chain, it might be
  188. /// necessary to call addChainCertificate() to specify
  189. /// additional certificates.
  190. ///
  191. /// Note that useCertificate() must always be called before
  192. /// usePrivateKey().
  193. void addChainCertificate(const Poco::Crypto::X509Certificate& certificate);
  194. /// Adds a certificate for certificate chain validation.
  195. void addCertificateAuthority(const Poco::Crypto::X509Certificate& certificate);
  196. /// Add one trusted certification authority to be used by the Context.
  197. void usePrivateKey(const Poco::Crypto::RSAKey& key);
  198. /// Sets the private key to be used by the Context.
  199. ///
  200. /// Note that useCertificate() must always be called before
  201. /// usePrivateKey().
  202. ///
  203. /// Note: If the private key is protected by a passphrase, a PrivateKeyPassphraseHandler
  204. /// must have been setup with the SSLManager, or the SSLManager's PrivateKeyPassphraseRequired
  205. /// event must be handled.
  206. SSL_CTX* sslContext() const;
  207. /// Returns the underlying OpenSSL SSL Context object.
  208. Usage usage() const;
  209. /// Returns whether the context is for use by a client or by a server
  210. /// and whether TLSv1 is required.
  211. bool isForServerUse() const;
  212. /// Returns true iff the context is for use by a server.
  213. Context::VerificationMode verificationMode() const;
  214. /// Returns the verification mode.
  215. void enableSessionCache(bool flag = true);
  216. /// Enable or disable SSL/TLS session caching.
  217. /// For session caching to work, it must be enabled
  218. /// on the server, as well as on the client side.
  219. ///
  220. /// The default is disabled session caching.
  221. ///
  222. /// To enable session caching on the server side, use the
  223. /// two-argument version of this method to specify
  224. /// a session ID context.
  225. void enableSessionCache(bool flag, const std::string& sessionIdContext);
  226. /// Enables or disables SSL/TLS session caching on the server.
  227. /// For session caching to work, it must be enabled
  228. /// on the server, as well as on the client side.
  229. ///
  230. /// SessionIdContext contains the application's unique
  231. /// session ID context, which becomes part of each
  232. /// session identifier generated by the server within this
  233. /// context. SessionIdContext can be an arbitrary sequence
  234. /// of bytes with a maximum length of SSL_MAX_SSL_SESSION_ID_LENGTH.
  235. ///
  236. /// A non-empty sessionIdContext should be specified even if
  237. /// session caching is disabled to avoid problems with clients
  238. /// requesting to reuse a session (e.g. Firefox 3.6).
  239. ///
  240. /// This method may only be called on SERVER_USE Context objects.
  241. bool sessionCacheEnabled() const;
  242. /// Returns true iff the session cache is enabled.
  243. void setSessionCacheSize(std::size_t size);
  244. /// Sets the maximum size of the server session cache, in number of
  245. /// sessions. The default size (according to OpenSSL documentation)
  246. /// is 1024*20, which may be too large for many applications,
  247. /// especially on embedded platforms with limited memory.
  248. ///
  249. /// Specifying a size of 0 will set an unlimited cache size.
  250. ///
  251. /// This method may only be called on SERVER_USE Context objects.
  252. std::size_t getSessionCacheSize() const;
  253. /// Returns the current maximum size of the server session cache.
  254. ///
  255. /// This method may only be called on SERVER_USE Context objects.
  256. void setSessionTimeout(long seconds);
  257. /// Sets the timeout (in seconds) of cached sessions on the server.
  258. /// A cached session will be removed from the cache if it has
  259. /// not been used for the given number of seconds.
  260. ///
  261. /// This method may only be called on SERVER_USE Context objects.
  262. long getSessionTimeout() const;
  263. /// Returns the timeout (in seconds) of cached sessions on the server.
  264. ///
  265. /// This method may only be called on SERVER_USE Context objects.
  266. void flushSessionCache();
  267. /// Flushes the SSL session cache on the server.
  268. ///
  269. /// This method may only be called on SERVER_USE Context objects.
  270. void enableExtendedCertificateVerification(bool flag = true);
  271. /// Enable or disable the automatic post-connection
  272. /// extended certificate verification.
  273. ///
  274. /// See X509Certificate::verify() for more information.
  275. bool extendedCertificateVerificationEnabled() const;
  276. /// Returns true iff automatic extended certificate
  277. /// verification is enabled.
  278. void disableStatelessSessionResumption();
  279. /// Newer versions of OpenSSL support RFC 4507 tickets for stateless
  280. /// session resumption.
  281. ///
  282. /// The feature can be disabled by calling this method.
  283. void disableProtocols(int protocols);
  284. /// Disables the given protocols.
  285. ///
  286. /// The protocols to be disabled are specified by OR-ing
  287. /// values from the Protocols enumeration, e.g.:
  288. ///
  289. /// context.disableProtocols(PROTO_SSLV2 | PROTO_SSLV3);
  290. void preferServerCiphers();
  291. /// When choosing a cipher, use the server's preferences instead of the client
  292. /// preferences. When not called, the SSL server will always follow the clients
  293. /// preferences. When called, the SSL/TLS server will choose following its own
  294. /// preferences.
  295. private:
  296. void init(const Params& params);
  297. /// Initializes the Context with the given parameters.
  298. void initDH(const std::string& dhFile);
  299. /// Initializes the Context with Diffie-Hellman parameters.
  300. void initECDH(const std::string& curve);
  301. /// Initializes the Context with Elliptic-Curve Diffie-Hellman key
  302. /// exchange curve parameters.
  303. void createSSLContext();
  304. /// Create a SSL_CTX object according to Context configuration.
  305. Usage _usage;
  306. VerificationMode _mode;
  307. SSL_CTX* _pSSLContext;
  308. bool _extendedCertificateVerification;
  309. };
  310. //
  311. // inlines
  312. //
  313. inline Context::Usage Context::usage() const
  314. {
  315. return _usage;
  316. }
  317. inline bool Context::isForServerUse() const
  318. {
  319. return _usage == SERVER_USE
  320. || _usage == TLSV1_SERVER_USE
  321. || _usage == TLSV1_1_SERVER_USE
  322. || _usage == TLSV1_2_SERVER_USE;
  323. }
  324. inline Context::VerificationMode Context::verificationMode() const
  325. {
  326. return _mode;
  327. }
  328. inline SSL_CTX* Context::sslContext() const
  329. {
  330. return _pSSLContext;
  331. }
  332. inline bool Context::extendedCertificateVerificationEnabled() const
  333. {
  334. return _extendedCertificateVerification;
  335. }
  336. } } // namespace Poco::Net
  337. #endif // NetSSL_Context_INCLUDED