[MAJOR] rework of the server FSM

srv_state has been removed from HTTP state machines, and states
have been split in either TCP states or analyzers. For instance,
the TARPIT state has just become a simple analyzer.

New flags have been added to the struct buffer to compensate this.
The high-level stream processors sometimes need to force a disconnection
without touching a file-descriptor (eg: report an error). But if
they touched BF_SHUTW or BF_SHUTR, the file descriptor would not
be closed. Thus, the two SHUT?_NOW flags have been added so that
an application can request a forced close which the stream interface
will be forced to obey.

During this change, a new BF_HIJACK flag was added. It will
be used for data generation, eg during a stats dump. It
prevents the producer on a buffer from sending data into it.

  BF_SHUTR_NOW  /* the producer must shut down for reads ASAP  */
  BF_SHUTW_NOW  /* the consumer must shut down for writes ASAP */
  BF_HIJACK     /* the producer is temporarily replaced        */

BF_SHUTW_NOW has precedence over BF_HIJACK. BF_HIJACK has
precedence over BF_MAY_FORWARD (so that it does not need it).

New functions buffer_shutr_now(), buffer_shutw_now(), buffer_abort()
are provided to manipulate BF_SHUT* flags.

A new type "stream_interface" has been added to describe both
sides of a buffer. A stream interface has states and error
reporting. The session now has two stream interfaces (one per
side). Each buffer has stream_interface pointers to both
consumer and producer sides.

The server-side file descriptor has moved to its stream interface,
so that even the buffer has access to it.

process_srv() has been split into three parts :
  - tcp_get_connection() obtains a connection to the server
  - tcp_connection_failed() tests if a previously attempted
    connection has succeeded or not.
  - process_srv_data() only manages the data phase, and in
    this sense should be roughly equivalent to process_cli.

Little code has been removed, and a lot of old code has been
left in comments for now.
diff --git a/include/types/buffers.h b/include/types/buffers.h
index f516ffe..6374271 100644
--- a/include/types/buffers.h
+++ b/include/types/buffers.h
@@ -57,6 +57,15 @@
 #define BF_READ_TIMEOUT     32768  /* timeout while waiting for producer */
 #define BF_WRITE_TIMEOUT    65536  /* timeout while waiting for consumer */
 
+/* When either BF_SHUTR_NOW or BF_HIJACK is set, it is strictly forbidden for
+ * the stream interface to alter the buffer contents. When BF_SHUTW_NOW is set,
+ * it is strictly forbidden for the stream interface to send anything from the
+ * buffer.
+ */
+#define BF_SHUTR_NOW       131072  /* the producer must shut down for reads ASAP */
+#define BF_SHUTW_NOW       262144  /* the consumer must shut down for writes ASAP */
+#define BF_HIJACK          524288  /* the producer is temporarily replaced */
+
 
 /* Analysers (buffer->analysers).
  * Those bits indicate that there are some processing to do on the buffer
@@ -68,7 +77,8 @@
 #define AN_REQ_INSPECT          0x00000001  /* inspect request contents */
 #define AN_REQ_HTTP_HDR         0x00000002  /* inspect HTTP request headers */
 #define AN_REQ_HTTP_BODY        0x00000004  /* inspect HTTP request body */
-#define AN_RTR_HTTP_HDR         0x00000008  /* inspect HTTP response headers */
+#define AN_REQ_HTTP_TARPIT      0x00000008  /* wait for end of HTTP tarpit */
+#define AN_RTR_HTTP_HDR         0x00000010  /* inspect HTTP response headers */
 
 /* describes a chunk of string */
 struct chunk {
@@ -91,6 +101,8 @@
 	unsigned char xfer_large;       /* number of consecutive large xfers */
 	unsigned char xfer_small;       /* number of consecutive small xfers */
 	unsigned long long total;       /* total data read */
+	struct stream_interface *prod;  /* producer attached to this buffer */
+	struct stream_interface *cons;  /* consumer attached to this buffer */
 	char data[BUFSIZE];
 };
 
diff --git a/include/types/session.h b/include/types/session.h
index 3035956..2d0439b 100644
--- a/include/types/session.h
+++ b/include/types/session.h
@@ -36,6 +36,7 @@
 #include <types/proxy.h>
 #include <types/queue.h>
 #include <types/server.h>
+#include <types/stream_interface.h>
 #include <types/task.h>
 
 
@@ -156,7 +157,6 @@
 	struct proxy *fe;			/* the proxy this session depends on for the client side */
 	struct proxy *be;			/* the proxy this session depends on for the server side */
 	int cli_fd;				/* the client side fd */
-	int srv_fd;				/* the server side fd */
 	int cli_state;				/* state of the client side */
 	int srv_state;				/* state of the server side */
 	int conn_retries;			/* number of connect retries left */
@@ -164,6 +164,7 @@
 	unsigned term_trace;			/* term trace: 4*8 bits indicating which part of the code closed */
 	struct buffer *req;			/* request buffer */
 	struct buffer *rep;			/* response buffer */
+	struct stream_interface si[2];          /* client and server stream interfaces */
 	struct sockaddr_storage cli_addr;	/* the client address */
 	struct sockaddr_storage frt_addr;	/* the frontend address reached by the client if SN_FRT_ADDR_SET is set */
 	struct sockaddr_in srv_addr;		/* the address to connect to */
diff --git a/include/types/stream_interface.h b/include/types/stream_interface.h
new file mode 100644
index 0000000..edfb758
--- /dev/null
+++ b/include/types/stream_interface.h
@@ -0,0 +1,73 @@
+/*
+  include/types/stream_interface.h
+  This file describes the stream_interface struct and associated constants.
+
+  Copyright (C) 2000-2008 Willy Tarreau - w@1wt.eu
+
+  This library is free software; you can redistribute it and/or
+  modify it under the terms of the GNU Lesser General Public
+  License as published by the Free Software Foundation, version 2.1
+  exclusively.
+
+  This library is distributed in the hope that it will be useful,
+  but WITHOUT ANY WARRANTY; without even the implied warranty of
+  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+  Lesser General Public License for more details.
+
+  You should have received a copy of the GNU Lesser General Public
+  License along with this library; if not, write to the Free Software
+  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
+*/
+
+#ifndef _TYPES_STREAM_INTERFACE_H
+#define _TYPES_STREAM_INTERFACE_H
+
+#include <stdlib.h>
+
+#include <common/config.h>
+
+/* A stream interface must have its own errors independantly of the buffer's,
+ * so that applications can rely on what the buffer reports while the stream
+ * interface is performing some retries (eg: connection error).
+ */
+enum {
+	SI_ST_INI = 0,           /* interface not initialized yet and might not exist */
+	SI_ST_QUE,               /* interface waiting in queue */
+	SI_ST_TAR,               /* interface in turn-around state after failed connect attempt */
+	SI_ST_ASS,               /* server just assigned to this interface */
+	SI_ST_CON,               /* initiated connection request (resource exists) */
+	SI_ST_EST,               /* connection established (resource exists) */
+	SI_ST_CLO,               /* stream interface closed, might not existing anymore */
+};
+
+/* error types reported on the streams interface for more accurate reporting */
+enum {
+	SI_ET_NONE = 0,         /* no error yet, leave it to zero */
+	SI_ET_QUEUE_TO,         /* queue timeout */
+	SI_ET_QUEUE_ERR,        /* queue error (eg: full) */
+	SI_ET_QUEUE_ABRT,       /* aborted in queue by external cause */
+	SI_ET_CONN_TO,          /* connection timeout */
+	SI_ET_CONN_ERR,         /* connection error (eg: no server available) */
+	SI_ET_CONN_ABRT,        /* connection aborted by external cause (eg: abort) */
+	SI_ET_CONN_OTHER,       /* connection aborted for other reason (eg: 500) */
+	SI_ET_DATA_TO,          /* timeout during data phase */
+	SI_ET_DATA_ERR,         /* error during data phase */
+	SI_ET_DATA_ABRT,        /* data phase aborted by external cause */
+};
+
+struct stream_interface {
+	unsigned int state;     /* SI_ST* */
+	int err_type;           /* first error detected, one of SI_ET_* */
+	void *err_loc;          /* commonly the server, NULL when SI_ET_NONE */
+	int fd;                 /* file descriptor for a stream driver when known */
+};
+
+
+#endif /* _TYPES_STREAM_INTERFACE_H */
+
+/*
+ * Local variables:
+ *  c-indent-level: 8
+ *  c-basic-offset: 8
+ * End:
+ */