20,11 → 20,11 |
|
/** |
------------ |
CVS : $Id: edf.c,v 1.8 2003-09-29 16:24:36 giacomo Exp $ |
CVS : $Id: edf.c,v 1.7 2003-07-24 12:24:51 giacomo Exp $ |
|
File: $File$ |
Revision: $Revision: 1.8 $ |
Last update: $Date: 2003-09-29 16:24:36 $ |
Revision: $Revision: 1.7 $ |
Last update: $Date: 2003-07-24 12:24:51 $ |
------------ |
|
This file contains the scheduling module EDF (Earliest Deadline First) |
62,7 → 62,7 |
#include <kernel/func.h> |
#include <kernel/trace.h> |
|
//#define EDF_DEBUG |
//#define EDFDEBUG |
#define edf_printf kern_printf |
|
/*+ Status used in the level +*/ |
77,6 → 77,8 |
#define EDF_FLAG_NORAISEEXC 2 |
#define EDF_FLAG_SLEEP 4 |
|
#undef EDFDEBUG |
|
/*+ the level redefinition for the Earliest Deadline First level +*/ |
typedef struct { |
level_des l; /*+ the standard level descriptor +*/ |
105,12 → 107,12 |
EDF_level_des *lev; |
struct timespec *temp; |
|
#ifdef EDFDEBUG |
edf_printf("$"); |
#endif |
|
lev = (EDF_level_des *)level_table[proc_table[p].task_level]; |
|
#ifdef EDF_DEBUG |
edf_printf("(EDF:Dl TIMER:%d)",p); |
#endif |
|
switch (proc_table[p].status) { |
case EDF_ZOMBIE: |
/* we finally put the task in the ready queue */ |
131,6 → 133,9 |
lev->deadline_timer[p] = kern_event_post(temp, |
EDF_timer_deadline, |
(void *)p); |
#ifdef EDFDEBUG |
edf_printf("(dline p%d ev%d %d.%d)",(int)p,(int)lev->deadline_timer[p],(int)temp->tv_sec,(int)temp->tv_nsec/1000); |
#endif |
event_need_reschedule(); |
break; |
|
145,6 → 150,10 |
|
default: |
/* else, a deadline miss occurred!!! */ |
#ifdef EDFDEBUG |
edf_printf("\nstatus %d\n", (int)proc_table[p].status); |
edf_printf("timer_deadline:AAARRRGGGHHH!!!"); |
#endif |
kern_raise(XDEADLINE_MISS,p); |
} |
} |
153,9 → 162,9 |
{ |
PID p = (PID) par; |
|
#ifdef EDF_DEBUG |
edf_printf("(EDF:AAARRRGGGHHH!!!)"); |
#endif |
#ifdef EDFDEBUG |
edf_printf("AAARRRGGGHHH!!!"); |
#endif |
kern_raise(XDEADLINE_MISS,p); |
} |
|
163,6 → 172,11 |
static PID EDF_public_scheduler(LEVEL l) |
{ |
EDF_level_des *lev = (EDF_level_des *)(level_table[l]); |
|
#ifdef EDFDEBUG |
edf_printf("(s%d)", iq_query_first(&lev->ready)); |
#endif |
|
return iq_query_first(&lev->ready); |
} |
|
203,9 → 217,9 |
|
/* now we know that m is a valid model */ |
|
#ifdef EDF_DEBUG |
edf_printf("(EDF:PubCrt:%d)", p); |
#endif |
#ifdef EDFDEBUG |
edf_printf("(cr%d)", p); |
#endif |
|
lev->period[p] = h->mit; |
|
233,9 → 247,9 |
|
EDF_level_des *lev = (EDF_level_des *)(level_table[l]); |
|
#ifdef EDF_DEBUG |
edf_printf("(EDF:PubDet:%d)", p); |
#endif |
#ifdef EDFDEBUG |
edf_printf("(det%d)", p); |
#endif |
|
if (lev->flags & EDF_ENABLE_GUARANTEE) { |
lev->U -= (MAX_BANDWIDTH / lev->period[p]) * proc_table[p].wcet; |
246,9 → 260,9 |
{ |
EDF_level_des *lev = (EDF_level_des *)(level_table[l]); |
|
#ifdef EDF_DEBUG |
edf_printf("(EDF:PubDsp:%d)",p); |
#endif |
#ifdef EDFDEBUG |
edf_printf("(disp p%d %d.%d)",(int)p,(int)schedule_time.tv_sec,(int)schedule_time.tv_nsec/1000); |
#endif |
|
/* the task state is set EXE by the scheduler() |
we extract the task from the ready queue |
260,9 → 274,9 |
{ |
EDF_level_des *lev = (EDF_level_des *)(level_table[l]); |
|
#ifdef EDF_DEBUG |
edf_printf("(EDF:PubEpi:%d)",p); |
#endif |
#ifdef EDFDEBUG |
edf_printf("(epil p%d %d.%d)",p,(int)schedule_time.tv_sec,(int)schedule_time.tv_nsec/1000); |
#endif |
|
/* check if the wcet is finished... */ |
if ((lev->flags & EDF_ENABLE_WCET_CHECK) && proc_table[p].avail_time <= 0) { |
282,9 → 296,9 |
EDF_level_des *lev = (EDF_level_des *)(level_table[l]); |
struct timespec *temp; |
|
#ifdef EDF_DEBUG |
edf_printf("(EDF:PubAct:%d)", p); |
#endif |
#ifdef EDFDEBUG |
edf_printf("(act%d sleep%d)", p, lev->flag[p]&EDF_FLAG_SLEEP); |
#endif |
|
if (lev->flag[p] & EDF_FLAG_SLEEP) { |
lev->flag[p] &= ~EDF_FLAG_SLEEP; |
318,6 → 332,9 |
lev->deadline_timer[p] = kern_event_post(temp, |
EDF_timer_deadline, |
(void *)p); |
#ifdef EDFDEBUG |
edf_printf("(dline p%d ev%d %d.%d)",p,(int)lev->deadline_timer[p],(int)temp->tv_sec,(int)temp->tv_nsec/1000); |
#endif |
} |
|
static void EDF_public_unblock(LEVEL l, PID p) |
349,14 → 366,14 |
{ |
EDF_level_des *lev = (EDF_level_des *)(level_table[l]); |
|
/* task_message evaluation */ |
//task_message evaluation |
switch((long)(m)) { |
|
/* task_endcycle */ |
//task_endcycle |
case (long)(NULL): |
|
#ifdef EDF_DEBUG |
edf_printf("(EDF:EndCyc:%d)",p); |
#ifdef EDFDEBUG |
edf_printf("(ecyc p%d %d.%d)",p,(int)schedule_time.tv_sec,(int)schedule_time.tv_nsec/1000); |
#endif |
|
/* the task has terminated his job before it consume the wcet. All OK! */ |
375,11 → 392,11 |
|
break; |
|
/* task_disable */ |
//task_disable |
case 1: |
|
#ifdef EDF_DEBUG |
edf_printf("(EDF:Dis:%d)",p); |
#ifdef EDFDEBUG |
edf_printf("(disable%d)",p); |
#endif |
|
/* Set the EDF_FLAG_SLEEP, in the next endcycle the task will |
463,6 → 480,9 |
{ |
EDF_level_des *lev = (EDF_level_des *)(level_table[l]); |
|
#ifdef EDFDEBUG |
edf_printf("EDF_guest_end: dline timer %d\n",lev->deadline_timer[p]); |
#endif |
if (proc_table[p].status == EDF_READY) |
iq_extract(p, &lev->ready); |
|