/demos/trunk/block/common.c |
---|
36,6 → 36,7 |
void ctrlc_exit(KEY_EVT *k) |
{ |
//sys_status(SCHED_STATUS); |
cprintf("CTRL-C pressed!\n"); |
sys_end(); |
} |
/demos/trunk/perf/perf3.c |
---|
16,11 → 16,11 |
/** |
------------ |
CVS : $Id: perf3.c,v 1.2 2003-01-07 17:10:18 pj Exp $ |
CVS : $Id: perf3.c,v 1.1 2002-11-11 08:24:49 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2003-01-07 17:10:18 $ |
Revision: $Revision: 1.1 $ |
Last update: $Date: 2002-11-11 08:24:49 $ |
------------ |
Performance Test 3: |
311,7 → 311,7 |
TIME delta; |
// get the current time |
kern_gettime(&t); |
ll_gettime(TIME_EXACT, &t); |
// compute the delta |
SUBTIMESPEC(&t, &last_random_time, &sub); |
/demos/trunk/perf/perf1.c |
---|
16,11 → 16,11 |
/** |
------------ |
CVS : $Id: perf1.c,v 1.2 2003-01-07 17:10:18 pj Exp $ |
CVS : $Id: perf1.c,v 1.1 2002-11-11 08:24:49 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2003-01-07 17:10:18 $ |
Revision: $Revision: 1.1 $ |
Last update: $Date: 2002-11-11 08:24:49 $ |
------------ |
Performance test 1: |
32,9 → 32,6 |
the test have to be compiled with the one shot timer, and it does not |
use any init file. |
NOTE: after the task_sleep() removal, the test may be "not so correct". |
That is because also the task end is accounted into the EDF time. |
**/ |
/* |
124,7 → 121,7 |
kern_cli(); |
/* timespec read time */ |
for (i=0; i<TIMESPEC_N; i++) { |
t[i] = kern_gettime(NULL); |
t[i] = ll_gettime(TIME_EXACT, NULL); |
} |
kern_sti(); |
161,7 → 158,7 |
for (;;) { |
for (i=0; i<RR_N; i++); |
task_endcycle(); |
task_sleep(); |
} |
return 0; |
} |
170,9 → 167,11 |
{ |
int i; |
for (i=0; i<EDF_N; i++) |
task_endcycle(); |
for (;;) { |
for (i=0; i<EDF_N; i++) |
task_endcycle(); |
task_sleep(); |
} |
return 0; |
} |
/demos/trunk/base/aster5.c |
---|
34,7 → 34,7 |
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
* |
* |
* CVS : $Id: aster5.c,v 1.2 2003-01-07 17:10:15 pj Exp $ |
* CVS : $Id: aster5.c,v 1.1 2002-11-11 08:22:45 pj Exp $ |
this is a part of the classic Hartik demo Aster. |
400,6 → 400,7 |
emerg.flag = ALTL_BIT; |
keyb_hook(emerg,fine); |
clear(); |
hard_task_default_model(m); |
/demos/trunk/base/aster6.c |
---|
34,7 → 34,7 |
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
* |
* |
* CVS : $Id: aster6.c,v 1.2 2003-01-07 17:10:15 pj Exp $ |
* CVS : $Id: aster6.c,v 1.1 2002-11-11 08:22:45 pj Exp $ |
this is a part of the classic Hartik demo Aster. |
302,7 → 302,6 |
printf_xy(62,4,WHITE,"Ucbs=%12u",CBS_usedbandwidth(2)); |
mutex_unlock(&m1); |
task_endcycle(); |
if (++s > 59) { |
393,6 → 392,7 |
emerg.flag = ALTL_BIT; |
keyb_hook(emerg,fine); |
set_exchandler_grx(); |
clear(); |
hard_task_default_model(m); |
478,7 → 478,6 |
fineprg.tv_nsec = 0; |
kern_event_post(&fineprg,(void (*)(void *))fine,NULL); |
group_activate(1); |
return 0; |
} |
/demos/trunk/base/aster7.c |
---|
34,7 → 34,7 |
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
* |
* |
* CVS : $Id: aster7.c,v 1.2 2003-01-07 17:10:15 pj Exp $ |
* CVS : $Id: aster7.c,v 1.1 2002-11-11 08:22:45 pj Exp $ |
this is a part of the classic Hartik demo Aster. |
246,6 → 246,8 |
cprintf("Press Alt-x to end the demo..."); |
set_exchandler_grx(); |
//keyb_set_map(itaMap); |
emerg.ascii = 'x'; |
emerg.scan = KEY_X; |
/demos/trunk/base/aster8.c |
---|
34,7 → 34,7 |
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
* |
* |
* CVS : $Id: aster8.c,v 1.2 2003-01-07 17:10:15 pj Exp $ |
* CVS : $Id: aster8.c,v 1.1 2002-11-11 08:22:45 pj Exp $ |
Test for Sporadic Server (ss): |
438,6 → 438,8 |
cprintf("Press Alt-x to end the demo..."); |
set_exchandler_grx(); |
hard_task_default_model(m); |
hard_task_def_mit(m,100000); |
hard_task_def_wcet(m,ASTER_WCET); |
/demos/trunk/base/sched.c |
---|
34,7 → 34,7 |
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
* |
* |
* CVS : $Id: sched.c,v 1.2 2003-01-07 17:10:15 pj Exp $ |
* CVS : $Id: sched.c,v 1.1 2002-11-11 08:22:46 pj Exp $ |
This demo is derived from the cbsmouse.c Hartik's example. |
306,6 → 306,8 |
HARD_TASK_MODEL m_per; |
int modenum; |
set_exchandler_grx(); |
if (argc>=3) |
switch(*argv[2]) { |
case 'h': |
/demos/trunk/base/pcdemo.c |
---|
34,7 → 34,7 |
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
* |
* |
* CVS : $Id: pcdemo.c,v 1.2 2003-01-07 17:10:15 pj Exp $ |
* CVS : $Id: pcdemo.c,v 1.1 2002-11-11 08:22:46 pj Exp $ |
This test verify the correctness of the PC module. |
142,8 → 142,6 |
KEY_EVT emerg; |
clear(); |
cprintf("Priority Ceiling demo. Press Alt-X to exit the demo\n"); |
//keyb_set_map(itaMap); |
/demos/trunk/base/srpdemo.c |
---|
34,7 → 34,7 |
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
* |
* |
* CVS : $Id: srpdemo.c,v 1.2 2003-01-07 17:10:16 pj Exp $ |
* CVS : $Id: srpdemo.c,v 1.1 2002-11-11 08:22:46 pj Exp $ |
This test verify the correctness of the SRP module. |
173,8 → 173,6 |
KEY_EVT emerg; |
clear(); |
cprintf("Stack resource Policy demo. Press Alt-X to exit the demo\n"); |
//keyb_set_map(itaMap); |
/demos/trunk/base/preempt.c |
---|
34,7 → 34,7 |
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
* |
* |
* CVS : $Id: preempt.c,v 1.2 2003-01-07 17:10:15 pj Exp $ |
* CVS : $Id: preempt.c,v 1.1 2002-11-11 08:22:46 pj Exp $ |
CBS test with preemption disabling |
53,8 → 53,6 |
task_endcycle(); |
} |
cprintf("Periodic: Task %d end.\n", exec_shadow); |
return 0; |
} |
/demos/trunk/base/pidemo.c |
---|
34,7 → 34,7 |
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
* |
* |
* CVS : $Id: pidemo.c,v 1.2 2003-01-07 17:10:15 pj Exp $ |
* CVS : $Id: pidemo.c,v 1.1 2002-11-11 08:22:46 pj Exp $ |
This test verify the correctness of the PI module. |
79,6 → 79,8 |
PI_mutexattr_t a; |
set_exchandler_grx(); |
hard_task_default_model(m); |
hard_task_def_mit(m,50000); |
hard_task_def_wcet(m,20000); |
/demos/trunk/base/aster.c |
---|
34,7 → 34,7 |
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
* |
* |
* CVS : $Id: aster.c,v 1.2 2003-01-07 17:10:15 pj Exp $ |
* CVS : $Id: aster.c,v 1.1 2002-11-11 08:22:45 pj Exp $ |
Author: Gerardo Lamastra |
Giuseppe Lipari |
259,7 → 259,7 |
c = keyb_getchar(); |
if (c == ESC) { |
esc = TRUE; |
task_endcycle(); |
task_sleep(); |
} |
else { |
#ifdef __VPAGING__ |
302,6 → 302,11 |
sys_end(); |
} |
void res(void *arg) |
{ |
sys_status(CLOCK_STATUS|SCHED_STATUS); |
} |
int main(int argc, char **argv) |
{ |
PID p1,p2,p3,p4,p5,p6; |
314,6 → 319,8 |
// double rif; |
struct timespec t; |
sys_atrunlevel(res, NULL, RUNLEVEL_BEFORE_EXIT); |
//keyb_set_map(itaMap); |
emerg.ascii = 'x'; |
emerg.scan = KEY_X; |
391,7 → 398,10 |
group_activate(1); |
while (!esc) { |
sys_gettime(&t); |
kern_cli(); |
ll_gettime(TIME_EXACT,&t); |
kern_sti(); |
printf_xy(0,21,WHITE,"Clock : %-9ds %-9dns",(int)t.tv_sec, (int)t.tv_nsec); |
} |
/demos/trunk/base/aster3.c |
---|
34,7 → 34,7 |
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
* |
* |
* CVS : $Id: aster3.c,v 1.3 2003-01-07 17:10:15 pj Exp $ |
* CVS : $Id: aster3.c,v 1.2 2002-11-11 08:20:44 pj Exp $ |
Test Number 10 (A): |
238,6 → 238,8 |
clear(); |
set_exchandler_grx(); |
hard_task_default_model(m); |
hard_task_def_wcet(m,ASTER_WCET); |
hard_task_def_mit(m,10000); |
/demos/trunk/base/sig.c |
---|
18,11 → 18,11 |
/** |
------------ |
CVS : $Id: sig.c,v 1.3 2003-01-07 17:10:15 pj Exp $ |
CVS : $Id: sig.c,v 1.2 2002-11-11 08:20:44 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.3 $ |
Last update: $Date: 2003-01-07 17:10:15 $ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2002-11-11 08:20:44 $ |
------------ |
**/ |
81,19 → 81,14 |
return 0; |
} |
void catchit_RT(int signo, siginfo_t *info, void *extra) |
void catchit(int signo, siginfo_t *info, void *extra) |
{ |
cprintf("RT signal: Current Running Task = %d signo=%d code=%d value=%d from pid=%d\n", |
cprintf("Current Running Task = %d signo=%d code=%d value=%d from pid=%d\n", |
exec_shadow, |
info->si_signo, info->si_code, |
info->si_value.sival_int, info->si_task); |
} |
void catchit(int signo) |
{ |
cprintf("RT signal: Current Running Task = %d signo=%d\n", |
exec_shadow, signo); |
} |
int main(int argc, char **argv) |
{ |
110,7 → 105,7 |
/* Set the signal action */ |
action.sa_flags = SA_SIGINFO; |
action.sa_sigaction = catchit_RT; |
action.sa_sigaction = catchit; |
action.sa_handler = 0; |
action.sa_mask = 0; |
/demos/trunk/base/aster1.c |
---|
34,7 → 34,7 |
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
* |
* |
* CVS : $Id: aster1.c,v 1.2 2003-01-07 17:10:15 pj Exp $ |
* CVS : $Id: aster1.c,v 1.1 2002-10-28 08:13:37 pj Exp $ |
this is a reduced verion of the classic Hartik demo Aster. |
168,6 → 168,7 |
sys_gettime(&t); |
} while (t.tv_sec < 6); |
sys_status(SCHED_STATUS); |
sys_end(); |
return 0; |
} |
/demos/trunk/base/cabs.c |
---|
34,7 → 34,7 |
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
* |
* |
* CVS : $Id: cabs.c,v 1.3 2003-01-07 17:10:15 pj Exp $ |
* CVS : $Id: cabs.c,v 1.2 2002-10-28 08:11:29 pj Exp $ |
*/ |
/*--------------------------------------------------------------*/ |
88,6 → 88,32 |
/****************************************************************/ |
/* This is the exception handler. It is called when an exception |
is raised. |
It exits from the graphical mode, then it prints a message and |
shutdown the kernel using sys_abort() |
*/ |
void demo_exc_handler(int signo, siginfo_t *info, void *extra) |
{ |
struct timespec t; |
grx_close(); |
/* Default action for an kern exception is */ |
kern_cli(); |
ll_gettime(TIME_EXACT, &t), |
cprintf("\nS.Ha.R.K. Exception raised!!!" |
"\nTime (s:ns) :%ld:%ld" |
"\nException number:%d (numbers in include/bits/errno.h)" |
"\nPID :%d\n", |
t.tv_sec, t.tv_nsec, info->si_value.sival_int, |
info->si_task); |
sys_abort(1); |
} |
/******************************************************************/ |
/* This function is called when Alt-X is pressed. |
It simply shutdown the system using sys_end. |
Note that the byebye() function is called only if we exit from |
134,10 → 160,23 |
int main(int argc, char **argv) |
{ |
struct sigaction action; |
char c = 0; /* character from keyboard */ |
/* Init the standard S.Ha.R.K. exception handler */ |
action.sa_flags = SA_SIGINFO; /* Set the signal action */ |
action.sa_sigaction = demo_exc_handler; |
action.sa_handler = 0; |
sigfillset(&action.sa_mask); /* we block all the other signals... */ |
if (sigaction(SIGHEXC, &action, NULL) == -1) { /* set the signal */ |
perror("Error initializing signals..."); |
sys_end(); |
} |
/* Set the closing function */ |
sys_atrunlevel(byebye, NULL, RUNLEVEL_BEFORE_EXIT); |
sys_atrunlevel(byebye, NULL, RUNLEVEL_BEFORE_EXIT|NO_AT_ABORT); |
/* graphic card Initialization */ |
if (grx_init() < 1) { |
/demos/trunk/base/ego.c |
---|
18,11 → 18,11 |
/** |
------------ |
CVS : $Id: ego.c,v 1.3 2003-01-07 17:10:15 pj Exp $ |
CVS : $Id: ego.c,v 1.2 2002-10-28 08:11:29 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.3 $ |
Last update: $Date: 2003-01-07 17:10:15 $ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2002-10-28 08:11:29 $ |
------------ |
**/ |
111,6 → 111,32 |
/****************************************************************/ |
/* This is the exception handler. It is called when an exception |
is raised. |
It exits from the graphical mode, then it prints a message and |
shutdown the kernel using sys_abort() |
*/ |
void demo_exc_handler(int signo, siginfo_t *info, void *extra) |
{ |
struct timespec t; |
grx_close(); |
/* Default action for an kern exception is */ |
kern_cli(); |
ll_gettime(TIME_EXACT, &t), |
cprintf("\nS.Ha.R.K. Exception raised!!!" |
"\nTime (s:ns) :%ld:%ld" |
"\nException number:%d (numbers in include/bits/errno.h)" |
"\nPID :%d\n", |
t.tv_sec, t.tv_nsec, info->si_value.sival_int, |
info->si_task); |
sys_abort(1); |
} |
/******************************************************************/ |
/* This function is called when Alt-X is pressed. |
It simply shutdown the system using sys_end. |
Note that the byebye() function is called only if we exit from |
150,9 → 176,21 |
PID pid1, pid2, pid3; |
KEY_EVT emerg; |
HARD_TASK_MODEL m1, m2, m3; |
struct sigaction action; |
/* Init the standard S.Ha.R.K. exception handler */ |
action.sa_flags = SA_SIGINFO; /* Set the signal action */ |
action.sa_sigaction = demo_exc_handler; |
action.sa_handler = 0; |
sigfillset(&action.sa_mask); /* we block all the other signals... */ |
if (sigaction(SIGHEXC, &action, NULL) == -1) { /* set the signal */ |
perror("Error initializing signals..."); |
sys_end(); |
} |
/* Set the closing function */ |
sys_atrunlevel(byebye, NULL, RUNLEVEL_BEFORE_EXIT); |
sys_atrunlevel(byebye, NULL, RUNLEVEL_BEFORE_EXIT|NO_AT_ABORT); |
/* Initializes the semaphore */ |
sem_init(&mutex,0,1); |
/demos/trunk/base/fly.c |
---|
18,11 → 18,11 |
/** |
------------ |
CVS : $Id: fly.c,v 1.3 2003-01-07 17:10:15 pj Exp $ |
CVS : $Id: fly.c,v 1.2 2002-10-28 08:11:29 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.3 $ |
Last update: $Date: 2003-01-07 17:10:15 $ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2002-10-28 08:11:29 $ |
------------ |
**/ |
160,6 → 160,9 |
int i = 0; /* number of tasks created */ |
TIME seme; /* used to init the random seed */ |
/* Set the exception handler */ |
set_exchandler_grx(); |
/* Set the closing function */ |
sys_atrunlevel(byebye, NULL, RUNLEVEL_BEFORE_EXIT); |
/demos/trunk/auto/edfact.c |
---|
18,11 → 18,11 |
/** |
------------ |
CVS : $Id: edfact.c,v 1.4 2003-01-07 17:10:15 pj Exp $ |
CVS : $Id: edfact.c,v 1.3 2002-11-11 08:19:19 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.4 $ |
Last update: $Date: 2003-01-07 17:10:15 $ |
Revision: $Revision: 1.3 $ |
Last update: $Date: 2002-11-11 08:19:19 $ |
------------ |
**/ |
95,14 → 95,14 |
static void EDFACT_timer_deadline(void *par); |
static void EDFACT_internal_activate(EDFACT_level_des *lev, PID p, |
struct timespec *t) |
static void EDFACT_internal_activate(EDFACT_level_des *lev, PID p) |
{ |
struct timespec *temp; |
temp = iq_query_timespec(p, &lev->ready); |
TIMESPEC_ASSIGN(temp,t); |
TIMESPEC_ASSIGN(temp, |
&proc_table[p].request_time); |
ADDUSEC2TIMESPEC(lev->period[p], temp); |
TIMESPEC_ASSIGN(&lev->deadline_timespec[p], |
116,6 → 116,18 |
proc_table[p].control |= CONTROL_CAP; |
} |
static char *EDFACT_status_to_a(WORD status) |
{ |
if (status < MODULE_STATUS_BASE) |
return status_to_a(status); |
switch (status) { |
case EDFACT_READY : return "EDFACT_Ready"; |
case EDFACT_IDLE : return "EDFACT_Idle"; |
default : return "EDFACT_Unknown"; |
} |
} |
static void EDFACT_timer_deadline(void *par) |
{ |
PID p = (PID) par; |
127,8 → 139,10 |
case EDFACT_IDLE: |
edfact_printf("I%d",p); |
EDFACT_internal_activate(lev,p, &lev->deadline_timespec[p]); |
*iq_query_timespec(p, &lev->ready) = proc_table[p].request_time; |
EDFACT_internal_activate(lev,p); |
event_need_reschedule(); |
break; |
159,17 → 173,93 |
kern_raise(XDEADLINE_MISS,p); |
} |
static int EDFACT_level_accept_task_model(LEVEL l, TASK_MODEL *m) |
{ |
if (m->pclass == HARD_PCLASS || m->pclass == (HARD_PCLASS | l)) { |
HARD_TASK_MODEL *h = (HARD_TASK_MODEL *)m; |
if (h->wcet && h->mit && h->periodicity == PERIODIC) |
return 0; |
} |
return -1; |
} |
static int EDFACT_level_accept_guest_model(LEVEL l, TASK_MODEL *m) |
{ |
if (m->pclass == JOB_PCLASS || m->pclass == (JOB_PCLASS | l)) |
return 0; |
else |
return -1; |
} |
static char *onoff(int i) |
{ |
if (i) |
return "On "; |
else |
return "Off"; |
} |
static void EDFACT_level_status(LEVEL l) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
PID p = iq_query_first(&lev->ready); |
kern_printf("On-line guarantee : %s\n", |
onoff(lev->flags & EDFACT_ENABLE_GUARANTEE)); |
kern_printf("Used Bandwidth : %u/%u\n", |
lev->U, MAX_BANDWIDTH); |
while (p != NIL) { |
if ((proc_table[p].pclass) == JOB_PCLASS) |
kern_printf("Pid: %2d (GUEST)\n", p); |
else |
kern_printf("Pid: %2d Name: %10s %s: %9d Dline: %9d.%6d Stat: %s\n", |
p, |
proc_table[p].name, |
"Period ", |
lev->period[p], |
iq_query_timespec(p, &lev->ready)->tv_sec, |
iq_query_timespec(p, &lev->ready)->tv_nsec/1000, |
EDFACT_status_to_a(proc_table[p].status)); |
p = iq_query_next(p, &lev->ready); |
} |
for (p=0; p<MAX_PROC; p++) |
if (proc_table[p].task_level == l && proc_table[p].status != EDFACT_READY |
&& proc_table[p].status != FREE ) |
kern_printf("Pid: %2d Name: %10s %s: %9d Dline: %9d.%6d Stat: %s\n", |
p, |
proc_table[p].name, |
"Period ", |
lev->period[p], |
iq_query_timespec(p, &lev->ready)->tv_sec, |
iq_query_timespec(p, &lev->ready)->tv_nsec/1000, |
EDFACT_status_to_a(proc_table[p].status)); |
} |
/* The scheduler only gets the first task in the queue */ |
static PID EDFACT_public_scheduler(LEVEL l) |
static PID EDFACT_level_scheduler(LEVEL l) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
/* { // print 4 dbg the ready queue |
PID p= lev->ready; |
kern_printf("(s"); |
while (p != NIL) { |
kern_printf("%d ",p); |
p = proc_table[p].next; |
} |
kern_printf(") "); |
} |
*/ |
return iq_query_first(&lev->ready); |
} |
/* The on-line guarantee is enabled only if the appropriate flag is set... */ |
static int EDFACT_public_guarantee(LEVEL l, bandwidth_t *freebandwidth) |
static int EDFACT_level_guarantee(LEVEL l, bandwidth_t *freebandwidth) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
187,17 → 277,14 |
} |
static int EDFACT_public_create(LEVEL l, PID p, TASK_MODEL *m) |
static int EDFACT_task_create(LEVEL l, PID p, TASK_MODEL *m) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
HARD_TASK_MODEL *h; |
/* if the EDFACT_task_create is called, then the pclass must be a |
valid pclass. */ |
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; |
/* now we know that m is a valid model */ |
HARD_TASK_MODEL *h = (HARD_TASK_MODEL *)m; |
lev->period[p] = h->mit; |
239,7 → 326,7 |
return 0; /* OK, also if the task cannot be guaranteed... */ |
} |
static void EDFACT_public_detach(LEVEL l, PID p) |
static void EDFACT_task_detach(LEVEL l, PID p) |
{ |
/* the EDFACT level doesn't introduce any dinamic allocated new field. |
we have only to reset the NO_GUARANTEE FIELD and decrement the allocated |
253,8 → 340,13 |
lev->U -= (MAX_BANDWIDTH / lev->period[p]) * proc_table[p].wcet; |
} |
static void EDFACT_public_dispatch(LEVEL l, PID p, int nostop) |
static int EDFACT_task_eligible(LEVEL l, PID p) |
{ |
return 0; /* if the task p is chosen, it is always eligible */ |
} |
static void EDFACT_task_dispatch(LEVEL l, PID p, int nostop) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
/* the task state is set EXE by the scheduler() |
263,7 → 355,7 |
iq_extract(p, &lev->ready); |
} |
static void EDFACT_public_epilogue(LEVEL l, PID p) |
static void EDFACT_task_epilogue(LEVEL l, PID p) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
280,10 → 372,9 |
proc_table[p].status = EDFACT_READY; |
} |
static void EDFACT_public_activate(LEVEL l, PID p) |
static void EDFACT_task_activate(LEVEL l, PID p) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
struct timespec t; |
/* Test if we are trying to activate a non sleeping task */ |
/* save activation (only if needed... */ |
293,9 → 384,10 |
return; |
} |
kern_gettime(&t); |
EDFACT_internal_activate(lev,p, &t); |
ll_gettime(TIME_EXACT, &proc_table[p].request_time); |
EDFACT_internal_activate(lev,p); |
/* Set the deadline timer */ |
lev->deadline_timer[p] = kern_event_post(&lev->deadline_timespec[p], |
EDFACT_timer_deadline, |
303,7 → 395,7 |
} |
static void EDFACT_public_unblock(LEVEL l, PID p) |
static void EDFACT_task_insert(LEVEL l, PID p) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
312,15 → 404,15 |
iq_timespec_insert(p,&lev->ready); |
} |
static void EDFACT_public_block(LEVEL l, PID p) |
static void EDFACT_task_extract(LEVEL l, PID p) |
{ |
} |
static int EDFACT_public_message(LEVEL l, PID p, void *m) |
static void EDFACT_task_endcycle(LEVEL l, PID p) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
struct timespec t; |
/* we reset the capacity counters... */ |
proc_table[p].avail_time = proc_table[p].wcet; |
331,14 → 423,15 |
lev->nact[p]--; |
/* see also EDFACT_timer_deadline */ |
kern_gettime(&t); |
EDFACT_internal_activate(lev,p, &t); |
ll_gettime(TIME_EXACT, &proc_table[p].request_time); |
EDFACT_internal_activate(lev,p); |
/* check if the deadline has already expired */ |
if (TIMESPEC_A_LT_B(iq_query_timespec(p, &lev->ready), &schedule_time)) { |
/* count the deadline miss */ |
lev->dline_miss[p]++; |
kern_event_delete(lev->deadline_timer[p]); |
event_delete(lev->deadline_timer[p]); |
} |
} |
349,16 → 442,11 |
proc_table[p].status = EDFACT_IDLE; |
/* when the deadline timer fire, it recognize the situation and set |
correctly all the stuffs (like reactivation, etc... ) */ |
correctly all the stuffs (like reactivation, request_time, etc... ) */ |
} |
jet_update_endcycle(); /* Update the Jet data... */ |
trc_logevent(TRC_ENDCYCLE,&exec_shadow); /* tracer stuff */ |
return 0; |
} |
static void EDFACT_public_end(LEVEL l, PID p) |
static void EDFACT_task_end(LEVEL l, PID p) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
372,28 → 460,25 |
if (lev->deadline_timer[p] != -1) { |
edfact_printf("²%d",p); |
kern_event_delete(lev->deadline_timer[p]); |
event_delete(lev->deadline_timer[p]); |
} |
} |
static void EDFACT_task_sleep(LEVEL l, PID p) |
{ kern_raise(XINVALID_TASK,exec_shadow); } |
/* Guest Functions |
These functions manages a JOB_TASK_MODEL, that is used to put |
a guest task in the EDFACT ready queue. */ |
static void EDFACT_private_insert(LEVEL l, PID p, TASK_MODEL *m) |
static int EDFACT_guest_create(LEVEL l, PID p, TASK_MODEL *m) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
JOB_TASK_MODEL *job = (JOB_TASK_MODEL *)m; |
JOB_TASK_MODEL *job; |
/* if the EDFACT_guest_create is called, then the pclass must be a |
valid pclass. */ |
if (m->pclass != JOB_PCLASS || (m->level != 0 && m->level != l) ) { |
kern_raise(XINVALID_TASK, p); |
return; |
} |
job = (JOB_TASK_MODEL *)m; |
TIMESPEC_ASSIGN(iq_query_timespec(p, &lev->ready), &job->deadline); |
lev->deadline_timer[p] = -1; |
403,25 → 488,26 |
if (job->noraiseexc) |
lev->flag[p] = EDFACT_FLAG_NORAISEEXC; |
else { |
else |
lev->flag[p] = 0; |
lev->deadline_timer[p] = kern_event_post(iq_query_timespec(p, &lev->ready), |
EDFACT_timer_guest_deadline, |
(void *)p); |
} |
lev->period[p] = job->period; |
/* Insert task in the correct position */ |
iq_timespec_insert(p,&lev->ready); |
proc_table[p].status = EDFACT_READY; |
/* there is no bandwidth guarantee at this level, it is performed |
by the level that inserts guest tasks... */ |
return 0; /* OK, also if the task cannot be guaranteed... */ |
} |
static void EDFACT_private_dispatch(LEVEL l, PID p, int nostop) |
static void EDFACT_guest_detach(LEVEL l, PID p) |
{ |
/* the EDFACT level doesn't introduce any dinamic allocated new field. |
No guarantee is performed on guest tasks... so we don't have to reset |
the NO_GUARANTEE FIELD */ |
} |
static void EDFACT_guest_dispatch(LEVEL l, PID p, int nostop) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
/* the task state is set to EXE by the scheduler() |
430,7 → 516,7 |
iq_extract(p, &lev->ready); |
} |
static void EDFACT_private_epilogue(LEVEL l, PID p) |
static void EDFACT_guest_epilogue(LEVEL l, PID p) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
439,10 → 525,42 |
proc_table[p].status = EDFACT_READY; |
} |
static void EDFACT_private_extract(LEVEL l, PID p) |
static void EDFACT_guest_activate(LEVEL l, PID p) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
/* Insert task in the correct position */ |
iq_timespec_insert(p,&lev->ready); |
proc_table[p].status = EDFACT_READY; |
/* Set the deadline timer */ |
if (!(lev->flag[p] & EDFACT_FLAG_NORAISEEXC)) |
lev->deadline_timer[p] = kern_event_post(iq_query_timespec(p, &lev->ready), |
EDFACT_timer_guest_deadline, |
(void *)p); |
} |
static void EDFACT_guest_insert(LEVEL l, PID p) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
/* Insert task in the correct position */ |
iq_timespec_insert(p,&lev->ready); |
proc_table[p].status = EDFACT_READY; |
} |
static void EDFACT_guest_extract(LEVEL l, PID p) |
{ |
} |
static void EDFACT_guest_endcycle(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void EDFACT_guest_end(LEVEL l, PID p) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
//kern_printf("EDFACT_guest_end: dline timer %d\n",lev->deadline_timer[p]); |
if (proc_table[p].status == EDFACT_READY) |
{ |
453,17 → 571,20 |
/* we remove the deadline timer, because the slice is finished */ |
if (lev->deadline_timer[p] != NIL) { |
// kern_printf("EDFACT_guest_end: dline timer %d\n",lev->deadline_timer[p]); |
kern_event_delete(lev->deadline_timer[p]); |
event_delete(lev->deadline_timer[p]); |
lev->deadline_timer[p] = NIL; |
} |
} |
static void EDFACT_guest_sleep(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
/* Registration functions */ |
/*+ Registration function: |
int flags the init flags ... see EDFACT.h +*/ |
LEVEL EDFACT_register_level(int flags) |
void EDFACT_register_level(int flags) |
{ |
LEVEL l; /* the level that we register */ |
EDFACT_level_des *lev; /* for readableness only */ |
472,33 → 593,56 |
printk("EDFACT_register_level\n"); |
/* request an entry in the level_table */ |
l = level_alloc_descriptor(sizeof(EDFACT_level_des)); |
l = level_alloc_descriptor(); |
lev = (EDFACT_level_des *)level_table[l]; |
printk(" alloco descrittore %d %d\n",l,(int)sizeof(EDFACT_level_des)); |
/* alloc the space needed for the EDFACT_level_des */ |
lev = (EDFACT_level_des *)kern_alloc(sizeof(EDFACT_level_des)); |
printk(" lev=%d\n",(int)lev); |
/* update the level_table with the new entry */ |
level_table[l] = (level_des *)lev; |
/* fill the standard descriptor */ |
lev->l.private_insert = EDFACT_private_insert; |
lev->l.private_extract = EDFACT_private_extract; |
lev->l.private_dispatch = EDFACT_private_dispatch; |
lev->l.private_epilogue = EDFACT_private_epilogue; |
strncpy(lev->l.level_name, EDFACT_LEVELNAME, MAX_LEVELNAME); |
lev->l.level_code = EDFACT_LEVEL_CODE; |
lev->l.level_version = EDFACT_LEVEL_VERSION; |
lev->l.public_scheduler = EDFACT_public_scheduler; |
lev->l.level_accept_task_model = EDFACT_level_accept_task_model; |
lev->l.level_accept_guest_model = EDFACT_level_accept_guest_model; |
lev->l.level_status = EDFACT_level_status; |
lev->l.level_scheduler = EDFACT_level_scheduler; |
if (flags & EDFACT_ENABLE_GUARANTEE) |
lev->l.public_guarantee = EDFACT_public_guarantee; |
lev->l.level_guarantee = EDFACT_level_guarantee; |
else |
lev->l.public_guarantee = NULL; |
lev->l.public_create = EDFACT_public_create; |
lev->l.public_detach = EDFACT_public_detach; |
lev->l.public_end = EDFACT_public_end; |
lev->l.public_dispatch = EDFACT_public_dispatch; |
lev->l.public_epilogue = EDFACT_public_epilogue; |
lev->l.public_activate = EDFACT_public_activate; |
lev->l.public_unblock = EDFACT_public_unblock; |
lev->l.public_block = EDFACT_public_block; |
lev->l.public_message = EDFACT_public_message; |
lev->l.level_guarantee = NULL; |
lev->l.task_create = EDFACT_task_create; |
lev->l.task_detach = EDFACT_task_detach; |
lev->l.task_eligible = EDFACT_task_eligible; |
lev->l.task_dispatch = EDFACT_task_dispatch; |
lev->l.task_epilogue = EDFACT_task_epilogue; |
lev->l.task_activate = EDFACT_task_activate; |
lev->l.task_insert = EDFACT_task_insert; |
lev->l.task_extract = EDFACT_task_extract; |
lev->l.task_endcycle = EDFACT_task_endcycle; |
lev->l.task_end = EDFACT_task_end; |
lev->l.task_sleep = EDFACT_task_sleep; |
lev->l.guest_create = EDFACT_guest_create; |
lev->l.guest_detach = EDFACT_guest_detach; |
lev->l.guest_dispatch = EDFACT_guest_dispatch; |
lev->l.guest_epilogue = EDFACT_guest_epilogue; |
lev->l.guest_activate = EDFACT_guest_activate; |
lev->l.guest_insert = EDFACT_guest_insert; |
lev->l.guest_extract = EDFACT_guest_extract; |
lev->l.guest_endcycle = EDFACT_guest_endcycle; |
lev->l.guest_end = EDFACT_guest_end; |
lev->l.guest_sleep = EDFACT_guest_sleep; |
/* fill the EDFACT descriptor part */ |
for(i=0; i<MAX_PROC; i++) { |
lev->period[i] = 0; |
512,15 → 656,16 |
iq_init(&lev->ready,&freedesc, 0); |
lev->flags = flags & 0x07; |
lev->U = 0; |
return l; |
} |
bandwidth_t EDFACT_usedbandwidth(LEVEL l) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
return lev->U; |
if (lev->l.level_code == EDFACT_LEVEL_CODE && |
lev->l.level_version == EDFACT_LEVEL_VERSION) |
return lev->U; |
else |
return 0; |
} |
int EDFACT_get_dline_miss(PID p) |
527,8 → 672,11 |
{ |
LEVEL l = proc_table[p].task_level; |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
return lev->dline_miss[p]; |
if (lev->l.level_code == EDFACT_LEVEL_CODE && |
lev->l.level_version == EDFACT_LEVEL_VERSION) |
return lev->dline_miss[p]; |
else |
return -1; |
} |
int EDFACT_get_wcet_miss(PID p) |
535,8 → 683,11 |
{ |
LEVEL l = proc_table[p].task_level; |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
return lev->wcet_miss[p]; |
if (lev->l.level_code == EDFACT_LEVEL_CODE && |
lev->l.level_version == EDFACT_LEVEL_VERSION) |
return lev->wcet_miss[p]; |
else |
return -1; |
} |
int EDFACT_get_nact(PID p) |
543,8 → 694,11 |
{ |
LEVEL l = proc_table[p].task_level; |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
return lev->nact[p]; |
if (lev->l.level_code == EDFACT_LEVEL_CODE && |
lev->l.level_version == EDFACT_LEVEL_VERSION) |
return lev->nact[p]; |
else |
return -1; |
} |
int EDFACT_reset_dline_miss(PID p) |
551,9 → 705,14 |
{ |
LEVEL l = proc_table[p].task_level; |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
lev->dline_miss[p] = 0; |
return 0; |
if (lev->l.level_code == EDFACT_LEVEL_CODE && |
lev->l.level_version == EDFACT_LEVEL_VERSION) |
{ |
lev->dline_miss[p] = 0; |
return 0; |
} |
else |
return -1; |
} |
int EDFACT_reset_wcet_miss(PID p) |
560,8 → 719,13 |
{ |
LEVEL l = proc_table[p].task_level; |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
lev->wcet_miss[p] = 0; |
return 0; |
if (lev->l.level_code == EDFACT_LEVEL_CODE && |
lev->l.level_version == EDFACT_LEVEL_VERSION) |
{ |
lev->wcet_miss[p] = 0; |
return 0; |
} |
else |
return -1; |
} |
/demos/trunk/auto/auto.c |
---|
21,11 → 21,11 |
/** |
------------ |
CVS : $Id: auto.c,v 1.2 2003-01-07 17:10:15 pj Exp $ |
CVS : $Id: auto.c,v 1.1.1.1 2002-09-02 09:37:42 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2003-01-07 17:10:15 $ |
Revision: $Revision: 1.1.1.1 $ |
Last update: $Date: 2002-09-02 09:37:42 $ |
------------ |
**/ |
324,6 → 324,9 |
sys_end(); |
} |
/* Set the exception handler */ |
set_exchandler_grx(); |
/* Set the closing function */ |
sys_atrunlevel(byebye, NULL, RUNLEVEL_BEFORE_EXIT); |
/demos/trunk/auto/edfact.h |
---|
20,11 → 20,11 |
/** |
------------ |
CVS : $Id: edfact.h,v 1.2 2003-01-07 17:10:15 pj Exp $ |
CVS : $Id: edfact.h,v 1.1.1.1 2002-09-02 09:37:42 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2003-01-07 17:10:15 $ |
Revision: $Revision: 1.1.1.1 $ |
Last update: $Date: 2002-09-02 09:37:42 $ |
------------ |
This file contains the server EDFACT (EDF with pending activations) |
103,6 → 103,7 |
#include <kernel/config.h> |
#include <sys/types.h> |
#include <kernel/types.h> |
#include <modules/codes.h> |
131,10 → 132,8 |
/*+ Registration function: |
int flags Options to be used in this level instance... |
returns the level number at which the module has been registered. |
+*/ |
LEVEL EDFACT_register_level(int flags); |
void EDFACT_register_level(int flags); |
/*+ Returns the used bandwidth of a level +*/ |
bandwidth_t EDFACT_usedbandwidth(LEVEL l); |
/demos/trunk/bca/esplo.c |
---|
18,7 → 18,7 |
* http://shark.sssup.it |
*/ |
/* CVS : $Id: esplo.c,v 1.3 2003-01-07 17:10:16 pj Exp $ */ |
/* CVS : $Id: esplo.c,v 1.2 2002-11-11 08:15:13 pj Exp $ */ |
/* |
* Copyright (C) 2000 Fabio Calabrese <fabiocalabrese77@yahoo.it> |
44,8 → 44,6 |
//* included by: bca.c * |
//************************ |
#include <time.h> |
PID crea_soft_esplo(int index) |
{ |
SOFT_TASK_MODEL m; |
/demos/trunk/bca/bca.c |
---|
18,7 → 18,7 |
* http://shark.sssup.it |
*/ |
/* CVS : $Id: bca.c,v 1.4 2003-01-07 17:10:16 pj Exp $ */ |
/* CVS : $Id: bca.c,v 1.3 2002-11-11 08:15:13 pj Exp $ */ |
/* |
* Copyright (C) 2000 Fabio Calabrese <fabiocalabrese77@yahoo.it> |
130,7 → 130,7 |
/* Default action for an kern exception is */ |
kern_cli(); |
kern_gettime(&t), |
ll_gettime(TIME_EXACT, &t), |
kern_printf("\nS.Ha.R.K. Exception raised!!!" |
"\nTime (s:ns) :%ld:%ld" |
"\nException number:%d" |
191,6 → 191,8 |
k.ascii = '4'; |
keyb_hook(k,decrementa_cannoni_fun); |
set_exchandler_grx(); |
sys_atrunlevel(my_close, NULL, RUNLEVEL_BEFORE_EXIT); |
FAB_grx_open(800,600); |
/demos/trunk/bca/fab_lib.c |
---|
18,7 → 18,7 |
* http://shark.sssup.it |
*/ |
/* CVS : $Id: fab_lib.c,v 1.3 2003-01-07 17:10:16 pj Exp $ */ |
/* CVS : $Id: fab_lib.c,v 1.2 2002-10-01 10:33:51 pj Exp $ */ |
/* |
* Copyright (C) 2000 Fabio Calabrese <fabiocalabrese77@yahoo.it> |
89,14 → 89,13 |
// *** Corpo delle funzioni in FAB_show.h *** // |
void FAB_show_sched_modules() |
{ //int i; |
{ int i; |
FAB_print("MODULI DI SCHEDULAZIONE",NULL); |
kern_printf("\n (livello) (nome)"); |
kern_printf("Names non more available!"); |
//for (i=0; i<sched_levels; i++) |
// {kern_printf("\n %-9d %s",i,(level_table[i])->level_name); |
// } |
for (i=0; i<sched_levels; i++) |
{kern_printf("\n %-9d %s",i,(level_table[i])->level_name); |
} |
FAB_newline(); |
} |
/demos/trunk/eli/eli.c |
---|
18,11 → 18,11 |
/** |
------------ |
CVS : $Id: eli.c,v 1.3 2003-01-07 17:10:16 pj Exp $ |
CVS : $Id: eli.c,v 1.2 2002-11-11 08:18:26 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.3 $ |
Last update: $Date: 2003-01-07 17:10:16 $ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2002-11-11 08:18:26 $ |
------------ |
This file is similar to the configuration of Hartik 3.3.1 |
697,6 → 697,8 |
// Sezione esecutiva del main ## |
//#################################### |
set_exchandler_grx(); |
// Inizializzazione dei parametri hartik |
sem_init(&mutex,0,1); |
sem_init(&pu,0,1); |
/demos/trunk/fsdemo/xread.c |
---|
18,7 → 18,6 |
#include <stdio.h> |
#include <stdlib.h> |
#include <unistd.h> |
#include <time.h> |
#include <assert.h> |
/demos/trunk/first/cbsstar.c |
---|
20,11 → 20,11 |
/* |
------------ |
CVS : $Id: cbsstar.c,v 1.4 2003-01-07 17:10:16 pj Exp $ |
CVS : $Id: cbsstar.c,v 1.3 2002-11-11 08:17:59 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.4 $ |
Last update: $Date: 2003-01-07 17:10:16 $ |
Revision: $Revision: 1.3 $ |
Last update: $Date: 2002-11-11 08:17:59 $ |
------------ |
Read CBSSTAR.h for general details. |
77,7 → 77,7 |
//#define CBSSTAR_DEBUG |
#ifdef CBSSTAR_DEBUG |
#ifdef CBSSTAR_DEBUF |
static __inline__ void fake_printf(char *fmt, ...) {} |
206,7 → 206,10 |
job_task_default_model(job, b->dline); |
job_task_def_noexc(job); |
level_table[ lev->scheduling_level ]-> |
private_insert(lev->scheduling_level, p, (TASK_MODEL *)&job); |
guest_create(lev->scheduling_level, p, (TASK_MODEL *)&job); |
level_table[ lev->scheduling_level ]-> |
guest_activate(lev->scheduling_level, p); |
} |
225,8 → 228,35 |
} |
static int CBSSTAR_level_accept_task_model(LEVEL l, TASK_MODEL *m) |
{ |
return -1; |
} |
static int CBSSTAR_level_accept_guest_model(LEVEL l, TASK_MODEL *m) |
{ |
if (m->pclass == BUDGET_PCLASS || m->pclass == (BUDGET_PCLASS | l)) { |
return 0; |
} |
return -1; |
} |
static void CBSSTAR_level_status(LEVEL l) |
{ |
kern_printf("CBSSTAR level_status (level %d)\n", l); |
} |
static PID CBSSTAR_level_scheduler(LEVEL l) |
{ |
/* the CBSSTAR don't schedule anything... |
it's an EDF level or similar that do it! */ |
return NIL; |
} |
/* The on-line guarantee is enabled only if the appropriate flag is set... */ |
static int CBSSTAR_public_guarantee(LEVEL l, bandwidth_t *freebandwidth) |
static int CBSSTAR_level_guarantee(LEVEL l, bandwidth_t *freebandwidth) |
{ |
CBSSTAR_level_des *lev = (CBSSTAR_level_des *)(level_table[l]); |
242,8 → 272,19 |
return 0; |
} |
static int CBSSTAR_private_eligible(LEVEL l, PID p) |
static int CBSSTAR_task_create(LEVEL l, PID p, TASK_MODEL *m) |
{ |
kern_raise(XINVALID_TASK,exec_shadow); |
return 0; /* OK, also if the task cannot be guaranteed... */ |
} |
static void CBSSTAR_task_detach(LEVEL l, PID p) |
{ kern_raise(XINVALID_TASK,exec_shadow); } |
static int CBSSTAR_task_eligible(LEVEL l, PID p) |
{ |
/* this function is never called! ... maybe I should remove it? */ |
#if 0 |
CBSSTAR_level_des *lev = (CBSSTAR_level_des *)(level_table[l]); |
struct budget_struct *b = &lev->b[lev->tb[p]]; |
JOB_TASK_MODEL job; |
262,7 → 303,7 |
if ( TIMESPEC_A_LT_B(&b->dline, &schedule_time) ) { |
/* we kill the current activation */ |
level_table[ lev->scheduling_level ]-> |
private_extract(lev->scheduling_level, p); |
guest_end(lev->scheduling_level, p); |
/* we modify the deadline ... */ |
TIMESPEC_ASSIGN(&b->dline, &schedule_time); |
281,7 → 322,9 |
job_task_default_model(job, b->dline); |
job_task_def_noexc(job); |
level_table[ lev->scheduling_level ]-> |
private_insert(lev->scheduling_level, p, (TASK_MODEL *)&job); |
guest_create(lev->scheduling_level, p, (TASK_MODEL *)&job); |
level_table[ lev->scheduling_level ]-> |
guest_activate(lev->scheduling_level, p); |
return -1; |
} |
289,10 → 332,35 |
cbsstar_printf(")"); |
#endif |
#endif |
return 0; |
} |
static void CBSSTAR_private_insert(LEVEL l, PID p, TASK_MODEL *m) |
static void CBSSTAR_task_dispatch(LEVEL l, PID p, int nostop) |
{ kern_raise(XINVALID_TASK,exec_shadow); } |
static void CBSSTAR_task_epilogue(LEVEL l, PID p) |
{ kern_raise(XINVALID_TASK,exec_shadow); } |
static void CBSSTAR_task_activate(LEVEL l, PID p) |
{ kern_raise(XINVALID_TASK,exec_shadow); } |
static void CBSSTAR_task_insert(LEVEL l, PID p) |
{ kern_raise(XINVALID_TASK,exec_shadow); } |
static void CBSSTAR_task_extract(LEVEL l, PID p) |
{ kern_raise(XINVALID_TASK,exec_shadow); } |
static void CBSSTAR_task_endcycle(LEVEL l, PID p) |
{ kern_raise(XINVALID_TASK,exec_shadow); } |
static void CBSSTAR_task_end(LEVEL l, PID p) |
{ kern_raise(XINVALID_TASK,exec_shadow); } |
static void CBSSTAR_task_sleep(LEVEL l, PID p) |
{ kern_raise(XINVALID_TASK,exec_shadow); } |
static int CBSSTAR_guest_create(LEVEL l, PID p, TASK_MODEL *m) |
{ |
/* A task has been activated for some reason. Basically, the task is |
inserted in the queue if the queue is empty, otherwise the task is |
299,15 → 367,8 |
inserted into the master module, and an oslib event is posted. */ |
CBSSTAR_level_des *lev = (CBSSTAR_level_des *)(level_table[l]); |
BUDGET_TASK_MODEL *budget; |
BUDGET_TASK_MODEL *budget = (BUDGET_TASK_MODEL *)m; |
if (m->pclass != BUDGET_PCLASS || |
(m->level != 0 && m->level != l)) { |
kern_raise(XINVALID_TASK, p); |
return; |
} |
budget = (BUDGET_TASK_MODEL *)m; |
#ifdef CBSSTAR_DEBUG |
cbsstar_printf("(C:gcr %d b%d", p, budget->b); |
#endif |
318,7 → 379,7 |
/* This is the first task in the budget, |
the task have to be inserted into the master module */ |
struct timespec t; |
kern_gettime(&t); |
ll_gettime(TIME_EXACT, &t); |
CBSSTAR_activation(lev,p,&t); |
} else { |
/* The budget is not empty, another task is already into the |
333,9 → 394,11 |
#ifdef CBSSTAR_DEBUG |
cbsstar_printf(")"); |
#endif |
return 0; |
} |
static void CBSSTAR_private_extract(LEVEL l, PID p) |
static void CBSSTAR_guest_end(LEVEL l, PID p) |
{ |
CBSSTAR_level_des *lev = (CBSSTAR_level_des *)(level_table[l]); |
353,7 → 416,7 |
if (lev->b[lev->tb[p]].current == p) { |
/* remove the task from the master module */ |
level_table[ lev->scheduling_level ]-> |
private_extract(lev->scheduling_level, p); |
guest_end(lev->scheduling_level, p); |
#ifdef CBSSTAR_DEBUG |
cbsstar_printq(&lev->b[lev->tb[p]].tasks); |
369,7 → 432,7 |
PID n; |
struct timespec t; |
kern_gettime(&t); |
ll_gettime(TIME_EXACT, &t); |
n = iq_getfirst(&lev->b[lev->tb[p]].tasks); |
#ifdef CBSSTAR_DEBUG |
cbsstar_printf("{p%d n%d}",p,n); |
381,7 → 444,7 |
iq_extract(p, &lev->b[lev->tb[p]].tasks); |
} |
static void CBSSTAR_private_dispatch(LEVEL l, PID p, int nostop) |
static void CBSSTAR_guest_dispatch(LEVEL l, PID p, int nostop) |
{ |
CBSSTAR_level_des *lev = (CBSSTAR_level_des *)(level_table[l]); |
struct timespec ty; |
398,7 → 461,7 |
/* ... then, we dispatch it to the master level */ |
level_table[ lev->scheduling_level ]-> |
private_dispatch(lev->scheduling_level,p,nostop); |
guest_dispatch(lev->scheduling_level,p,nostop); |
/* ...and finally, we have to post a capacity event */ |
if (!nostop) { |
408,7 → 471,7 |
} |
} |
static void CBSSTAR_private_epilogue(LEVEL l, PID p) |
static void CBSSTAR_guest_epilogue(LEVEL l, PID p) |
{ |
CBSSTAR_level_des *lev = (CBSSTAR_level_des *)(level_table[l]); |
struct budget_struct *b = &lev->b[lev->tb[p]]; |
424,7 → 487,7 |
/* there is capacity available, maybe it is simply a preemption; |
the task have to return to the ready queue */ |
level_table[ lev->scheduling_level ]-> |
private_epilogue(lev->scheduling_level,p); |
guest_epilogue(lev->scheduling_level,p); |
#ifdef CBSSTAR_DEBUG |
cbsstar_printf2(" *av=%d", b->avail); |
#endif |
435,7 → 498,7 |
/* we kill the current activation */ |
level_table[ lev->scheduling_level ]-> |
private_extract(lev->scheduling_level, p); |
guest_end(lev->scheduling_level, p); |
/* we modify the deadline according to rule 4 ... */ |
/* there is a while because if the wcet is << than the system tick |
457,7 → 520,9 |
job_task_default_model(job, b->dline); |
job_task_def_noexc(job); |
level_table[ lev->scheduling_level ]-> |
private_insert(lev->scheduling_level, p, (TASK_MODEL *)&job); |
guest_create(lev->scheduling_level, p, (TASK_MODEL *)&job); |
level_table[ lev->scheduling_level ]-> |
guest_activate(lev->scheduling_level, p); |
} |
#ifdef CBSSTAR_DEBUG |
cbsstar_printf(")"); |
464,7 → 529,27 |
#endif |
} |
static void CBSSTAR_guest_detach(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void CBSSTAR_guest_activate(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void CBSSTAR_guest_insert(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void CBSSTAR_guest_extract(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void CBSSTAR_guest_endcycle(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void CBSSTAR_guest_sleep(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
/* Registration functions */ |
/*+ Registration function: |
480,21 → 565,56 |
#endif |
/* request an entry in the level_table */ |
l = level_alloc_descriptor(sizeof(CBSSTAR_level_des)); |
l = level_alloc_descriptor(); |
lev = (CBSSTAR_level_des *)level_table[l]; |
#ifdef CBSSTAR_DEBUG |
cbsstar_printf(" alloco descrittore %d %d\n",l,(int)sizeof(CBSSTAR_level_des)); |
#endif |
printk(" lev=%d\n",(int)lev); |
/* alloc the space needed for the CBSSTAR_level_des */ |
lev = (CBSSTAR_level_des *)kern_alloc(sizeof(CBSSTAR_level_des)); |
#ifdef CBSSTAR_DEBUG |
cbsstar_printf(" lev=%d\n",(int)lev); |
#endif |
/* update the level_table with the new entry */ |
level_table[l] = (level_des *)lev; |
/* fill the standard descriptor */ |
lev->l.private_insert = CBSSTAR_private_insert; |
lev->l.private_extract = CBSSTAR_private_extract; |
lev->l.private_eligible = CBSSTAR_private_eligible; |
lev->l.private_dispatch = CBSSTAR_private_dispatch; |
lev->l.private_epilogue = CBSSTAR_private_epilogue; |
strncpy(lev->l.level_name, CBSSTAR_LEVELNAME, MAX_LEVELNAME); |
lev->l.level_code = CBSSTAR_LEVEL_CODE; |
lev->l.level_version = CBSSTAR_LEVEL_VERSION; |
lev->l.public_guarantee = CBSSTAR_public_guarantee; |
lev->l.level_accept_task_model = CBSSTAR_level_accept_task_model; |
lev->l.level_accept_guest_model = CBSSTAR_level_accept_guest_model; |
lev->l.level_status = CBSSTAR_level_status; |
lev->l.level_scheduler = CBSSTAR_level_scheduler; |
lev->l.level_guarantee = CBSSTAR_level_guarantee; |
lev->l.task_create = CBSSTAR_task_create; |
lev->l.task_detach = CBSSTAR_task_detach; |
lev->l.task_eligible = CBSSTAR_task_eligible; |
lev->l.task_dispatch = CBSSTAR_task_dispatch; |
lev->l.task_epilogue = CBSSTAR_task_epilogue; |
lev->l.task_activate = CBSSTAR_task_activate; |
lev->l.task_insert = CBSSTAR_task_insert; |
lev->l.task_extract = CBSSTAR_task_extract; |
lev->l.task_endcycle = CBSSTAR_task_endcycle; |
lev->l.task_end = CBSSTAR_task_end; |
lev->l.task_sleep = CBSSTAR_task_sleep; |
lev->l.guest_create = CBSSTAR_guest_create; |
lev->l.guest_detach = CBSSTAR_guest_detach; |
lev->l.guest_dispatch = CBSSTAR_guest_dispatch; |
lev->l.guest_epilogue = CBSSTAR_guest_epilogue; |
lev->l.guest_activate = CBSSTAR_guest_activate; |
lev->l.guest_insert = CBSSTAR_guest_insert; |
lev->l.guest_extract = CBSSTAR_guest_extract; |
lev->l.guest_endcycle = CBSSTAR_guest_endcycle; |
lev->l.guest_end = CBSSTAR_guest_end; |
lev->l.guest_sleep = CBSSTAR_guest_sleep; |
/* fill the CBSSTAR descriptor part */ |
lev->b = (struct budget_struct *)kern_alloc(sizeof(struct budget_struct)*n); |
529,25 → 649,30 |
cbsstar_printf("(C:sbud)"); |
#endif |
if (lev->freebudgets != lev->n) { |
bandwidth_t b; |
b = (MAX_BANDWIDTH / T) * Q; |
/* really update lev->U, checking an overflow... */ |
if (Q< T && MAX_BANDWIDTH - lev->U > b) { |
int r = lev->freebudgets; // the return value |
if (lev->l.level_code == CBSSTAR_LEVEL_CODE && |
lev->l.level_version == CBSSTAR_LEVEL_VERSION) { |
if (lev->freebudgets != lev->n) { |
bandwidth_t b; |
b = (MAX_BANDWIDTH / T) * Q; |
lev->U += b; |
lev->freebudgets++; |
lev->b[r].Q = Q; |
lev->b[r].T = T; |
return r; |
/* really update lev->U, checking an overflow... */ |
if (Q< T && MAX_BANDWIDTH - lev->U > b) { |
int r = lev->freebudgets; // the return value |
lev->U += b; |
lev->freebudgets++; |
lev->b[r].Q = Q; |
lev->b[r].T = T; |
return r; |
} |
else |
return -2; |
} |
else |
return -2; |
return -1; |
} |
else |
return -1; |
return -3; |
} |
/demos/trunk/first/rmstar.c |
---|
18,11 → 18,11 |
/** |
------------ |
CVS : $Id: rmstar.c,v 1.4 2003-01-07 17:10:17 pj Exp $ |
CVS : $Id: rmstar.c,v 1.3 2002-11-11 08:17:59 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.4 $ |
Last update: $Date: 2003-01-07 17:10:17 $ |
Revision: $Revision: 1.3 $ |
Last update: $Date: 2002-11-11 08:17:59 $ |
------------ |
**/ |
66,7 → 66,7 |
//#define RMSTAR_DEBUG |
#ifdef RMSTAR_DEBUG |
#ifdef RMSTAR_DEBUF |
static __inline__ fake_printf(char *fmt, ...) {} |
131,7 → 131,7 |
if ((first = iq_query_first(&lev->ready)) != lev->activated) { |
if (lev->activated != NIL) |
level_table[ lev->scheduling_level ]-> |
private_extract(lev->scheduling_level, lev->activated); |
guest_end(lev->scheduling_level, lev->activated); |
lev->activated = first; |
140,7 → 140,7 |
budget_task_default_model(b, lev->budget); |
level_table[ lev->scheduling_level ]-> |
private_insert(lev->scheduling_level, first, (TASK_MODEL *)&b); |
guest_create(lev->scheduling_level, first, (TASK_MODEL *)&b); |
} |
} |
} |
147,17 → 147,19 |
static void RMSTAR_timer_deadline(void *par); |
static void RMSTAR_internal_activate(RMSTAR_level_des *lev, PID p, |
struct timespec *t) |
static void RMSTAR_internal_activate(RMSTAR_level_des *lev, PID p) |
{ |
struct timespec temp; |
#ifdef RMSTAR_DEBUG |
rmstar_printf("(E:iact)"); |
#endif |
ADDUSEC2TIMESPEC(lev->period[p], t); |
TIMESPEC_ASSIGN(&temp, &proc_table[p].request_time); |
ADDUSEC2TIMESPEC(lev->period[p], &temp); |
*iq_query_timespec(p, &lev->ready) = *t; |
lev->deadline_timespec[p] = *t; |
*iq_query_timespec(p, &lev->ready) = temp; |
lev->deadline_timespec[p] = temp; |
/* Insert task in the correct position */ |
proc_table[p].status = RMSTAR_READY; |
170,6 → 172,18 |
RMSTAR_check_preemption(lev); |
} |
static char *RMSTAR_status_to_a(WORD status) |
{ |
if (status < MODULE_STATUS_BASE) |
return status_to_a(status); |
switch (status) { |
case RMSTAR_READY : return "RMSTAR_Ready"; |
case RMSTAR_IDLE : return "RMSTAR_Idle"; |
default : return "RMSTAR_Unknown"; |
} |
} |
static void RMSTAR_timer_deadline(void *par) |
{ |
PID p = (PID) par; |
187,8 → 201,10 |
// rmstar_printf2("I%d",p); |
#endif |
/* set the request time */ |
RMSTAR_internal_activate(lev,p,iq_query_timespec(p, &lev->ready)); |
proc_table[p].request_time = *iq_query_timespec(p, &lev->ready); |
RMSTAR_internal_activate(lev,p); |
event_need_reschedule(); |
break; |
227,20 → 243,104 |
kern_raise(XDEADLINE_MISS,p); |
} |
static int RMSTAR_public_create(LEVEL l, PID p, TASK_MODEL *m) |
static int RMSTAR_level_accept_task_model(LEVEL l, TASK_MODEL *m) |
{ |
#ifdef RMSTAR_DEBUG |
rmstar_printf("(E:lacct)"); |
#endif |
if (m->pclass == HARD_PCLASS || m->pclass == (HARD_PCLASS | l)) { |
HARD_TASK_MODEL *h = (HARD_TASK_MODEL *)m; |
if (h->wcet && h->mit && h->periodicity == PERIODIC) |
return 0; |
} |
return -1; |
} |
static int RMSTAR_level_accept_guest_model(LEVEL l, TASK_MODEL *m) |
{ |
#ifdef RMSTAR_DEBUG |
rmstar_printf("(E:laccg)"); |
#endif |
if (m->pclass == JOB_PCLASS || m->pclass == (JOB_PCLASS | l)) |
return 0; |
else |
return -1; |
} |
static char *onoff(int i) |
{ |
if (i) |
return "On "; |
else |
return "Off"; |
} |
static void RMSTAR_level_status(LEVEL l) |
{ |
RMSTAR_level_des *lev = (RMSTAR_level_des *)(level_table[l]); |
PID p = iq_query_first(&lev->ready); |
struct timespec temp; |
kern_printf("Budget number : %u\n", lev->budget); |
kern_printf("Master level : %u\n", lev->scheduling_level); |
kern_printf("Active PID : %u\n", lev->activated); |
while (p != NIL) { |
if ((proc_table[p].pclass) == JOB_PCLASS) |
kern_printf("Pid: %2d (GUEST)\n", p); |
else { |
temp = *iq_query_timespec(p, &lev->ready); |
kern_printf("Pid: %2d Name: %10s %s: %9ld Dline: %9ld.%6ld Stat: %s\n", |
p, |
proc_table[p].name, |
"Period ", |
lev->period[p], |
temp.tv_sec, |
temp.tv_nsec/1000, |
RMSTAR_status_to_a(proc_table[p].status)); |
p = iq_query_next(p, &lev->ready); |
} |
} |
for (p=0; p<MAX_PROC; p++) |
if (proc_table[p].task_level == l |
&& proc_table[p].status != RMSTAR_READY |
&& proc_table[p].status != FREE ) { |
temp = *iq_query_timespec(p, &lev->ready); |
kern_printf("Pid: %2d Name: %10s %s: %9ld Dline: %9ld.%6ld Stat: %s\n", |
p, |
proc_table[p].name, |
"Period ", |
lev->period[p], |
temp.tv_sec, |
temp.tv_nsec/1000, |
RMSTAR_status_to_a(proc_table[p].status)); |
} |
} |
/* The scheduler only gets the first task in the queue */ |
static PID RMSTAR_level_scheduler(LEVEL l) |
{ |
//RMSTAR_level_des *lev = (RMSTAR_level_des *)(level_table[l]); |
return NIL; |
} |
static int RMSTAR_task_create(LEVEL l, PID p, TASK_MODEL *m) |
{ |
RMSTAR_level_des *lev = (RMSTAR_level_des *)(level_table[l]); |
/* if the RMSTAR_task_create is called, then the pclass must be a |
valid pclass. */ |
HARD_TASK_MODEL *h; |
HARD_TASK_MODEL *h = (HARD_TASK_MODEL *)m; |
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; |
/* now we know that m is a valid model */ |
#ifdef RMSTAR_DEBUG |
rmstar_printf("(E:tcr)"); |
#endif |
262,8 → 362,24 |
return 0; /* OK, also if the task cannot be guaranteed... */ |
} |
static void RMSTAR_public_dispatch(LEVEL l, PID p, int nostop) |
static void RMSTAR_task_detach(LEVEL l, PID p) |
{ |
#ifdef RMSTAR_DEBUG |
rmstar_printf2("(E:tdt)"); |
#endif |
} |
static int RMSTAR_task_eligible(LEVEL l, PID p) |
{ |
#ifdef RMSTAR_DEBUG |
rmstar_printf2("(E:eli)"); |
#endif |
return 0; /* if the task p is chosen, it is always eligible */ |
} |
static void RMSTAR_task_dispatch(LEVEL l, PID p, int nostop) |
{ |
RMSTAR_level_des *lev = (RMSTAR_level_des *)(level_table[l]); |
#ifdef RMSTAR_DEBUG |
275,10 → 391,10 |
#endif |
level_table[ lev->scheduling_level ]-> |
private_dispatch(lev->scheduling_level,p,nostop); |
guest_dispatch(lev->scheduling_level,p,nostop); |
} |
static void RMSTAR_public_epilogue(LEVEL l, PID p) |
static void RMSTAR_task_epilogue(LEVEL l, PID p) |
{ |
RMSTAR_level_des *lev = (RMSTAR_level_des *)(level_table[l]); |
300,15 → 416,14 |
#endif |
level_table[ lev->scheduling_level ]-> |
private_epilogue(lev->scheduling_level,p); |
guest_epilogue(lev->scheduling_level,p); |
proc_table[p].status = RMSTAR_READY; |
} |
static void RMSTAR_public_activate(LEVEL l, PID p) |
static void RMSTAR_task_activate(LEVEL l, PID p) |
{ |
RMSTAR_level_des *lev = (RMSTAR_level_des *)(level_table[l]); |
struct timespec t; |
#ifdef RMSTAR_DEBUG |
rmstar_printf("(E:act)"); |
322,9 → 437,9 |
return; |
} |
kern_gettime(&t); |
ll_gettime(TIME_EXACT, &proc_table[p].request_time); |
RMSTAR_internal_activate(lev,p, &t); |
RMSTAR_internal_activate(lev,p); |
/* Set the deadline timer */ |
lev->deadline_timer[p] = kern_event_post(&lev->deadline_timespec[p], |
333,7 → 448,7 |
} |
static void RMSTAR_public_unblock(LEVEL l, PID p) |
static void RMSTAR_task_insert(LEVEL l, PID p) |
{ |
RMSTAR_level_des *lev = (RMSTAR_level_des *)(level_table[l]); |
349,7 → 464,7 |
RMSTAR_check_preemption(lev); |
} |
static void RMSTAR_public_block(LEVEL l, PID p) |
static void RMSTAR_task_extract(LEVEL l, PID p) |
{ |
RMSTAR_level_des *lev = (RMSTAR_level_des *)(level_table[l]); |
365,7 → 480,7 |
RMSTAR_check_preemption(lev); |
} |
static int RMSTAR_public_message(LEVEL l, PID p, void *m) |
static void RMSTAR_task_endcycle(LEVEL l, PID p) |
{ |
RMSTAR_level_des *lev = (RMSTAR_level_des *)(level_table[l]); |
struct timespec temp; |
377,7 → 492,8 |
/* 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; |
guest_end(lev->scheduling_level,p); |
lev->activated = NIL; |
iq_extract(p,&lev->ready); |
393,9 → 509,9 |
lev->nact[p]--; |
/* see also RMSTAR_timer_deadline */ |
kern_gettime(&temp); |
ll_gettime(TIME_EXACT, &proc_table[p].request_time); |
RMSTAR_internal_activate(lev,p,&temp); |
RMSTAR_internal_activate(lev,p); |
/* check if the deadline has already expired */ |
temp = *iq_query_timespec(p, &lev->ready); |
402,7 → 518,7 |
if (TIMESPEC_A_LT_B(&temp, &schedule_time)) { |
/* count the deadline miss */ |
lev->dline_miss[p]++; |
kern_event_delete(lev->deadline_timer[p]); |
event_delete(lev->deadline_timer[p]); |
} |
} |
418,19 → 534,14 |
RMSTAR_check_preemption(lev); |
/* when the deadline timer fire, it recognize the situation and set |
correctly all the stuffs (like reactivation, etc... ) */ |
correctly all the stuffs (like reactivation, request_time, etc... ) */ |
} |
#ifdef RMSTAR_DEBUG |
rmstar_printf(")"); |
#endif |
jet_update_endcycle(); /* Update the Jet data... */ |
trc_logevent(TRC_ENDCYCLE,&exec_shadow); /* tracer stuff */ |
return 0; |
} |
static void RMSTAR_public_end(LEVEL l, PID p) |
static void RMSTAR_task_end(LEVEL l, PID p) |
{ |
RMSTAR_level_des *lev = (RMSTAR_level_des *)(level_table[l]); |
446,7 → 557,7 |
iq_insertfirst(p,&freedesc); |
if (lev->deadline_timer[p] != -1) { |
kern_event_delete(lev->deadline_timer[p]); |
event_delete(lev->deadline_timer[p]); |
} |
/* and finally, a preemption check! (it will also call guest_end) */ |
453,23 → 564,22 |
RMSTAR_check_preemption(lev); |
} |
static void RMSTAR_task_sleep(LEVEL l, PID p) |
{ kern_raise(XINVALID_TASK,exec_shadow); } |
/* Guest Functions |
These functions manages a JOB_TASK_MODEL, that is used to put |
a guest task in the RMSTAR ready queue. */ |
static void RMSTAR_private_insert(LEVEL l, PID p, TASK_MODEL *m) |
static int RMSTAR_guest_create(LEVEL l, PID p, TASK_MODEL *m) |
{ |
RMSTAR_level_des *lev = (RMSTAR_level_des *)(level_table[l]); |
JOB_TASK_MODEL *job; |
JOB_TASK_MODEL *job = (JOB_TASK_MODEL *)m; |
if (m->pclass != JOB_PCLASS || (m->level != 0 && m->level != l) ) { |
kern_raise(XINVALID_TASK, p); |
return; |
} |
/* if the RMSTAR_guest_create is called, then the pclass must be a |
valid pclass. */ |
job = (JOB_TASK_MODEL *)m; |
*iq_query_timespec(p, &lev->ready) = job->deadline; |
lev->deadline_timer[p] = -1; |
479,12 → 589,8 |
if (job->noraiseexc) |
lev->flag[p] = RMSTAR_FLAG_NORAISEEXC; |
else { |
else |
lev->flag[p] = 0; |
lev->deadline_timer[p] = kern_event_post(iq_query_timespec(p, &lev->ready), |
RMSTAR_timer_guest_deadline, |
(void *)p); |
} |
lev->period[p] = job->period; |
*iq_query_priority(p, &lev->ready) = job->period; |
492,6 → 598,39 |
/* there is no bandwidth guarantee at this level, it is performed |
by the level that inserts guest tasks... */ |
return 0; /* OK, also if the task cannot be guaranteed... */ |
} |
static void RMSTAR_guest_detach(LEVEL l, PID p) |
{ |
/* the RMSTAR level doesn't introduce any dinamic allocated new field. |
No guarantee is performed on guest tasks... so we don't have to reset |
the NO_GUARANTEE FIELD */ |
} |
static void RMSTAR_guest_dispatch(LEVEL l, PID p, int nostop) |
{ |
RMSTAR_level_des *lev = (RMSTAR_level_des *)(level_table[l]); |
level_table[ lev->scheduling_level ]-> |
guest_dispatch(lev->scheduling_level,p,nostop); |
} |
static void RMSTAR_guest_epilogue(LEVEL l, PID p) |
{ |
RMSTAR_level_des *lev = (RMSTAR_level_des *)(level_table[l]); |
/* the task has been preempted. it returns into the ready queue... */ |
level_table[ lev->scheduling_level ]-> |
guest_epilogue(lev->scheduling_level,p); |
proc_table[p].status = RMSTAR_READY; |
} |
static void RMSTAR_guest_activate(LEVEL l, PID p) |
{ |
RMSTAR_level_des *lev = (RMSTAR_level_des *)(level_table[l]); |
/* Insert task in the correct position */ |
iq_priority_insert(p,&lev->ready); |
proc_table[p].status = RMSTAR_READY; |
498,28 → 637,40 |
/* check for preemption */ |
RMSTAR_check_preemption(lev); |
/* Set the deadline timer */ |
if (!(lev->flag[p] & RMSTAR_FLAG_NORAISEEXC)) |
lev->deadline_timer[p] = kern_event_post(iq_query_timespec(p, &lev->ready), |
RMSTAR_timer_guest_deadline, |
(void *)p); |
} |
static void RMSTAR_private_dispatch(LEVEL l, PID p, int nostop) |
static void RMSTAR_guest_insert(LEVEL l, PID p) |
{ |
RMSTAR_level_des *lev = (RMSTAR_level_des *)(level_table[l]); |
level_table[ lev->scheduling_level ]-> |
private_dispatch(lev->scheduling_level,p,nostop); |
/* Insert task in the correct position */ |
iq_priority_insert(p,&lev->ready); |
proc_table[p].status = RMSTAR_READY; |
/* and check for preemption! */ |
RMSTAR_check_preemption(lev); |
} |
static void RMSTAR_private_epilogue(LEVEL l, PID p) |
static void RMSTAR_guest_extract(LEVEL l, PID p) |
{ |
RMSTAR_level_des *lev = (RMSTAR_level_des *)(level_table[l]); |
/* the task has been preempted. it returns into the ready queue... */ |
level_table[ lev->scheduling_level ]-> |
private_epilogue(lev->scheduling_level,p); |
/* 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); |
proc_table[p].status = RMSTAR_READY; |
/* and finally, a preemption check! (it will also call guest_end() */ |
RMSTAR_check_preemption(lev); |
} |
static void RMSTAR_private_extract(LEVEL l, PID p) |
static void RMSTAR_guest_end(LEVEL l, PID p) |
{ |
RMSTAR_level_des *lev = (RMSTAR_level_des *)(level_table[l]); |
534,7 → 685,7 |
#ifdef RMSTAR_DEBUG |
// kern_printf("RMSTAR_guest_end: dline timer %d\n",lev->deadline_timer[p]); |
#endif |
kern_event_delete(lev->deadline_timer[p]); |
event_delete(lev->deadline_timer[p]); |
lev->deadline_timer[p] = NIL; |
} |
542,6 → 693,12 |
RMSTAR_check_preemption(lev); |
} |
static void RMSTAR_guest_endcycle(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void RMSTAR_guest_sleep(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
/* Registration functions */ |
/* Registration function: |
557,28 → 714,55 |
#endif |
/* request an entry in the level_table */ |
l = level_alloc_descriptor(sizeof(RMSTAR_level_des)); |
l = level_alloc_descriptor(); |
lev = (RMSTAR_level_des *)level_table[l]; |
#ifdef RMSTAR_DEBUG |
printk(" alloco descrittore %d %d\n",l,(int)sizeof(RMSTAR_level_des)); |
#endif |
/* alloc the space needed for the RMSTAR_level_des */ |
lev = (RMSTAR_level_des *)kern_alloc(sizeof(RMSTAR_level_des)); |
#ifdef RMSTAR_DEBUG |
printk(" lev=%d\n",(int)lev); |
#endif |
/* update the level_table with the new entry */ |
level_table[l] = (level_des *)lev; |
/* fill the standard descriptor */ |
lev->l.private_insert = RMSTAR_private_insert; |
lev->l.private_extract = RMSTAR_private_extract; |
lev->l.private_dispatch = RMSTAR_private_dispatch; |
lev->l.private_epilogue = RMSTAR_private_epilogue; |
strncpy(lev->l.level_name, RMSTAR_LEVELNAME, MAX_LEVELNAME); |
lev->l.level_code = RMSTAR_LEVEL_CODE; |
lev->l.level_version = RMSTAR_LEVEL_VERSION; |
lev->l.public_guarantee = NULL; |
lev->l.public_create = RMSTAR_public_create; |
lev->l.public_end = RMSTAR_public_end; |
lev->l.public_dispatch = RMSTAR_public_dispatch; |
lev->l.public_epilogue = RMSTAR_public_epilogue; |
lev->l.public_activate = RMSTAR_public_activate; |
lev->l.public_unblock = RMSTAR_public_unblock; |
lev->l.public_block = RMSTAR_public_block; |
lev->l.public_message = RMSTAR_public_message; |
lev->l.level_accept_task_model = RMSTAR_level_accept_task_model; |
lev->l.level_accept_guest_model = RMSTAR_level_accept_guest_model; |
lev->l.level_status = RMSTAR_level_status; |
lev->l.level_scheduler = RMSTAR_level_scheduler; |
lev->l.level_guarantee = NULL; |
lev->l.task_create = RMSTAR_task_create; |
lev->l.task_detach = RMSTAR_task_detach; |
lev->l.task_eligible = RMSTAR_task_eligible; |
lev->l.task_dispatch = RMSTAR_task_dispatch; |
lev->l.task_epilogue = RMSTAR_task_epilogue; |
lev->l.task_activate = RMSTAR_task_activate; |
lev->l.task_insert = RMSTAR_task_insert; |
lev->l.task_extract = RMSTAR_task_extract; |
lev->l.task_endcycle = RMSTAR_task_endcycle; |
lev->l.task_end = RMSTAR_task_end; |
lev->l.task_sleep = RMSTAR_task_sleep; |
lev->l.guest_create = RMSTAR_guest_create; |
lev->l.guest_detach = RMSTAR_guest_detach; |
lev->l.guest_dispatch = RMSTAR_guest_dispatch; |
lev->l.guest_epilogue = RMSTAR_guest_epilogue; |
lev->l.guest_activate = RMSTAR_guest_activate; |
lev->l.guest_insert = RMSTAR_guest_insert; |
lev->l.guest_extract = RMSTAR_guest_extract; |
lev->l.guest_endcycle = RMSTAR_guest_endcycle; |
lev->l.guest_end = RMSTAR_guest_end; |
lev->l.guest_sleep = RMSTAR_guest_sleep; |
/* fill the RMSTAR descriptor part */ |
for(i=0; i<MAX_PROC; i++) { |
lev->period[i] = 0; |
602,8 → 786,11 |
{ |
LEVEL l = proc_table[p].task_level; |
RMSTAR_level_des *lev = (RMSTAR_level_des *)(level_table[l]); |
return lev->dline_miss[p]; |
if (lev->l.level_code == RMSTAR_LEVEL_CODE && |
lev->l.level_version == RMSTAR_LEVEL_VERSION) |
return lev->dline_miss[p]; |
else |
return -1; |
} |
int RMSTAR_get_wcet_miss(PID p) |
610,8 → 797,11 |
{ |
LEVEL l = proc_table[p].task_level; |
RMSTAR_level_des *lev = (RMSTAR_level_des *)(level_table[l]); |
return lev->wcet_miss[p]; |
if (lev->l.level_code == RMSTAR_LEVEL_CODE && |
lev->l.level_version == RMSTAR_LEVEL_VERSION) |
return lev->wcet_miss[p]; |
else |
return -1; |
} |
int RMSTAR_get_nact(PID p) |
618,8 → 808,11 |
{ |
LEVEL l = proc_table[p].task_level; |
RMSTAR_level_des *lev = (RMSTAR_level_des *)(level_table[l]); |
return lev->nact[p]; |
if (lev->l.level_code == RMSTAR_LEVEL_CODE && |
lev->l.level_version == RMSTAR_LEVEL_VERSION) |
return lev->nact[p]; |
else |
return -1; |
} |
int RMSTAR_reset_dline_miss(PID p) |
626,9 → 819,14 |
{ |
LEVEL l = proc_table[p].task_level; |
RMSTAR_level_des *lev = (RMSTAR_level_des *)(level_table[l]); |
lev->dline_miss[p] = 0; |
return 0; |
if (lev->l.level_code == RMSTAR_LEVEL_CODE && |
lev->l.level_version == RMSTAR_LEVEL_VERSION) |
{ |
lev->dline_miss[p] = 0; |
return 0; |
} |
else |
return -1; |
} |
int RMSTAR_reset_wcet_miss(PID p) |
635,8 → 833,13 |
{ |
LEVEL l = proc_table[p].task_level; |
RMSTAR_level_des *lev = (RMSTAR_level_des *)(level_table[l]); |
lev->wcet_miss[p] = 0; |
return 0; |
if (lev->l.level_code == RMSTAR_LEVEL_CODE && |
lev->l.level_version == RMSTAR_LEVEL_VERSION) |
{ |
lev->wcet_miss[p] = 0; |
return 0; |
} |
else |
return -1; |
} |
/demos/trunk/first/testiq.c |
---|
18,11 → 18,11 |
/* |
------------ |
CVS : $Id: testiq.c,v 1.3 2003-01-07 17:10:17 pj Exp $ |
CVS : $Id: testiq.c,v 1.2 2002-11-11 08:17:59 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.3 $ |
Last update: $Date: 2003-01-07 17:10:17 $ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2002-11-11 08:17:59 $ |
------------ |
The purpose of this test is to show that two budgets with different |
246,6 → 246,8 |
{ |
KEY_EVT k; |
set_exchandler_grx(); |
sem_init(&s,0,1); |
k.flag = 0; |
/demos/trunk/first/edfstar.c |
---|
18,11 → 18,11 |
/** |
------------ |
CVS : $Id: edfstar.c,v 1.4 2003-01-07 17:10:16 pj Exp $ |
CVS : $Id: edfstar.c,v 1.3 2002-11-11 08:17:59 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.4 $ |
Last update: $Date: 2003-01-07 17:10:16 $ |
Revision: $Revision: 1.3 $ |
Last update: $Date: 2002-11-11 08:17:59 $ |
------------ |
**/ |
133,7 → 133,7 |
if ((first = iq_query_first(&lev->ready)) != lev->activated) { |
if (lev->activated != NIL) |
level_table[ lev->scheduling_level ]-> |
private_extract(lev->scheduling_level, lev->activated); |
guest_end(lev->scheduling_level, lev->activated); |
lev->activated = first; |
142,7 → 142,7 |
budget_task_default_model(b, lev->budget); |
level_table[ lev->scheduling_level ]-> |
private_insert(lev->scheduling_level, first, (TASK_MODEL *)&b); |
guest_create(lev->scheduling_level, first, (TASK_MODEL *)&b); |
} |
} |
} |
149,17 → 149,19 |
static void EDFSTAR_timer_deadline(void *par); |
static void EDFSTAR_internal_activate(EDFSTAR_level_des *lev, PID p, |
struct timespec *t) |
static void EDFSTAR_internal_activate(EDFSTAR_level_des *lev, PID p) |
{ |
struct timespec temp; |
#ifdef EDFSTAR_DEBUG |
edfstar_printf("(E:iact)"); |
#endif |
ADDUSEC2TIMESPEC(lev->period[p], t); |
TIMESPEC_ASSIGN(&temp, &proc_table[p].request_time); |
ADDUSEC2TIMESPEC(lev->period[p], &temp); |
*iq_query_timespec(p, &lev->ready) = *t; |
lev->deadline_timespec[p] = *t; |
*iq_query_timespec(p, &lev->ready) = temp; |
lev->deadline_timespec[p] = temp; |
/* Insert task in the correct position */ |
proc_table[p].status = EDFSTAR_READY; |
172,6 → 174,18 |
EDFSTAR_check_preemption(lev); |
} |
static char *EDFSTAR_status_to_a(WORD status) |
{ |
if (status < MODULE_STATUS_BASE) |
return status_to_a(status); |
switch (status) { |
case EDFSTAR_READY : return "EDFSTAR_Ready"; |
case EDFSTAR_IDLE : return "EDFSTAR_Idle"; |
default : return "EDFSTAR_Unknown"; |
} |
} |
static void EDFSTAR_timer_deadline(void *par) |
{ |
PID p = (PID) par; |
189,8 → 203,10 |
// edfstar_printf2("I%d",p); |
#endif |
/* set the request time */ |
EDFSTAR_internal_activate(lev,p,iq_query_timespec(p, &lev->ready)); |
proc_table[p].request_time = *iq_query_timespec(p, &lev->ready); |
EDFSTAR_internal_activate(lev,p); |
event_need_reschedule(); |
break; |
229,21 → 245,104 |
kern_raise(XDEADLINE_MISS,p); |
} |
static int EDFSTAR_public_create(LEVEL l, PID p, TASK_MODEL *m) |
static int EDFSTAR_level_accept_task_model(LEVEL l, TASK_MODEL *m) |
{ |
#ifdef EDFSTAR_DEBUG |
edfstar_printf("(E:lacct)"); |
#endif |
if (m->pclass == HARD_PCLASS || m->pclass == (HARD_PCLASS | l)) { |
HARD_TASK_MODEL *h = (HARD_TASK_MODEL *)m; |
if (h->wcet && h->mit && h->periodicity == PERIODIC) |
return 0; |
} |
return -1; |
} |
static int EDFSTAR_level_accept_guest_model(LEVEL l, TASK_MODEL *m) |
{ |
#ifdef EDFSTAR_DEBUG |
edfstar_printf("(E:laccg)"); |
#endif |
if (m->pclass == JOB_PCLASS || m->pclass == (JOB_PCLASS | l)) |
return 0; |
else |
return -1; |
} |
static char *onoff(int i) |
{ |
if (i) |
return "On "; |
else |
return "Off"; |
} |
static void EDFSTAR_level_status(LEVEL l) |
{ |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
PID p = iq_query_first(&lev->ready); |
struct timespec temp; |
kern_printf("Budget number : %u\n", lev->budget); |
kern_printf("Master level : %u\n", lev->scheduling_level); |
kern_printf("Active PID : %u\n", lev->activated); |
while (p != NIL) { |
if ((proc_table[p].pclass) == JOB_PCLASS) |
kern_printf("Pid: %2d (GUEST)\n", p); |
else { |
temp = *iq_query_timespec(p, &lev->ready); |
kern_printf("Pid: %2d Name: %10s %s: %9ld Dline: %9ld.%6ld Stat: %s\n", |
p, |
proc_table[p].name, |
"Period ", |
lev->period[p], |
temp.tv_sec, |
temp.tv_nsec/1000, |
EDFSTAR_status_to_a(proc_table[p].status)); |
p = iq_query_next(p, &lev->ready); |
} |
} |
for (p=0; p<MAX_PROC; p++) |
if (proc_table[p].task_level == l |
&& proc_table[p].status != EDFSTAR_READY |
&& proc_table[p].status != FREE ) { |
temp = *iq_query_timespec(p, &lev->ready); |
kern_printf("Pid: %2d Name: %10s %s: %9ld Dline: %9ld.%6ld Stat: %s\n", |
p, |
proc_table[p].name, |
"Period ", |
lev->period[p], |
temp.tv_sec, |
temp.tv_nsec/1000, |
EDFSTAR_status_to_a(proc_table[p].status)); |
} |
} |
/* The scheduler only gets the first task in the queue */ |
static PID EDFSTAR_level_scheduler(LEVEL l) |
{ |
//EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
return NIL; |
} |
static int EDFSTAR_task_create(LEVEL l, PID p, TASK_MODEL *m) |
{ |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
/* if the EDFSTAR_task_create is called, then the pclass must be a |
valid pclass. */ |
HARD_TASK_MODEL *h; |
HARD_TASK_MODEL *h = (HARD_TASK_MODEL *)m; |
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; |
/* now we know that m is a valid model */ |
#ifdef EDFSTAR_DEBUG |
edfstar_printf("(E:tcr)"); |
#endif |
264,19 → 363,23 |
return 0; /* OK, also if the task cannot be guaranteed... */ |
} |
static void EDFSTAR_task_detach(LEVEL l, PID p) |
{ |
#ifdef EDFSTAR_DEBUG |
edfstar_printf2("(E:tdt)"); |
#endif |
} |
static int EDFSTAR_task_eligible(LEVEL l, PID p) |
{ |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
#ifdef EDFSTAR_DEBUG |
edfstar_printf2("(E:eli)"); |
#endif |
return level_table[ lev->scheduling_level ]-> |
private_eligible(lev->scheduling_level,p); |
return 0; /* if the task p is chosen, it is always eligible */ |
} |
static void EDFSTAR_public_dispatch(LEVEL l, PID p, int nostop) |
static void EDFSTAR_task_dispatch(LEVEL l, PID p, int nostop) |
{ |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
289,10 → 392,10 |
#endif |
level_table[ lev->scheduling_level ]-> |
private_dispatch(lev->scheduling_level,p,nostop); |
guest_dispatch(lev->scheduling_level,p,nostop); |
} |
static void EDFSTAR_public_epilogue(LEVEL l, PID p) |
static void EDFSTAR_task_epilogue(LEVEL l, PID p) |
{ |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
314,15 → 417,14 |
#endif |
level_table[ lev->scheduling_level ]-> |
private_epilogue(lev->scheduling_level,p); |
guest_epilogue(lev->scheduling_level,p); |
proc_table[p].status = EDFSTAR_READY; |
} |
static void EDFSTAR_public_activate(LEVEL l, PID p) |
static void EDFSTAR_task_activate(LEVEL l, PID p) |
{ |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
struct timespec t; |
#ifdef EDFSTAR_DEBUG |
edfstar_printf("(E:act)"); |
336,9 → 438,9 |
return; |
} |
kern_gettime(&t); |
ll_gettime(TIME_EXACT, &proc_table[p].request_time); |
EDFSTAR_internal_activate(lev,p, &t); |
EDFSTAR_internal_activate(lev,p); |
/* Set the deadline timer */ |
lev->deadline_timer[p] = kern_event_post(&lev->deadline_timespec[p], |
347,7 → 449,7 |
} |
static void EDFSTAR_public_unblock(LEVEL l, PID p) |
static void EDFSTAR_task_insert(LEVEL l, PID p) |
{ |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
363,7 → 465,7 |
EDFSTAR_check_preemption(lev); |
} |
static void EDFSTAR_public_block(LEVEL l, PID p) |
static void EDFSTAR_task_extract(LEVEL l, PID p) |
{ |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
379,7 → 481,7 |
EDFSTAR_check_preemption(lev); |
} |
static int EDFSTAR_public_message(LEVEL l, PID p, void *m) |
static void EDFSTAR_task_endcycle(LEVEL l, PID p) |
{ |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
struct timespec temp; |
391,7 → 493,7 |
/* 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); |
guest_end(lev->scheduling_level,p); |
lev->activated = NIL; |
iq_extract(p,&lev->ready); |
408,9 → 510,9 |
lev->nact[p]--; |
/* see also EDFSTAR_timer_deadline */ |
kern_gettime(&temp); |
ll_gettime(TIME_EXACT, &proc_table[p].request_time); |
EDFSTAR_internal_activate(lev,p, &temp); |
EDFSTAR_internal_activate(lev,p); |
/* check if the deadline has already expired */ |
temp = *iq_query_timespec(p, &lev->ready); |
417,7 → 519,7 |
if (TIMESPEC_A_LT_B(&temp, &schedule_time)) { |
/* count the deadline miss */ |
lev->dline_miss[p]++; |
kern_event_delete(lev->deadline_timer[p]); |
event_delete(lev->deadline_timer[p]); |
} |
} |
433,19 → 535,14 |
EDFSTAR_check_preemption(lev); |
/* when the deadline timer fire, it recognize the situation and set |
correctly all the stuffs (like reactivation, etc... ) */ |
correctly all the stuffs (like reactivation, request_time, etc... ) */ |
} |
#ifdef EDFSTAR_DEBUG |
edfstar_printf(")"); |
#endif |
jet_update_endcycle(); /* Update the Jet data... */ |
trc_logevent(TRC_ENDCYCLE,&exec_shadow); /* tracer stuff */ |
return 0; |
} |
static void EDFSTAR_public_end(LEVEL l, PID p) |
static void EDFSTAR_task_end(LEVEL l, PID p) |
{ |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
461,7 → 558,7 |
iq_insertfirst(p,&freedesc); |
if (lev->deadline_timer[p] != -1) { |
kern_event_delete(lev->deadline_timer[p]); |
event_delete(lev->deadline_timer[p]); |
} |
/* and finally, a preemption check! (it will also call guest_end) */ |
468,22 → 565,18 |
EDFSTAR_check_preemption(lev); |
} |
static void EDFSTAR_task_sleep(LEVEL l, PID p) |
{ kern_raise(XINVALID_TASK,exec_shadow); } |
/* Guest Functions |
These functions manages a JOB_TASK_MODEL, that is used to put |
a guest task in the EDFSTAR ready queue. */ |
static void EDFSTAR_private_insert(LEVEL l, PID p, TASK_MODEL *m) |
static int EDFSTAR_guest_create(LEVEL l, PID p, TASK_MODEL *m) |
{ |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
JOB_TASK_MODEL *job; |
JOB_TASK_MODEL *job = (JOB_TASK_MODEL *)m; |
if (m->pclass != JOB_PCLASS || (m->level != 0 && m->level != l) ) { |
kern_raise(XINVALID_TASK, p); |
return; |
} |
job = (JOB_TASK_MODEL *)m; |
/* if the EDFSTAR_guest_create is called, then the pclass must be a |
valid pclass. */ |
496,15 → 589,47 |
if (job->noraiseexc) |
lev->flag[p] = EDFSTAR_FLAG_NORAISEEXC; |
else { |
else |
lev->flag[p] = 0; |
lev->deadline_timer[p] = kern_event_post(iq_query_timespec(p, &lev->ready), |
EDFSTAR_timer_guest_deadline, |
(void *)p); |
} |
lev->period[p] = job->period; |
/* there is no bandwidth guarantee at this level, it is performed |
by the level that inserts guest tasks... */ |
return 0; /* OK, also if the task cannot be guaranteed... */ |
} |
static void EDFSTAR_guest_detach(LEVEL l, PID p) |
{ |
/* the EDFSTAR level doesn't introduce any dinamic allocated new field. |
No guarantee is performed on guest tasks... so we don't have to reset |
the NO_GUARANTEE FIELD */ |
} |
static void EDFSTAR_guest_dispatch(LEVEL l, PID p, int nostop) |
{ |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
level_table[ lev->scheduling_level ]-> |
guest_dispatch(lev->scheduling_level,p,nostop); |
} |
static void EDFSTAR_guest_epilogue(LEVEL l, PID p) |
{ |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
/* the task has been preempted. it returns into the ready queue... */ |
level_table[ lev->scheduling_level ]-> |
guest_epilogue(lev->scheduling_level,p); |
proc_table[p].status = EDFSTAR_READY; |
} |
static void EDFSTAR_guest_activate(LEVEL l, PID p) |
{ |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
/* Insert task in the correct position */ |
iq_timespec_insert(p,&lev->ready); |
proc_table[p].status = EDFSTAR_READY; |
512,30 → 637,39 |
/* check for preemption */ |
EDFSTAR_check_preemption(lev); |
/* there is no bandwidth guarantee at this level, it is performed |
by the level that inserts guest tasks... */ |
/* Set the deadline timer */ |
if (!(lev->flag[p] & EDFSTAR_FLAG_NORAISEEXC)) |
lev->deadline_timer[p] = kern_event_post(iq_query_timespec(p, &lev->ready), |
EDFSTAR_timer_guest_deadline, |
(void *)p); |
} |
static void EDFSTAR_private_dispatch(LEVEL l, PID p, int nostop) |
static void EDFSTAR_guest_insert(LEVEL l, PID p) |
{ |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
level_table[ lev->scheduling_level ]-> |
private_dispatch(lev->scheduling_level,p,nostop); |
/* Insert task in the correct position */ |
iq_timespec_insert(p,&lev->ready); |
proc_table[p].status = EDFSTAR_READY; |
/* and check for preemption! */ |
EDFSTAR_check_preemption(lev); |
} |
static void EDFSTAR_private_epilogue(LEVEL l, PID p) |
static void EDFSTAR_guest_extract(LEVEL l, PID p) |
{ |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
/* the task has been preempted. it returns into the ready queue... */ |
level_table[ lev->scheduling_level ]-> |
private_epilogue(lev->scheduling_level,p); |
/* 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); |
proc_table[p].status = EDFSTAR_READY; |
/* and finally, a preemption check! (it will also call guest_end() */ |
EDFSTAR_check_preemption(lev); |
} |
static void EDFSTAR_private_extract(LEVEL l, PID p) |
static void EDFSTAR_guest_end(LEVEL l, PID p) |
{ |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
550,7 → 684,7 |
#ifdef EDFSTAR_DEBUG |
// kern_printf("EDFSTAR_guest_end: dline timer %d\n",lev->deadline_timer[p]); |
#endif |
kern_event_delete(lev->deadline_timer[p]); |
event_delete(lev->deadline_timer[p]); |
lev->deadline_timer[p] = NIL; |
} |
558,6 → 692,12 |
EDFSTAR_check_preemption(lev); |
} |
static void EDFSTAR_guest_endcycle(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void EDFSTAR_guest_sleep(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
/* Registration functions */ |
/* Registration function: |
573,28 → 713,55 |
#endif |
/* request an entry in the level_table */ |
l = level_alloc_descriptor(sizeof(EDFSTAR_level_des)); |
l = level_alloc_descriptor(); |
lev = (EDFSTAR_level_des *)level_table[l]; |
#ifdef EDFSTAR_DEBUG |
printk(" alloco descrittore %d %d\n",l,(int)sizeof(EDFSTAR_level_des)); |
#endif |
/* alloc the space needed for the EDFSTAR_level_des */ |
lev = (EDFSTAR_level_des *)kern_alloc(sizeof(EDFSTAR_level_des)); |
#ifdef EDFSTAR_DEBUG |
printk(" lev=%d\n",(int)lev); |
#endif |
/* update the level_table with the new entry */ |
level_table[l] = (level_des *)lev; |
/* fill the standard descriptor */ |
lev->l.private_insert = EDFSTAR_private_insert; |
lev->l.private_extract = EDFSTAR_private_extract; |
lev->l.private_dispatch = EDFSTAR_private_dispatch; |
lev->l.private_epilogue = EDFSTAR_private_epilogue; |
strncpy(lev->l.level_name, EDFSTAR_LEVELNAME, MAX_LEVELNAME); |
lev->l.level_code = EDFSTAR_LEVEL_CODE; |
lev->l.level_version = EDFSTAR_LEVEL_VERSION; |
lev->l.public_guarantee = NULL; |
lev->l.public_create = EDFSTAR_public_create; |
lev->l.public_end = EDFSTAR_public_end; |
lev->l.public_dispatch = EDFSTAR_public_dispatch; |
lev->l.public_epilogue = EDFSTAR_public_epilogue; |
lev->l.public_activate = EDFSTAR_public_activate; |
lev->l.public_unblock = EDFSTAR_public_unblock; |
lev->l.public_block = EDFSTAR_public_block; |
lev->l.public_message = EDFSTAR_public_message; |
lev->l.level_accept_task_model = EDFSTAR_level_accept_task_model; |
lev->l.level_accept_guest_model = EDFSTAR_level_accept_guest_model; |
lev->l.level_status = EDFSTAR_level_status; |
lev->l.level_scheduler = EDFSTAR_level_scheduler; |
lev->l.level_guarantee = NULL; |
lev->l.task_create = EDFSTAR_task_create; |
lev->l.task_detach = EDFSTAR_task_detach; |
lev->l.task_eligible = EDFSTAR_task_eligible; |
lev->l.task_dispatch = EDFSTAR_task_dispatch; |
lev->l.task_epilogue = EDFSTAR_task_epilogue; |
lev->l.task_activate = EDFSTAR_task_activate; |
lev->l.task_insert = EDFSTAR_task_insert; |
lev->l.task_extract = EDFSTAR_task_extract; |
lev->l.task_endcycle = EDFSTAR_task_endcycle; |
lev->l.task_end = EDFSTAR_task_end; |
lev->l.task_sleep = EDFSTAR_task_sleep; |
lev->l.guest_create = EDFSTAR_guest_create; |
lev->l.guest_detach = EDFSTAR_guest_detach; |
lev->l.guest_dispatch = EDFSTAR_guest_dispatch; |
lev->l.guest_epilogue = EDFSTAR_guest_epilogue; |
lev->l.guest_activate = EDFSTAR_guest_activate; |
lev->l.guest_insert = EDFSTAR_guest_insert; |
lev->l.guest_extract = EDFSTAR_guest_extract; |
lev->l.guest_endcycle = EDFSTAR_guest_endcycle; |
lev->l.guest_end = EDFSTAR_guest_end; |
lev->l.guest_sleep = EDFSTAR_guest_sleep; |
/* fill the EDFSTAR descriptor part */ |
for(i=0; i<MAX_PROC; i++) { |
lev->period[i] = 0; |
618,8 → 785,11 |
{ |
LEVEL l = proc_table[p].task_level; |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
return lev->dline_miss[p]; |
if (lev->l.level_code == EDFSTAR_LEVEL_CODE && |
lev->l.level_version == EDFSTAR_LEVEL_VERSION) |
return lev->dline_miss[p]; |
else |
return -1; |
} |
int EDFSTAR_get_wcet_miss(PID p) |
626,8 → 796,11 |
{ |
LEVEL l = proc_table[p].task_level; |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
return lev->wcet_miss[p]; |
if (lev->l.level_code == EDFSTAR_LEVEL_CODE && |
lev->l.level_version == EDFSTAR_LEVEL_VERSION) |
return lev->wcet_miss[p]; |
else |
return -1; |
} |
int EDFSTAR_get_nact(PID p) |
634,8 → 807,11 |
{ |
LEVEL l = proc_table[p].task_level; |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
return lev->nact[p]; |
if (lev->l.level_code == EDFSTAR_LEVEL_CODE && |
lev->l.level_version == EDFSTAR_LEVEL_VERSION) |
return lev->nact[p]; |
else |
return -1; |
} |
int EDFSTAR_reset_dline_miss(PID p) |
642,9 → 818,14 |
{ |
LEVEL l = proc_table[p].task_level; |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
lev->dline_miss[p] = 0; |
return 0; |
if (lev->l.level_code == EDFSTAR_LEVEL_CODE && |
lev->l.level_version == EDFSTAR_LEVEL_VERSION) |
{ |
lev->dline_miss[p] = 0; |
return 0; |
} |
else |
return -1; |
} |
int EDFSTAR_reset_wcet_miss(PID p) |
651,8 → 832,13 |
{ |
LEVEL l = proc_table[p].task_level; |
EDFSTAR_level_des *lev = (EDFSTAR_level_des *)(level_table[l]); |
lev->wcet_miss[p] = 0; |
return 0; |
if (lev->l.level_code == EDFSTAR_LEVEL_CODE && |
lev->l.level_version == EDFSTAR_LEVEL_VERSION) |
{ |
lev->wcet_miss[p] = 0; |
return 0; |
} |
else |
return -1; |
} |
/demos/trunk/first/test1.c |
---|
18,11 → 18,11 |
/* |
------------ |
CVS : $Id: test1.c,v 1.2 2003-01-07 17:10:17 pj Exp $ |
CVS : $Id: test1.c,v 1.1 2002-09-02 10:29:30 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2003-01-07 17:10:17 $ |
Revision: $Revision: 1.1 $ |
Last update: $Date: 2002-09-02 10:29:30 $ |
------------ |
this test shows a set of 5 tasks (+main+dummy+keyboard driver). |
120,6 → 120,7 |
//keyb_def_ctrlC(kparms, NULL); |
//keyb_def_map(kparms,itaMap); |
KEYB_init(&kparms); |
__call_main__(mb); |
return (void *)0; |
228,9 → 229,11 |
{ |
char c; |
set_exchandler_grx(); |
clear(); |
cprintf("Hello, world!\nPress ESC to end the demo...\n"); |
cprintf("Hello, world!"); |
create1(); |
/demos/trunk/first/test2.c |
---|
18,11 → 18,11 |
/* |
------------ |
CVS : $Id: test2.c,v 1.2 2003-01-07 17:10:17 pj Exp $ |
CVS : $Id: test2.c,v 1.1 2002-09-02 10:29:30 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2003-01-07 17:10:17 $ |
Revision: $Revision: 1.1 $ |
Last update: $Date: 2002-09-02 10:29:30 $ |
------------ |
The purpose of this test is to show that two budgets with different |
224,6 → 224,8 |
{ |
char c; |
set_exchandler_grx(); |
cprintf("Hello, world!"); |
create1(); |
/demos/trunk/first/test3.c |
---|
18,11 → 18,11 |
/* |
------------ |
CVS : $Id: test3.c,v 1.2 2003-01-07 17:10:17 pj Exp $ |
CVS : $Id: test3.c,v 1.1 2002-09-02 10:29:30 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2003-01-07 17:10:17 $ |
Revision: $Revision: 1.1 $ |
Last update: $Date: 2002-09-02 10:29:30 $ |
------------ |
The purpose of this test is to show that two budgets with different |
199,6 → 199,8 |
{ |
KEY_EVT k; |
set_exchandler_grx(); |
sem_init(&s,0,1); |
k.flag = 0; |
/demos/trunk/first/test4.c |
---|
18,11 → 18,11 |
/* |
------------ |
CVS : $Id: test4.c,v 1.2 2003-01-07 17:10:17 pj Exp $ |
CVS : $Id: test4.c,v 1.1 2002-09-02 10:29:30 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2003-01-07 17:10:17 $ |
Revision: $Revision: 1.1 $ |
Last update: $Date: 2002-09-02 10:29:30 $ |
------------ |
The purpose of this test is to show that two budgets with different |
217,6 → 217,8 |
{ |
KEY_EVT k; |
set_exchandler_grx(); |
sem_init(&s,0,1); |
k.flag = 0; |
/demos/trunk/first/test5.c |
---|
18,11 → 18,11 |
/* |
------------ |
CVS : $Id: test5.c,v 1.2 2003-01-07 17:10:17 pj Exp $ |
CVS : $Id: test5.c,v 1.1 2002-09-02 10:29:30 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2003-01-07 17:10:17 $ |
Revision: $Revision: 1.1 $ |
Last update: $Date: 2002-09-02 10:29:30 $ |
------------ |
The purpose of this test is to show that two budgets with different |
234,6 → 234,8 |
{ |
KEY_EVT k; |
set_exchandler_grx(); |
sem_init(&s,0,1); |
k.flag = 0; |
/demos/trunk/first/test6.c |
---|
18,11 → 18,11 |
/* |
------------ |
CVS : $Id: test6.c,v 1.2 2003-01-07 17:10:17 pj Exp $ |
CVS : $Id: test6.c,v 1.1 2002-09-02 10:29:30 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2003-01-07 17:10:17 $ |
Revision: $Revision: 1.1 $ |
Last update: $Date: 2002-09-02 10:29:30 $ |
------------ |
this test shows a set of 5 tasks (+main+dummy+keyboard driver). |
229,6 → 229,8 |
{ |
char c; |
set_exchandler_grx(); |
clear(); |
cprintf("Hello, world!"); |
/demos/trunk/first/rmstar.h |
---|
20,11 → 20,11 |
/** |
------------ |
CVS : $Id: rmstar.h,v 1.2 2003-01-07 17:10:17 pj Exp $ |
CVS : $Id: rmstar.h,v 1.1 2002-09-02 10:29:30 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2003-01-07 17:10:17 $ |
Revision: $Revision: 1.1 $ |
Last update: $Date: 2002-09-02 10:29:30 $ |
------------ |
Title: |
92,6 → 92,7 |
#include <kernel/config.h> |
#include <sys/types.h> |
#include <kernel/types.h> |
#include <modules/codes.h> |
/demos/trunk/first/edfstar.h |
---|
20,11 → 20,11 |
/** |
------------ |
CVS : $Id: edfstar.h,v 1.2 2003-01-07 17:10:17 pj Exp $ |
CVS : $Id: edfstar.h,v 1.1 2002-09-02 10:29:30 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2003-01-07 17:10:17 $ |
Revision: $Revision: 1.1 $ |
Last update: $Date: 2002-09-02 10:29:30 $ |
------------ |
Title: |
102,6 → 102,7 |
#include <kernel/config.h> |
#include <sys/types.h> |
#include <kernel/types.h> |
#include <modules/codes.h> |
/demos/trunk/cbs_ft/cbs_ft.c |
---|
15,11 → 15,11 |
/** |
------------ |
CVS : $Id: cbs_ft.c,v 1.4 2003-01-07 17:10:16 pj Exp $ |
CVS : $Id: cbs_ft.c,v 1.3 2002-11-11 08:14:22 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.4 $ |
Last update: $Date: 2003-01-07 17:10:16 $ |
Revision: $Revision: 1.3 $ |
Last update: $Date: 2002-11-11 08:14:22 $ |
------------ |
This file contains the server CBS_FT |
50,6 → 50,18 |
#include "cbs_ft.h" |
/*+ 4 debug purposes +*/ |
#undef CBS_FT_TEST |
#ifdef TESTG |
#include "drivers/glib.h" |
TIME x,oldx; |
extern TIME starttime; |
#endif |
/*+ Status used in the level +*/ |
#define CBS_FT_IDLE APER_STATUS_BASE /*+ waiting the activation +*/ |
#define CBS_FT_ZOMBIE APER_STATUS_BASE+1 /*+ waiting the period end +*/ |
263,16 → 275,32 |
job_task_default_model(job, lev->cbs_ft_dline[p]); |
job_task_def_yesexc(job); |
level_table[ lev->scheduling_level ]-> |
private_insert(lev->scheduling_level, p, (TASK_MODEL *)&job); |
guest_create(lev->scheduling_level, p, (TASK_MODEL *)&job); |
level_table[ lev->scheduling_level ]-> |
guest_activate(lev->scheduling_level, p); |
} |
static char *CBS_FT_status_to_a(WORD status) |
{ |
if (status < MODULE_STATUS_BASE) |
return status_to_a(status); |
switch (status) { |
case CBS_FT_IDLE : return "CBS_FT_Idle"; |
case CBS_FT_ZOMBIE : return "CBS_FT_Zombie"; |
default : return "CBS_FT_Unknown"; |
} |
} |
/* this is the periodic reactivation of the task... */ |
static void CBS_FT_timer_reactivate(void *par) |
{ |
PID p = (PID) par; |
CBS_FT_level_des *lev; |
struct timespec t; |
lev = (CBS_FT_level_des *)level_table[proc_table[p].task_level]; |
281,7 → 309,7 |
reactivated */ |
/* request_time represents the time of the last instance release!! */ |
TIMESPEC_ASSIGN(&t, &lev->reactivation_time[p]); |
TIMESPEC_ASSIGN(&proc_table[p].request_time, &lev->reactivation_time[p]); |
/* If idle=1, then we have to discharge the capacities stored in |
the capacity queue up to the length of the idle interval */ |
289,7 → 317,7 |
TIME interval; |
struct timespec delta; |
lev->idle = 0; |
SUBTIMESPEC(&t, &lev->start_idle, &delta); |
SUBTIMESPEC(&proc_table[p].request_time, &lev->start_idle, &delta); |
/* length of the idle interval expressed in usec! */ |
interval = TIMESPEC2NANOSEC(&delta) / 1000; |
412,14 → 440,67 |
lev->U -= (MAX_BANDWIDTH / lev->period[p]) * (TIME)lev->maxcap[p]; |
} |
static PID CBS_FT_public_scheduler(LEVEL l) |
static int CBS_FT_level_accept_task_model(LEVEL l, TASK_MODEL *m) |
{ |
if (m->pclass == FT_PCLASS || m->pclass == |
(FT_PCLASS | l)) { |
FT_TASK_MODEL *f = (FT_TASK_MODEL *) m; |
//kern_printf("accept :FAULT TOLERANT TASK found!!!!!!\n"); */ |
if (f->type == PRIMARY && f->execP > 0 && f->budget < (int)f->period |
&& f->backup != NIL) return 0; |
if (f->type == BACKUP && f->wcetB > 0) |
return 0; |
} |
return -1; |
} |
static int CBS_FT_level_accept_guest_model(LEVEL l, TASK_MODEL *m) |
{ |
return -1; |
} |
static char *onoff(int i) |
{ |
if (i) |
return "On "; |
else |
return "Off"; |
} |
static void CBS_FT_level_status(LEVEL l) |
{ |
CBS_FT_level_des *lev = (CBS_FT_level_des *)(level_table[l]); |
PID p; |
kern_printf("On-line guarantee : %s\n", |
onoff(lev->flags & CBS_FT_ENABLE_GUARANTEE)); |
kern_printf("Used Bandwidth : %u/%u\n", |
lev->U, MAX_BANDWIDTH); |
for (p=0; p<MAX_PROC; p++) |
if (proc_table[p].task_level == l && proc_table[p].status != FREE ) |
kern_printf("Pid: %2d Name: %10s Period: %9ld Dline: %9ld.%6ld Stat: %s\n", |
p, |
proc_table[p].name, |
lev->period[p], |
lev->cbs_ft_dline[p].tv_sec, |
lev->cbs_ft_dline[p].tv_nsec/1000, |
CBS_FT_status_to_a(proc_table[p].status)); |
} |
static PID CBS_FT_level_scheduler(LEVEL l) |
{ |
CBS_FT_level_des *lev = (CBS_FT_level_des *)(level_table[l]); |
/* it stores the actual time and set the IDLE flag in order to handle |
the capacity queue discharging!!! */ |
lev->idle = 1; |
kern_gettime(&lev->start_idle); |
ll_gettime(TIME_EXACT, &lev->start_idle); |
/* the CBS_FT don't schedule anything... |
429,7 → 510,7 |
/* The on-line guarantee is enabled only if the appropriate flag is set... */ |
static int CBS_FT_public_guarantee(LEVEL l, bandwidth_t *freebandwidth) |
static int CBS_FT_level_guarantee(LEVEL l, bandwidth_t *freebandwidth) |
{ |
CBS_FT_level_des *lev = (CBS_FT_level_des *)(level_table[l]); |
450,22 → 531,17 |
} |
static int CBS_FT_public_create(LEVEL l, PID p, TASK_MODEL *m) |
static int CBS_FT_task_create(LEVEL l, PID p, TASK_MODEL *m) |
{ |
CBS_FT_level_des *lev = (CBS_FT_level_des *)(level_table[l]); |
FT_TASK_MODEL *s; |
if (m->pclass != FT_PCLASS) return -1; |
if (m->level != 0 && m->level != l) return -1; |
s = (FT_TASK_MODEL *) m; |
//kern_printf("accept :FAULT TOLERANT TASK found!!!!!!\n"); */ |
if (!(s->type == PRIMARY && s->execP > 0 && s->budget < (int)s->period |
&& s->backup != NIL)) return -1; |
if (!(s->type == BACKUP && s->wcetB > 0)) |
return -1; |
/* now we know that m is a valid model */ |
/* if the CBS_FT_task_create is called, then the pclass must be a |
valid pclass. */ |
FT_TASK_MODEL *s = (FT_TASK_MODEL *)m; |
/* Enable budget check */ |
proc_table[p].control |= CONTROL_CAP; |
507,7 → 583,7 |
} |
static void CBS_FT_public_detach(LEVEL l, PID p) |
static void CBS_FT_task_detach(LEVEL l, PID p) |
{ |
/* the CBS_FT level doesn't introduce any dynamic allocated new field. |
we have only to reset the NO_GUARANTEE FIELD and decrement the allocated |
522,14 → 598,19 |
} |
static void CBS_FT_public_dispatch(LEVEL l, PID p, int nostop) |
static int CBS_FT_task_eligible(LEVEL l, PID p) |
{ |
return 0; /* if the task p is chosen, it is always eligible */ |
} |
static void CBS_FT_task_dispatch(LEVEL l, PID p, int nostop) |
{ |
CBS_FT_level_des *lev = (CBS_FT_level_des *)(level_table[l]); |
level_table[ lev->scheduling_level ]-> |
private_dispatch(lev->scheduling_level,p,nostop); |
guest_dispatch(lev->scheduling_level,p,nostop); |
} |
static void CBS_FT_public_epilogue(LEVEL l, PID p) |
static void CBS_FT_task_epilogue(LEVEL l, PID p) |
{ |
CBS_FT_level_des *lev = (CBS_FT_level_des *)(level_table[l]); |
542,7 → 623,7 |
kern_raise(XWCET_VIOLATION,p); |
/* we kill the current activation */ |
level_table[ lev->scheduling_level ]-> |
private_extract(lev->scheduling_level, p); |
guest_end(lev->scheduling_level, p); |
return; |
} |
556,7 → 637,7 |
lev->CP[p] = 0; |
/* we kill the current activation */ |
level_table[ lev->scheduling_level ]-> |
private_extract(lev->scheduling_level, p); |
guest_end(lev->scheduling_level, p); |
return; |
} |
} |
564,17 → 645,18 |
/* the task returns into the ready queue by |
calling the guest_epilogue... */ |
level_table[ lev->scheduling_level ]-> |
private_epilogue(lev->scheduling_level,p); |
guest_epilogue(lev->scheduling_level,p); |
} |
static void CBS_FT_public_activate(LEVEL l, PID p) |
static void CBS_FT_task_activate(LEVEL l, PID p) |
{ |
CBS_FT_level_des *lev = (CBS_FT_level_des *)(level_table[l]); |
struct timespec t; |
kern_gettime(&t); |
ll_gettime(TIME_EXACT, &proc_table[p].request_time); |
if (lev->P_or_B[p] == BACKUP) { |
kern_printf("\nTrying to activate a BACKUP task!\n"); |
kern_raise(XINVALID_TASK, p); |
587,7 → 669,7 |
TIME interval; |
struct timespec delta; |
lev->idle = 0; |
SUBTIMESPEC(&t, &lev->start_idle, &delta); |
SUBTIMESPEC(&proc_table[p].request_time, &lev->start_idle, &delta); |
/* length of the idle interval expressed in usec! */ |
interval = TIMESPEC2NANOSEC(&delta) / 1000; |
607,7 → 689,7 |
} |
} |
CBS_FT_activation(lev, p, &t); |
CBS_FT_activation(lev, p, &proc_table[p].request_time); |
/* Set the reactivation timer */ |
620,13 → 702,28 |
} |
} |
static int CBS_FT_public_message(LEVEL l, PID p, void *m) |
static void CBS_FT_task_insert(LEVEL l, PID p) |
{ |
printk("CBS_FT_task_insert\n"); |
kern_raise(XINVALID_TASK,p); |
} |
static void CBS_FT_task_extract(LEVEL l, PID p) |
{ |
printk("CBS_FT_task_extract\n"); |
kern_raise(XINVALID_TASK,p); |
} |
static void CBS_FT_task_endcycle(LEVEL l, PID p) |
{ |
CBS_FT_level_des *lev = (CBS_FT_level_des *)(level_table[l]); |
level_table[ lev->scheduling_level ]-> |
private_extract(lev->scheduling_level,p); |
guest_end(lev->scheduling_level,p); |
proc_table[p].status = CBS_FT_IDLE; |
646,8 → 743,10 |
job_task_default_model(job, lev->cbs_ft_dline[p]); |
job_task_def_yesexc(job); |
level_table[ lev->scheduling_level ]-> |
private_insert(lev->scheduling_level, lev->backup[p], |
guest_create(lev->scheduling_level, lev->backup[p], |
(TASK_MODEL *)&job); |
level_table[ lev->scheduling_level ]-> |
guest_activate(lev->scheduling_level, lev->backup[p]); |
} |
else { |
/* A spare capacity is inserted in the capacity queue!! */ |
668,15 → 767,10 |
proc_table[p].avail_time = 0; |
} |
} |
jet_update_endcycle(); /* Update the Jet data... */ |
trc_logevent(TRC_ENDCYCLE,&exec_shadow); /* tracer stuff */ |
return 0; |
} |
static void CBS_FT_public_end(LEVEL l, PID p) |
static void CBS_FT_task_end(LEVEL l, PID p) |
{ |
CBS_FT_level_des *lev = (CBS_FT_level_des *)(level_table[l]); |
698,11 → 792,11 |
} |
level_table[ lev->scheduling_level ]-> |
private_extract(lev->scheduling_level,p); |
guest_end(lev->scheduling_level,p); |
/* we delete the reactivation timer */ |
kern_event_delete(lev->reactivation_timer[p]); |
event_delete(lev->reactivation_timer[p]); |
lev->reactivation_timer[p] = -1; |
714,11 → 808,52 |
(void *)p); |
} |
static void CBS_FT_task_sleep(LEVEL l, PID p) |
{ |
printk("CBS_FT_task_sleep\n"); |
kern_raise(XINVALID_TASK,p); |
} |
static int CBS_FT_guest_create(LEVEL l, PID p, TASK_MODEL *m) |
{ kern_raise(XINVALID_GUEST,exec_shadow); return 0; } |
static void CBS_FT_guest_detach(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void CBS_FT_guest_dispatch(LEVEL l, PID p, int nostop) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void CBS_FT_guest_epilogue(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void CBS_FT_guest_activate(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void CBS_FT_guest_insert(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void CBS_FT_guest_extract(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void CBS_FT_guest_endcycle(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void CBS_FT_guest_end(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void CBS_FT_guest_sleep(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
/* Registration functions */ |
/*+ Registration function: |
int flags the init flags ... see CBS.h +*/ |
LEVEL CBS_FT_register_level(int flags, LEVEL master) |
void CBS_FT_register_level(int flags, LEVEL master) |
{ |
LEVEL l; /* the level that we register */ |
CBS_FT_level_des *lev; /* for readableness only */ |
727,28 → 862,56 |
printk("CBS_FT_register_level\n"); |
/* request an entry in the level_table */ |
l = level_alloc_descriptor(sizeof(CBS_FT_level_des)); |
l = level_alloc_descriptor(); |
lev = (CBS_FT_level_des *)level_table[l]; |
printk(" alloco descrittore %d %d\n",l,sizeof(CBS_FT_level_des)); |
/* alloc the space needed for the CBS_FT_level_des */ |
lev = (CBS_FT_level_des *)kern_alloc(sizeof(CBS_FT_level_des)); |
printk(" lev=%d\n",(int)lev); |
/* update the level_table with the new entry */ |
level_table[l] = (level_des *)lev; |
/* fill the standard descriptor */ |
lev->l.public_scheduler = CBS_FT_public_scheduler; |
strncpy(lev->l.level_name, CBS_FT_LEVELNAME, MAX_LEVELNAME); |
lev->l.level_code = CBS_FT_LEVEL_CODE; |
lev->l.level_version = CBS_FT_LEVEL_VERSION; |
lev->l.level_accept_task_model = CBS_FT_level_accept_task_model; |
lev->l.level_accept_guest_model = CBS_FT_level_accept_guest_model; |
lev->l.level_status = CBS_FT_level_status; |
lev->l.level_scheduler = CBS_FT_level_scheduler; |
if (flags & CBS_FT_ENABLE_GUARANTEE) |
lev->l.public_guarantee = CBS_FT_public_guarantee; |
lev->l.level_guarantee = CBS_FT_level_guarantee; |
else |
lev->l.public_guarantee = NULL; |
lev->l.level_guarantee = NULL; |
lev->l.public_create = CBS_FT_public_create; |
lev->l.public_detach = CBS_FT_public_detach; |
lev->l.public_end = CBS_FT_public_end; |
lev->l.public_dispatch = CBS_FT_public_dispatch; |
lev->l.public_epilogue = CBS_FT_public_epilogue; |
lev->l.public_activate = CBS_FT_public_activate; |
lev->l.public_message = CBS_FT_public_message; |
lev->l.task_create = CBS_FT_task_create; |
lev->l.task_detach = CBS_FT_task_detach; |
lev->l.task_eligible = CBS_FT_task_eligible; |
lev->l.task_dispatch = CBS_FT_task_dispatch; |
lev->l.task_epilogue = CBS_FT_task_epilogue; |
lev->l.task_activate = CBS_FT_task_activate; |
lev->l.task_insert = CBS_FT_task_insert; |
lev->l.task_extract = CBS_FT_task_extract; |
lev->l.task_endcycle = CBS_FT_task_endcycle; |
lev->l.task_end = CBS_FT_task_end; |
lev->l.task_sleep = CBS_FT_task_sleep; |
lev->l.guest_create = CBS_FT_guest_create; |
lev->l.guest_detach = CBS_FT_guest_detach; |
lev->l.guest_dispatch = CBS_FT_guest_dispatch; |
lev->l.guest_epilogue = CBS_FT_guest_epilogue; |
lev->l.guest_activate = CBS_FT_guest_activate; |
lev->l.guest_insert = CBS_FT_guest_insert; |
lev->l.guest_extract = CBS_FT_guest_extract; |
lev->l.guest_endcycle = CBS_FT_guest_endcycle; |
lev->l.guest_end = CBS_FT_guest_end; |
lev->l.guest_sleep = CBS_FT_guest_sleep; |
/* fill the CBS_FT descriptor part */ |
for (i=0; i<MAX_PROC; i++) { |
NULL_TIMESPEC(&lev->cbs_ft_dline[i]); |
768,8 → 931,6 |
lev->scheduling_level = master; |
lev->flags = flags & 0x07; |
return l; |
} |
776,9 → 937,13 |
bandwidth_t CBS_FT_usedbandwidth(LEVEL l) |
{ |
CBS_FT_level_des *lev = (CBS_FT_level_des *)(level_table[l]); |
return lev->U; |
if (lev->l.level_code == CBS_FT_LEVEL_CODE && |
lev->l.level_version == CBS_FT_LEVEL_VERSION) |
return lev->U; |
else |
return 0; |
} |
/demos/trunk/cbs_ft/cbs_ft.h |
---|
15,11 → 15,11 |
/** |
------------ |
CVS : $Id: cbs_ft.h,v 1.2 2003-01-07 17:10:16 pj Exp $ |
CVS : $Id: cbs_ft.h,v 1.1.1.1 2002-09-02 09:37:41 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2003-01-07 17:10:16 $ |
Revision: $Revision: 1.1.1.1 $ |
Last update: $Date: 2002-09-02 09:37:41 $ |
------------ |
This file contains the server CBS_FT |
57,7 → 57,6 |
#include <kernel/descr.h> |
#include <kernel/var.h> |
#include <kernel/func.h> |
#include <kernel/trace.h> |
134,7 → 133,7 |
#define ft_task_def_primary_exec(m,b) (m).execP = b |
/************************************************************************/ |
LEVEL CBS_FT_register_level(int flags, LEVEL master); |
void CBS_FT_register_level(int flags, LEVEL master); |
bandwidth_t CBS_FT_usedbandwidth(LEVEL l); |
/demos/trunk/jumpball/demo.c |
---|
18,11 → 18,11 |
/** |
------------ |
CVS : $Id: demo.c,v 1.3 2003-01-07 17:10:17 pj Exp $ |
CVS : $Id: demo.c,v 1.2 2002-11-11 08:13:47 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.3 $ |
Last update: $Date: 2003-01-07 17:10:17 $ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2002-11-11 08:13:47 $ |
------------ |
**/ |
144,7 → 144,7 |
/* Default action for an kern exception is */ |
kern_cli(); |
kern_gettime(&t), |
ll_gettime(TIME_EXACT, &t), |
kern_printf("\nS.Ha.R.K. Exception raised!!!" |
"\nTime (s:ns) :%ld:%ld" |
"\nException number:%d" |
182,8 → 182,8 |
grx_close(); |
kern_cli(); |
for (p = firstevent; p != NULL; p = p->next) { |
kern_printf("par:%d time:%ld.%ld p:%d handler:%d\n", |
(int)p->par, p->time.tv_sec, p->time.tv_nsec/1000, (int)p, (int)p->handler); |
kern_printf("par:%d time:%ld.%ld p:%ld handler:%ld\n", |
p->par, p->time.tv_sec, p->time.tv_nsec/1000, p, p->handler); |
} |
kern_sti(); |
} |
216,6 → 216,7 |
k.ascii = 13; |
keyb_hook(k,endfun); |
set_exchandler_grx(); |
sys_atrunlevel(my_close, NULL, RUNLEVEL_BEFORE_EXIT); |
/demos/trunk/myapp2/makefile |
---|
0,0 → 1,16 |
# |
# |
# |
ifndef BASE |
BASE=../.. |
endif |
include $(BASE)/config/config.mk |
PROGS= $(APP) |
include $(BASE)/config/example.mk |
$(APP): |
make -f $(SUBMAKE) INIT=hartik3.o OTHEROBJS= |
/demos/trunk/myapp2/myapp.c |
---|
0,0 → 1,55 |
/* |
* Project: S.Ha.R.K. |
* |
* Coordinators: Giorgio Buttazzo <giorgio@sssup.it> |
* |
* Authors : Paolo Gai <pj@hartik.sssup.it> |
* (see authors.txt for full list of hartik's authors) |
* |
* ReTiS Lab (Scuola Superiore S.Anna - Pisa - Italy) |
* |
* http://www.sssup.it |
* http://retis.sssup.it |
* http://shark.sssup.it |
*/ |
/* |
* Copyright (C) 2000 Paolo Gai |
* |
* This program is free software; you can redistribute it and/or modify |
* it under the terms of the GNU General Public License as published by |
* the Free Software Foundation; either version 2 of the License, or |
* (at your option) any later version. |
* |
* This program is distributed in the hope that it will be useful, |
* but WITHOUT ANY WARRANTY; without even the implied warranty of |
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
* GNU General Public License for more details. |
* |
* You should have received a copy of the GNU General Public License |
* along with this program; if not, write to the Free Software |
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
* |
*/ |
// if you want to use some functions, types, task models provided |
// by your new module |
#include "mymod.h" |
// then, include any file you want here |
// then, the classic C-style function |
int main(int argc, char **argv) |
{ |
// ... your stuff here |
return 0; |
} |
/demos/trunk/myapp2/readme.txt |
---|
0,0 → 1,7 |
This is a template application, and it DOES NOTHING!!! |
This is only an example package. |
Please refer to the How To Compile reference guide for more informations. |
Paolo |
/demos/trunk/myapp/mymod.c |
---|
0,0 → 1,261 |
/* |
* Project: HARTIK (HA-rd R-eal TI-me K-ernel) |
* |
* Coordinators: Giorgio Buttazzo <giorgio@sssup.it> |
* Gerardo Lamastra <gerardo@sssup.it> |
* |
* Authors : Paolo Gai <pj@hartik.sssup.it> |
* (see authors.txt for full list of hartik's authors) |
* |
* ReTiS Lab (Scuola Superiore S.Anna - Pisa - Italy) |
* |
* http://www.sssup.it |
* http://retis.sssup.it |
* http://hartik.sssup.it |
*/ |
/* |
* Copyright (C) 2000 Paolo Gai |
* |
* This program is free software; you can redistribute it and/or modify |
* it under the terms of the GNU General Public License as published by |
* the Free Software Foundation; either version 2 of the License, or |
* (at your option) any later version. |
* |
* This program is distributed in the hope that it will be useful, |
* but WITHOUT ANY WARRANTY; without even the implied warranty of |
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
* GNU General Public License for more details. |
* |
* You should have received a copy of the GNU General Public License |
* along with this program; if not, write to the Free Software |
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
* |
*/ |
#include "mymod.h" |
#include <ll/string.h> |
#include <kernel/model.h> |
#include <kernel/descr.h> |
#include <kernel/var.h> |
#include <kernel/func.h> |
// other include files if needed |
// NOTE: NO GLOBAL OR STATIC VARIABLES!!! |
// (put them inside the level descriptor!) |
/* Statuses used in the level */ |
#define MYMOD_READY MODULE_STATUS_BASE |
#define MYMOD_WAIT MODULE_STATUS_BASE+3 |
#define MYMOD_IDLE MODULE_STATUS_BASE+4 |
/* the level redefinition for the Module */ |
typedef struct { |
level_des l; /* the standard level descriptor */ |
int myvar[100]; /* other local (private) variables of the module */ |
} MYMOD_level_des; |
// example of OSLib event |
static void MYMOD_timer_deadline(void *par) |
{ |
// usually the void *par is a pointer to a structure or a PID |
// if it is a PID, you can do that to retrieve it and the correspondent |
// level descriptor |
PID p = (PID) par; |
MYMOD_level_des *lev; |
lev = (MYMOD_level_des *)level_table[proc_table[p].task_level]; |
// now you know the PID of the task and the level descriptor |
// ... so, you know all the things you need |
} |
static int MYMOD_level_accept_task_model(LEVEL l, TASK_MODEL *m) |
{ |
// your code here |
return 0; // dummy number |
} |
static int MYMOD_level_accept_guest_model(LEVEL l, TASK_MODEL *m) |
{ |
// your code here |
return 0; // dummy number |
} |
static void MYMOD_level_status(LEVEL l) |
{ |
} |
/* The scheduler only gets the first task in the queue */ |
static PID MYMOD_level_scheduler(LEVEL l) |
{ |
return 0; // dummy number |
} |
/* The on-line guarantee is enabled only if the appropriate flag is set... */ |
static int MYMOD_level_guarantee(LEVEL l, bandwidth_t *freebandwidth) |
{ |
return 0; // dummy number |
} |
static int MYMOD_task_create(LEVEL l, PID p, TASK_MODEL *m) |
{ |
return 0; // dummy number |
} |
static void MYMOD_task_detach(LEVEL l, PID p) |
{ |
} |
static int MYMOD_task_eligible(LEVEL l, PID p) |
{ |
return 0; // dummy number |
} |
static void MYMOD_task_dispatch(LEVEL l, PID p, int nostop) |
{ |
} |
static void MYMOD_task_epilogue(LEVEL l, PID p) |
{ |
} |
static void MYMOD_task_activate(LEVEL l, PID p) |
{ |
} |
static void MYMOD_task_insert(LEVEL l, PID p) |
{ |
} |
static void MYMOD_task_extract(LEVEL l, PID p) |
{ |
} |
static void MYMOD_task_endcycle(LEVEL l, PID p) |
{ |
} |
static void MYMOD_task_end(LEVEL l, PID p) |
{ |
} |
static void MYMOD_task_sleep(LEVEL l, PID p) |
{ |
} |
static int MYMOD_guest_create(LEVEL l, PID p, TASK_MODEL *m) |
{ |
return 0; // dummy number |
} |
static void MYMOD_guest_detach(LEVEL l, PID p) |
{ |
} |
static void MYMOD_guest_dispatch(LEVEL l, PID p, int nostop) |
{ |
} |
static void MYMOD_guest_epilogue(LEVEL l, PID p) |
{ |
} |
static void MYMOD_guest_activate(LEVEL l, PID p) |
{ |
} |
static void MYMOD_guest_insert(LEVEL l, PID p) |
{ |
} |
static void MYMOD_guest_extract(LEVEL l, PID p) |
{ |
} |
static void MYMOD_guest_endcycle(LEVEL l, PID p) |
{ |
} |
static void MYMOD_guest_end(LEVEL l, PID p) |
{ |
} |
static void MYMOD_guest_sleep(LEVEL l, PID p) |
{ |
} |
/* Registration functions */ |
/*+ Registration function: |
int flags the init flags ... see MYMOD.h +*/ |
void MYMOD_register_level(int flags) |
{ |
LEVEL l; /* the level that we register */ |
MYMOD_level_des *lev; /* for readableness only */ |
PID i; /* a counter */ |
/* request an entry in the level_table */ |
l = level_alloc_descriptor(); |
/* alloc the space needed for the MYMOD_level_des */ |
lev = (MYMOD_level_des *)kern_alloc(sizeof(MYMOD_level_des)); |
/* update the level_table with the new entry */ |
level_table[l] = (level_des *)lev; |
/* fill the standard descriptor */ |
strncpy(lev->l.level_name, MYMOD_LEVELNAME, MAX_LEVELNAME); |
lev->l.level_code = MYMOD_LEVEL_CODE; |
lev->l.level_version = MYMOD_LEVEL_VERSION; |
lev->l.level_accept_task_model = MYMOD_level_accept_task_model; |
lev->l.level_accept_guest_model = MYMOD_level_accept_guest_model; |
lev->l.level_status = MYMOD_level_status; |
lev->l.level_scheduler = MYMOD_level_scheduler; |
lev->l.level_guarantee = MYMOD_level_guarantee; |
lev->l.task_create = MYMOD_task_create; |
lev->l.task_detach = MYMOD_task_detach; |
lev->l.task_eligible = MYMOD_task_eligible; |
lev->l.task_dispatch = MYMOD_task_dispatch; |
lev->l.task_epilogue = MYMOD_task_epilogue; |
lev->l.task_activate = MYMOD_task_activate; |
lev->l.task_insert = MYMOD_task_insert; |
lev->l.task_extract = MYMOD_task_extract; |
lev->l.task_endcycle = MYMOD_task_endcycle; |
lev->l.task_end = MYMOD_task_end; |
lev->l.task_sleep = MYMOD_task_sleep; |
lev->l.guest_create = MYMOD_guest_create; |
lev->l.guest_detach = MYMOD_guest_detach; |
lev->l.guest_dispatch = MYMOD_guest_dispatch; |
lev->l.guest_epilogue = MYMOD_guest_epilogue; |
lev->l.guest_activate = MYMOD_guest_activate; |
lev->l.guest_insert = MYMOD_guest_insert; |
lev->l.guest_extract = MYMOD_guest_extract; |
lev->l.guest_endcycle = MYMOD_guest_endcycle; |
lev->l.guest_end = MYMOD_guest_end; |
lev->l.guest_sleep = MYMOD_guest_sleep; |
/* fill the MYMOD descriptor part */ |
for (i=0; i<100; i++) |
lev->myvar[i] = 0; |
} |
// put here the other interface functions added |
/demos/trunk/myapp/makefile |
---|
0,0 → 1,16 |
# |
# |
# |
ifndef BASE |
BASE=../.. |
endif |
include $(BASE)/config/config.mk |
PROGS= myapp |
include $(BASE)/config/example.mk |
myapp: |
make -f $(SUBMAKE) APP=myapp INIT= OTHEROBJS="initfile.o mymod.o" |
/demos/trunk/myapp/initfile.c |
---|
0,0 → 1,66 |
/* |
* Project: HARTIK (HA-rd R-eal TI-me K-ernel) |
* |
* Coordinators: Giorgio Buttazzo <giorgio@sssup.it> |
* Gerardo Lamastra <gerardo@sssup.it> |
* |
* Authors : Paolo Gai <pj@hartik.sssup.it> |
* (see authors.txt for full list of hartik's authors) |
* |
* ReTiS Lab (Scuola Superiore S.Anna - Pisa - Italy) |
* |
* http://www.sssup.it |
* http://retis.sssup.it |
* http://hartik.sssup.it |
*/ |
/* |
* Copyright (C) 2000 Paolo Gai |
* |
* This program is free software; you can redistribute it and/or modify |
* it under the terms of the GNU General Public License as published by |
* the Free Software Foundation; either version 2 of the License, or |
* (at your option) any later version. |
* |
* This program is distributed in the hope that it will be useful, |
* but WITHOUT ANY WARRANTY; without even the implied warranty of |
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
* GNU General Public License for more details. |
* |
* You should have received a copy of the GNU General Public License |
* along with this program; if not, write to the Free Software |
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
* |
*/ |
#include "kernel/kern.h" |
#include "mymod.h" |
#include "modules/dummy.h" |
/*+ sysyem tick in us +*/ |
#define TICK 300 |
TIME __kernel_register_levels__(void *arg) |
{ |
struct multiboot_info *mb = (struct multiboot_info *)arg; |
MYMOD_register_level(120); |
dummy_register_level(); |
// periodic timer |
return TICK; |
// one-shot timer |
// return 0 |
} |
TASK __init__(void *arg) |
{ |
struct multiboot_info *mb = (struct multiboot_info *)arg; |
__call_main__(mb); |
return (void *)0; |
} |
/demos/trunk/myapp/myapp.c |
---|
0,0 → 1,55 |
/* |
* Project: S.Ha.R.K. |
* |
* Coordinators: Giorgio Buttazzo <giorgio@sssup.it> |
* |
* Authors : Paolo Gai <pj@hartik.sssup.it> |
* (see authors.txt for full list of hartik's authors) |
* |
* ReTiS Lab (Scuola Superiore S.Anna - Pisa - Italy) |
* |
* http://www.sssup.it |
* http://retis.sssup.it |
* http://shark.sssup.it |
*/ |
/* |
* Copyright (C) 2000 Paolo Gai |
* |
* This program is free software; you can redistribute it and/or modify |
* it under the terms of the GNU General Public License as published by |
* the Free Software Foundation; either version 2 of the License, or |
* (at your option) any later version. |
* |
* This program is distributed in the hope that it will be useful, |
* but WITHOUT ANY WARRANTY; without even the implied warranty of |
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
* GNU General Public License for more details. |
* |
* You should have received a copy of the GNU General Public License |
* along with this program; if not, write to the Free Software |
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
* |
*/ |
// if you want to use some functions, types, task models provided |
// by your new module |
#include "mymod.h" |
// then, include any file you want here |
// then, the classic C-style function |
int main(int argc, char **argv) |
{ |
// ... your stuff here |
return 0; |
} |
/demos/trunk/myapp/readme.txt |
---|
0,0 → 1,7 |
This is a template application, and it DOES NOTHING!!! |
This is only an example package. |
Please refer to the How To Compile reference guide for more informations. |
Paolo |
/demos/trunk/myapp/mymod.h |
---|
0,0 → 1,113 |
/* |
* Project: S.Ha.R.K. |
* |
* Coordinators: Giorgio Buttazzo <giorgio@sssup.it> |
* |
* Authors : Paolo Gai <pj@hartik.sssup.it> |
* (see authors.txt for full list of hartik's authors) |
* |
* ReTiS Lab (Scuola Superiore S.Anna - Pisa - Italy) |
* |
* http://www.sssup.it |
* http://retis.sssup.it |
* http://shark.sssup.it |
*/ |
/* put here a description of the module */ |
/* |
* Copyright (C) 2000 Paolo Gai |
* |
* This program is free software; you can redistribute it and/or modify |
* it under the terms of the GNU General Public License as published by |
* the Free Software Foundation; either version 2 of the License, or |
* (at your option) any later version. |
* |
* This program is distributed in the hope that it will be useful, |
* but WITHOUT ANY WARRANTY; without even the implied warranty of |
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
* GNU General Public License for more details. |
* |
* You should have received a copy of the GNU General Public License |
* along with this program; if not, write to the Free Software |
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
* |
*/ |
#ifndef __MYMOD_H__ |
#define __MYMOD_H__ |
#include <kernel/model.h> |
// maybe you need here some include file |
// then... we define a new Task Model without modifying |
// the standard kernel distribution |
// pick a pclass number not used into include/kernel/model.h |
#define MY_PCLASS 0x0700 |
/* |
maybe a description of the new fields of the Model is useful here |
*/ |
typedef struct { |
TASK_MODEL t; |
int myparameter; |
} MY_TASK_MODEL; |
#define my_task_default_model(m) \ |
task_default_model((m).t,MY_PCLASS), \ |
(m).myparameter = 0 |
#define my_task_def_level(m,l) task_def_level((m).t,l) |
#define my_task_def_arg(m,a) task_def_arg((m).t,a) |
#define my_task_def_stack(m,s) task_def_stack((m).t,s) |
#define my_task_def_stackaddr(m,s) task_def_stackaddr((m).t,s) |
#define my_task_def_group(m,g) task_def_group((m).t,g) |
#define my_task_def_usemath(m) task_def_usemath((m).t) |
#define my_task_def_system(m) task_def_system((m).t) |
#define my_task_def_nokill(m) task_def_nokill((m).t) |
#define my_task_def_ctrl_jet(m) task_def_ctrl_jet((m).t) |
#define my_task_def_myparameter(m,p) (m).myparameter = (p) |
#define my_task_def_joinable(m) task_def_joinable((m).t) |
#define my_task_def_unjoinable(m) task_def_unjoinable((m).t) |
#define my_task_def_trace(m) task_def_trace((m).t) |
#define my_task_def_notrace(m) task_def_notrace((m).t) |
// pick a code and a version not used into the file include/modules/codes.h |
#define MYMOD_LEVELNAME "My new scheduling module" |
#define MYMOD_LEVEL_CODE 999 |
#define MYMOD_LEVEL_VERSION 1 |
// if the module raises some new exception list them here |
// pincking up unused numbers from include/bits/errno.h |
/*+ Registration function: |
int parameter Options to be used in this level instance... +*/ |
void MYMOD_register_level(int parameter); |
/* here you can also put some other functions similar for example |
to the EDF_usedbandwidth() in the file include/modules/edf.h */ |
#endif |
/demos/trunk/orbit/orbit.c |
---|
18,11 → 18,11 |
/* |
------------ |
CVS : $Id: orbit.c,v 1.3 2003-01-07 17:10:17 pj Exp $ |
CVS : $Id: orbit.c,v 1.2 2002-11-11 08:02:15 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.3 $ |
Last update: $Date: 2003-01-07 17:10:17 $ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2002-11-11 08:02:15 $ |
------------ |
*/ |
190,6 → 190,7 |
HARD_TASK_MODEL m; |
char c; /* carattere letto da tastiera */ |
set_exchandler_grx(); |
sys_atrunlevel(my_fine, NULL, RUNLEVEL_BEFORE_EXIT); |
sem_init(&mutex,0,1); |
/demos/trunk/mix/mix.c |
---|
18,11 → 18,11 |
/* |
------------ |
CVS : $Id: mix.c,v 1.3 2003-01-07 17:10:17 pj Exp $ |
CVS : $Id: mix.c,v 1.2 2002-11-11 08:02:43 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.3 $ |
Last update: $Date: 2003-01-07 17:10:17 $ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2002-11-11 08:02:43 $ |
------------ |
*/ |
648,6 → 648,7 |
NRT_TASK_MODEL m2; |
KEY_EVT eva, evx, evs; |
set_exchandler_grx(); |
sys_atrunlevel(byebye, NULL, RUNLEVEL_BEFORE_EXIT); |
/* set the keyboard handler */ |
/demos/trunk/simcity/simcity.c |
---|
76,6 → 76,23 |
cprintf("Ferrari Fabio\n"); |
} |
void demo_exc_handler(int signo, siginfo_t *info, void *extra) |
{ |
struct timespec t; |
grx_close(); |
/* Default action for an kern exception is */ |
kern_cli(); |
ll_gettime(TIME_EXACT, &t), |
kern_printf("\nS.Ha.R.K. Exception raised!!!" |
"\nTime (s:ns) :%ld:%ld" |
"\nException number:%d" |
"\nPID :%d\n", |
t.tv_sec, t.tv_nsec, info->si_value.sival_int, |
info->si_task); |
sys_end(); |
} |
void my_close(void *arg) |
{ |
grx_close(); |
86,9 → 103,20 |
{ |
int i; |
char tl_name[4]; |
struct sigaction action; |
version(); |
/* Init the standard Hartik exception handler */ |
/* Set the signal action */ |
action.sa_flags = SA_SIGINFO; |
action.sa_sigaction = demo_exc_handler; |
action.sa_handler = 0; |
sigfillset(&action.sa_mask); /* we block all the other signals... */ |
if (sigaction(SIGHEXC, &action, NULL) == -1) { |
perror("Error initializing signals..."); |
sys_end(); |
} |
sys_atrunlevel(my_close, NULL, RUNLEVEL_BEFORE_EXIT); |
//resetting kill flags |
/demos/trunk/static/static.c |
---|
18,11 → 18,11 |
/** |
------------ |
CVS : $Id: static.c,v 1.4 2003-01-07 17:10:18 pj Exp $ |
CVS : $Id: static.c,v 1.3 2002-11-11 07:55:13 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.4 $ |
Last update: $Date: 2003-01-07 17:10:18 $ |
Revision: $Revision: 1.3 $ |
Last update: $Date: 2002-11-11 07:55:13 $ |
------------ |
**/ |
130,8 → 130,26 |
} |
static int STATIC_level_accept_task_model(LEVEL l, TASK_MODEL *m) |
{ |
if (m->pclass == STATIC_PCLASS || m->pclass == (STATIC_PCLASS | l)) |
return 0; |
return -1; |
} |
static int STATIC_level_accept_guest_model(LEVEL l, TASK_MODEL *m) |
{ |
return -1; |
} |
static void STATIC_level_status(LEVEL l) |
{ kern_raise(XINVALID_TASK,exec_shadow); } |
/* The scheduler only gets the first task in the queue */ |
static PID STATIC_public_scheduler(LEVEL l) |
static PID STATIC_level_scheduler(LEVEL l) |
{ |
STATIC_level_des *lev = (STATIC_level_des *)(level_table[l]); |
138,8 → 156,14 |
return lev->currenttask; |
} |
static int STATIC_public_create(LEVEL l, PID p, TASK_MODEL *m) |
/* The on-line guarantee is enabled only if the appropriate flag is set... */ |
static int STATIC_level_guarantee(LEVEL l, bandwidth_t *freebandwidth) |
{ |
return 1; |
} |
static int STATIC_task_create(LEVEL l, PID p, TASK_MODEL *m) |
{ |
STATIC_level_des *lev = (STATIC_level_des *)(level_table[l]); |
/* if the STATIC_task_create is called, then the pclass must be a |
147,9 → 171,6 |
STATIC_TASK_MODEL *h = (STATIC_TASK_MODEL *)m; |
if (m->pclass != STATIC_PCLASS) return -1; |
if (m->level != 0 && m->level != l) return -1; |
iq_query_timespec(p, &lev->mytable)->tv_sec = h->offset.tv_sec; |
iq_query_timespec(p, &lev->mytable)->tv_nsec = h->offset.tv_nsec; |
iq_timespec_insert(p,&lev->mytable); |
157,39 → 178,43 |
return 0; /* OK, also if the task cannot be guaranteed... */ |
} |
static void STATIC_public_dispatch(LEVEL l, PID p, int nostop) |
static void STATIC_task_detach(LEVEL l, PID p) |
{ |
} |
static void STATIC_public_epilogue(LEVEL l, PID p) |
static int STATIC_task_eligible(LEVEL l, PID p) |
{ |
return 0; /* if the task p is chosen, it is always eligible */ |
} |
static void STATIC_public_activate(LEVEL l, PID p) |
static void STATIC_task_dispatch(LEVEL l, PID p, int nostop) |
{ |
} |
static void STATIC_public_unblock(LEVEL l, PID p) |
static void STATIC_task_epilogue(LEVEL l, PID p) |
{ |
} |
static void STATIC_public_block(LEVEL l, PID p) |
static void STATIC_task_activate(LEVEL l, PID p) |
{ |
} |
static int STATIC_public_message(LEVEL l, PID p, void *m) |
static void STATIC_task_insert(LEVEL l, PID p) |
{ |
} |
static void STATIC_task_extract(LEVEL l, PID p) |
{ |
} |
static void STATIC_task_endcycle(LEVEL l, PID p) |
{ |
STATIC_level_des *lev = (STATIC_level_des *)(level_table[l]); |
lev->currenttask = NIL; |
jet_update_endcycle(); /* Update the Jet data... */ |
trc_logevent(TRC_ENDCYCLE,&exec_shadow); /* tracer stuff */ |
return 0; |
} |
static void STATIC_public_end(LEVEL l, PID p) |
static void STATIC_task_end(LEVEL l, PID p) |
{ |
STATIC_level_des *lev = (STATIC_level_des *)(level_table[l]); |
202,11 → 227,48 |
iq_insertfirst(p,&freedesc); |
} |
static void STATIC_task_sleep(LEVEL l, PID p) |
{ kern_raise(XINVALID_TASK,exec_shadow); } |
/* Guest Functions |
These functions manages a JOB_TASK_MODEL, that is used to put |
a guest task in the STATIC ready queue. */ |
static int STATIC_guest_create(LEVEL l, PID p, TASK_MODEL *m) |
{ kern_raise(XINVALID_GUEST,exec_shadow); return 0; } |
static void STATIC_guest_detach(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void STATIC_guest_dispatch(LEVEL l, PID p, int nostop) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void STATIC_guest_epilogue(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void STATIC_guest_activate(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void STATIC_guest_insert(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void STATIC_guest_extract(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void STATIC_guest_endcycle(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void STATIC_guest_end(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void STATIC_guest_sleep(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
/* Registration functions */ |
/*+ Registration function: |
int flags the init flags ... see STATIC.h +*/ |
LEVEL STATIC_register_level() |
void STATIC_register_level() |
{ |
LEVEL l; /* the level that we register */ |
STATIC_level_des *lev; /* for readableness only */ |
214,23 → 276,53 |
printk("STATIC_register_level\n"); |
/* request an entry in the level_table */ |
l = level_alloc_descriptor(sizeof(STATIC_level_des)); |
l = level_alloc_descriptor(); |
lev = (STATIC_level_des *)level_table[l]; |
printk(" alloco descrittore %d %d\n",l,(int)sizeof(STATIC_level_des)); |
/* alloc the space needed for the STATIC_level_des */ |
lev = (STATIC_level_des *)kern_alloc(sizeof(STATIC_level_des)); |
printk(" lev=%d\n",(int)lev); |
/* update the level_table with the new entry */ |
level_table[l] = (level_des *)lev; |
/* fill the standard descriptor */ |
lev->l.public_scheduler = STATIC_public_scheduler; |
lev->l.public_create = STATIC_public_create; |
lev->l.public_end = STATIC_public_end; |
lev->l.public_dispatch = STATIC_public_dispatch; |
lev->l.public_epilogue = STATIC_public_epilogue; |
lev->l.public_activate = STATIC_public_activate; |
lev->l.public_unblock = STATIC_public_unblock; |
lev->l.public_block = STATIC_public_block; |
lev->l.public_message = STATIC_public_message; |
strncpy(lev->l.level_name, STATIC_LEVELNAME, MAX_LEVELNAME); |
lev->l.level_code = STATIC_LEVEL_CODE; |
lev->l.level_version = STATIC_LEVEL_VERSION; |
lev->l.level_accept_task_model = STATIC_level_accept_task_model; |
lev->l.level_accept_guest_model = STATIC_level_accept_guest_model; |
lev->l.level_status = STATIC_level_status; |
lev->l.level_scheduler = STATIC_level_scheduler; |
lev->l.level_guarantee = NULL; |
lev->l.task_create = STATIC_task_create; |
lev->l.task_detach = STATIC_task_detach; |
lev->l.task_eligible = STATIC_task_eligible; |
lev->l.task_dispatch = STATIC_task_dispatch; |
lev->l.task_epilogue = STATIC_task_epilogue; |
lev->l.task_activate = STATIC_task_activate; |
lev->l.task_insert = STATIC_task_insert; |
lev->l.task_extract = STATIC_task_extract; |
lev->l.task_endcycle = STATIC_task_endcycle; |
lev->l.task_end = STATIC_task_end; |
lev->l.task_sleep = STATIC_task_sleep; |
lev->l.guest_create = STATIC_guest_create; |
lev->l.guest_detach = STATIC_guest_detach; |
lev->l.guest_dispatch = STATIC_guest_dispatch; |
lev->l.guest_epilogue = STATIC_guest_epilogue; |
lev->l.guest_activate = STATIC_guest_activate; |
lev->l.guest_insert = STATIC_guest_insert; |
lev->l.guest_extract = STATIC_guest_extract; |
lev->l.guest_endcycle = STATIC_guest_endcycle; |
lev->l.guest_end = STATIC_guest_end; |
lev->l.guest_sleep = STATIC_guest_sleep; |
/* fill the STATIC descriptor part */ |
iq_init(&lev->mytable, &freedesc, 0); |
238,8 → 330,6 |
NULL_TIMESPEC(&lev->hp); |
NULL_TIMESPEC(&lev->ref); |
return l; |
} |
void STATIC_start(LEVEL l, struct timespec *h, struct timespec *o) |
248,7 → 338,7 |
struct timespec x; |
kern_cli(); |
kern_gettime(&x); |
ll_gettime(TIME_EXACT, &x); |
lev->hp = *h; |
ADDTIMESPEC(&x,o,&lev->ref); |
/demos/trunk/static/static.h |
---|
20,11 → 20,11 |
/** |
------------ |
CVS : $Id: static.h,v 1.2 2003-01-07 17:10:18 pj Exp $ |
CVS : $Id: static.h,v 1.1.1.1 2002-09-02 09:37:48 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2003-01-07 17:10:18 $ |
Revision: $Revision: 1.1.1.1 $ |
Last update: $Date: 2002-09-02 09:37:48 $ |
------------ |
Static scheduler demo (FIRST Project Hand-off) |
58,6 → 58,7 |
#include <kernel/config.h> |
#include <sys/types.h> |
#include <kernel/types.h> |
#include <modules/codes.h> |
80,6 → 81,10 |
#define STATIC_LEVEL_VERSION 1 |
/* ----------------------------------------------------------------------- |
ELASTIC_HARD_TASK_MODEL: elastic hard Tasks |
----------------------------------------------------------------------- */ |
typedef struct { |
TASK_MODEL t; |
109,7 → 114,7 |
/*+ Registration function: |
int flags Options to be used in this level instance... |
+*/ |
LEVEL STATIC_register_level(void); |
void STATIC_register_level(void); |
void STATIC_start(LEVEL l, struct timespec *h, struct timespec *o); |
/demos/trunk/cash/cash.c |
---|
20,11 → 20,11 |
/** |
------------ |
CVS : $Id: cash.c,v 1.4 2003-01-07 17:10:16 pj Exp $ |
CVS : $Id: cash.c,v 1.3 2002-11-11 07:56:31 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.4 $ |
Last update: $Date: 2003-01-07 17:10:16 $ |
Revision: $Revision: 1.3 $ |
Last update: $Date: 2002-11-11 07:56:31 $ |
------------ |
This file contains the aperiodic server CBS (Total Bandwidth Server) |
60,9 → 60,21 |
#include <kernel/descr.h> |
#include <kernel/var.h> |
#include <kernel/func.h> |
#include <kernel/trace.h> |
/*+ 4 debug purposes +*/ |
#undef CBS_TEST |
#ifdef TESTG |
#include "drivers/glib.h" |
TIME x,oldx; |
extern TIME starttime; |
#endif |
/*+ Status used in the level +*/ |
#define CBSGHD_IDLE APER_STATUS_BASE /*+ waiting the activation +*/ |
#define CBSGHD_ZOMBIE APER_STATUS_BASE+1 /*+ waiting the period end +*/ |
95,7 → 107,6 |
TIME act_period[MAX_PROC]; /*+ actual period of each elastic task: it |
must be less than maxperiod!!! +*/ |
struct timespec request_time[MAX_PROC]; /* used for the response time */ |
TIME last_response_time[MAX_PROC]; /* response time of the last instance */ |
TIME cnormal[MAX_PROC]; /*+ CBSGHD normal computation time +*/ |
262,10 → 273,27 |
job_task_default_model(job, lev->cbsghd_dline[p]); |
job_task_def_yesexc(job); |
level_table[ lev->scheduling_level ]-> |
private_insert(lev->scheduling_level, p, (TASK_MODEL *)&job); |
guest_create(lev->scheduling_level, p, (TASK_MODEL *)&job); |
level_table[ lev->scheduling_level ]-> |
guest_activate(lev->scheduling_level, p); |
} |
static char *CBSGHD_status_to_a(WORD status) |
{ |
if (status < MODULE_STATUS_BASE) |
return status_to_a(status); |
switch (status) { |
case CBSGHD_IDLE : return "CBSGHD_Idle"; |
case CBSGHD_ZOMBIE : return "CBSGHD_Zombie"; |
default : return "CBSGHD_Unknown"; |
} |
} |
/* this is the periodic reactivation of the task... */ |
static void CBSGHD_timer_reactivate(void *par) |
{ |
279,7 → 307,7 |
reactivated */ |
/* request_time represents the time of the last instance release!! */ |
TIMESPEC_ASSIGN(&lev->request_time[p], &lev->reactivation_time[p]); |
TIMESPEC_ASSIGN(&proc_table[p].request_time, &lev->reactivation_time[p]); |
/* If idle=1, then we have to discharge the capacities stored in |
the capacity queue up to the length of the idle interval */ |
287,7 → 315,7 |
TIME interval; |
struct timespec delta; |
lev->idle = 0; |
SUBTIMESPEC(&lev->request_time[p], &lev->start_idle, &delta); |
SUBTIMESPEC(&proc_table[p].request_time, &lev->start_idle, &delta); |
/* length of the idle interval expressed in usec! */ |
interval = TIMESPEC2NANOSEC(&delta) / 1000; |
433,7 → 461,7 |
if (TIMESPEC_A_LT_B(&lev->reactivation_time[p], &lev->cbsghd_dline[p])) { |
/* we delete the reactivation timer */ |
kern_event_delete(lev->reactivation_timer[p]); |
event_delete(lev->reactivation_timer[p]); |
/* repost the event at the next instance deadline... */ |
lev->reactivation_time[p] = lev->cbsghd_dline[p]; |
lev->reactivation_timer[p] = kern_event_post(&lev->reactivation_time[p], |
475,14 → 503,69 |
} |
static PID CBSGHD_public_scheduler(LEVEL l) |
static int CBSGHD_level_accept_task_model(LEVEL l, TASK_MODEL *m) |
{ |
if (m->pclass == ELASTIC_HARD_PCLASS || m->pclass == |
(ELASTIC_HARD_PCLASS | l)) { |
ELASTIC_HARD_TASK_MODEL *s = (ELASTIC_HARD_TASK_MODEL *)m; |
bandwidth_t b1, b2; |
/* kern_printf("accept :ELASTIC TASK found!!!!!!\n"); */ |
b1 = (MAX_BANDWIDTH / s->period) * s->cnormal; |
b2 = (MAX_BANDWIDTH / s->maxperiod) * s->wcet; |
if (s->wcet && s->cnormal && s->period && s->maxperiod && |
s->wcet >= s->cnormal && b1 >= b2) |
return 0; |
/* kern_printf("period: %d maxperiod: %d cnormal: %d wcet: %d, b1: %d b2: |
%d\n", s->period, s->maxperiod, s->cnormal, s->wcet, b1, b2); */ |
} |
return -1; |
} |
static int CBSGHD_level_accept_guest_model(LEVEL l, TASK_MODEL *m) |
{ |
return -1; |
} |
static char *onoff(int i) |
{ |
if (i) |
return "On "; |
else |
return "Off"; |
} |
static void CBSGHD_level_status(LEVEL l) |
{ |
CBSGHD_level_des *lev = (CBSGHD_level_des *)(level_table[l]); |
PID p; |
kern_printf("On-line guarantee : %s\n", |
onoff(lev->flags & CBSGHD_ENABLE_GUARANTEE)); |
kern_printf("Used Bandwidth : %u/%u\n", |
lev->U, MAX_BANDWIDTH); |
for (p=0; p<MAX_PROC; p++) |
if (proc_table[p].task_level == l && proc_table[p].status != FREE ) |
kern_printf("Pid: %2d Name: %10s Period: %9ld Dline: %9ld.%6ld Stat: %s\n", |
p, |
proc_table[p].name, |
lev->period[p], |
lev->cbsghd_dline[p].tv_sec, |
lev->cbsghd_dline[p].tv_nsec/1000, |
CBSGHD_status_to_a(proc_table[p].status)); |
} |
static PID CBSGHD_level_scheduler(LEVEL l) |
{ |
CBSGHD_level_des *lev = (CBSGHD_level_des *)(level_table[l]); |
/* it stores the actual time and set the IDLE flag in order to handle |
the capacity queue discharging!!! */ |
lev->idle = 1; |
kern_gettime(&lev->start_idle); |
ll_gettime(TIME_EXACT, &lev->start_idle); |
/* the CBSGHD don't schedule anything... |
491,7 → 574,7 |
} |
/* The on-line guarantee is enabled only if the appropriate flag is set... */ |
static int CBSGHD_public_guarantee(LEVEL l, bandwidth_t *freebandwidth) |
static int CBSGHD_level_guarantee(LEVEL l, bandwidth_t *freebandwidth) |
{ |
CBSGHD_level_des *lev = (CBSGHD_level_des *)(level_table[l]); |
511,28 → 594,14 |
} |
} |
static int CBSGHD_public_create(LEVEL l, PID p, TASK_MODEL *m) |
static int CBSGHD_task_create(LEVEL l, PID p, TASK_MODEL *m) |
{ |
CBSGHD_level_des *lev = (CBSGHD_level_des *)(level_table[l]); |
ELASTIC_HARD_TASK_MODEL *s; |
bandwidth_t b1, b2; |
if (m->pclass != ELASTIC_HARD_PCLASS) return -1; |
if (m->level != 0 && m->level != l) return -1; |
s = (ELASTIC_HARD_TASK_MODEL *)m; |
/* if the CBSGHD_task_create is called, then the pclass must be a |
valid pclass. */ |
ELASTIC_HARD_TASK_MODEL *s = (ELASTIC_HARD_TASK_MODEL *)m; |
/* kern_printf("accept :ELASTIC TASK found!!!!!!\n"); */ |
b1 = (MAX_BANDWIDTH / s->period) * s->cnormal; |
b2 = (MAX_BANDWIDTH / s->maxperiod) * s->wcet; |
if (!(s->wcet && s->cnormal && s->period && s->maxperiod && |
s->wcet >= s->cnormal && b1 >= b2) ) |
return -1; |
/* kern_printf("period: %d maxperiod: %d cnormal: %d wcet: %d, b1: %d b2: |
%d\n", s->period, s->maxperiod, s->cnormal, s->wcet, b1, b2); */ |
/* now we know that m is a valid model */ |
/* Enable wcet check */ |
proc_table[p].avail_time = 0; |
proc_table[p].wcet = s->wcet; |
542,9 → 611,8 |
lev->maxperiod[p] = s->maxperiod; |
lev->cnormal[p] = s->cnormal; |
NULL_TIMESPEC(&lev->cbsghd_dline[p]); |
NULL_TIMESPEC(&lev->request_time[p]); |
/* update the bandwidth... */ |
if (lev->flags & CBSGHD_ENABLE_GUARANTEE) { |
bandwidth_t b; |
564,7 → 632,7 |
return 0; /* OK, also if the task cannot be guaranteed... */ |
} |
static void CBSGHD_public_detach(LEVEL l, PID p) |
static void CBSGHD_task_detach(LEVEL l, PID p) |
{ |
/* the CBSGHD level doesn't introduce any dinamic allocated new field. |
we have only to reset the NO_GUARANTEE FIELD and decrement the allocated |
580,15 → 648,20 |
} |
static void CBSGHD_public_dispatch(LEVEL l, PID p, int nostop) |
static int CBSGHD_task_eligible(LEVEL l, PID p) |
{ |
return 0; /* if the task p is chosen, it is always eligible */ |
} |
static void CBSGHD_task_dispatch(LEVEL l, PID p, int nostop) |
{ |
CBSGHD_level_des *lev = (CBSGHD_level_des *)(level_table[l]); |
level_table[ lev->scheduling_level ]-> |
private_dispatch(lev->scheduling_level,p,nostop); |
guest_dispatch(lev->scheduling_level,p,nostop); |
} |
static void CBSGHD_public_epilogue(LEVEL l, PID p) |
static void CBSGHD_task_epilogue(LEVEL l, PID p) |
{ |
CBSGHD_level_des *lev = (CBSGHD_level_des *)(level_table[l]); |
JOB_TASK_MODEL job; |
597,7 → 670,7 |
if ( proc_table[p].avail_time <= 0) { |
/* we kill the current activation */ |
level_table[ lev->scheduling_level ]-> |
private_extract(lev->scheduling_level, p); |
guest_end(lev->scheduling_level, p); |
/* we modify the deadline */ |
CBSGHD_avail_time_check(lev, p); |
606,7 → 679,9 |
job_task_default_model(job, lev->cbsghd_dline[p]); |
job_task_def_yesexc(job); |
level_table[ lev->scheduling_level ]-> |
private_insert(lev->scheduling_level, p, (TASK_MODEL *)&job); |
guest_create(lev->scheduling_level, p, (TASK_MODEL *)&job); |
level_table[ lev->scheduling_level ]-> |
guest_activate(lev->scheduling_level, p); |
// kern_printf("epil : dl %d per %d p %d |\n", |
// lev->cbsghd_dline[p].tv_nsec/1000,lev->period[p],p); |
615,14 → 690,14 |
/* the task has been preempted. it returns into the ready queue by |
calling the guest_epilogue... */ |
level_table[ lev->scheduling_level ]-> |
private_epilogue(lev->scheduling_level,p); |
guest_epilogue(lev->scheduling_level,p); |
} |
static void CBSGHD_public_activate(LEVEL l, PID p) |
static void CBSGHD_task_activate(LEVEL l, PID p) |
{ |
CBSGHD_level_des *lev = (CBSGHD_level_des *)(level_table[l]); |
kern_gettime(&lev->request_time[p]); |
ll_gettime(TIME_EXACT, &proc_table[p].request_time); |
/* If idle=1, then we have to discharge the capacities stored in |
the capacity queue up to the length of the idle interval */ |
630,7 → 705,7 |
TIME interval; |
struct timespec delta; |
lev->idle = 0; |
SUBTIMESPEC(&lev->request_time[p], &lev->start_idle, &delta); |
SUBTIMESPEC(&proc_table[p].request_time, &lev->start_idle, &delta); |
/* length of the idle interval expressed in usec! */ |
interval = TIMESPEC2NANOSEC(&delta) / 1000; |
650,7 → 725,7 |
} |
} |
CBSGHD_activation(lev, p, &lev->request_time[p]); |
CBSGHD_activation(lev, p, &proc_table[p].request_time); |
/* check the constraint on the maximum period permitted... */ |
669,31 → 744,31 |
// kern_printf("act : %d %d |",lev->cbsghd_dline[p].tv_nsec/1000,p); |
} |
static void CBSGHD_public_unblock(LEVEL l, PID p) |
static void CBSGHD_task_insert(LEVEL l, PID p) |
{ |
printk("CBSGHD_task_insert\n"); |
kern_raise(XINVALID_TASK,p); |
} |
static void CBSGHD_public_block(LEVEL l, PID p) |
static void CBSGHD_task_extract(LEVEL l, PID p) |
{ |
printk("CBSGHD_task_extract\n"); |
kern_raise(XINVALID_TASK,p); |
} |
static int CBSGHD_public_message(LEVEL l, PID p, void *m) |
static void CBSGHD_task_endcycle(LEVEL l, PID p) |
{ |
CBSGHD_level_des *lev = (CBSGHD_level_des *)(level_table[l]); |
struct timespec act_time, res; |
/* It computes the response time of the current instance... */ |
kern_gettime(&act_time); |
SUBTIMESPEC(&act_time, &lev->request_time[p], &res); |
ll_gettime(TIME_EXACT, &act_time); |
SUBTIMESPEC(&act_time, &proc_table[p].request_time, &res); |
/* response time expressed in usec! */ |
lev->last_response_time[p] = TIMESPEC2NANOSEC(&res) / 1000; |
level_table[ lev->scheduling_level ]-> |
private_extract(lev->scheduling_level,p); |
guest_end(lev->scheduling_level,p); |
/* A spare capacity is inserted in the capacity queue!! */ |
704,14 → 779,9 |
proc_table[p].status = CBSGHD_IDLE; |
jet_update_endcycle(); /* Update the Jet data... */ |
trc_logevent(TRC_ENDCYCLE,&exec_shadow); /* tracer stuff */ |
return 0; |
} |
static void CBSGHD_public_end(LEVEL l, PID p) |
static void CBSGHD_task_end(LEVEL l, PID p) |
{ |
CBSGHD_level_des *lev = (CBSGHD_level_des *)(level_table[l]); |
725,10 → 795,10 |
} |
level_table[ lev->scheduling_level ]-> |
private_extract(lev->scheduling_level,p); |
guest_end(lev->scheduling_level,p); |
/* we delete the reactivation timer */ |
kern_event_delete(lev->reactivation_timer[p]); |
event_delete(lev->reactivation_timer[p]); |
lev->reactivation_timer[p] = -1; |
740,11 → 810,48 |
(void *)p); |
} |
static void CBSGHD_task_sleep(LEVEL l, PID p) |
{ |
printk("CBSGHD_task_sleep\n"); |
kern_raise(XINVALID_TASK,p); |
} |
static int CBSGHD_guest_create(LEVEL l, PID p, TASK_MODEL *m) |
{ kern_raise(XINVALID_GUEST,exec_shadow); return 0; } |
static void CBSGHD_guest_detach(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void CBSGHD_guest_dispatch(LEVEL l, PID p, int nostop) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void CBSGHD_guest_epilogue(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void CBSGHD_guest_activate(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void CBSGHD_guest_insert(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void CBSGHD_guest_extract(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void CBSGHD_guest_endcycle(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void CBSGHD_guest_end(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void CBSGHD_guest_sleep(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
/* Registration functions */ |
/*+ Registration function: |
int flags the init flags ... see CBS.h +*/ |
LEVEL CBSGHD_register_level(int flags, LEVEL master) |
void CBSGHD_register_level(int flags, LEVEL master) |
{ |
LEVEL l; /* the level that we register */ |
CBSGHD_level_des *lev; /* for readableness only */ |
753,35 → 860,60 |
printk("CBSGHD_register_level\n"); |
/* request an entry in the level_table */ |
l = level_alloc_descriptor(sizeof(CBSGHD_level_des)); |
l = level_alloc_descriptor(); |
lev = (CBSGHD_level_des *)level_table[l]; |
printk(" alloco descrittore %d %d\n",l,sizeof(CBSGHD_level_des)); |
/* alloc the space needed for the CBSGHD_level_des */ |
lev = (CBSGHD_level_des *)kern_alloc(sizeof(CBSGHD_level_des)); |
printk(" lev=%d\n",(int)lev); |
/* update the level_table with the new entry */ |
level_table[l] = (level_des *)lev; |
/* fill the standard descriptor */ |
lev->l.public_scheduler = CBSGHD_public_scheduler; |
strncpy(lev->l.level_name, CBSGHD_LEVELNAME, MAX_LEVELNAME); |
lev->l.level_code = CBSGHD_LEVEL_CODE; |
lev->l.level_version = CBSGHD_LEVEL_VERSION; |
lev->l.level_accept_task_model = CBSGHD_level_accept_task_model; |
lev->l.level_accept_guest_model = CBSGHD_level_accept_guest_model; |
lev->l.level_status = CBSGHD_level_status; |
lev->l.level_scheduler = CBSGHD_level_scheduler; |
if (flags & CBSGHD_ENABLE_GUARANTEE) |
lev->l.public_guarantee = CBSGHD_public_guarantee; |
lev->l.level_guarantee = CBSGHD_level_guarantee; |
else |
lev->l.public_guarantee = NULL; |
lev->l.level_guarantee = NULL; |
lev->l.public_create = CBSGHD_public_create; |
lev->l.public_detach = CBSGHD_public_detach; |
lev->l.public_end = CBSGHD_public_end; |
lev->l.public_dispatch = CBSGHD_public_dispatch; |
lev->l.public_epilogue = CBSGHD_public_epilogue; |
lev->l.public_activate = CBSGHD_public_activate; |
lev->l.public_unblock = CBSGHD_public_unblock; |
lev->l.public_block = CBSGHD_public_block; |
lev->l.public_message = CBSGHD_public_message; |
lev->l.task_create = CBSGHD_task_create; |
lev->l.task_detach = CBSGHD_task_detach; |
lev->l.task_eligible = CBSGHD_task_eligible; |
lev->l.task_dispatch = CBSGHD_task_dispatch; |
lev->l.task_epilogue = CBSGHD_task_epilogue; |
lev->l.task_activate = CBSGHD_task_activate; |
lev->l.task_insert = CBSGHD_task_insert; |
lev->l.task_extract = CBSGHD_task_extract; |
lev->l.task_endcycle = CBSGHD_task_endcycle; |
lev->l.task_end = CBSGHD_task_end; |
lev->l.task_sleep = CBSGHD_task_sleep; |
lev->l.guest_create = CBSGHD_guest_create; |
lev->l.guest_detach = CBSGHD_guest_detach; |
lev->l.guest_dispatch = CBSGHD_guest_dispatch; |
lev->l.guest_epilogue = CBSGHD_guest_epilogue; |
lev->l.guest_activate = CBSGHD_guest_activate; |
lev->l.guest_insert = CBSGHD_guest_insert; |
lev->l.guest_extract = CBSGHD_guest_extract; |
lev->l.guest_endcycle = CBSGHD_guest_endcycle; |
lev->l.guest_end = CBSGHD_guest_end; |
lev->l.guest_sleep = CBSGHD_guest_sleep; |
/* fill the CBSGHD descriptor part */ |
for (i=0; i<MAX_PROC; i++) { |
NULL_TIMESPEC(&lev->cbsghd_dline[i]); |
lev->period[i] = 0; |
NULL_TIMESPEC(&lev->request_time[i]); |
lev->last_response_time[i] = 0; |
NULL_TIMESPEC(&lev->reactivation_time[i]); |
lev->reactivation_timer[i] = -1; |
795,8 → 927,6 |
lev->scheduling_level = master; |
lev->flags = flags & 0x07; |
return l; |
} |
803,7 → 933,6 |
int CBSGHD_get_response_time(LEVEL l, PID p) |
{ |
CBSGHD_level_des *lev = (CBSGHD_level_des *)(level_table[l]); |
return lev->last_response_time[p]; |
} |
811,7 → 940,10 |
bandwidth_t CBSGHD_usedbandwidth(LEVEL l) |
{ |
CBSGHD_level_des *lev = (CBSGHD_level_des *)(level_table[l]); |
return lev->U; |
if (lev->l.level_code == CBSGHD_LEVEL_CODE && |
lev->l.level_version == CBSGHD_LEVEL_VERSION) |
return lev->U; |
else |
return 0; |
} |
/demos/trunk/cash/cash.h |
---|
20,11 → 20,11 |
/** |
------------ |
CVS : $Id: cash.h,v 1.2 2003-01-07 17:10:16 pj Exp $ |
CVS : $Id: cash.h,v 1.1.1.1 2002-09-02 09:37:41 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2003-01-07 17:10:16 $ |
Revision: $Revision: 1.1.1.1 $ |
Last update: $Date: 2002-09-02 09:37:41 $ |
------------ |
This file contains the server CBSHD (CASH Algorithm) |
97,6 → 97,7 |
#include <kernel/config.h> |
#include <sys/types.h> |
#include <kernel/types.h> |
#include <modules/codes.h> |
165,10 → 166,8 |
int flags Options to be used in this level instance... |
LEVEL master the level that must be used as master level for the |
CBSGHD tasks |
returns the level number at which the module has been registered. |
+*/ |
LEVEL CBSGHD_register_level(int flags, LEVEL master); |
void CBSGHD_register_level(int flags, LEVEL master); |
/*+ Returns the used bandwidth of a level +*/ |
bandwidth_t CBSGHD_usedbandwidth(LEVEL l); |
/demos/trunk/edfact/edfact.c |
---|
18,11 → 18,11 |
/** |
------------ |
CVS : $Id: edfact.c,v 1.4 2003-01-07 17:10:16 pj Exp $ |
CVS : $Id: edfact.c,v 1.3 2002-11-11 07:55:55 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.4 $ |
Last update: $Date: 2003-01-07 17:10:16 $ |
Revision: $Revision: 1.3 $ |
Last update: $Date: 2002-11-11 07:55:55 $ |
------------ |
**/ |
95,14 → 95,14 |
static void EDFACT_timer_deadline(void *par); |
static void EDFACT_internal_activate(EDFACT_level_des *lev, PID p, |
struct timespec *t) |
static void EDFACT_internal_activate(EDFACT_level_des *lev, PID p) |
{ |
struct timespec *temp; |
temp = iq_query_timespec(p, &lev->ready); |
TIMESPEC_ASSIGN(temp,t); |
TIMESPEC_ASSIGN(temp, |
&proc_table[p].request_time); |
ADDUSEC2TIMESPEC(lev->period[p], temp); |
TIMESPEC_ASSIGN(&lev->deadline_timespec[p], |
116,6 → 116,18 |
proc_table[p].control |= CONTROL_CAP; |
} |
static char *EDFACT_status_to_a(WORD status) |
{ |
if (status < MODULE_STATUS_BASE) |
return status_to_a(status); |
switch (status) { |
case EDFACT_READY : return "EDFACT_Ready"; |
case EDFACT_IDLE : return "EDFACT_Idle"; |
default : return "EDFACT_Unknown"; |
} |
} |
static void EDFACT_timer_deadline(void *par) |
{ |
PID p = (PID) par; |
127,8 → 139,10 |
case EDFACT_IDLE: |
edfact_printf("I%d",p); |
EDFACT_internal_activate(lev,p, &lev->deadline_timespec[p]); |
*iq_query_timespec(p, &lev->ready) = proc_table[p].request_time; |
EDFACT_internal_activate(lev,p); |
event_need_reschedule(); |
break; |
159,17 → 173,93 |
kern_raise(XDEADLINE_MISS,p); |
} |
static int EDFACT_level_accept_task_model(LEVEL l, TASK_MODEL *m) |
{ |
if (m->pclass == HARD_PCLASS || m->pclass == (HARD_PCLASS | l)) { |
HARD_TASK_MODEL *h = (HARD_TASK_MODEL *)m; |
if (h->wcet && h->mit && h->periodicity == PERIODIC) |
return 0; |
} |
return -1; |
} |
static int EDFACT_level_accept_guest_model(LEVEL l, TASK_MODEL *m) |
{ |
if (m->pclass == JOB_PCLASS || m->pclass == (JOB_PCLASS | l)) |
return 0; |
else |
return -1; |
} |
static char *onoff(int i) |
{ |
if (i) |
return "On "; |
else |
return "Off"; |
} |
static void EDFACT_level_status(LEVEL l) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
PID p = iq_query_first(&lev->ready); |
kern_printf("On-line guarantee : %s\n", |
onoff(lev->flags & EDFACT_ENABLE_GUARANTEE)); |
kern_printf("Used Bandwidth : %u/%u\n", |
lev->U, MAX_BANDWIDTH); |
while (p != NIL) { |
if ((proc_table[p].pclass) == JOB_PCLASS) |
kern_printf("Pid: %2d (GUEST)\n", p); |
else |
kern_printf("Pid: %2d Name: %10s %s: %9d Dline: %9d.%6d Stat: %s\n", |
p, |
proc_table[p].name, |
"Period ", |
lev->period[p], |
iq_query_timespec(p, &lev->ready)->tv_sec, |
iq_query_timespec(p, &lev->ready)->tv_nsec/1000, |
EDFACT_status_to_a(proc_table[p].status)); |
p = iq_query_next(p, &lev->ready); |
} |
for (p=0; p<MAX_PROC; p++) |
if (proc_table[p].task_level == l && proc_table[p].status != EDFACT_READY |
&& proc_table[p].status != FREE ) |
kern_printf("Pid: %2d Name: %10s %s: %9d Dline: %9d.%6d Stat: %s\n", |
p, |
proc_table[p].name, |
"Period ", |
lev->period[p], |
iq_query_timespec(p, &lev->ready)->tv_sec, |
iq_query_timespec(p, &lev->ready)->tv_nsec/1000, |
EDFACT_status_to_a(proc_table[p].status)); |
} |
/* The scheduler only gets the first task in the queue */ |
static PID EDFACT_public_scheduler(LEVEL l) |
static PID EDFACT_level_scheduler(LEVEL l) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
/* { // print 4 dbg the ready queue |
PID p= lev->ready; |
kern_printf("(s"); |
while (p != NIL) { |
kern_printf("%d ",p); |
p = proc_table[p].next; |
} |
kern_printf(") "); |
} |
*/ |
return iq_query_first(&lev->ready); |
} |
/* The on-line guarantee is enabled only if the appropriate flag is set... */ |
static int EDFACT_public_guarantee(LEVEL l, bandwidth_t *freebandwidth) |
static int EDFACT_level_guarantee(LEVEL l, bandwidth_t *freebandwidth) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
187,17 → 277,14 |
} |
static int EDFACT_public_create(LEVEL l, PID p, TASK_MODEL *m) |
static int EDFACT_task_create(LEVEL l, PID p, TASK_MODEL *m) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
HARD_TASK_MODEL *h; |
/* if the EDFACT_task_create is called, then the pclass must be a |
valid pclass. */ |
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; |
/* now we know that m is a valid model */ |
HARD_TASK_MODEL *h = (HARD_TASK_MODEL *)m; |
lev->period[p] = h->mit; |
239,7 → 326,7 |
return 0; /* OK, also if the task cannot be guaranteed... */ |
} |
static void EDFACT_public_detach(LEVEL l, PID p) |
static void EDFACT_task_detach(LEVEL l, PID p) |
{ |
/* the EDFACT level doesn't introduce any dinamic allocated new field. |
we have only to reset the NO_GUARANTEE FIELD and decrement the allocated |
253,8 → 340,13 |
lev->U -= (MAX_BANDWIDTH / lev->period[p]) * proc_table[p].wcet; |
} |
static void EDFACT_public_dispatch(LEVEL l, PID p, int nostop) |
static int EDFACT_task_eligible(LEVEL l, PID p) |
{ |
return 0; /* if the task p is chosen, it is always eligible */ |
} |
static void EDFACT_task_dispatch(LEVEL l, PID p, int nostop) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
/* the task state is set EXE by the scheduler() |
263,7 → 355,7 |
iq_extract(p, &lev->ready); |
} |
static void EDFACT_public_epilogue(LEVEL l, PID p) |
static void EDFACT_task_epilogue(LEVEL l, PID p) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
280,10 → 372,9 |
proc_table[p].status = EDFACT_READY; |
} |
static void EDFACT_public_activate(LEVEL l, PID p) |
static void EDFACT_task_activate(LEVEL l, PID p) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
struct timespec t; |
/* Test if we are trying to activate a non sleeping task */ |
/* save activation (only if needed... */ |
293,9 → 384,10 |
return; |
} |
kern_gettime(&t); |
EDFACT_internal_activate(lev,p, &t); |
ll_gettime(TIME_EXACT, &proc_table[p].request_time); |
EDFACT_internal_activate(lev,p); |
/* Set the deadline timer */ |
lev->deadline_timer[p] = kern_event_post(&lev->deadline_timespec[p], |
EDFACT_timer_deadline, |
303,7 → 395,7 |
} |
static void EDFACT_public_unblock(LEVEL l, PID p) |
static void EDFACT_task_insert(LEVEL l, PID p) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
312,15 → 404,15 |
iq_timespec_insert(p,&lev->ready); |
} |
static void EDFACT_public_block(LEVEL l, PID p) |
static void EDFACT_task_extract(LEVEL l, PID p) |
{ |
} |
static int EDFACT_public_message(LEVEL l, PID p, void *m) |
static void EDFACT_task_endcycle(LEVEL l, PID p) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
struct timespec t; |
/* we reset the capacity counters... */ |
proc_table[p].avail_time = proc_table[p].wcet; |
331,14 → 423,15 |
lev->nact[p]--; |
/* see also EDFACT_timer_deadline */ |
kern_gettime(&t); |
EDFACT_internal_activate(lev,p, &t); |
ll_gettime(TIME_EXACT, &proc_table[p].request_time); |
EDFACT_internal_activate(lev,p); |
/* check if the deadline has already expired */ |
if (TIMESPEC_A_LT_B(iq_query_timespec(p, &lev->ready), &schedule_time)) { |
/* count the deadline miss */ |
lev->dline_miss[p]++; |
kern_event_delete(lev->deadline_timer[p]); |
event_delete(lev->deadline_timer[p]); |
} |
} |
349,16 → 442,11 |
proc_table[p].status = EDFACT_IDLE; |
/* when the deadline timer fire, it recognize the situation and set |
correctly all the stuffs (like reactivation, etc... ) */ |
correctly all the stuffs (like reactivation, request_time, etc... ) */ |
} |
jet_update_endcycle(); /* Update the Jet data... */ |
trc_logevent(TRC_ENDCYCLE,&exec_shadow); /* tracer stuff */ |
return 0; |
} |
static void EDFACT_public_end(LEVEL l, PID p) |
static void EDFACT_task_end(LEVEL l, PID p) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
372,28 → 460,26 |
if (lev->deadline_timer[p] != -1) { |
edfact_printf("²%d",p); |
kern_event_delete(lev->deadline_timer[p]); |
event_delete(lev->deadline_timer[p]); |
} |
} |
static void EDFACT_task_sleep(LEVEL l, PID p) |
{ kern_raise(XINVALID_TASK,exec_shadow); } |
/* Guest Functions |
These functions manages a JOB_TASK_MODEL, that is used to put |
a guest task in the EDFACT ready queue. */ |
static void EDFACT_private_insert(LEVEL l, PID p, TASK_MODEL *m) |
static int EDFACT_guest_create(LEVEL l, PID p, TASK_MODEL *m) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
JOB_TASK_MODEL *job = (JOB_TASK_MODEL *)m; |
JOB_TASK_MODEL *job; |
/* if the EDFACT_guest_create is called, then the pclass must be a |
valid pclass. */ |
if (m->pclass != JOB_PCLASS || (m->level != 0 && m->level != l) ) { |
kern_raise(XINVALID_TASK, p); |
return; |
} |
job = (JOB_TASK_MODEL *)m; |
TIMESPEC_ASSIGN(iq_query_timespec(p, &lev->ready), &job->deadline); |
lev->deadline_timer[p] = -1; |
403,25 → 489,26 |
if (job->noraiseexc) |
lev->flag[p] = EDFACT_FLAG_NORAISEEXC; |
else { |
else |
lev->flag[p] = 0; |
lev->deadline_timer[p] = kern_event_post(iq_query_timespec(p, &lev->ready), |
EDFACT_timer_guest_deadline, |
(void *)p); |
} |
lev->period[p] = job->period; |
/* Insert task in the correct position */ |
iq_timespec_insert(p,&lev->ready); |
proc_table[p].status = EDFACT_READY; |
/* there is no bandwidth guarantee at this level, it is performed |
by the level that inserts guest tasks... */ |
return 0; /* OK, also if the task cannot be guaranteed... */ |
} |
static void EDFACT_private_dispatch(LEVEL l, PID p, int nostop) |
static void EDFACT_guest_detach(LEVEL l, PID p) |
{ |
/* the EDFACT level doesn't introduce any dinamic allocated new field. |
No guarantee is performed on guest tasks... so we don't have to reset |
the NO_GUARANTEE FIELD */ |
} |
static void EDFACT_guest_dispatch(LEVEL l, PID p, int nostop) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
/* the task state is set to EXE by the scheduler() |
430,7 → 517,7 |
iq_extract(p, &lev->ready); |
} |
static void EDFACT_private_epilogue(LEVEL l, PID p) |
static void EDFACT_guest_epilogue(LEVEL l, PID p) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
439,10 → 526,42 |
proc_table[p].status = EDFACT_READY; |
} |
static void EDFACT_private_extract(LEVEL l, PID p) |
static void EDFACT_guest_activate(LEVEL l, PID p) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
/* Insert task in the correct position */ |
iq_timespec_insert(p,&lev->ready); |
proc_table[p].status = EDFACT_READY; |
/* Set the deadline timer */ |
if (!(lev->flag[p] & EDFACT_FLAG_NORAISEEXC)) |
lev->deadline_timer[p] = kern_event_post(iq_query_timespec(p, &lev->ready), |
EDFACT_timer_guest_deadline, |
(void *)p); |
} |
static void EDFACT_guest_insert(LEVEL l, PID p) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
/* Insert task in the correct position */ |
iq_timespec_insert(p,&lev->ready); |
proc_table[p].status = EDFACT_READY; |
} |
static void EDFACT_guest_extract(LEVEL l, PID p) |
{ |
} |
static void EDFACT_guest_endcycle(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void EDFACT_guest_end(LEVEL l, PID p) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
//kern_printf("EDFACT_guest_end: dline timer %d\n",lev->deadline_timer[p]); |
if (proc_table[p].status == EDFACT_READY) |
{ |
453,17 → 572,20 |
/* we remove the deadline timer, because the slice is finished */ |
if (lev->deadline_timer[p] != NIL) { |
// kern_printf("EDFACT_guest_end: dline timer %d\n",lev->deadline_timer[p]); |
kern_event_delete(lev->deadline_timer[p]); |
event_delete(lev->deadline_timer[p]); |
lev->deadline_timer[p] = NIL; |
} |
} |
static void EDFACT_guest_sleep(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
/* Registration functions */ |
/*+ Registration function: |
int flags the init flags ... see EDFACT.h +*/ |
LEVEL EDFACT_register_level(int flags) |
void EDFACT_register_level(int flags) |
{ |
LEVEL l; /* the level that we register */ |
EDFACT_level_des *lev; /* for readableness only */ |
472,33 → 594,56 |
printk("EDFACT_register_level\n"); |
/* request an entry in the level_table */ |
l = level_alloc_descriptor(sizeof(EDFACT_level_des)); |
l = level_alloc_descriptor(); |
lev = (EDFACT_level_des *)level_table[l]; |
printk(" alloco descrittore %d %d\n",l,(int)sizeof(EDFACT_level_des)); |
/* alloc the space needed for the EDFACT_level_des */ |
lev = (EDFACT_level_des *)kern_alloc(sizeof(EDFACT_level_des)); |
printk(" lev=%d\n",(int)lev); |
/* update the level_table with the new entry */ |
level_table[l] = (level_des *)lev; |
/* fill the standard descriptor */ |
lev->l.private_insert = EDFACT_private_insert; |
lev->l.private_extract = EDFACT_private_extract; |
lev->l.private_dispatch = EDFACT_private_dispatch; |
lev->l.private_epilogue = EDFACT_private_epilogue; |
strncpy(lev->l.level_name, EDFACT_LEVELNAME, MAX_LEVELNAME); |
lev->l.level_code = EDFACT_LEVEL_CODE; |
lev->l.level_version = EDFACT_LEVEL_VERSION; |
lev->l.public_scheduler = EDFACT_public_scheduler; |
lev->l.level_accept_task_model = EDFACT_level_accept_task_model; |
lev->l.level_accept_guest_model = EDFACT_level_accept_guest_model; |
lev->l.level_status = EDFACT_level_status; |
lev->l.level_scheduler = EDFACT_level_scheduler; |
if (flags & EDFACT_ENABLE_GUARANTEE) |
lev->l.public_guarantee = EDFACT_public_guarantee; |
lev->l.level_guarantee = EDFACT_level_guarantee; |
else |
lev->l.public_guarantee = NULL; |
lev->l.public_create = EDFACT_public_create; |
lev->l.public_detach = EDFACT_public_detach; |
lev->l.public_end = EDFACT_public_end; |
lev->l.public_dispatch = EDFACT_public_dispatch; |
lev->l.public_epilogue = EDFACT_public_epilogue; |
lev->l.public_activate = EDFACT_public_activate; |
lev->l.public_unblock = EDFACT_public_unblock; |
lev->l.public_block = EDFACT_public_block; |
lev->l.public_message = EDFACT_public_message; |
lev->l.level_guarantee = NULL; |
lev->l.task_create = EDFACT_task_create; |
lev->l.task_detach = EDFACT_task_detach; |
lev->l.task_eligible = EDFACT_task_eligible; |
lev->l.task_dispatch = EDFACT_task_dispatch; |
lev->l.task_epilogue = EDFACT_task_epilogue; |
lev->l.task_activate = EDFACT_task_activate; |
lev->l.task_insert = EDFACT_task_insert; |
lev->l.task_extract = EDFACT_task_extract; |
lev->l.task_endcycle = EDFACT_task_endcycle; |
lev->l.task_end = EDFACT_task_end; |
lev->l.task_sleep = EDFACT_task_sleep; |
lev->l.guest_create = EDFACT_guest_create; |
lev->l.guest_detach = EDFACT_guest_detach; |
lev->l.guest_dispatch = EDFACT_guest_dispatch; |
lev->l.guest_epilogue = EDFACT_guest_epilogue; |
lev->l.guest_activate = EDFACT_guest_activate; |
lev->l.guest_insert = EDFACT_guest_insert; |
lev->l.guest_extract = EDFACT_guest_extract; |
lev->l.guest_endcycle = EDFACT_guest_endcycle; |
lev->l.guest_end = EDFACT_guest_end; |
lev->l.guest_sleep = EDFACT_guest_sleep; |
/* fill the EDFACT descriptor part */ |
for(i=0; i<MAX_PROC; i++) { |
lev->period[i] = 0; |
512,15 → 657,16 |
iq_init(&lev->ready,&freedesc, 0); |
lev->flags = flags & 0x07; |
lev->U = 0; |
return l; |
} |
bandwidth_t EDFACT_usedbandwidth(LEVEL l) |
{ |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
return lev->U; |
if (lev->l.level_code == EDFACT_LEVEL_CODE && |
lev->l.level_version == EDFACT_LEVEL_VERSION) |
return lev->U; |
else |
return 0; |
} |
int EDFACT_get_dline_miss(PID p) |
527,8 → 673,11 |
{ |
LEVEL l = proc_table[p].task_level; |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
return lev->dline_miss[p]; |
if (lev->l.level_code == EDFACT_LEVEL_CODE && |
lev->l.level_version == EDFACT_LEVEL_VERSION) |
return lev->dline_miss[p]; |
else |
return -1; |
} |
int EDFACT_get_wcet_miss(PID p) |
535,8 → 684,11 |
{ |
LEVEL l = proc_table[p].task_level; |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
return lev->wcet_miss[p]; |
if (lev->l.level_code == EDFACT_LEVEL_CODE && |
lev->l.level_version == EDFACT_LEVEL_VERSION) |
return lev->wcet_miss[p]; |
else |
return -1; |
} |
int EDFACT_get_nact(PID p) |
543,8 → 695,11 |
{ |
LEVEL l = proc_table[p].task_level; |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
return lev->nact[p]; |
if (lev->l.level_code == EDFACT_LEVEL_CODE && |
lev->l.level_version == EDFACT_LEVEL_VERSION) |
return lev->nact[p]; |
else |
return -1; |
} |
int EDFACT_reset_dline_miss(PID p) |
551,9 → 706,14 |
{ |
LEVEL l = proc_table[p].task_level; |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
lev->dline_miss[p] = 0; |
return 0; |
if (lev->l.level_code == EDFACT_LEVEL_CODE && |
lev->l.level_version == EDFACT_LEVEL_VERSION) |
{ |
lev->dline_miss[p] = 0; |
return 0; |
} |
else |
return -1; |
} |
int EDFACT_reset_wcet_miss(PID p) |
560,8 → 720,13 |
{ |
LEVEL l = proc_table[p].task_level; |
EDFACT_level_des *lev = (EDFACT_level_des *)(level_table[l]); |
lev->wcet_miss[p] = 0; |
return 0; |
if (lev->l.level_code == EDFACT_LEVEL_CODE && |
lev->l.level_version == EDFACT_LEVEL_VERSION) |
{ |
lev->wcet_miss[p] = 0; |
return 0; |
} |
else |
return -1; |
} |
/demos/trunk/edfact/edfact.h |
---|
20,11 → 20,11 |
/** |
------------ |
CVS : $Id: edfact.h,v 1.2 2003-01-07 17:10:16 pj Exp $ |
CVS : $Id: edfact.h,v 1.1.1.1 2002-09-02 09:37:41 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2003-01-07 17:10:16 $ |
Revision: $Revision: 1.1.1.1 $ |
Last update: $Date: 2002-09-02 09:37:41 $ |
------------ |
This file contains the server EDFACT (EDF with pending activations) |
103,6 → 103,7 |
#include <kernel/config.h> |
#include <sys/types.h> |
#include <kernel/types.h> |
#include <modules/codes.h> |
131,10 → 132,8 |
/*+ Registration function: |
int flags Options to be used in this level instance... |
returns the level number at which the module has been registered. |
+*/ |
LEVEL EDFACT_register_level(int flags); |
void EDFACT_register_level(int flags); |
/*+ Returns the used bandwidth of a level +*/ |
bandwidth_t EDFACT_usedbandwidth(LEVEL l); |
/demos/trunk/slsh/slsh.c |
---|
20,11 → 20,11 |
/** |
------------ |
CVS : $Id: slsh.c,v 1.4 2003-01-07 17:10:18 pj Exp $ |
CVS : $Id: slsh.c,v 1.3 2002-11-11 07:54:33 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.4 $ |
Last update: $Date: 2003-01-07 17:10:18 $ |
Revision: $Revision: 1.3 $ |
Last update: $Date: 2002-11-11 07:54:33 $ |
------------ |
This file contains the scheduling module for Slot-Shifting. |
63,7 → 63,6 |
#include <kernel/descr.h> |
#include <kernel/var.h> |
#include <kernel/func.h> |
#include <kernel/trace.h> |
//#define eslsh_printf kern_printf |
#define slsh_printf printk |
108,6 → 107,39 |
} SLSH_level_des; |
/* Which task models the Slot-Shifting module accepts */ |
static int SLSH_level_accept_task_model(LEVEL l, TASK_MODEL* m) |
{ |
HARD_TASK_MODEL* h; |
SOFT_TASK_MODEL* s; |
/* Check the models */ |
switch(m->pclass) |
{ |
case STATIC_PCLASS: /* offline scheduled tasks */ |
return 0; |
case HARD_PCLASS: /* hard aperiodic tasks */ |
h = (HARD_TASK_MODEL *) m; |
if(h->drel != 0 && h->wcet != 0) /* must be set */ |
return 0; |
break; |
case SOFT_PCLASS: /* soft aperiodic tasks */ |
s = (SOFT_TASK_MODEL *) m; |
if(s->wcet != 0) /* must be set */ |
return 0; |
break; |
default: |
} |
return -1; /* Not accepted model */ |
} |
static void SLSH_level_status(LEVEL l) |
{ |
kern_printf("Level status not implemented\n"); |
} |
/* check if some tasks are ready, return 0 if ready, -1 otherwise */ |
static int SLSH_R(SLSH_task* tasks) |
{ |
174,8 → 206,8 |
{ |
lowest_dl = lev->tasks[t].dabs; |
pid = t; |
} |
} |
} |
} |
}/* for all tasks */ |
186,7 → 218,7 |
static PID SLSH_candidates(SLSH_task* tasks) |
{ |
int lowest_dl = 0; |
PID pid = -1; |
PID pid; |
int t; |
/* Use the EDL algorithm again to decide which task to run */ |
251,7 → 283,7 |
} |
/* The scheduler, decides which task to run. */ |
static PID SLSH_public_scheduler(LEVEL l) |
static PID SLSH_level_scheduler(LEVEL l) |
{ |
SLSH_level_des* lev = (SLSH_level_des *)(level_table[l]); |
PID pid; |
290,7 → 322,7 |
} |
/* not used, slot-shifting handles all guarantees itself, it handles all bandwidth */ |
static int SLSH_public_guarantee(LEVEL l, bandwidth_t *freebandwidth) |
static int SLSH_level_guarantee(LEVEL l, bandwidth_t *freebandwidth) |
{ |
*freebandwidth = 0; |
return 1; |
424,7 → 456,7 |
} |
/* check if task model is accepted and store nessecary parameters */ |
static int SLSH_public_create(LEVEL l, PID p, TASK_MODEL *m) |
static int SLSH_task_create(LEVEL l, PID p, TASK_MODEL *m) |
{ |
SLSH_level_des *lev = (SLSH_level_des *)(level_table[l]); |
STATIC_TASK_MODEL* s; |
431,27 → 463,6 |
HARD_TASK_MODEL* h; |
SOFT_TASK_MODEL* u; |
/* Check the models */ |
switch(m->pclass) |
{ |
case STATIC_PCLASS: /* offline scheduled tasks */ |
break; |
case HARD_PCLASS: /* hard aperiodic tasks */ |
h = (HARD_TASK_MODEL *) m; |
if (h->drel == 0 || h->wcet == 0) /* must be set */ |
return -1; |
break; |
case SOFT_PCLASS: /* soft aperiodic tasks */ |
u = (SOFT_TASK_MODEL *) m; |
if(u->wcet == 0) /* must be set */ |
return -1; |
break; |
default: |
return -1; |
} |
/* if the SLSH_task_create is called, then the pclass must be a |
valid pclass. Slot-shifting accepts STATIC_TASK, HARD_TASK |
and SOFT_TASK models with some restrictions */ |
494,6 → 505,17 |
return 0; |
} |
static void SLSH_task_detach(LEVEL l, PID p) |
{ |
/* do nothing */ |
} |
/* check if a task chosen by scheduler is correct */ |
static int SLSH_task_eligible(LEVEL l, PID p) |
{ |
return 0; /* if the task p is chosen, it is always eligible */ |
} |
/************* The slot end event handler *************/ |
static void SLSH_slot_end(void* p) |
{ |
537,7 → 559,7 |
} |
/* when a task becomes executing (EXE status) */ |
static void SLSH_public_dispatch(LEVEL l, PID pid, int nostop) |
static void SLSH_task_dispatch(LEVEL l, PID pid, int nostop) |
{ |
SLSH_level_des *lev = (SLSH_level_des *)(level_table[l]); |
struct timespec t; |
555,7 → 577,7 |
} |
/* called when task is moved from EXE status */ |
static void SLSH_public_epilogue(LEVEL l, PID pid) |
static void SLSH_task_epilogue(LEVEL l, PID pid) |
{ |
SLSH_level_des *lev = (SLSH_level_des *)(level_table[l]); |
576,7 → 598,7 |
} |
/* when task go from SLEEP to SLSH_READY or SLSH_WAIT */ |
static void SLSH_public_activate(LEVEL l, PID pid) |
static void SLSH_task_activate(LEVEL l, PID pid) |
{ |
SLSH_level_des *lev = (SLSH_level_des *)(level_table[l]); |
WORD type = proc_table[pid].pclass; |
604,7 → 626,7 |
} |
/* when a task i returned to module from a semaphore, mutex ... */ |
static void SLSH_public_unblock(LEVEL l, PID pid) |
static void SLSH_task_insert(LEVEL l, PID pid) |
{ |
SLSH_level_des *lev = (SLSH_level_des *)(level_table[l]); |
616,7 → 638,7 |
} |
/* when a semaphore, mutex ... taskes a task from module */ |
static void SLSH_public_block(LEVEL l, PID pid) |
static void SLSH_task_extract(LEVEL l, PID pid) |
{ |
/* Extract the running task from the level |
. we have already extract it from the ready queue at the dispatch time. |
629,8 → 651,14 |
*/ |
} |
/* task has finished execution for this period */ |
static void SLSH_task_endcycle(LEVEL l, PID pid) |
{ |
/* do nothing */ |
} |
/* the task has finihed its wcet, kill task (dont kill static tasks) */ |
static void SLSH_public_end(LEVEL l, PID pid) |
static void SLSH_task_end(LEVEL l, PID pid) |
{ |
SLSH_level_des *lev = (SLSH_level_des *)(level_table[l]); |
657,25 → 685,57 |
} |
/* called when a task should sleep but not execute for awhile, mabe a mode change */ |
//static void SLSH_task_sleep(LEVEL l, PID pid) |
//{ |
// |
// /* the task has terminated his job before it consume the wcet. All OK! */ |
// proc_table[pid].status = SLEEP; |
// |
// /* we reset the capacity counters... only for static tasks */ |
// if (proc_table[pid].pclass == STATIC_PCLASS) |
// proc_table[pid].avail_time = proc_table[pid].wcet; |
// |
//} |
static void SLSH_task_sleep(LEVEL l, PID pid) |
{ |
/* the task has terminated his job before it consume the wcet. All OK! */ |
proc_table[pid].status = SLEEP; |
/* we reset the capacity counters... only for static tasks */ |
if (proc_table[pid].pclass == STATIC_PCLASS) |
proc_table[pid].avail_time = proc_table[pid].wcet; |
} |
/** Guest Functions, slot shifing accepts no guests, so all generates exceptions **/ |
static int SLSH_level_accept_guest_model(LEVEL l, TASK_MODEL* m) { return -1; } |
static int SLSH_guest_create(LEVEL l, PID p, TASK_MODEL *m) |
{ kern_raise(XINVALID_GUEST,exec_shadow); return 0; } |
static void SLSH_guest_detach(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void SLSH_guest_dispatch(LEVEL l, PID p, int nostop) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void SLSH_guest_epilogue(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void SLSH_guest_activate(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void SLSH_guest_insert(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void SLSH_guest_extract(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void SLSH_guest_endcycle(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void SLSH_guest_end(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
static void SLSH_guest_sleep(LEVEL l, PID p) |
{ kern_raise(XINVALID_GUEST,exec_shadow); } |
/******* Registration functions *******/ |
/*+ Registration function: */ |
LEVEL SLSH_register_level() |
void SLSH_register_level() |
{ |
LEVEL l; /* the level that we register */ |
SLSH_level_des *lev; /* for readableness only */ |
683,24 → 743,51 |
kern_printf("SLSH_register_level\n"); |
/* request an entry in the level_table */ |
l = level_alloc_descriptor(sizeof(SLSH_level_des)); |
/* request an entry in the level_table */ |
l = level_alloc_descriptor(); |
lev = (SLSH_level_des *)level_table[l]; |
/* alloc the space needed for the EDF_level_des */ |
lev = (SLSH_level_des *)kern_alloc(sizeof(SLSH_level_des)); |
printk(" lev=%d\n",(int)lev); |
/* update the level_table with the new entry */ |
level_table[l] = (level_des *)lev; |
/* fill the standard descriptor */ |
lev->l.public_scheduler = SLSH_public_scheduler; |
lev->l.public_guarantee = SLSH_public_guarantee; |
lev->l.public_create = SLSH_public_create; |
lev->l.public_end = SLSH_public_end; |
lev->l.public_dispatch = SLSH_public_dispatch; |
lev->l.public_epilogue = SLSH_public_epilogue; |
lev->l.public_activate = SLSH_public_activate; |
lev->l.public_unblock = SLSH_public_unblock; |
lev->l.public_block = SLSH_public_block; |
/* fill the standard descriptor */ |
strncpy(lev->l.level_name, SLSH_LEVELNAME, MAX_LEVELNAME); |
lev->l.level_code = SLSH_LEVEL_CODE; |
lev->l.level_version = SLSH_LEVEL_VERSION; |
lev->l.level_accept_task_model = SLSH_level_accept_task_model; |
lev->l.level_accept_guest_model = SLSH_level_accept_guest_model; |
lev->l.level_status = SLSH_level_status; |
lev->l.level_scheduler = SLSH_level_scheduler; |
lev->l.level_guarantee = SLSH_level_guarantee; |
lev->l.task_create = SLSH_task_create; |
lev->l.task_detach = SLSH_task_detach; |
lev->l.task_eligible = SLSH_task_eligible; |
lev->l.task_dispatch = SLSH_task_dispatch; |
lev->l.task_epilogue = SLSH_task_epilogue; |
lev->l.task_activate = SLSH_task_activate; |
lev->l.task_insert = SLSH_task_insert; |
lev->l.task_extract = SLSH_task_extract; |
lev->l.task_endcycle = SLSH_task_endcycle; |
lev->l.task_end = SLSH_task_end; |
lev->l.task_sleep = SLSH_task_sleep; |
lev->l.guest_create = SLSH_guest_create; |
lev->l.guest_detach = SLSH_guest_detach; |
lev->l.guest_dispatch = SLSH_guest_dispatch; |
lev->l.guest_epilogue = SLSH_guest_epilogue; |
lev->l.guest_activate = SLSH_guest_activate; |
lev->l.guest_insert = SLSH_guest_insert; |
lev->l.guest_extract = SLSH_guest_extract; |
lev->l.guest_endcycle = SLSH_guest_endcycle; |
lev->l.guest_end = SLSH_guest_end; |
lev->l.guest_sleep = SLSH_guest_sleep; |
/* fill the SLSH descriptor part */ |
for(i = 0; i < MAX_PROC; i++) |
{ |
723,8 → 810,6 |
lev->slot = 0; |
lev->slot_length = 0; |
lev->slot_event = -1; |
return l; |
} |
/demos/trunk/slsh/slsh.h |
---|
21,11 → 21,11 |
/** |
------------ |
CVS : $Id: slsh.h,v 1.2 2003-01-07 17:10:18 pj Exp $ |
CVS : $Id: slsh.h,v 1.1.1.1 2002-09-02 09:37:41 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2003-01-07 17:10:18 $ |
Revision: $Revision: 1.1.1.1 $ |
Last update: $Date: 2002-09-02 09:37:41 $ |
------------ |
Author: Tomas Lennvall, Date: Feb 2000. |
127,6 → 127,7 |
#include <kernel/config.h> |
#include <sys/types.h> |
#include <kernel/types.h> |
#include <modules/codes.h> |
#define STATIC_PCLASS 0x0500 |
195,7 → 196,7 |
} SLSH_interval; |
/*+ Registration function: */ |
LEVEL SLSH_register_level(); |
void SLSH_register_level(); |
void SLSH_set_interval(LEVEL l, int start, int end, int maxt); |
void SLSH_set_variables(LEVEL l, TIME length); |
/demos/trunk/tracer/small/common.c |
---|
111,6 → 111,7 |
extern void dump_nop_table(void); |
//dump_sem_table(); |
//dump_nop_table(); |
//sys_status(SCHED_STATUS); |
sys_end(); |
} |
/demos/trunk/oldexamples/stdio/common.c |
---|
112,6 → 112,7 |
extern void dump_nop_table(void); |
//dump_sem_table(); |
//dump_nop_table(); |
//sys_status(SCHED_STATUS); |
cprintf("CTRL-C pressed!\n"); |
sys_end(); |
} |
/demos/trunk/oldexamples/fs/common.c |
---|
112,6 → 112,7 |
extern void dump_nop_table(void); |
//dump_sem_table(); |
//dump_nop_table(); |
//sys_status(SCHED_STATUS); |
cprintf("CTRL-C pressed!\n"); |
sys_end(); |
} |
/demos/trunk/oldexamples/mpeg/mplay.c |
---|
35,11 → 35,11 |
*/ |
/* |
* CVS : $Id: mplay.c,v 1.2 2003-01-07 17:10:17 pj Exp $ |
* CVS : $Id: mplay.c,v 1.1.1.1 2002-09-02 09:37:48 pj Exp $ |
* |
* File: $File$ |
* Revision: $Revision: 1.2 $ |
* Last update: $Date: 2003-01-07 17:10:17 $ |
* Revision: $Revision: 1.1.1.1 $ |
* Last update: $Date: 2002-09-02 09:37:48 $ |
*/ |
#include <ll/sys/types.h> |
198,6 → 198,10 |
cprintf("Total time: %lu\n", t);*/ |
//cprintf("Frame rate: %lu\n", (n * 1000) / ttt); |
/* cprintf("Max frame time: %lu\n", mft);*/ |
/* |
sys_status(READY_RT_STATUS | READY_NRT_STATUS | BLOCKED_STATUS | |
IDLE_STATUS | SLEEP_STATUS | EXEC_STATUS); |
*/ |
} |
#define MAINSLEEP 20000 |
/demos/trunk/oldexamples/mpeg/mplay2.c |
---|
35,11 → 35,11 |
*/ |
/* |
* CVS : $Id: mplay2.c,v 1.2 2003-01-07 17:10:17 pj Exp $ |
* CVS : $Id: mplay2.c,v 1.1.1.1 2002-09-02 09:37:48 pj Exp $ |
* |
* File: $File$ |
* Revision: $Revision: 1.2 $ |
* Last update: $Date: 2003-01-07 17:10:17 $ |
* Revision: $Revision: 1.1.1.1 $ |
* Last update: $Date: 2002-09-02 09:37:48 $ |
*/ |
#include <ll/sys/types.h> |
96,6 → 96,7 |
grx_close(); |
#endif |
cprintf("CTRL-C pressed!\n"); |
//sys_status(SCHED_STATUS); |
#ifndef NOSHOW |
grx_modeinfo(); |
#endif |
/demos/trunk/parport/ppdemo.c |
---|
26,11 → 26,11 |
/** |
------------ |
CVS : $Id: ppdemo.c,v 1.2 2003-01-07 17:10:18 pj Exp $ |
CVS : $Id: ppdemo.c,v 1.1 2002-10-28 08:18:27 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2003-01-07 17:10:18 $ |
Revision: $Revision: 1.1 $ |
Last update: $Date: 2002-10-28 08:18:27 $ |
------------ |
**/ |
329,6 → 329,32 |
/****************************************************************/ |
/* This is the exception handler. It is called when an exception |
is raised. |
It exits from the graphical mode, then it prints a message and |
shutdown the kernel using sys_abort() |
*/ |
void demo_exc_handler(int signo, siginfo_t *info, void *extra) |
{ |
struct timespec t; |
grx_close(); |
/* Default action for an kern exception is */ |
kern_cli(); |
ll_gettime(TIME_EXACT, &t), |
kern_printf("\nS.Ha.R.K. Exception raised!!!" |
"\nTime (s:ns) :%ld:%ld" |
"\nException number:%d (numbers in include/bits/errno.h)" |
"\nPID :%d\n", |
t.tv_sec, t.tv_nsec, info->si_value.sival_int, |
info->si_task); |
sys_abort(1); |
} |
/******************************************************************/ |
/* This function is called when Alt-X is pressed. |
It simply shutdown the system using sys_end. |
Note that the byebye() function is called only if we exit from |
372,8 → 398,20 |
HARD_TASK_MODEL m2; |
SOFT_TASK_MODEL mp; |
struct sigaction action; |
/* Init the standard S.Ha.R.K. exception handler */ |
action.sa_flags = SA_SIGINFO; /* Set the signal action */ |
action.sa_sigaction = demo_exc_handler; |
action.sa_handler = 0; |
sigfillset(&action.sa_mask); /* we block all the other signals... */ |
if (sigaction(SIGHEXC, &action, NULL) == -1) { /* set the signal */ |
perror("Error initializing signals..."); sys_end();} |
/* Set the closing function */ |
sys_atrunlevel(byebye, NULL, RUNLEVEL_BEFORE_EXIT); |
sys_atrunlevel(byebye, NULL, RUNLEVEL_BEFORE_EXIT|NO_AT_ABORT); |
/demos/trunk/thdemo/demo.c |
---|
137,9 → 137,29 |
} |
void demo_exc_handler(int signo, siginfo_t *info, void *extra) |
{ |
struct timespec t; |
grx_close(); |
/* Default action for an kern exception is */ |
kern_cli(); |
ll_gettime(TIME_EXACT, &t), |
kern_printf("\nHartik Exception raised!!!" |
"\nTime (s:ns) :%ld:%ld" |
"\nException number:%d" |
"\nPID :%d\n", |
t.tv_sec, t.tv_nsec, info->si_value.sival_int, |
info->si_task); |
sys_end(); |
// ll_abort(5); |
} |
void my_close(void *arg) |
{ |
grx_close(); |
// sys_status(3); |
} |
179,6 → 199,8 |
KEY_EVT k; |
struct sigaction action; |
srand(4); |
version(); |
212,6 → 234,18 |
k.ascii = 13; |
keyb_hook(k,endfun); |
/* Init the standard Hartik exception handler */ |
/* Set the signal action */ |
action.sa_flags = SA_SIGINFO; |
action.sa_sigaction = demo_exc_handler; |
action.sa_handler = 0; |
sigfillset(&action.sa_mask); /* we block all the other signals... */ |
if (sigaction(SIGHEXC, &action, NULL) == -1) { |
perror("Error initializing signals..."); |
sys_end(); |
} |
sys_atrunlevel(my_close, NULL, RUNLEVEL_BEFORE_EXIT); |
/demos/trunk/thdemo/fftplay.c |
---|
619,6 → 619,7 |
void my_close(void *arg) |
{ |
grx_close(); |
sys_status(3); |
} |
/demos/trunk/robots/mouse2.c |
---|
770,6 → 770,8 |
// char StrAux[15]; |
set_exchandler_grx(); |
for (i=0; i<NMouses; i++) |
Mouse[i].Flag=0; |
for (i=0; i<(360+90); i++) // Inicializar a tabela de senos |
/demos/trunk/soccer/soccer.c |
---|
18,11 → 18,11 |
/* |
------------ |
CVS : $Id: soccer.c,v 1.2 2003-01-07 17:10:18 pj Exp $ |
CVS : $Id: soccer.c,v 1.1.1.1 2002-09-02 09:37:44 pj Exp $ |
File: $File$ |
Revision: $Revision: 1.2 $ |
Last update: $Date: 2003-01-07 17:10:18 $ |
Revision: $Revision: 1.1.1.1 $ |
Last update: $Date: 2002-09-02 09:37:44 $ |
------------ |
*/ |
571,6 → 571,9 |
TIME seme; /* used to init the random seed */ |
/* Set the exception handler */ |
set_exchandler_grx(); |
/* Set the closing function */ |
sys_atrunlevel(byebye, NULL, RUNLEVEL_BEFORE_EXIT); |