to a farm, most connections will be redistributed to different
servers. This can be inconvenient with caches for instance.
+ avalanche this mechanism uses the default map-based hashing described
+ above but applies a full avalanche hash before performing the
+ mapping. The result is a slightly less smooth hash for most
+ situations, but the hash becomes better than pure map-based
+ hashes when the number of servers is a multiple of the size of
+ the input set. When using URI hash with a number of servers
+ multiple of 64, it's desirable to change the hash type to
+ this value.
+
consistent the hash table is a tree filled with many occurrences of each
server. The hash key is looked up in the tree and the closest
server is chosen. This hash is dynamic, it supports changing
/* hash types */
#define BE_LB_HASH_MAP 0x000000 /* map-based hash (default) */
#define BE_LB_HASH_CONS 0x100000 /* consistent hashbit to indicate a dynamic algorithm */
-#define BE_LB_HASH_TYPE 0x100000 /* get/clear hash types */
+#define BE_LB_HASH_AVAL 0x200000 /* run an avalanche hash before a map */
+#define BE_LB_HASH_TYPE 0x300000 /* get/clear hash types */
/* various constants */
h ^= ntohl(*(unsigned int *)(&addr[l]));
l += sizeof (int);
}
+ if ((px->lbprm.algo & BE_LB_HASH_TYPE) != BE_LB_HASH_MAP)
+ h = full_hash(h);
hash_done:
if (px->lbprm.algo & BE_LB_LKUP_CHTREE)
return chash_get_server_hash(px, h);
hash = c + (hash << 6) + (hash << 16) - hash;
}
+ if ((px->lbprm.algo & BE_LB_HASH_TYPE) != BE_LB_HASH_MAP)
+ hash = full_hash(hash);
hash_done:
if (px->lbprm.algo & BE_LB_LKUP_CHTREE)
return chash_get_server_hash(px, hash);
uri_len--;
p++;
}
+ if ((px->lbprm.algo & BE_LB_HASH_TYPE) != BE_LB_HASH_MAP)
+ hash = full_hash(hash);
if (px->lbprm.algo & BE_LB_LKUP_CHTREE)
return chash_get_server_hash(px, hash);
else
p++;
/* should we break if vlen exceeds limit? */
}
+ if ((px->lbprm.algo & BE_LB_HASH_TYPE) != BE_LB_HASH_MAP)
+ hash = full_hash(hash);
if (px->lbprm.algo & BE_LB_LKUP_CHTREE)
return chash_get_server_hash(px, hash);
else
p--;
}
}
+ if ((px->lbprm.algo & BE_LB_HASH_TYPE) != BE_LB_HASH_MAP)
+ hash = full_hash(hash);
hash_done:
if (px->lbprm.algo & BE_LB_LKUP_CHTREE)
return chash_get_server_hash(px, hash);
len--;
p++;
}
+ if ((px->lbprm.algo & BE_LB_HASH_TYPE) != BE_LB_HASH_MAP)
+ hash = full_hash(hash);
hash_done:
if (px->lbprm.algo & BE_LB_LKUP_CHTREE)
return chash_get_server_hash(px, hash);
curproxy->lbprm.algo &= ~BE_LB_HASH_TYPE;
curproxy->lbprm.algo |= BE_LB_HASH_MAP;
}
+ else if (strcmp(args[1], "avalanche") == 0) { /* use full hash before map-based hashing */
+ curproxy->lbprm.algo &= ~BE_LB_HASH_TYPE;
+ curproxy->lbprm.algo |= BE_LB_HASH_AVAL;
+ }
else {
- Alert("parsing [%s:%d] : '%s' only supports 'consistent' and 'map-based'.\n", file, linenum, args[0]);
+ Alert("parsing [%s:%d] : '%s' only supports 'avalanche', 'consistent' and 'map-based'.\n", file, linenum, args[0]);
err_code |= ERR_ALERT | ERR_FATAL;
goto out;
}
else
return NULL;
- hash = full_hash(hash);
-
/* find the node after and the node before */
next = eb32_lookup_ge(root, hash);
if (!next)