REORG/MINOR: use dedicated proxy flags for the cookie handling

Cookies were mixed with many other options while they're not used as options.
Move them to a dedicated bitmask (ck_opts). This has released 7 flags in the
proxy options and leaves some room for new proxy flags.
This commit is contained in:
Willy Tarreau 2012-05-31 20:40:20 +02:00
parent 99a7ca2fa6
commit 674021329c
4 changed files with 43 additions and 37 deletions

View File

@ -73,18 +73,13 @@ enum {
/* bits for proxy->options */
#define PR_O_REDISP 0x00000001 /* allow reconnection to dispatch in case of errors */
#define PR_O_TRANSP 0x00000002 /* transparent mode : use original DEST as dispatch */
#define PR_O_COOK_RW 0x00000004 /* rewrite all direct cookies with the right serverid */
#define PR_O_COOK_IND 0x00000008 /* keep only indirect cookies */
#define PR_O_COOK_INS 0x00000010 /* insert cookies when not accessing a server directly */
#define PR_O_COOK_PFX 0x00000020 /* rewrite all cookies by prefixing the right serverid */
#define PR_O_COOK_ANY (PR_O_COOK_RW | PR_O_COOK_IND | PR_O_COOK_INS | PR_O_COOK_PFX)
/* unused: 0x04, 0x08, 0x10, 0x20 */
#define PR_O_DISPATCH 0x00000040 /* use dispatch mode */
#define PR_O_KEEPALIVE 0x00000080 /* follow keep-alive sessions */
#define PR_O_FWDFOR 0x00000100 /* conditionally insert x-forwarded-for with client address */
#define PR_O_BIND_SRC 0x00000200 /* bind to a specific source address when connect()ing */
#define PR_O_NULLNOLOG 0x00000400 /* a connect without request will not be logged */
#define PR_O_COOK_NOC 0x00000800 /* add a 'Cache-control' header with the cookie */
#define PR_O_COOK_POST 0x00001000 /* don't insert cookies for requests other than a POST */
/* unused: 0x0800, 0x1000 */
#define PR_O_FF_ALWAYS 0x00002000 /* always set x-forwarded-for */
#define PR_O_PERSIST 0x00004000 /* server persistence stays effective even when server is down */
#define PR_O_LOGASAP 0x00008000 /* log as soon as possible, without waiting for the session to complete */
@ -150,7 +145,7 @@ enum {
#define PR_O2_EXP_RSTR 0x02000000 /* http-check expect rstring */
#define PR_O2_EXP_TYPE 0x03800000 /* mask for http-check expect type */
#define PR_O2_EXP_INV 0x04000000 /* http-check expect !<rule> */
#define PR_O2_COOK_PSV 0x08000000 /* cookie ... preserve */
/* unused: 0x08000000 */
/* server health checks */
#define PR_O2_CHK_NONE 0x00000000 /* no L7 health checks configured (TCP by default) */
@ -165,6 +160,16 @@ enum {
#define PR_O2_CHK_ANY 0xF0000000 /* Mask to cover any check */
/* end of proxy->options2 */
/* Cookie settings for pr->ck_opts */
#define PR_CK_RW 0x00000001 /* rewrite all direct cookies with the right serverid */
#define PR_CK_IND 0x00000002 /* keep only indirect cookies */
#define PR_CK_INS 0x00000004 /* insert cookies when not accessing a server directly */
#define PR_CK_PFX 0x00000008 /* rewrite all cookies by prefixing the right serverid */
#define PR_CK_ANY (PR_CK_RW | PR_CK_IND | PR_CK_INS | PR_CK_PFX)
#define PR_CK_NOC 0x00000010 /* add a 'Cache-control' header with the cookie */
#define PR_CK_POST 0x00000020 /* don't insert cookies for requests other than a POST */
#define PR_CK_PSV 0x00000040 /* cookie ... preserve */
/* bits for sticking rules */
#define STK_IS_MATCH 0x00000001 /* match on request fetch */
#define STK_IS_STORE 0x00000002 /* store on request fetch */
@ -198,6 +203,7 @@ struct proxy {
int state; /* proxy state */
int options; /* PR_O_REDISP, PR_O_TRANSP, ... */
int options2; /* PR_O2_* */
unsigned int ck_opts; /* PR_CK_* (cookie options) */
unsigned int fe_req_ana, be_req_ana; /* bitmap of common request protocol analysers for the frontend and backend */
unsigned int fe_rsp_ana, be_rsp_ana; /* bitmap of common response protocol analysers for the frontend and backend */
int mode; /* mode = PR_MODE_TCP, PR_MODE_HTTP or PR_MODE_HEALTH */

View File

@ -1489,6 +1489,7 @@ int cfg_parse_listen(const char *file, int linenum, char **args, int kwm)
}
}
curproxy->ck_opts = defproxy.ck_opts;
if (defproxy.cookie_name)
curproxy->cookie_name = strdup(defproxy.cookie_name);
curproxy->cookie_len = defproxy.cookie_len;
@ -2130,8 +2131,7 @@ int cfg_parse_listen(const char *file, int linenum, char **args, int kwm)
goto out;
}
curproxy->options &= ~PR_O_COOK_ANY;
curproxy->options2 &= ~PR_O2_COOK_PSV;
curproxy->ck_opts = 0;
curproxy->cookie_maxidle = curproxy->cookie_maxlife = 0;
free(curproxy->cookie_domain); curproxy->cookie_domain = NULL;
free(curproxy->cookie_name);
@ -2141,25 +2141,25 @@ int cfg_parse_listen(const char *file, int linenum, char **args, int kwm)
cur_arg = 2;
while (*(args[cur_arg])) {
if (!strcmp(args[cur_arg], "rewrite")) {
curproxy->options |= PR_O_COOK_RW;
curproxy->ck_opts |= PR_CK_RW;
}
else if (!strcmp(args[cur_arg], "indirect")) {
curproxy->options |= PR_O_COOK_IND;
curproxy->ck_opts |= PR_CK_IND;
}
else if (!strcmp(args[cur_arg], "insert")) {
curproxy->options |= PR_O_COOK_INS;
curproxy->ck_opts |= PR_CK_INS;
}
else if (!strcmp(args[cur_arg], "nocache")) {
curproxy->options |= PR_O_COOK_NOC;
curproxy->ck_opts |= PR_CK_NOC;
}
else if (!strcmp(args[cur_arg], "postonly")) {
curproxy->options |= PR_O_COOK_POST;
curproxy->ck_opts |= PR_CK_POST;
}
else if (!strcmp(args[cur_arg], "preserve")) {
curproxy->options2 |= PR_O2_COOK_PSV;
curproxy->ck_opts |= PR_CK_PSV;
}
else if (!strcmp(args[cur_arg], "prefix")) {
curproxy->options |= PR_O_COOK_PFX;
curproxy->ck_opts |= PR_CK_PFX;
}
else if (!strcmp(args[cur_arg], "domain")) {
if (!*args[cur_arg + 1]) {
@ -2253,19 +2253,19 @@ int cfg_parse_listen(const char *file, int linenum, char **args, int kwm)
}
cur_arg++;
}
if (!POWEROF2(curproxy->options & (PR_O_COOK_RW|PR_O_COOK_IND))) {
if (!POWEROF2(curproxy->ck_opts & (PR_CK_RW|PR_CK_IND))) {
Alert("parsing [%s:%d] : cookie 'rewrite' and 'indirect' modes are incompatible.\n",
file, linenum);
err_code |= ERR_ALERT | ERR_FATAL;
}
if (!POWEROF2(curproxy->options & (PR_O_COOK_RW|PR_O_COOK_INS|PR_O_COOK_PFX))) {
if (!POWEROF2(curproxy->ck_opts & (PR_CK_RW|PR_CK_INS|PR_CK_PFX))) {
Alert("parsing [%s:%d] : cookie 'rewrite', 'insert' and 'prefix' modes are incompatible.\n",
file, linenum);
err_code |= ERR_ALERT | ERR_FATAL;
}
if ((curproxy->options2 & PR_O2_COOK_PSV) && !(curproxy->options & (PR_O_COOK_INS|PR_O_COOK_IND))) {
if ((curproxy->ck_opts & (PR_CK_PSV | PR_CK_INS | PR_CK_IND)) == PR_CK_PSV) {
Alert("parsing [%s:%d] : cookie 'preserve' requires at least 'insert' or 'indirect'.\n",
file, linenum);
err_code |= ERR_ALERT | ERR_FATAL;
@ -6410,7 +6410,7 @@ out_uri_auth_compat:
if (curproxy->mode != PR_MODE_HTTP) {
int optnum;
if (curproxy->options & PR_O_COOK_ANY) {
if (curproxy->ck_opts) {
Warning("config : 'cookie' statement ignored for %s '%s' as it requires HTTP mode.\n",
proxy_type_str(curproxy), curproxy->id);
err_code |= ERR_WARN;

View File

@ -1091,8 +1091,8 @@ int build_logline(struct session *s, char *dst, size_t maxsize, struct list *lis
case LOG_FMT_TERMSTATE_CK: // %tsc, same as TS with cookie state (for mode HTTP)
LOGCHAR(sess_term_cond[(s->flags & SN_ERR_MASK) >> SN_ERR_SHIFT]);
LOGCHAR(sess_fin_state[(s->flags & SN_FINST_MASK) >> SN_FINST_SHIFT]);
LOGCHAR((be->options & PR_O_COOK_ANY) ? sess_cookie[(txn->flags & TX_CK_MASK) >> TX_CK_SHIFT] : '-');
LOGCHAR((be->options & PR_O_COOK_ANY) ? sess_set_cookie[(txn->flags & TX_SCK_MASK) >> TX_SCK_SHIFT] : '-');
LOGCHAR((be->ck_opts & PR_CK_ANY) ? sess_cookie[(txn->flags & TX_CK_MASK) >> TX_CK_SHIFT] : '-');
LOGCHAR((be->ck_opts & PR_CK_ANY) ? sess_set_cookie[(txn->flags & TX_SCK_MASK) >> TX_SCK_SHIFT] : '-');
last_isspace = 0;
break;

View File

@ -4715,7 +4715,7 @@ int http_wait_for_response(struct session *s, struct buffer *rep, int an_bit)
* Cache-Control or Expires header fields."
*/
if (likely(txn->meth != HTTP_METH_POST) &&
(s->be->options & (PR_O_CHK_CACHE|PR_O_COOK_NOC)))
((s->be->options & PR_O_CHK_CACHE) || (s->be->ck_opts & PR_CK_NOC)))
txn->flags |= TX_CACHEABLE | TX_CACHE_COOK;
break;
default:
@ -5034,20 +5034,20 @@ int http_process_res_common(struct session *t, struct buffer *rep, int an_bit, s
/*
* 5: check for cache-control or pragma headers if required.
*/
if ((t->be->options & (PR_O_COOK_NOC | PR_O_CHK_CACHE)) != 0)
if ((t->be->options & PR_O_CHK_CACHE) || (t->be->ck_opts & PR_CK_NOC))
check_response_for_cacheability(t, rep);
/*
* 6: add server cookie in the response if needed
*/
if (target_srv(&t->target) && (t->be->options & PR_O_COOK_INS) &&
!((txn->flags & TX_SCK_FOUND) && (t->be->options2 & PR_O2_COOK_PSV)) &&
if (target_srv(&t->target) && (t->be->ck_opts & PR_CK_INS) &&
!((txn->flags & TX_SCK_FOUND) && (t->be->ck_opts & PR_CK_PSV)) &&
(!(t->flags & SN_DIRECT) ||
((t->be->cookie_maxidle || txn->cookie_last_date) &&
(!txn->cookie_last_date || (txn->cookie_last_date - date.tv_sec) < 0)) ||
(t->be->cookie_maxlife && !txn->cookie_first_date) || // set the first_date
(!t->be->cookie_maxlife && txn->cookie_first_date)) && // remove the first_date
(!(t->be->options & PR_O_COOK_POST) || (txn->meth == HTTP_METH_POST)) &&
(!(t->be->ck_opts & PR_CK_POST) || (txn->meth == HTTP_METH_POST)) &&
!(t->flags & SN_IGNORE_PRST)) {
int len;
/* the server is known, it's not the one the client requested, or the
@ -5100,7 +5100,7 @@ int http_process_res_common(struct session *t, struct buffer *rep, int an_bit, s
* Some caches understand the correct form: 'no-cache="set-cookie"', but
* others don't (eg: apache <= 1.3.26). So we use 'private' instead.
*/
if ((t->be->options & PR_O_COOK_NOC) && (txn->flags & TX_CACHEABLE)) {
if ((t->be->ck_opts & PR_CK_NOC) && (txn->flags & TX_CACHEABLE)) {
txn->flags &= ~TX_CACHEABLE & ~TX_CACHE_COOK;
@ -6127,7 +6127,7 @@ void manage_client_side_cookies(struct session *t, struct buffer *req)
* +-------------------------> hdr_beg
*/
if (t->be->options & PR_O_COOK_PFX) {
if (t->be->ck_opts & PR_CK_PFX) {
for (delim = val_beg; delim < val_end; delim++)
if (*delim == COOKIE_DELIM)
break;
@ -6241,7 +6241,7 @@ void manage_client_side_cookies(struct session *t, struct buffer *req)
* application cookie so that it does not get accidentely removed later,
* if we're in cookie prefix mode
*/
if ((t->be->options & PR_O_COOK_PFX) && (delim != val_end)) {
if ((t->be->ck_opts & PR_CK_PFX) && (delim != val_end)) {
int delta; /* negative */
delta = buffer_replace2(req, val_beg, delim + 1, NULL, 0);
@ -6256,7 +6256,7 @@ void manage_client_side_cookies(struct session *t, struct buffer *req)
preserve_hdr = 1; /* we want to keep this cookie */
}
else if (del_from == NULL &&
(t->be->options & (PR_O_COOK_INS | PR_O_COOK_IND)) == (PR_O_COOK_INS | PR_O_COOK_IND)) {
(t->be->ck_opts & (PR_CK_INS | PR_CK_IND)) == (PR_CK_INS | PR_CK_IND)) {
del_from = prev;
}
} else {
@ -6801,13 +6801,13 @@ void manage_server_side_cookies(struct session *t, struct buffer *res)
* We'll delete it too if the "indirect" option is set and we're in
* a direct access.
*/
if (t->be->options2 & PR_O2_COOK_PSV) {
if (t->be->ck_opts & PR_CK_PSV) {
/* The "preserve" flag was set, we don't want to touch the
* server's cookie.
*/
}
else if ((srv && (t->be->options & PR_O_COOK_INS)) ||
((t->flags & SN_DIRECT) && (t->be->options & PR_O_COOK_IND))) {
else if ((srv && (t->be->ck_opts & PR_CK_INS)) ||
((t->flags & SN_DIRECT) && (t->be->ck_opts & PR_CK_IND))) {
/* this cookie must be deleted */
if (*prev == ':' && next == hdr_end) {
/* whole header */
@ -6834,7 +6834,7 @@ void manage_server_side_cookies(struct session *t, struct buffer *res)
txn->flags |= TX_SCK_DELETED;
/* and go on with next cookie */
}
else if (srv && srv->cookie && (t->be->options & PR_O_COOK_RW)) {
else if (srv && srv->cookie && (t->be->ck_opts & PR_CK_RW)) {
/* replace bytes val_beg->val_end with the cookie name associated
* with this server since we know it.
*/
@ -6848,7 +6848,7 @@ void manage_server_side_cookies(struct session *t, struct buffer *res)
txn->flags &= ~TX_SCK_MASK;
txn->flags |= TX_SCK_REPLACED;
}
else if (srv && srv && (t->be->options & PR_O_COOK_PFX)) {
else if (srv && srv && (t->be->ck_opts & PR_CK_PFX)) {
/* insert the cookie name associated with this server
* before existing cookie, and insert a delimiter between them..
*/