ngx_http_upstream_conpaas_module.c
/**
 * Selects a peer to serve a request. This function implements the load
 * balancing policy.
 */
Selects a peer to serve a request. This function implements the load
balancing policy.
Selects a peer to serve a request . This function implements the load balancing policy .
static ngx_uint_t
ngx_http_upstream_conpaas_select_peer(ngx_http_upstream_conpaas_peers_t *peers,
		ngx_http_upstream_conpaas_conf_t *conf, ngx_peer_connection_t *pc)
{
    ngx_uint_t                    i, n;
    ngx_int_t						elapsed_msecs;
    ngx_http_upstream_rr_peer_t  *peer;
    ngx_time_t now;
    float							current_req_rate;
    peer = &peers->peer[0];
    if (peers -> peer_to_test < 0 && sig_profiling == 1) { 
    	sig_profiling = 0;
    	get_profiling_config(conf -> profiling_file, peers -> number);
    	if (n_profile_peers > 0) {
    		peers -> idx_peer_to_test = 0;
    		peers -> peer_to_test = profile_peers[peers -> idx_peer_to_test];
    		ngx_log_debug1(NGX_LOG_DEBUG_HTTP, pc->log, 0,
    		    		                    "conpaas_load_balancing: profiling peer %d...", peers -> peer_to_test);
    		peers -> wl_index = 0;
    		ngx_log_debug1(NGX_LOG_DEBUG_HTTP, pc->log, 0,
    				"conpaas_load_balancing: start profiling, profile time: %d", profile_time);
    	}
    }
    now = *ngx_timeofday();
    if (peers -> peer_to_test >= 0) { 
    	if ((peers -> test_start_time.sec != 0 ) &&
    			(ngx_difftime_msec(now, peers -> test_start_time) > 1000 * profile_time)) { 
    		(peers -> wl_index)++;
    		if (peers -> wl_index < n_workloads) {
    			ngx_log_debug2(NGX_LOG_DEBUG_HTTP, pc->log, 0,
                    "conpaas_load_balancing: switching to workload no. %d, req/sec: %d", peers -> wl_index, workloads[peers -> wl_index]);
    		}
    		(peers -> last_test_req_time).sec = (peers -> last_test_req_time).msec = 0;
    		(peers -> test_start_time).sec = (peers -> test_start_time).msec = 0;
    		peers -> n_tested_requests = 0;
    	}
    	if (peers -> wl_index < n_workloads) {
    		if ((peers -> last_test_req_time).sec == 0) { 
    			peers -> last_test_req_time = now;
    			peers -> test_start_time = now;
    			peers -> n_tested_requests = 1;
    			ngx_log_debug1(NGX_LOG_DEBUG_HTTP, pc->log, 0,
    			    	"conpaas_load_balancing: first time choosing tested peer: %d", peers -> peer_to_test);
    			return peers -> peer_to_test;
    		}
    		elapsed_msecs = ngx_difftime_msec(now, peers -> test_start_time);
    		current_req_rate = (float)(peers -> n_tested_requests * 1000) / elapsed_msecs;
    		ngx_log_debug2(NGX_LOG_DEBUG_HTTP, pc->log, 0,
    		    "conpaas_load_balancing: elapsed_msecs %d, req_rate %f", elapsed_msecs, current_req_rate);
    		if (current_req_rate < workloads[peers -> wl_index]) {
    			peers -> last_test_req_time = now;
    			(peers -> n_tested_requests)++;
    			ngx_log_debug1(NGX_LOG_DEBUG_HTTP, pc->log, 0,
    			    "conpaas_load_balancing: choosing tested peer: %d", peers -> peer_to_test);
    			return peers -> peer_to_test;
    		}
    	} else { 
    		(peers -> idx_peer_to_test)++; 
    		if (peers -> idx_peer_to_test >= n_profile_peers) {
    		    peers -> peer_to_test = -1;
    		    ngx_log_debug0(NGX_LOG_DEBUG_HTTP, pc->log, 0,
    		                        "conpaas_load_balancing: done profiling...");
    		} else {
    			peers -> peer_to_test = profile_peers[peers -> idx_peer_to_test];
    			peers -> wl_index = 0;
    			ngx_log_debug1(NGX_LOG_DEBUG_HTTP, pc->log, 0,
    		                    "conpaas_load_balancing: profiling peer %d...", peers -> peer_to_test);
    		}
    	}
    }
    for ( ;; ) {
        for (i = 0; i < peers->number; i++) {
        	ngx_log_debug3(NGX_LOG_DEBUG_HTTP, pc->log, 0,
        	    	"conpaas_load_balancing: peer_to_test %d peer %d weight %d", peers -> peer_to_test, i, peer[i].current_weight);
            if (peer[i].current_weight <= 0 || ((ngx_int_t)i == peers -> peer_to_test)) {
                continue;
            }
            n = i;
            while (i < peers->number - 1) {
                i++;
                if (peer[i].current_weight <= 0 || ((ngx_int_t)i == peers -> peer_to_test)) {
                    continue;
                }
                if (peer[n].current_weight * 1000 / peer[i].current_weight
                    > peer[n].weight * 1000 / peer[i].weight)
                {
                	ngx_log_debug1(NGX_LOG_DEBUG_HTTP, pc->log, 0,
                	 "conpaas_load_balancing: normal return 1 peer %d...", n);
                    return n;
                }
                n = i;
            }
            if (peer[i].current_weight > 0 && ((ngx_int_t)i != peers -> peer_to_test)) {
                n = i;
            }
            ngx_log_debug1(NGX_LOG_DEBUG_HTTP, pc->log, 0,
              "conpaas_load_balancing: normal return 2 peer %d...", n);
            return n;
        }
        for (i = 0; i < peers->number; i++) {
            peer[i].current_weight = peer[i].weight;
        }
    }
}
static ngx_uint_t ngx_http_upstream_conpaas_select_peer ( ngx_http_upstream_conpaas_peers_t * peers , ngx_http_upstream_conpaas_conf_t * conf , ngx_peer_connection_t * pc ) { ngx_uint_t i , n ; ngx_int_t elapsed_msecs ; ngx_http_upstream_rr_peer_t * peer ; ngx_time_t now ; float current_req_rate ; peer = & peers -> peer [ 0 ] ; if ( peers -> peer_to_test < 0 && sig_profiling == 1 ) { sig_profiling = 0 ; get_profiling_config ( conf -> profiling_file , peers -> number ) ; if ( n_profile_peers > 0 ) { peers -> idx_peer_to_test = 0 ; peers -> peer_to_test = profile_peers [ peers -> idx_peer_to_test ] ; ngx_log_debug1 ( NGX_LOG_DEBUG_HTTP , pc -> log , 0 , " " , peers -> peer_to_test ) ; peers -> wl_index = 0 ; ngx_log_debug1 ( NGX_LOG_DEBUG_HTTP , pc -> log , 0 , " " , profile_time ) ; } } now = * ngx_timeofday ( ) ; if ( peers -> peer_to_test >= 0 ) { if ( ( peers -> test_start_time . sec != 0 ) && ( ngx_difftime_msec ( now , peers -> test_start_time ) > 1000 * profile_time ) ) { ( peers -> wl_index ) ++ ; if ( peers -> wl_index < n_workloads ) { ngx_log_debug2 ( NGX_LOG_DEBUG_HTTP , pc -> log , 0 , " " , peers -> wl_index , workloads [ peers -> wl_index ] ) ; } ( peers -> last_test_req_time ) . sec = ( peers -> last_test_req_time ) . msec = 0 ; ( peers -> test_start_time ) . sec = ( peers -> test_start_time ) . msec = 0 ; peers -> n_tested_requests = 0 ; } if ( peers -> wl_index < n_workloads ) { if ( ( peers -> last_test_req_time ) . sec == 0 ) { peers -> last_test_req_time = now ; peers -> test_start_time = now ; peers -> n_tested_requests = 1 ; ngx_log_debug1 ( NGX_LOG_DEBUG_HTTP , pc -> log , 0 , " " , peers -> peer_to_test ) ; return peers -> peer_to_test ; } elapsed_msecs = ngx_difftime_msec ( now , peers -> test_start_time ) ; current_req_rate = ( float ) ( peers -> n_tested_requests * 1000 ) / elapsed_msecs ; ngx_log_debug2 ( NGX_LOG_DEBUG_HTTP , pc -> log , 0 , " " , elapsed_msecs , current_req_rate ) ; if ( current_req_rate < workloads [ peers -> wl_index ] ) { peers -> last_test_req_time = now ; ( peers -> n_tested_requests ) ++ ; ngx_log_debug1 ( NGX_LOG_DEBUG_HTTP , pc -> log , 0 , " " , peers -> peer_to_test ) ; return peers -> peer_to_test ; } } else { ( peers -> idx_peer_to_test ) ++ ; if ( peers -> idx_peer_to_test >= n_profile_peers ) { peers -> peer_to_test = -1 ; ngx_log_debug0 ( NGX_LOG_DEBUG_HTTP , pc -> log , 0 , " " ) ; } else { peers -> peer_to_test = profile_peers [ peers -> idx_peer_to_test ] ; peers -> wl_index = 0 ; ngx_log_debug1 ( NGX_LOG_DEBUG_HTTP , pc -> log , 0 , " " , peers -> peer_to_test ) ; } } } for ( ; ; ) { for ( i = 0 ; i < peers -> number ; i ++ ) { ngx_log_debug3 ( NGX_LOG_DEBUG_HTTP , pc -> log , 0 , " " , peers -> peer_to_test , i , peer [ i ] . current_weight ) ; if ( peer [ i ] . current_weight <= 0 || ( ( ngx_int_t ) i == peers -> peer_to_test ) ) { continue ; } n = i ; while ( i < peers -> number - 1 ) { i ++ ; if ( peer [ i ] . current_weight <= 0 || ( ( ngx_int_t ) i == peers -> peer_to_test ) ) { continue ; } if ( peer [ n ] . current_weight * 1000 / peer [ i ] . current_weight > peer [ n ] . weight * 1000 / peer [ i ] . weight ) { ngx_log_debug1 ( NGX_LOG_DEBUG_HTTP , pc -> log , 0 , " " , n ) ; return n ; } n = i ; } if ( peer [ i ] . current_weight > 0 && ( ( ngx_int_t ) i != peers -> peer_to_test ) ) { n = i ; } ngx_log_debug1 ( NGX_LOG_DEBUG_HTTP , pc -> log , 0 , " " , n ) ; return n ; } for ( i = 0 ; i < peers -> number ; i ++ ) { peer [ i ] . current_weight = peer [ i ] . weight ; } } }
Selects a peer to serve a request.
Selects a peer to serve a request .
/* start profiling */ /* read the profiling configuration from the file */ /* start with the first peer */ /* start with the first workload value from the list */ /* we are in profiling mode */ /* we finished testing the current workload */ /* (now.sec > (peers -> test_start_time.sec + profile_time))) { */ /* move to the next workload value, reset timers */ /* first test request for this workload */ //elapsed_msecs = ngx_difftime_msec(now, peers -> last_test_req_time); //if (elapsed_msecs * workloads[peers -> wl_index] >= 1000) { /* we should send the request to the tested peer */ /* we are done testing this peer */ /* move to the next peer */ /* if (peers -> peer_to_test >= (ngx_int_t)(peers -> number)) { */ /* we are done testing all the peers, reset the peer counter */