From 1b8e68e89aadb2740d79034c217257a78e9747b9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Fr=C3=A9d=C3=A9ric=20L=C3=A9caille?= Date: Thu, 14 Mar 2019 07:07:41 +0100 Subject: [PATCH] MEDIUM: stick-table: Stop handling stick-tables as proxies. This patch adds the support for the "table" line parsing in "peers" sections to declare stick-table in such sections. This also prevents the user from having to declare dummy backends sections with a unique stick-table inside. Even if still supported, this usage will become deprecated. To do so, the ->table member of proxy struct which is a stktable struct is replaced by a pointer to a stktable struct allocated at parsing time in src/cfgparse-listen.c for the dummy stick-table backends and in src/cfgparse.c for "peers" sections. This has an impact on the code for stick-table sample converters and on the stickiness rules parsers which first store the name of the dummy before resolving the rules. This patch replaces proxy_tbl_by_name() calls by stktable_find_by_name() calls to lookup for stick-tables stored in "stktable_by_name" ebtree at parsing time. There is only one remaining place where proxy_tbl_by_name() is used: src/hlua.c. At several places in the code we relied on the fact that ->size member of stick-table was equal to zero to consider the stick-table was present by not configured, this do not make sense anymore as ->table member of struct proxyis fow now on a pointer. These tests are replaced by a test on ->table value itself. In "peers" section we do not have to temporary store the name of the section the stick-table are attached to because this name is obviously already known just after having entered this "peers" section. About the CLI stick-table I/O handler, the pointer to proxy struct is replaced by a pointer to a stktable struct. --- include/proto/stick_table.h | 4 + include/types/applet.h | 2 +- include/types/arg.h | 2 + include/types/hlua.h | 1 + include/types/proxy.h | 2 +- include/types/stick_table.h | 1 + src/action.c | 21 ++-- src/cfgparse-listen.c | 23 +++- src/cfgparse.c | 118 ++++++++++++------- src/haproxy.c | 2 +- src/hlua_fcn.c | 4 +- src/proxy.c | 16 +-- src/sample.c | 28 +++-- src/stick_table.c | 218 ++++++++++++++++++++---------------- 14 files changed, 267 insertions(+), 175 deletions(-) diff --git a/include/proto/stick_table.h b/include/proto/stick_table.h index 962c95a1f..3010d812e 100644 --- a/include/proto/stick_table.h +++ b/include/proto/stick_table.h @@ -28,9 +28,13 @@ #include #include +extern struct stktable *stktables_list; + #define stktable_data_size(type) (sizeof(((union stktable_data*)0)->type)) #define stktable_data_cast(ptr, type) ((union stktable_data*)(ptr))->type +void stktable_store_name(struct stktable *t); +struct stktable *stktable_find_by_name(const char *name); struct stksess *stksess_new(struct stktable *t, struct stktable_key *key); void stksess_setkey(struct stktable *t, struct stksess *ts, struct stktable_key *key); void stksess_free(struct stktable *t, struct stksess *ts); diff --git a/include/types/applet.h b/include/types/applet.h index 4786b31f2..b7b297cee 100644 --- a/include/types/applet.h +++ b/include/types/applet.h @@ -144,7 +144,7 @@ struct appctx { } errors; struct { void *target; /* table we want to dump, or NULL for all */ - struct proxy *proxy; /* table being currently dumped (first if NULL) */ + struct stktable *t; /* table being currently dumped (first if NULL) */ struct stksess *entry; /* last entry we were trying to dump (or first if NULL) */ long long value; /* value to compare against */ signed char data_type; /* type of data to compare, or -1 if none */ diff --git a/include/types/arg.h b/include/types/arg.h index 6580c1583..a9778f2ec 100644 --- a/include/types/arg.h +++ b/include/types/arg.h @@ -30,6 +30,7 @@ #include #include +#include /* encoding of each arg type : up to 31 types are supported */ #define ARGT_BITS 5 @@ -99,6 +100,7 @@ union arg_data { struct in6_addr ipv6; struct proxy *prx; /* used for fe, be, tables */ struct server *srv; + struct stktable *t; struct userlist *usr; struct map_descriptor *map; struct my_regex *reg; diff --git a/include/types/hlua.h b/include/types/hlua.h index f9709bbbb..36554e265 100644 --- a/include/types/hlua.h +++ b/include/types/hlua.h @@ -11,6 +11,7 @@ #include #include #include +#include #define CLASS_CORE "Core" #define CLASS_TXN "TXN" diff --git a/include/types/proxy.h b/include/types/proxy.h index dababea34..f6d2634f6 100644 --- a/include/types/proxy.h +++ b/include/types/proxy.h @@ -416,7 +416,7 @@ struct proxy { struct fe_counters fe_counters; /* frontend statistics counters */ struct list listener_queue; /* list of the temporarily limited listeners because of lack of a proxy resource */ - struct stktable table; /* table for storing sticking streams */ + struct stktable *table; /* table for storing sticking streams */ struct task *task; /* the associated task, mandatory to manage rate limiting, stopping and resource shortage, NULL if disabled */ struct list tcpcheck_rules; /* tcp-check send / expect rules */ diff --git a/include/types/stick_table.h b/include/types/stick_table.h index a6a4a49eb..ff9546cd5 100644 --- a/include/types/stick_table.h +++ b/include/types/stick_table.h @@ -152,6 +152,7 @@ struct stktable { const char *file; /* The file where the stick-table is declared. */ int line; /* The line in this the stick-table is declared. */ } conf; + struct ebpt_node name; /* Stick-table are lookup by name here. */ struct eb_root keys; /* head of sticky session tree */ struct eb_root exps; /* head of sticky session expiration tree */ struct eb_root updates; /* head of sticky updates sequence tree */ diff --git a/src/action.c b/src/action.c index 9b6dcfd80..4cce7a418 100644 --- a/src/action.c +++ b/src/action.c @@ -30,37 +30,34 @@ */ int check_trk_action(struct act_rule *rule, struct proxy *px, char **err) { - struct proxy *target; + struct stktable *target; if (rule->arg.trk_ctr.table.n) - target = proxy_tbl_by_name(rule->arg.trk_ctr.table.n); + target = stktable_find_by_name(rule->arg.trk_ctr.table.n); else - target = px; + target = px->table; if (!target) { memprintf(err, "unable to find table '%s' referenced by track-sc%d", - rule->arg.trk_ctr.table.n, trk_idx(rule->action)); + rule->arg.trk_ctr.table.n ? rule->arg.trk_ctr.table.n : px->id, + trk_idx(rule->action)); return 0; } - else if (target->table.size == 0) { - memprintf(err, "table '%s' used but not configured", - rule->arg.trk_ctr.table.n ? rule->arg.trk_ctr.table.n : px->id); - return 0; - } - else if (!stktable_compatible_sample(rule->arg.trk_ctr.expr, target->table.type)) { + + if (!stktable_compatible_sample(rule->arg.trk_ctr.expr, target->type)) { memprintf(err, "stick-table '%s' uses a type incompatible with the 'track-sc%d' rule", rule->arg.trk_ctr.table.n ? rule->arg.trk_ctr.table.n : px->id, trk_idx(rule->action)); return 0; } - else if (px->bind_proc & ~target->bind_proc) { + else if (target->proxy && (px->bind_proc & ~target->proxy->bind_proc)) { memprintf(err, "stick-table '%s' referenced by 'track-sc%d' rule not present on all processes covered by proxy '%s'", target->id, trk_idx(rule->action), px->id); return 0; } else { free(rule->arg.trk_ctr.table.n); - rule->arg.trk_ctr.table.t = &target->table; + rule->arg.trk_ctr.table.t = target; /* Note: if we decide to enhance the track-sc syntax, we may be * able to pass a list of counters to track and allocate them * right here using stktable_alloc_data_type(). diff --git a/src/cfgparse-listen.c b/src/cfgparse-listen.c index c0f4a4669..2b2785a55 100644 --- a/src/cfgparse-listen.c +++ b/src/cfgparse-listen.c @@ -1711,7 +1711,7 @@ int cfg_parse_listen(const char *file, int linenum, char **args, int kwm) LIST_ADDQ(&curproxy->persist_rules, &rule->list); } else if (!strcmp(args[0], "stick-table")) { - struct proxy *other; + struct stktable *other; if (curproxy == &defproxy) { ha_alert("parsing [%s:%d] : 'stick-table' is not supported in 'defaults' section.\n", @@ -1720,20 +1720,35 @@ int cfg_parse_listen(const char *file, int linenum, char **args, int kwm) goto out; } - other = proxy_tbl_by_name(curproxy->id); + other = stktable_find_by_name(curproxy->id); if (other) { ha_alert("parsing [%s:%d] : stick-table name '%s' conflicts with table declared in %s '%s' at %s:%d.\n", - file, linenum, curproxy->id, proxy_type_str(other), other->id, other->conf.file, other->conf.line); + file, linenum, curproxy->id, + other->proxy ? proxy_cap_str(other->proxy->cap) : "peers", + other->proxy ? other->id : other->peers.p->id, + other->conf.file, other->conf.line); err_code |= ERR_ALERT | ERR_FATAL; goto out; } - err_code |= parse_stick_table(file, linenum, args, &curproxy->table, curproxy->id, NULL); + curproxy->table = calloc(1, sizeof *curproxy->table); + if (!curproxy->table) { + ha_alert("parsing [%s:%d]: '%s %s' : memory allocation failed\n", + file, linenum, args[0], args[1]); + err_code |= ERR_ALERT | ERR_FATAL; + goto out; + } + + err_code |= parse_stick_table(file, linenum, args, curproxy->table, curproxy->id, NULL); if (err_code & ERR_FATAL) goto out; /* Store the proxy in the stick-table. */ curproxy->table->proxy = curproxy; + + stktable_store_name(curproxy->table); + curproxy->table->next = stktables_list; + stktables_list = curproxy->table; } else if (!strcmp(args[0], "stick")) { struct sticking_rule *rule; diff --git a/src/cfgparse.c b/src/cfgparse.c index 24b5714d2..3e326330f 100644 --- a/src/cfgparse.c +++ b/src/cfgparse.c @@ -856,7 +856,45 @@ int cfg_parse_peers(const char *file, int linenum, char **args, int kwm) l->default_target = curpeers->peers_fe->default_target; l->options |= LI_O_UNLIMITED; /* don't make the peers subject to global limits */ global.maxsock++; /* for the listening socket */ - } /* neither "peer" nor "peers" */ + } + else if (!strcmp(args[0], "table")) { + struct stktable *t, *other; + char *id; + + /* Line number and peer ID are updated only if this peer is the local one. */ + if (init_peers_frontend(file, -1, NULL, curpeers) != 0) { + err_code |= ERR_ALERT | ERR_ABORT; + goto out; + } + + other = stktable_find_by_name(args[1]); + if (other) { + ha_alert("parsing [%s:%d] : stick-table name '%s' conflicts with table declared in %s '%s' at %s:%d.\n", + file, linenum, args[1], + other->proxy ? proxy_cap_str(other->proxy->cap) : "peers", + other->proxy ? other->id : other->peers.p->id, + other->conf.file, other->conf.line); + err_code |= ERR_ALERT | ERR_FATAL; + goto out; + } + + t = calloc(1, sizeof *t); + id = strdup(args[1]); + if (!t || !id) { + ha_alert("parsing [%s:%d]: '%s %s' : memory allocation failed\n", + file, linenum, args[0], args[1]); + err_code |= ERR_ALERT | ERR_FATAL; + goto out; + } + + err_code |= parse_stick_table(file, linenum, args, t, id, curpeers); + if (err_code & ERR_FATAL) + goto out; + + stktable_store_name(t); + t->next = stktables_list; + stktables_list = t; + } else if (!strcmp(args[0], "disabled")) { /* disables this peers section */ curpeers->state = PR_STSTOPPED; } @@ -2171,6 +2209,7 @@ int check_config_validity() { int cfgerr = 0; struct proxy *curproxy = NULL; + struct stktable *t; struct server *newsrv = NULL; int err_code = 0; unsigned int next_pxid = 1; @@ -2261,8 +2300,8 @@ int check_config_validity() if (curproxy->state == PR_STSTOPPED) { /* ensure we don't keep listeners uselessly bound */ stop_proxy(curproxy); - free((void *)curproxy->table.peers.name); - curproxy->table.peers.p = NULL; + free((void *)curproxy->table->peers.name); + curproxy->table->peers.p = NULL; continue; } @@ -2624,79 +2663,69 @@ int check_config_validity() /* find the target table for 'stick' rules */ list_for_each_entry(mrule, &curproxy->sticking_rules, list) { - struct proxy *target; + struct stktable *target; curproxy->be_req_ana |= AN_REQ_STICKING_RULES; if (mrule->flags & STK_IS_STORE) curproxy->be_rsp_ana |= AN_RES_STORE_RULES; if (mrule->table.name) - target = proxy_tbl_by_name(mrule->table.name); + target = stktable_find_by_name(mrule->table.name); else - target = curproxy; + target = curproxy->table; if (!target) { ha_alert("Proxy '%s': unable to find stick-table '%s'.\n", curproxy->id, mrule->table.name); cfgerr++; } - else if (target->table.size == 0) { - ha_alert("Proxy '%s': stick-table '%s' used but not configured.\n", - curproxy->id, mrule->table.name ? mrule->table.name : curproxy->id); - cfgerr++; - } - else if (!stktable_compatible_sample(mrule->expr, target->table.type)) { + else if (!stktable_compatible_sample(mrule->expr, target->type)) { ha_alert("Proxy '%s': type of fetch not usable with type of stick-table '%s'.\n", curproxy->id, mrule->table.name ? mrule->table.name : curproxy->id); cfgerr++; } - else if (curproxy->bind_proc & ~target->bind_proc) { + else if (target->proxy && curproxy->bind_proc & ~target->proxy->bind_proc) { ha_alert("Proxy '%s': stick-table '%s' referenced 'stick-store' rule not present on all processes covered by proxy '%s'.\n", curproxy->id, target->id, curproxy->id); cfgerr++; } else { free((void *)mrule->table.name); - mrule->table.t = &(target->table); - stktable_alloc_data_type(&target->table, STKTABLE_DT_SERVER_ID, NULL); + mrule->table.t = target; + stktable_alloc_data_type(target, STKTABLE_DT_SERVER_ID, NULL); } } /* find the target table for 'store response' rules */ list_for_each_entry(mrule, &curproxy->storersp_rules, list) { - struct proxy *target; + struct stktable *target; curproxy->be_rsp_ana |= AN_RES_STORE_RULES; if (mrule->table.name) - target = proxy_tbl_by_name(mrule->table.name); + target = stktable_find_by_name(mrule->table.name); else - target = curproxy; + target = curproxy->table; if (!target) { ha_alert("Proxy '%s': unable to find store table '%s'.\n", curproxy->id, mrule->table.name); cfgerr++; } - else if (target->table.size == 0) { - ha_alert("Proxy '%s': stick-table '%s' used but not configured.\n", - curproxy->id, mrule->table.name ? mrule->table.name : curproxy->id); - cfgerr++; - } - else if (!stktable_compatible_sample(mrule->expr, target->table.type)) { + else if (!stktable_compatible_sample(mrule->expr, target->type)) { ha_alert("Proxy '%s': type of fetch not usable with type of stick-table '%s'.\n", curproxy->id, mrule->table.name ? mrule->table.name : curproxy->id); cfgerr++; } - else if (curproxy->bind_proc & ~target->bind_proc) { + else if (target->proxy && (curproxy->bind_proc & ~target->proxy->bind_proc)) { ha_alert("Proxy '%s': stick-table '%s' referenced 'stick-store' rule not present on all processes covered by proxy '%s'.\n", curproxy->id, target->id, curproxy->id); cfgerr++; } else { free((void *)mrule->table.name); - mrule->table.t = &(target->table); - stktable_alloc_data_type(&target->table, STKTABLE_DT_SERVER_ID, NULL); + mrule->table.t = target; + stktable_alloc_data_type(target, STKTABLE_DT_SERVER_ID, NULL); } } @@ -2760,32 +2789,32 @@ int check_config_validity() LIST_INIT(&curproxy->block_rules); } - if (curproxy->table.peers.name) { + if (curproxy->table && curproxy->table->peers.name) { struct peers *curpeers; for (curpeers = cfg_peers; curpeers; curpeers = curpeers->next) { - if (strcmp(curpeers->id, curproxy->table.peers.name) == 0) { - free((void *)curproxy->table.peers.name); - curproxy->table.peers.p = curpeers; + if (strcmp(curpeers->id, curproxy->table->peers.name) == 0) { + free((void *)curproxy->table->peers.name); + curproxy->table->peers.p = curpeers; break; } } if (!curpeers) { ha_alert("Proxy '%s': unable to find sync peers '%s'.\n", - curproxy->id, curproxy->table.peers.name); - free((void *)curproxy->table.peers.name); - curproxy->table.peers.p = NULL; + curproxy->id, curproxy->table->peers.name); + free((void *)curproxy->table->peers.name); + curproxy->table->peers.p = NULL; cfgerr++; } else if (curpeers->state == PR_STSTOPPED) { /* silently disable this peers section */ - curproxy->table.peers.p = NULL; + curproxy->table->peers.p = NULL; } else if (!curpeers->peers_fe) { ha_alert("Proxy '%s': unable to find local peer '%s' in peers section '%s'.\n", curproxy->id, localpeer, curpeers->id); - curproxy->table.peers.p = NULL; + curproxy->table->peers.p = NULL; cfgerr++; } } @@ -3829,8 +3858,8 @@ out_uri_auth_compat: /* compute the required process bindings for the peers */ for (curproxy = proxies_list; curproxy; curproxy = curproxy->next) - if (curproxy->table.peers.p) - curproxy->table.peers.p->peers_fe->bind_proc |= curproxy->bind_proc; + if (curproxy->table && curproxy->table->peers.p) + curproxy->table->peers.p->peers_fe->bind_proc |= curproxy->bind_proc; if (cfg_peers) { struct peers *curpeers = cfg_peers, **last; @@ -3920,15 +3949,24 @@ out_uri_auth_compat: } } + for (t = stktables_list; t; t = t->next) { + if (t->proxy) + continue; + if (!stktable_init(t)) { + ha_alert("Proxy '%s': failed to initialize stick-table.\n", t->id); + cfgerr++; + } + } + /* initialize stick-tables on backend capable proxies. This must not * be done earlier because the data size may be discovered while parsing * other proxies. */ for (curproxy = proxies_list; curproxy; curproxy = curproxy->next) { - if (curproxy->state == PR_STSTOPPED) + if (curproxy->state == PR_STSTOPPED || !curproxy->table) continue; - if (!stktable_init(&curproxy->table)) { + if (!stktable_init(curproxy->table)) { ha_alert("Proxy '%s': failed to initialize stick-table.\n", curproxy->id); cfgerr++; } diff --git a/src/haproxy.c b/src/haproxy.c index 33f945362..bf91c0b88 100644 --- a/src/haproxy.c +++ b/src/haproxy.c @@ -2369,7 +2369,7 @@ void deinit(void) pool_destroy(p->req_cap_pool); pool_destroy(p->rsp_cap_pool); - pool_destroy(p->table.pool); + pool_destroy(p->table->pool); p0 = p; p = p->next; diff --git a/src/hlua_fcn.c b/src/hlua_fcn.c index 472fb0c71..60882f3eb 100644 --- a/src/hlua_fcn.c +++ b/src/hlua_fcn.c @@ -1269,9 +1269,9 @@ int hlua_fcn_new_proxy(lua_State *L, struct proxy *px) } lua_settable(L, -3); - if (px->table.id) { + if (px->table && px->table->id) { lua_pushstring(L, "stktable"); - hlua_fcn_new_stktable(L, &px->table); + hlua_fcn_new_stktable(L, px->table); lua_settable(L, -3); } diff --git a/src/proxy.c b/src/proxy.c index 18f016c83..3c599d683 100644 --- a/src/proxy.c +++ b/src/proxy.c @@ -587,7 +587,7 @@ struct proxy *proxy_find_by_id(int id, int cap, int table) if ((px->cap & cap) != cap) continue; - if (table && !px->table.size) + if (table && (!px->table || !px->table->size)) continue; return px; @@ -620,7 +620,7 @@ struct proxy *proxy_find_by_name(const char *name, int cap, int table) if ((curproxy->cap & cap) != cap) continue; - if (table && !curproxy->table.size) + if (table && (!curproxy->table || !curproxy->table->size)) continue; return curproxy; @@ -993,12 +993,12 @@ struct task *manage_proxy(struct task *t, void *context, unsigned short state) * be in neither list. Any entry being dumped will have ref_cnt > 0. * However we protect tables that are being synced to peers. */ - if (unlikely(stopping && p->state == PR_STSTOPPED && p->table.current)) { - if (!p->table.syncing) { - stktable_trash_oldest(&p->table, p->table.current); + if (unlikely(stopping && p->state == PR_STSTOPPED && p->table && p->table->current)) { + if (!p->table->syncing) { + stktable_trash_oldest(p->table, p->table->current); pool_gc(NULL); } - if (p->table.current) { + if (p->table->current) { /* some entries still remain, let's recheck in one second */ next = tick_first(next, tick_add(now_ms, 1000)); } @@ -1138,8 +1138,8 @@ void soft_stop(void) /* Note: do not wake up stopped proxies' task nor their tables' * tasks as these ones might point to already released entries. */ - if (p->table.size && p->table.sync_task) - task_wakeup(p->table.sync_task, TASK_WOKEN_MSG); + if (p->table && p->table->size && p->table->sync_task) + task_wakeup(p->table->sync_task, TASK_WOKEN_MSG); if (p->task) task_wakeup(p->task, TASK_WOKEN_MSG); diff --git a/src/sample.c b/src/sample.c index 54f7c9b34..aa20d35d1 100644 --- a/src/sample.c +++ b/src/sample.c @@ -1109,7 +1109,8 @@ int smp_resolve_args(struct proxy *p) list_for_each_entry_safe(cur, bak, &p->conf.args.list, list) { struct proxy *px; struct server *srv; - char *pname, *sname; + struct stktable *t; + char *pname, *sname, *stktname; char *err; arg = cur->arg; @@ -1244,30 +1245,35 @@ int smp_resolve_args(struct proxy *p) break; case ARGT_TAB: - if (arg->data.str.data) { - pname = arg->data.str.area; - px = proxy_tbl_by_name(pname); + if (!arg->data.str.data) { + ha_alert("parsing [%s:%d] : missing table name in arg %d of %s%s%s%s '%s' %s proxy '%s'.\n", + cur->file, cur->line, + cur->arg_pos + 1, conv_pre, conv_ctx, conv_pos, ctx, cur->kw, where, p->id); + cfgerr++; + continue; } - if (!px) { + stktname = arg->data.str.area; + t = stktable_find_by_name(stktname); + if (!t) { ha_alert("parsing [%s:%d] : unable to find table '%s' referenced in arg %d of %s%s%s%s '%s' %s proxy '%s'.\n", - cur->file, cur->line, pname, + cur->file, cur->line, stktname, cur->arg_pos + 1, conv_pre, conv_ctx, conv_pos, ctx, cur->kw, where, p->id); cfgerr++; break; } - if (!px->table.size) { + if (!t->size) { ha_alert("parsing [%s:%d] : no table in proxy '%s' referenced in arg %d of %s%s%s%s '%s' %s proxy '%s'.\n", - cur->file, cur->line, pname, + cur->file, cur->line, stktname, cur->arg_pos + 1, conv_pre, conv_ctx, conv_pos, ctx, cur->kw, where, p->id); cfgerr++; break; } - if (p->bind_proc & ~px->bind_proc) { + if (t->proxy && (p->bind_proc & ~t->proxy->bind_proc)) { ha_alert("parsing [%s:%d] : stick-table '%s' not present on all processes covered by proxy '%s'.\n", - cur->file, cur->line, px->id, p->id); + cur->file, cur->line, t->proxy->id, p->id); cfgerr++; break; } @@ -1275,7 +1281,7 @@ int smp_resolve_args(struct proxy *p) free(arg->data.str.area); arg->data.str.area = NULL; arg->unresolved = 0; - arg->data.prx = px; + arg->data.t = t; break; case ARGT_USR: diff --git a/src/stick_table.c b/src/stick_table.c index d8053dc04..87a26e6a9 100644 --- a/src/stick_table.c +++ b/src/stick_table.c @@ -47,7 +47,36 @@ /* structure used to return a table key built from a sample */ static THREAD_LOCAL struct stktable_key static_table_key; +struct stktable *stktables_list; +struct eb_root stktable_by_name = EB_ROOT; + #define round_ptr_size(i) (((i) + (sizeof(void *) - 1)) &~ (sizeof(void *) - 1)) + +/* This function inserts stktable into the tree of known stick-table. + * The stick-table ID is used as the storing key so it must already have + * been initialized. + */ +void stktable_store_name(struct stktable *t) +{ + t->name.key = t->id; + ebis_insert(&stktable_by_name, &t->name); +} + +struct stktable *stktable_find_by_name(const char *name) +{ + struct ebpt_node *node; + struct stktable *t; + + node = ebis_lookup(&stktable_by_name, name); + if (node) { + t = container_of(node, struct stktable, name); + if (!strcmp(t->id, name)) + return t; + } + + return NULL; +} + /* * Free an allocated sticky session , and decrease sticky sessions counter * in table . @@ -1063,7 +1092,7 @@ static int sample_conv_in_table(const struct arg *arg_p, struct sample *smp, voi struct stktable_key *key; struct stksess *ts; - t = &arg_p[0].data.prx->table; + t = arg_p[0].data.t; key = smp_to_stkey(smp, t); if (!key) @@ -1091,7 +1120,7 @@ static int sample_conv_table_bytes_in_rate(const struct arg *arg_p, struct sampl struct stksess *ts; void *ptr; - t = &arg_p[0].data.prx->table; + t = arg_p[0].data.t; key = smp_to_stkey(smp, t); if (!key) @@ -1128,7 +1157,7 @@ static int sample_conv_table_conn_cnt(const struct arg *arg_p, struct sample *sm struct stksess *ts; void *ptr; - t = &arg_p[0].data.prx->table; + t = arg_p[0].data.t; key = smp_to_stkey(smp, t); if (!key) @@ -1164,7 +1193,7 @@ static int sample_conv_table_conn_cur(const struct arg *arg_p, struct sample *sm struct stksess *ts; void *ptr; - t = &arg_p[0].data.prx->table; + t = arg_p[0].data.t; key = smp_to_stkey(smp, t); if (!key) @@ -1200,7 +1229,7 @@ static int sample_conv_table_conn_rate(const struct arg *arg_p, struct sample *s struct stksess *ts; void *ptr; - t = &arg_p[0].data.prx->table; + t = arg_p[0].data.t; key = smp_to_stkey(smp, t); if (!key) @@ -1237,7 +1266,7 @@ static int sample_conv_table_bytes_out_rate(const struct arg *arg_p, struct samp struct stksess *ts; void *ptr; - t = &arg_p[0].data.prx->table; + t = arg_p[0].data.t; key = smp_to_stkey(smp, t); if (!key) @@ -1274,7 +1303,7 @@ static int sample_conv_table_gpt0(const struct arg *arg_p, struct sample *smp, v struct stksess *ts; void *ptr; - t = &arg_p[0].data.prx->table; + t = arg_p[0].data.t; key = smp_to_stkey(smp, t); if (!key) @@ -1310,7 +1339,7 @@ static int sample_conv_table_gpc0(const struct arg *arg_p, struct sample *smp, v struct stksess *ts; void *ptr; - t = &arg_p[0].data.prx->table; + t = arg_p[0].data.t; key = smp_to_stkey(smp, t); if (!key) @@ -1346,7 +1375,7 @@ static int sample_conv_table_gpc0_rate(const struct arg *arg_p, struct sample *s struct stksess *ts; void *ptr; - t = &arg_p[0].data.prx->table; + t = arg_p[0].data.t; key = smp_to_stkey(smp, t); if (!key) @@ -1383,7 +1412,7 @@ static int sample_conv_table_gpc1(const struct arg *arg_p, struct sample *smp, v struct stksess *ts; void *ptr; - t = &arg_p[0].data.prx->table; + t = arg_p[0].data.t; key = smp_to_stkey(smp, t); if (!key) @@ -1419,7 +1448,7 @@ static int sample_conv_table_gpc1_rate(const struct arg *arg_p, struct sample *s struct stksess *ts; void *ptr; - t = &arg_p[0].data.prx->table; + t = arg_p[0].data.t; key = smp_to_stkey(smp, t); if (!key) @@ -1456,7 +1485,7 @@ static int sample_conv_table_http_err_cnt(const struct arg *arg_p, struct sample struct stksess *ts; void *ptr; - t = &arg_p[0].data.prx->table; + t = arg_p[0].data.t; key = smp_to_stkey(smp, t); if (!key) @@ -1492,7 +1521,7 @@ static int sample_conv_table_http_err_rate(const struct arg *arg_p, struct sampl struct stksess *ts; void *ptr; - t = &arg_p[0].data.prx->table; + t = arg_p[0].data.t; key = smp_to_stkey(smp, t); if (!key) @@ -1529,7 +1558,7 @@ static int sample_conv_table_http_req_cnt(const struct arg *arg_p, struct sample struct stksess *ts; void *ptr; - t = &arg_p[0].data.prx->table; + t = arg_p[0].data.t; key = smp_to_stkey(smp, t); if (!key) @@ -1565,7 +1594,7 @@ static int sample_conv_table_http_req_rate(const struct arg *arg_p, struct sampl struct stksess *ts; void *ptr; - t = &arg_p[0].data.prx->table; + t = arg_p[0].data.t; key = smp_to_stkey(smp, t); if (!key) @@ -1602,7 +1631,7 @@ static int sample_conv_table_kbytes_in(const struct arg *arg_p, struct sample *s struct stksess *ts; void *ptr; - t = &arg_p[0].data.prx->table; + t = arg_p[0].data.t; key = smp_to_stkey(smp, t); if (!key) @@ -1638,7 +1667,7 @@ static int sample_conv_table_kbytes_out(const struct arg *arg_p, struct sample * struct stksess *ts; void *ptr; - t = &arg_p[0].data.prx->table; + t = arg_p[0].data.t; key = smp_to_stkey(smp, t); if (!key) @@ -1674,7 +1703,7 @@ static int sample_conv_table_server_id(const struct arg *arg_p, struct sample *s struct stksess *ts; void *ptr; - t = &arg_p[0].data.prx->table; + t = arg_p[0].data.t; key = smp_to_stkey(smp, t); if (!key) @@ -1710,7 +1739,7 @@ static int sample_conv_table_sess_cnt(const struct arg *arg_p, struct sample *sm struct stksess *ts; void *ptr; - t = &arg_p[0].data.prx->table; + t = arg_p[0].data.t; key = smp_to_stkey(smp, t); if (!key) @@ -1746,7 +1775,7 @@ static int sample_conv_table_sess_rate(const struct arg *arg_p, struct sample *s struct stksess *ts; void *ptr; - t = &arg_p[0].data.prx->table; + t = arg_p[0].data.t; key = smp_to_stkey(smp, t); if (!key) @@ -1782,7 +1811,7 @@ static int sample_conv_table_trackers(const struct arg *arg_p, struct sample *sm struct stktable_key *key; struct stksess *ts; - t = &arg_p[0].data.prx->table; + t = arg_p[0].data.t; key = smp_to_stkey(smp, t); if (!key) @@ -2062,7 +2091,7 @@ smp_fetch_table_cnt(const struct arg *args, struct sample *smp, const char *kw, { smp->flags = SMP_F_VOL_TEST; smp->data.type = SMP_T_SINT; - smp->data.u.sint = args->data.prx->table.current; + smp->data.u.sint = args->data.t->current; return 1; } @@ -2072,12 +2101,12 @@ smp_fetch_table_cnt(const struct arg *args, struct sample *smp, const char *kw, static int smp_fetch_table_avl(const struct arg *args, struct sample *smp, const char *kw, void *private) { - struct proxy *px; + struct stktable *t; - px = args->data.prx; + t = args->data.t; smp->flags = SMP_F_VOL_TEST; smp->data.type = SMP_T_SINT; - smp->data.u.sint = px->table.size - px->table.current; + smp->data.u.sint = t->size - t->current; return 1; } @@ -2125,11 +2154,11 @@ smp_fetch_sc_stkctr(struct session *sess, struct stream *strm, const struct arg return NULL; /* Converts into key. */ - key = smp_to_stkey(&smp, &args->data.prx->table); + key = smp_to_stkey(&smp, args->data.t); if (!key) return NULL; - stkctr->table = &args->data.prx->table; + stkctr->table = args->data.t; stkctr_set_entry(stkctr, stktable_lookup_key(stkctr->table, key)); return stkctr; } @@ -2154,7 +2183,7 @@ smp_fetch_sc_stkctr(struct session *sess, struct stream *strm, const struct arg if (unlikely(args[arg].type == ARGT_TAB)) { /* an alternate table was specified, let's look up the same key there */ - stkctr->table = &args[arg].data.prx->table; + stkctr->table = args[arg].data.t; stkctr_set_entry(stkctr, stktable_lookup(stkctr->table, stksess)); return stkctr; } @@ -2187,11 +2216,11 @@ smp_create_src_stkctr(struct session *sess, struct stream *strm, const struct ar return NULL; /* Converts into key. */ - key = smp_to_stkey(&smp, &args->data.prx->table); + key = smp_to_stkey(&smp, args->data.t); if (!key) return NULL; - stkctr->table = &args->data.prx->table; + stkctr->table = args->data.t; stkctr_set_entry(stkctr, stktable_get_entry(stkctr->table, key)); return stkctr; } @@ -2709,7 +2738,7 @@ smp_fetch_src_updt_conn_cnt(const struct arg *args, struct sample *smp, const ch struct stksess *ts; struct stktable_key *key; void *ptr; - struct proxy *px; + struct stktable *t; if (!conn) return 0; @@ -2719,17 +2748,17 @@ smp_fetch_src_updt_conn_cnt(const struct arg *args, struct sample *smp, const ch return 0; /* Converts into key. */ - key = smp_to_stkey(smp, &args->data.prx->table); + key = smp_to_stkey(smp, args->data.t); if (!key) return 0; - px = args->data.prx; + t = args->data.t; - if ((ts = stktable_get_entry(&px->table, key)) == NULL) + if ((ts = stktable_get_entry(t, key)) == NULL) /* entry does not exist and could not be created */ return 0; - ptr = stktable_data_ptr(&px->table, ts, STKTABLE_DT_CONN_CNT); + ptr = stktable_data_ptr(t, ts, STKTABLE_DT_CONN_CNT); if (!ptr) { return 0; /* parameter not stored in this table */ } @@ -2744,7 +2773,7 @@ smp_fetch_src_updt_conn_cnt(const struct arg *args, struct sample *smp, const ch smp->flags = SMP_F_VOL_TEST; - stktable_touch_local(&px->table, ts, 1); + stktable_touch_local(t, ts, 1); /* Touch was previously performed by stktable_update_key */ return 1; @@ -3229,12 +3258,12 @@ enum { */ static int table_dump_head_to_buffer(struct buffer *msg, struct stream_interface *si, - struct proxy *proxy, struct proxy *target) + struct stktable *t, struct stktable *target) { struct stream *s = si_strm(si); chunk_appendf(msg, "# table: %s, type: %s, size:%d, used:%d\n", - proxy->id, stktable_types[proxy->table.type].kw, proxy->table.size, proxy->table.current); + t->id, stktable_types[t->type].kw, t->size, t->current); /* any other information should be dumped here */ @@ -3255,32 +3284,32 @@ static int table_dump_head_to_buffer(struct buffer *msg, */ static int table_dump_entry_to_buffer(struct buffer *msg, struct stream_interface *si, - struct proxy *proxy, struct stksess *entry) + struct stktable *t, struct stksess *entry) { int dt; chunk_appendf(msg, "%p:", entry); - if (proxy->table.type == SMP_T_IPV4) { + if (t->type == SMP_T_IPV4) { char addr[INET_ADDRSTRLEN]; inet_ntop(AF_INET, (const void *)&entry->key.key, addr, sizeof(addr)); chunk_appendf(msg, " key=%s", addr); } - else if (proxy->table.type == SMP_T_IPV6) { + else if (t->type == SMP_T_IPV6) { char addr[INET6_ADDRSTRLEN]; inet_ntop(AF_INET6, (const void *)&entry->key.key, addr, sizeof(addr)); chunk_appendf(msg, " key=%s", addr); } - else if (proxy->table.type == SMP_T_SINT) { + else if (t->type == SMP_T_SINT) { chunk_appendf(msg, " key=%u", *(unsigned int *)entry->key.key); } - else if (proxy->table.type == SMP_T_STR) { + else if (t->type == SMP_T_STR) { chunk_appendf(msg, " key="); - dump_text(msg, (const char *)entry->key.key, proxy->table.key_size); + dump_text(msg, (const char *)entry->key.key, t->key_size); } else { chunk_appendf(msg, " key="); - dump_binary(msg, (const char *)entry->key.key, proxy->table.key_size); + dump_binary(msg, (const char *)entry->key.key, t->key_size); } chunk_appendf(msg, " use=%d exp=%d", entry->ref_cnt - 1, tick_remain(now_ms, entry->expire)); @@ -3288,14 +3317,14 @@ static int table_dump_entry_to_buffer(struct buffer *msg, for (dt = 0; dt < STKTABLE_DATA_TYPES; dt++) { void *ptr; - if (proxy->table.data_ofs[dt] == 0) + if (t->data_ofs[dt] == 0) continue; if (stktable_data_types[dt].arg_type == ARG_T_DELAY) - chunk_appendf(msg, " %s(%d)=", stktable_data_types[dt].name, proxy->table.data_arg[dt].u); + chunk_appendf(msg, " %s(%d)=", stktable_data_types[dt].name, t->data_arg[dt].u); else chunk_appendf(msg, " %s=", stktable_data_types[dt].name); - ptr = stktable_data_ptr(&proxy->table, entry, dt); + ptr = stktable_data_ptr(t, entry, dt); switch (stktable_data_types[dt].std_type) { case STD_T_SINT: chunk_appendf(msg, "%d", stktable_data_cast(ptr, std_t_sint)); @@ -3309,7 +3338,7 @@ static int table_dump_entry_to_buffer(struct buffer *msg, case STD_T_FRQP: chunk_appendf(msg, "%d", read_freq_ctr_period(&stktable_data_cast(ptr, std_t_frqp), - proxy->table.data_arg[dt].u)); + t->data_arg[dt].u)); break; } } @@ -3330,7 +3359,7 @@ static int table_dump_entry_to_buffer(struct buffer *msg, static int table_process_entry_per_key(struct appctx *appctx, char **args) { struct stream_interface *si = appctx->owner; - struct proxy *px = appctx->ctx.table.target; + struct stktable *t = appctx->ctx.table.target; struct stksess *ts; uint32_t uint32_key; unsigned char ip6_key[sizeof(struct in6_addr)]; @@ -3347,7 +3376,7 @@ static int table_process_entry_per_key(struct appctx *appctx, char **args) return 1; } - switch (px->table.type) { + switch (t->type) { case SMP_T_IPV4: uint32_key = htonl(inetaddr_host(args[4])); static_table_key.key = &uint32_key; @@ -3408,30 +3437,30 @@ static int table_process_entry_per_key(struct appctx *appctx, char **args) switch (appctx->ctx.table.action) { case STK_CLI_ACT_SHOW: - ts = stktable_lookup_key(&px->table, &static_table_key); + ts = stktable_lookup_key(t, &static_table_key); if (!ts) return 1; chunk_reset(&trash); - if (!table_dump_head_to_buffer(&trash, si, px, px)) { - stktable_release(&px->table, ts); + if (!table_dump_head_to_buffer(&trash, si, t, t)) { + stktable_release(t, ts); return 0; } HA_RWLOCK_RDLOCK(STK_SESS_LOCK, &ts->lock); - if (!table_dump_entry_to_buffer(&trash, si, px, ts)) { + if (!table_dump_entry_to_buffer(&trash, si, t, ts)) { HA_RWLOCK_RDUNLOCK(STK_SESS_LOCK, &ts->lock); - stktable_release(&px->table, ts); + stktable_release(t, ts); return 0; } HA_RWLOCK_RDUNLOCK(STK_SESS_LOCK, &ts->lock); - stktable_release(&px->table, ts); + stktable_release(t, ts); break; case STK_CLI_ACT_CLR: - ts = stktable_lookup_key(&px->table, &static_table_key); + ts = stktable_lookup_key(t, &static_table_key); if (!ts) return 1; - if (!stksess_kill(&px->table, ts, 1)) { + if (!stksess_kill(t, ts, 1)) { /* don't delete an entry which is currently referenced */ appctx->ctx.cli.severity = LOG_ERR; appctx->ctx.cli.msg = "Entry currently in use, cannot remove\n"; @@ -3442,7 +3471,7 @@ static int table_process_entry_per_key(struct appctx *appctx, char **args) break; case STK_CLI_ACT_SET: - ts = stktable_get_entry(&px->table, &static_table_key); + ts = stktable_get_entry(t, &static_table_key); if (!ts) { /* don't delete an entry which is currently referenced */ appctx->ctx.cli.severity = LOG_ERR; @@ -3458,7 +3487,7 @@ static int table_process_entry_per_key(struct appctx *appctx, char **args) appctx->ctx.cli.msg = "\"data.\" followed by a value expected\n"; appctx->st0 = CLI_ST_PRINT; HA_RWLOCK_WRUNLOCK(STK_SESS_LOCK, &ts->lock); - stktable_touch_local(&px->table, ts, 1); + stktable_touch_local(t, ts, 1); return 1; } @@ -3468,16 +3497,16 @@ static int table_process_entry_per_key(struct appctx *appctx, char **args) appctx->ctx.cli.msg = "Unknown data type\n"; appctx->st0 = CLI_ST_PRINT; HA_RWLOCK_WRUNLOCK(STK_SESS_LOCK, &ts->lock); - stktable_touch_local(&px->table, ts, 1); + stktable_touch_local(t, ts, 1); return 1; } - if (!px->table.data_ofs[data_type]) { + if (!t->data_ofs[data_type]) { appctx->ctx.cli.severity = LOG_ERR; appctx->ctx.cli.msg = "Data type not stored in this table\n"; appctx->st0 = CLI_ST_PRINT; HA_RWLOCK_WRUNLOCK(STK_SESS_LOCK, &ts->lock); - stktable_touch_local(&px->table, ts, 1); + stktable_touch_local(t, ts, 1); return 1; } @@ -3486,11 +3515,11 @@ static int table_process_entry_per_key(struct appctx *appctx, char **args) appctx->ctx.cli.msg = "Require a valid integer value to store\n"; appctx->st0 = CLI_ST_PRINT; HA_RWLOCK_WRUNLOCK(STK_SESS_LOCK, &ts->lock); - stktable_touch_local(&px->table, ts, 1); + stktable_touch_local(t, ts, 1); return 1; } - ptr = stktable_data_ptr(&px->table, ts, data_type); + ptr = stktable_data_ptr(t, ts, data_type); switch (stktable_data_types[data_type].std_type) { case STD_T_SINT: @@ -3520,7 +3549,7 @@ static int table_process_entry_per_key(struct appctx *appctx, char **args) } } HA_RWLOCK_WRUNLOCK(STK_SESS_LOCK, &ts->lock); - stktable_touch_local(&px->table, ts, 1); + stktable_touch_local(t, ts, 1); break; default: @@ -3553,7 +3582,7 @@ static int table_prepare_data_request(struct appctx *appctx, char **args) return 1; } - if (!((struct proxy *)appctx->ctx.table.target)->table.data_ofs[appctx->ctx.table.data_type]) { + if (!((struct proxy *)appctx->ctx.table.target)->table->data_ofs[appctx->ctx.table.data_type]) { appctx->ctx.cli.severity = LOG_ERR; appctx->ctx.cli.msg = "Data type not stored in this table\n"; appctx->st0 = CLI_ST_PRINT; @@ -3584,12 +3613,11 @@ static int cli_parse_table_req(char **args, char *payload, struct appctx *appctx { appctx->ctx.table.data_type = -1; appctx->ctx.table.target = NULL; - appctx->ctx.table.proxy = NULL; appctx->ctx.table.entry = NULL; appctx->ctx.table.action = (long)private; // keyword argument, one of STK_CLI_ACT_* if (*args[2]) { - appctx->ctx.table.target = proxy_tbl_by_name(args[2]); + appctx->ctx.table.target = stktable_find_by_name(args[2]); if (!appctx->ctx.table.target) { appctx->ctx.cli.severity = LOG_ERR; appctx->ctx.cli.msg = "No such table\n"; @@ -3663,7 +3691,7 @@ static int cli_io_handler_table(struct appctx *appctx) if (unlikely(si_ic(si)->flags & (CF_WRITE_ERROR|CF_SHUTW))) { /* in case of abort, remove any refcount we might have set on an entry */ if (appctx->st2 == STAT_ST_LIST) { - stksess_kill_if_expired(&appctx->ctx.table.proxy->table, appctx->ctx.table.entry, 1); + stksess_kill_if_expired(appctx->ctx.table.t, appctx->ctx.table.entry, 1); } return 1; } @@ -3673,42 +3701,42 @@ static int cli_io_handler_table(struct appctx *appctx) while (appctx->st2 != STAT_ST_FIN) { switch (appctx->st2) { case STAT_ST_INIT: - appctx->ctx.table.proxy = appctx->ctx.table.target; - if (!appctx->ctx.table.proxy) - appctx->ctx.table.proxy = proxies_list; + appctx->ctx.table.t = appctx->ctx.table.target; + if (!appctx->ctx.table.t) + appctx->ctx.table.t = stktables_list; appctx->ctx.table.entry = NULL; appctx->st2 = STAT_ST_INFO; break; case STAT_ST_INFO: - if (!appctx->ctx.table.proxy || + if (!appctx->ctx.table.t || (appctx->ctx.table.target && - appctx->ctx.table.proxy != appctx->ctx.table.target)) { + appctx->ctx.table.t != appctx->ctx.table.target)) { appctx->st2 = STAT_ST_END; break; } - if (appctx->ctx.table.proxy->table.size) { - if (show && !table_dump_head_to_buffer(&trash, si, appctx->ctx.table.proxy, appctx->ctx.table.target)) + if (appctx->ctx.table.t->size) { + if (show && !table_dump_head_to_buffer(&trash, si, appctx->ctx.table.t, appctx->ctx.table.target)) return 0; if (appctx->ctx.table.target && (strm_li(s)->bind_conf->level & ACCESS_LVL_MASK) >= ACCESS_LVL_OPER) { /* dump entries only if table explicitly requested */ - HA_SPIN_LOCK(STK_TABLE_LOCK, &appctx->ctx.table.proxy->table.lock); - eb = ebmb_first(&appctx->ctx.table.proxy->table.keys); + HA_SPIN_LOCK(STK_TABLE_LOCK, &appctx->ctx.table.t->lock); + eb = ebmb_first(&appctx->ctx.table.t->keys); if (eb) { appctx->ctx.table.entry = ebmb_entry(eb, struct stksess, key); appctx->ctx.table.entry->ref_cnt++; appctx->st2 = STAT_ST_LIST; - HA_SPIN_UNLOCK(STK_TABLE_LOCK, &appctx->ctx.table.proxy->table.lock); + HA_SPIN_UNLOCK(STK_TABLE_LOCK, &appctx->ctx.table.t->lock); break; } - HA_SPIN_UNLOCK(STK_TABLE_LOCK, &appctx->ctx.table.proxy->table.lock); + HA_SPIN_UNLOCK(STK_TABLE_LOCK, &appctx->ctx.table.t->lock); } } - appctx->ctx.table.proxy = appctx->ctx.table.proxy->next; + appctx->ctx.table.t = appctx->ctx.table.t->next; break; case STAT_ST_LIST: @@ -3723,7 +3751,7 @@ static int cli_io_handler_table(struct appctx *appctx) dt = appctx->ctx.table.data_type; - ptr = stktable_data_ptr(&appctx->ctx.table.proxy->table, + ptr = stktable_data_ptr(appctx->ctx.table.t, appctx->ctx.table.entry, dt); @@ -3740,7 +3768,7 @@ static int cli_io_handler_table(struct appctx *appctx) break; case STD_T_FRQP: data = read_freq_ctr_period(&stktable_data_cast(ptr, std_t_frqp), - appctx->ctx.table.proxy->table.data_arg[dt].u); + appctx->ctx.table.t->data_arg[dt].u); break; } @@ -3761,14 +3789,14 @@ static int cli_io_handler_table(struct appctx *appctx) } if (show && !skip_entry && - !table_dump_entry_to_buffer(&trash, si, appctx->ctx.table.proxy, appctx->ctx.table.entry)) { + !table_dump_entry_to_buffer(&trash, si, appctx->ctx.table.t, appctx->ctx.table.entry)) { HA_RWLOCK_RDUNLOCK(STK_SESS_LOCK, &appctx->ctx.table.entry->lock); return 0; } HA_RWLOCK_RDUNLOCK(STK_SESS_LOCK, &appctx->ctx.table.entry->lock); - HA_SPIN_LOCK(STK_TABLE_LOCK, &appctx->ctx.table.proxy->table.lock); + HA_SPIN_LOCK(STK_TABLE_LOCK, &appctx->ctx.table.t->lock); appctx->ctx.table.entry->ref_cnt--; eb = ebmb_next(&appctx->ctx.table.entry->key); @@ -3776,23 +3804,23 @@ static int cli_io_handler_table(struct appctx *appctx) struct stksess *old = appctx->ctx.table.entry; appctx->ctx.table.entry = ebmb_entry(eb, struct stksess, key); if (show) - __stksess_kill_if_expired(&appctx->ctx.table.proxy->table, old); + __stksess_kill_if_expired(appctx->ctx.table.t, old); else if (!skip_entry && !appctx->ctx.table.entry->ref_cnt) - __stksess_kill(&appctx->ctx.table.proxy->table, old); + __stksess_kill(appctx->ctx.table.t, old); appctx->ctx.table.entry->ref_cnt++; - HA_SPIN_UNLOCK(STK_TABLE_LOCK, &appctx->ctx.table.proxy->table.lock); + HA_SPIN_UNLOCK(STK_TABLE_LOCK, &appctx->ctx.table.t->lock); break; } if (show) - __stksess_kill_if_expired(&appctx->ctx.table.proxy->table, appctx->ctx.table.entry); + __stksess_kill_if_expired(appctx->ctx.table.t, appctx->ctx.table.entry); else if (!skip_entry && !appctx->ctx.table.entry->ref_cnt) - __stksess_kill(&appctx->ctx.table.proxy->table, appctx->ctx.table.entry); + __stksess_kill(appctx->ctx.table.t, appctx->ctx.table.entry); - HA_SPIN_UNLOCK(STK_TABLE_LOCK, &appctx->ctx.table.proxy->table.lock); + HA_SPIN_UNLOCK(STK_TABLE_LOCK, &appctx->ctx.table.t->lock); - appctx->ctx.table.proxy = appctx->ctx.table.proxy->next; + appctx->ctx.table.t = appctx->ctx.table.t->next; appctx->st2 = STAT_ST_INFO; break; @@ -3807,7 +3835,7 @@ static int cli_io_handler_table(struct appctx *appctx) static void cli_release_show_table(struct appctx *appctx) { if (appctx->st2 == STAT_ST_LIST) { - stksess_kill_if_expired(&appctx->ctx.table.proxy->table, appctx->ctx.table.entry, 1); + stksess_kill_if_expired(appctx->ctx.table.t, appctx->ctx.table.entry, 1); } }