[monitoring-plugins/monitoring-plugins] check_http and EPIPE with HAProxy + SSL (#1419)

Peter Pramberger <[email protected]> Fri, 20 May 2016 07:15:36 -0700
Newsgroups gmane.network.nagios.devel
Message-ID <monitoring-plugins/monitoring-plugins/issues/[email protected]>
----==_mimepart_573f1c0872992_726f3f9c870b729c1943aa
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 7bit

Using check_http to monitor [HAProxy](http://www.haproxy.org/) via SSL on an
URL configured via monitor-uri (that is, [HAProxy](http://www.haproxy.org/)
is handling the HTTP request itself without forwarding it to the backend) is
currently not possible, as check_http dies with an `EPIPE` before returning
any output:

    write(3, "\25\3\1\0 \256\235\31\353\0\276\347\361\367e\221\323:3\336\302I\257\2232\270\307c\256\357\270\346"..., 37) = -1 EPIPE (Broken pipe)
    --- SIGPIPE {si_signo=SIGPIPE, si_code=SI_USER, si_pid=16924, si_uid=57000} ---
    +++ killed by SIGPIPE +++

This is due to the fact that [HAProxy](http://www.haproxy.org/) immediately
closes the monitoring connection after the response, without waiting for any
SSL shutdown. Unfortunately (in this case) `SSL_shutdown()` tries to send a
SSL shutdown message on a connection which does not exist anymore,
triggering the EPIPE.

The only workaround for that issue so far is disabling `SIGPIPE` before
`SSL_shutdown()`, as I found no way to check the socket state without
writing to it:

    --- monitoring-plugins-2.1.2/plugins/sslutils.c.orig    2015-10-16 11:06:18.000000000 +0200
    +++ monitoring-plugins-2.1.2/plugins/sslutils.c 2016-05-20 15:55:39.915793381 +0200
    @@ -127,7 +127,10 @@ void np_net_ssl_cleanup() {
     #ifdef SSL_set_tlsext_host_name
                    SSL_set_tlsext_host_name(s, NULL);
     #endif
    +               /* XXX: Ignore SIGPIPE or SSL_shutdown() will EPIPE on dropped connections */
    +               (void) signal (SIGPIPE, SIG_IGN);
                    SSL_shutdown(s);
    +               (void) signal (SIGPIPE, SIG_DFL);
                    SSL_free(s);
                    if (c) {
                            SSL_CTX_free(c);

Please consider this fix for inclusion.

---
You are receiving this because you are subscribed to this thread.
Reply to this email directly or view it on GitHub:
https://github.com/monitoring-plugins/monitoring-plugins/issues/1419
----==_mimepart_573f1c0872992_726f3f9c870b729c1943aa
Content-Type: text/html; charset=UTF-8
Content-Transfer-Encoding: 7bit

<p>Using check_http to monitor <a href="http://www.haproxy.org/">HAProxy</a> via SSL on an URL configured via monitor-uri (that is, <a href="http://www.haproxy.org/">HAProxy</a> is handling the HTTP request itself without forwarding it to the backend) is currently not possible, as check_http dies with an <code>EPIPE</code> before returning any output:</p>

<pre><code>write(3, "\25\3\1\0 \256\235\31\353\0\276\347\361\367e\221\323:3\336\302I\257\2232\270\307c\256\357\270\346"..., 37) = -1 EPIPE (Broken pipe)
--- SIGPIPE {si_signo=SIGPIPE, si_code=SI_USER, si_pid=16924, si_uid=57000} ---
+++ killed by SIGPIPE +++
</code></pre>

<p>This is due to the fact that <a href="http://www.haproxy.org/">HAProxy</a> immediately closes the monitoring connection after the response, without waiting for any SSL shutdown. Unfortunately (in this case) <code>SSL_shutdown()</code> tries to send a SSL shutdown message on a connection which does not exist anymore, triggering the EPIPE.</p>

<p>The only workaround for that issue so far is disabling <code>SIGPIPE</code> before <code>SSL_shutdown()</code>, as I found no way to check the socket state without writing to it:</p>

<pre><code>--- monitoring-plugins-2.1.2/plugins/sslutils.c.orig    2015-10-16 11:06:18.000000000 +0200
+++ monitoring-plugins-2.1.2/plugins/sslutils.c 2016-05-20 15:55:39.915793381 +0200
@@ -127,7 +127,10 @@ void np_net_ssl_cleanup() {
 #ifdef SSL_set_tlsext_host_name
                SSL_set_tlsext_host_name(s, NULL);
 #endif
+               /* XXX: Ignore SIGPIPE or SSL_shutdown() will EPIPE on dropped connections */
+               (void) signal (SIGPIPE, SIG_IGN);
                SSL_shutdown(s);
+               (void) signal (SIGPIPE, SIG_DFL);
                SSL_free(s);
                if (c) {
                        SSL_CTX_free(c);
</code></pre>

<p>Please consider this fix for inclusion.</p>

<p style="font-size:small;-webkit-text-size-adjust:none;color:#666;">&mdash;<br />You are receiving this because you are subscribed to this thread.<br /><a href="https://github.com/monitoring-plugins/monitoring-plugins/issues/1419">Reply to this email on GitHub</a><img alt="" height="1" src="https://github.com/notifications/beacon/AFQl2QFN4R5WXBsiFdrgpN-jF7bNhKBLks5qDcIIgaJpZM4IjPUx.gif" width="1" /></p>
<div itemscope itemtype="http://schema.org/EmailMessage">
<div itemprop="action" itemscope itemtype="http://schema.org/ViewAction">
  <link itemprop="url" href="https://github.com/monitoring-plugins/monitoring-plugins/issues/1419"></link>
  <meta itemprop="name" content="View Issue"></meta>
</div>
<meta itemprop="description" content="View this Issue on GitHub"></meta>
</div>


----==_mimepart_573f1c0872992_726f3f9c870b729c1943aa--