132,6 → 132,14 |
int cavg[MAX_PROC]; /* avg of computation time */ |
int ccount[MAX_PROC]; /* number of istance */ |
|
long long int u_predicted; |
long long int u_p_avg; |
long long int sched_error_prev; |
int nro; |
long long int delta_old; |
long long int delta_new; |
|
|
} FEDFSTAR_level_des; |
|
#define HISTORY_BACK 4 |
139,34 → 147,37 |
|
typedef bandwidth_t inv_bandwidth_t; |
|
static long long int delta_new; |
static long long int tita[HISTORY_BACK][FSF_MAX_N_SERVERS]; |
static bandwidth_t u[HISTORY_BACK][FSF_MAX_N_SERVERS]; |
|
|
void init_feedbackstruct(void) { |
int i=0, j=0; |
for (i=0; i<FSF_MAX_N_SERVERS; i++) |
for (i=0; i<FSF_MAX_N_SERVERS; i++) { |
for (j=0; j<HISTORY_BACK; j++) { |
u[j][i]=0; |
tita[j][i]=0; |
} |
} |
} |
|
|
long long int FDB_sample(int sched_error, TIME server_period, TIME cavg) |
long long int FDB_sample(FEDFSTAR_level_des *lev, int sched_error, TIME server_period, TIME cavg) |
{ |
static long long int delta_old=0; |
static int sched_error_prev=0; |
|
long long int temp,temp1; |
long long int delta_new=0; |
int beta_1; //Not really this value |
int gamma_1; |
int beta_2; |
int gamma_2; |
|
#ifdef FDB_DEBUG |
#ifdef FDB_DEBUG |
kern_printf("(FDB:sample:period:%d:cavg:%d:sched_error:%d)",(int)server_period,(int)cavg, sched_error); |
#endif |
|
#endif |
|
//if (delta_old==0) |
//delta_old=1000*server_period/cavg; |
temp=1000*server_period/cavg; |
beta_1=temp*6/5; |
gamma_1=temp*(-93)/100; |
173,27 → 184,27 |
beta_2=temp/5; |
gamma_2=temp*7/100; |
|
#ifdef FDB_DEBUG |
#ifdef FDB_DEBUG |
kern_printf("(FDB:sample:b1:%d:g1:%d:b2:%d:g2:%d:temp:%d)",beta_1,gamma_1,beta_2,gamma_2, (int)temp); |
#endif |
#endif |
|
if ((long long int)sched_error>=(long long int)server_period) { |
temp=beta_1*(long long int)sched_error/server_period; |
temp1=gamma_1*(long long int)sched_error_prev/server_period; |
delta_new=delta_old-temp-temp1; |
temp1=gamma_1*(long long int)lev->sched_error_prev/server_period; |
delta_new=lev->delta_old-temp-temp1; |
} |
else { |
temp=beta_2*(long long int)sched_error/server_period; |
temp1=gamma_2*(long long int)sched_error_prev/server_period; |
delta_new=delta_old-temp-temp1; |
temp1=gamma_2*(long long int)lev->sched_error_prev/server_period; |
delta_new=lev->delta_old-temp-temp1; |
} |
#ifdef FDB_DEBUG |
kern_printf("(FDB1:sched_error:%d:delta_new:%d)",sched_error, (int)delta_new); |
kern_printf("(FDB1:sched_error:%d:delta_new:%lld)",sched_error, delta_new); |
#endif |
|
delta_old=delta_new; |
lev->delta_old=delta_new; |
|
sched_error_prev=sched_error; |
lev->sched_error_prev=sched_error; |
|
return(delta_new); |
} |
204,52 → 215,58 |
It has to add the blocking time if the task may be block |
And to determine the bandwidth it has to add the bandwidth determine in the previous function |
*/ |
TIME FDB_activate(fsf_server_id_t server, TIME server_period, TIME blk_time, TIME c_time, TIME c_avg, bandwidth_t bw) |
TIME FDB_activate(FEDFSTAR_level_des *lev,fsf_server_id_t server, TIME server_period, TIME blk_time, TIME c_time, TIME c_avg, bandwidth_t bw) |
{ |
//Filter coefficients |
static int mu=2000; //convergence factor |
static long long int u_predicted=0; |
static int mu=4; //convergence factor |
static long long int pred_error=0; |
bandwidth_t u_avg; |
long long int u_avg; |
bandwidth_t unew; |
int i; |
TIME Q_new; |
long long int u_new; |
static long long int u_p_avg=0; |
static int nro=0; |
|
//u_avg=server_bandwidth_avg; |
|
|
nro++; |
pred_error=u_predicted-(long long int)u[0][server]; |
lev->nro++; |
pred_error=lev->u_predicted-(long long int)u[0][server]; |
|
|
for (i=0;i<HISTORY_BACK;i++) { |
long long int temp=0; |
temp=pred_error*(long long int)u[i][server]/mu; |
temp=(pred_error*(long long int)u[i][server])/MAX_BANDWIDTH*mu; |
tita[i][server]=tita[i][server]-temp; |
} |
|
u_predicted=0; |
lev->u_predicted=0; |
for (i=0;i<HISTORY_BACK;i++) |
u_predicted+=((tita[i][server]*(long long int)u[i][server])); |
lev->u_predicted+=((tita[i][server]*(long long int)u[i][server])/MAX_BANDWIDTH); |
|
for (i=0; i<(HISTORY_BACK-1); i++) |
u[i+1][server]=u[i][server]; |
|
u_p_avg=(u_p_avg*(nro-1)+u_predicted)/nro; //OK |
lev->u_p_avg=(lev->u_p_avg*(lev->nro-1)+lev->u_predicted)/lev->nro; //OK |
|
|
if (c_avg!=0) |
mul32div32to32(MAX_BANDWIDTH,c_avg,server_period,u_avg); |
else |
u_avg=bw; |
// if (c_avg!=0) |
// u_avg=MAX_BANDWIDTH*c_avg/server_period; |
//else |
// u_avg=bw; |
|
kern_printf("(FDB:act_int:cavg:%d:sp:%d)", c_avg, server_period, u_avg); |
if (lev->u_p_avg==0) |
lev->u_p_avg=bw; |
|
|
#ifdef FDB_DEBUG |
kern_printf("(FDB:u_p_avg %lld)\n", lev->u_p_avg); |
kern_printf("(FDB:c_time %d)\n---------------\n",c_time); |
#endif |
|
if (c_time!=0) |
mul32div32to32(MAX_BANDWIDTH,c_time,server_period,u[0][server]); // last real computation value |
else u[0][server]=bw; |
|
mul32div32to32(MAX_BANDWIDTH,c_time,server_period,u[0][server]); // last real computation value |
|
// c_predicted+=blk_time; |
|
|
256,23 → 273,28 |
|
/* What follows is the update of the server budget based on the FDB_sample return value and the prediction function |
*/ |
|
delta_new=MAX_BANDWIDTH*(delta_new/1000); |
u_new=delta_new+(long long int)u_avg; |
if (u_new<0) exit(-1); |
if (u_new>MAX_BANDWIDTH) exit(-1); |
unew=(bandwidth_t)u_new; |
if (lev->delta_new!=0) |
lev->delta_new=MAX_BANDWIDTH*1000/lev->delta_new; /*1000; */ |
u_new=lev->delta_new+lev->u_p_avg; |
//if (u_new<0) exit(-1); |
//if (u_new>MAX_BANDWIDTH) exit(-1); |
unew=u_new; |
|
#ifdef FDB_DEBUG |
kern_printf("(FDB:unew %d)", unew); |
#endif |
|
mul32div32to32(server_period,unew, MAX_BANDWIDTH, Q_new); |
|
|
|
//Q_new=server_period*1000/u; |
//#ifdef FDB_DEBUG |
kern_printf("(FDB:act_int:unew:%d:delta_new:%d:uavg:%d)",unew, delta_new, u_avg); |
//#endif |
|
#ifdef FDB_DEBUG |
kern_printf("(FDB:uavg %lld\n)", lev->u_p_avg); |
#endif |
#ifdef FDB_DEBUG |
kern_printf("(FDB:act_int:qnew:%ld)",Q_new); |
#endif |
return(Q_new); |
} |
|
339,7 → 361,7 |
|
mul32div32to32(MAX_BANDWIDTH, Q, T, bw); |
|
Q=FDB_activate(budget, T, 0, lev->ctime[p], lev->cavg[p], bw); |
Q=FDB_activate(lev, budget, T, 0, lev->ctime[p],lev->cavg[p], bw); |
|
SERVER_adjust_budget(lev->scheduling_level, Q, T, D, budget); |
|
677,15 → 699,16 |
if (FEDFSTAR_private_change_level(l,p)) return 0; |
|
sched_error_act=0; |
/* Get the server deadline */ |
budget=FEDFSTAR_getbudget(l,p); |
SERVER_getbudgetinfo(lev->scheduling_level, &Q, &T, &D, budget); |
SERVER_getdeadline(lev->scheduling_level, budget, &t); |
//rnumber=CBSNHSTAR_getrecharge_number(lev->scheduling_level, budget); |
|
/* check if the deadline has already expired */ |
/* Get the task deadline */ |
temp = *iq_query_timespec(p, &lev->ready); |
#ifdef FDB_DEBUG |
kern_printf("(dt sec %ld, us %ld)", temp.tv_sec, temp.tv_nsec/1000); |
kern_printf("(ds sec %ld, us %ld)", t.tv_sec, t.tv_nsec/1000); |
#endif |
if (/* 1 */ TIMESPEC_A_LT_B(&t,&temp)) { |
SUBTIMESPEC(&temp, &t, &diff); |
sched_error_act=-TIMESPEC2USEC(&diff); |
705,9 → 728,8 |
|
iq_extract(p,&lev->ready); |
|
/* we reset the capacity counters... */ |
proc_table[p].avail_time = proc_table[p].wcet; |
|
|
|
lev->ctime[p]=proc_table[p].wcet-proc_table[p].avail_time; |
|
lev->cavg[p]=(lev->ctime[p]+(lev->cavg[p])*(lev->ccount[p]))/(lev->ccount[p]+1); |
714,8 → 736,11 |
|
lev->ccount[p]=(lev->ccount[p]%INT_MAX)+1; |
|
delta_new=FDB_sample(sched_error_act, T, lev->cavg[p]); |
lev->delta_new=FDB_sample(lev,sched_error_act, T, lev->cavg[p]); |
|
/* we reset the capacity counters... */ |
proc_table[p].avail_time = proc_table[p].wcet; |
|
if (lev->nact[p] > 0) { |
|
#ifdef FEDFSTAR_DEBUG |
998,6 → 1023,13 |
lev->ccount[i] = 0; |
} |
|
lev->u_predicted=0; |
lev->u_p_avg=0; |
lev->nro=0; |
lev->sched_error_prev=0; |
lev->delta_old=0; |
lev->delta_new=0; |
|
iq_init(&lev->ready, NULL, IQUEUE_NO_PRIORITY); |
lev->activated = NIL; |
|