aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorChristian Cunningham <cc@localhost>2022-03-24 16:44:51 -0700
committerChristian Cunningham <cc@localhost>2022-03-24 16:44:51 -0700
commit49bd4c133fc83de1cb1761ff089a2de03699d991 (patch)
tree1033663698e3651d0fdbc6773c6a3db8261ae3c3
parentbb6ddd5a82ab4f2afa253b6048a71504c64274bb (diff)
IRQ Subscription
-rw-r--r--include/cpu/irq.h14
-rw-r--r--include/globals.h2
-rw-r--r--include/symbols.h2
-rw-r--r--include/usr/main.h3
-rw-r--r--kernel/cpu/irq.c54
-rw-r--r--kernel/globals.c2
-rw-r--r--kernel/sys/core.c38
-rw-r--r--usr/main.c49
8 files changed, 120 insertions, 44 deletions
diff --git a/include/cpu/irq.h b/include/cpu/irq.h
index 1879707..c5e59bb 100644
--- a/include/cpu/irq.h
+++ b/include/cpu/irq.h
@@ -1,6 +1,19 @@
#ifndef CPU_IRQ_H
#define CPU_IRQ_H
+#define UART_IRQ 0
+#define SYS_TIMER_0_IRQ 1
+#define SYS_TIMER_1_IRQ 2
+#define SYS_TIMER_2_IRQ 3
+#define SYS_TIMER_3_IRQ 4
+#define LOCAL_TIMER_IRQ 5
+#define MAX_IRQS LOCAL_TIMER_IRQ+1
+
+struct IrqEntry {
+ void* handler;
+ void* handler_info;
+};
+
static inline void enableirq(void)
{
asm volatile("cpsie i");
@@ -20,5 +33,6 @@ static inline void disablefiq(void)
unsigned long c_irq_handler(void);
unsigned long c_fiq_handler(void);
+void subscribe_irq(unsigned long irq_num, void* handler, void* handler_info);
#endif
diff --git a/include/globals.h b/include/globals.h
index 6c7e1f1..478b62e 100644
--- a/include/globals.h
+++ b/include/globals.h
@@ -1,5 +1,6 @@
#ifndef GLOBALS_H
#define GLOBALS_H
+#include <cpu/irq.h>
#include <sys/schedule.h>
#include <util/mutex.h>
@@ -20,6 +21,7 @@ extern struct Mutex mutexs[MAX_MUTEXS];
extern struct Entry mutex_entries[MAX_MUTEXS];
extern struct Thread threads[MAX_THREADS];
extern struct Entry thread_entries[MAX_THREADS];
+extern struct IrqEntry irqs[MAX_IRQS];
#endif
#endif
diff --git a/include/symbols.h b/include/symbols.h
index 90cfcf0..b81b1a9 100644
--- a/include/symbols.h
+++ b/include/symbols.h
@@ -50,7 +50,7 @@ enum
IRQ_BASIC_DISABLE = (IRQ_BASE + 0x224),
// Peripherals Interrupts
- UART_IRQ = 57,
+ //UART_IRQ = 57,
GPIO_IRQ_0 = 49,
GPIO_IRQ_1 = 50,
GPIO_IRQ_2 = 51,
diff --git a/include/usr/main.h b/include/usr/main.h
index 5fd29f9..3aec5a9 100644
--- a/include/usr/main.h
+++ b/include/usr/main.h
@@ -2,11 +2,12 @@
#define USR_MAIN_H
#ifdef RPI_BUILD
- #define USR_TIME 40
+ #define USR_TIME 260
#else
#define USR_TIME 2000
#endif
void main(void);
+void handle_data(unsigned char);
#endif
diff --git a/kernel/cpu/irq.c b/kernel/cpu/irq.c
index f89bba9..9490489 100644
--- a/kernel/cpu/irq.c
+++ b/kernel/cpu/irq.c
@@ -13,8 +13,6 @@
#define CPS 1000
-void handle_data(unsigned char);
-
static unsigned long counter = 0;
unsigned long c_irq_handler(void)
{
@@ -37,19 +35,19 @@ unsigned long c_irq_handler(void)
}
#endif
// Add task to handle the data
- {
- add_thread(handle_data, (void*)data, PRIORITIES-1);
+ if (irqs[UART_IRQ].handler != 0) {
+ add_thread(irqs[UART_IRQ].handler, (void*)data, *(unsigned long*)irqs[UART_IRQ].handler_info);
return 1;
}
}
}
// Check if System Time Compare 0 Triggered the Interrupt
- if (*(volatile unsigned long*)SYS_TIMER_CS & SYS_TIMER_SC_M0) {
+ if (*(volatile unsigned long*)SYS_TIMER_CS & SYS_TIMER_SC_M0 && irqs[SYS_TIMER_0_IRQ].handler != 0) {
volatile unsigned long* timer_cs = (volatile unsigned long*)SYS_TIMER_CS;
volatile unsigned long* timer_chi = (volatile unsigned long*)SYS_TIMER_CHI;
volatile unsigned long* nexttime = (volatile unsigned long*)SYS_TIMER_C0;
- add_thread_without_duplicate(main, 0, 0);
- *nexttime = *timer_chi + USR_TIME;
+ add_thread(irqs[SYS_TIMER_0_IRQ].handler, 0, 1);
+ *nexttime = *timer_chi + *(unsigned long*)irqs[SYS_TIMER_0_IRQ].handler_info;
*timer_cs = SYS_TIMER_SC_M0;
return 1;
}
@@ -69,25 +67,39 @@ unsigned long c_fiq_handler(void)
{
unsigned long source = load32(CORE0_FIQ_SOURCE);
// Check if CNTV triggered the interrupt
- if (source & (1 << 3)) {
+ if (source & (1 << 3) && irqs[LOCAL_TIMER_IRQ].handler != 0) {
+ add_thread(irqs[LOCAL_TIMER_IRQ].handler, 0, 1);
write_cntv_tval(cntfrq);
}
return 0;
}
-void handle_data(unsigned char data)
+void subscribe_irq(unsigned long irq_num, void* handler, void* handler_info)
{
- // Newline Case
- if (data == 0x0D) {
- // Backspace Case
- } else if (data == 0x08 || data == 0x7F) {
- } else if (data == 0x61) {
- add_thread(uart_scheduler, 0, 2);
- } else if (data == 0x62) {
- //add_thread(test_entry, 0, 2);
- }
- // Draw it on the screen
- {
- draw_chex32(0, 9, data, 0xAA00FF);
+ if (irq_num >= MAX_IRQS)
+ return;
+ irqs[irq_num].handler = handler;
+ irqs[irq_num].handler_info = handler_info;
+ switch (irq_num) {
+ case UART_IRQ:
+ store32(1<<4, UART0_IMSC);
+ store32(1<<25, IRQ_ENABLE2);
+ break;
+ case SYS_TIMER_0_IRQ:
+ store32(SYS_TIMER_SC_M0, IRQ_ENABLE1);
+ *(volatile unsigned long*)SYS_TIMER_C0 = *(volatile unsigned long*)SYS_TIMER_CHI + *(unsigned long*)handler_info;
+ break;
+ case SYS_TIMER_1_IRQ:
+ store32(SYS_TIMER_SC_M1, IRQ_ENABLE1);
+ *(volatile unsigned long*)SYS_TIMER_C1 = *(volatile unsigned long*)SYS_TIMER_CHI + *(unsigned long*)handler_info;
+ break;
+ case SYS_TIMER_2_IRQ:
+ store32(SYS_TIMER_SC_M2, IRQ_ENABLE1);
+ *(volatile unsigned long*)SYS_TIMER_C2 = *(volatile unsigned long*)SYS_TIMER_CHI + *(unsigned long*)handler_info;
+ break;
+ case SYS_TIMER_3_IRQ:
+ store32(SYS_TIMER_SC_M3, IRQ_ENABLE1);
+ *(volatile unsigned long*)SYS_TIMER_C3 = *(volatile unsigned long*)SYS_TIMER_CHI + *(unsigned long*)handler_info;
+ break;
}
}
diff --git a/kernel/globals.c b/kernel/globals.c
index 5118e96..5cdab01 100644
--- a/kernel/globals.c
+++ b/kernel/globals.c
@@ -1,4 +1,5 @@
#define GLOBALS_C
+#include <cpu/irq.h>
#include <sys/schedule.h>
#include <util/mutex.h>
char* os_name = "Jobbed";
@@ -18,6 +19,7 @@ __attribute__((section(".bss"))) unsigned int gwidth;
__attribute__((section(".bss"))) unsigned int gheight;
__attribute__((section(".bss"))) unsigned int gpitch;
__attribute__((section(".bss"))) unsigned int gisrgb;
+__attribute__((section(".bss"))) struct IrqEntry irqs[MAX_IRQS];
__attribute__((section(".bss.mutexs"))) struct Mutex mutexs[MAX_MUTEXS];
__attribute__((section(".bss.mutexe"))) struct Entry mutex_entries[MAX_MUTEXS];
__attribute__((section(".bss.threads"))) struct Thread threads[MAX_THREADS];
diff --git a/kernel/sys/core.c b/kernel/sys/core.c
index d76b712..7f42d6e 100644
--- a/kernel/sys/core.c
+++ b/kernel/sys/core.c
@@ -10,6 +10,7 @@
#include <sys/core.h>
#include <sys/power.h>
#include <sys/schedule.h>
+#include <usr/main.h>
#include <util/mutex.h>
#include <util/status.h>
#include <util/time.h>
@@ -18,30 +19,30 @@
void sysinit(void)
{
// Initialize System Globals
- stimeh = *(unsigned long*)SYS_TIMER_CHI;
- stimel = *(unsigned long*)SYS_TIMER_CLO;
- *(unsigned long*) SYS_TIMER_C0 = 2000000 + stimeh; // 2 second trigger
+ //stimeh = *(unsigned long*)SYS_TIMER_CHI;
+ //stimel = *(unsigned long*)SYS_TIMER_CLO;
+ //*(unsigned long*) SYS_TIMER_C0 = 2000000 + stimeh; // 2 second trigger
uart_init();
///...
// Route GPU interrupts to Core 0
store32(0x00, GPU_INTERRUPTS_ROUTING);
- // Mask Overrun of UART0
- store32(1<<4, UART0_IMSC);
- // Enable UART GPU IRQ
- store32(1<<25, IRQ_ENABLE2);
- // Enable Timer
- //// Get the frequency
- cntfrq = read_cntfrq();
- // Clear cntv interrupt and set next 1 second timer
- write_cntv_tval(cntfrq);
- // Route timer to core0 fiq
- routing_core0cntv_to_core0fiq();
- // Enable timer
- enablecntv();
- // Enable system timer
- store32(SYS_TIMER_SC_M0, IRQ_ENABLE1);
+ //// Mask Overrun of UART0
+ //store32(1<<4, UART0_IMSC);
+ //// Enable UART GPU IRQ
+ //store32(1<<25, IRQ_ENABLE2);
+ //// Enable Timer
+ ////// Get the frequency
+ //cntfrq = read_cntfrq();
+ //// Clear cntv interrupt and set next 1 second timer
+ //write_cntv_tval(cntfrq);
+ //// Route timer to core0 fiq
+ //routing_core0cntv_to_core0fiq();
+ //// Enable timer
+ //enablecntv();
+ //// Enable system timer
+ //store32(SYS_TIMER_SC_M0, IRQ_ENABLE1);
// Graphics Initialize
lfb_init();
@@ -55,4 +56,5 @@ void sysinit(void)
// Start Scheduler
init_scheduler();
+ add_thread(main, 0, 0);
}
diff --git a/usr/main.c b/usr/main.c
index 3543c31..9c8a7d8 100644
--- a/usr/main.c
+++ b/usr/main.c
@@ -1,5 +1,27 @@
#include <graphics/lfb.h>
+#include <globals.h>
#include <symbols.h>
+#include <sys/schedule.h>
+#include <util/time.h>
+
+void loop(void);
+
+void handle_data(unsigned char data)
+{
+ // Newline Case
+ if (data == 0x0D) {
+ // Backspace Case
+ } else if (data == 0x08 || data == 0x7F) {
+ } else if (data == 0x61) {
+ add_thread(uart_scheduler, 0, 2);
+ } else if (data == 0x62) {
+ //add_thread(test_entry, 0, 2);
+ }
+ // Draw it on the screen
+ {
+ draw_chex32(0, 9, data, 0xAA00FF);
+ }
+}
char* ulong_to_string(unsigned long value, char* data)
{
@@ -21,16 +43,37 @@ char* ulong_to_string(unsigned long value, char* data)
return dptr;
}
-void main(void)
+void loop(void)
{
static char str[13];
static unsigned long previous = 0;
char* start;
unsigned long current = *(volatile unsigned long*)SYS_TIMER_CHI;
start = ulong_to_string(current, str);
+ draw_string(0, 10, " ");
draw_string(0, 10, start);
- start = ulong_to_string(current - previous, str);
+ start = ulong_to_string(previous, str);
draw_string(0, 11, " ");
draw_string(0, 11, start);
- previous = current;
+ start = ulong_to_string(nextpid, str);
+ draw_string(0, 12, " ");
+ draw_string(0, 12, start);
+ previous++;
+ wait_msec(3000);
+ add_thread(loop, 0, 3);
+}
+
+void loopt(void)
+{
+ static char str[13];
+ draw_string(0, 9, ulong_to_string(*(volatile unsigned long*)SYS_TIMER_CHI, str));
+}
+
+static unsigned long TICK_RATE = 5000000;
+static unsigned long UART_PRIORITY = 2;
+void main(void)
+{
+ subscribe_irq(UART_IRQ, handle_data, &UART_PRIORITY);
+ subscribe_irq(SYS_TIMER_0_IRQ, loopt, &TICK_RATE);
+ add_thread(loop, 0, 0);
}