Reproduce the bug:
Emulate this situation with ipfw firewall (70% packet loss from our monitoring server):
00150 3918 1237188 prob 0.700000 deny ip from 91.103.XX.XX to me
Then we compiled nrpe3 with debugging information and found the place in which the loop occurs.
srv2# lldb -p 1923
(lldb) process attach --pid 1923
Process 1923 stopped
Executable module set to "/home/admin/nrpe/nrpe3".
Architecture set to: x86_64--freebsd11.1.
(lldb) bt
* thread #1
* frame #0: 0x0000000800d19900 libcrypto.so.8`lh_retrieve + 64
frame #1: 0x0000000800d27fb1 libcrypto.so.8`___lldb_unnamed_symbol529$$libcrypto.so.8 + 193
frame #2: 0x0000000800d26439 libcrypto.so.8`ERR_get_state + 169
frame #3: 0x0000000800d2662c libcrypto.so.8`ERR_clear_error + 12
frame #4: 0x00000008008718c3 libssl.so.8`ssl23_accept + 67
frame #5: nrpe3`handle_conn_ssl(sock=5, ssl_ptr=0x0000000801aa0700) at nrpe.c:1922
frame #6: nrpe3`handle_connection(sock=5) at nrpe.c:1668
frame #7: nrpe3`wait_for_connections at nrpe.c:1363
frame #8: nrpe3`run_daemon at nrpe.c:647
frame #9: nrpe3`main(argc=4, argv=0x00007fffffffeaf8) at nrpe.c:225
frame #10: 0x0000000000403eaf nrpe3`_start + 383
(lldb) frame s 5
frame #5: nrpe3`handle_conn_ssl(sock=5, ssl_ptr=0x0000000801aa0700) at nrpe.c:1922
1919 SSL_set_fd(ssl, sock);
1920
1921 /* keep attempting the request if needed */
-> 1922 while (((rc = SSL_accept(ssl)) != 1)
1923 && (SSL_get_error(ssl, rc) == SSL_ERROR_WANT_READ));
1924
1925 if (rc != 1) {
(lldb) frame info
frame #5: nrpe3`handle_conn_ssl(sock=5, ssl_ptr=0x0000000801aa0700) at nrpe.c:1922
(lldb) frame variable
(int) sock = 5
(void *) ssl_ptr = 0x0000000801aa0700
(const SSL_CIPHER *) c = 0x00007fffffffeaf0
(const char *) errmsg = 0x0000000000000000
(char [2048]) buffer = ""
(SSL *) ssl = 0x0000000801aa0700
(X509 *) peer = 0x0000000000000000
(int) rc = -1
(int) x = 0
(lldb)
Your current implementation is DOS attack prone. When using a non-blocking socket, nothing is to be done, but select() can be used to check for the required condition.
Hello! nrpe-3.2.1 has a bug that allows CPU exhausting attack against servers where the daemon is running!
We use FreeBSD 11.2 amd64. Not so long ago, we recorded an increased CPU load on a group of their servers which there were packet losses.
Reproduce the bug: Emulate this situation with ipfw firewall (70% packet loss from our monitoring server):
Then we compiled nrpe3 with debugging information and found the place in which the loop occurs.
Your current implementation is DOS attack prone. When using a non-blocking socket, nothing is to be done, but select() can be used to check for the required condition.
https://www.openssl.org/docs/man1.1.1/man3/SSL_accept.html https://www.openssl.org/docs/man1.1.1/man3/SSL_read.html