Annotation of hatari/tests/serial/scc_ser.c, revision 1.1.1.1

1.1       root        1: /*
                      2:  * Hatari SCC serial port test
                      3:  *
                      4:  * Partly based on the file serport.c and mfp.h from EmuTOS:
                      5:  * Copyright (C) 2013-2018 The EmuTOS development team
                      6:  *
                      7:  * This file is distributed under the GPL, version 2 or at your
                      8:  * option any later version.  See doc/license.txt for details.
                      9:  */
                     10: 
                     11: #include <tos.h>
                     12: 
                     13: volatile int delay_cnt;
                     14: 
                     15: static void delay_loop(int loops)
                     16: {
                     17:        int i;
                     18: 
                     19:        for (i = 0; i < loops; i++)
                     20:                delay_cnt++;
                     21: }
                     22: 
                     23: /*
                     24:  * defines
                     25:  */
                     26: #define RESET_RECOVERY_DELAY    delay_loop(8)
                     27: #define RECOVERY_DELAY          delay_loop(4)
                     28: 
                     29: #define SCC_BASE                0xffff8c80UL
                     30: 
                     31: #define HIBYTE(x) ((unsigned char)((unsigned short)(x) >> 8))
                     32: #define LOBYTE(x) ((unsigned char)(unsigned short)(x))
                     33: 
                     34: /*
                     35:  * structures
                     36:  */
                     37: typedef struct {
                     38:     unsigned char dum1;
                     39:     volatile unsigned char ctl;
                     40:     unsigned char dum2;
                     41:     volatile unsigned char data;
                     42: } PORT;
                     43: typedef struct {
                     44:     PORT portA;
                     45:     PORT portB;
                     46: } SCC;
                     47: 
                     48: /*
                     49:  * SCC port B i/o routines
                     50:  */
                     51: static long bcostatB(void)
                     52: {
                     53:        SCC *scc = (SCC *)SCC_BASE;
                     54:        long rc;
                     55: 
                     56:        rc = (scc->portB.ctl & 0x04) ? -1L : 0L;
                     57:        RECOVERY_DELAY;
                     58: 
                     59:        return rc;
                     60: }
                     61: 
                     62: long bconoutB(unsigned char b)
                     63: {
                     64:        SCC *scc = (SCC *)SCC_BASE;
                     65: 
                     66:        while(!bcostatB())
                     67:                ;
                     68:        scc->portB.data = b;
                     69:        RECOVERY_DELAY;
                     70: 
                     71:        return 1L;
                     72: }
                     73: 
                     74: static void write_scc(PORT *port, unsigned char reg, unsigned char data)
                     75: {
                     76:        port->ctl = reg;
                     77:        RECOVERY_DELAY;
                     78:        port->ctl = data;
                     79:        RECOVERY_DELAY;
                     80: }
                     81: 
                     82: static const short SCC_init_string[] = {
                     83:        0x0444,     /* x16 clock mode, 1 stop bit, no parity */
                     84:        0x0104,     /* 'parity is special condition' */
                     85:        0x0260,     /* interrupt vector #s start at 0x60 (lowmem 0x180) */
                     86:        0x03c0,     /* Rx 8 bits/char, disabled */
                     87:        0x05e2,     /* Tx 8 bits/char, disabled, DTR, RTS */
                     88:        0x0600,     /* SDLC (n/a) */
                     89:        0x0700,     /* SDLC (n/a) */
                     90:        0x0901,     /* status low, vector includes status */
                     91:        0x0a00,     /* misc flags */
                     92:        0x0b50,     /* Rx/Tx clocks from baudrate generator output */
                     93:        0x0c18,     /* time const low = 24 | so rate = (24+2)*2/BR clock period */
                     94:        0x0d00,     /* time const hi = 0   | = 52/(8053976/16) => 9680 bps      */
                     95:        0x0e02,     /* baudrate generator source = PCLK (8MHz) */
                     96:        0x0e03,     /* ditto + enable baudrate generator */
                     97:        0x03c1,     /* Rx 8 bits/char, enabled */
                     98:        0x05ea,     /* Tx 8 bits/char, enabled, DTR, RTS */
                     99:        0x0f20,     /* CTS interrupt enable */
                    100:        0x0010,     /* reset external/status interrupts */
                    101:        0x0010,     /* reset again (necessary, see manual) */
                    102:        0x0117,     /* interrupts for Rx, Tx, special condition; parity is special */
                    103:        0x0901,     /* status low, master interrupt disable */
                    104:                    /* NOTE: change above to 0x0909 to enable interrupts! */
                    105:        0xffff      /* end of table marker */
                    106: };
                    107: 
                    108: /*
                    109:  * initialise the SCC
                    110:  */
                    111: static void init_scc(void)
                    112: {
                    113:        SCC *scc = (SCC *)SCC_BASE;
                    114:        const short *p;
                    115: 
                    116:        /* issue hardware reset */
                    117:        scc->portA.ctl = 0x09;
                    118:        RECOVERY_DELAY;
                    119:        scc->portA.ctl = 0xC0;
                    120:        RESET_RECOVERY_DELAY;
                    121: 
                    122:        /* initialise channel A */
                    123:        for (p = SCC_init_string; *p >= 0; p++)
                    124:                write_scc(&scc->portA,HIBYTE(*p),LOBYTE(*p));
                    125: 
                    126:        /* initialise channel B */
                    127:        for (p = SCC_init_string; *p >= 0; p++)
                    128:                write_scc(&scc->portB,HIBYTE(*p),LOBYTE(*p));
                    129: 
                    130:        /*
                    131:         * Enable routing of the SCC interrupt through the SCU like TOS does.
                    132:         * Even though interrupts are not used here, other programs might
                    133:         * install their own interrupt vectors and expect the interrupt
                    134:         * to be available to them.
                    135:         */
                    136:         //if (HAS_VME)
                    137:         //   *(volatile BYTE *)VME_INT_MASK |= VME_INT_SCC;
                    138: }
                    139: 
                    140: int main(int argc, char *argv[])
                    141: {
                    142:        char text[] = "The quick brown fox\njumps over the lazy dog\n";
                    143:        int i;
                    144:        void *sp = (void*)Super(0);
                    145: 
                    146:        init_scc();
                    147: 
                    148:        for (i = 0; text[i] != 0; i++)
                    149:                bconoutB(text[i]);
                    150: 
                    151:        Super(sp);
                    152: 
                    153:        return 0;
                    154: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.