@cryptotaxi247 / netdata-1 / commits / 54d461b17

fix SSL related crashes (#14076)

prevent concurrent initialization of SSL from multiple threads; prevent re-initialization of SSL

Costa Tsaousis committed Dec 1, 2022 at 15:56 UTC 54d461b179b1a3b825acde60911fb50515c4bea8
2 files changed +33 -16
libnetdata/socket/security.c
+25 -13
@@ -204,31 +204,43 @@ static SSL_CTX * security_initialize_openssl_server() {
204 * NETDATA_SSL_CONTEXT_EXPORTING - Starts the OpenTSDB context
205 */
206 void security_start_ssl(int selector) {
207 + static SPINLOCK sp = NETDATA_SPINLOCK_INITIALIZER;
208 + netdata_spinlock_lock(&sp);
209 +
210 switch (selector) {
211 case NETDATA_SSL_CONTEXT_SERVER: {
209 - struct stat statbuf;
210 - if (stat(netdata_ssl_security_key, &statbuf) || stat(netdata_ssl_security_cert, &statbuf)) {
211 - info("To use encryption it is necessary to set \"ssl certificate\" and \"ssl key\" in [web] !\n");
212 - return;
212 + if(!netdata_ssl_srv_ctx) {
213 + struct stat statbuf;
214 + if (stat(netdata_ssl_security_key, &statbuf) || stat(netdata_ssl_security_cert, &statbuf))
215 + info("To use encryption it is necessary to set \"ssl certificate\" and \"ssl key\" in [web] !\n");
216 + else {
217 + netdata_ssl_srv_ctx = security_initialize_openssl_server();
218 + SSL_CTX_set_mode(netdata_ssl_srv_ctx, SSL_MODE_ENABLE_PARTIAL_WRITE);
219 + }
220 }
214 -
215 - netdata_ssl_srv_ctx = security_initialize_openssl_server();
216 - SSL_CTX_set_mode(netdata_ssl_srv_ctx, SSL_MODE_ENABLE_PARTIAL_WRITE);
221 break;
222 }
223 +
224 case NETDATA_SSL_CONTEXT_STREAMING: {
220 - netdata_ssl_client_ctx = security_initialize_openssl_client();
221 - //This is necessary for the stream, because it is working sometimes with nonblock socket.
222 - //It returns the bitmask after to change, there is not any description of errors in the documentation
223 - SSL_CTX_set_mode(
224 - netdata_ssl_client_ctx, SSL_MODE_ENABLE_PARTIAL_WRITE |SSL_MODE_ACCEPT_MOVING_WRITE_BUFFER |SSL_MODE_AUTO_RETRY);
225 + if(!netdata_ssl_client_ctx) {
226 + netdata_ssl_client_ctx = security_initialize_openssl_client();
227 + //This is necessary for the stream, because it is working sometimes with nonblock socket.
228 + //It returns the bitmask after to change, there is not any description of errors in the documentation
229 + SSL_CTX_set_mode(netdata_ssl_client_ctx,
230 + SSL_MODE_ENABLE_PARTIAL_WRITE | SSL_MODE_ACCEPT_MOVING_WRITE_BUFFER |
231 + SSL_MODE_AUTO_RETRY);
232 + }
233 break;
234 }
235 +
236 case NETDATA_SSL_CONTEXT_EXPORTING: {
228 - netdata_ssl_exporting_ctx = security_initialize_openssl_client();
237 + if(!netdata_ssl_exporting_ctx)
238 + netdata_ssl_exporting_ctx = security_initialize_openssl_client();
239 break;
240 }
241 }
242 +
243 + netdata_spinlock_unlock(&sp);
244 }
245
246 /**
streaming/sender.c
+8 -3
@@ -1114,9 +1114,14 @@ void *rrdpush_sender_thread(void *ptr) {
1114 }
1115
1116 #ifdef ENABLE_HTTPS
1117 - if (netdata_use_ssl_on_stream & NETDATA_SSL_FORCE ){
1118 - security_start_ssl(NETDATA_SSL_CONTEXT_STREAMING);
1119 - ssl_security_location_for_context(netdata_ssl_client_ctx, netdata_ssl_ca_file, netdata_ssl_ca_path);
1117 + if (netdata_use_ssl_on_stream & NETDATA_SSL_FORCE ) {
1118 + static SPINLOCK sp = NETDATA_SPINLOCK_INITIALIZER;
1119 + netdata_spinlock_lock(&sp);
1120 + if(!netdata_ssl_client_ctx) {
1121 + security_start_ssl(NETDATA_SSL_CONTEXT_STREAMING);
1122 + ssl_security_location_for_context(netdata_ssl_client_ctx, netdata_ssl_ca_file, netdata_ssl_ca_path);
1123 + }
1124 + netdata_spinlock_unlock(&sp);
1125 }
1126 #endif
1127