aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDimitri Sokolyuk <demon@dim13.org>2011-12-23 13:12:53 +0000
committerDimitri Sokolyuk <demon@dim13.org>2011-12-23 13:12:53 +0000
commit672bff2b5ace7b9f424dd2341b9247f1ad3af983 (patch)
treec94fb82700bddfcacf4a372292bc0752cd1a0db6
parentc6b1412bf46cc0e87895d22cd2536057c49081ae (diff)
still buggy
-rw-r--r--kernel/dmx.c21
-rw-r--r--kernel/kernel.c76
-rw-r--r--kernel/kernel.h2
3 files changed, 43 insertions, 56 deletions
diff --git a/kernel/dmx.c b/kernel/dmx.c
index 3d9a51e..691239f 100644
--- a/kernel/dmx.c
+++ b/kernel/dmx.c
@@ -16,6 +16,7 @@
*/
#include <stdint.h>
+#include <string.h>
#include <avr/io.h>
#include <avr/cpufunc.h>
#include "kernel.h"
@@ -48,28 +49,28 @@ main()
#define HIGH 0
#if 1
- exec(heartbeat, STACK, 0, LOW);
+ exec(heartbeat, NULL, STACK, LOW);
#endif
#if 1
- exec(rgb, STACK + 16, &rgbargs, MID);
- exec(pwm, STACK, &pwmargs[0], HIGH);
- exec(pwm, STACK, &pwmargs[1], HIGH);
- exec(pwm, STACK, &pwmargs[2], HIGH);
- exec(adc, STACK, &adcarg, LOW);
+ exec(rgb, &rgbargs, STACK + 16, MID);
+ exec(pwm, &pwmargs[0], STACK, HIGH);
+ exec(pwm, &pwmargs[1], STACK, HIGH);
+ exec(pwm, &pwmargs[2], STACK, HIGH);
+ exec(adc, &adcarg, STACK, LOW);
#endif
#if 1
- exec(lcd, STACK, &lcdarg, LOW);
- exec(clock, STACK + 48, &clockarg, LOW);
+ exec(lcd, &lcdarg, STACK, LOW);
+ exec(clock, &clockarg, STACK + 48, LOW);
#endif
#if 0
- exec(cmd, STACK, &rgbargs, 0);
+ exec(cmd, &rgbargs, STACK, LOW);
#endif
#if 0
- exec(ppm, STACK, &ppmarg, 0);
+ exec(ppm, &ppmarg, STACK, LOW);
#endif
for (;;)
diff --git a/kernel/kernel.c b/kernel/kernel.c
index f11fdc1..18e9f53 100644
--- a/kernel/kernel.c
+++ b/kernel/kernel.c
@@ -30,7 +30,7 @@
#define DEBUG 1
#define NPRIO 4
-enum State { TERMINATED, RUNQ, TIMEQ, WAITQ };
+enum State { TERMINATED, RTR, RUNQ, SLEEPING, WAITING };
#define LO8(x) ((uint8_t)((uint16_t)(x)))
#define HI8(x) ((uint8_t)((uint16_t)(x) >> 8))
@@ -79,53 +79,39 @@ ISR(TIMER1_COMPA_vect, ISR_NAKED)
PORTB ^= _BV(PB1); /* DEBUG */
#endif
- /* save stack pointer */
- tp = kernel.current;
- tp->sp = SP;
-
-#if 0
- /* involuntary switch, reduce prio */
- switch (tp->state) {
- case RUNQ: /* involuntay, reduce prio */
- if (tp->prio > 0)
- --(tp->prio);
- break;
- case TIMEQ: /* voluntary, rise prio */
- if (tp->prio < (NPRIO - 1))
- ++(tp->prio);
- break;
- default:
- break;
- }
-#endif
-
- tp->state = TIMEQ;
-
- /* drop current task from run-queue */
- SIMPLEQ_REMOVE_HEAD(&kernel.runq[tp->prio], link);
+ /* save stack pointer and drop task from run-queue */
+ kernel.current->sp = SP;
+ if (kernel.current->state == RUNQ)
+ kernel.current->state = RTR;
+ SIMPLEQ_REMOVE_HEAD(&kernel.runq[kernel.current->prio], link);
nexthit = 0xffff;
prio = 0;
/* walk through tasks and assemble run-queue */
for (tp = &kernel.task[1]; tp <= kernel.last; tp++) {
- if (tp->state != TIMEQ)
- continue;
- dist = DISTANCE(now, tp->release);
- if (dist <= 0) {
- tp->state = RUNQ;
+ if (tp->state == SLEEPING) {
+ dist = DISTANCE(now, tp->release);
+ if (dist <= 0)
+ tp->state = RTR;
+ else if (dist < nexthit)
+ nexthit = dist;
+ }
+ if (tp->state == RTR) {
+ /* find highest priority */
if (tp->prio > prio)
prio = tp->prio;
+ /* put task on queue */
+ tp->state = RUNQ;
SIMPLEQ_INSERT_TAIL(&kernel.runq[tp->prio], tp, link);
- } else if (dist < nexthit)
- nexthit = dist;
+ }
}
/* idle if all queues empty */
- if (!prio && SIMPLEQ_EMPTY(kernel.runq))
- SIMPLEQ_INSERT_HEAD(kernel.runq, kernel.task, link);
+ if (prio == 0 && SIMPLEQ_EMPTY(&kernel.runq[0]))
+ SIMPLEQ_INSERT_HEAD(&kernel.runq[0], &kernel.task[0], link);
- /* restore stack pointer */
+ /* pick highest priority and restore stack pointer */
kernel.current = SIMPLEQ_FIRST(&kernel.runq[prio]);
SP = kernel.current->sp;
@@ -164,13 +150,14 @@ init(uint8_t stack)
kernel.task->state = RUNQ;
kernel.last = kernel.task;
kernel.current = kernel.task;
- SIMPLEQ_INSERT_HEAD(kernel.runq, kernel.task, link);
+
+ SIMPLEQ_INSERT_HEAD(&kernel.runq[0], &kernel.task[0], link);
sei();
}
void
-exec(void (*fun)(void *), uint8_t stack, void *args, uint8_t prio)
+exec(void (*fun)(void *), void *args, uint8_t stack, uint8_t prio)
{
struct task *t;
uint8_t *sp;
@@ -195,11 +182,13 @@ exec(void (*fun)(void *), uint8_t stack, void *args, uint8_t prio)
t = ++kernel.last;
- t->release = NOW(kernel.cycles, TCNT1);
+ t->release = 0;
+
if (prio >= NPRIO)
prio = NPRIO - 1;
t->prio = prio;
- t->state = TIMEQ;
+
+ t->state = RTR;
t->sp = (uint16_t)sp; /* SP */
@@ -259,13 +248,10 @@ signal(uint8_t sema)
void
sleep(uint32_t ticks)
{
- struct task *tp;
-
cli();
- tp = kernel.current;
- tp->release += ticks;
- tp->state = TIMEQ;
+ kernel.current->release += ticks;
+ kernel.current->state = SLEEPING;
SCHEDULE();
}
@@ -281,7 +267,7 @@ suspend(void)
{
cli();
- kernel.current = TERMINATED;
+ kernel.current->state = TERMINATED;
SCHEDULE();
}
diff --git a/kernel/kernel.h b/kernel/kernel.h
index 3e58917..bf64b39 100644
--- a/kernel/kernel.h
+++ b/kernel/kernel.h
@@ -92,7 +92,7 @@
/* __BEGIN_DECLS */
void init(uint8_t stack);
-void exec(void (*fun)(void *), uint8_t stack, void *args, uint8_t prio);
+void exec(void (*fun)(void *), void *args, uint8_t stack, uint8_t prio);
void semaphore(uint8_t semnbr, uint8_t initVal);
void wait(uint8_t semnbr);