Greetings,

I have reproduced this same issue on haproxy-1.4.6.

Configure a backend with
        balance url_param x
        hash-type consistent
        server s1 host1:80
        server s2 host2:80
        server s3 host3:80
        server s4 host4:80

The server will only dispatch requests to two servers.

The problem is seen in chash_init_server_tree:

        /* queue active and backup servers in two distinct groups */
        for (srv = p->srv; srv; srv = srv->next) {
        
srv->lb_tree = (srv->state & SRV_BACKUP) ? &p->lbprm.chash.bck : &p- >lbprm.chash.act;
                srv->lb_nodes_tot = srv->uweight * BE_WEIGHT_SCALE;
                srv->lb_nodes_now = 0;
srv->lb_nodes = (struct tree_occ *)calloc(srv->lb_nodes_tot, sizeof(struct tree_occ));

                for (node = 0; node < srv->lb_nodes_tot; node++) {
                        srv->lb_nodes[node].server = srv;
srv->lb_nodes[node].node.key = chash_hash(srv->puid * SRV_EWGHT_RANGE + node);
                }

                if (srv_is_usable(srv->state, srv->eweight))
                        chash_queue_dequeue_srv(srv);
        }

The problem is that when this code runs, all of the servers have the same srv->puid == 0. With equal weights, each server generates the exact same set of node keys.

Regardless of the key you lookup using eb32_lookup_ge, you get a node for the last server. The chash_get_server_hash function is reduced to choosing between the closer of the last or first server.

Any insights as to why srv->puid is zero and not unique per server?

Jeff Persch



Reply via email to