For more information regarding the security incident at F5, the actions we are taking to address it, and our ongoing efforts to protect our customers, click here.

Forum Discussion

David_Bradley_2's avatar
David_Bradley_2
Icon for Nimbostratus rankNimbostratus
Apr 10, 2007

LB::reselect not working as expected

I'm got an LB_SELECTED that is checking if the choice made by the LB is acceptable, and doing an LB::reselect if not. I setup an artificial condition in my lab in which no choice is acceptable. Based on the code below, what i'd expect to see is the connection be ultimately rejected after having looped through all the servers in the pool and determined that none of them were acceptable candidates. What i'm actually seeing is the LB::reselect happening twice, and on the second time, it's putting the connection on the server chosen by the LB, not looping to the next one according to the LB algo. (which is round-robin btw). There are 3 servers in the pool. Here is my LB_SELECTED rule:

 

 

when LB_SELECTED {

 

 

If we don't have the capacity to host this client on

 

the selected server, then reselect. If we've gone

 

through all the servers in the list, then reject.

 

 

if { [LB::server ratio] < $client_weight } {

 

if { $retry_count >= [active_members [LB::server pool]] } {

 

log local0. "Found no server of [active_members [LB::server pool]] in pool [LB::server pool] with enough capacity to handle $sender of weight $client_weight. Rejecting connection."

 

reject

 

return

 

} incr retry_count

 

log local0. "LB chose member ([LB::server addr]) with too little capacity ([LB::server ratio]) for sender $sender. Need at least $client_weight. Reselect try number $retry_count."

 

LB::reselect

 

}

 

}

 

 

 

Thanks in advance.

 

 

Dave

13 Replies

  • Citizen,

     

     

    Thanks for your help. I thought of doing that. I'd have to:

     

     

    1) maintain a class with the same information that's already in the pool definition. If there were some way to find out the pool members from within the irule, then I would be nicer. But I could do this.

     

    2) In order to "load" the class data with the current ratios, i'd have to make a pass through LB_SELECTED for each server in the pool. I guess the only way to reliably do this is via a "pool member " from the CLIENT_DATA event. i.e. pseudocode

     

     

    CLIENT_DATA

     

    foreach member in class

     

    if member(capacity) uninitialized

     

    pool

     

    elsif member(capacity) > incoming client's weight

     

    pool

     

    endif

     

    endfor

     

     

    LB_SELECTED

     

    if uninitialized capacity value for this member

     

    member(capacity) = [LB::server ratio]

     

    if member(capacity) < incoming client's weight

     

    LB::reselect

     

    endif

     

    endif

     

     

     

     

     

    Is this the best (or only) way you can think of to pull this off?

     

     

    Dave
  • I was thinking this could be done within the LB_SELECTED event:

    
    when LB_SELECTED {
      set current_pool [LB::server pool]
      LB::detach
      foreach i in $::pool_members {
        pool $current_pool member $i
        set current_ratio [LB::server ratio]
         BUILD ARRAY LOGIC HERE 
        LB::detach
      }
       EXTRACT APPROPRIATE SELECTION FROM ARRAY HERE 
      pool $current_pool member $best_selection
    }

    Sorry, my TCL is fairly limited. Also, this is just a guess as to what's possible. I'm not sure the pool setting matters much until the event is finished, so it could all be for not.

  • Do you a completed iRule that works properly that works to do retries, logs properly, soup to nuts?