]> git.ipfire.org Git - thirdparty/haproxy.git/commitdiff
MEDIUM: connection: it's not the data layer's role to validate the connection
authorWilly Tarreau <w@1wt.eu>
Thu, 4 Oct 2012 18:20:46 +0000 (20:20 +0200)
committerWilly Tarreau <w@1wt.eu>
Thu, 4 Oct 2012 20:26:11 +0000 (22:26 +0200)
Till now we used to perform the L4_CONN check in the data layer
(eg: stream interface) but that does not make sense, because some transport
layers will imply that the connection is opened (eg: SSL), and also because
the complexity to check for this is higher in the data layer than in the
transport layer. This is so much true that some read0 cases did not validate
the connection.

So as of now, the transport layer is responsible for clearing L4_CONN when
it detects an activity, and the data layer may safely rely on this flag. This
only impacts a minor change in raw_sock and stream_interface for now.

src/raw_sock.c
src/stream_interface.c

index 9298ed780f9ccfe7d92f23ee49157bbfa4fa3ad2..52a48a5e4ee06e6bbf0e30e0fc255cba54c6c759 100644 (file)
@@ -156,10 +156,13 @@ int raw_sock_to_pipe(struct connection *conn, struct pipe *pipe, unsigned int co
                }
        } /* while */
 
+       if (unlikely(conn->flags & CO_FL_WAIT_L4_CONN) && retval)
+               conn->flags &= ~CO_FL_WAIT_L4_CONN;
        return retval;
 
  out_read0:
        conn_sock_read0(conn);
+       conn->flags &= ~CO_FL_WAIT_L4_CONN;
        return retval;
 }
 
@@ -190,6 +193,8 @@ int raw_sock_from_pipe(struct connection *conn, struct pipe *pipe)
                done += ret;
                pipe->data -= ret;
        }
+       if (unlikely(conn->flags & CO_FL_WAIT_L4_CONN) && done)
+               conn->flags &= ~CO_FL_WAIT_L4_CONN;
        return done;
 }
 
@@ -269,10 +274,14 @@ static int raw_sock_to_buf(struct connection *conn, struct buffer *buf, int coun
                        break;
                }
        }
+
+       if (unlikely(conn->flags & CO_FL_WAIT_L4_CONN) && done)
+               conn->flags &= ~CO_FL_WAIT_L4_CONN;
        return done;
 
  read0:
        conn_sock_read0(conn);
+       conn->flags &= ~CO_FL_WAIT_L4_CONN;
        return done;
 }
 
@@ -330,6 +339,8 @@ static int raw_sock_from_buf(struct connection *conn, struct buffer *buf, int fl
                        break;
                }
        }
+       if (unlikely(conn->flags & CO_FL_WAIT_L4_CONN) && done)
+               conn->flags &= ~CO_FL_WAIT_L4_CONN;
        return done;
 }
 
index 8bc5bbbb253cb82e7d6d5e0ec58c71ab2c863fdb..e857c129bb6682d79b17b57de9a1d62d6f8d8a98 100644 (file)
@@ -721,9 +721,6 @@ static int si_conn_send_loop(struct connection *conn)
                if (ret <= 0)
                        break;
 
-               if (si->conn.flags & CO_FL_WAIT_L4_CONN)
-                       si->conn.flags &= ~CO_FL_WAIT_L4_CONN;
-
                b->flags |= CF_WRITE_PARTIAL;
 
                if (!b->buf.o) {
@@ -1049,9 +1046,6 @@ static void si_conn_recv_cb(struct connection *conn)
                        b_adv(&b->buf, fwd);
                }
 
-               if (conn->flags & CO_FL_WAIT_L4_CONN)
-                       conn->flags &= ~CO_FL_WAIT_L4_CONN;
-
                b->flags |= CF_READ_PARTIAL;
                b->total += ret;