/*
 * FastCGI mux-demux for connections
 *
 * Copyright (C) 2019 HAProxy Technologies, Christopher Faulet <cfaulet@haproxy.com>
 *
 * This program is free software; you can redistribute it and/or
 * modify it under the terms of the GNU General Public License
 * as published by the Free Software Foundation; either version
 * 2 of the License, or (at your option) any later version.
 *
 */

#include <import/ist.h>

#include <haproxy/api.h>
#include <haproxy/cfgparse.h>
#include <haproxy/connection.h>
#include <haproxy/errors.h>
#include <haproxy/fcgi-app.h>
#include <haproxy/fcgi.h>
#include <haproxy/h1.h>
#include <haproxy/h1_htx.h>
#include <haproxy/http_htx.h>
#include <haproxy/htx.h>
#include <haproxy/list.h>
#include <haproxy/log.h>
#include <haproxy/net_helper.h>
#include <haproxy/proxy.h>
#include <haproxy/regex.h>
#include <haproxy/session-t.h>
#include <haproxy/ssl_sock.h>
#include <haproxy/stream.h>
#include <haproxy/stream_interface.h>
#include <haproxy/trace.h>


/* FCGI Connection flags (32 bits) */
#define FCGI_CF_NONE           0x00000000

/* Flags indicating why writing to the mux is blockes */
#define FCGI_CF_MUX_MALLOC      0x00000001 /* mux is blocked on lack connection's mux buffer */
#define FCGI_CF_MUX_MFULL       0x00000002 /* mux is blocked on connection's mux buffer full */
#define FCGI_CF_MUX_BLOCK_ANY   0x00000003 /* mux is blocked on connection's mux buffer full */

/* Flags indicating why writing to the demux is blocked.
 * The first two ones directly affect the ability for the mux to receive data
 * from the connection. The other ones affect the mux's ability to demux
 * received data.
 */
#define FCGI_CF_DEM_DALLOC      0x00000004  /* demux blocked on lack of connection's demux buffer */
#define FCGI_CF_DEM_DFULL       0x00000008  /* demux blocked on connection's demux buffer full */
#define FCGI_CF_DEM_MROOM       0x00000010  /* demux blocked on lack of room in mux buffer */
#define FCGI_CF_DEM_SALLOC      0x00000020  /* demux blocked on lack of stream's rx buffer */
#define FCGI_CF_DEM_SFULL       0x00000040  /* demux blocked on stream request buffer full */
#define FCGI_CF_DEM_TOOMANY     0x00000080  /* demux blocked waiting for some conn_streams to leave */
#define FCGI_CF_DEM_BLOCK_ANY   0x000000F0  /* aggregate of the demux flags above except DALLOC/DFULL */

/* Other flags */
#define FCGI_CF_MPXS_CONNS      0x00000100  /* connection multiplexing is supported */
#define FCGI_CF_ABRTS_SENT      0x00000200  /* a record ABORT was successfully sent to all active streams */
#define FCGI_CF_ABRTS_FAILED    0x00000400  /* failed to abort processing of all streams */
#define FCGI_CF_WAIT_FOR_HS     0x00000800  /* We did check that at least a stream was waiting for handshake */
#define FCGI_CF_KEEP_CONN       0x00001000  /* HAProxy is responsible to close the connection */
#define FCGI_CF_GET_VALUES      0x00002000  /* retrieve settings */

/* FCGI connection state (fcgi_conn->state) */
enum fcgi_conn_st {
	FCGI_CS_INIT = 0,    /* init done, waiting for sending GET_VALUES record */
	FCGI_CS_SETTINGS,    /* GET_VALUES sent, waiting for the GET_VALUES_RESULT record */
	FCGI_CS_RECORD_H,    /* GET_VALUES_RESULT received, waiting for a record header */
	FCGI_CS_RECORD_D,    /* Record header OK, waiting for a record data */
	FCGI_CS_RECORD_P,    /* Record processed, remains the padding */
	FCGI_CS_CLOSED,      /* abort requests if necessary and  close the connection ASAP */
	FCGI_CS_ENTRIES
} __attribute__((packed));

/* 32 buffers: one for the ring's root, rest for the mbuf itself */
#define FCGI_C_MBUF_CNT 32

/* Size for a record header (also size of empty record) */
#define FCGI_RECORD_HEADER_SZ 8

/* FCGI connection descriptor */
struct fcgi_conn {
	struct connection *conn;

	enum fcgi_conn_st state;              /* FCGI connection state */
	int16_t max_id;                       /* highest ID known on this connection, <0 before mgmt records */
	uint32_t streams_limit;               /* maximum number of concurrent streams the peer supports */
	uint32_t flags;                      /* Connection flags: FCGI_CF_* */

	int16_t  dsi;                        /* dmux stream ID (<0 = idle ) */
	uint16_t drl;                        /* demux record length (if dsi >= 0) */
	uint8_t  drt;                        /* demux record type (if dsi >= 0) */
	uint8_t  drp;                        /* demux record padding (if dsi >= 0) */

	struct buffer dbuf;                  /* demux buffer */
	struct buffer mbuf[FCGI_C_MBUF_CNT]; /* mux buffers (ring) */

	int timeout;                         /* idle timeout duration in ticks */
	int shut_timeout;                    /* idle timeout duration in ticks after shutdown */
	unsigned int nb_streams;             /* number of streams in the tree */
	unsigned int nb_cs;                  /* number of attached conn_streams */
	unsigned int nb_reserved;            /* number of reserved streams */
	unsigned int stream_cnt;             /* total number of streams seen */

	struct proxy *proxy;                 /* the proxy this connection was created for */
	struct fcgi_app *app;                /* FCGI application used by this mux */
	struct task *task;                   /* timeout management task */
	struct eb_root streams_by_id;        /* all active streams by their ID */

	struct list send_list;               /* list of blocked streams requesting to send */

	struct buffer_wait buf_wait;         /* Wait list for buffer allocation */
	struct wait_event wait_event;        /* To be used if we're waiting for I/Os */
};


/* FCGI stream state, in fcgi_strm->state */
enum fcgi_strm_st {
	FCGI_SS_IDLE = 0,
	FCGI_SS_OPEN,
	FCGI_SS_HREM,     // half-closed(remote)
	FCGI_SS_HLOC,     // half-closed(local)
	FCGI_SS_ERROR,
	FCGI_SS_CLOSED,
	FCGI_SS_ENTRIES
} __attribute__((packed));


/* FCGI stream flags (32 bits) */
#define FCGI_SF_NONE           0x00000000
#define FCGI_SF_ES_RCVD        0x00000001 /* end-of-stream received (empty STDOUT or EDN_REQUEST record) */
#define FCGI_SF_ES_SENT        0x00000002 /* end-of-stream sent (empty STDIN record) */
#define FCGI_SF_EP_SENT        0x00000004 /* end-of-param sent (empty PARAMS  record) */
#define FCGI_SF_ABRT_SENT      0x00000008 /* abort sent (ABORT_REQUEST record) */

/* Stream flags indicating the reason the stream is blocked */
#define FCGI_SF_BLK_MBUSY      0x00000010 /* blocked waiting for mux access (transient) */
#define FCGI_SF_BLK_MROOM      0x00000020 /* blocked waiting for room in the mux */
#define FCGI_SF_BLK_ANY        0x00000030 /* any of the reasons above */

#define FCGI_SF_BEGIN_SENT     0x00000100  /* a BEGIN_REQUEST record was sent for this stream */
#define FCGI_SF_OUTGOING_DATA  0x00000200  /* set whenever we've seen outgoing data */
#define FCGI_SF_NOTIFIED       0x00000400  /* a paused stream was notified to try to send again */

#define FCGI_SF_WANT_SHUTR     0x00001000  /* a stream couldn't shutr() (mux full/busy) */
#define FCGI_SF_WANT_SHUTW     0x00002000  /* a stream couldn't shutw() (mux full/busy) */
#define FCGI_SF_KILL_CONN      0x00004000  /* kill the whole connection with this stream */


/* FCGI stream descriptor */
struct fcgi_strm {
	struct conn_stream *cs;
	struct session *sess;
	struct fcgi_conn *fconn;

	int32_t id;                   /* stream ID */

	uint32_t flags;               /* Connection flags: FCGI_SF_* */
	enum fcgi_strm_st state;      /* FCGI stream state */
	int proto_status;             /* FCGI_PS_* */

	struct h1m h1m;               /* response parser state for H1 */

	struct buffer rxbuf;          /* receive buffer, always valid (buf_empty or real buffer) */

	struct eb32_node by_id;       /* place in fcgi_conn's streams_by_id */
	struct wait_event *subs;      /* Address of the wait_event the conn_stream associated is waiting on */
	struct list send_list;        /* To be used when adding in fcgi_conn->send_list */
	struct tasklet *shut_tl;      /* deferred shutdown tasklet, to retry to close after we failed to by lack of space */
};

/* Flags representing all default FCGI parameters */
#define FCGI_SP_CGI_GATEWAY    0x00000001
#define FCGI_SP_DOC_ROOT       0x00000002
#define FCGI_SP_SCRIPT_NAME    0x00000004
#define FCGI_SP_PATH_INFO      0x00000008
#define FCGI_SP_REQ_URI        0x00000010
#define FCGI_SP_REQ_METH       0x00000020
#define FCGI_SP_REQ_QS         0x00000040
#define FCGI_SP_SRV_PORT       0x00000080
#define FCGI_SP_SRV_PROTO      0x00000100
#define FCGI_SP_SRV_NAME       0x00000200
#define FCGI_SP_REM_ADDR       0x00000400
#define FCGI_SP_REM_PORT       0x00000800
#define FCGI_SP_SCRIPT_FILE    0x00001000
#define FCGI_SP_PATH_TRANS     0x00002000
#define FCGI_SP_CONT_LEN       0x00004000
#define FCGI_SP_HTTPS          0x00008000
#define FCGI_SP_MASK           0x0000FFFF
#define FCGI_SP_URI_MASK       (FCGI_SP_SCRIPT_NAME|FCGI_SP_PATH_INFO|FCGI_SP_REQ_QS)

/* FCGI parameters used when PARAMS record is sent */
struct fcgi_strm_params {
	uint32_t mask;
	struct ist docroot;
	struct ist scriptname;
	struct ist pathinfo;
	struct ist meth;
	struct ist uri;
	struct ist vsn;
	struct ist qs;
	struct ist srv_name;
	struct ist srv_port;
	struct ist rem_addr;
	struct ist rem_port;
	struct ist cont_len;
	int https;
	struct buffer *p;
};

/* Maximum amount of data we're OK with re-aligning for buffer optimizations */
#define MAX_DATA_REALIGN 1024

/* trace source and events */
static void fcgi_trace(enum trace_level level, uint64_t mask,
		       const struct trace_source *src,
		       const struct ist where, const struct ist func,
		       const void *a1, const void *a2, const void *a3, const void *a4);

/* The event representation is split like this :
 *   fconn - internal FCGI connection
 *   fstrm - internal FCGI stream
 *   strm  - application layer
 *   rx    - data receipt
 *   tx    - data transmission
 *   rsp   - response parsing
 */
static const struct trace_event fcgi_trace_events[] = {
#define           FCGI_EV_FCONN_NEW     (1ULL <<  0)
	{ .mask = FCGI_EV_FCONN_NEW,    .name = "fconn_new",        .desc = "new FCGI connection" },
#define           FCGI_EV_FCONN_RECV    (1ULL <<  1)
	{ .mask = FCGI_EV_FCONN_RECV,   .name = "fconn_recv",       .desc = "Rx on FCGI connection" },
#define           FCGI_EV_FCONN_SEND    (1ULL <<  2)
	{ .mask = FCGI_EV_FCONN_SEND,   .name = "fconn_send",       .desc = "Tx on FCGI connection" },
#define           FCGI_EV_FCONN_BLK     (1ULL <<  3)
	{ .mask = FCGI_EV_FCONN_BLK,    .name = "fconn_blk",        .desc = "FCGI connection blocked" },
#define           FCGI_EV_FCONN_WAKE    (1ULL <<  4)
	{ .mask = FCGI_EV_FCONN_WAKE,   .name = "fconn_wake",       .desc = "FCGI connection woken up" },
#define           FCGI_EV_FCONN_END     (1ULL <<  5)
	{ .mask = FCGI_EV_FCONN_END,    .name = "fconn_end",        .desc = "FCGI connection terminated" },
#define           FCGI_EV_FCONN_ERR     (1ULL <<  6)
	{ .mask = FCGI_EV_FCONN_ERR,    .name = "fconn_err",        .desc = "error on FCGI connection" },

#define           FCGI_EV_RX_FHDR       (1ULL <<  7)
	{ .mask = FCGI_EV_RX_FHDR,      .name = "rx_fhdr",          .desc = "FCGI record header received" },
#define           FCGI_EV_RX_RECORD     (1ULL <<  8)
	{ .mask = FCGI_EV_RX_RECORD,    .name = "rx_record",        .desc = "receipt of any FCGI record" },
#define           FCGI_EV_RX_EOI        (1ULL <<  9)
	{ .mask = FCGI_EV_RX_EOI,       .name = "rx_eoi",           .desc = "receipt of end of FCGI input" },
#define           FCGI_EV_RX_GETVAL     (1ULL << 10)
	{ .mask = FCGI_EV_RX_GETVAL,    .name = "rx_get_values",    .desc = "receipt of FCGI GET_VALUES_RESULT record" },
#define           FCGI_EV_RX_STDOUT     (1ULL << 11)
	{ .mask = FCGI_EV_RX_STDOUT,    .name = "rx_stdout",        .desc = "receipt of FCGI STDOUT record" },
#define           FCGI_EV_RX_STDERR     (1ULL << 12)
	{ .mask = FCGI_EV_RX_STDERR,    .name = "rx_stderr",        .desc = "receipt of FCGI STDERR record" },
#define           FCGI_EV_RX_ENDREQ     (1ULL << 13)
	{ .mask = FCGI_EV_RX_ENDREQ,    .name = "rx_end_req",       .desc = "receipt of FCGI END_REQUEST record" },

#define           FCGI_EV_TX_RECORD     (1ULL << 14)
	{ .mask = FCGI_EV_TX_RECORD,    .name = "tx_record",        .desc = "transmission of any FCGI record" },
#define           FCGI_EV_TX_EOI        (1ULL << 15)
	{ .mask = FCGI_EV_TX_EOI,       .name = "tx_eoi",           .desc = "transmission of FCGI end of input" },
#define           FCGI_EV_TX_BEGREQ     (1ULL << 16)
	{ .mask = FCGI_EV_TX_BEGREQ,    .name = "tx_begin_request", .desc = "transmission of FCGI BEGIN_REQUEST record" },
#define           FCGI_EV_TX_GETVAL     (1ULL << 17)
	{ .mask = FCGI_EV_TX_GETVAL,    .name = "tx_get_values",    .desc = "transmission of FCGI GET_VALUES record" },
#define           FCGI_EV_TX_PARAMS     (1ULL << 18)
	{ .mask = FCGI_EV_TX_PARAMS,    .name = "tx_params",        .desc = "transmission of FCGI PARAMS record" },
#define           FCGI_EV_TX_STDIN      (1ULL << 19)
	{ .mask = FCGI_EV_TX_STDIN,     .name = "tx_stding",        .desc = "transmission of FCGI STDIN record" },
#define           FCGI_EV_TX_ABORT      (1ULL << 20)
	{ .mask = FCGI_EV_TX_ABORT,     .name = "tx_abort",         .desc = "transmission of FCGI ABORT record" },

#define           FCGI_EV_RSP_DATA      (1ULL << 21)
	{ .mask = FCGI_EV_RSP_DATA,     .name = "rsp_data",         .desc = "parse any data of H1 response" },
#define           FCGI_EV_RSP_EOM       (1ULL << 22)
	{ .mask = FCGI_EV_RSP_EOM,      .name = "rsp_eom",          .desc = "reach the end of message of H1 response" },
#define           FCGI_EV_RSP_HDRS      (1ULL << 23)
	{ .mask = FCGI_EV_RSP_HDRS,     .name = "rsp_headers",      .desc = "parse headers of H1 response" },
#define           FCGI_EV_RSP_BODY      (1ULL << 24)
	{ .mask = FCGI_EV_RSP_BODY,     .name = "rsp_body",         .desc = "parse body part of H1 response" },
#define           FCGI_EV_RSP_TLRS      (1ULL << 25)
	{ .mask = FCGI_EV_RSP_TLRS,     .name = "rsp_trailerus",    .desc = "parse trailers of H1 response" },

#define           FCGI_EV_FSTRM_NEW     (1ULL << 26)
	{ .mask = FCGI_EV_FSTRM_NEW,    .name = "fstrm_new",        .desc = "new FCGI stream" },
#define           FCGI_EV_FSTRM_BLK     (1ULL << 27)
	{ .mask = FCGI_EV_FSTRM_BLK,    .name = "fstrm_blk",        .desc = "FCGI stream blocked" },
#define           FCGI_EV_FSTRM_END     (1ULL << 28)
	{ .mask = FCGI_EV_FSTRM_END,    .name = "fstrm_end",        .desc = "FCGI stream terminated" },
#define           FCGI_EV_FSTRM_ERR     (1ULL << 29)
	{ .mask = FCGI_EV_FSTRM_ERR,    .name = "fstrm_err",        .desc = "error on FCGI stream" },

#define           FCGI_EV_STRM_NEW      (1ULL << 30)
	{ .mask = FCGI_EV_STRM_NEW,     .name = "strm_new",         .desc = "app-layer stream creation" },
#define           FCGI_EV_STRM_RECV     (1ULL << 31)
	{ .mask = FCGI_EV_STRM_RECV,    .name = "strm_recv",        .desc = "receiving data for stream" },
#define           FCGI_EV_STRM_SEND     (1ULL << 32)
	{ .mask = FCGI_EV_STRM_SEND,    .name = "strm_send",        .desc = "sending data for stream" },
#define           FCGI_EV_STRM_FULL     (1ULL << 33)
	{ .mask = FCGI_EV_STRM_FULL,    .name = "strm_full",        .desc = "stream buffer full" },
#define           FCGI_EV_STRM_WAKE     (1ULL << 34)
	{ .mask = FCGI_EV_STRM_WAKE,    .name = "strm_wake",        .desc = "stream woken up" },
#define           FCGI_EV_STRM_SHUT     (1ULL << 35)
	{ .mask = FCGI_EV_STRM_SHUT,    .name = "strm_shut",        .desc = "stream shutdown" },
#define           FCGI_EV_STRM_END      (1ULL << 36)
	{ .mask = FCGI_EV_STRM_END,     .name = "strm_end",         .desc = "detaching app-layer stream" },
#define           FCGI_EV_STRM_ERR      (1ULL << 37)
	{ .mask = FCGI_EV_STRM_ERR,     .name = "strm_err",         .desc = "stream error" },

	{ }
};

static const struct name_desc fcgi_trace_lockon_args[4] = {
	/* arg1 */ { /* already used by the connection */ },
	/* arg2 */ { .name="fstrm", .desc="FCGI stream" },
	/* arg3 */ { },
	/* arg4 */ { }
};


static const struct name_desc fcgi_trace_decoding[] = {
#define FCGI_VERB_CLEAN    1
	{ .name="clean",    .desc="only user-friendly stuff, generally suitable for level \"user\"" },
#define FCGI_VERB_MINIMAL  2
	{ .name="minimal",  .desc="report only fconn/fstrm state and flags, no real decoding" },
#define FCGI_VERB_SIMPLE   3
	{ .name="simple",   .desc="add request/response status line or htx info when available" },
#define FCGI_VERB_ADVANCED 4
	{ .name="advanced", .desc="add header fields or record decoding when available" },
#define FCGI_VERB_COMPLETE 5
	{ .name="complete", .desc="add full data dump when available" },
	{ /* end */ }
};

static struct trace_source trace_fcgi __read_mostly = {
	.name = IST("fcgi"),
	.desc = "FastCGI multiplexer",
	.arg_def = TRC_ARG1_CONN,  // TRACE()'s first argument is always a connection
	.default_cb = fcgi_trace,
	.known_events = fcgi_trace_events,
	.lockon_args = fcgi_trace_lockon_args,
	.decoding = fcgi_trace_decoding,
	.report_events = ~0,  // report everything by default
};

#define TRACE_SOURCE &trace_fcgi
INITCALL1(STG_REGISTER, trace_register_source, TRACE_SOURCE);

/* FCGI connection and stream pools */
DECLARE_STATIC_POOL(pool_head_fcgi_conn, "fcgi_conn", sizeof(struct fcgi_conn));
DECLARE_STATIC_POOL(pool_head_fcgi_strm, "fcgi_strm", sizeof(struct fcgi_strm));

struct task *fcgi_timeout_task(struct task *t, void *context, unsigned int state);
static int fcgi_process(struct fcgi_conn *fconn);
/* fcgi_io_cb is exported to see it resolved in "show fd" */
struct task *fcgi_io_cb(struct task *t, void *ctx, unsigned int state);
static inline struct fcgi_strm *fcgi_conn_st_by_id(struct fcgi_conn *fconn, int id);
struct task *fcgi_deferred_shut(struct task *t, void *ctx, unsigned int state);
static struct fcgi_strm *fcgi_conn_stream_new(struct fcgi_conn *fconn, struct conn_stream *cs, struct session *sess);
static void fcgi_strm_notify_recv(struct fcgi_strm *fstrm);
static void fcgi_strm_notify_send(struct fcgi_strm *fstrm);
static void fcgi_strm_alert(struct fcgi_strm *fstrm);
static int fcgi_strm_send_abort(struct fcgi_conn *fconn, struct fcgi_strm *fstrm);

/* a dmumy management stream */
static const struct fcgi_strm *fcgi_mgmt_stream = &(const struct fcgi_strm){
	.cs        = NULL,
	.fconn     = NULL,
	.state     = FCGI_SS_CLOSED,
	.flags     = FCGI_SF_NONE,
	.id        = 0,
};

/* and a dummy idle stream for use with any unknown stream */
static const struct fcgi_strm *fcgi_unknown_stream = &(const struct fcgi_strm){
	.cs        = NULL,
	.fconn     = NULL,
	.state     = FCGI_SS_IDLE,
	.flags     = FCGI_SF_NONE,
	.id        = 0,
};

/* returns a fconn state as an abbreviated 3-letter string, or "???" if unknown */
static inline const char *fconn_st_to_str(enum fcgi_conn_st st)
{
	switch (st) {
		case FCGI_CS_INIT     : return "INI";
		case FCGI_CS_SETTINGS : return "STG";
		case FCGI_CS_RECORD_H : return "RDH";
		case FCGI_CS_RECORD_D : return "RDD";
		case FCGI_CS_RECORD_P : return "RDP";
		case FCGI_CS_CLOSED   : return "CLO";
		default               : return "???";
	}
}

/* returns a fstrm state as an abbreviated 3-letter string, or "???" if unknown */
static inline const char *fstrm_st_to_str(enum fcgi_strm_st st)
{
	switch (st) {
		case FCGI_SS_IDLE   : return "IDL";
		case FCGI_SS_OPEN   : return "OPN";
		case FCGI_SS_HREM   : return "RCL";
		case FCGI_SS_HLOC   : return "HCL";
		case FCGI_SS_ERROR  : return "ERR";
		case FCGI_SS_CLOSED : return "CLO";
		default             : return "???";
	}
}


/* the FCGI traces always expect that arg1, if non-null, is of type connection
 * (from which we can derive fconn), that arg2, if non-null, is of type fstrm,
 * and that arg3, if non-null, is a htx for rx/tx headers.
 */
static void fcgi_trace(enum trace_level level, uint64_t mask, const struct trace_source *src,
		       const struct ist where, const struct ist func,
		       const void *a1, const void *a2, const void *a3, const void *a4)
{
	const struct connection *conn = a1;
	const struct fcgi_conn *fconn = conn ? conn->ctx : NULL;
	const struct fcgi_strm *fstrm = a2;
	const struct htx *htx = a3;
	const size_t     *val = a4;

	if (!fconn)
		fconn = (fstrm ? fstrm->fconn : NULL);

	if (!fconn || src->verbosity < FCGI_VERB_CLEAN)
		return;

	/* Display the response state if fstrm is defined */
	if (fstrm)
		chunk_appendf(&trace_buf, " [rsp:%s]", h1m_state_str(fstrm->h1m.state));

	if (src->verbosity == FCGI_VERB_CLEAN)
		return;

	/* Display the value to the 4th argument (level > STATE) */
	if (src->level > TRACE_LEVEL_STATE && val)
		chunk_appendf(&trace_buf, " - VAL=%lu", (long)*val);

	/* Display status-line if possible (verbosity > MINIMAL) */
	if (src->verbosity > FCGI_VERB_MINIMAL && htx && htx_nbblks(htx)) {
		const struct htx_blk *blk = htx_get_head_blk(htx);
		const struct htx_sl  *sl  = htx_get_blk_ptr(htx, blk);
		enum htx_blk_type    type = htx_get_blk_type(blk);

		if (type == HTX_BLK_REQ_SL || type == HTX_BLK_RES_SL)
			chunk_appendf(&trace_buf, " - \"%.*s %.*s %.*s\"",
				      HTX_SL_P1_LEN(sl), HTX_SL_P1_PTR(sl),
				      HTX_SL_P2_LEN(sl), HTX_SL_P2_PTR(sl),
				      HTX_SL_P3_LEN(sl), HTX_SL_P3_PTR(sl));
	}

	/* Display fconn info and, if defined, fstrm info */
	chunk_appendf(&trace_buf, " - fconn=%p(%s,0x%08x)", fconn, fconn_st_to_str(fconn->state), fconn->flags);
	if (fstrm)
		chunk_appendf(&trace_buf, " fstrm=%p(%d,%s,0x%08x)", fstrm, fstrm->id, fstrm_st_to_str(fstrm->state), fstrm->flags);

	if (!fstrm || fstrm->id <= 0)
		chunk_appendf(&trace_buf, " dsi=%d", fconn->dsi);
	if (fconn->dsi >= 0 && (mask & FCGI_EV_RX_FHDR))
		chunk_appendf(&trace_buf, " drt=%s", fcgi_rt_str(fconn->drt));

	if (src->verbosity == FCGI_VERB_MINIMAL)
		return;

	/* Display mbuf and dbuf info (level > USER & verbosity > SIMPLE) */
	if (src->level > TRACE_LEVEL_USER) {
		if (src->verbosity == FCGI_VERB_COMPLETE ||
		    (src->verbosity == FCGI_VERB_ADVANCED && (mask & (FCGI_EV_FCONN_RECV|FCGI_EV_RX_RECORD))))
			chunk_appendf(&trace_buf, " dbuf=%u@%p+%u/%u",
				      (unsigned int)b_data(&fconn->dbuf), b_orig(&fconn->dbuf),
				      (unsigned int)b_head_ofs(&fconn->dbuf), (unsigned int)b_size(&fconn->dbuf));
		if (src->verbosity == FCGI_VERB_COMPLETE ||
		    (src->verbosity == FCGI_VERB_ADVANCED && (mask & (FCGI_EV_FCONN_SEND|FCGI_EV_TX_RECORD)))) {
			struct buffer *hmbuf = br_head((struct buffer *)fconn->mbuf);
			struct buffer *tmbuf = br_tail((struct buffer *)fconn->mbuf);

			chunk_appendf(&trace_buf, " .mbuf=[%u..%u|%u],h=[%u@%p+%u/%u],t=[%u@%p+%u/%u]",
				      br_head_idx(fconn->mbuf), br_tail_idx(fconn->mbuf), br_size(fconn->mbuf),
				      (unsigned int)b_data(hmbuf), b_orig(hmbuf),
				      (unsigned int)b_head_ofs(hmbuf), (unsigned int)b_size(hmbuf),
				      (unsigned int)b_data(tmbuf), b_orig(tmbuf),
				      (unsigned int)b_head_ofs(tmbuf), (unsigned int)b_size(tmbuf));
		}

		if (fstrm && (src->verbosity == FCGI_VERB_COMPLETE ||
			      (src->verbosity == FCGI_VERB_ADVANCED && (mask & (FCGI_EV_STRM_RECV|FCGI_EV_RSP_DATA)))))
			chunk_appendf(&trace_buf, " rxbuf=%u@%p+%u/%u",
				      (unsigned int)b_data(&fstrm->rxbuf), b_orig(&fstrm->rxbuf),
				      (unsigned int)b_head_ofs(&fstrm->rxbuf), (unsigned int)b_size(&fstrm->rxbuf));
	}

	/* Display htx info if defined (level > USER) */
	if (src->level > TRACE_LEVEL_USER && htx) {
		int full = 0;

		/* Full htx info (level > STATE && verbosity > SIMPLE) */
		if (src->level > TRACE_LEVEL_STATE) {
			if (src->verbosity == FCGI_VERB_COMPLETE)
				full = 1;
			else if (src->verbosity == FCGI_VERB_ADVANCED && (mask & (FCGI_EV_RSP_HDRS|FCGI_EV_TX_PARAMS)))
				full = 1;
		}

		chunk_memcat(&trace_buf, "\n\t", 2);
		htx_dump(&trace_buf, htx, full);
	}
}

/*****************************************************/
/* functions below are for dynamic buffer management */
/*****************************************************/

/* Indicates whether or not the we may call the fcgi_recv() function to attempt
 * to receive data into the buffer and/or demux pending data. The condition is
 * a bit complex due to some API limits for now. The rules are the following :
 *   - if an error or a shutdown was detected on the connection and the buffer
 *     is empty, we must not attempt to receive
 *   - if the demux buf failed to be allocated, we must not try to receive and
 *     we know there is nothing pending
 *   - if no flag indicates a blocking condition, we may attempt to receive,
 *     regardless of whether the demux buffer is full or not, so that only
 *     de demux part decides whether or not to block. This is needed because
 *     the connection API indeed prevents us from re-enabling receipt that is
 *     already enabled in a polled state, so we must always immediately stop
 *     as soon as the demux can't proceed so as never to hit an end of read
 *     with data pending in the buffers.
 *   - otherwise must may not attempt
 */
static inline int fcgi_recv_allowed(const struct fcgi_conn *fconn)
{
	if (b_data(&fconn->dbuf) == 0 &&
	    (fconn->state == FCGI_CS_CLOSED ||
	     fconn->conn->flags & CO_FL_ERROR ||
	     conn_xprt_read0_pending(fconn->conn)))
		return 0;

	if (!(fconn->flags & FCGI_CF_DEM_DALLOC) &&
	    !(fconn->flags & FCGI_CF_DEM_BLOCK_ANY))
		return 1;

	return 0;
}

/* Restarts reading on the connection if it was not enabled */
static inline void fcgi_conn_restart_reading(const struct fcgi_conn *fconn, int consider_buffer)
{
	if (!fcgi_recv_allowed(fconn))
		return;
	if ((!consider_buffer || !b_data(&fconn->dbuf)) &&
	    (fconn->wait_event.events & SUB_RETRY_RECV))
		return;
	tasklet_wakeup(fconn->wait_event.tasklet);
}


/* Tries to grab a buffer and to re-enable processing on mux <target>. The
 * fcgi_conn flags are used to figure what buffer was requested. It returns 1 if
 * the allocation succeeds, in which case the connection is woken up, or 0 if
 * it's impossible to wake up and we prefer to be woken up later.
 */
static int fcgi_buf_available(void *target)
{
	struct fcgi_conn *fconn = target;
	struct fcgi_strm *fstrm;

	if ((fconn->flags & FCGI_CF_DEM_DALLOC) && b_alloc(&fconn->dbuf)) {
		TRACE_STATE("unblocking fconn, dbuf allocated", FCGI_EV_FCONN_RECV|FCGI_EV_FCONN_BLK|FCGI_EV_FCONN_WAKE, fconn->conn);
		fconn->flags &= ~FCGI_CF_DEM_DALLOC;
		fcgi_conn_restart_reading(fconn, 1);
		return 1;
	}

	if ((fconn->flags & FCGI_CF_MUX_MALLOC) && b_alloc(br_tail(fconn->mbuf))) {
		TRACE_STATE("unblocking fconn, mbuf allocated", FCGI_EV_FCONN_SEND|FCGI_EV_FCONN_BLK|FCGI_EV_FCONN_WAKE, fconn->conn);
		fconn->flags &= ~FCGI_CF_MUX_MALLOC;
		if (fconn->flags & FCGI_CF_DEM_MROOM) {
			fconn->flags &= ~FCGI_CF_DEM_MROOM;
			fcgi_conn_restart_reading(fconn, 1);
		}
		return 1;
	}

	if ((fconn->flags & FCGI_CF_DEM_SALLOC) &&
	    (fstrm = fcgi_conn_st_by_id(fconn, fconn->dsi)) && fstrm->cs &&
	    b_alloc(&fstrm->rxbuf)) {
		TRACE_STATE("unblocking fstrm, rxbuf allocated", FCGI_EV_STRM_RECV|FCGI_EV_FSTRM_BLK|FCGI_EV_STRM_WAKE, fconn->conn, fstrm);
		fconn->flags &= ~FCGI_CF_DEM_SALLOC;
		fcgi_conn_restart_reading(fconn, 1);
		fcgi_strm_notify_recv(fstrm);
		return 1;
	}

	return 0;
}

static inline struct buffer *fcgi_get_buf(struct fcgi_conn *fconn, struct buffer *bptr)
{
	struct buffer *buf = NULL;

	if (likely(!LIST_INLIST(&fconn->buf_wait.list)) &&
	    unlikely((buf = b_alloc(bptr)) == NULL)) {
		fconn->buf_wait.target = fconn;
		fconn->buf_wait.wakeup_cb = fcgi_buf_available;
		LIST_APPEND(&ti->buffer_wq, &fconn->buf_wait.list);
	}
	return buf;
}

static inline void fcgi_release_buf(struct fcgi_conn *fconn, struct buffer *bptr)
{
	if (bptr->size) {
		b_free(bptr);
		offer_buffers(NULL, 1);
	}
}

static inline void fcgi_release_mbuf(struct fcgi_conn *fconn)
{
	struct buffer *buf;
	unsigned int count = 0;

	while (b_size(buf = br_head_pick(fconn->mbuf))) {
		b_free(buf);
		count++;
	}
	if (count)
		offer_buffers(NULL, count);
}

/* Returns the number of allocatable outgoing streams for the connection taking
 * the number reserved streams into account.
 */
static inline int fcgi_streams_left(const struct fcgi_conn *fconn)
{
	int ret;

	ret = (unsigned int)(0x7FFF - fconn->max_id) - fconn->nb_reserved - 1;
	if (ret < 0)
		ret = 0;
	return ret;
}

/* Returns the number of streams in use on a connection to figure if it's
 * idle or not. We check nb_cs and not nb_streams as the caller will want
 * to know if it was the last one after a detach().
 */
static int fcgi_used_streams(struct connection *conn)
{
	struct fcgi_conn *fconn = conn->ctx;

	return fconn->nb_cs;
}

/* Returns the number of concurrent streams available on the connection */
static int fcgi_avail_streams(struct connection *conn)
{
	struct server *srv = objt_server(conn->target);
	struct fcgi_conn *fconn = conn->ctx;
	int ret1, ret2;

	/* Don't open new stream if the connection is closed */
	if (fconn->state == FCGI_CS_CLOSED)
		return 0;

	/* May be negative if this setting has changed */
	ret1 = (fconn->streams_limit - fconn->nb_streams);

	/* we must also consider the limit imposed by stream IDs */
	ret2 = fcgi_streams_left(fconn);
	ret1 = MIN(ret1, ret2);
	if (ret1 > 0 && srv && srv->max_reuse >= 0) {
		ret2 = ((fconn->stream_cnt <= srv->max_reuse) ? srv->max_reuse - fconn->stream_cnt + 1: 0);
		ret1 = MIN(ret1, ret2);
	}
	return ret1;
}

/*****************************************************************/
/* functions below are dedicated to the mux setup and management */
/*****************************************************************/

/* Initializes the mux once it's attached. Only outgoing connections are
 * supported. So the context is already initialized before installing the
 * mux. <input> is always used as Input buffer and may contain data. It is the
 * caller responsibility to not reuse it anymore. Returns < 0 on error.
 */
static int fcgi_init(struct connection *conn, struct proxy *px, struct session *sess,
		     struct buffer *input)
{
	struct fcgi_conn *fconn;
	struct fcgi_strm *fstrm;
	struct fcgi_app *app = get_px_fcgi_app(px);
	struct task *t = NULL;
	void *conn_ctx = conn->ctx;

	TRACE_ENTER(FCGI_EV_FSTRM_NEW);

	if (!app) {
		TRACE_ERROR("No FCGI app found, don't create fconn", FCGI_EV_FCONN_NEW|FCGI_EV_FCONN_END|FCGI_EV_FCONN_ERR);
		goto fail_conn;
	}

	fconn = pool_alloc(pool_head_fcgi_conn);
	if (!fconn) {
		TRACE_ERROR("fconn allocation failure", FCGI_EV_FCONN_NEW|FCGI_EV_FCONN_END|FCGI_EV_FCONN_ERR);
		goto fail_conn;
	}

	fconn->shut_timeout = fconn->timeout = px->timeout.server;
	if (tick_isset(px->timeout.serverfin))
		fconn->shut_timeout = px->timeout.serverfin;

	fconn->flags = FCGI_CF_NONE;

	/* Retrieve useful info from the FCGI app */
	if (app->flags & FCGI_APP_FL_KEEP_CONN)
		fconn->flags |= FCGI_CF_KEEP_CONN;
	if (app->flags & FCGI_APP_FL_GET_VALUES)
		fconn->flags |= FCGI_CF_GET_VALUES;
	if (app->flags & FCGI_APP_FL_MPXS_CONNS)
		fconn->flags |= FCGI_CF_MPXS_CONNS;

	fconn->proxy = px;
	fconn->app = app;
	fconn->task = NULL;
	if (tick_isset(fconn->timeout)) {
		t = task_new(tid_bit);
		if (!t) {
			TRACE_ERROR("fconn task allocation failure", FCGI_EV_FCONN_NEW|FCGI_EV_FCONN_END|FCGI_EV_FCONN_ERR);
			goto fail;
		}

		fconn->task = t;
		t->process = fcgi_timeout_task;
		t->context = fconn;
		t->expire = tick_add(now_ms, fconn->timeout);
	}

	fconn->wait_event.tasklet = tasklet_new();
	if (!fconn->wait_event.tasklet)
		goto fail;
	fconn->wait_event.tasklet->process = fcgi_io_cb;
	fconn->wait_event.tasklet->context = fconn;
	fconn->wait_event.events = 0;

	/* Initialise the context. */
	fconn->state = FCGI_CS_INIT;
	fconn->conn = conn;
	fconn->streams_limit = app->maxreqs;
	fconn->max_id = -1;
	fconn->nb_streams = 0;
	fconn->nb_cs = 0;
	fconn->nb_reserved = 0;
	fconn->stream_cnt = 0;

	fconn->dbuf = *input;
	fconn->dsi = -1;

	br_init(fconn->mbuf, sizeof(fconn->mbuf) / sizeof(fconn->mbuf[0]));
	fconn->streams_by_id = EB_ROOT;
	LIST_INIT(&fconn->send_list);
	LIST_INIT(&fconn->buf_wait.list);

	conn->ctx = fconn;

	if (t)
		task_queue(t);

	/* FIXME: this is temporary, for outgoing connections we need to
	 * immediately allocate a stream until the code is modified so that the
	 * caller calls ->attach(). For now the outgoing cs is stored as
	 * conn->ctx by the caller and saved in conn_ctx.
	 */
	fstrm = fcgi_conn_stream_new(fconn, conn_ctx, sess);
	if (!fstrm)
		goto fail;


	/* Repare to read something */
	fcgi_conn_restart_reading(fconn, 1);
	TRACE_LEAVE(FCGI_EV_FCONN_NEW, conn);
	return 0;

  fail:
	task_destroy(t);
	if (fconn->wait_event.tasklet)
		tasklet_free(fconn->wait_event.tasklet);
	pool_free(pool_head_fcgi_conn, fconn);
  fail_conn:
	conn->ctx = conn_ctx; // restore saved ctx
	TRACE_DEVEL("leaving in error", FCGI_EV_FCONN_NEW|FCGI_EV_FCONN_END|FCGI_EV_FCONN_ERR);
	return -1;
}

/* Returns the next allocatable outgoing stream ID for the FCGI connection, or
 * -1 if no more is allocatable.
 */
static inline int32_t fcgi_conn_get_next_sid(const struct fcgi_conn *fconn)
{
	int32_t id = (fconn->max_id + 1) | 1;

	if ((id & 0x80000000U))
		id = -1;
	return id;
}

/* Returns the stream associated with id <id> or NULL if not found */
static inline struct fcgi_strm *fcgi_conn_st_by_id(struct fcgi_conn *fconn, int id)
{
	struct eb32_node *node;

	if (id == 0)
	 	return (struct fcgi_strm *)fcgi_mgmt_stream;

	if (id > fconn->max_id)
		return (struct fcgi_strm *)fcgi_unknown_stream;

	node = eb32_lookup(&fconn->streams_by_id, id);
	if (!node)
		return (struct fcgi_strm *)fcgi_unknown_stream;
	return container_of(node, struct fcgi_strm, by_id);
}


/* Release function. This one should be called to free all resources allocated
 * to the mux.
 */
static void fcgi_release(struct fcgi_conn *fconn)
{
	struct connection *conn = NULL;

	TRACE_POINT(FCGI_EV_FCONN_END);

	if (fconn) {
		/* The connection must be attached to this mux to be released */
		if (fconn->conn && fconn->conn->ctx == fconn)
			conn = fconn->conn;

		TRACE_DEVEL("freeing fconn", FCGI_EV_FCONN_END, conn);

		if (LIST_INLIST(&fconn->buf_wait.list))
			LIST_DEL_INIT(&fconn->buf_wait.list);

		fcgi_release_buf(fconn, &fconn->dbuf);
		fcgi_release_mbuf(fconn);

		if (fconn->task) {
			fconn->task->context = NULL;
			task_wakeup(fconn->task, TASK_WOKEN_OTHER);
			fconn->task = NULL;
		}
		if (fconn->wait_event.tasklet)
			tasklet_free(fconn->wait_event.tasklet);
		if (conn && fconn->wait_event.events != 0)
			conn->xprt->unsubscribe(conn, conn->xprt_ctx, fconn->wait_event.events,
						&fconn->wait_event);

		pool_free(pool_head_fcgi_conn, fconn);
	}

	if (conn) {
		conn->mux = NULL;
		conn->ctx = NULL;
		TRACE_DEVEL("freeing conn", FCGI_EV_FCONN_END, conn);

		conn_stop_tracking(conn);
		conn_full_close(conn);
		if (conn->destroy_cb)
			conn->destroy_cb(conn);
		conn_free(conn);
	}
}

/* Detect a pending read0 for a FCGI connection. It happens if a read0 is
 * pending on the connection AND if there is no more data in the demux
 * buffer. The function returns 1 to report a read0 or 0 otherwise.
 */
static int fcgi_conn_read0_pending(struct fcgi_conn *fconn)
{
	if (conn_xprt_read0_pending(fconn->conn) && !b_data(&fconn->dbuf))
		return 1;
	return 0;
}


/* Returns true if the FCGI connection must be release */
static inline int fcgi_conn_is_dead(struct fcgi_conn *fconn)
{
	if (eb_is_empty(&fconn->streams_by_id) &&               /* don't close if streams exist */
	    (!(fconn->flags & FCGI_CF_KEEP_CONN) ||             /* don't keep the connection alive */
	     (fconn->conn->flags & CO_FL_ERROR) ||              /* errors close immediately */
	     (fconn->state == FCGI_CS_CLOSED && !fconn->task) ||/* a timeout stroke earlier */
	     (!(fconn->conn->owner)) ||                         /* Nobody's left to take care of the connection, drop it now */
	     (!br_data(fconn->mbuf) &&                          /* mux buffer empty, also process clean events below */
	      conn_xprt_read0_pending(fconn->conn))))
		return 1;
	return 0;
}


/********************************************************/
/* functions below are for the FCGI protocol processing */
/********************************************************/

/* Marks an error on the stream. */
static inline void fcgi_strm_error(struct fcgi_strm *fstrm)
{
	if (fstrm->id && fstrm->state != FCGI_SS_ERROR) {
		TRACE_POINT(FCGI_EV_FSTRM_ERR, fstrm->fconn->conn, fstrm);
		if (fstrm->state < FCGI_SS_ERROR) {
			fstrm->state = FCGI_SS_ERROR;
			TRACE_STATE("switching to ERROR", FCGI_EV_FSTRM_ERR, fstrm->fconn->conn, fstrm);
		}
		if (fstrm->cs)
			cs_set_error(fstrm->cs);
	}
}

/* Attempts to notify the data layer of recv availability */
static void fcgi_strm_notify_recv(struct fcgi_strm *fstrm)
{
	if (fstrm->subs && (fstrm->subs->events & SUB_RETRY_RECV)) {
		TRACE_POINT(FCGI_EV_STRM_WAKE, fstrm->fconn->conn, fstrm);
		tasklet_wakeup(fstrm->subs->tasklet);
		fstrm->subs->events &= ~SUB_RETRY_RECV;
		if (!fstrm->subs->events)
			fstrm->subs = NULL;
	}
}

/* Attempts to notify the data layer of send availability */
static void fcgi_strm_notify_send(struct fcgi_strm *fstrm)
{
	if (fstrm->subs && (fstrm->subs->events & SUB_RETRY_SEND)) {
		TRACE_POINT(FCGI_EV_STRM_WAKE, fstrm->fconn->conn, fstrm);
		fstrm->flags |= FCGI_SF_NOTIFIED;
		tasklet_wakeup(fstrm->subs->tasklet);
		fstrm->subs->events &= ~SUB_RETRY_SEND;
		if (!fstrm->subs->events)
			fstrm->subs = NULL;
	}
	else if (fstrm->flags & (FCGI_SF_WANT_SHUTR | FCGI_SF_WANT_SHUTW)) {
		TRACE_POINT(FCGI_EV_STRM_WAKE, fstrm->fconn->conn, fstrm);
		tasklet_wakeup(fstrm->shut_tl);
	}
}

/* Alerts the data layer, trying to wake it up by all means, following
 * this sequence :
 *   - if the fcgi stream' data layer is subscribed to recv, then it's woken up
 *     for recv
 *   - if its subscribed to send, then it's woken up for send
 *   - if it was subscribed to neither, its ->wake() callback is called
 * It is safe to call this function with a closed stream which doesn't have a
 * conn_stream anymore.
 */
static void fcgi_strm_alert(struct fcgi_strm *fstrm)
{
	TRACE_POINT(FCGI_EV_STRM_WAKE, fstrm->fconn->conn, fstrm);
	if (fstrm->subs ||
	    (fstrm->flags & (FCGI_SF_WANT_SHUTR|FCGI_SF_WANT_SHUTW))) {
		fcgi_strm_notify_recv(fstrm);
		fcgi_strm_notify_send(fstrm);
	}
	else if (fstrm->cs && fstrm->cs->data_cb->wake != NULL) {
		TRACE_POINT(FCGI_EV_STRM_WAKE, fstrm->fconn->conn, fstrm);
		fstrm->cs->data_cb->wake(fstrm->cs);
	}
}

/* Writes the 16-bit record size <len> at address <record> */
static inline void fcgi_set_record_size(void *record, uint16_t len)
{
	uint8_t *out = (record + 4);

	*out       = (len >> 8);
	*(out + 1) = (len & 0xff);
}

/* Writes the 16-bit stream id <id> at address <record> */
static inline void fcgi_set_record_id(void *record, uint16_t id)
{
	uint8_t *out = (record + 2);

	*out       = (id >> 8);
	*(out + 1) = (id & 0xff);
}

/* Marks a FCGI stream as CLOSED and decrement the number of active streams for
 * its connection if the stream was not yet closed. Please use this exclusively
 * before closing a stream to ensure stream count is well maintained.
 */
static inline void fcgi_strm_close(struct fcgi_strm *fstrm)
{
	if (fstrm->state != FCGI_SS_CLOSED) {
		TRACE_ENTER(FCGI_EV_FSTRM_END, fstrm->fconn->conn, fstrm);
		fstrm->fconn->nb_streams--;
		if (!fstrm->id)
			fstrm->fconn->nb_reserved--;
		if (fstrm->cs) {
			if (!(fstrm->cs->flags & CS_FL_EOS) && !b_data(&fstrm->rxbuf))
				fcgi_strm_notify_recv(fstrm);
		}
		fstrm->state = FCGI_SS_CLOSED;
		TRACE_STATE("switching to CLOSED", FCGI_EV_FSTRM_END, fstrm->fconn->conn, fstrm);
		TRACE_LEAVE(FCGI_EV_FSTRM_END, fstrm->fconn->conn, fstrm);
	}
}

/* Detaches a FCGI stream from its FCGI connection and releases it to the
 * fcgi_strm pool.
 */
static void fcgi_strm_destroy(struct fcgi_strm *fstrm)
{
	struct connection *conn = fstrm->fconn->conn;

	TRACE_ENTER(FCGI_EV_FSTRM_END, conn, fstrm);

	fcgi_strm_close(fstrm);
	eb32_delete(&fstrm->by_id);
	if (b_size(&fstrm->rxbuf)) {
		b_free(&fstrm->rxbuf);
		offer_buffers(NULL, 1);
	}
	if (fstrm->subs)
		fstrm->subs->events = 0;
	/* There's no need to explicitly call unsubscribe here, the only
	 * reference left would be in the fconn send_list/fctl_list, and if
	 * we're in it, we're getting out anyway
	 */
	LIST_DEL_INIT(&fstrm->send_list);
	tasklet_free(fstrm->shut_tl);
	pool_free(pool_head_fcgi_strm, fstrm);

	TRACE_LEAVE(FCGI_EV_FSTRM_END, conn);
}

/* Allocates a new stream <id> for connection <fconn> and adds it into fconn's
 * stream tree. In case of error, nothing is added and NULL is returned. The
 * causes of errors can be any failed memory allocation. The caller is
 * responsible for checking if the connection may support an extra stream prior
 * to calling this function.
 */
static struct fcgi_strm *fcgi_strm_new(struct fcgi_conn *fconn, int id)
{
	struct fcgi_strm *fstrm;

	TRACE_ENTER(FCGI_EV_FSTRM_NEW, fconn->conn);

	fstrm = pool_alloc(pool_head_fcgi_strm);
	if (!fstrm) {
		TRACE_ERROR("fstrm allocation failure", FCGI_EV_FSTRM_NEW|FCGI_EV_FSTRM_ERR|FCGI_EV_FSTRM_END, fconn->conn);
		goto out;
	}

	fstrm->shut_tl = tasklet_new();
	if (!fstrm->shut_tl) {
		TRACE_ERROR("fstrm shut tasklet allocation failure", FCGI_EV_FSTRM_NEW|FCGI_EV_FSTRM_ERR|FCGI_EV_FSTRM_END, fconn->conn);
		pool_free(pool_head_fcgi_strm, fstrm);
		goto out;
	}
	fstrm->subs = NULL;
	fstrm->shut_tl->process = fcgi_deferred_shut;
	fstrm->shut_tl->context = fstrm;
	LIST_INIT(&fstrm->send_list);
	fstrm->fconn = fconn;
	fstrm->cs = NULL;
	fstrm->flags = FCGI_SF_NONE;
	fstrm->proto_status = 0;
	fstrm->state = FCGI_SS_IDLE;
	fstrm->rxbuf = BUF_NULL;

	h1m_init_res(&fstrm->h1m);
	fstrm->h1m.err_pos = -1; // don't care about errors on the request path
	fstrm->h1m.flags |= (H1_MF_NO_PHDR|H1_MF_CLEAN_CONN_HDR);

	fstrm->by_id.key = fstrm->id = id;
	if (id > 0)
		fconn->max_id = id;
	else
		fconn->nb_reserved++;

	eb32_insert(&fconn->streams_by_id, &fstrm->by_id);
	fconn->nb_streams++;
	fconn->stream_cnt++;

	TRACE_LEAVE(FCGI_EV_FSTRM_NEW, fconn->conn, fstrm);
	return fstrm;

  out:
	TRACE_DEVEL("leaving in error", FCGI_EV_FSTRM_NEW|FCGI_EV_FSTRM_ERR|FCGI_EV_FSTRM_END, fconn->conn);
	return NULL;
}

/* Allocates a new stream associated to conn_stream <cs> on the FCGI connection
 * <fconn> and returns it, or NULL in case of memory allocation error or if the
 * highest possible stream ID was reached.
 */
static struct fcgi_strm *fcgi_conn_stream_new(struct fcgi_conn *fconn, struct conn_stream *cs,
					      struct session *sess)
{
	struct fcgi_strm *fstrm = NULL;

	TRACE_ENTER(FCGI_EV_FSTRM_NEW, fconn->conn);
	if (fconn->nb_streams >= fconn->streams_limit) {
		TRACE_ERROR("streams_limit reached", FCGI_EV_FSTRM_NEW|FCGI_EV_FSTRM_END|FCGI_EV_FSTRM_ERR, fconn->conn);
		goto out;
	}

	if (fcgi_streams_left(fconn) < 1) {
		TRACE_ERROR("!streams_left", FCGI_EV_FSTRM_NEW|FCGI_EV_FSTRM_END|FCGI_EV_FSTRM_ERR, fconn->conn);
		goto out;
	}

	/* Defer choosing the ID until we send the first message to create the stream */
	fstrm = fcgi_strm_new(fconn, 0);
	if (!fstrm) {
		TRACE_ERROR("fstream allocation failure", FCGI_EV_FSTRM_NEW|FCGI_EV_FSTRM_END|FCGI_EV_FSTRM_ERR, fconn->conn);
		goto out;
	}

	fstrm->cs = cs;
	fstrm->sess = sess;
	cs->ctx = fstrm;
	fconn->nb_cs++;

	TRACE_LEAVE(FCGI_EV_FSTRM_NEW, fconn->conn, fstrm);
	return fstrm;

  out:
	TRACE_DEVEL("leaving on error", FCGI_EV_FSTRM_NEW|FCGI_EV_FSTRM_END|FCGI_EV_FSTRM_ERR, fconn->conn);
	return NULL;
}

/* Wakes a specific stream and assign its conn_stream some CS_FL_* flags among
 * CS_FL_ERR_PENDING and CS_FL_ERROR if needed. The stream's state is
 * automatically updated accordingly. If the stream is orphaned, it is
 * destroyed.
 */
static void fcgi_strm_wake_one_stream(struct fcgi_strm *fstrm)
{
	struct fcgi_conn *fconn = fstrm->fconn;

	TRACE_ENTER(FCGI_EV_STRM_WAKE, fconn->conn, fstrm);

	if (!fstrm->cs) {
		/* this stream was already orphaned */
		fcgi_strm_destroy(fstrm);
		TRACE_DEVEL("leaving with no fstrm", FCGI_EV_STRM_WAKE, fconn->conn);
		return;
	}

	if (fcgi_conn_read0_pending(fconn)) {
		if (fstrm->state == FCGI_SS_OPEN) {
			fstrm->state = FCGI_SS_HREM;
			TRACE_STATE("switching to HREM", FCGI_EV_STRM_WAKE|FCGI_EV_FSTRM_END, fconn->conn, fstrm);
		}
		else if (fstrm->state == FCGI_SS_HLOC)
			fcgi_strm_close(fstrm);
	}

	if ((fconn->state == FCGI_CS_CLOSED || fconn->conn->flags & CO_FL_ERROR)) {
		fstrm->cs->flags |= CS_FL_ERR_PENDING;
		if (fstrm->cs->flags & CS_FL_EOS)
			fstrm->cs->flags |= CS_FL_ERROR;

		if (fstrm->state < FCGI_SS_ERROR) {
			fstrm->state = FCGI_SS_ERROR;
			TRACE_STATE("switching to ERROR", FCGI_EV_STRM_WAKE|FCGI_EV_FSTRM_END, fconn->conn, fstrm);
		}
	}

	fcgi_strm_alert(fstrm);

	TRACE_LEAVE(FCGI_EV_STRM_WAKE, fconn->conn, fstrm);
}

/* Wakes unassigned streams (ID == 0) attached to the connection. */
static void fcgi_wake_unassigned_streams(struct fcgi_conn *fconn)
{
	struct eb32_node *node;
	struct fcgi_strm *fstrm;

	node = eb32_lookup(&fconn->streams_by_id, 0);
	while (node) {
		fstrm = container_of(node, struct fcgi_strm, by_id);
		if (fstrm->id > 0)
			break;
		node = eb32_next(node);
		fcgi_strm_wake_one_stream(fstrm);
	}
}

/* Wakes the streams attached to the connection, whose id is greater than <last>
 * or unassigned.
 */
static void fcgi_wake_some_streams(struct fcgi_conn *fconn, int last)
{
	struct eb32_node *node;
	struct fcgi_strm *fstrm;

	TRACE_ENTER(FCGI_EV_STRM_WAKE, fconn->conn);

	/* Wake all streams with ID > last */
	node = eb32_lookup_ge(&fconn->streams_by_id, last + 1);
	while (node) {
		fstrm = container_of(node, struct fcgi_strm, by_id);
		node = eb32_next(node);
		fcgi_strm_wake_one_stream(fstrm);
	}
	fcgi_wake_unassigned_streams(fconn);

	TRACE_LEAVE(FCGI_EV_STRM_WAKE, fconn->conn);
}

static int fcgi_set_default_param(struct fcgi_conn *fconn, struct fcgi_strm *fstrm,
				  struct htx *htx, struct htx_sl *sl,
				  struct fcgi_strm_params *params)
{
	struct connection *cli_conn = objt_conn(fstrm->sess->origin);
	struct ist p;

	if (!sl)
		goto error;

	if (!(params->mask & FCGI_SP_DOC_ROOT))
		params->docroot = fconn->app->docroot;

	if (!(params->mask & FCGI_SP_REQ_METH)) {
		p  = htx_sl_req_meth(sl);
		params->meth = ist2(b_tail(params->p), p.len);
		chunk_memcat(params->p, p.ptr, p.len);
	}
	if (!(params->mask & FCGI_SP_REQ_URI)) {
		p = h1_get_uri(sl);
		params->uri = ist2(b_tail(params->p), p.len);
		chunk_memcat(params->p, p.ptr, p.len);
	}
	if (!(params->mask & FCGI_SP_SRV_PROTO)) {
		p  = htx_sl_req_vsn(sl);
		params->vsn = ist2(b_tail(params->p), p.len);
		chunk_memcat(params->p, p.ptr, p.len);
	}
	if (!(params->mask & FCGI_SP_SRV_PORT)) {
		char *end;
		int port = 0;
		if (cli_conn && conn_get_dst(cli_conn))
			port = get_host_port(cli_conn->dst);
		end = ultoa_o(port, b_tail(params->p), b_room(params->p));
		if (!end)
			goto error;
		params->srv_port = ist2(b_tail(params->p), end - b_tail(params->p));
		params->p->data += params->srv_port.len;
	}
	if (!(params->mask & FCGI_SP_SRV_NAME)) {
		/* If no Host header found, use the server address to fill
		 * srv_name */
		if (!istlen(params->srv_name)) {
			char *ptr = NULL;

			if (cli_conn && conn_get_dst(cli_conn))
				if (addr_to_str(cli_conn->dst, b_tail(params->p), b_room(params->p)) != -1)
					ptr = b_tail(params->p);
			if (ptr) {
				params->srv_name = ist(ptr);
				params->p->data += params->srv_name.len;
			}
		}
	}
	if (!(params->mask & FCGI_SP_REM_ADDR)) {
		char *ptr = NULL;

		if (cli_conn && conn_get_src(cli_conn))
			if (addr_to_str(cli_conn->src, b_tail(params->p), b_room(params->p)) != -1)
				ptr = b_tail(params->p);
		if (ptr) {
			params->rem_addr = ist(ptr);
			params->p->data += params->rem_addr.len;
		}
	}
	if (!(params->mask & FCGI_SP_REM_PORT)) {
		char *end;
		int port = 0;
		if (cli_conn && conn_get_src(cli_conn))
			port = get_host_port(cli_conn->src);
		end = ultoa_o(port, b_tail(params->p), b_room(params->p));
		if (!end)
			goto error;
		params->rem_port = ist2(b_tail(params->p), end - b_tail(params->p));
		params->p->data += params->rem_port.len;
	}
	if (!(params->mask & FCGI_SP_CONT_LEN)) {
		struct htx_blk *blk;
		enum htx_blk_type type;
		char *end;
		size_t len = 0;

		for (blk = htx_get_head_blk(htx); blk; blk = htx_get_next_blk(htx, blk)) {
			type = htx_get_blk_type(blk);

			if (type == HTX_BLK_TLR || type == HTX_BLK_EOT)
				break;
			if (type == HTX_BLK_DATA)
				len += htx_get_blksz(blk);
		}
		end = ultoa_o(len, b_tail(params->p), b_room(params->p));
		if (!end)
			goto error;
		params->cont_len = ist2(b_tail(params->p), end - b_tail(params->p));
		params->p->data += params->cont_len.len;
	}
#ifdef USE_OPENSSL
	if (!(params->mask & FCGI_SP_HTTPS)) {
		if (cli_conn)
			params->https = ssl_sock_is_ssl(cli_conn);
	}
#endif
	if ((params->mask & FCGI_SP_URI_MASK) != FCGI_SP_URI_MASK) {
		/* one of scriptname, pathinfo or query_string is no set */
		struct ist path = http_get_path(params->uri);
		int len;

		/* No scrit_name set but no valid path ==> error */
		if (!(params->mask & FCGI_SP_SCRIPT_NAME) && !istlen(path))
			goto error;

		/* If there is a query-string, Set it if not already set */
		if (!(params->mask & FCGI_SP_REQ_QS)) {
			struct ist qs = istfind(path, '?');

			/* Update the path length */
			path.len -= qs.len;

			/* Set the query-string skipping the '?', if any */
			if (istlen(qs))
				params->qs = istnext(qs);
		}

		/* If the script_name is set, don't try to deduce the path_info
		 * too. The opposite is not true.
		 */
		if (params->mask & FCGI_SP_SCRIPT_NAME) {
			params->mask |= FCGI_SP_PATH_INFO;
			goto end;
		}

		/* Decode the path. it must first be copied to keep the URI
		 * untouched.
		 */
		chunk_memcat(params->p, path.ptr, path.len);
		path.ptr = b_tail(params->p) - path.len;
		len = url_decode(ist0(path), 0);
		if (len < 0)
			goto error;
		path.len = len;

		/* script_name not set, preset it with the path for now */
		params->scriptname = path;

		/* If there is no regex to match the pathinfo, just to the last
		 * part and see if the index must be used.
		 */
		if (!fconn->app->pathinfo_re)
			goto check_index;

		/* If some special characters are found in the decoded path (\n
		 * or \0), the PATH_INFO regex cannot match. This is theorically
		 * valid, but probably unexpected, to have such characters. So,
		 * to avoid any surprises, an error is triggered in this
		 * case.
		 */
		if (istchr(path, '\n') || istchr(path, '\0'))
			goto error;

		/* The regex does not match, just to the last part and see if
		 * the index must be used.
		 */
		if (!regex_exec_match2(fconn->app->pathinfo_re, path.ptr, len, MAX_MATCH, pmatch, 0))
			goto check_index;

		/* We must have at least 1 capture for the script name,
		 * otherwise we do nothing and jump to the last part.
		 */
		if (pmatch[1].rm_so == -1 || pmatch[1].rm_eo == -1)
			goto check_index;

		/* Finally we can set the script_name and the path_info. The
		 * path_info is set if not already defined, and if it was
		 * captured
		 */
		params->scriptname = ist2(path.ptr + pmatch[1].rm_so, pmatch[1].rm_eo - pmatch[1].rm_so);
		if (!(params->mask & FCGI_SP_PATH_INFO) &&  (pmatch[2].rm_so == -1 || pmatch[2].rm_eo == -1))
			params->pathinfo = ist2(path.ptr + pmatch[2].rm_so, pmatch[2].rm_eo - pmatch[2].rm_so);

	  check_index:
		len = params->scriptname.len;
		/* the script_name if finished by a '/' so we can add the index
		 * part, if any.
		 */
		if (istlen(fconn->app->index) && params->scriptname.ptr[len-1] == '/') {
			struct ist sn = params->scriptname;

			params->scriptname = ist2(b_tail(params->p), len+fconn->app->index.len);
			chunk_memcat(params->p, sn.ptr, sn.len);
			chunk_memcat(params->p, fconn->app->index.ptr, fconn->app->index.len);
		}
	}

  end:
	return 1;
  error:
	return 0;
}

static int fcgi_encode_default_param(struct fcgi_conn *fconn, struct fcgi_strm *fstrm,
				     struct fcgi_strm_params *params, struct buffer *outbuf, int flag)
{
	struct fcgi_param p;

	if (params->mask & flag)
		return 1;

	chunk_reset(&trash);

	switch (flag) {
		case FCGI_SP_CGI_GATEWAY:
			p.n = ist("GATEWAY_INTERFACE");
			p.v = ist("CGI/1.1");
			goto encode;
		case FCGI_SP_DOC_ROOT:
			p.n = ist("DOCUMENT_ROOT");
			p.v = params->docroot;
			goto encode;
		case FCGI_SP_SCRIPT_NAME:
			p.n = ist("SCRIPT_NAME");
			p.v = params->scriptname;
			goto encode;
		case FCGI_SP_PATH_INFO:
			p.n = ist("PATH_INFO");
			p.v = params->pathinfo;
			goto encode;
		case FCGI_SP_REQ_URI:
			p.n = ist("REQUEST_URI");
			p.v = params->uri;
			goto encode;
		case FCGI_SP_REQ_METH:
			p.n = ist("REQUEST_METHOD");
			p.v = params->meth;
			goto encode;
		case FCGI_SP_REQ_QS:
			p.n = ist("QUERY_STRING");
			p.v = params->qs;
			goto encode;
		case FCGI_SP_SRV_NAME:
			p.n = ist("SERVER_NAME");
			p.v = params->srv_name;
			goto encode;
		case FCGI_SP_SRV_PORT:
			p.n = ist("SERVER_PORT");
			p.v = params->srv_port;
			goto encode;
		case FCGI_SP_SRV_PROTO:
			p.n = ist("SERVER_PROTOCOL");
			p.v = params->vsn;
			goto encode;
		case FCGI_SP_REM_ADDR:
			p.n = ist("REMOTE_ADDR");
			p.v = params->rem_addr;
			goto encode;
		case FCGI_SP_REM_PORT:
			p.n = ist("REMOTE_PORT");
			p.v = params->rem_port;
			goto encode;
		case FCGI_SP_SCRIPT_FILE:
			p.n = ist("SCRIPT_FILENAME");
			chunk_memcat(&trash, params->docroot.ptr, params->docroot.len);
			chunk_memcat(&trash, params->scriptname.ptr, params->scriptname.len);
			p.v = ist2(b_head(&trash), b_data(&trash));
			goto encode;
		case FCGI_SP_PATH_TRANS:
			if (!istlen(params->pathinfo))
				goto skip;
			p.n = ist("PATH_TRANSLATED");
			chunk_memcat(&trash, params->docroot.ptr, params->docroot.len);
			chunk_memcat(&trash, params->pathinfo.ptr, params->pathinfo.len);
			p.v = ist2(b_head(&trash), b_data(&trash));
			goto encode;
		case FCGI_SP_CONT_LEN:
			p.n = ist("CONTENT_LENGTH");
			p.v = params->cont_len;
			goto encode;
		case FCGI_SP_HTTPS:
			if (!params->https)
				goto skip;
			p.n = ist("HTTPS");
			p.v = ist("on");
			goto encode;
		default:
			goto skip;
	}

  encode:
	if (!istlen(p.v))
		goto skip;
	if (!fcgi_encode_param(outbuf, &p))
		return 0;
  skip:
	params->mask |= flag;
	return 1;
}

/* Sends a GET_VALUES record. Returns > 0 on success, 0 if it couldn't do
 * anything. It is highly unexpected, but if the record is larger than a buffer
 * and cannot be encoded in one time, an error is triggered and the connection is
 * closed. GET_VALUES record cannot be split.
 */
static int fcgi_conn_send_get_values(struct fcgi_conn *fconn)
{
	struct buffer outbuf;
	struct buffer *mbuf;
	struct fcgi_param max_reqs   = { .n = ist("FCGI_MAX_REQS"),   .v = ist("")};
	struct fcgi_param mpxs_conns = { .n = ist("FCGI_MPXS_CONNS"), .v = ist("")};
	int ret = 0;

	TRACE_ENTER(FCGI_EV_TX_RECORD|FCGI_EV_TX_GETVAL, fconn->conn);

	mbuf = br_tail(fconn->mbuf);
  retry:
	if (!fcgi_get_buf(fconn, mbuf)) {
		fconn->flags |= FCGI_CF_MUX_MALLOC;
		fconn->flags |= FCGI_CF_DEM_MROOM;
		TRACE_STATE("waiting for fconn mbuf ring allocation", FCGI_EV_TX_RECORD|FCGI_EV_FCONN_BLK, fconn->conn);
		ret = 0;
		goto end;
	}

	while (1) {
		outbuf = b_make(b_tail(mbuf), b_contig_space(mbuf), 0, 0);
		if (outbuf.size >= FCGI_RECORD_HEADER_SZ || !b_space_wraps(mbuf))
			break;
	  realign_again:
		b_slow_realign(mbuf, trash.area, b_data(mbuf));
	}

	if (outbuf.size < FCGI_RECORD_HEADER_SZ)
		goto full;

	/* vsn: 1(FCGI_VERSION), type: (9)FCGI_GET_VALUES, id: 0x0000,
	 *  len: 0x0000 (fill later), padding: 0x00, rsv: 0x00 */
	memcpy(outbuf.area, "\x01\x09\x00\x00\x00\x00\x00\x00", FCGI_RECORD_HEADER_SZ);
	outbuf.data = FCGI_RECORD_HEADER_SZ;

	/* Note: Don't send the param FCGI_MAX_CONNS because its value cannot be
	 *       handled by HAProxy.
	 */
	if (!fcgi_encode_param(&outbuf, &max_reqs) || !fcgi_encode_param(&outbuf, &mpxs_conns))
		goto full;

	/* update the record's size now */
	TRACE_PROTO("FCGI GET_VALUES record xferred", FCGI_EV_TX_RECORD|FCGI_EV_TX_GETVAL, fconn->conn, 0, 0, (size_t[]){outbuf.data-8});
	fcgi_set_record_size(outbuf.area, outbuf.data - FCGI_RECORD_HEADER_SZ);
	b_add(mbuf, outbuf.data);
	ret = 1;

  end:
	TRACE_LEAVE(FCGI_EV_TX_RECORD|FCGI_EV_TX_GETVAL, fconn->conn);
	return ret;
  full:
	/* Too large to be encoded. For GET_VALUES records, it is an error */
	if (!b_data(mbuf)) {
		TRACE_ERROR("GET_VALUES record too large", FCGI_EV_TX_RECORD|FCGI_EV_TX_GETVAL|FCGI_EV_FCONN_ERR, fconn->conn);
		goto fail;
	}

	if ((mbuf = br_tail_add(fconn->mbuf)) != NULL)
		goto retry;
	fconn->flags |= FCGI_CF_MUX_MFULL;
	fconn->flags |= FCGI_CF_DEM_MROOM;
	TRACE_STATE("mbuf ring full", FCGI_EV_TX_RECORD|FCGI_EV_FCONN_BLK, fconn->conn);
	ret = 0;
	goto end;
  fail:
	fconn->state = FCGI_CS_CLOSED;
	TRACE_STATE("switching to CLOSED", FCGI_EV_TX_RECORD|FCGI_EV_TX_GETVAL|FCGI_EV_FCONN_END, fconn->conn);
	TRACE_DEVEL("leaving on error", FCGI_EV_TX_RECORD|FCGI_EV_TX_GETVAL|FCGI_EV_FCONN_ERR, fconn->conn);
	return 0;
}

/* Processes a GET_VALUES_RESULT record. Returns > 0 on success, 0 if it
 * couldn't do anything. It is highly unexpected, but if the record is larger
 * than a buffer and cannot be decoded in one time, an error is triggered and
 * the connection is closed. GET_VALUES_RESULT record cannot be split.
 */
static int fcgi_conn_handle_values_result(struct fcgi_conn *fconn)
{
	struct buffer inbuf;
	struct buffer *dbuf;
	size_t offset;

	TRACE_ENTER(FCGI_EV_RX_RECORD|FCGI_EV_RX_GETVAL, fconn->conn);

	dbuf = &fconn->dbuf;

	/* Record too large to be fully decoded */
	if (b_size(dbuf) < (fconn->drl + fconn->drp))
		goto fail;

	/* process full record only */
	if (b_data(dbuf) < (fconn->drl + fconn->drp)) {
		TRACE_DEVEL("leaving on missing data", FCGI_EV_RX_RECORD|FCGI_EV_RX_GETVAL, fconn->conn);
		return 0;
	}

	if (unlikely(b_contig_data(dbuf, b_head_ofs(dbuf)) < fconn->drl)) {
		/* Realign the dmux buffer if the record wraps. It is unexpected
		 * at this stage because it should be the first record received
		 * from the FCGI application.
		 */
		b_slow_realign(dbuf, trash.area, 0);
	}

	inbuf = b_make(b_head(dbuf), b_data(dbuf), 0, fconn->drl);

	for (offset = 0; offset < b_data(&inbuf); ) {
		struct fcgi_param p;
		size_t ret;

		ret = fcgi_aligned_decode_param(&inbuf, offset, &p);
		if (!ret) {
			/* name or value too large to be decoded at once */
			TRACE_ERROR("error decoding GET_VALUES_RESULT param", FCGI_EV_RX_RECORD|FCGI_EV_RX_GETVAL|FCGI_EV_FCONN_ERR, fconn->conn);
			goto fail;
		}
		offset += ret;

		if (isteqi(p.n, ist("FCGI_MPXS_CONNS"))) {
			if (isteq(p.v, ist("1"))) {
				TRACE_STATE("set mpxs param", FCGI_EV_RX_RECORD|FCGI_EV_RX_GETVAL, fconn->conn, 0, 0, (size_t[]){1});
				fconn->flags |= FCGI_CF_MPXS_CONNS;
			}
			else {
				TRACE_STATE("set mpxs param", FCGI_EV_RX_RECORD|FCGI_EV_RX_GETVAL, fconn->conn, 0, 0, (size_t[]){0});
				fconn->flags &= ~FCGI_CF_MPXS_CONNS;
			}
		}
		else if (isteqi(p.n, ist("FCGI_MAX_REQS"))) {
			fconn->streams_limit = strl2ui(p.v.ptr, p.v.len);
			TRACE_STATE("set streams_limit", FCGI_EV_RX_RECORD|FCGI_EV_RX_GETVAL, fconn->conn, 0, 0, (size_t[]){fconn->streams_limit});
		}
		/*
		 * Ignore all other params
		 */
	}

	/* Reset the number of concurrent streams supported if the FCGI
	 * application does not support connection multiplexing
	 */
	if (!(fconn->flags & FCGI_CF_MPXS_CONNS)) {
		fconn->streams_limit = 1;
		TRACE_STATE("no mpxs for streams_limit to 1", FCGI_EV_RX_RECORD|FCGI_EV_RX_GETVAL, fconn->conn);
	}

	/* We must be sure to have read exactly the announced record length, no
	 * more no less
	 */
	if (offset != fconn->drl) {
		TRACE_ERROR("invalid GET_VALUES_RESULT record length", FCGI_EV_RX_RECORD|FCGI_EV_RX_GETVAL|FCGI_EV_FCONN_ERR, fconn->conn);
		goto fail;
	}

	TRACE_PROTO("FCGI GET_VALUES_RESULT record rcvd", FCGI_EV_RX_RECORD|FCGI_EV_RX_GETVAL, fconn->conn, 0, 0, (size_t[]){fconn->drl});
	b_del(&fconn->dbuf, fconn->drl + fconn->drp);
	fconn->drl = 0;
	fconn->drp = 0;
	fconn->state = FCGI_CS_RECORD_H;
	fcgi_wake_unassigned_streams(fconn);
	TRACE_STATE("switching to RECORD_H", FCGI_EV_RX_RECORD|FCGI_EV_RX_FHDR, fconn->conn);
	TRACE_LEAVE(FCGI_EV_RX_RECORD|FCGI_EV_RX_GETVAL, fconn->conn);
	return 1;
  fail:
	fconn->state = FCGI_CS_CLOSED;
	TRACE_STATE("switching to CLOSED", FCGI_EV_RX_RECORD|FCGI_EV_RX_GETVAL, fconn->conn);
	TRACE_DEVEL("leaving on error", FCGI_EV_RX_RECORD|FCGI_EV_RX_GETVAL|FCGI_EV_FCONN_ERR, fconn->conn);
	return 0;
}

/* Sends an ABORT_REQUEST record for each active streams. Closed streams are
 * excluded, as the streams which already received the end-of-stream. It returns
 * > 0 if the record was sent tp all streams. Otherwise it returns 0.
 */
static int fcgi_conn_send_aborts(struct fcgi_conn *fconn)
{
	struct eb32_node *node;
	struct fcgi_strm *fstrm;

	TRACE_ENTER(FCGI_EV_TX_RECORD, fconn->conn);

	node = eb32_lookup_ge(&fconn->streams_by_id, 1);
	while (node) {
		fstrm = container_of(node, struct fcgi_strm, by_id);
		node = eb32_next(node);
		if (fstrm->state != FCGI_SS_CLOSED &&
		    !(fstrm->flags & (FCGI_SF_ES_RCVD|FCGI_SF_ABRT_SENT)) &&
		    !fcgi_strm_send_abort(fconn, fstrm))
			return 0;
	}
	fconn->flags |= FCGI_CF_ABRTS_SENT;
	TRACE_STATE("aborts sent to all fstrms", FCGI_EV_TX_RECORD, fconn->conn);
	TRACE_LEAVE(FCGI_EV_TX_RECORD, fconn->conn);
	return 1;
}

/* Sends a BEGIN_REQUEST record. It returns > 0 on success, 0 if it couldn't do
 * anything. BEGIN_REQUEST record cannot be split. So we wait to have enough
 * space to proceed. It is small enough to be encoded in an empty buffer.
 */
static int fcgi_strm_send_begin_request(struct fcgi_conn *fconn, struct fcgi_strm *fstrm)
{
	struct buffer outbuf;
	struct buffer *mbuf;
	struct fcgi_begin_request rec = { .role = FCGI_RESPONDER, .flags = 0};
	int ret;

	TRACE_ENTER(FCGI_EV_TX_RECORD|FCGI_EV_TX_BEGREQ, fconn->conn, fstrm);

	mbuf = br_tail(fconn->mbuf);
  retry:
	if (!fcgi_get_buf(fconn, mbuf)) {
		fconn->flags |= FCGI_CF_MUX_MALLOC;
		fstrm->flags |= FCGI_SF_BLK_MROOM;
		TRACE_STATE("waiting for fconn mbuf ring allocation", FCGI_EV_TX_RECORD|FCGI_EV_FSTRM_BLK|FCGI_EV_FCONN_BLK, fconn->conn, fstrm);
		ret = 0;
		goto end;
	}

	while (1) {
		outbuf = b_make(b_tail(mbuf), b_contig_space(mbuf), 0, 0);
		if (outbuf.size >= FCGI_RECORD_HEADER_SZ || !b_space_wraps(mbuf))
			break;
	  realign_again:
		b_slow_realign(mbuf, trash.area, b_data(mbuf));
	}

	if (outbuf.size < FCGI_RECORD_HEADER_SZ)
		goto full;

	/* vsn: 1(FCGI_VERSION), type: (1)FCGI_BEGIN_REQUEST, id: fstrm->id,
	 *  len: 0x0008, padding: 0x00, rsv: 0x00 */
	memcpy(outbuf.area, "\x01\x01\x00\x00\x00\x08\x00\x00", FCGI_RECORD_HEADER_SZ);
	fcgi_set_record_id(outbuf.area, fstrm->id);
	outbuf.data = FCGI_RECORD_HEADER_SZ;

	if (fconn->flags & FCGI_CF_KEEP_CONN) {
		TRACE_STATE("keep connection opened", FCGI_EV_TX_RECORD|FCGI_EV_TX_BEGREQ, fconn->conn, fstrm);
		rec.flags |= FCGI_KEEP_CONN;
	}
	if (!fcgi_encode_begin_request(&outbuf, &rec))
		goto full;

	/* commit the record */
	TRACE_PROTO("FCGI BEGIN_REQUEST record xferred", FCGI_EV_TX_RECORD|FCGI_EV_TX_BEGREQ, fconn->conn, fstrm, 0, (size_t[]){0});
	b_add(mbuf, outbuf.data);
	fstrm->flags |= FCGI_SF_BEGIN_SENT;
	fstrm->state = FCGI_SS_OPEN;
	TRACE_STATE("switching to OPEN", FCGI_EV_TX_RECORD|FCGI_EV_TX_BEGREQ, fconn->conn, fstrm);
	ret = 1;

  end:
	TRACE_LEAVE(FCGI_EV_TX_RECORD|FCGI_EV_TX_BEGREQ, fconn->conn, fstrm);
	return ret;
  full:
	if ((mbuf = br_tail_add(fconn->mbuf)) != NULL)
		goto retry;
	fconn->flags |= FCGI_CF_MUX_MFULL;
	fstrm->flags |= FCGI_SF_BLK_MROOM;
	TRACE_STATE("mbuf ring full", FCGI_EV_TX_RECORD|FCGI_EV_FSTRM_BLK|FCGI_EV_FCONN_BLK, fconn->conn);
	ret = 0;
	goto end;
}

/* Sends an empty record of type <rtype>. It returns > 0 on success, 0 if it
 * couldn't do anything. Empty record cannot be split. So we wait to have enough
 * space to proceed. It is small enough to be encoded in an empty buffer.
 */
static int fcgi_strm_send_empty_record(struct fcgi_conn *fconn, struct fcgi_strm *fstrm,
				       enum fcgi_record_type rtype)
{
	struct buffer outbuf;
	struct buffer *mbuf;
	int ret;

	TRACE_ENTER(FCGI_EV_TX_RECORD, fconn->conn, fstrm);
	mbuf = br_tail(fconn->mbuf);
  retry:
	if (!fcgi_get_buf(fconn, mbuf)) {
		fconn->flags |= FCGI_CF_MUX_MALLOC;
		fstrm->flags |= FCGI_SF_BLK_MROOM;
		TRACE_STATE("waiting for fconn mbuf ring allocation", FCGI_EV_TX_RECORD|FCGI_EV_FSTRM_BLK|FCGI_EV_FCONN_BLK, fconn->conn, fstrm);
		ret = 0;
		goto end;
	}

	while (1) {
		outbuf = b_make(b_tail(mbuf), b_contig_space(mbuf), 0, 0);
		if (outbuf.size >= FCGI_RECORD_HEADER_SZ || !b_space_wraps(mbuf))
			break;
	  realign_again:
		b_slow_realign(mbuf, trash.area, b_data(mbuf));
	}

	if (outbuf.size < FCGI_RECORD_HEADER_SZ)
		goto full;

	/* vsn: 1(FCGI_VERSION), type: rtype, id: fstrm->id,
	 *  len: 0x0000, padding: 0x00, rsv: 0x00 */
	memcpy(outbuf.area, "\x01\x05\x00\x00\x00\x00\x00\x00", FCGI_RECORD_HEADER_SZ);
	outbuf.area[1] = rtype;
	fcgi_set_record_id(outbuf.area, fstrm->id);
	outbuf.data = FCGI_RECORD_HEADER_SZ;

	/* commit the record */
	b_add(mbuf, outbuf.data);
	ret = 1;

  end:
	TRACE_LEAVE(FCGI_EV_TX_RECORD, fconn->conn, fstrm);
	return ret;
  full:
	if ((mbuf = br_tail_add(fconn->mbuf)) != NULL)
		goto retry;
	fconn->flags |= FCGI_CF_MUX_MFULL;
	fstrm->flags |= FCGI_SF_BLK_MROOM;
	TRACE_STATE("mbuf ring full", FCGI_EV_TX_RECORD|FCGI_EV_FSTRM_BLK|FCGI_EV_FCONN_BLK, fconn->conn, fstrm);
	ret = 0;
	goto end;
}


/* Sends an empty PARAMS record. It relies on fcgi_strm_send_empty_record(). It
 * marks the end of params.
 */
static int fcgi_strm_send_empty_params(struct fcgi_conn *fconn, struct fcgi_strm *fstrm)
{
	int ret;

	TRACE_POINT(FCGI_EV_TX_RECORD|FCGI_EV_TX_PARAMS, fconn->conn, fstrm);
	ret = fcgi_strm_send_empty_record(fconn, fstrm, FCGI_PARAMS);
	if (ret) {
		fstrm->flags |= FCGI_SF_EP_SENT;
		TRACE_PROTO("FCGI PARAMS record xferred", FCGI_EV_TX_RECORD|FCGI_EV_TX_STDIN, fconn->conn, fstrm, 0, (size_t[]){0});
	}
	return ret;
}

/* Sends an empty STDIN record. It relies on fcgi_strm_send_empty_record(). It
 * marks the end of input. On success, all the request was successfully sent.
 */
static int fcgi_strm_send_empty_stdin(struct fcgi_conn *fconn, struct fcgi_strm *fstrm)
{
	int ret;

	TRACE_POINT(FCGI_EV_TX_RECORD|FCGI_EV_TX_STDIN|FCGI_EV_TX_EOI, fconn->conn, fstrm);
	ret = fcgi_strm_send_empty_record(fconn, fstrm, FCGI_STDIN);
	if (ret) {
		fstrm->flags |= FCGI_SF_ES_SENT;
		TRACE_PROTO("FCGI STDIN record xferred", FCGI_EV_TX_RECORD|FCGI_EV_TX_STDIN, fconn->conn, fstrm, 0, (size_t[]){0});
		TRACE_USER("FCGI request fully xferred", FCGI_EV_TX_RECORD|FCGI_EV_TX_STDIN|FCGI_EV_TX_EOI, fconn->conn, fstrm);
		TRACE_STATE("stdin data fully sent", FCGI_EV_TX_RECORD|FCGI_EV_TX_STDIN|FCGI_EV_TX_EOI, fconn->conn, fstrm);
	}
	return ret;
}

/* Sends an ABORT_REQUEST record. It relies on fcgi_strm_send_empty_record(). It
 * stops the request processing.
 */
static int fcgi_strm_send_abort(struct fcgi_conn *fconn, struct fcgi_strm *fstrm)
{
	int ret;

	TRACE_POINT(FCGI_EV_TX_RECORD|FCGI_EV_TX_ABORT, fconn->conn, fstrm);
	ret = fcgi_strm_send_empty_record(fconn, fstrm, FCGI_ABORT_REQUEST);
	if (ret) {
		fstrm->flags |= FCGI_SF_ABRT_SENT;
		TRACE_PROTO("FCGI ABORT record xferred", FCGI_EV_TX_RECORD|FCGI_EV_TX_ABORT, fconn->conn, fstrm, 0, (size_t[]){0});
		TRACE_USER("FCGI request aborted", FCGI_EV_TX_RECORD|FCGI_EV_TX_ABORT, fconn->conn, fstrm);
		TRACE_STATE("abort sent", FCGI_EV_TX_RECORD|FCGI_EV_TX_ABORT, fconn->conn, fstrm);
	}
	return ret;
}

/* Sends a PARAMS record. Returns > 0 on success, 0 if it couldn't do
 * anything. If there are too much K/V params to be encoded in a PARAMS record,
 * several records are sent. However, a K/V param cannot be split between 2
 * records.
 */
static size_t fcgi_strm_send_params(struct fcgi_conn *fconn, struct fcgi_strm *fstrm,
				    struct htx *htx)
{
	struct buffer outbuf;
	struct buffer *mbuf;
	struct htx_blk *blk;
	struct htx_sl *sl = NULL;
	struct fcgi_strm_params params;
	size_t total = 0;

	TRACE_ENTER(FCGI_EV_TX_RECORD|FCGI_EV_TX_PARAMS, fconn->conn, fstrm, htx);

	memset(&params, 0, sizeof(params));
	params.p = get_trash_chunk();

	mbuf = br_tail(fconn->mbuf);
  retry:
	if (!fcgi_get_buf(fconn, mbuf)) {
		fconn->flags |= FCGI_CF_MUX_MALLOC;
		fstrm->flags |= FCGI_SF_BLK_MROOM;
		TRACE_STATE("waiting for fconn mbuf ring allocation", FCGI_EV_TX_RECORD|FCGI_EV_FSTRM_BLK|FCGI_EV_FCONN_BLK, fconn->conn, fstrm);
		goto end;
	}

	while (1) {
		outbuf = b_make(b_tail(mbuf), b_contig_space(mbuf), 0, 0);
		if (outbuf.size >= FCGI_RECORD_HEADER_SZ || !b_space_wraps(mbuf))
			break;
	  realign_again:
		b_slow_realign(mbuf, trash.area, b_data(mbuf));
	}

	if (outbuf.size < FCGI_RECORD_HEADER_SZ)
		goto full;

	/* vsn: 1(FCGI_VERSION), type: (4)FCGI_PARAMS, id: fstrm->id,
	 *  len: 0x0000 (fill later), padding: 0x00, rsv: 0x00 */
	memcpy(outbuf.area, "\x01\x04\x00\x00\x00\x00\x00\x00", FCGI_RECORD_HEADER_SZ);
	fcgi_set_record_id(outbuf.area, fstrm->id);
	outbuf.data = FCGI_RECORD_HEADER_SZ;

	blk = htx_get_head_blk(htx);
	while (blk) {
		enum htx_blk_type type;
		uint32_t size = htx_get_blksz(blk);
		struct fcgi_param p;

		type = htx_get_blk_type(blk);
		switch (type) {
			case HTX_BLK_REQ_SL:
				sl = htx_get_blk_ptr(htx, blk);
				if (sl->info.req.meth == HTTP_METH_HEAD)
					fstrm->h1m.flags |= H1_MF_METH_HEAD;
				if (sl->flags & HTX_SL_F_VER_11)
					fstrm->h1m.flags |= H1_MF_VER_11;
				break;

			case HTX_BLK_HDR:
				p.n = htx_get_blk_name(htx, blk);
				p.v = htx_get_blk_value(htx, blk);

				if (istmatch(p.n, ist(":fcgi-"))) {
					p.n.ptr += 6;
					p.n.len -= 6;
					if (isteq(p.n, ist("gateway_interface")))
						params.mask |= FCGI_SP_CGI_GATEWAY;
					else if (isteq(p.n, ist("document_root"))) {
						params.mask |= FCGI_SP_DOC_ROOT;
						params.docroot = p.v;
					}
					else if (isteq(p.n, ist("script_name"))) {
						params.mask |= FCGI_SP_SCRIPT_NAME;
						params.scriptname = p.v;
					}
					else if (isteq(p.n, ist("path_info"))) {
						params.mask |= FCGI_SP_PATH_INFO;
						params.pathinfo = p.v;
					}
					else if (isteq(p.n, ist("request_uri"))) {
						params.mask |= FCGI_SP_REQ_URI;
						params.uri = p.v;
					}
					else if (isteq(p.n, ist("request_meth")))
						params.mask |= FCGI_SP_REQ_METH;
					else if (isteq(p.n, ist("query_string")))
						params.mask |= FCGI_SP_REQ_QS;
					else if (isteq(p.n, ist("server_name")))
						params.mask |= FCGI_SP_SRV_NAME;
					else if (isteq(p.n, ist("server_port")))
						params.mask |= FCGI_SP_SRV_PORT;
					else if (isteq(p.n, ist("server_protocol")))
						params.mask |= FCGI_SP_SRV_PROTO;
					else if (isteq(p.n, ist("remote_addr")))
						params.mask |= FCGI_SP_REM_ADDR;
					else if (isteq(p.n, ist("remote_port")))
						params.mask |= FCGI_SP_REM_PORT;
					else if (isteq(p.n, ist("script_filename")))
						params.mask |= FCGI_SP_SCRIPT_FILE;
					else if (isteq(p.n, ist("path_translated")))
						params.mask |= FCGI_SP_PATH_TRANS;
					else if (isteq(p.n, ist("https")))
						params.mask |= FCGI_SP_HTTPS;
				}
				else if (isteq(p.n, ist("content-length"))) {
					p.n = ist("CONTENT_LENGTH");
					params.mask |= FCGI_SP_CONT_LEN;
				}
				else if (isteq(p.n, ist("content-type")))
					p.n = ist("CONTENT_TYPE");
				else {
					if (isteq(p.n, ist("host")))
						params.srv_name = p.v;

					/* Skip header if same name is used to add the server name */
					if (fconn->proxy->server_id_hdr_name &&
					    isteq(p.n, ist2(fconn->proxy->server_id_hdr_name, fconn->proxy->server_id_hdr_len)))
						break;

					memcpy(trash.area, "http_", 5);
					memcpy(trash.area+5, p.n.ptr, p.n.len);
					p.n = ist2(trash.area, p.n.len+5);
				}

				if (!fcgi_encode_param(&outbuf, &p)) {
					if (b_space_wraps(mbuf))
						goto realign_again;
					if (outbuf.data == FCGI_RECORD_HEADER_SZ)
						goto full;
					goto done;
				}
				break;

			case HTX_BLK_EOH:
				if (fconn->proxy->server_id_hdr_name) {
					struct server *srv = objt_server(fconn->conn->target);

					if (!srv)
						goto done;

					memcpy(trash.area, "http_", 5);
					memcpy(trash.area+5, fconn->proxy->server_id_hdr_name, fconn->proxy->server_id_hdr_len);
					p.n = ist2(trash.area, fconn->proxy->server_id_hdr_len+5);
					p.v = ist(srv->id);

					if (!fcgi_encode_param(&outbuf, &p)) {
						if (b_space_wraps(mbuf))
							goto realign_again;
						if (outbuf.data == FCGI_RECORD_HEADER_SZ)
							goto full;
					}
					TRACE_STATE("add server name header", FCGI_EV_TX_RECORD|FCGI_EV_TX_PARAMS, fconn->conn, fstrm);
				}
				goto done;

			default:
				break;
		}
		total += size;
		blk = htx_remove_blk(htx, blk);
	}

  done:
	if (!fcgi_set_default_param(fconn, fstrm, htx, sl, &params)) {
		TRACE_ERROR("error setting default params", FCGI_EV_TX_RECORD|FCGI_EV_STRM_ERR, fconn->conn, fstrm);
		goto error;
	}

	if (!fcgi_encode_default_param(fconn, fstrm, &params, &outbuf, FCGI_SP_CGI_GATEWAY) ||
	    !fcgi_encode_default_param(fconn, fstrm, &params, &outbuf, FCGI_SP_DOC_ROOT)    ||
	    !fcgi_encode_default_param(fconn, fstrm, &params, &outbuf, FCGI_SP_SCRIPT_NAME) ||
	    !fcgi_encode_default_param(fconn, fstrm, &params, &outbuf, FCGI_SP_PATH_INFO)   ||
	    !fcgi_encode_default_param(fconn, fstrm, &params, &outbuf, FCGI_SP_REQ_URI)     ||
	    !fcgi_encode_default_param(fconn, fstrm, &params, &outbuf, FCGI_SP_REQ_METH)    ||
	    !fcgi_encode_default_param(fconn, fstrm, &params, &outbuf, FCGI_SP_REQ_QS)      ||
	    !fcgi_encode_default_param(fconn, fstrm, &params, &outbuf, FCGI_SP_SRV_NAME)    ||
	    !fcgi_encode_default_param(fconn, fstrm, &params, &outbuf, FCGI_SP_SRV_PORT)    ||
	    !fcgi_encode_default_param(fconn, fstrm, &params, &outbuf, FCGI_SP_SRV_PROTO)   ||
	    !fcgi_encode_default_param(fconn, fstrm, &params, &outbuf, FCGI_SP_REM_ADDR)    ||
	    !fcgi_encode_default_param(fconn, fstrm, &params, &outbuf, FCGI_SP_REM_PORT)    ||
	    !fcgi_encode_default_param(fconn, fstrm, &params, &outbuf, FCGI_SP_SCRIPT_FILE) ||
	    !fcgi_encode_default_param(fconn, fstrm, &params, &outbuf, FCGI_SP_PATH_TRANS)  ||
	    !fcgi_encode_default_param(fconn, fstrm, &params, &outbuf, FCGI_SP_CONT_LEN)    ||
	    !fcgi_encode_default_param(fconn, fstrm, &params, &outbuf, FCGI_SP_HTTPS)) {
		TRACE_ERROR("error encoding default params", FCGI_EV_TX_RECORD|FCGI_EV_STRM_ERR, fconn->conn, fstrm);
		goto error;
	}

	/* update the record's size */
	TRACE_PROTO("FCGI PARAMS record xferred", FCGI_EV_TX_RECORD|FCGI_EV_TX_PARAMS, fconn->conn, fstrm, 0, (size_t[]){outbuf.data - FCGI_RECORD_HEADER_SZ});
	fcgi_set_record_size(outbuf.area, outbuf.data - FCGI_RECORD_HEADER_SZ);
	b_add(mbuf, outbuf.data);

  end:
	TRACE_LEAVE(FCGI_EV_TX_RECORD|FCGI_EV_TX_PARAMS, fconn->conn, fstrm, htx, (size_t[]){total});
	return total;
  full:
	if ((mbuf = br_tail_add(fconn->mbuf)) != NULL)
		goto retry;
	fconn->flags |= FCGI_CF_MUX_MFULL;
	fstrm->flags |= FCGI_SF_BLK_MROOM;
	TRACE_STATE("mbuf ring full", FCGI_EV_TX_RECORD|FCGI_EV_FSTRM_BLK|FCGI_EV_FCONN_BLK, fconn->conn, fstrm);
	if (total)
		goto error;
	goto end;

  error:
	htx->flags |= HTX_FL_PROCESSING_ERROR;
	TRACE_ERROR("processing error sending PARAMS record", FCGI_EV_TX_RECORD|FCGI_EV_STRM_ERR, fconn->conn, fstrm);
	fcgi_strm_error(fstrm);
	goto end;
}

/* Sends a STDIN record. Returns > 0 on success, 0 if it couldn't do
 * anything. STDIN records contain the request body.
 */
static size_t fcgi_strm_send_stdin(struct fcgi_conn *fconn, struct fcgi_strm *fstrm,
				   struct htx *htx, size_t count, struct buffer *buf)
{
	struct buffer outbuf;
	struct buffer *mbuf;
	struct htx_blk *blk;
	enum htx_blk_type type;
	uint32_t size, extra_bytes;
	size_t total = 0;

	extra_bytes = 0;

	TRACE_ENTER(FCGI_EV_TX_RECORD|FCGI_EV_TX_STDIN, fconn->conn, fstrm, htx, (size_t[]){count});
	if (!count)
		goto end;

	mbuf = br_tail(fconn->mbuf);
  retry:
	if (!fcgi_get_buf(fconn, mbuf)) {
		fconn->flags |= FCGI_CF_MUX_MALLOC;
		fstrm->flags |= FCGI_SF_BLK_MROOM;
		TRACE_STATE("waiting for fconn mbuf ring allocation", FCGI_EV_TX_RECORD|FCGI_EV_FSTRM_BLK|FCGI_EV_FCONN_BLK, fconn->conn, fstrm);
		goto end;
	}

	/* Perform some optimizations to reduce the number of buffer copies.
	 * First, if the mux's buffer is empty and the htx area contains exactly
	 * one data block of the same size as the requested count, and this
	 * count fits within the record size, then it's possible to simply swap
	 * the caller's buffer with the mux's output buffer and adjust offsets
	 * and length to match the entire DATA HTX block in the middle. In this
	 * case we perform a true zero-copy operation from end-to-end. This is
	 * the situation that happens all the time with large files. Second, if
	 * this is not possible, but the mux's output buffer is empty, we still
	 * have an opportunity to avoid the copy to the intermediary buffer, by
	 * making the intermediary buffer's area point to the output buffer's
	 * area. In this case we want to skip the HTX header to make sure that
	 * copies remain aligned and that this operation remains possible all
	 * the time. This goes for headers, data blocks and any data extracted
	 * from the HTX blocks.
	 */
	blk  = htx_get_head_blk(htx);
	if (!blk)
		goto end;
	type = htx_get_blk_type(blk);
	size = htx_get_blksz(blk);
	if (unlikely(size == count && htx_nbblks(htx) == 1 && type == HTX_BLK_DATA)) {
		void *old_area = mbuf->area;

		 /* Last block of the message: Reserve the size for the empty stdin record */
		if (htx->flags & HTX_FL_EOM)
			extra_bytes = FCGI_RECORD_HEADER_SZ;

		if (b_data(mbuf)) {
			/* Too bad there are data left there. We're willing to memcpy/memmove
			 * up to 1/4 of the buffer, which means that it's OK to copy a large
			 * record into a buffer containing few data if it needs to be realigned,
			 * and that it's also OK to copy few data without realigning. Otherwise
			 * we'll pretend the mbuf is full and wait for it to become empty.
			 */
			if (size + FCGI_RECORD_HEADER_SZ + extra_bytes <= b_room(mbuf) &&
			    (b_data(mbuf) <= b_size(mbuf) / 4 ||
			     (size <= b_size(mbuf) / 4 && size + FCGI_RECORD_HEADER_SZ + extra_bytes <= b_contig_space(mbuf))))
				goto copy;
			goto full;
		}

		TRACE_PROTO("sending stding data (zero-copy)", FCGI_EV_TX_RECORD|FCGI_EV_TX_STDIN, fconn->conn, fstrm, htx, (size_t[]){size});
		/* map a FCGI record to the HTX block so that we can put the
		 * record header there.
		 */
		*mbuf = b_make(buf->area, buf->size, sizeof(struct htx) + blk->addr - FCGI_RECORD_HEADER_SZ, size + FCGI_RECORD_HEADER_SZ);
		outbuf.area = b_head(mbuf);

		/* prepend a FCGI record header just before the DATA block */
		memcpy(outbuf.area, "\x01\x05\x00\x00\x00\x00\x00\x00", FCGI_RECORD_HEADER_SZ);
		fcgi_set_record_id(outbuf.area, fstrm->id);
		fcgi_set_record_size(outbuf.area, size);

		/* and exchange with our old area */
		buf->area = old_area;
		buf->data = buf->head = 0;
		total += size;

		htx = (struct htx *)buf->area;
		htx_reset(htx);
		goto end;
	}

  copy:
	while (1) {
		outbuf = b_make(b_tail(mbuf), b_contig_space(mbuf), 0, 0);
		if (outbuf.size >= FCGI_RECORD_HEADER_SZ + extra_bytes || !b_space_wraps(mbuf))
			break;
	  realign_again:
		b_slow_realign(mbuf, trash.area, b_data(mbuf));
	}

	if (outbuf.size < FCGI_RECORD_HEADER_SZ + extra_bytes)
		goto full;

	/* vsn: 1(FCGI_VERSION), type: (5)FCGI_STDIN, id: fstrm->id,
	 *  len: 0x0000 (fill later), padding: 0x00, rsv: 0x00 */
	memcpy(outbuf.area, "\x01\x05\x00\x00\x00\x00\x00\x00", FCGI_RECORD_HEADER_SZ);
	fcgi_set_record_id(outbuf.area, fstrm->id);
	outbuf.data = FCGI_RECORD_HEADER_SZ;

	blk = htx_get_head_blk(htx);
	while (blk && count) {
		enum htx_blk_type type = htx_get_blk_type(blk);
		uint32_t size = htx_get_blksz(blk);
		struct ist v;

		switch (type) {
			case HTX_BLK_DATA:
				TRACE_PROTO("sending stding data", FCGI_EV_TX_RECORD|FCGI_EV_TX_STDIN, fconn->conn, fstrm, htx, (size_t[]){size});
				v = htx_get_blk_value(htx, blk);

				if (htx_is_unique_blk(htx, blk) && (htx->flags & HTX_FL_EOM))
					extra_bytes = FCGI_RECORD_HEADER_SZ; /* Last block of the message */

				if (v.len > count) {
					v.len = count;
					extra_bytes = 0;
				}

				if (v.len + FCGI_RECORD_HEADER_SZ + extra_bytes > b_room(&outbuf)) {
					/* It doesn't fit at once. If it at least fits once split and
					 * the amount of data to move is low, let's defragment the
					 * buffer now.
					 */
					if (b_space_wraps(mbuf) &&
					    b_data(&outbuf) + v.len + extra_bytes <= b_room(mbuf) &&
					    b_data(mbuf) <= MAX_DATA_REALIGN)
						goto realign_again;
					v.len = b_room(&outbuf) - FCGI_RECORD_HEADER_SZ - extra_bytes;
				}
				if (!v.len || !chunk_memcat(&outbuf, v.ptr, v.len)) {
					if (outbuf.data == FCGI_RECORD_HEADER_SZ)
						goto full;
					goto done;
				}
				if (v.len != size) {
					total += v.len;
					count -= v.len;
					htx_cut_data_blk(htx, blk, v.len);
					goto done;
				}
				break;

			default:
				break;
		}
		total += size;
		count -= size;
		blk = htx_remove_blk(htx, blk);
	}

  done:
	/* update the record's size */
	TRACE_PROTO("FCGI STDIN record xferred", FCGI_EV_TX_RECORD|FCGI_EV_TX_STDIN, fconn->conn, fstrm, 0, (size_t[]){outbuf.data - FCGI_RECORD_HEADER_SZ});
	fcgi_set_record_size(outbuf.area, outbuf.data - FCGI_RECORD_HEADER_SZ);
	b_add(mbuf, outbuf.data);

	/* Send the empty stding here to finish the message */
	if (htx_is_empty(htx) && (htx->flags & HTX_FL_EOM)) {
		TRACE_PROTO("sending FCGI STDIN record", FCGI_EV_TX_RECORD|FCGI_EV_TX_STDIN, fconn->conn, fstrm, htx);
		if (!fcgi_strm_send_empty_stdin(fconn, fstrm)) {
			/* bytes already reserved for this record. It should not fail */
			htx->flags |= HTX_FL_PROCESSING_ERROR;
			TRACE_ERROR("processing error sending empty STDIN record", FCGI_EV_TX_RECORD|FCGI_EV_STRM_ERR, fconn->conn, fstrm);
			fcgi_strm_error(fstrm);
		}
	}

  end:
	TRACE_LEAVE(FCGI_EV_TX_RECORD|FCGI_EV_TX_STDIN, fconn->conn, fstrm, htx, (size_t[]){total});
	return total;
  full:
	if ((mbuf = br_tail_add(fconn->mbuf)) != NULL)
		goto retry;
	fconn->flags |= FCGI_CF_MUX_MFULL;
	fstrm->flags |= FCGI_SF_BLK_MROOM;
	TRACE_STATE("mbuf ring full", FCGI_EV_TX_RECORD|FCGI_EV_FSTRM_BLK|FCGI_EV_FCONN_BLK, fconn->conn, fstrm);
	goto end;
}

/* Processes a STDOUT record. Returns > 0 on success, 0 if it couldn't do
 * anything. STDOUT records contain the entire response. All the content is
 * copied in the stream's rxbuf. The parsing will be handled in fcgi_rcv_buf().
 */
static int fcgi_strm_handle_stdout(struct fcgi_conn *fconn, struct fcgi_strm *fstrm)
{
	struct buffer *dbuf;
	size_t ret;
	size_t max;

	TRACE_ENTER(FCGI_EV_RX_RECORD|FCGI_EV_RX_STDOUT, fconn->conn, fstrm);

	dbuf = &fconn->dbuf;

	/* Only padding remains */
	if (fconn->state == FCGI_CS_RECORD_P)
		goto end_transfer;

	if (b_data(dbuf) < (fconn->drl + fconn->drp) &&
	    b_size(dbuf) > (fconn->drl + fconn->drp) &&
	    buf_room_for_htx_data(dbuf))
		goto fail; // incomplete record

	if (!fcgi_get_buf(fconn, &fstrm->rxbuf)) {
		fconn->flags |= FCGI_CF_DEM_SALLOC;
		TRACE_STATE("waiting for fstrm rxbuf allocation", FCGI_EV_RX_RECORD|FCGI_EV_FSTRM_BLK, fconn->conn, fstrm);
		goto fail;
	}

	/*max = MIN(b_room(&fstrm->rxbuf), fconn->drl);*/
	max = buf_room_for_htx_data(&fstrm->rxbuf);
	if (!b_data(&fstrm->rxbuf))
		fstrm->rxbuf.head = sizeof(struct htx);
	if (max > fconn->drl)
		max = fconn->drl;

	ret = b_xfer(&fstrm->rxbuf, dbuf, max);
	if (!ret)
		goto fail;
	fconn->drl -= ret;
	TRACE_DATA("move some data to fstrm rxbuf", FCGI_EV_RX_RECORD|FCGI_EV_RX_STDOUT, fconn->conn, fstrm, 0, (size_t[]){ret});
	TRACE_PROTO("FCGI STDOUT record rcvd", FCGI_EV_RX_RECORD|FCGI_EV_RX_STDOUT, fconn->conn, fstrm, 0, (size_t[]){ret});

	if (!buf_room_for_htx_data(&fstrm->rxbuf)) {
		fconn->flags |= FCGI_CF_DEM_SFULL;
		TRACE_STATE("fstrm rxbuf full", FCGI_EV_RX_RECORD|FCGI_EV_FSTRM_BLK, fconn->conn, fstrm);
	}

	if (fconn->drl)
		goto fail;

  end_transfer:
	fconn->state = FCGI_CS_RECORD_P;
	fconn->drl += fconn->drp;
	fconn->drp = 0;
	ret = MIN(b_data(&fconn->dbuf), fconn->drl);
	b_del(&fconn->dbuf, ret);
	fconn->drl -= ret;
	if (fconn->drl)
		goto fail;

	fconn->state = FCGI_CS_RECORD_H;
	TRACE_STATE("switching to RECORD_H", FCGI_EV_RX_RECORD|FCGI_EV_RX_FHDR, fconn->conn, fstrm);
	TRACE_LEAVE(FCGI_EV_RX_RECORD|FCGI_EV_RX_STDOUT, fconn->conn, fstrm);
	return 1;
  fail:
	TRACE_DEVEL("leaving on missing data or error", FCGI_EV_RX_RECORD|FCGI_EV_RX_STDOUT, fconn->conn, fstrm);
	return 0;
}


/* Processes an empty STDOUT. Returns > 0 on success, 0 if it couldn't do
 * anything. It only skip the padding in fact, there is no payload for such
 * records. It marks the end of the response.
 */
static int fcgi_strm_handle_empty_stdout(struct fcgi_conn *fconn, struct fcgi_strm *fstrm)
{
	int ret;

	TRACE_ENTER(FCGI_EV_RX_RECORD|FCGI_EV_RX_STDOUT, fconn->conn, fstrm);

	fconn->state = FCGI_CS_RECORD_P;
	TRACE_STATE("switching to RECORD_P", FCGI_EV_RX_RECORD|FCGI_EV_RX_STDOUT, fconn->conn, fstrm);
	fconn->drl += fconn->drp;
	fconn->drp = 0;
	ret = MIN(b_data(&fconn->dbuf), fconn->drl);
	b_del(&fconn->dbuf, ret);
	fconn->drl -= ret;
	if (fconn->drl) {
		TRACE_DEVEL("leaving on missing data or error", FCGI_EV_RX_RECORD|FCGI_EV_RX_STDOUT, fconn->conn, fstrm);
		return 0;
	}
	fconn->state = FCGI_CS_RECORD_H;
	fstrm->flags |= FCGI_SF_ES_RCVD;
	TRACE_PROTO("FCGI STDOUT record rcvd", FCGI_EV_RX_RECORD|FCGI_EV_RX_STDOUT, fconn->conn, fstrm, 0, (size_t[]){0});
	TRACE_STATE("stdout data fully send, switching to RECORD_H", FCGI_EV_RX_RECORD|FCGI_EV_RX_FHDR|FCGI_EV_RX_EOI, fconn->conn, fstrm);
	TRACE_LEAVE(FCGI_EV_RX_RECORD|FCGI_EV_RX_STDOUT, fconn->conn, fstrm);
	return 1;
}

/* Processes a STDERR record. Returns > 0 on success, 0 if it couldn't do
 * anything.
 */
static int fcgi_strm_handle_stderr(struct fcgi_conn *fconn, struct fcgi_strm *fstrm)
{
	struct buffer *dbuf;
	struct buffer tag;
	size_t ret;

	TRACE_ENTER(FCGI_EV_RX_RECORD|FCGI_EV_RX_STDERR, fconn->conn, fstrm);
	dbuf = &fconn->dbuf;

	/* Only padding remains */
	if (fconn->state == FCGI_CS_RECORD_P || !fconn->drl)
		goto end_transfer;

	if (b_data(dbuf) < (fconn->drl + fconn->drp) &&
	    b_size(dbuf) > (fconn->drl + fconn->drp) &&
	    buf_room_for_htx_data(dbuf))
		goto fail; // incomplete record

	chunk_reset(&trash);
	ret = b_xfer(&trash, dbuf, MIN(b_room(&trash), fconn->drl));
	if (!ret)
		goto fail;
	fconn->drl -= ret;
	TRACE_PROTO("FCGI STDERR record rcvd", FCGI_EV_RX_RECORD|FCGI_EV_RX_STDERR, fconn->conn, fstrm, 0, (size_t[]){ret});

	trash.area[ret]   = '\n';
	trash.area[ret+1] = '\0';
	tag.area = fconn->app->name; tag.data = strlen(fconn->app->name);
	app_log(&fconn->app->logsrvs, &tag, LOG_ERR, "%s", trash.area);

	if (fconn->drl)
		goto fail;

  end_transfer:
	fconn->state = FCGI_CS_RECORD_P;
	fconn->drl += fconn->drp;
	fconn->drp = 0;
	ret = MIN(b_data(&fconn->dbuf), fconn->drl);
	b_del(&fconn->dbuf, ret);
	fconn->drl -= ret;
	if (fconn->drl)
		goto fail;
	fconn->state = FCGI_CS_RECORD_H;
	TRACE_STATE("switching to RECORD_H", FCGI_EV_RX_RECORD|FCGI_EV_RX_FHDR, fconn->conn, fstrm);
	TRACE_LEAVE(FCGI_EV_RX_RECORD|FCGI_EV_RX_STDERR, fconn->conn, fstrm);
	return 1;
  fail:
	TRACE_DEVEL("leaving on missing data or error", FCGI_EV_RX_RECORD|FCGI_EV_RX_STDERR, fconn->conn, fstrm);
	return 0;
}

/* Processes an END_REQUEST record. Returns > 0 on success, 0 if it couldn't do
 * anything. If the empty STDOUT record is not already received, this one marks
 * the end of the response. It is highly unexpected, but if the record is larger
 * than a buffer and cannot be decoded in one time, an error is triggered and
 * the connection is closed. END_REQUEST record cannot be split.
 */
static int fcgi_strm_handle_end_request(struct fcgi_conn *fconn, struct fcgi_strm *fstrm)
{
	struct buffer inbuf;
	struct buffer *dbuf;
	struct fcgi_end_request endreq;

	TRACE_ENTER(FCGI_EV_RX_RECORD|FCGI_EV_RX_ENDREQ, fconn->conn, fstrm);
	dbuf = &fconn->dbuf;

	/* Record too large to be fully decoded */
	if (b_size(dbuf) < (fconn->drl + fconn->drp)) {
		TRACE_ERROR("END_REQUEST record too large", FCGI_EV_RX_RECORD|FCGI_EV_RX_ENDREQ|FCGI_EV_FSTRM_ERR, fconn->conn, fstrm);
		goto fail;
	}

	/* process full record only */
	if (b_data(dbuf) < (fconn->drl + fconn->drp)) {
		TRACE_DEVEL("leaving on missing data", FCGI_EV_RX_RECORD|FCGI_EV_RX_ENDREQ, fconn->conn);
		return 0;
	}

	if (unlikely(b_contig_data(dbuf, b_head_ofs(dbuf)) < fconn->drl)) {
		/* Realign the dmux buffer if the record wraps. It is unexpected
		 * at this stage because it should be the first record received
		 * from the FCGI application.
		 */
		b_slow_realign(dbuf, trash.area, 0);
	}

	inbuf = b_make(b_head(dbuf), b_data(dbuf), 0, fconn->drl);

	if (!fcgi_decode_end_request(&inbuf, 0, &endreq)) {
		TRACE_ERROR("END_REQUEST record decoding failure", FCGI_EV_RX_RECORD|FCGI_EV_RX_ENDREQ|FCGI_EV_FSTRM_ERR, fconn->conn, fstrm);
		goto fail;
	}

	fstrm->flags |= FCGI_SF_ES_RCVD;
	TRACE_STATE("end of script reported", FCGI_EV_RX_RECORD|FCGI_EV_RX_ENDREQ|FCGI_EV_RX_EOI, fconn->conn, fstrm);
	TRACE_PROTO("FCGI END_REQUEST record rcvd", FCGI_EV_RX_RECORD|FCGI_EV_RX_ENDREQ, fconn->conn, fstrm, 0, (size_t[]){fconn->drl});
	fstrm->proto_status = endreq.errcode;
	fcgi_strm_close(fstrm);

	b_del(&fconn->dbuf, fconn->drl + fconn->drp);
	fconn->drl = 0;
	fconn->drp = 0;
	fconn->state = FCGI_CS_RECORD_H;
	TRACE_STATE("switching to RECORD_H", FCGI_EV_RX_RECORD|FCGI_EV_RX_FHDR, fconn->conn, fstrm);
	TRACE_LEAVE(FCGI_EV_RX_RECORD|FCGI_EV_RX_ENDREQ, fconn->conn, fstrm);
	return 1;

  fail:
	fcgi_strm_error(fstrm);
	TRACE_DEVEL("leaving on error", FCGI_EV_RX_RECORD|FCGI_EV_RX_ENDREQ|FCGI_EV_FSTRM_ERR, fconn->conn, fstrm);
	return 0;
}

/* process Rx records to be demultiplexed */
static void fcgi_process_demux(struct fcgi_conn *fconn)
{
	struct fcgi_strm *fstrm = NULL, *tmp_fstrm;
	struct fcgi_header hdr;
	int ret;

	TRACE_ENTER(FCGI_EV_FCONN_WAKE, fconn->conn);

	if (fconn->state == FCGI_CS_CLOSED)
		return;

	if (unlikely(fconn->state < FCGI_CS_RECORD_H)) {
		if (fconn->state == FCGI_CS_INIT) {
			TRACE_STATE("waiting FCGI GET_VALUES to be sent", FCGI_EV_RX_RECORD|FCGI_EV_RX_FHDR|FCGI_EV_RX_GETVAL, fconn->conn);
			return;
		}
		if (fconn->state == FCGI_CS_SETTINGS) {
			/* ensure that what is pending is a valid GET_VALUES_RESULT record. */
			TRACE_STATE("receiving FCGI record header", FCGI_EV_RX_RECORD|FCGI_EV_RX_FHDR, fconn->conn);
			ret = fcgi_decode_record_hdr(&fconn->dbuf, 0, &hdr);
			if (!ret) {
				TRACE_ERROR("header record decoding failure", FCGI_EV_RX_RECORD|FCGI_EV_RX_ENDREQ|FCGI_EV_FSTRM_ERR, fconn->conn, fstrm);
				goto fail;
			}
			b_del(&fconn->dbuf, ret);

			if (hdr.id || (hdr.type != FCGI_GET_VALUES_RESULT && hdr.type != FCGI_UNKNOWN_TYPE)) {
				fconn->state = FCGI_CS_CLOSED;
				TRACE_ERROR("unexpected record type or flags", FCGI_EV_RX_RECORD|FCGI_EV_RX_FHDR|FCGI_EV_RX_GETVAL|FCGI_EV_FCONN_ERR, fconn->conn);
				TRACE_STATE("switching to CLOSED", FCGI_EV_RX_RECORD|FCGI_EV_RX_FHDR|FCGI_EV_RX_GETVAL|FCGI_EV_FCONN_ERR, fconn->conn);
				goto fail;
			}
			goto new_record;
		}
	}

	/* process as many incoming records as possible below */
	while (1) {
		if (!b_data(&fconn->dbuf)) {
			TRACE_DEVEL("no more Rx data", FCGI_EV_RX_RECORD, fconn->conn);
			break;
		}

		if (fconn->state == FCGI_CS_CLOSED) {
			TRACE_STATE("end of connection reported", FCGI_EV_RX_RECORD|FCGI_EV_RX_EOI, fconn->conn);
			break;
		}

		if (fconn->state == FCGI_CS_RECORD_H) {
			TRACE_PROTO("receiving FCGI record header", FCGI_EV_RX_RECORD|FCGI_EV_RX_FHDR, fconn->conn);
			ret = fcgi_decode_record_hdr(&fconn->dbuf, 0, &hdr);
			if (!ret)
				break;
			b_del(&fconn->dbuf, ret);

		  new_record:
			fconn->dsi = hdr.id;
			fconn->drt = hdr.type;
			fconn->drl = hdr.len;
			fconn->drp = hdr.padding;
			fconn->state = FCGI_CS_RECORD_D;
			TRACE_STATE("FCGI record header rcvd, switching to RECORD_D", FCGI_EV_RX_RECORD|FCGI_EV_RX_FHDR, fconn->conn);
		}

		/* Only FCGI_CS_RECORD_D or FCGI_CS_RECORD_P */
		tmp_fstrm = fcgi_conn_st_by_id(fconn, fconn->dsi);

		if (tmp_fstrm != fstrm && fstrm && fstrm->cs &&
		    (b_data(&fstrm->rxbuf) ||
		     fcgi_conn_read0_pending(fconn) ||
		     fstrm->state == FCGI_SS_CLOSED ||
		     (fstrm->flags & FCGI_SF_ES_RCVD) ||
		     (fstrm->cs->flags & (CS_FL_ERROR|CS_FL_ERR_PENDING|CS_FL_EOS)))) {
			/* we may have to signal the upper layers */
			TRACE_DEVEL("notifying stream before switching SID", FCGI_EV_RX_RECORD|FCGI_EV_STRM_WAKE, fconn->conn, fstrm);
			fstrm->cs->flags |= CS_FL_RCV_MORE;
			fcgi_strm_notify_recv(fstrm);
		}
		fstrm = tmp_fstrm;

		if (fstrm->state == FCGI_SS_CLOSED && fconn->dsi != 0) {
			/* ignore all record for closed streams */
			goto ignore_record;
		}
		if (fstrm->state == FCGI_SS_IDLE) {
			/* ignore all record for unknown streams */
			goto ignore_record;
		}

		switch (fconn->drt) {
			case FCGI_GET_VALUES_RESULT:
				TRACE_PROTO("receiving FCGI GET_VALUES_RESULT record", FCGI_EV_RX_RECORD|FCGI_EV_RX_GETVAL, fconn->conn);
				ret = fcgi_conn_handle_values_result(fconn);
				break;

			case FCGI_STDOUT:
				if (fstrm->flags & FCGI_SF_ES_RCVD)
					goto ignore_record;

				TRACE_PROTO("receiving FCGI STDOUT record", FCGI_EV_RX_RECORD|FCGI_EV_RX_STDOUT, fconn->conn, fstrm);
				if (fconn->drl)
					ret = fcgi_strm_handle_stdout(fconn, fstrm);
				else
					ret = fcgi_strm_handle_empty_stdout(fconn, fstrm);
				break;

			case FCGI_STDERR:
				TRACE_PROTO("receiving FCGI STDERR record", FCGI_EV_RX_RECORD|FCGI_EV_RX_STDERR, fconn->conn, fstrm);
				ret = fcgi_strm_handle_stderr(fconn, fstrm);
				break;

			case FCGI_END_REQUEST:
				TRACE_PROTO("receiving FCGI END_REQUEST record", FCGI_EV_RX_RECORD|FCGI_EV_RX_ENDREQ, fconn->conn, fstrm);
				ret = fcgi_strm_handle_end_request(fconn, fstrm);
				break;

			/* implement all extra record types here */
			default:
			  ignore_record:
				/* drop records that we ignore. They may be
				 * larger than the buffer so we drain all of
				 * their contents until we reach the end.
				 */
				fconn->state = FCGI_CS_RECORD_P;
				fconn->drl += fconn->drp;
				fconn->drp = 0;
				ret = MIN(b_data(&fconn->dbuf), fconn->drl);
				TRACE_PROTO("receiving FCGI ignored record", FCGI_EV_RX_RECORD, fconn->conn, fstrm, 0, (size_t[]){ret});
				TRACE_STATE("switching to RECORD_P", FCGI_EV_RX_RECORD, fconn->conn, fstrm);
				b_del(&fconn->dbuf, ret);
				fconn->drl -= ret;
				ret = (fconn->drl == 0);
		}

		/* error or missing data condition met above ? */
		if (ret <= 0) {
			TRACE_DEVEL("insufficient data to proceed", FCGI_EV_RX_RECORD, fconn->conn, fstrm);
			break;
		}

		if (fconn->state != FCGI_CS_RECORD_H && !(fconn->drl+fconn->drp)) {
			fconn->state = FCGI_CS_RECORD_H;
			TRACE_STATE("switching to RECORD_H", FCGI_EV_RX_RECORD|FCGI_EV_RX_FHDR, fconn->conn);
		}
	}

 fail:
	/* we can go here on missing data, blocked response or error */
	if (fstrm && fstrm->cs &&
	    (b_data(&fstrm->rxbuf) ||
	     fcgi_conn_read0_pending(fconn) ||
	     fstrm->state == FCGI_SS_CLOSED ||
	     (fstrm->flags & FCGI_SF_ES_RCVD) ||
	     (fstrm->cs->flags & (CS_FL_ERROR|CS_FL_ERR_PENDING|CS_FL_EOS)))) {
		/* we may have to signal the upper layers */
		TRACE_DEVEL("notifying stream before switching SID", FCGI_EV_RX_RECORD|FCGI_EV_STRM_WAKE, fconn->conn, fstrm);
		fstrm->cs->flags |= CS_FL_RCV_MORE;
		fcgi_strm_notify_recv(fstrm);
	}

	fcgi_conn_restart_reading(fconn, 0);
}

/* process Tx records from streams to be multiplexed. Returns > 0 if it reached
 * the end.
 */
static int fcgi_process_mux(struct fcgi_conn *fconn)
{
	struct fcgi_strm *fstrm, *fstrm_back;

	TRACE_ENTER(FCGI_EV_FCONN_WAKE, fconn->conn);

	if (unlikely(fconn->state < FCGI_CS_RECORD_H)) {
		if (unlikely(fconn->state == FCGI_CS_INIT)) {
			if (!(fconn->flags & FCGI_CF_GET_VALUES)) {
				fconn->state = FCGI_CS_RECORD_H;
				TRACE_STATE("switching to RECORD_H", FCGI_EV_TX_RECORD|FCGI_EV_RX_RECORD|FCGI_EV_RX_FHDR, fconn->conn);
				fcgi_wake_unassigned_streams(fconn);
				goto mux;
			}
			TRACE_PROTO("sending FCGI GET_VALUES record", FCGI_EV_TX_RECORD|FCGI_EV_TX_GETVAL, fconn->conn);
			if (unlikely(!fcgi_conn_send_get_values(fconn)))
				goto fail;
			fconn->state = FCGI_CS_SETTINGS;
			TRACE_STATE("switching to SETTINGS", FCGI_EV_TX_RECORD|FCGI_EV_RX_RECORD|FCGI_EV_RX_GETVAL, fconn->conn);
		}
		/* need to wait for the other side */
		if (fconn->state < FCGI_CS_RECORD_H)
			goto done;
	}

  mux:
	list_for_each_entry_safe(fstrm, fstrm_back, &fconn->send_list, send_list) {
		if (fconn->state == FCGI_CS_CLOSED || fconn->flags & FCGI_CF_MUX_BLOCK_ANY)
			break;

		if (fstrm->flags & FCGI_SF_NOTIFIED)
			continue;

		/* If the sender changed his mind and unsubscribed, let's just
		 * remove the stream from the send_list.
		 */
		if (!(fstrm->flags & (FCGI_SF_WANT_SHUTR|FCGI_SF_WANT_SHUTW)) &&
		    (!fstrm->subs || !(fstrm->subs->events & SUB_RETRY_SEND))) {
			LIST_DEL_INIT(&fstrm->send_list);
			continue;
		}

		if (fstrm->subs && fstrm->subs->events & SUB_RETRY_SEND) {
			TRACE_POINT(FCGI_EV_STRM_WAKE, fconn->conn, fstrm);
			fstrm->flags &= ~FCGI_SF_BLK_ANY;
			fstrm->flags |= FCGI_SF_NOTIFIED;
			tasklet_wakeup(fstrm->subs->tasklet);
			fstrm->subs->events &= ~SUB_RETRY_SEND;
			if (!fstrm->subs->events)
				fstrm->subs = NULL;
		} else {
			/* it's the shut request that was queued */
			TRACE_POINT(FCGI_EV_STRM_WAKE, fconn->conn, fstrm);
			tasklet_wakeup(fstrm->shut_tl);
		}
	}

 fail:
	if (fconn->state == FCGI_CS_CLOSED) {
		if (fconn->stream_cnt - fconn->nb_reserved > 0) {
			fcgi_conn_send_aborts(fconn);
			if (fconn->flags & FCGI_CF_MUX_BLOCK_ANY) {
				TRACE_DEVEL("leaving in blocked situation", FCGI_EV_FCONN_WAKE|FCGI_EV_FCONN_BLK, fconn->conn);
				return 0;
			}
		}
	}

  done:
	TRACE_LEAVE(FCGI_EV_FCONN_WAKE, fconn->conn);
	return 1;
}


/* Attempt to read data, and subscribe if none available.
 * The function returns 1 if data has been received, otherwise zero.
 */
static int fcgi_recv(struct fcgi_conn *fconn)
{
	struct connection *conn = fconn->conn;
	struct buffer *buf;
	int max;
	size_t ret;

	TRACE_ENTER(FCGI_EV_FCONN_RECV, conn);

	if (fconn->wait_event.events & SUB_RETRY_RECV) {
		TRACE_DEVEL("leaving on sub_recv", FCGI_EV_FCONN_RECV, conn);
		return (b_data(&fconn->dbuf));
	}

	if (!fcgi_recv_allowed(fconn)) {
		TRACE_DEVEL("leaving on !recv_allowed", FCGI_EV_FCONN_RECV, conn);
		return 1;
	}

	buf = fcgi_get_buf(fconn, &fconn->dbuf);
	if (!buf) {
		TRACE_DEVEL("waiting for fconn dbuf allocation", FCGI_EV_FCONN_RECV|FCGI_EV_FCONN_BLK, conn);
		fconn->flags |= FCGI_CF_DEM_DALLOC;
		return 0;
	}

	if (!b_data(buf)) {
		/* try to pre-align the buffer like the
		 * rxbufs will be to optimize memory copies. We'll make
		 * sure that the record header lands at the end of the
		 * HTX block to alias it upon recv. We cannot use the
		 * head because rcv_buf() will realign the buffer if
		 * it's empty. Thus we cheat and pretend we already
		 * have a few bytes there.
		 */
		max = buf_room_for_htx_data(buf) + (fconn->state == FCGI_CS_RECORD_H ? FCGI_RECORD_HEADER_SZ : 0);
		buf->head = sizeof(struct htx) - (fconn->state == FCGI_CS_RECORD_H ? FCGI_RECORD_HEADER_SZ : 0);
	}
	else
		max = buf_room_for_htx_data(buf);

	ret = max ? conn->xprt->rcv_buf(conn, conn->xprt_ctx, buf, max, 0) : 0;

	if (max && !ret && fcgi_recv_allowed(fconn)) {
		TRACE_DATA("failed to receive data, subscribing", FCGI_EV_FCONN_RECV, conn);
		conn->xprt->subscribe(conn, conn->xprt_ctx, SUB_RETRY_RECV, &fconn->wait_event);
	}
	else
		TRACE_DATA("recv data", FCGI_EV_FCONN_RECV, conn, 0, 0, (size_t[]){ret});

	if (!b_data(buf)) {
		fcgi_release_buf(fconn, &fconn->dbuf);
		TRACE_LEAVE(FCGI_EV_FCONN_RECV, conn);
		return (conn->flags & CO_FL_ERROR || conn_xprt_read0_pending(conn));
	}

	if (ret == max) {
		TRACE_DEVEL("fconn dbuf full", FCGI_EV_FCONN_RECV|FCGI_EV_FCONN_BLK, conn);
		fconn->flags |= FCGI_CF_DEM_DFULL;
	}

	TRACE_LEAVE(FCGI_EV_FCONN_RECV, conn);
	return !!ret || (conn->flags & CO_FL_ERROR) || conn_xprt_read0_pending(conn);
}


/* Try to send data if possible.
 * The function returns 1 if data have been sent, otherwise zero.
 */
static int fcgi_send(struct fcgi_conn *fconn)
{
	struct connection *conn = fconn->conn;
	int done;
	int sent = 0;

	TRACE_ENTER(FCGI_EV_FCONN_SEND, conn);

	if (conn->flags & CO_FL_ERROR) {
		TRACE_DEVEL("leaving on connection error", FCGI_EV_FCONN_SEND, conn);
		return 1;
	}


	if (conn->flags & CO_FL_WAIT_XPRT) {
		/* a handshake was requested */
		goto schedule;
	}

	/* This loop is quite simple : it tries to fill as much as it can from
	 * pending streams into the existing buffer until it's reportedly full
	 * or the end of send requests is reached. Then it tries to send this
	 * buffer's contents out, marks it not full if at least one byte could
	 * be sent, and tries again.
	 *
	 * The snd_buf() function normally takes a "flags" argument which may
	 * be made of a combination of CO_SFL_MSG_MORE to indicate that more
	 * data immediately comes and CO_SFL_STREAMER to indicate that the
	 * connection is streaming lots of data (used to increase TLS record
	 * size at the expense of latency). The former can be sent any time
	 * there's a buffer full flag, as it indicates at least one stream
	 * attempted to send and failed so there are pending data. An
	 * alternative would be to set it as long as there's an active stream
	 * but that would be problematic for ACKs until we have an absolute
	 * guarantee that all waiters have at least one byte to send. The
	 * latter should possibly not be set for now.
	 */

	done = 0;
	while (!done) {
		unsigned int flags = 0;
		unsigned int released = 0;
		struct buffer *buf;

		/* fill as much as we can into the current buffer */
		while (((fconn->flags & (FCGI_CF_MUX_MFULL|FCGI_CF_MUX_MALLOC)) == 0) && !done)
			done = fcgi_process_mux(fconn);

		if (fconn->flags & FCGI_CF_MUX_MALLOC)
			done = 1; // we won't go further without extra buffers

		if (conn->flags & CO_FL_ERROR)
			break;

		if (fconn->flags & (FCGI_CF_MUX_MFULL | FCGI_CF_DEM_MROOM))
			flags |= CO_SFL_MSG_MORE;

		for (buf = br_head(fconn->mbuf); b_size(buf); buf = br_del_head(fconn->mbuf)) {
			if (b_data(buf)) {
				int ret;

				ret = conn->xprt->snd_buf(conn, conn->xprt_ctx, buf, b_data(buf), flags);
				if (!ret) {
					done = 1;
					break;
				}
				sent = 1;
				TRACE_DATA("send data", FCGI_EV_FCONN_SEND, conn, 0, 0, (size_t[]){ret});
				b_del(buf, ret);
				if (b_data(buf)) {
					done = 1;
					break;
				}
			}
			b_free(buf);
			released++;
		}

		if (released)
			offer_buffers(NULL, released);

		/* wrote at least one byte, the buffer is not full anymore */
		if (fconn->flags & (FCGI_CF_MUX_MFULL | FCGI_CF_DEM_MROOM))
			TRACE_STATE("fconn mbuf ring not fill anymore", FCGI_EV_FCONN_SEND|FCGI_EV_FCONN_BLK, conn);
		fconn->flags &= ~(FCGI_CF_MUX_MFULL | FCGI_CF_DEM_MROOM);
	}

	if (conn->flags & CO_FL_SOCK_WR_SH) {
		/* output closed, nothing to send, clear the buffer to release it */
		b_reset(br_tail(fconn->mbuf));
	}
	/* We're not full anymore, so we can wake any task that are waiting
	 * for us.
	 */
	if (!(fconn->flags & (FCGI_CF_MUX_MFULL | FCGI_CF_DEM_MROOM)) && fconn->state >= FCGI_CS_RECORD_H) {
		struct fcgi_strm *fstrm;

		list_for_each_entry(fstrm, &fconn->send_list, send_list) {
			if (fconn->state == FCGI_CS_CLOSED || fconn->flags & FCGI_CF_MUX_BLOCK_ANY)
				break;

			if (fstrm->flags & FCGI_SF_NOTIFIED)
				continue;

			/* If the sender changed his mind and unsubscribed, let's just
			 * remove the stream from the send_list.
			 */
			if (!(fstrm->flags & (FCGI_SF_WANT_SHUTR|FCGI_SF_WANT_SHUTW)) &&
			    (!fstrm->subs || !(fstrm->subs->events & SUB_RETRY_SEND))) {
				LIST_DEL_INIT(&fstrm->send_list);
				continue;
			}

			if (fstrm->subs && fstrm->subs->events & SUB_RETRY_SEND) {
				TRACE_DEVEL("waking up pending stream", FCGI_EV_FCONN_SEND|FCGI_EV_STRM_WAKE, conn, fstrm);
				fstrm->flags &= ~FCGI_SF_BLK_ANY;
				fstrm->flags |= FCGI_SF_NOTIFIED;
				tasklet_wakeup(fstrm->subs->tasklet);
				fstrm->subs->events &= ~SUB_RETRY_SEND;
				if (!fstrm->subs->events)
					fstrm->subs = NULL;
			} else {
				/* it's the shut request that was queued */
				TRACE_POINT(FCGI_EV_STRM_WAKE, fconn->conn, fstrm);
				tasklet_wakeup(fstrm->shut_tl);
			}
		}
	}
	/* We're done, no more to send */
	if (!br_data(fconn->mbuf)) {
		TRACE_DEVEL("leaving with everything sent", FCGI_EV_FCONN_SEND, conn);
		return sent;
	}
schedule:
	if (!(conn->flags & CO_FL_ERROR) && !(fconn->wait_event.events & SUB_RETRY_SEND)) {
		TRACE_STATE("more data to send, subscribing", FCGI_EV_FCONN_SEND, conn);
		conn->xprt->subscribe(conn, conn->xprt_ctx, SUB_RETRY_SEND, &fconn->wait_event);
	}

	TRACE_DEVEL("leaving with some data left to send", FCGI_EV_FCONN_SEND, conn);
	return sent;
}

/* this is the tasklet referenced in fconn->wait_event.tasklet */
struct task *fcgi_io_cb(struct task *t, void *ctx, unsigned int state)
{
	struct connection *conn;
	struct fcgi_conn *fconn = ctx;
	struct tasklet *tl = (struct tasklet *)t;
	int conn_in_list;
	int ret = 0;

	if (state & TASK_F_USR1) {
		/* the tasklet was idling on an idle connection, it might have
		 * been stolen, let's be careful!
		 */
		HA_SPIN_LOCK(IDLE_CONNS_LOCK, &idle_conns[tid].idle_conns_lock);
		if (tl->context == NULL) {
			/* The connection has been taken over by another thread,
			 * we're no longer responsible for it, so just free the
			 * tasklet, and do nothing.
			 */
			HA_SPIN_UNLOCK(IDLE_CONNS_LOCK, &idle_conns[tid].idle_conns_lock);
			tasklet_free(tl);
			return NULL;
		}
		conn = fconn->conn;
		TRACE_POINT(FCGI_EV_FCONN_WAKE, conn);

		conn_in_list = conn->flags & CO_FL_LIST_MASK;
		if (conn_in_list)
			conn_delete_from_tree(&conn->hash_node->node);

		HA_SPIN_UNLOCK(IDLE_CONNS_LOCK, &idle_conns[tid].idle_conns_lock);
	} else {
		/* we're certain the connection was not in an idle list */
		conn = fconn->conn;
		TRACE_ENTER(FCGI_EV_FCONN_WAKE, conn);
		conn_in_list = 0;
	}

	if (!(fconn->wait_event.events & SUB_RETRY_SEND))
		ret = fcgi_send(fconn);
	if (!(fconn->wait_event.events & SUB_RETRY_RECV))
		ret |= fcgi_recv(fconn);
	if (ret || b_data(&fconn->dbuf))
		ret = fcgi_process(fconn);

	/* If we were in an idle list, we want to add it back into it,
	 * unless fcgi_process() returned -1, which mean it has destroyed
	 * the connection (testing !ret is enough, if fcgi_process() wasn't
	 * called then ret will be 0 anyway.
	 */
	if (ret < 0)
		t = NULL;

	if (!ret && conn_in_list) {
		struct server *srv = objt_server(conn->target);

		HA_SPIN_LOCK(IDLE_CONNS_LOCK, &idle_conns[tid].idle_conns_lock);
		if (conn_in_list == CO_FL_SAFE_LIST)
			ebmb_insert(&srv->per_thr[tid].safe_conns, &conn->hash_node->node, sizeof(conn->hash_node->hash));
		else
			ebmb_insert(&srv->per_thr[tid].idle_conns, &conn->hash_node->node, sizeof(conn->hash_node->hash));
		HA_SPIN_UNLOCK(IDLE_CONNS_LOCK, &idle_conns[tid].idle_conns_lock);
	}
	return t;
}

/* callback called on any event by the connection handler.
 * It applies changes and returns zero, or < 0 if it wants immediate
 * destruction of the connection (which normally doesn not happen in FCGI).
 */
static int fcgi_process(struct fcgi_conn *fconn)
{
	struct connection *conn = fconn->conn;

	TRACE_POINT(FCGI_EV_FCONN_WAKE, conn);

	if (b_data(&fconn->dbuf) && !(fconn->flags & FCGI_CF_DEM_BLOCK_ANY)) {
		fcgi_process_demux(fconn);

		if (fconn->state == FCGI_CS_CLOSED || conn->flags & CO_FL_ERROR)
			b_reset(&fconn->dbuf);

		if (buf_room_for_htx_data(&fconn->dbuf))
			fconn->flags &= ~FCGI_CF_DEM_DFULL;
	}
	fcgi_send(fconn);

	if (unlikely(fconn->proxy->disabled)) {
		/* frontend is stopping, reload likely in progress, let's try
		 * to announce a graceful shutdown if not yet done. We don't
		 * care if it fails, it will be tried again later.
		 */
		TRACE_STATE("proxy stopped, sending ABORT to all streams", FCGI_EV_FCONN_WAKE|FCGI_EV_TX_RECORD, conn);
		if (!(fconn->flags & (FCGI_CF_ABRTS_SENT|FCGI_CF_ABRTS_FAILED))) {
			if (fconn->stream_cnt - fconn->nb_reserved > 0)
				fcgi_conn_send_aborts(fconn);
		}
	}

	/*
	 * If we received early data, and the handshake is done, wake
	 * any stream that was waiting for it.
	 */
	if (!(fconn->flags & FCGI_CF_WAIT_FOR_HS) &&
	    (conn->flags & (CO_FL_EARLY_SSL_HS | CO_FL_WAIT_XPRT | CO_FL_EARLY_DATA)) == CO_FL_EARLY_DATA) {
		struct eb32_node *node;
		struct fcgi_strm *fstrm;

		fconn->flags |= FCGI_CF_WAIT_FOR_HS;
		node = eb32_lookup_ge(&fconn->streams_by_id, 1);

		while (node) {
			fstrm = container_of(node, struct fcgi_strm, by_id);
			if (fstrm->cs && fstrm->cs->flags & CS_FL_WAIT_FOR_HS)
				fcgi_strm_notify_recv(fstrm);
			node = eb32_next(node);
		}
	}

	if ((conn->flags & CO_FL_ERROR) || fcgi_conn_read0_pending(fconn) ||
	    fconn->state == FCGI_CS_CLOSED || (fconn->flags & FCGI_CF_ABRTS_FAILED) ||
	    eb_is_empty(&fconn->streams_by_id)) {
		fcgi_wake_some_streams(fconn, 0);

		if (eb_is_empty(&fconn->streams_by_id)) {
			/* no more stream, kill the connection now */
			fcgi_release(fconn);
			TRACE_DEVEL("leaving after releasing the connection", FCGI_EV_FCONN_WAKE);
			return -1;
		}
	}

	if (!b_data(&fconn->dbuf))
		fcgi_release_buf(fconn, &fconn->dbuf);

	if ((conn->flags & CO_FL_SOCK_WR_SH) ||
	    fconn->state == FCGI_CS_CLOSED  || (fconn->flags & FCGI_CF_ABRTS_FAILED) ||
	    (!br_data(fconn->mbuf) && ((fconn->flags & FCGI_CF_MUX_BLOCK_ANY) || LIST_ISEMPTY(&fconn->send_list))))
		fcgi_release_mbuf(fconn);

	if (fconn->task) {
		fconn->task->expire = tick_add(now_ms, (fconn->state == FCGI_CS_CLOSED ? fconn->shut_timeout : fconn->timeout));
		task_queue(fconn->task);
	}

	fcgi_send(fconn);
	TRACE_LEAVE(FCGI_EV_FCONN_WAKE, conn);
	return 0;
}


/* wake-up function called by the connection layer (mux_ops.wake) */
static int fcgi_wake(struct connection *conn)
{
	struct fcgi_conn *fconn = conn->ctx;

	TRACE_POINT(FCGI_EV_FCONN_WAKE, conn);
	return (fcgi_process(fconn));
}


static int fcgi_ctl(struct connection *conn, enum mux_ctl_type mux_ctl, void *output)
{
	int ret = 0;
	switch (mux_ctl) {
	case MUX_STATUS:
		if (!(conn->flags & CO_FL_WAIT_XPRT))
			ret |= MUX_STATUS_READY;
		return ret;
	case MUX_EXIT_STATUS:
		return MUX_ES_UNKNOWN;
	default:
		return -1;
	}
}

/* Connection timeout management. The principle is that if there's no receipt
 * nor sending for a certain amount of time, the connection is closed. If the
 * MUX buffer still has lying data or is not allocatable, the connection is
 * immediately killed. If it's allocatable and empty, we attempt to send a
 * ABORT records.
 */
struct task *fcgi_timeout_task(struct task *t, void *context, unsigned int state)
{
	struct fcgi_conn *fconn = context;
	int expired = tick_is_expired(t->expire, now_ms);

	TRACE_ENTER(FCGI_EV_FCONN_WAKE, (fconn ? fconn->conn : NULL));

	if (fconn) {
		HA_SPIN_LOCK(IDLE_CONNS_LOCK, &idle_conns[tid].idle_conns_lock);

		/* Somebody already stole the connection from us, so we should not
		 * free it, we just have to free the task.
		 */
		if (!t->context) {
			HA_SPIN_UNLOCK(IDLE_CONNS_LOCK, &idle_conns[tid].idle_conns_lock);
			fconn = NULL;
			goto do_leave;
		}

		if (!expired) {
			HA_SPIN_UNLOCK(IDLE_CONNS_LOCK, &idle_conns[tid].idle_conns_lock);
			TRACE_DEVEL("leaving (not expired)", FCGI_EV_FCONN_WAKE, fconn->conn);
			return t;
		}

		/* We're about to destroy the connection, so make sure nobody attempts
		 * to steal it from us.
		 */
		if (fconn->conn->flags & CO_FL_LIST_MASK)
			conn_delete_from_tree(&fconn->conn->hash_node->node);

		HA_SPIN_UNLOCK(IDLE_CONNS_LOCK, &idle_conns[tid].idle_conns_lock);
	}

do_leave:
	task_destroy(t);

	if (!fconn) {
		/* resources were already deleted */
		TRACE_DEVEL("leaving (not more fconn)", FCGI_EV_FCONN_WAKE);
		return NULL;
	}

	fconn->task = NULL;
	fconn->state = FCGI_CS_CLOSED;
	fcgi_wake_some_streams(fconn, 0);

	if (br_data(fconn->mbuf)) {
		/* don't even try to send aborts, the buffer is stuck */
		fconn->flags |= FCGI_CF_ABRTS_FAILED;
		goto end;
	}

	/* try to send but no need to insist */
	if (!fcgi_conn_send_aborts(fconn))
		fconn->flags |= FCGI_CF_ABRTS_FAILED;

	if (br_data(fconn->mbuf) && !(fconn->flags & FCGI_CF_ABRTS_FAILED) &&
	    conn_xprt_ready(fconn->conn)) {
		unsigned int released = 0;
		struct buffer *buf;

		for (buf = br_head(fconn->mbuf); b_size(buf); buf = br_del_head(fconn->mbuf)) {
			if (b_data(buf)) {
				int ret = fconn->conn->xprt->snd_buf(fconn->conn, fconn->conn->xprt_ctx,
								     buf, b_data(buf), 0);
				if (!ret)
					break;
				b_del(buf, ret);
				if (b_data(buf))
					break;
				b_free(buf);
				released++;
			}
		}

		if (released)
			offer_buffers(NULL, released);
	}

  end:
	/* either we can release everything now or it will be done later once
	 * the last stream closes.
	 */
	if (eb_is_empty(&fconn->streams_by_id))
		fcgi_release(fconn);

	TRACE_LEAVE(FCGI_EV_FCONN_WAKE);
	return NULL;
}


/*******************************************/
/* functions below are used by the streams */
/*******************************************/

/* Append the description of what is present in error snapshot <es> into <out>.
 * The description must be small enough to always fit in a buffer. The output
 * buffer may be the trash so the trash must not be used inside this function.
 */
static void fcgi_show_error_snapshot(struct buffer *out, const struct error_snapshot *es)
{
	chunk_appendf(out,
		      "  FCGI connection flags 0x%08x, FCGI stream flags 0x%08x\n"
		      "  H1 msg state %s(%d), H1 msg flags 0x%08x\n"
		      "  H1 chunk len %lld bytes, H1 body len %lld bytes :\n",
		      es->ctx.h1.c_flags, es->ctx.h1.s_flags,
		      h1m_state_str(es->ctx.h1.state), es->ctx.h1.state,
		      es->ctx.h1.m_flags, es->ctx.h1.m_clen, es->ctx.h1.m_blen);
}
/*
 * Capture a bad response and archive it in the proxy's structure.  By default
 * it tries to report the error position as h1m->err_pos. However if this one is
 * not set, it will then report h1m->next, which is the last known parsing
 * point. The function is able to deal with wrapping buffers. It always displays
 * buffers as a contiguous area starting at buf->p. The direction is determined
 * thanks to the h1m's flags.
 */
static void fcgi_strm_capture_bad_message(struct fcgi_conn *fconn, struct fcgi_strm *fstrm,
					  struct h1m *h1m, struct buffer *buf)
{
	struct session *sess = fstrm->sess;
	struct proxy *proxy = fconn->proxy;
	struct proxy *other_end;
	union error_snapshot_ctx ctx;

	if (fstrm->cs && fstrm->cs->data) {
		if (sess == NULL)
			sess = si_strm(fstrm->cs->data)->sess;
		if (!(h1m->flags & H1_MF_RESP))
			other_end = si_strm(fstrm->cs->data)->be;
		else
			other_end = sess->fe;
	} else
		other_end = NULL;
	/* http-specific part now */
	ctx.h1.state   = h1m->state;
	ctx.h1.c_flags = fconn->flags;
	ctx.h1.s_flags = fstrm->flags;
	ctx.h1.m_flags = h1m->flags;
	ctx.h1.m_clen  = h1m->curr_len;
	ctx.h1.m_blen  = h1m->body_len;

	proxy_capture_error(proxy, 1, other_end, fconn->conn->target, sess, buf, 0, 0,
			    (h1m->err_pos >= 0) ? h1m->err_pos : h1m->next,
			    &ctx, fcgi_show_error_snapshot);
}

static size_t fcgi_strm_parse_headers(struct fcgi_strm *fstrm, struct h1m *h1m, struct htx *htx,
				      struct buffer *buf, size_t *ofs, size_t max)
{
	int ret;

	TRACE_ENTER(FCGI_EV_RSP_DATA|FCGI_EV_RSP_HDRS, fstrm->fconn->conn, fstrm, 0, (size_t[]){max});
	ret = h1_parse_msg_hdrs(h1m, NULL, htx, buf, *ofs, max);
	if (!ret) {
		TRACE_DEVEL("leaving on missing data or error", FCGI_EV_RSP_DATA|FCGI_EV_RSP_HDRS, fstrm->fconn->conn, fstrm);
		if (htx->flags & HTX_FL_PARSING_ERROR) {
			TRACE_ERROR("parsing error, reject H1 response", FCGI_EV_RSP_DATA|FCGI_EV_RSP_HDRS|FCGI_EV_FSTRM_ERR, fstrm->fconn->conn, fstrm);
			fcgi_strm_error(fstrm);
			fcgi_strm_capture_bad_message(fstrm->fconn, fstrm, h1m, buf);
		}
		goto end;
	}

	*ofs += ret;
  end:
	TRACE_LEAVE(FCGI_EV_RSP_DATA|FCGI_EV_RSP_HDRS, fstrm->fconn->conn, fstrm, 0, (size_t[]){ret});
	return ret;

}

static size_t fcgi_strm_parse_data(struct fcgi_strm *fstrm, struct h1m *h1m, struct htx **htx,
				   struct buffer *buf, size_t *ofs, size_t max, struct buffer *htxbuf)
{
	int ret;

	TRACE_ENTER(FCGI_EV_RSP_DATA|FCGI_EV_RSP_BODY, fstrm->fconn->conn, fstrm, 0, (size_t[]){max});
	ret = h1_parse_msg_data(h1m, htx, buf, *ofs, max, htxbuf);
	if (!ret) {
		TRACE_DEVEL("leaving on missing data or error", FCGI_EV_RSP_DATA|FCGI_EV_RSP_BODY, fstrm->fconn->conn, fstrm);
		if ((*htx)->flags & HTX_FL_PARSING_ERROR) {
			TRACE_ERROR("parsing error, reject H1 response", FCGI_EV_RSP_DATA|FCGI_EV_RSP_BODY|FCGI_EV_FSTRM_ERR, fstrm->fconn->conn, fstrm);
			fcgi_strm_error(fstrm);
			fcgi_strm_capture_bad_message(fstrm->fconn, fstrm, h1m, buf);
		}
		goto end;
	}
	*ofs += ret;
  end:
	TRACE_LEAVE(FCGI_EV_RSP_DATA|FCGI_EV_RSP_BODY, fstrm->fconn->conn, fstrm, 0, (size_t[]){ret});
	return ret;
}

static size_t fcgi_strm_parse_trailers(struct fcgi_strm *fstrm, struct h1m *h1m, struct htx *htx,
				       struct buffer *buf, size_t *ofs, size_t max)
{
	int ret;

	TRACE_ENTER(FCGI_EV_RSP_DATA|FCGI_EV_RSP_TLRS, fstrm->fconn->conn, fstrm, 0, (size_t[]){max});
	ret = h1_parse_msg_tlrs(h1m, htx, buf, *ofs, max);
	if (!ret) {
		TRACE_DEVEL("leaving on missing data or error", FCGI_EV_RSP_DATA|FCGI_EV_RSP_TLRS, fstrm->fconn->conn, fstrm);
		if (htx->flags & HTX_FL_PARSING_ERROR) {
			TRACE_ERROR("parsing error, reject H1 response", FCGI_EV_RSP_DATA|FCGI_EV_RSP_TLRS|FCGI_EV_FSTRM_ERR, fstrm->fconn->conn, fstrm);
			fcgi_strm_error(fstrm);
			fcgi_strm_capture_bad_message(fstrm->fconn, fstrm, h1m, buf);
		}
		goto end;
	}
	*ofs += ret;
  end:
	TRACE_LEAVE(FCGI_EV_RSP_DATA|FCGI_EV_RSP_TLRS, fstrm->fconn->conn, fstrm, 0, (size_t[]){ret});
	return ret;
}

static size_t fcgi_strm_parse_response(struct fcgi_strm *fstrm, struct buffer *buf, size_t count)
{
	struct fcgi_conn *fconn = fstrm->fconn;
	struct htx *htx;
	struct h1m *h1m = &fstrm->h1m;
	size_t ret, data, total = 0;

	htx = htx_from_buf(buf);
	TRACE_ENTER(FCGI_EV_RSP_DATA, fconn->conn, fstrm, htx, (size_t[]){count});

	data = htx->data;
	if (fstrm->state == FCGI_SS_ERROR)
		goto end;

	do {
		size_t used = htx_used_space(htx);

		if (h1m->state <= H1_MSG_LAST_LF) {
			TRACE_PROTO("parsing response headers", FCGI_EV_RSP_DATA|FCGI_EV_RSP_HDRS, fconn->conn, fstrm);
			ret = fcgi_strm_parse_headers(fstrm, h1m, htx, &fstrm->rxbuf, &total, count);
			if (!ret)
				break;

			TRACE_USER("rcvd H1 response headers", FCGI_EV_RSP_DATA|FCGI_EV_RSP_HDRS, fconn->conn, fstrm, htx);

			if ((h1m->flags & (H1_MF_VER_11|H1_MF_XFER_LEN)) == H1_MF_VER_11) {
				struct htx_blk *blk = htx_get_head_blk(htx);
				struct htx_sl *sl;

				if (!blk)
					break;
				sl = htx_get_blk_ptr(htx, blk);
				sl->flags |= HTX_SL_F_XFER_LEN;
				htx->extra = 0;
			}
		}
		else if (h1m->state < H1_MSG_TRAILERS) {
			TRACE_PROTO("parsing response payload", FCGI_EV_RSP_DATA|FCGI_EV_RSP_BODY, fconn->conn, fstrm);
			ret = fcgi_strm_parse_data(fstrm, h1m, &htx, &fstrm->rxbuf, &total, count, buf);

			if (!(h1m->flags & H1_MF_XFER_LEN) && fstrm->state != FCGI_SS_ERROR &&
			    (fstrm->flags & FCGI_SF_ES_RCVD) && b_data(&fstrm->rxbuf) == total) {
				TRACE_DEVEL("end of data", FCGI_EV_RSP_DATA, fconn->conn, fstrm);
				htx->flags |= HTX_FL_EOM;
				h1m->state = H1_MSG_DONE;
				TRACE_USER("H1 response fully rcvd", FCGI_EV_RSP_DATA|FCGI_EV_RSP_EOM, fconn->conn, fstrm, htx);
			}

			if (!ret && h1m->state != H1_MSG_DONE)
				break;

			TRACE_PROTO("rcvd response payload data", FCGI_EV_RSP_DATA|FCGI_EV_RSP_BODY, fconn->conn, fstrm, htx);
		}
		else if (h1m->state == H1_MSG_TRAILERS) {
			TRACE_PROTO("parsing response trailers", FCGI_EV_RSP_DATA|FCGI_EV_RSP_TLRS, fconn->conn, fstrm);
			ret = fcgi_strm_parse_trailers(fstrm, h1m, htx, &fstrm->rxbuf, &total, count);
			if (!ret && h1m->state != H1_MSG_DONE)
				break;

			TRACE_PROTO("rcvd H1 response trailers", FCGI_EV_RSP_DATA|FCGI_EV_RSP_TLRS, fconn->conn, fstrm, htx);
		}
		else if (h1m->state == H1_MSG_DONE) {
			TRACE_USER("H1 response fully rcvd", FCGI_EV_RSP_DATA|FCGI_EV_RSP_EOM, fconn->conn, fstrm, htx);
			if (b_data(&fstrm->rxbuf) > total) {
				htx->flags |= HTX_FL_PARSING_ERROR;
				TRACE_PROTO("too much data, parsing error", FCGI_EV_RSP_DATA, fconn->conn, fstrm);
				fcgi_strm_error(fstrm);
			}
			break;
		}
		else {
			htx->flags |= HTX_FL_PROCESSING_ERROR;
			TRACE_ERROR("unexpected processing error", FCGI_EV_RSP_DATA|FCGI_EV_STRM_ERR, fconn->conn, fstrm);
			fcgi_strm_error(fstrm);
			break;
		}

		count -= htx_used_space(htx) - used;
	} while (fstrm->state != FCGI_SS_ERROR);

	if (fstrm->state == FCGI_SS_ERROR) {
		b_reset(&fstrm->rxbuf);
		htx_to_buf(htx, buf);
		TRACE_DEVEL("leaving on error", FCGI_EV_RSP_DATA|FCGI_EV_STRM_ERR, fconn->conn, fstrm);
		return 0;
	}

	b_del(&fstrm->rxbuf, total);

  end:
	htx_to_buf(htx, buf);
	ret = htx->data - data;
	TRACE_LEAVE(FCGI_EV_RSP_DATA, fconn->conn, fstrm, htx, (size_t[]){ret});
	return ret;
}

/*
 * Attach a new stream to a connection
 * (Used for outgoing connections)
 */
static struct conn_stream *fcgi_attach(struct connection *conn, struct session *sess)
{
	struct conn_stream *cs;
	struct fcgi_strm *fstrm;
	struct fcgi_conn *fconn = conn->ctx;

	TRACE_ENTER(FCGI_EV_FSTRM_NEW, conn);
	cs = cs_new(conn, conn->target);
	if (!cs) {
		TRACE_ERROR("CS allocation failure", FCGI_EV_FSTRM_NEW|FCGI_EV_FSTRM_ERR, conn);
		goto err;
	}
	fstrm = fcgi_conn_stream_new(fconn, cs, sess);
	if (!fstrm) {
		cs_free(cs);
		goto err;
	}

	/* the connection is not idle anymore, let's mark this */
	HA_ATOMIC_AND(&fconn->wait_event.tasklet->state, ~TASK_F_USR1);
	xprt_set_used(conn, conn->xprt, conn->xprt_ctx);

	TRACE_LEAVE(FCGI_EV_FSTRM_NEW, conn, fstrm);
	return cs;

  err:
	TRACE_DEVEL("leaving on error", FCGI_EV_FSTRM_NEW|FCGI_EV_FSTRM_ERR, conn);
	return NULL;
}

/* Retrieves the first valid conn_stream from this connection, or returns NULL.
 * We have to scan because we may have some orphan streams. It might be
 * beneficial to scan backwards from the end to reduce the likeliness to find
 * orphans.
 */
static const struct conn_stream *fcgi_get_first_cs(const struct connection *conn)
{
	struct fcgi_conn *fconn = conn->ctx;
	struct fcgi_strm *fstrm;
	struct eb32_node *node;

	node = eb32_first(&fconn->streams_by_id);
	while (node) {
		fstrm = container_of(node, struct fcgi_strm, by_id);
		if (fstrm->cs)
			return fstrm->cs;
		node = eb32_next(node);
	}
	return NULL;
}

/*
 * Destroy the mux and the associated connection, if it is no longer used
 */
static void fcgi_destroy(void *ctx)
{
	struct fcgi_conn *fconn = ctx;

	TRACE_POINT(FCGI_EV_FCONN_END, fconn->conn);
	if (eb_is_empty(&fconn->streams_by_id) || !fconn->conn || fconn->conn->ctx != fconn)
		fcgi_release(fconn);
}

/*
 * Detach the stream from the connection and possibly release the connection.
 */
static void fcgi_detach(struct conn_stream *cs)
{
	struct fcgi_strm *fstrm = cs->ctx;
	struct fcgi_conn *fconn;
	struct session *sess;

	TRACE_ENTER(FCGI_EV_STRM_END, (fstrm ? fstrm->fconn->conn : NULL), fstrm);

	cs->ctx = NULL;
	if (!fstrm) {
		TRACE_LEAVE(FCGI_EV_STRM_END);
		return;
	}

	/* there's no txbuf so we're certain no to be able to send anything */
	fstrm->flags &= ~FCGI_SF_NOTIFIED;

	sess = fstrm->sess;
	fconn = fstrm->fconn;
	fstrm->cs = NULL;
	fconn->nb_cs--;

	if (fstrm->proto_status == FCGI_PS_CANT_MPX_CONN) {
		fconn->flags &= ~FCGI_CF_MPXS_CONNS;
		fconn->streams_limit = 1;
	}
	else if (fstrm->proto_status == FCGI_PS_OVERLOADED ||
		 fstrm->proto_status == FCGI_PS_UNKNOWN_ROLE) {
		fconn->flags &= ~FCGI_CF_KEEP_CONN;
		fconn->state = FCGI_CS_CLOSED;
	}

	/* this stream may be blocked waiting for some data to leave, so orphan
	 * it in this case.
	 */
	if (!(cs->conn->flags & CO_FL_ERROR) &&
	    (fconn->state != FCGI_CS_CLOSED) &&
	    (fstrm->flags & (FCGI_SF_BLK_MBUSY|FCGI_SF_BLK_MROOM)) &&
	    (fstrm->subs || (fstrm->flags & (FCGI_SF_WANT_SHUTR|FCGI_SF_WANT_SHUTW)))) {
		TRACE_DEVEL("leaving on stream blocked", FCGI_EV_STRM_END|FCGI_EV_FSTRM_BLK, fconn->conn, fstrm);
		return;
	}

	if ((fconn->flags & FCGI_CF_DEM_BLOCK_ANY && fstrm->id == fconn->dsi)) {
		/* unblock the connection if it was blocked on this stream. */
		fconn->flags &= ~FCGI_CF_DEM_BLOCK_ANY;
		fcgi_conn_restart_reading(fconn, 1);
	}

	fcgi_strm_destroy(fstrm);

	if (!(fconn->conn->flags & (CO_FL_ERROR|CO_FL_SOCK_RD_SH|CO_FL_SOCK_WR_SH)) &&
	    (fconn->flags & FCGI_CF_KEEP_CONN)) {
		if (fconn->conn->flags & CO_FL_PRIVATE) {
			/* Add the connection in the session serverlist, if not already done */
			if (!session_add_conn(sess, fconn->conn, fconn->conn->target)) {
				fconn->conn->owner = NULL;
				if (eb_is_empty(&fconn->streams_by_id)) {
					/* let's kill the connection right away */
					fconn->conn->mux->destroy(fconn);
					TRACE_DEVEL("outgoing connection killed", FCGI_EV_STRM_END|FCGI_EV_FCONN_ERR);
					return;
				}
			}
			if (eb_is_empty(&fconn->streams_by_id)) {
				if (session_check_idle_conn(fconn->conn->owner, fconn->conn) != 0) {
					/* The connection is destroyed, let's leave */
					TRACE_DEVEL("outgoing connection killed", FCGI_EV_STRM_END|FCGI_EV_FCONN_ERR);
					return;
				}
			}
		}
		else {
			if (eb_is_empty(&fconn->streams_by_id)) {
				/* If the connection is owned by the session, first remove it
				 * from its list
				 */
				if (fconn->conn->owner) {
					session_unown_conn(fconn->conn->owner, fconn->conn);
					fconn->conn->owner = NULL;
				}

				/* mark that the tasklet may lose its context to another thread and
				 * that the handler needs to check it under the idle conns lock.
				 */
				HA_ATOMIC_OR(&fconn->wait_event.tasklet->state, TASK_F_USR1);
				xprt_set_idle(fconn->conn, fconn->conn->xprt, fconn->conn->xprt_ctx);

				if (!srv_add_to_idle_list(objt_server(fconn->conn->target), fconn->conn, 1)) {
					/* The server doesn't want it, let's kill the connection right away */
					fconn->conn->mux->destroy(fconn);
					TRACE_DEVEL("outgoing connection killed", FCGI_EV_STRM_END|FCGI_EV_FCONN_ERR);
					return;
				}
				/* At this point, the connection has been added to the
				 * server idle list, so another thread may already have
				 * hijacked it, so we can't do anything with it.
				 */
				TRACE_DEVEL("reusable idle connection", FCGI_EV_STRM_END, fconn->conn);
				return;
			}
			else if (!fconn->conn->hash_node->node.node.leaf_p &&
				 fcgi_avail_streams(fconn->conn) > 0 && objt_server(fconn->conn->target) &&
				 !LIST_INLIST(&fconn->conn->session_list)) {
				ebmb_insert(&__objt_server(fconn->conn->target)->per_thr[tid].avail_conns,
				            &fconn->conn->hash_node->node,
				            sizeof(fconn->conn->hash_node->hash));
			}
		}
	}

	/* We don't want to close right now unless we're removing the last
	 * stream and the connection is in error.
	 */
	if (fcgi_conn_is_dead(fconn)) {
		/* no more stream will come, kill it now */
		TRACE_DEVEL("leaving, killing dead connection", FCGI_EV_STRM_END, fconn->conn);
		fcgi_release(fconn);
	}
	else if (fconn->task) {
		fconn->task->expire = tick_add(now_ms, (fconn->state == FCGI_CS_CLOSED ? fconn->shut_timeout : fconn->timeout));
		task_queue(fconn->task);
		TRACE_DEVEL("leaving, refreshing connection's timeout", FCGI_EV_STRM_END, fconn->conn);
	}
	else
		TRACE_DEVEL("leaving", FCGI_EV_STRM_END, fconn->conn);
}


/* Performs a synchronous or asynchronous shutr(). */
static void fcgi_do_shutr(struct fcgi_strm *fstrm)
{
	struct fcgi_conn *fconn = fstrm->fconn;

	TRACE_ENTER(FCGI_EV_STRM_SHUT, fconn->conn, fstrm);

	if (fstrm->state == FCGI_SS_CLOSED)
		goto done;

	/* a connstream may require us to immediately kill the whole connection
	 * for example because of a "tcp-request content reject" rule that is
	 * normally used to limit abuse.
	 */
	if ((fstrm->flags & FCGI_SF_KILL_CONN) &&
	    !(fconn->flags & (FCGI_CF_ABRTS_SENT|FCGI_CF_ABRTS_FAILED))) {
		TRACE_STATE("stream wants to kill the connection", FCGI_EV_STRM_SHUT, fconn->conn, fstrm);
		fconn->state = FCGI_CS_CLOSED;
	}
	else if (fstrm->flags & FCGI_SF_BEGIN_SENT) {
		TRACE_STATE("no headers sent yet, trying a retryable abort", FCGI_EV_STRM_SHUT, fconn->conn, fstrm);
		if (!(fstrm->flags & (FCGI_SF_ES_SENT|FCGI_SF_ABRT_SENT)) &&
		    !fcgi_strm_send_abort(fconn, fstrm))
			goto add_to_list;
	}

	fcgi_strm_close(fstrm);

	if (!(fconn->wait_event.events & SUB_RETRY_SEND))
		tasklet_wakeup(fconn->wait_event.tasklet);
  done:
	fstrm->flags &= ~FCGI_SF_WANT_SHUTR;
	TRACE_LEAVE(FCGI_EV_STRM_SHUT, fconn->conn, fstrm);
	return;

  add_to_list:
	/* Let the handler know we want to shutr, and add ourselves to the
	 * send list if not yet done. fcgi_deferred_shut() will be
	 * automatically called via the shut_tl tasklet when there's room
	 * again.
	 */
	if (!LIST_INLIST(&fstrm->send_list)) {
		if (fstrm->flags & (FCGI_SF_BLK_MBUSY|FCGI_SF_BLK_MROOM)) {
			LIST_APPEND(&fconn->send_list, &fstrm->send_list);
		}
	}
	fstrm->flags |= FCGI_SF_WANT_SHUTR;
	TRACE_LEAVE(FCGI_EV_STRM_SHUT, fconn->conn, fstrm);
	return;
}

/* Performs a synchronous or asynchronous shutw(). */
static void fcgi_do_shutw(struct fcgi_strm *fstrm)
{
	struct fcgi_conn *fconn = fstrm->fconn;

	TRACE_ENTER(FCGI_EV_STRM_SHUT, fconn->conn, fstrm);

	if (fstrm->state != FCGI_SS_HLOC || fstrm->state == FCGI_SS_CLOSED)
		goto done;

	if (fstrm->state != FCGI_SS_ERROR && (fstrm->flags & FCGI_SF_BEGIN_SENT)) {
		if (!(fstrm->flags & (FCGI_SF_ES_SENT|FCGI_SF_ABRT_SENT)) &&
		    !fcgi_strm_send_abort(fconn, fstrm))
			goto add_to_list;

		if (fstrm->state == FCGI_SS_HREM)
			fcgi_strm_close(fstrm);
		else
			fstrm->state = FCGI_SS_HLOC;
	} else {
		/* a connstream may require us to immediately kill the whole connection
		 * for example because of a "tcp-request content reject" rule that is
		 * normally used to limit abuse.
		 */
		if ((fstrm->flags & FCGI_SF_KILL_CONN) &&
		    !(fconn->flags & (FCGI_CF_ABRTS_SENT|FCGI_CF_ABRTS_FAILED))) {
			TRACE_STATE("stream wants to kill the connection", FCGI_EV_STRM_SHUT, fconn->conn, fstrm);
			fconn->state = FCGI_CS_CLOSED;
		}

		fcgi_strm_close(fstrm);
	}

	if (!(fconn->wait_event.events & SUB_RETRY_SEND))
		tasklet_wakeup(fconn->wait_event.tasklet);
  done:
	fstrm->flags &= ~FCGI_SF_WANT_SHUTW;
	TRACE_LEAVE(FCGI_EV_STRM_SHUT, fconn->conn, fstrm);
	return;

  add_to_list:
	/* Let the handler know we want to shutr, and add ourselves to the
	 * send list if not yet done. fcgi_deferred_shut() will be
	 * automatically called via the shut_tl tasklet when there's room
	 * again.
	 */
	if (!LIST_INLIST(&fstrm->send_list)) {
		if (fstrm->flags & (FCGI_SF_BLK_MBUSY|FCGI_SF_BLK_MROOM)) {
			LIST_APPEND(&fconn->send_list, &fstrm->send_list);
		}
	}
	fstrm->flags |= FCGI_SF_WANT_SHUTW;
	TRACE_LEAVE(FCGI_EV_STRM_SHUT, fconn->conn, fstrm);
	return;
}

/* This is the tasklet referenced in fstrm->shut_tl, it is used for
 * deferred shutdowns when the fcgi_detach() was done but the mux buffer was full
 * and prevented the last record from being emitted.
 */
struct task *fcgi_deferred_shut(struct task *t, void *ctx, unsigned int state)
{
	struct fcgi_strm *fstrm = ctx;
	struct fcgi_conn *fconn = fstrm->fconn;

	TRACE_ENTER(FCGI_EV_STRM_SHUT, fconn->conn, fstrm);

	if (fstrm->flags & FCGI_SF_NOTIFIED) {
		/* some data processing remains to be done first */
		goto end;
	}

	if (fstrm->flags & FCGI_SF_WANT_SHUTW)
		fcgi_do_shutw(fstrm);

	if (fstrm->flags & FCGI_SF_WANT_SHUTR)
		fcgi_do_shutr(fstrm);

	if (!(fstrm->flags & (FCGI_SF_WANT_SHUTR|FCGI_SF_WANT_SHUTW))) {
		/* We're done trying to send, remove ourself from the send_list */
		LIST_DEL_INIT(&fstrm->send_list);

		if (!fstrm->cs) {
			fcgi_strm_destroy(fstrm);
			if (fcgi_conn_is_dead(fconn))
				fcgi_release(fconn);
		}
	}
 end:
	TRACE_LEAVE(FCGI_EV_STRM_SHUT);
	return NULL;
}

/* shutr() called by the conn_stream (mux_ops.shutr) */
static void fcgi_shutr(struct conn_stream *cs, enum cs_shr_mode mode)
{
	struct fcgi_strm *fstrm = cs->ctx;

	TRACE_POINT(FCGI_EV_STRM_SHUT, fstrm->fconn->conn, fstrm);
	if (cs->flags & CS_FL_KILL_CONN)
		fstrm->flags |= FCGI_SF_KILL_CONN;

	if (!mode)
		return;

	fcgi_do_shutr(fstrm);
}

/* shutw() called by the conn_stream (mux_ops.shutw) */
static void fcgi_shutw(struct conn_stream *cs, enum cs_shw_mode mode)
{
	struct fcgi_strm *fstrm = cs->ctx;

	TRACE_POINT(FCGI_EV_STRM_SHUT, fstrm->fconn->conn, fstrm);
	if (cs->flags & CS_FL_KILL_CONN)
		fstrm->flags |= FCGI_SF_KILL_CONN;

	fcgi_do_shutw(fstrm);
}

/* Called from the upper layer, to subscribe <es> to events <event_type>. The
 * event subscriber <es> is not allowed to change from a previous call as long
 * as at least one event is still subscribed. The <event_type> must only be a
 * combination of SUB_RETRY_RECV and SUB_RETRY_SEND. It always returns 0.
 */
static int fcgi_subscribe(struct conn_stream *cs, int event_type, struct wait_event *es)
{
	struct fcgi_strm *fstrm = cs->ctx;
	struct fcgi_conn *fconn = fstrm->fconn;

	BUG_ON(event_type & ~(SUB_RETRY_SEND|SUB_RETRY_RECV));
	BUG_ON(fstrm->subs && fstrm->subs != es);

	es->events |= event_type;
	fstrm->subs = es;

	if (event_type & SUB_RETRY_RECV)
		TRACE_DEVEL("unsubscribe(recv)", FCGI_EV_STRM_RECV, fconn->conn, fstrm);

	if (event_type & SUB_RETRY_SEND) {
		TRACE_DEVEL("unsubscribe(send)", FCGI_EV_STRM_SEND, fconn->conn, fstrm);
		if (!LIST_INLIST(&fstrm->send_list))
			LIST_APPEND(&fconn->send_list, &fstrm->send_list);
	}
	return 0;
}

/* Called from the upper layer, to unsubscribe <es> from events <event_type>
 * (undo fcgi_subscribe). The <es> pointer is not allowed to differ from the one
 * passed to the subscribe() call. It always returns zero.
 */
static int fcgi_unsubscribe(struct conn_stream *cs, int event_type, struct wait_event *es)
{
	struct fcgi_strm *fstrm = cs->ctx;
	struct fcgi_conn *fconn = fstrm->fconn;

	BUG_ON(event_type & ~(SUB_RETRY_SEND|SUB_RETRY_RECV));
	BUG_ON(fstrm->subs && fstrm->subs != es);

	es->events &= ~event_type;
	if (!es->events)
		fstrm->subs = NULL;

	if (event_type & SUB_RETRY_RECV)
		TRACE_DEVEL("subscribe(recv)", FCGI_EV_STRM_RECV, fconn->conn, fstrm);

	if (event_type & SUB_RETRY_SEND) {
		TRACE_DEVEL("subscribe(send)", FCGI_EV_STRM_SEND, fconn->conn, fstrm);
		fstrm->flags &= ~FCGI_SF_NOTIFIED;
		if (!(fstrm->flags & (FCGI_SF_WANT_SHUTR|FCGI_SF_WANT_SHUTW)))
			LIST_DEL_INIT(&fstrm->send_list);
	}
	return 0;
}

/* Called from the upper layer, to receive data */
static size_t fcgi_rcv_buf(struct conn_stream *cs, struct buffer *buf, size_t count, int flags)
{
	struct fcgi_strm *fstrm = cs->ctx;
	struct fcgi_conn *fconn = fstrm->fconn;
	size_t ret = 0;

	TRACE_ENTER(FCGI_EV_STRM_RECV, fconn->conn, fstrm);

	if (!(fconn->flags & FCGI_CF_DEM_SALLOC))
		ret = fcgi_strm_parse_response(fstrm, buf, count);
	else
		TRACE_STATE("fstrm rxbuf not allocated", FCGI_EV_STRM_RECV|FCGI_EV_FSTRM_BLK, fconn->conn, fstrm);

	if (b_data(&fstrm->rxbuf))
		cs->flags |= (CS_FL_RCV_MORE | CS_FL_WANT_ROOM);
	else {
		cs->flags &= ~(CS_FL_RCV_MORE | CS_FL_WANT_ROOM);
		if (fstrm->state == FCGI_SS_ERROR || (fstrm->h1m.state == H1_MSG_DONE)) {
			cs->flags |= CS_FL_EOI;
			if (!(fstrm->h1m.flags & (H1_MF_VER_11|H1_MF_XFER_LEN)))
				cs->flags |= CS_FL_EOS;
		}
		if (fcgi_conn_read0_pending(fconn))
			cs->flags |= CS_FL_EOS;
		if (cs->flags & CS_FL_ERR_PENDING)
			cs->flags |= CS_FL_ERROR;
		fcgi_release_buf(fconn, &fstrm->rxbuf);
	}

	if (ret && fconn->dsi == fstrm->id) {
		/* demux is blocking on this stream's buffer */
		fconn->flags &= ~FCGI_CF_DEM_SFULL;
		fcgi_conn_restart_reading(fconn, 1);
	}

	TRACE_LEAVE(FCGI_EV_STRM_RECV, fconn->conn, fstrm);
	return ret;
}


/* Called from the upper layer, to send data from buffer <buf> for no more than
 * <count> bytes. Returns the number of bytes effectively sent. Some status
 * flags may be updated on the conn_stream.
 */
static size_t fcgi_snd_buf(struct conn_stream *cs, struct buffer *buf, size_t count, int flags)
{
	struct fcgi_strm *fstrm = cs->ctx;
	struct fcgi_conn *fconn = fstrm->fconn;
	size_t total = 0;
	size_t ret;
	struct htx *htx = NULL;
	struct htx_sl *sl;
	struct htx_blk *blk;
	uint32_t bsize;

	TRACE_ENTER(FCGI_EV_STRM_SEND, fconn->conn, fstrm, 0, (size_t[]){count});

	/* If we were not just woken because we wanted to send but couldn't,
	 * and there's somebody else that is waiting to send, do nothing,
	 * we will subscribe later and be put at the end of the list
	 */
	if (!(fstrm->flags & FCGI_SF_NOTIFIED) && !LIST_ISEMPTY(&fconn->send_list)) {
		TRACE_STATE("other streams already waiting, going to the queue and leaving", FCGI_EV_STRM_SEND|FCGI_EV_FSTRM_BLK, fconn->conn, fstrm);
		return 0;
	}
	fstrm->flags &= ~FCGI_SF_NOTIFIED;

	if (fconn->state < FCGI_CS_RECORD_H) {
		TRACE_STATE("connection not ready, leaving", FCGI_EV_STRM_SEND|FCGI_EV_FSTRM_BLK, fconn->conn, fstrm);
		return 0;
	}

	htx = htxbuf(buf);
	if (fstrm->id == 0) {
		int32_t id = fcgi_conn_get_next_sid(fconn);

		if (id < 0) {
			fcgi_strm_close(fstrm);
			cs->flags |= CS_FL_ERROR;
			TRACE_DEVEL("couldn't get a stream ID, leaving in error", FCGI_EV_STRM_SEND|FCGI_EV_FSTRM_ERR|FCGI_EV_STRM_ERR, fconn->conn, fstrm);
			return 0;
		}

		eb32_delete(&fstrm->by_id);
		fstrm->by_id.key = fstrm->id = id;
		fconn->max_id = id;
		fconn->nb_reserved--;
		eb32_insert(&fconn->streams_by_id, &fstrm->by_id);


		/* Check if length of the body is known or if the message is
		 * full. Otherwise, the request is invalid.
		 */
		sl = http_get_stline(htx);
		if (!sl || (!(sl->flags & HTX_SL_F_CLEN) && !(htx->flags & HTX_FL_EOM))) {
			htx->flags |= HTX_FL_PARSING_ERROR;
			fcgi_strm_error(fstrm);
			goto done;
		}
	}

	if (!(fstrm->flags & FCGI_SF_BEGIN_SENT)) {
		TRACE_PROTO("sending FCGI BEGIN_REQUEST record", FCGI_EV_TX_RECORD|FCGI_EV_TX_BEGREQ, fconn->conn, fstrm);
		if (!fcgi_strm_send_begin_request(fconn, fstrm))
			goto done;
	}

	if (!(fstrm->flags & FCGI_SF_OUTGOING_DATA) && count)
		fstrm->flags |= FCGI_SF_OUTGOING_DATA;

	while (fstrm->state < FCGI_SS_HLOC && !(fstrm->flags & FCGI_SF_BLK_ANY) &&
	       count && !htx_is_empty(htx)) {
		blk = htx_get_head_blk(htx);
		ALREADY_CHECKED(blk);
		bsize = htx_get_blksz(blk);

		switch (htx_get_blk_type(blk)) {
			case HTX_BLK_REQ_SL:
			case HTX_BLK_HDR:
				TRACE_USER("sending FCGI PARAMS record", FCGI_EV_TX_RECORD|FCGI_EV_TX_PARAMS, fconn->conn, fstrm, htx);
				ret = fcgi_strm_send_params(fconn, fstrm, htx);
				if (!ret) {
					goto done;
				}
				total += ret;
				count -= ret;
				break;

			case HTX_BLK_EOH:
				if (!(fstrm->flags & FCGI_SF_EP_SENT)) {
					TRACE_PROTO("sending FCGI PARAMS record", FCGI_EV_TX_RECORD|FCGI_EV_TX_PARAMS, fconn->conn, fstrm, htx);
					ret = fcgi_strm_send_empty_params(fconn, fstrm);
					if (!ret)
						goto done;
				}
				if (htx_is_unique_blk(htx, blk) && (htx->flags & HTX_FL_EOM)) {
					TRACE_PROTO("sending FCGI STDIN record", FCGI_EV_TX_RECORD|FCGI_EV_TX_STDIN, fconn->conn, fstrm, htx);
					ret = fcgi_strm_send_empty_stdin(fconn, fstrm);
					if (!ret)
						goto done;
				}
				goto remove_blk;

			case HTX_BLK_DATA:
				TRACE_PROTO("sending FCGI STDIN record", FCGI_EV_TX_RECORD|FCGI_EV_TX_STDIN, fconn->conn, fstrm, htx);
				ret = fcgi_strm_send_stdin(fconn, fstrm, htx, count, buf);
				if (ret > 0) {
					htx = htx_from_buf(buf);
					total += ret;
					count -= ret;
					if (ret < bsize)
						goto done;
				}
				break;

			default:
			  remove_blk:
				htx_remove_blk(htx, blk);
				total += bsize;
				count -= bsize;
				break;
		}
	}

  done:
	if (fstrm->state >= FCGI_SS_HLOC) {
		/* trim any possibly pending data after we close (extra CR-LF,
		 * unprocessed trailers, abnormal extra data, ...)
		 */
		total += count;
		count = 0;
	}

	if (fstrm->state == FCGI_SS_ERROR) {
		TRACE_DEVEL("reporting error to the app-layer stream", FCGI_EV_STRM_SEND|FCGI_EV_FSTRM_ERR|FCGI_EV_STRM_ERR, fconn->conn, fstrm);
		cs_set_error(cs);
		if (!(fstrm->flags & FCGI_SF_BEGIN_SENT) || fcgi_strm_send_abort(fconn, fstrm))
			fcgi_strm_close(fstrm);
	}

	if (htx)
		htx_to_buf(htx, buf);

	if (total > 0) {
		if (!(fconn->wait_event.events & SUB_RETRY_SEND)) {
			TRACE_DEVEL("data queued, waking up fconn sender", FCGI_EV_STRM_SEND|FCGI_EV_FCONN_SEND|FCGI_EV_FCONN_WAKE, fconn->conn, fstrm);
			tasklet_wakeup(fconn->wait_event.tasklet);
		}

		/* Ok we managed to send something, leave the send_list */
		if (!(fstrm->flags & (FCGI_SF_WANT_SHUTR|FCGI_SF_WANT_SHUTW)))
			LIST_DEL_INIT(&fstrm->send_list);
	}

	TRACE_LEAVE(FCGI_EV_STRM_SEND, fconn->conn, fstrm, htx, (size_t[]){total});
	return total;
}

/* for debugging with CLI's "show fd" command */
static int fcgi_show_fd(struct buffer *msg, struct connection *conn)
{
	struct fcgi_conn *fconn = conn->ctx;
	struct fcgi_strm *fstrm = NULL;
	struct eb32_node *node;
	int send_cnt = 0;
	int tree_cnt = 0;
	int orph_cnt = 0;
	struct buffer *hmbuf, *tmbuf;

	if (!fconn)
		return 0;

	list_for_each_entry(fstrm, &fconn->send_list, send_list)
		send_cnt++;

	fstrm = NULL;
	node = eb32_first(&fconn->streams_by_id);
	while (node) {
		fstrm = container_of(node, struct fcgi_strm, by_id);
		tree_cnt++;
		if (!fstrm->cs)
			orph_cnt++;
		node = eb32_next(node);
	}

	hmbuf = br_head(fconn->mbuf);
	tmbuf = br_tail(fconn->mbuf);
	chunk_appendf(msg, " fconn.st0=%d .maxid=%d .flg=0x%04x .nbst=%u"
		      " .nbcs=%u .send_cnt=%d .tree_cnt=%d .orph_cnt=%d .sub=%d "
		      ".dsi=%d .dbuf=%u@%p+%u/%u .mbuf=[%u..%u|%u],h=[%u@%p+%u/%u],t=[%u@%p+%u/%u]",
		      fconn->state, fconn->max_id, fconn->flags,
		      fconn->nb_streams, fconn->nb_cs, send_cnt, tree_cnt, orph_cnt,
		      fconn->wait_event.events, fconn->dsi,
		      (unsigned int)b_data(&fconn->dbuf), b_orig(&fconn->dbuf),
		      (unsigned int)b_head_ofs(&fconn->dbuf), (unsigned int)b_size(&fconn->dbuf),
		      br_head_idx(fconn->mbuf), br_tail_idx(fconn->mbuf), br_size(fconn->mbuf),
		      (unsigned int)b_data(hmbuf), b_orig(hmbuf),
		      (unsigned int)b_head_ofs(hmbuf), (unsigned int)b_size(hmbuf),
		      (unsigned int)b_data(tmbuf), b_orig(tmbuf),
		      (unsigned int)b_head_ofs(tmbuf), (unsigned int)b_size(tmbuf));

	if (fstrm) {
		chunk_appendf(msg, " last_fstrm=%p .id=%d .flg=0x%04x .rxbuf=%u@%p+%u/%u .cs=%p",
			      fstrm, fstrm->id, fstrm->flags,
			      (unsigned int)b_data(&fstrm->rxbuf), b_orig(&fstrm->rxbuf),
			      (unsigned int)b_head_ofs(&fstrm->rxbuf), (unsigned int)b_size(&fstrm->rxbuf),
			      fstrm->cs);
		if (fstrm->cs)
			chunk_appendf(msg, " .cs.flg=0x%08x .cs.data=%p",
				      fstrm->cs->flags, fstrm->cs->data);
		chunk_appendf(&trash, " .subs=%p", fstrm->subs);
		if (fstrm->subs) {
			chunk_appendf(&trash, "(ev=%d tl=%p", fstrm->subs->events, fstrm->subs->tasklet);
			chunk_appendf(&trash, " tl.calls=%d tl.ctx=%p tl.fct=",
				      fstrm->subs->tasklet->calls,
				      fstrm->subs->tasklet->context);
			resolve_sym_name(&trash, NULL, fstrm->subs->tasklet->process);
			chunk_appendf(&trash, ")");
		}
	}
	return 0;
}

/* Migrate the the connection to the current thread.
 * Return 0 if successful, non-zero otherwise.
 * Expected to be called with the old thread lock held.
 */
static int fcgi_takeover(struct connection *conn, int orig_tid)
{
	struct fcgi_conn *fcgi = conn->ctx;
	struct task *task;

	if (fd_takeover(conn->handle.fd, conn) != 0)
		return -1;

	if (conn->xprt->takeover && conn->xprt->takeover(conn, conn->xprt_ctx, orig_tid) != 0) {
		/* We failed to takeover the xprt, even if the connection may
		 * still be valid, flag it as error'd, as we have already
		 * taken over the fd, and wake the tasklet, so that it will
		 * destroy it.
		 */
		conn->flags |= CO_FL_ERROR;
		tasklet_wakeup_on(fcgi->wait_event.tasklet, orig_tid);
		return -1;
	}

	if (fcgi->wait_event.events)
		fcgi->conn->xprt->unsubscribe(fcgi->conn, fcgi->conn->xprt_ctx,
		    fcgi->wait_event.events, &fcgi->wait_event);
	/* To let the tasklet know it should free itself, and do nothing else,
	 * set its context to NULL;
	 */
	fcgi->wait_event.tasklet->context = NULL;
	tasklet_wakeup_on(fcgi->wait_event.tasklet, orig_tid);

	task = fcgi->task;
	if (task) {
		task->context = NULL;
		fcgi->task = NULL;
		__ha_barrier_store();
		task_kill(task);

		fcgi->task = task_new(tid_bit);
		if (!fcgi->task) {
			fcgi_release(fcgi);
			return -1;
		}
		fcgi->task->process = fcgi_timeout_task;
		fcgi->task->context = fcgi;
	}
	fcgi->wait_event.tasklet = tasklet_new();
	if (!fcgi->wait_event.tasklet) {
		fcgi_release(fcgi);
		return -1;
	}
	fcgi->wait_event.tasklet->process = fcgi_io_cb;
	fcgi->wait_event.tasklet->context = fcgi;
	fcgi->conn->xprt->subscribe(fcgi->conn, fcgi->conn->xprt_ctx,
		                    SUB_RETRY_RECV, &fcgi->wait_event);

	return 0;
}

/****************************************/
/* MUX initialization and instantiation */
/****************************************/

/* The mux operations */
static const struct mux_ops mux_fcgi_ops = {
	.init          = fcgi_init,
	.wake          = fcgi_wake,
	.attach        = fcgi_attach,
	.get_first_cs  = fcgi_get_first_cs,
	.detach        = fcgi_detach,
	.destroy       = fcgi_destroy,
	.avail_streams = fcgi_avail_streams,
	.used_streams  = fcgi_used_streams,
	.rcv_buf       = fcgi_rcv_buf,
	.snd_buf       = fcgi_snd_buf,
	.subscribe     = fcgi_subscribe,
	.unsubscribe   = fcgi_unsubscribe,
	.shutr         = fcgi_shutr,
	.shutw         = fcgi_shutw,
	.ctl           = fcgi_ctl,
	.show_fd       = fcgi_show_fd,
	.takeover      = fcgi_takeover,
	.flags         = MX_FL_HTX|MX_FL_HOL_RISK|MX_FL_NO_UPG,
	.name          = "FCGI",
};


/* this mux registers FCGI proto */
static struct mux_proto_list mux_proto_fcgi =
{ .token = IST("fcgi"), .mode = PROTO_MODE_HTTP, .side = PROTO_SIDE_BE, .mux = &mux_fcgi_ops };

INITCALL1(STG_REGISTER, register_mux_proto, &mux_proto_fcgi);

/*
 * Local variables:
 *  c-indent-level: 8
 *  c-basic-offset: 8
 * End:
 */
