summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorWilly Tarreau <w@1wt.eu>2009-06-15 10:56:05 +0200
committerWilly Tarreau <w@1wt.eu>2009-07-14 20:15:27 +0200
commit1c2f47166c1bc121a227c90c2c7d98c4825d4b8f (patch)
tree9e8cdbdfe7d4731e80592f4edd6a55d0722405ee /src
parentde5ba00c9a79a50f53229e6bd4bb34a2344be053 (diff)
downloadhaproxy-1c2f47166c1bc121a227c90c2c7d98c4825d4b8f.tar.gz
[MEDIUM] support setting a server weight to zero
Sometimes it is useful to be able to set a server's weight to zero. It allows the server to receive only persistent traffic but never normal traffic. (cherry picked from commit 6704d67d656574a602ddf81a603cdb4f482f90a9)
Diffstat (limited to 'src')
-rw-r--r--src/backend.c31
-rw-r--r--src/cfgparse.c4
2 files changed, 24 insertions, 11 deletions
diff --git a/src/backend.c b/src/backend.c
index b830bdb92..bb830f290 100644
--- a/src/backend.c
+++ b/src/backend.c
@@ -201,7 +201,8 @@ void recalc_server_map(struct proxy *px)
int max = 0;
best = NULL;
for (cur = px->srv; cur; cur = cur->next) {
- if (flag == (cur->state &
+ if (cur->eweight &&
+ flag == (cur->state &
(SRV_RUNNING | SRV_GOINGDOWN | SRV_BACKUP))) {
int v;
@@ -248,15 +249,24 @@ void init_server_map(struct proxy *p)
return;
/* We will factor the weights to reduce the table,
- * using Euclide's largest common divisor algorithm
+ * using Euclide's largest common divisor algorithm.
+ * Since we may have zero weights, we have to first
+ * find a non-zero weight server.
*/
- pgcd = p->srv->uweight;
- for (srv = p->srv->next; srv && pgcd > 1; srv = srv->next) {
- int w = srv->uweight;
- while (w) {
- int t = pgcd % w;
- pgcd = w;
- w = t;
+ pgcd = 1;
+ srv = p->srv;
+ while (srv && !srv->uweight)
+ srv = srv->next;
+
+ if (srv) {
+ pgcd = srv->uweight; /* note: cannot be zero */
+ while (pgcd > 1 && (srv = srv->next)) {
+ int w = srv->uweight;
+ while (w) {
+ int t = pgcd % w;
+ pgcd = w;
+ w = t;
+ }
}
}
@@ -281,6 +291,9 @@ void init_server_map(struct proxy *p)
if (act < bck)
act = bck;
+ if (!act)
+ act = 1;
+
p->lbprm.map.srv = (struct server **)calloc(act, sizeof(struct server *));
/* recounts servers and their weights */
p->lbprm.map.state = PR_MAP_RECALC;
diff --git a/src/cfgparse.c b/src/cfgparse.c
index b268d598a..311476457 100644
--- a/src/cfgparse.c
+++ b/src/cfgparse.c
@@ -2126,8 +2126,8 @@ int cfg_parse_listen(const char *file, int linenum, char **args, int inv)
else if (!strcmp(args[cur_arg], "weight")) {
int w;
w = atol(args[cur_arg + 1]);
- if (w < 1 || w > 256) {
- Alert("parsing [%s:%d] : weight of server %s is not within 1 and 256 (%d).\n",
+ if (w < 0 || w > 256) {
+ Alert("parsing [%s:%d] : weight of server %s is not within 0 and 256 (%d).\n",
file, linenum, newsrv->id, w);
return -1;
}