OpenCores
URL https://opencores.org/ocsvn/s6soc/s6soc/trunk

Subversion Repositories s6soc

[/] [s6soc/] [trunk/] [sw/] [zipos/] [kernel.c] - Diff between revs 22 and 27

Go to most recent revision | Show entire file | Details | Blame | View Log

Rev 22 Rev 27
Line 66... Line 66...
 
 
void kwrite_audio(TASKP tsk, int dev, int *dst, int len);
void kwrite_audio(TASKP tsk, int dev, int *dst, int len);
void kwrite_txuart(TASKP tsk, int dev, int *dst, int len);
void kwrite_txuart(TASKP tsk, int dev, int *dst, int len);
int     kpost(TASKP *task, unsigned events, int milliseconds);
int     kpost(TASKP *task, unsigned events, int milliseconds);
TASKP   kschedule(int LAST_TASK, TASKP *tasklist, TASKP last);
TASKP   kschedule(int LAST_TASK, TASKP *tasklist, TASKP last);
 
extern TASKP    *ksetup(void);
 
 
int     LAST_TASK;
int     LAST_TASK;
 
 
 
extern  int     nwritten, nread, nstarts;
 
 
void    kernel_entry(void) {
void    kernel_entry(void) {
        int     nheartbeats= 0, tickcount = 0, milliseconds=0, ticks = 0;
        int     nheartbeats= 0, tickcount = 0, milliseconds=0, ticks = 0;
        int     audiostate = 0;
        int     audiostate = 0, buttonstate = 0;
        TASKP   *tasklist, current;
        TASKP   *tasklist, current;
        int     *last_context;
        int     *last_context;
        IOSPACE *sys = (IOSPACE *)IOADDR;
        IOSPACE *sys = (IOSPACE *)IOADDR;
        sys->io_spio = 0x0f0;
 
        sys->io_timb = 0;        // Turn off the watchdog timer
 
        LAST_TASK = kntasks();
 
        heap = _top_of_heap;
 
 
 
        pipedev = sys_malloc(sizeof(KDEVICE));
 
        pipedev->write = (RWFDFUN)kwrite_syspipe;
 
        pipedev->read  = (RWFDFUN)kread_syspipe;
 
        pipedev->close = NULL;
 
 
 
        /*
 
        txdev = sys_malloc(sizeof(KDEVICE));
 
        txdev->write = (RWFDFUN)kwrite_txuart;
 
        txdev->read  = (RWFDFUN)kread_syspipe;
 
        txdev->close = NULL;
 
 
 
        pwmdev = sys_malloc(sizeof(KDEVICE));
 
        pwmdev->write = (RWFDFUN)kwrite_audio;
 
        pwmdev->read  = (RWFDFUN)kread_syspipe;
 
        pwmdev->close = NULL;
 
        */
 
 
 
        txdev = pwmdev = pipedev;
 
 
 
        rxpipe  = new_syspipe(16);      //rxpipe->m_wrtask=INTERRUPT_WRITE_TASK;
 
        txpipe  = new_syspipe(16);      txpipe->m_rdtask = INTERRUPT_READ_TASK;
 
        keypipe = new_syspipe(16);
 
        lcdpipe = new_syspipe(16);
 
        pwmpipe = new_syspipe(256);     pwmpipe->m_rdtask= INTERRUPT_READ_TASK;
 
        cmdpipe = new_syspipe(16);
 
 
 
        tasklist = sys_malloc(sizeof(TASKP)*(1+LAST_TASK));
 
        kinit(tasklist);
 
        tasklist[LAST_TASK] = new_task(2, idle_task);
 
 
 
 
        tasklist = ksetup();
 
 
        // current = tasklist[0];
        current = tasklist[0];
        current = tasklist[LAST_TASK];
 
        restore_context(current->context);
        restore_context(current->context);
        last_context = current->context;
        last_context = current->context;
 
 
        // Turn all interrupts off, acknowledge all at the same time
 
        sys->io_pic = 0x7fff7fff;
 
        unsigned enableset =
        unsigned enableset =
                INT_ENABLEV(INT_BUTTON)
                INT_ENABLEV(INT_BUTTON)
                |INT_ENABLEV(INT_TIMA)
                |INT_ENABLEV(INT_TIMA)
                // |INT_ENABLEV(INT_UARTRX)
                // |INT_ENABLEV(INT_UARTRX)
                // |INT_ENABLEV(INT_UARTTX) // Needs to be turned on by driver
                // |INT_ENABLEV(INT_UARTTX) // Needs to be turned on by driver
                // |INT_ENABLEV(INT_AUDIO // Needs to be turned on by driver)
                // |INT_ENABLEV(INT_AUDIO // Needs to be turned on by driver)
                // |INT_ENABLEV(INT_GPIO)
                // |INT_ENABLEV(INT_GPIO)
                // |INT_ENABLEV(INT_TIMB);
                // |INT_ENABLEV(INT_TIMB);
                ;
                ;
        // Then selectively turn some of them back on
        // Then selectively turn some of them back on
        sys->io_pic = INT_ENABLE | enableset;
        sys->io_pic = INT_ENABLE | enableset | 0x07fff;
 
 
        sys->io_tima = CONTEXT_LENGTH | TM_REPEAT;
 
 
 
        sys->io_spio = 0x0f1;
 
        if (1) {
 
                // Reset our wishbone scope for debug later
 
                SCOPE   *scope = (SCOPE *)SCOPEADDR;
 
                scope->s_control = 12;
 
        }
 
 
 
        if (0) {
 
                // Wait on a button press before starting
 
                while((sys->io_spio & 0x0f0)==0)
 
                        ;
 
                sys->io_spio = 0xf3;
 
                for(int i=0; i<0x40000; i++)
 
                        sys->io_spio = ((i>>14)&2)|0x20;
 
                sys->io_spio = 0xf7;
 
        }
 
        sys->io_pic = 0x7fff|INT_ENABLE;
 
 
 
        do {
        do {
                int need_resched = 0, context_has_been_saved, pic;
                int need_resched = 0, context_has_been_saved, pic;
                nheartbeats++;
                nheartbeats++;
 
 
                if (0) {
 
                        int v = 0xe4, p = sys->io_pic;
 
                        if (p < 0)       // LED 4 if interrupts enabled
 
                                v &= ~4;
 
                        if(p & 0x8000)  // LED 8 if any already active
 
                                v |= 8;
 
                        sys->io_spio = v;
 
                }
 
 
 
                // if (sys->io_timb == 0)
 
                        // sys->io_timb = 1600000000; // CONTEXT_LENGTH;
 
                // sys->io_timb = (sys->io_tima & 0x7fffffff) + 350;
 
                // sys->io_spio = 0x0e0;
 
                zip_rtu();
                zip_rtu();
                // sys->io_spio = 0xe2;
 
                // sys->io_timb = CONTEXT_LENGTH;
 
 
 
                last_context = current->context;
                last_context = current->context;
                context_has_been_saved = 0;
                context_has_been_saved = 0;
                pic = sys->io_pic;
                pic = sys->io_pic;
 
 
Line 197... Line 129...
                                        tickcount++;
                                        tickcount++;
                                        ticks = 0;
                                        ticks = 0;
                                        sys->io_spio = ((sys->io_spio&1)^1)|0x010;
                                        sys->io_spio = ((sys->io_spio&1)^1)|0x010;
                                        pic |= SWINT_CLOCK;
                                        pic |= SWINT_CLOCK;
                                }
                                }
 
                                if (buttonstate)
 
                                        buttonstate--;
 
                                else
 
                                        enableset |= INT_ENABLEV(INT_BUTTON);
                        }
                        }
                        // 
                        // 
                        if (pic&INT_BUTTON) {
                        if (pic&INT_BUTTON) {
                                // Need to turn the button interrupt off
                                // Need to turn the button interrupt off
                                enableset &= ~(INT_ENABLEV(INT_BUTTON));
                                enableset &= ~(INT_ENABLEV(INT_BUTTON));
                                if ((sys->io_spio&0x0f0)==0x030)
                                if ((sys->io_spio&0x0f0)==0x030)
                                        kpanic();
                                        kpanic();
                        } else // We can turn it back on when the button
                                buttonstate = 3;
                                // is released
                        }
                                enableset |= INT_ENABLEV(INT_BUTTON);
 
                        if (pic & INT_UARTRX) {
                        if (pic & INT_UARTRX) {
                                int v = sys->io_uart;
                                int v = sys->io_uart;
 
 
                                if ((v & (~0x7f))==0) {
                                if ((v & (~0x7f))==0) {
                                        kpush_syspipe(rxpipe, v);
                                        kpush_syspipe(rxpipe, v);
 
 
                                        // Local Echo
                                        // Local Echo
                                        if (pic & INT_UARTTX)
                                        if (pic & INT_UARTTX) {
                                                sys->io_uart = v;
                                                sys->io_uart = v;
 
                                                sys->io_pic = INT_UARTTX;
 
                                                pic &= ~INT_UARTTX;
 
                                        }
                                }
                                }
                        } if (pic & INT_UARTTX) {
                        } if (pic & INT_UARTTX) {
                                if (kpop_syspipe(txpipe, (int *)&sys->io_uart)==0) {
                                int     v;
 
                                if (kpop_syspipe(txpipe, &v)==0) {
                                        enableset |= (INT_ENABLEV(INT_UARTTX));
                                        enableset |= (INT_ENABLEV(INT_UARTTX));
 
                                        sys->io_uart= v;
                                        sys->io_pic = INT_UARTTX;
                                        sys->io_pic = INT_UARTTX;
                                } else {
                                        // if (v == 'W')
                                        if (txpipe->m_wrtask)
                                                // sys->io_timb = 5;
                                                txpipe->m_wrtask->state = SCHED_READY;
                                                // 75k was writing the 'e'
 
                                } else
                                        enableset &= ~(INT_ENABLEV(INT_UARTTX));
                                        enableset &= ~(INT_ENABLEV(INT_UARTTX));
                                }
 
                        } if (audiostate) {
                        } if (audiostate) {
                                if (pic & INT_AUDIO) {
                                if (pic & INT_AUDIO) {
                                int v;
                                int v;
                                // States: 
                                // States: 
                                //      0 -- not in use
                                //      0 -- not in use
Line 241... Line 181...
                                        sys->io_pwm_audio = (audiostate>>2)&0x0ffff;
                                        sys->io_pwm_audio = (audiostate>>2)&0x0ffff;
                                        audiostate = 1;
                                        audiostate = 1;
                                } else if (kpop_syspipe(pwmpipe, &v)==0) {
                                } else if (kpop_syspipe(pwmpipe, &v)==0) {
                                        audiostate = (2|(v<<2))&0x03ffff;
                                        audiostate = (2|(v<<2))&0x03ffff;
                                        sys->io_pwm_audio = (v>>16)&0x0ffff;
                                        sys->io_pwm_audio = (v>>16)&0x0ffff;
 
                                        nread++;
                                } else {
                                } else {
                                        audiostate = 0;
                                        audiostate = 0;
                                        // Turn the device off
                                        // Turn the device off
                                        sys->io_pwm_audio = 0x10000;
                                        sys->io_pwm_audio = 0x10000;
                                        // Turn the interrupts off
                                        // Turn the interrupts off
Line 253... Line 194...
                                }
                                }
 
 
                                // This particular interrupt cannot be cleared
                                // This particular interrupt cannot be cleared
                                // until the port has been written to.  Hence,
                                // until the port has been written to.  Hence,
                                // now that we've written to the port, we clear
                                // now that we've written to the port, we clear
                                // it now.
                                // it now.  If it needs retriggering, the port
 
                                // will retrigger itself -- despite being
 
                                // cleared here.
                                sys->io_pic = INT_AUDIO;
                                sys->io_pic = INT_AUDIO;
                        }} else { // if (audiostate == 0)
                        }} else { // if (audiostate == 0)
                                int     v;
                                int     sample;
                                if (kpop_syspipe(pwmpipe, &v)==0) {
                                if (kpop_syspipe(pwmpipe, &sample)==0) {
                                        audiostate = (2|(v<<2))&0x03ffff;
                                        nstarts++;
                                        sys->io_pwm_audio = 0x310000 | ((v>>16)&0x0ffff);
                                        nread++;
 
                                        audiostate = (2|(sample<<2))&0x03ffff;
 
                                        sys->io_pwm_audio = 0x310000 | ((sample>>16)&0x0ffff);
                                        enableset |= (INT_ENABLEV(INT_AUDIO));
                                        enableset |= (INT_ENABLEV(INT_AUDIO));
                                        sys->io_spio = 0x022;
                                        sys->io_spio = 0x022;
                                        sys->io_pic = INT_AUDIO;
                                        sys->io_pic = INT_AUDIO;
                                } // else sys->io_spio = 0x020;
                                } // else sys->io_spio = 0x020;
                        } milliseconds = kpost(tasklist, pic, milliseconds);
                        } milliseconds = kpost(tasklist, pic, milliseconds);
Line 271... Line 216...
                        // Restart interrupts
                        // Restart interrupts
                        enableset &= (~0x0ffff); // Keep the bottom bits off
                        enableset &= (~0x0ffff); // Keep the bottom bits off
                        sys->io_pic = INT_ENABLE|enableset;
                        sys->io_pic = INT_ENABLE|enableset;
                } else {
                } else {
                        sys->io_pic = INT_ENABLE; // Make sure interrupts are on
                        sys->io_pic = INT_ENABLE; // Make sure interrupts are on
                        int     v;
                        int     sample;
 
 
                        // Check for the beginning of an audio pipe.  If the
                        // Check for the beginning of an audio pipe.  If the
                        // interrupt is not enabled, we still might need to
                        // interrupt is not enabled, we still might need to
                        // enable it.
                        // enable it.
                        if ((audiostate==0)&&(kpop_syspipe(pwmpipe, &v)==0)) {
                        if ((audiostate==0)&&(kpop_syspipe(pwmpipe, &sample)==0)) {
                                audiostate = (2|(v<<2))&0x03ffff;
                                audiostate = (2|(sample<<2))&0x03ffff;
                                sys->io_pwm_audio = 0x310000 | ((v>>16)&0x0ffff);
                                sys->io_pwm_audio = 0x310000 | ((sample>>16)&0x0ffff);
 
                                sys->io_pic = INT_AUDIO;
                                enableset |= (INT_ENABLEV(INT_AUDIO));
                                enableset |= (INT_ENABLEV(INT_AUDIO));
                                sys->io_spio = 0x022;
                                sys->io_spio = 0x022;
 
                                nstarts++;
 
                                nread++;
                        } // else sys->io_spio = 0x020;
                        } // else sys->io_spio = 0x020;
 
 
                        // Or the beginning of a transmit pipe.  
                        // Or the beginning of a transmit pipe.  
                        if (pic & INT_UARTTX) {
                        if (pic & INT_UARTTX) {
                                if (kpop_syspipe(txpipe, (int *)&sys->io_uart)==0) {
                                int     v;
 
                                if (kpop_syspipe(txpipe, &v)==0) {
                                        enableset |= (INT_ENABLEV(INT_UARTTX));
                                        enableset |= (INT_ENABLEV(INT_UARTTX));
 
                                        sys->io_uart = v;
                                        sys->io_pic = INT_UARTTX;
                                        sys->io_pic = INT_UARTTX;
                                } else {
                                        // if (v == 'W')
                                        if (txpipe->m_wrtask)
                                                // sys->io_timb = 5;
                                                txpipe->m_wrtask = SCHED_READY;
                                } else
                                        enableset &= ~(INT_ENABLEV(INT_UARTTX));
                                        enableset &= ~(INT_ENABLEV(INT_UARTTX));
                                }
                                }
                        }
 
 
 
                        // What if the interrupt bit for the buttons is off?
 
                        if ((sys->io_spio & 0x0f0)==0)
 
                                enableset |= INT_ENABLEV(INT_BUTTON);
 
 
 
                        // What if someone left interrupts off?
                        // What if someone left interrupts off?
                        // This might happen as part of a wait trap call, such
                        // This might happen as part of a wait trap call, such
                        // as syspipe() accomplishes within uwrite_syspipe()
                        // as syspipe() accomplishes within uwrite_syspipe()
                        // (We also might've just turned them off ... ooops)
                        // (We also might've just turned them off ... ooops)
Line 501... Line 446...
                        tasklist[i]->waitsig = 0;
                        tasklist[i]->waitsig = 0;
                }
                }
        } return milliseconds;
        } return milliseconds;
}
}
 
 
void    kuserexit(int a) {
 
        syscall(TRAPID_EXIT, a, 0, 0);
 
}
 
 
 
void    *sys_malloc(int sz) {
 
        {
 
                SCOPE   *s = (SCOPE *)SCOPEADDR;
 
                s->s_control = TRIGGER_SCOPE_NOW | (s->s_control & 0x0ffff);
 
        }
 
 
 
        void    *res = heap;
 
        heap += sz;
 
        if ((int)heap > ((int)&res)-32) {
 
                IOSPACE *sys = (IOSPACE *)IOADDR;
 
                sys->io_spio = 0xf3;
 
                asm("break 0");
 
        }
 
        return res;
 
}
 
 
 
/*
 
// This won't work.  Once we apply an rtu(), there will be an immediate
 
// interrupt before the task has had a chance to fill in a first value.  By
 
// instead waiting until the task comes back from it's first task swap, perhaps
 
// having stalled it's pipe, then we can get our interrupt up and running.
 
// Not only that, but at that time we'll have plenty of info to stuff into the
 
// interrupt as well.
 
void kwrite_audio(TASKP tsk, int dev, int *dst, int len) {
 
        kwrite_syspipe(tsk,dev,dst,len);
 
        if (tsk->context[15] == (int)uwrite_syspipe) {
 
                IOSPACE *io = (IOSPACE *)IOADDR;
 
                // Turn our audio interrupt on.
 
                io->pic = INT_ENABLEV(INT_AUDIO);
 
        }
 
}
 
 
 
void kwrite_txuart(TASKP tsk, int dev, int *dst, int len) {
 
        kwrite_syspipe(tsk,dev,dst,len);
 
        if (tsk->context[15] == (int)uwrite_syspipe) {
 
                IOSPACE *io = (IOSPACE *)IOADDR;
 
                // Turn our UART transmit interrupt on.
 
                io->pic = INT_ENABLEV(INT_UARTTX);
 
        }
 
}
 
 
 
*/
 
 
 
 
 
 No newline at end of file
 No newline at end of file

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.