122,13 → 122,10 |
|
} EDFSTAR_level_des; |
|
|
|
static void capacity_handler(void *l) |
{ |
EDFSTAR_level_des *lev = l; |
lev->cap_lev = NIL; |
//kern_printf("(/)"); |
event_need_reschedule(); |
} |
|
136,9 → 133,9 |
{ |
PID first; |
|
#ifdef EDFSTAR_DEBUG |
edfstar_printf("(E:chk)"); |
#endif |
#ifdef EDFSTAR_DEBUG |
edfstar_printf("(E:chk)"); |
#endif |
|
if ((first = iq_query_first(&lev->ready)) != lev->activated) { |
if (lev->activated != NIL) |
162,10 → 159,11 |
static void EDFSTAR_internal_activate(EDFSTAR_level_des *lev, PID p, |
struct timespec *t) |
{ |
#ifdef EDFSTAR_DEBUG |
edfstar_printf("(E:iact)"); |
#endif |
|
#ifdef EDFSTAR_DEBUG |
edfstar_printf("(E:iact)"); |
#endif |
|
ADDUSEC2TIMESPEC(lev->period[p], t); |
|
*iq_query_timespec(p, &lev->ready) = *t; |
176,9 → 174,6 |
iq_timespec_insert(p,&lev->ready); |
proc_table[p].control &= ~CONTROL_CAP; |
|
/* needed because when there is a wcet miss I disable CONTROL_CAP */ |
//proc_table[p].control |= CONTROL_CAP; |
|
/* check for preemption */ |
EDFSTAR_check_preemption(lev); |
} |
188,17 → 183,10 |
PID p = (PID) par; |
EDFSTAR_level_des *lev; |
|
#ifdef EDFSTAR_DEBUG |
// edfstar_printf("(E:tdl "); |
#endif |
|
lev = (EDFSTAR_level_des *)level_table[proc_table[p].task_level]; |
|
switch (proc_table[p].status) { |
case EDFSTAR_IDLE: |
#ifdef EDFSTAR_DEBUG |
// edfstar_printf2("I%d",p); |
#endif |
/* set the request time */ |
if (!(lev->flag[p] & EDFSTAR_FLAG_SPORADIC)) |
EDFSTAR_internal_activate(lev,p,iq_query_timespec(p, &lev->ready)); |
207,17 → 195,17 |
break; |
|
default: |
#ifdef EDFSTAR_DEBUG |
kern_printf("(E:Dl:%d)",p); |
#endif |
#ifdef EDFSTAR_DEBUG |
kern_printf("(E:Dl:%d)",p); |
#endif |
/* else, a deadline miss occurred!!! */ |
lev->dline_miss[p]++; |
|
/* the task is into another state */ |
lev->nact[p]++; |
|
/* Set the deadline timer */ |
ADDUSEC2TIMESPEC(lev->period[p], &lev->deadline_timespec[p]); |
if (!(lev->flag[p] & EDFSTAR_FLAG_SPORADIC)) { |
lev->nact[p]++; |
ADDUSEC2TIMESPEC(lev->period[p], &lev->deadline_timespec[p]); |
} |
} |
|
/* Set the deadline timer */ |
226,9 → 214,6 |
EDFSTAR_timer_deadline, |
(void *)p); |
|
#ifdef EDFSTAR_DEBUG |
// edfstar_printf(")"); |
#endif |
} |
|
static void EDFSTAR_timer_guest_deadline(void *par) |
235,9 → 220,9 |
{ |
PID p = (PID) par; |
|
#ifdef EDFSTAR_DEBUG |
edfstar_printf("(E:gdl)"); |
#endif |
#ifdef EDFSTAR_DEBUG |
edfstar_printf("(E:gdl)"); |
#endif |
|
kern_raise(XDEADLINE_MISS,p); |
} |
253,14 → 238,13 |
if (m->pclass != HARD_PCLASS) return -1; |
if (m->level != 0 && m->level != l) return -1; |
h = (HARD_TASK_MODEL *)m; |
if (!h->wcet || !h->mit /* || h->periodicity != PERIODIC */) return -1; |
if (!h->wcet || !h->mit) return -1; |
/* now we know that m is a valid model */ |
|
#ifdef EDFSTAR_DEBUG |
edfstar_printf("(E:Crt)"); |
#endif |
|
#ifdef EDFSTAR_DEBUG |
edfstar_printf("(E:tcr)"); |
#endif |
|
lev->period[p] = h->mit; |
|
lev->flag[p] = 0; |
276,7 → 260,6 |
/* Enable wcet check */ |
proc_table[p].avail_time = h->wcet; |
proc_table[p].wcet = h->wcet; |
//proc_table[p].control |= CONTROL_CAP; |
|
return 0; /* OK, also if the task cannot be guaranteed... */ |
} |
291,19 → 274,19 |
tx = TIMESPEC2USEC(&ty); |
|
proc_table[p].avail_time -= tx; |
//kern_printf("avail time pid %d , %d", p, proc_table[p].avail_time); |
} |
|
} |
static int EDFSTAR_public_eligible(LEVEL l, PID p) |
{ |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
|
#ifdef EDFSTAR_DEBUG |
edfstar_printf2("(E:eli)"); |
#endif |
#ifdef EDFSTAR_DEBUG |
edfstar_printf2("(E:eli)"); |
#endif |
|
return level_table[ lev->scheduling_level ]-> |
private_eligible(lev->scheduling_level,p); |
|
} |
|
static void EDFSTAR_public_dispatch(LEVEL l, PID p, int nostop) |
311,13 → 294,10 |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
struct timespec ty; |
|
#ifdef EDFSTAR_DEBUG |
edfstar_printf("(E:dis)"); |
|
edfstar_printf3("(%d %d)", |
iq_query_timespec(p, &lev->ready)->tv_nsec/1000000, |
schedule_time.tv_nsec/1000000); |
#endif |
#ifdef EDFSTAR_DEBUG |
edfstar_printf("(E:dis)"); |
#endif |
|
if (!nostop || proc_table[exec].task_level==l) { |
TIMESPEC_ASSIGN(&ty, &schedule_time); |
TIMESPEC_ASSIGN(&lev->cap_lasttime, &schedule_time); |
337,9 → 317,9 |
{ |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
|
#ifdef EDFSTAR_DEBUG |
edfstar_printf("(E:epi "); |
#endif |
#ifdef EDFSTAR_DEBUG |
edfstar_printf("(E:epi "); |
#endif |
|
if (lev->cap_lev!=NIL) { |
kern_event_delete(lev->cap_lev); |
354,20 → 334,22 |
/* check if the wcet is finished... */ |
if (proc_table[exec].avail_time <= 0) { |
/* wcet finished: disable wcet event and count wcet miss */ |
#ifdef EDFSTAR_DEBUG |
edfstar_printf2("W%d",p); |
#endif |
|
#ifdef EDFSTAR_DEBUG |
edfstar_printf2("W%d",p); |
#endif |
//proc_table[p].control &= ~CONTROL_CAP; |
lev->wcet_miss[exec]++; |
} |
#ifdef EDFSTAR_DEBUG |
edfstar_printf(")"); |
#endif |
|
level_table[ lev->scheduling_level ]-> |
private_epilogue(lev->scheduling_level,p); |
#ifdef EDFSTAR_DEBUG |
edfstar_printf(")"); |
#endif |
|
proc_table[exec].status = EDFSTAR_READY; |
level_table[ lev->scheduling_level ]-> |
private_epilogue(lev->scheduling_level,p); |
|
proc_table[exec].status = EDFSTAR_READY; |
} else |
level_table[proc_table[exec].task_level]->public_epilogue(proc_table[exec].task_level,p); |
|
387,13 → 369,14 |
if (proc_table[p].status != SLEEP) { |
/* a periodic task cannot be activated when it is already active */ |
/* but aperiodic task can be reactivate before */ |
if (lev->flag[p] & EDFSTAR_FLAG_SPORADIC) |
lev->nact[p]++; |
else |
if (lev->flag[p] & EDFSTAR_FLAG_SPORADIC) { |
if (proc_table[p].status != EDFSTAR_IDLE) { |
lev->nact[p]++; |
return; |
} |
} else { |
kern_raise(XACTIVATION,p); |
|
if (proc_table[p].status != EDFSTAR_IDLE) return; |
|
} |
} |
|
kern_gettime(&t); |
411,99 → 394,106 |
{ |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
|
#ifdef EDFSTAR_DEBUG |
edfstar_printf("(E:ins)"); |
#endif |
#ifdef EDFSTAR_DEBUG |
edfstar_printf("(E:ins)"); |
#endif |
|
/* Insert task in the correct position */ |
proc_table[p].status = EDFSTAR_READY; |
iq_timespec_insert(p,&lev->ready); |
/* Insert task in the correct position */ |
proc_table[p].status = EDFSTAR_READY; |
iq_timespec_insert(p,&lev->ready); |
|
/* and check for preemption! */ |
EDFSTAR_check_preemption(lev); |
/* and check for preemption! */ |
EDFSTAR_check_preemption(lev); |
|
} |
|
static void EDFSTAR_public_block(LEVEL l, PID p) |
{ |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
|
#ifdef EDFSTAR_DEBUG |
edfstar_printf("(E:ext)"); |
#endif |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
|
/* the task is blocked on a synchronization primitive. we have to |
remove it from the master module -and- from the local queue! */ |
iq_extract(p,&lev->ready); |
#ifdef EDFSTAR_DEBUG |
edfstar_printf("(E:ext)"); |
#endif |
|
/* and finally, a preemption check! (it will also call guest_end) */ |
EDFSTAR_check_preemption(lev); |
/* the task is blocked on a synchronization primitive. we have to |
remove it from the master module -and- from the local queue! */ |
iq_extract(p,&lev->ready); |
|
/* and finally, a preemption check! (it will also call guest_end) */ |
EDFSTAR_check_preemption(lev); |
} |
|
static int EDFSTAR_public_message(LEVEL l, PID p, void *m) |
{ |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
struct timespec temp; |
|
#ifdef EDFSTAR_DEBUG |
edfstar_printf("(E:ecy "); |
#endif |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
struct timespec temp; |
|
switch ((long)(m)) { |
#ifdef EDFSTAR_DEBUG |
edfstar_printf("(E:ecy "); |
#endif |
|
/* Task EndCycle */ |
case (long)(NULL): |
switch ((long)(m)) { |
|
/* we call guest_end directly here because the same task may |
be reinserted in the queue before calling the preemption check! */ |
level_table[ lev->scheduling_level ]-> |
private_extract(lev->scheduling_level,p); |
lev->activated = NIL; |
/* Task EndCycle */ |
case (long)(NULL): |
|
iq_extract(p,&lev->ready); |
/* we call guest_end directly here because the same task may |
be reinserted in the queue before calling the preemption check! */ |
level_table[ lev->scheduling_level ]-> |
private_extract(lev->scheduling_level,p); |
lev->activated = NIL; |
|
/* we reset the capacity counters... */ |
proc_table[p].avail_time = proc_table[p].wcet; |
iq_extract(p,&lev->ready); |
|
if (lev->nact[p] > 0) { |
/* we reset the capacity counters... */ |
proc_table[p].avail_time = proc_table[p].wcet; |
|
if (lev->nact[p] > 0) { |
|
#ifdef EDFSTAR_DEBUG |
edfstar_printf2("E%d",p); |
#endif |
#ifdef EDFSTAR_DEBUG |
edfstar_printf2("E%d",p); |
#endif |
|
/* Pending activation: reactivate the thread!!! */ |
lev->nact[p]--; |
/* Pending activation: reactivate the thread!!! */ |
lev->nact[p]--; |
|
/* see also EDFSTAR_timer_deadline */ |
kern_gettime(&temp); |
/* see also EDFSTAR_timer_deadline */ |
kern_gettime(&temp); |
|
EDFSTAR_internal_activate(lev,p, &temp); |
EDFSTAR_internal_activate(lev,p, &temp); |
|
/* check if the deadline has already expired */ |
temp = *iq_query_timespec(p, &lev->ready); |
if (TIMESPEC_A_LT_B(&temp, &schedule_time)) { |
/* count the deadline miss */ |
lev->dline_miss[p]++; |
kern_event_delete(lev->deadline_timer[p]); |
} |
/* check if the deadline has already expired */ |
temp = *iq_query_timespec(p, &lev->ready); |
if (TIMESPEC_A_LT_B(&temp, &schedule_time)) { |
/* count the deadline miss */ |
lev->dline_miss[p]++; |
kern_event_delete(lev->deadline_timer[p]); |
} |
|
} else { |
} else { |
|
#ifdef EDFSTAR_DEBUG |
edfstar_printf("e%d",p); |
#endif |
#ifdef EDFSTAR_DEBUG |
edfstar_printf("e%d",p); |
#endif |
|
/* the task has terminated his job before it consume the wcet. All OK! */ |
proc_table[p].status = EDFSTAR_IDLE; |
/* the task has terminated his job before it consume the wcet. All OK! */ |
proc_table[p].status = EDFSTAR_IDLE; |
|
if (lev->flag[p] & EDFSTAR_FLAG_SPORADIC && lev->deadline_timer[p] != NIL) |
kern_event_delete(lev->deadline_timer[p]); |
|
/* and finally, a preemption check! */ |
EDFSTAR_check_preemption(lev); |
/* and finally, a preemption check! */ |
EDFSTAR_check_preemption(lev); |
|
/* when the deadline timer fire, it recognize the situation and set |
correctly all the stuffs (like reactivation, etc... ) */ |
} |
#ifdef EDFSTAR_DEBUG |
edfstar_printf(")"); |
#endif |
/* when the deadline timer fire, it recognize the situation and set |
correctly all the stuffs (like reactivation, etc... ) */ |
} |
|
#ifdef EDFSTAR_DEBUG |
edfstar_printf(")"); |
#endif |
|
jet_update_endcycle(); /* Update the Jet data... */ |
trc_logevent(TRC_ENDCYCLE,&exec_shadow); /* tracer stuff */ |
521,9 → 511,9 |
{ |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
|
#ifdef EDFSTAR_DEBUG |
edfstar_printf("(E:end)"); |
#endif |
#ifdef EDFSTAR_DEBUG |
edfstar_printf("(E:end)"); |
#endif |
|
iq_extract(p,&lev->ready); |
|