Line data Source code
1 : // Event Dispatcher
2 : // Copyright (c) 2012-2019 Made to Order Software Corp. All Rights Reserved
3 : //
4 : // This program is free software; you can redistribute it and/or modify
5 : // it under the terms of the GNU General Public License as published by
6 : // the Free Software Foundation; either version 2 of the License, or
7 : // (at your option) any later version.
8 : //
9 : // This program is distributed in the hope that it will be useful,
10 : // but WITHOUT ANY WARRANTY; without even the implied warranty of
11 : // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 : // GNU General Public License for more details.
13 : //
14 : // You should have received a copy of the GNU General Public License
15 : // along with this program; if not, write to the Free Software
16 : // Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
17 :
18 : // make sure we use OpenSSL with multi-thread support
19 : // (TODO: move to .cpp once we have the impl!)
20 : #define OPENSSL_THREAD_DEFINES
21 :
22 : // self
23 : //
24 : #include "eventdispatcher/tcp_bio_options.h"
25 :
26 : #include "eventdispatcher/exception.h"
27 :
28 :
29 : // OpenSSL lib
30 : //
31 : #include <openssl/bio.h>
32 : #include <openssl/err.h>
33 :
34 :
35 : // C++
36 : //
37 : #include <memory>
38 :
39 :
40 : // last include
41 : //
42 : #include "snapdev/poison.h"
43 :
44 :
45 :
46 :
47 : #ifndef OPENSSL_THREADS
48 : #error "OPENSSL_THREADS is not defined. Snap! requires support for multiple threads in OpenSSL."
49 : #endif
50 :
51 : namespace ed
52 : {
53 :
54 :
55 :
56 : /** \brief Initialize the options object to the defaults.
57 : *
58 : * This constructor sets up the default options in this structure.
59 : */
60 0 : tcp_bio_options::tcp_bio_options()
61 : {
62 0 : }
63 :
64 :
65 : /** \brief Specify the depth of SSL certificate verification.
66 : *
67 : * When verifying a certificate, you may end up with a very long chain.
68 : * In most cases, a very long chain is not sensible and probably means
69 : * something fishy is going on. For this reason, this is verified here.
70 : *
71 : * The default is 4. Some people like to use 5 or 6. The full range
72 : * allows for way more, although really it should be very much
73 : * limited.
74 : *
75 : * \exception
76 : * This function accepts a number between 1 and 100. Any number outside
77 : * of that range and this exception is raised.
78 : *
79 : * \param[in] depth The depth for the verification of certificates.
80 : */
81 0 : void tcp_bio_options::set_verification_depth(size_t depth)
82 : {
83 0 : if(depth == 0
84 0 : || depth > MAX_VERIFICATION_DEPTH)
85 : {
86 0 : throw event_dispatcher_invalid_parameter("the depth parameter must be defined between 1 and 100 inclusive");
87 : }
88 :
89 0 : f_verification_depth = depth;
90 0 : }
91 :
92 :
93 : /** \brief Retrieve the verification maximum depth allowed.
94 : *
95 : * This function returns the verification depth parameter. This number
96 : * will always be between 1 and 100 inclusive.
97 : *
98 : * The inclusive maximum is actually defined as MAX_VERIFICATION_DEPTH.
99 : *
100 : * The default depth is 4.
101 : *
102 : * \return The current verification depth.
103 : */
104 0 : size_t tcp_bio_options::get_verification_depth() const
105 : {
106 0 : return f_verification_depth;
107 : }
108 :
109 :
110 : /** \brief Change the SSL options.
111 : *
112 : * This function sets the SSL options to the new \p ssl_options
113 : * values.
114 : *
115 : * By default the bio_clent forbids:
116 : *
117 : * * SSL version 2
118 : * * SSL version 3
119 : * * TLS version 1.0
120 : * * SSL compression
121 : *
122 : * which are parameter that are known to create security issues.
123 : *
124 : * To make it easier to add options to the defaults, the class
125 : * offers the DEFAULT_SSL_OPTIONS option. Just add and remove
126 : * bits starting from that value.
127 : *
128 : * \param[in] ssl_options The new SSL options.
129 : */
130 0 : void tcp_bio_options::set_ssl_options(ssl_options_t ssl_options)
131 : {
132 0 : f_ssl_options = ssl_options;
133 0 : }
134 :
135 :
136 : /** \brief Retrieve the current SSL options.
137 : *
138 : * This function can be used to add and remove SSL options to
139 : * bio_client connections.
140 : *
141 : * For example, to also prevent TLS 1.1, add the new flag:
142 : *
143 : * \code
144 : * bio.set_ssl_options(bio.get_ssl_options() | SSL_OP_NO_TLSv1_1);
145 : * \endcode
146 : *
147 : * And to allow compression, remove a flag which is set by default:
148 : *
149 : * \code
150 : * bio.set_ssl_options(bio.get_ssl_options() & ~(SSL_OP_NO_COMPRESSION));
151 : * \endcode
152 : *
153 : * \return The current SSL options.
154 : */
155 0 : tcp_bio_options::ssl_options_t tcp_bio_options::get_ssl_options() const
156 : {
157 0 : return f_ssl_options;
158 : }
159 :
160 :
161 : /** \brief Change the default path to SSL certificates.
162 : *
163 : * By default, we define the path to the SSL certificate as defined
164 : * on Ubuntu. This is under "/etc/ssl/certs".
165 : *
166 : * This function let you change that path to another one. Maybe you
167 : * would prefer to not allow all certificates to work in your
168 : * circumstances.
169 : *
170 : * \param[in] path The new path to SSL certificates used to verify
171 : * secure connections.
172 : */
173 0 : void tcp_bio_options::set_ssl_certificate_path(std::string const path)
174 : {
175 0 : f_ssl_certificate_path = path;
176 0 : }
177 :
178 :
179 : /** \brief Return the current SSL certificate path.
180 : *
181 : * This function returns the path where the SSL interface will
182 : * look for the root certificates used to verify a connection's
183 : * security.
184 : *
185 : * \return The current SSL certificate path.
186 : */
187 0 : std::string const & tcp_bio_options::get_ssl_certificate_path() const
188 : {
189 0 : return f_ssl_certificate_path;
190 : }
191 :
192 :
193 : /** \brief Set whether the SO_KEEPALIVE should be set.
194 : *
195 : * By default this option is turned ON meaning that all BIO_client have their
196 : * SO_KEEPALIVE turned on when created.
197 : *
198 : * You may turn this off if you are creating a socket for a very short
199 : * period of time, such as to send a fast REST command to a server.
200 : *
201 : * \attention
202 : * As per the TCP RFC, you should only use keepalive on a server, not a
203 : * client. (The client can quit any time and if it tries to access the
204 : * server and it fails, it can either quit or reconnect then.) That being
205 : * said, at times a server does not set the Keep-Alive and the client may
206 : * want to use it to maintain the connection when not much happens for
207 : * long durations.
208 : *
209 : * https://tools.ietf.org/html/rfc1122#page-101
210 : *
211 : * Some numbers about Keep-Alive:
212 : *
213 : * https://www.veritas.com/support/en_US/article.100028680
214 : *
215 : * For Linux (in seconds):
216 : *
217 : * \code
218 : * tcp_keepalive_time = 7200
219 : * tcp_keepalive_intvl = 75
220 : * tcp_keepalive_probes = 9
221 : * \endcode
222 : *
223 : * These can be access through the /proc file system:
224 : *
225 : * \code
226 : * /proc/sys/net/ipv4/tcp_keepalive_time
227 : * /proc/sys/net/ipv4/tcp_keepalive_intvl
228 : * /proc/sys/net/ipv4/tcp_keepalive_probes
229 : * \endcode
230 : *
231 : * See: http://tldp.org/HOWTO/TCP-Keepalive-HOWTO/usingkeepalive.html
232 : *
233 : * \warning
234 : * These numbers are used by all applications using TCP. Remember that
235 : * changing them will affect all your clients and servers.
236 : *
237 : * \param[in] keepalive true if you want the SO_KEEP_ALIVE turned on.
238 : *
239 : * \sa get_keepalive()
240 : */
241 0 : void tcp_bio_options::set_keepalive(bool keepalive)
242 : {
243 0 : f_keepalive = keepalive;
244 0 : }
245 :
246 :
247 : /** \brief Retrieve the SO_KEEPALIVE flag.
248 : *
249 : * This function returns the current value of the SO_KEEPALIVE flag. By
250 : * default this is true.
251 : *
252 : * Note that this function returns the flag status in the options, not
253 : * a connected socket.
254 : *
255 : * \return The current status of the SO_KEEPALIVE flag (true or false).
256 : *
257 : * \sa set_keepalive()
258 : */
259 0 : bool tcp_bio_options::get_keepalive() const
260 : {
261 0 : return f_keepalive;
262 : }
263 :
264 :
265 : /** \brief Set whether the SNI should be included in the SSL request.
266 : *
267 : * Whenever SSL connects a server, it has the option to include the
268 : * Server Name Indication, which is the server hostname to which
269 : * are think you are connecting. That way the server can verify that
270 : * you indeed were sent to the right server.
271 : *
272 : * The default is set to true, however, if you create a bio_client
273 : * object using an IP address (opposed to the hostname) then no
274 : * SNI will be included unless you also call the set_host() function
275 : * to setup the host.
276 : *
277 : * In other words, you can use the IP address on the bio_client
278 : * constructor and the hostname in the options and you will still
279 : * be able to get the SNI setup as expected.
280 : *
281 : * \param[in] sni true if you want the SNI to be included.
282 : *
283 : * \sa get_sni()
284 : * \sa set_host()
285 : */
286 0 : void tcp_bio_options::set_sni(bool sni)
287 : {
288 0 : f_sni = sni;
289 0 : }
290 :
291 :
292 : /** \brief Retrieve the SNI flag.
293 : *
294 : * This function returns the current value of the SNI flag. By
295 : * default this is true.
296 : *
297 : * Note that although the flag is true by default, the SSL request
298 : * may still not get to work if you don't include the host with
299 : * the set_host() and construct a bio_client object with an IP
300 : * address (opposed to a hostname.)
301 : *
302 : * \return The current status of the SNI (true or false).
303 : *
304 : * \sa set_sni()
305 : * \sa set_host()
306 : */
307 0 : bool tcp_bio_options::get_sni() const
308 : {
309 0 : return f_sni;
310 : }
311 :
312 :
313 : /** \brief Set the hostname.
314 : *
315 : * This function is used to setup the SNI hostname.
316 : *
317 : * The Server Name Indication is added to the SSL Hello message if
318 : * available (i.e. the host was specified here or the bio_client
319 : * constructor is called with the hostname and not an IP address.)
320 : *
321 : * If you construct the bio_client object with an IP address, you
322 : * can use this set_host() function to specify the hostname, but
323 : * you still need to make sure that both are a match.
324 : *
325 : * \param[in] host The host being accessed.
326 : */
327 0 : void tcp_bio_options::set_host(std::string const & host)
328 : {
329 0 : f_host = host;
330 0 : }
331 :
332 :
333 : /** \brief Retrieve the hostname.
334 : *
335 : * This function is used to retrieve the hostname. This name has
336 : * priority over the \p addr parameter specified to the
337 : * bio_client constructor.
338 : *
339 : * By default this name is empty in which case the bio_client
340 : * constructor checks the \p addr parameter and if it is
341 : * a hostname (opposed to direct IP addresses) then it uses
342 : * that \p addr parameter instead.
343 : *
344 : * If you do not want the Server Name Indication in the SSL
345 : * request, you must call set_sni(false) so even if the
346 : * bio_client constructor is called with a hostname, the
347 : * SNI won't be included in the request.
348 : *
349 : * \return A referemce string with the hostname.
350 : */
351 0 : std::string const & tcp_bio_options::get_host() const
352 : {
353 0 : return f_host;
354 : }
355 :
356 :
357 :
358 : } // namespace ed
359 : // vim: ts=4 sw=4 et
|