Subversion Repositories shark

Compare Revisions

Ignore whitespace Rev 1006 → Rev 1007

/shark/trunk/drivers/linuxc26/shark_linuxc26.c
24,7 → 24,7
extern int buses_init(void);
extern int classes_init(void);
extern int linuxcomp_init(void);
extern int shark_interrupt_server(void);
extern int shark_interrupt_server(int use_intdrv);
 
unsigned long read_time(void) {
 
39,7 → 39,7
}
 
/* Init the Emulation Library */
int LINUXC26_register_module() {
int LINUXC26_register_module(int use_intdrive) {
 
int res;
 
50,10 → 50,10
buses_init();
classes_init();
 
res = shark_interrupt_server();
res = shark_interrupt_server(use_intdrive);
if (res != 0) {
printk("ERROR: CANNOT REGISTER LINUX COMPATIBILITY LAYER\n");
return 1;
exit(1);
}
 
return 0;
/shark/trunk/drivers/linuxc26/include/linuxcomp.h
53,7 → 53,7
 
extern TIME sys_gettime(struct timespec *t);
 
#define MAX_INT_TABLE 64 /* Shark_glue table for interrupt and timers */
#define MAX_TIMER_TABLE 64 /* Shark_glue table for interrupt and timers */
 
unsigned long long read_jiffies(void);
 
64,7 → 64,7
int shark_timer_delete(int index);
 
/* Interrupt handler installation and removal */
int shark_handler_set(int no, void *fast, void *arg);
int shark_handler_set(int no, void *fast);
int shark_handler_remove(int no);
 
#endif
/shark/trunk/drivers/linuxc26/include/drivers/shark_linuxc26.h
21,6 → 21,6
#ifndef __SHARK_LINUXC26__
#define __SHARK_LINUXC26__
 
int LINUXC26_register_module(void);
int LINUXC26_register_module(int use_intdrive);
 
#endif
/shark/trunk/drivers/linuxc26/timer.c
29,24 → 29,22
value->tv_sec = j / HZ;
}
 
extern void *int_arg_table[MAX_INT_TABLE];
extern void *int_func_table[MAX_INT_TABLE];
/*extern void *timer_func_table[MAX_TIMER_TABLE];
extern void *timer_arg_table[MAX_TIMER_TABLE];
extern int intr_count;
 
/*
* Generic Linux time handler.
*/
void linux_timer(int no)
{
intr_count++;
if (int_func_table[no] != NULL)
(*(void (*)(void *arg))int_func_table[no])(int_arg_table[no]);
if (timer_func_table[no] != NULL)
(*(void (*)(void *arg))timer_func_table[no])(timer_arg_table[no]);
intr_count--;
}
}*/
 
/*
* Generic Linux time handler.
*/
void add_timer(struct timer_list *timer)
{
struct timespec timeout;
/shark/trunk/drivers/linuxc26/shark_glue.c
7,179 → 7,92
 
#include <linuxcomp.h>
 
//#define DEBUG_SHARK_GLUE
extern int add_interrupt_job(int no);
extern void set_noint_handler(void * new_handler);
 
PID intr_server = NIL;
extern int intr_count;
 
#define MAX_INT_LIST 50
//#define DEBUG_SHARK_GLUE
 
/* 1-15 for IRQ and 16-63 for timers */
void *timer_arg_table[MAX_TIMER_TABLE];
void *timer_func_table[MAX_TIMER_TABLE];
int timer_table[MAX_TIMER_TABLE];
int intr_table[NR_IRQS];
 
void *int_arg_table[MAX_INT_TABLE];
void *int_func_table[MAX_INT_TABLE];
int timer_table[MAX_INT_TABLE];
int use_intdrive = 0;
static int current_timer = 0;
 
int int_list[MAX_INT_LIST];
int next_free_int = 0;
int next_execute_int = 0;
int n_myact = 0, n_lost = 0;
void shark_internal_sem_create(void **sem, int init) {
*sem = (void *)malloc(sizeof(internal_sem_t));
internal_sem_init((internal_sem_t *)(*sem),init);
}
 
/* FIFO add job */
int add_interrupt_job(int no)
{
 
int old_free_int = next_free_int;
 
TRACER_LOGEVENT(FTrace_EVT_user_event_1, no, 0);
 
int_list[next_free_int] = no;
next_free_int++;
 
if (next_free_int == MAX_INT_LIST) next_free_int = 0;
if (next_free_int == next_execute_int) {
next_free_int = old_free_int;
n_lost++;
return -1;
}
 
return 0;
 
void shark_internal_sem_wait(void *sem) {
internal_sem_wait((internal_sem_t *)(sem));
}
 
/* FIFO get job */
int get_interrupt_job()
{
 
int res = -1;
 
if (next_free_int != next_execute_int) {
res = int_list[next_execute_int];
next_execute_int++;
if (next_execute_int == MAX_INT_LIST) next_execute_int = 0;
}
 
TRACER_LOGEVENT(FTrace_EVT_user_event_2, res, 0);
 
return res;
void shark_internal_sem_post(void *sem) {
internal_sem_post((internal_sem_t *)(sem));
}
 
static int current_timer = 16;
/* Timers */
 
int get_free_timer_slot()
{
int i = current_timer;
 
int i = current_timer, count = 0;
 
while(timer_table[i] != -1) {
if (i < MAX_INT_TABLE) {
if (i < MAX_TIMER_TABLE) {
i++;
count++;
} else {
i = 16;
i = 0;
}
if (count > 2) return -1;
if (i == current_timer) return -1;
}
 
current_timer = i+1;
if (current_timer >= MAX_INT_TABLE) current_timer = 16;
if (current_timer >= MAX_TIMER_TABLE) current_timer = 0;
 
return i;
 
}
 
extern void linux_intr(int no);
extern void linux_timer(int no);
 
 
/* The Interrupt TASK is an aperiodic task designed for
the INTDRIVE module. */
 
TASK Interrupt_Server(void *arg)
void shark_timer_exec(int n)
{
int no = n - 16;
void(*tmp_func)(void*) = timer_func_table[no];
 
int no;
while(1) {
#ifdef DEBUG_SHARK_GLUE
cprintf("(Timer EXEC %d)", no);
#endif
 
n_myact++;
 
no = get_interrupt_job();
 
if (no != -1 && no < 16) {
linux_intr(no);
irq_unmask(no);
}
 
if (no != -1 && no >= 16) {
linux_timer(no);
timer_table[no] = -1;
int_func_table[no] = NULL;
int_arg_table[no] = NULL;
}
 
task_endcycle();
 
if (tmp_func != NULL){
intr_count++;
(tmp_func)(timer_arg_table[no]);
intr_count--;
}
 
timer_table[no] = -1;
timer_func_table[no] = NULL;
timer_arg_table[no] = NULL;
}
 
int shark_interrupt_server() {
 
HARD_TASK_MODEL ht;
int i;
 
for(i=0;i<MAX_INT_TABLE;i++) {
int_arg_table[i] = NULL;
int_func_table[i] = NULL;
timer_table[i] = -1;
}
 
 
hard_task_default_model(ht);
hard_task_def_wcet(ht,10000);
hard_task_def_interrupt(ht);
hard_task_def_system(ht);
hard_task_def_nokill(ht);
 
intr_server = task_create("Interrupt Server",Interrupt_Server,&ht,NULL);
if (intr_server == NIL)
return -1;
 
return 0;
 
}
 
void shark_internal_sem_create(void **sem, int init) {
*sem = (void *)malloc(sizeof(internal_sem_t));
internal_sem_init((internal_sem_t *)(*sem),init);
}
 
void shark_internal_sem_wait(void *sem) {
internal_sem_wait((internal_sem_t *)(sem));
}
 
void shark_internal_sem_post(void *sem) {
internal_sem_post((internal_sem_t *)(sem));
}
 
/* Timers */
 
void fast_call_timer(void *arg)
{
int no = (int)arg;
int res;
 
int no = (int)arg,res;
#ifdef DEBUG_SHARK_GLUE
cprintf("(Timer fast %d)", no);
#endif
 
#ifdef DEBUG_SHARK_GLUE
cprintf("(Timer Exe)");
#endif
 
timer_table[no] = -2;
 
res = add_interrupt_job(no);
if (intr_server != NIL && res == 0)
task_activate(intr_server);
 
if (use_intdrive == TRUE) {
res = add_interrupt_job(no+16);
} else {
shark_timer_exec(no+16);
}
}
 
int shark_timer_set(const struct timespec *time, void *handler, void *arg)
189,9 → 102,9
 
f = kern_fsave();
 
#ifdef DEBUG_SHARK_GLUE
cprintf("(Timer Set)");
#endif
#ifdef DEBUG_SHARK_GLUE
cprintf("(Timer Set %d)", no);
#endif
 
i = get_free_timer_slot();
 
200,15 → 113,15
return -1;
}
 
int_func_table[i] = handler;
int_arg_table[i] = arg;
timer_func_table[i] = handler;
timer_arg_table[i] = arg;
 
timer_table[i] = kern_event_post(time,fast_call_timer,(void *)(i));
timer_table[i] = kern_event_post(time, fast_call_timer, (void *)(i));
if (timer_table[i] == -1) {
kern_frestore(f);
return -1;
}
return -1;
}
 
kern_frestore(f);
 
217,72 → 130,88
 
int shark_timer_delete(int index)
{
 
SYS_FLAGS f;
f = kern_fsave();
f = kern_fsave();
 
if (index <= 0 || index >= MAX_INT_TABLE) {
if (index <= 0 || index >= MAX_TIMER_TABLE) {
kern_frestore(f);
return -1;
}
 
#ifdef DEBUG_SHARK_GLUE
cprintf("(Timer Del)");
#endif
#ifdef DEBUG_SHARK_GLUE
cprintf("(Timer Del %d)", no);
#endif
 
if (timer_table[index] != -1 && timer_table[index] != -2) {
 
int_func_table[index] = NULL;
int_arg_table[index] = NULL;
timer_func_table[index] = NULL;
timer_arg_table[index] = NULL;
kern_event_delete(timer_table[index]);
 
timer_table[index] = -1;
 
}
kern_frestore(f);
kern_frestore(f);
 
return 0;
 
}
 
/* Interrupt */
int shark_handler_set(int no, void *fast){
 
void fast_call_intr(int no)
{
int res;
 
#ifdef DEBUG_SHARK_GLUE
cprintf("(Int Exe)");
#endif
 
irq_mask(no);
 
res = add_interrupt_job(no);
if (intr_server != NIL && res == 0)
task_activate(intr_server);
 
if ((no >= 1) && (no < 16) && (intr_table[no] <= 0)) {
if (use_intdrive == TRUE) {
intr_table[no] = handler_set(no, NULL, TRUE, NIL, fast);
#ifdef DEBUG_SHARK_GLUE
cprintf("(shark_handler_set - INT: %d - %d)", no, intr_table[no]);
#endif
} else {
intr_table[no] = handler_set(no, fast, TRUE, NIL, NULL);
#ifdef DEBUG_SHARK_GLUE
cprintf("(Shark_Handler_Set - NOINT: %d - %d)", no, intr_table[no]);
#endif
}
return intr_table[no];
} else {
#ifdef DEBUG_SHARK_GLUE
cprintf("(shark_handler_set - ERR: %d - %d)", no, intr_table[no]);
#endif
return -1;
}
}
 
int shark_handler_set(int no, void *fast, void *arg){
int shark_handler_remove(int no){
 
if (no >= 1 && no < 16 && int_func_table[no] == NULL) {
int_arg_table[no] = arg;
int_func_table[no] = fast;
return handler_set(no, fast_call_intr, NIL, TRUE);
} else {
return -1;
if (intr_table[no] == 1) {
handler_remove(no);
#ifdef DEBUG_SHARK_GLUE
cprintf("(shark_handler_remove: %d)", no);
#endif
intr_table[no] = 0;
}
 
return 0;
}
/* Boot function */
int shark_interrupt_server(int use_intdrv) {
int i;
 
int shark_handler_remove(int no){
for(i=0; i<MAX_TIMER_TABLE; i++) {
timer_arg_table[i] = NULL;
timer_func_table[i] = NULL;
timer_table[i] = -1;
}
for(i=0; i<NR_IRQS; i++) {
intr_table[i] = 0;
}
use_intdrive = use_intdrv;
#ifdef DEBUG_SHARK_GLUE
cprintf("(Use_intdrive: %d)", use_intdrive);
#endif
if (use_intdrive == TRUE)
set_noint_handler(shark_timer_exec);
 
int_func_table[no] = NULL;
int_arg_table[no] = NULL;
handler_remove(no);
return 0;
 
}
 
/shark/trunk/drivers/linuxc26/int.c
4,11 → 4,8
#include <asm-generic/errno-base.h>
#include <linux/kernel.h>
 
extern void *int_arg_table[MAX_INT_TABLE];
extern void *int_func_table[MAX_INT_TABLE];
#define MAX_IRQS (NR_IRQS +1)
 
#define MAX_IRQS 16
 
#ifndef NIL
#define NIL -1 /*+ integer unvalid value +*/
#endif
44,7 → 41,7
 
intr_count++;
 
//cprintf("(Int %d)", irq);
//cprintf("(linux_intr %d)", irq);
 
ihp=irq_list[irq].handlers;
while (ihp) {
66,8 → 63,6
*headp=ihp;
}
 
#define USE_IRQ_SERVER
 
/*
* Attach a handler to an IRQ.
*/
84,12 → 79,11
 
if (irq_list[irq].handlers == NULL)
{
//* Warning: check if irq is used from somebody that doesn't share!
#ifdef USE_IRQ_SERVER
shark_handler_set(irq, NULL, NULL);
#else
handler_set(irq, linux_intr, NIL, TRUE);
#endif
//* Warning: check if irq is used from somebody that doesn't share! (Claudio ?!?)
shark_handler_set(irq, linux_intr);
//shark_handler_set(irq, NULL, NULL);
 
//cprintf("(request_irq %d)", irq);
}
ihp->func = handler;
ihp->flags = flags;
122,7 → 116,9
 
if (irq_list[irq].handlers == NULL)
{
handler_remove(irq);
shark_handler_remove(irq);
 
//cprintf("(free_irq %d)", irq);
}
}