source: rtems/c/src/lib/libbsp/m68k/mrm332/console/sci.c @ ead1281f

5
Last change on this file since ead1281f was ead1281f, checked in by Sebastian Huber <sebastian.huber@…>, on Sep 13, 2017 at 8:13:18 AM

bsp/mrm332: Remove dead code

Update #3132.

  • Property mode set to 100644
File size: 50.5 KB
Line 
1/*****************************************************************************
2* File:     sci.c
3*
4* Desc:     This file contains the console IO routines for the SCI port.
5*           There are two interfaces in this module. One is for the rtems
6*           termios/console code and the other is a device driver interface.
7*           This module works together with the termio module which is
8*           sometimes referred to as the "line disciplines" which implements
9*           terminal i/o processing like tabs, backspaces, and newlines.
10*           The rtems printf uses interrupt io and the rtems printk routine
11*           uses polled io which is better for debugging.
12*
13* Index:    Documentation
14*           Section A  - Include Files
15*           Section B  - Manifest Constants
16*           Section C  - External Data
17*           Section D  - External Functions
18*           Section E  - Local Functions
19*           Section F  - Local Variables
20*           Section G  - A circular data buffer for rcv chars
21*           Section H  - RTEMS termios callbacks for the interrupt api
22*           Section I  - RTEMS termios callbacks for the polled api
23
24*           Section 0  - Miscellaneous routines
25*           Section 1  - Routines to manipulate the circular buffer
26*           Section 2  - Interrupt based entry points for the termios module
27*           Section 3  - Polling based entry points for the termios module
28*           Section 4  - Device driver public api entry points
29*           Section 5  - Hardware level routines
30*           Section 6  - Testing and debugging code
31*
32* Refer:    Motorola QSM Reference Manual - Chapter 5 - SCI sub-module
33*
34* Note:     See bsp.h,confdefs.h,system.h for installing drivers into RTEMS.
35*
36*****************************************************************************/
37
38/*****************************************************************************
39  Overview of serial port console terminal input/output
40*****************************************************************************/
41
42/*
43   +-----------+                               +---------+
44   |    app    |                               |   app   |
45   +-----------+                               +---------+
46         |                                          |
47         | (printf,scanf,etc.)                      |
48         v                                          |
49   +-----------+                                    |
50   |    libc   |                                    |
51   +-----------+                                    |
52         |                                          |
53         |                                          |
54         |     (open,close,read,write,ioctl)        |
55   ======|==========================================|========================
56         | /dev/console                             | /dev/sci
57         | (stdin,stdout,stderr)                    |
58   ======|==========================================|========================
59         |                                          |
60         |                                          |
61         v                                          v
62   +-----------+         +-----------+         +---------+
63   |  console  |  <--->  |  termios  |  <--->  |   sci   |
64   |  driver   |         |  module   |         |  driver |
65   +-----------+         +-----------+         +---------+
66                                                    |
67                                                    |
68                                                    v
69                                               +---------+
70                                               |         |
71                                               |  uart   |
72                                               |         |
73                                               +---------+
74*/
75
76
77/*****************************************************************************
78  Section A - Include Files
79*****************************************************************************/
80
81#include <rtems.h>
82#include <bsp.h>
83#include <rtems/bspIo.h>
84#include <stdio.h>
85#include <rtems/libio.h>
86#include <libchip/serial.h>
87#include <libchip/sersupp.h>
88#include "sci.h"
89#include <rtems/m68k/qsm.h>
90#include <inttypes.h>
91/*#include "../misc/include/cpu332.h" */
92
93/*****************************************************************************
94  Section B - Manifest Constants
95*****************************************************************************/
96
97#define SCI_MINOR       0                   /* minor device number */
98
99/* IMPORTANT - if the device driver api is opened, it means the sci is being
100 * used for direct hardware access, so other users (like termios) get ignored
101 */
102#define DRIVER_CLOSED   0                   /* the device driver api is closed */
103#define DRIVER_OPENED   1                   /* the device driver api is opened */
104
105/* system clock definitions, i dont have documentation on this... */
106
107#if 0 /* Not needed, this is provided in mrm332.h */
108#define XTAL            32768.0    /* crystal frequency in Hz */
109#define NUMB_W          0          /* system clock parameters */
110#define NUMB_X          1
111#define NUMB_Y          0x38       /* for 14.942 Mhz */
112#define NUMB_Y          0x3F       /* for 16.777 Mhz */
113
114#define SYS_CLOCK       (XTAL * 4.0 * (NUMB_Y+1) * (1 << (2 * NUMB_W + NUMB_X)))
115
116#endif
117
118
119/*****************************************************************************
120  Section C - External Data
121*****************************************************************************/
122
123
124
125/*****************************************************************************
126  Section D - External Functions
127*****************************************************************************/
128
129
130
131/*****************************************************************************
132  Section E - Local Functions
133*****************************************************************************/
134
135void SCI_output_char(char c);
136
137/*rtems_isr SciIsr( rtems_vector_number vector );   interrupt handler */
138
139const rtems_termios_callbacks * SciGetTermiosHandlers( int32_t   polled );
140
141rtems_device_driver SciInitialize(                     /* device driver api */
142    rtems_device_major_number, rtems_device_minor_number, void *);
143rtems_device_driver SciOpen(                           /* device driver api */
144    rtems_device_major_number, rtems_device_minor_number, void *);
145rtems_device_driver SciClose(                          /* device driver api */
146    rtems_device_major_number, rtems_device_minor_number, void *);
147rtems_device_driver SciRead(                           /* device driver api */
148    rtems_device_major_number, rtems_device_minor_number, void *);
149rtems_device_driver SciWrite(                          /* device driver api */
150    rtems_device_major_number, rtems_device_minor_number, void *);
151rtems_device_driver SciControl(                        /* device driver api */
152    rtems_device_major_number, rtems_device_minor_number, void *);
153rtems_device_driver SciRead (
154    rtems_device_major_number, rtems_device_minor_number, void *);
155
156rtems_isr SciIsr( rtems_vector_number vector );
157
158int     SciInterruptOpen(int, int, void *);               /* termios api */
159int     SciInterruptClose(int, int, void *);              /* termios api */
160ssize_t SciInterruptWrite(int, const char *, size_t);     /* termios api */
161
162int     SciSetAttributes(int, const struct termios*);     /* termios api */
163int     SciPolledOpen(int, int, void *);                  /* termios api */
164int     SciPolledClose(int, int, void *);                 /* termios api */
165int     SciPolledRead(int);                               /* termios api */
166ssize_t SciPolledWrite(int, const char *, size_t);        /* termios api */
167
168static void SciSetBaud(uint32_t   rate);                /* hardware routine */
169static void SciSetDataBits(uint16_t   bits);            /* hardware routine */
170static void SciSetParity(uint16_t   parity);            /* hardware routine */
171
172static void inline SciDisableAllInterrupts( void );     /* hardware routine */
173static void inline SciDisableTransmitInterrupts( void );/* hardware routine */
174static void inline SciDisableReceiveInterrupts( void ); /* hardware routine */
175
176static void inline SciEnableTransmitInterrupts( void ); /* hardware routine */
177static void inline SciEnableReceiveInterrupts( void );  /* hardware routine */
178
179static void inline SciDisableReceiver( void );          /* hardware routine */
180static void inline SciDisableTransmitter( void );       /* hardware routine */
181
182static void inline SciEnableReceiver( void );           /* hardware routine */
183static void inline SciEnableTransmitter( void );        /* hardware routine */
184
185void SciWriteCharWait  ( uint8_t );                     /* hardware routine */
186void SciWriteCharNoWait( uint8_t );                     /* hardware routine */
187
188uint8_t   inline SciCharAvailable( void );              /* hardware routine */
189
190static uint8_t   inline SciReadCharWait( void );        /* hardware routine */
191static uint8_t   inline SciReadCharNoWait( void );      /* hardware routine */
192
193void SciSendBreak( void );                              /* test routine */
194
195static int8_t   SciRcvBufGetChar(void);                 /* circular rcv buf */
196static void    SciRcvBufPutChar( uint8_t);              /* circular rcv buf */
197#if 0
198static void    SciRcvBufFlush( void );                  /* unused routine */
199#endif
200
201void SciUnitTest(void);                                 /* test routine */
202void SciPrintStats(void);                               /* test routine */
203
204
205/*****************************************************************************
206  Section F - Local Variables
207*****************************************************************************/
208
209static struct rtems_termios_tty *SciTermioTty;
210
211static uint8_t   SciInited = 0;             /* has the driver been inited */
212
213static uint8_t   SciOpened;                 /* has the driver been opened */
214
215static uint8_t   SciMajor;                  /* major device number */
216
217static uint16_t   SciBaud;                  /* current value in baud register */
218
219static uint32_t   SciBytesIn  = 0;          /* bytes received */
220static uint32_t   SciBytesOut = 0;          /* bytes transmitted */
221
222static uint32_t   SciErrorsParity  = 0;     /* error counter */
223static uint32_t   SciErrorsNoise   = 0;     /* error counter */
224static uint32_t   SciErrorsFraming = 0;     /* error counter */
225static uint32_t   SciErrorsOverrun = 0;     /* error counter */
226
227#if defined(CONSOLE_SCI)
228
229/* this is what rtems printk uses to do polling based output */
230
231BSP_output_char_function_type      BSP_output_char = SCI_output_char;
232BSP_polling_getchar_function_type  BSP_poll_char   = NULL;
233
234#endif
235
236/*****************************************************************************
237  Section G - A circular buffer for rcv chars when the driver interface is used.
238*****************************************************************************/
239
240/* it is trivial to wrap your buffer pointers when size is a power of two */
241
242#define SCI_RCV_BUF_SIZE        256         /* must be a power of 2 !!! */
243
244/* if someone opens the sci device using the device driver interface,
245 * then the receive data interrupt handler will put characters in this buffer
246 * instead of sending them up to the termios module for the console
247 */
248static uint8_t   SciRcvBuffer[SCI_RCV_BUF_SIZE];
249
250static uint8_t   SciRcvBufPutIndex = 0; /* array index to put in next char */
251
252static uint8_t   SciRcvBufGetIndex = 0; /* array index to take out next char */
253
254static uint16_t  SciRcvBufCount = 0;   /* how many bytes are in the buffer */
255
256
257
258/*****************************************************************************
259  Section H - RTEMS termios callbacks for the interrupt version of the driver
260*****************************************************************************/
261
262static const rtems_termios_callbacks SciInterruptCallbacks =
263{
264    SciInterruptOpen,                       /* first open */
265    SciInterruptClose,                      /* last close */
266    NULL,                                   /* polled read (not required) */
267    SciInterruptWrite,                      /* write */
268    SciSetAttributes,                       /* set attributes */
269    NULL,                                   /* stop remote xmit */
270    NULL,                                   /* start remote xmit */
271    TRUE                                    /* output uses interrupts */
272};
273
274/*****************************************************************************
275  Section I - RTEMS termios callbacks for the polled version of the driver
276*****************************************************************************/
277
278static const rtems_termios_callbacks SciPolledCallbacks =
279{
280    SciPolledOpen,                          /* first open */
281    SciPolledClose,                         /* last close */
282    SciPolledRead,                          /* polled read */
283    SciPolledWrite,                         /* write */
284    SciSetAttributes,                       /* set attributes */
285    NULL,                                   /* stop remote xmit */
286    NULL,                                   /* start remote xmit */
287    FALSE                                   /* output uses interrupts */
288};
289
290
291/*
292 *                              SECTION 0
293 *                        MISCELLANEOUS ROUTINES
294 */
295
296/****************************************************************************
297 * Func:     SCI_output_char
298 * Desc:     used by rtems printk function to send a char to the uart
299 * Inputs:   the character to transmit
300 * Outputs:  none
301 * Errors:   none
302 * Scope:    public
303 ****************************************************************************/
304
305void SCI_output_char(char c)
306{
307/*  ( minor device number, pointer to the character, length ) */
308
309    SciPolledWrite( SCI_MINOR, &c, 1);
310
311    return;
312}
313
314
315/****************************************************************************
316* Func:     SciGetTermiosHandlers
317* Desc:     returns a pointer to the table of serial io functions
318*           this is called from console_open with polled set to false
319* Inputs:   flag indicating whether we want polled or interrupt driven io
320* Outputs:  pointer to function table
321* Errors:   none
322* Scope:    public
323****************************************************************************/
324
325const rtems_termios_callbacks * SciGetTermiosHandlers( int32_t   polled )
326{
327    if ( polled )
328    {
329        return &SciPolledCallbacks;             /* polling based */
330    }
331    else
332    {
333        return &SciInterruptCallbacks;          /* interrupt driven */
334    }
335}
336
337
338/****************************************************************************
339* Func:     SciIsr
340* Desc:     interrupt handler for serial communications interface
341* Inputs:   vector number - unused
342* Outputs:  none
343* Errors:   none
344* Scope:    public API
345****************************************************************************/
346
347rtems_isr SciIsr( rtems_vector_number vector )
348{
349    uint8_t   ch;
350
351    if ( (*SCSR) & SCI_ERROR_PARITY  )   SciErrorsParity  ++;
352    if ( (*SCSR) & SCI_ERROR_FRAMING )   SciErrorsFraming ++;
353    if ( (*SCSR) & SCI_ERROR_NOISE   )   SciErrorsNoise   ++;
354    if ( (*SCSR) & SCI_ERROR_OVERRUN )   SciErrorsOverrun ++;
355
356    /* see if it was a transmit interrupt */
357    /* data reg empty, xmt complete */
358    if ( ( *SCCR1 & SCI_ENABLE_INT_TX ) && ( (*SCSR) & SCI_XMTR_AVAILABLE ) )
359    {
360        SciDisableTransmitInterrupts();
361
362        /* tell termios module that the charcter was sent */
363        /* he will call us later to transmit more if there are any */
364
365        if (rtems_termios_dequeue_characters( SciTermioTty, 1 ))
366        {
367            /* there are more bytes to transmit so enable TX interrupt */
368
369            SciEnableTransmitInterrupts();
370        }
371    }
372
373    /* see if it was a receive interrupt */
374    /* on the sci uart we just get one character per interrupt */
375
376    while (  SciCharAvailable() )               /* char in data register? */
377    {
378        ch = SciReadCharNoWait();               /* get the char from the uart */
379
380        /* IMPORTANT!!! */
381        /* either send it to the termios module or keep it locally */
382
383        if ( SciOpened == DRIVER_OPENED )       /* the driver is open */
384        {
385            SciRcvBufPutChar(ch);               /* keep it locally */
386        }
387        else                                    /* put in termios buffer */
388        {
389            char c = (char) ch;
390            rtems_termios_enqueue_raw_characters( SciTermioTty, &c, 1 );
391        }
392
393        *SCSR &= SCI_CLEAR_RX_INT;              /* clear the interrupt */
394    }
395}
396
397
398/*
399 *                              SECTION 1
400 *                ROUTINES TO MANIPULATE THE CIRCULAR BUFFER
401 */
402
403/****************************************************************************
404* Func:     SciRcvBufGetChar
405* Desc:     read a character from the circular buffer
406*           make sure there is data before you call this!
407* Inputs:   none
408* Outputs:  the character or -1
409* Errors:   none
410* Scope:    private
411****************************************************************************/
412
413static int8_t   SciRcvBufGetChar(void)
414{
415    rtems_interrupt_level level;
416    uint8_t   ch;
417
418    if ( SciRcvBufCount == 0 )
419    {
420        rtems_fatal_error_occurred(0xDEAD);     /* check the count first! */
421    }
422
423    rtems_interrupt_disable( level );           /* disable interrupts */
424
425    ch = SciRcvBuffer[SciRcvBufGetIndex];       /* get next byte */
426
427    SciRcvBufGetIndex++;                        /* bump the index */
428
429    SciRcvBufGetIndex &= SCI_RCV_BUF_SIZE - 1;  /* and wrap it */
430
431    SciRcvBufCount--;                           /* decrement counter */
432
433    rtems_interrupt_enable( level );            /* restore interrupts */
434
435    return ch;                                  /* return the char */
436}
437
438
439/****************************************************************************
440* Func:     SciRcvBufPutChar
441* Desc:     put a character into the rcv data circular buffer
442* Inputs:   the character
443* Outputs:  none
444* Errors:   none
445* Scope:    private
446****************************************************************************/
447
448static void SciRcvBufPutChar( uint8_t   ch )
449{
450    rtems_interrupt_level level;
451
452    if ( SciRcvBufCount == SCI_RCV_BUF_SIZE )   /* is there room? */
453    {
454        return;                                 /* no, throw it away */
455    }
456
457    rtems_interrupt_disable( level );           /* disable interrupts */
458
459    SciRcvBuffer[SciRcvBufPutIndex] = ch;       /* put it in the buf */
460
461    SciRcvBufPutIndex++;                        /* bump the index */
462
463    SciRcvBufPutIndex &= SCI_RCV_BUF_SIZE - 1;  /* and wrap it */
464
465    SciRcvBufCount++;                           /* increment counter */
466
467    rtems_interrupt_enable( level );            /* restore interrupts */
468
469    return;                                     /* return */
470}
471
472
473/****************************************************************************
474* Func:     SciRcvBufFlush
475* Desc:     completely reset and clear the rcv buffer
476* Inputs:   none
477* Outputs:  none
478* Errors:   none
479* Scope:    private
480****************************************************************************/
481
482#if 0                                           /* prevents compiler warning */
483static void SciRcvBufFlush( void )
484{
485    rtems_interrupt_level level;
486
487    rtems_interrupt_disable( level );           /* disable interrupts */
488
489    memset( SciRcvBuffer, 0, sizeof(SciRcvBuffer) );
490
491    SciRcvBufPutIndex = 0;                      /* clear */
492
493    SciRcvBufGetIndex = 0;                      /* clear */
494
495    SciRcvBufCount = 0;                         /* clear */
496
497    rtems_interrupt_enable( level );            /* restore interrupts */
498
499    return;                                     /* return */
500}
501#endif
502
503
504/*
505 *
506 *                              SECTION 2
507 *            INTERRUPT BASED ENTRY POINTS FOR THE TERMIOS MODULE
508 */
509
510/****************************************************************************
511* Func:     SciInterruptOpen
512* Desc:     open routine for the interrupt based device driver
513*           Default state is 9600 baud, 8 bits, No parity, and 1 stop bit. ??
514**CHANGED** Default baud rate is now 19200, 8N1
515*           called from rtems_termios_open which is called from console_open
516* Inputs:   major - device number
517*           minor - device number
518*           args - points to terminal info
519* Outputs:  success/fail
520* Errors:   none
521* Scope:    public API
522****************************************************************************/
523
524int   SciInterruptOpen(
525    int    major,
526    int    minor,
527    void  *arg
528)
529{
530    rtems_libio_open_close_args_t * args = arg;
531    rtems_isr_entry old_vector;
532
533    if ( minor != SCI_MINOR )                   /* check minor device num */
534    {
535        return -1;
536    }
537
538    if ( !args )                                /* must have args */
539    {
540        return -1;
541    }
542
543    SciTermioTty = args->iop->data1;            /* save address of struct */
544
545    SciDisableAllInterrupts();                  /* turn off sci interrupts */
546
547    /* THIS IS ACTUALLY A BAD THING - SETTING LINE PARAMETERS HERE */
548    /* IT SHOULD BE DONE THROUGH TCSETATTR() WHEN THE CONSOLE IS OPENED!!! */
549
550/*  SciSetBaud(115200);                         set the baud rate */
551/*  SciSetBaud( 57600);                         set the baud rate */
552/*  SciSetBaud( 38400);                         set the baud rate */
553/*  SciSetBaud( 19200);                         set the baud rate */
554    SciSetBaud(  9600);                      /* set the baud rate */
555
556    SciSetParity(SCI_PARITY_NONE);              /* set parity to none */
557
558    SciSetDataBits(SCI_8_DATA_BITS);            /* set data bits to 8 */
559
560    /* Install our interrupt handler into RTEMS. */
561    /* 68 is an unused user-defined vector.  Note that the vector must be */
562    /* even - it sets the low bit for SPI interrupts, and clears it for */
563    /* SCI interrupts.  Also note that vector 66 is used by CPU32bug on */
564    /* the mrm332. */
565
566    rtems_interrupt_catch( SciIsr, 68, &old_vector );
567
568    *QSMCR = (*QSMCR & ~IARB) | 1; // Is 1 a good value for qsm iarb?
569    *QIVR  = 68;
570    *QILR &= 0xf8;
571    *QILR |= 0x06 & 0x07;
572
573    SciEnableTransmitter();                     /* enable the transmitter */
574
575    SciEnableReceiver();                        /* enable the receiver */
576
577    SciEnableReceiveInterrupts();               /* enable rcv interrupts */
578
579    return RTEMS_SUCCESSFUL;
580}
581
582
583/****************************************************************************
584* Func:     SciInterruptClose
585* Desc:     close routine called by the termios module
586* Inputs:   major - device number
587*           minor - device number
588*           args - unused
589* Outputs:  success/fail
590* Errors:   none
591* Scope:    public - termio entry point
592****************************************************************************/
593
594int   SciInterruptClose(
595    int    major,
596    int    minor,
597    void  *arg
598)
599{
600    SciDisableAllInterrupts();
601
602    return RTEMS_SUCCESSFUL;
603}
604
605
606/****************************************************************************
607* Func:     SciInterruptWrite
608* Desc:     writes data to the uart using transmit interrupts
609* Inputs:   minor - device number
610*           buf - points to the data
611*           len - number of bytes to send
612* Outputs:  success/fail
613* Errors:   none
614* Scope:    public API
615****************************************************************************/
616
617ssize_t   SciInterruptWrite(
618    int         minor,
619    const char *buf,
620    size_t      len
621)
622{
623    /* We are using interrupt driven output so termios only sends us */
624    /* one character at a time. The sci does not have a fifo. */
625
626    if ( !len )                                 /* no data? */
627    {
628        return -1;                              /* return error */
629    }
630
631    if ( minor != SCI_MINOR )                   /* check the minor dev num */
632    {
633        return -1;                              /* return error */
634    }
635
636    if ( SciOpened == DRIVER_OPENED )           /* is the driver api open? */
637    {
638        return -1;                              /* yep, throw this away */
639    }
640
641    SciWriteCharNoWait(*buf);                   /* try to send a char */
642
643    *SCSR &= SCI_CLEAR_TDRE;                    /* clear tx data reg empty flag */
644
645    SciEnableTransmitInterrupts();              /* enable the tx interrupt */
646
647    return 0;                                   /* return success */
648}
649
650
651/****************************************************************************
652* Func:     SciSetAttributes
653* Desc:     setup the uart based on the termios modules requests
654* Inputs:   minor - device number
655*           t - pointer to the termios info struct
656* Outputs:  none
657* Errors:   none
658* Scope:    public API
659****************************************************************************/
660
661int   SciSetAttributes(
662    int                   minor,
663    const struct termios *t
664)
665{
666    uint32_t    baud_requested;
667    uint32_t    sci_rate = 0;
668    uint16_t    sci_parity = 0;
669    uint16_t    sci_databits = 0;
670
671    if ( minor != SCI_MINOR )                   /* check the minor dev num */
672    {
673        return -1;                              /* return error */
674    }
675
676    /* if you look closely you will see this is the only thing we use */
677    /* set the baud rate */
678
679    baud_requested = t->c_ospeed;               /* baud rate */
680
681    if (!baud_requested)
682    {
683        baud_requested = B9600;                /* default to 9600 baud */
684       /* baud_requested = B19200;                default to 19200 baud */
685    }
686
687    sci_rate = rtems_termios_baud_to_number( baud_requested );
688
689    /* parity error detection */
690
691    if (t->c_cflag & PARENB)                    /* enable parity detection? */
692    {
693        if (t->c_cflag & PARODD)
694        {
695            sci_parity = SCI_PARITY_ODD;        /* select odd parity */
696        }
697        else
698        {
699            sci_parity = SCI_PARITY_EVEN;       /* select even parity */
700        }
701    }
702    else
703    {
704        sci_parity = SCI_PARITY_NONE;           /* no parity, most common */
705    }
706
707    /*  set the number of data bits, 8 is most common */
708
709    if (t->c_cflag & CSIZE)                     /* was it specified? */
710    {
711        switch (t->c_cflag & CSIZE)
712        {
713            case CS8:   sci_databits = SCI_8_DATA_BITS;   break;
714            default :   sci_databits = SCI_9_DATA_BITS;   break;
715        }
716    }
717    else
718    {
719        sci_databits = SCI_8_DATA_BITS;         /* default to 8 data bits */
720    }
721
722    /*  the number of stop bits; always 1 for SCI */
723
724    if (t->c_cflag & CSTOPB)
725    {
726        /* do nothing */
727    }
728
729    /* setup the hardware with these serial port parameters */
730
731    SciSetBaud(sci_rate);                       /* set the baud rate */
732    SciSetParity(sci_parity);                   /* set the parity type */
733    SciSetDataBits(sci_databits);               /* set the data bits */
734
735    return RTEMS_SUCCESSFUL;
736}
737
738
739/*
740 *
741 *                              SECTION 3
742 *            POLLING BASED ENTRY POINTS FOR THE TERMIOS MODULE
743 */
744
745/****************************************************************************
746* Func:     SciPolledOpen
747* Desc:     open routine for the polled i/o version of the driver
748*           called from rtems_termios_open which is called from console_open
749* Inputs:   major - device number
750*           minor - device number
751*           args - points to terminal info struct
752* Outputs:  success/fail
753* Errors:   none
754* Scope:    public - termios entry point
755****************************************************************************/
756
757int   SciPolledOpen(
758    int   major,
759    int   minor,
760    void *arg
761)
762{
763    rtems_libio_open_close_args_t * args = arg;
764
765    if ( minor != SCI_MINOR )                   /* check minor device num */
766    {
767        return -1;
768    }
769
770    if ( !args )                                /* must have args */
771    {
772        return -1;
773    }
774
775    SciTermioTty = args->iop->data1;            /* Store tty pointer */
776
777    SciDisableAllInterrupts();                  /* don't generate interrupts */
778
779    /* THIS IS ACTUALLY A BAD THING - SETTING LINE PARAMETERS HERE */
780    /* IT SHOULD BE DONE THROUGH TCSETATTR() WHEN THE CONSOLE IS OPENED!!! */
781
782/*  SciSetBaud(115200);                            set the baud rate */
783/*  SciSetBaud( 57600);                            set the baud rate */
784/*  SciSetBaud( 38400);                            set the baud rate */
785/*  SciSetBaud( 19200);                          * set the baud rate */
786    SciSetBaud(  9600);                         /* set the baud rate */
787
788    SciSetParity(SCI_PARITY_NONE);              /* set no parity */
789
790    SciSetDataBits(SCI_8_DATA_BITS);            /* set 8 data bits */
791
792    SciEnableTransmitter();                     /* enable the xmitter */
793
794    SciEnableReceiver();                        /* enable the rcvr */
795
796    return RTEMS_SUCCESSFUL;
797}
798
799
800/****************************************************************************
801* Func:     SciPolledClose
802* Desc:     close routine for the device driver, same for both
803* Inputs:   major - device number
804*           minor - device number
805*           args - unused
806* Outputs:  success/fail
807* Errors:   none
808* Scope:    public termios API
809****************************************************************************/
810
811int   SciPolledClose(
812    int    major,
813    int    minor,
814    void  *arg
815)
816{
817    SciDisableAllInterrupts();
818
819    return RTEMS_SUCCESSFUL;
820}
821
822
823/****************************************************************************
824* Func:     SciPolledRead
825* Desc:     polling based read routine for the uart
826* Inputs:   minor - device number
827* Outputs:  error or the character read
828* Errors:   none
829* Scope:    public API
830****************************************************************************/
831
832int   SciPolledRead(
833    int   minor
834)
835{
836    if ( minor != SCI_MINOR )               /* check the type-punned dev num */
837    {
838        return -1;                          /* return error */
839    }
840
841    if ( SciCharAvailable() )               /* if a char is available */
842    {
843        return SciReadCharNoWait();         /* read the rx data register */
844    }
845
846    return -1;                              /* return error */
847}
848
849
850/****************************************************************************
851* Func:     SciPolledWrite
852* Desc:     writes out characters in polled mode, waiting for the uart
853*           check in console_open, but we only seem to use interrupt mode
854* Inputs:   minor - device number
855*           buf - points to the data
856*           len - how many bytes
857* Outputs:  error or number of bytes written
858* Errors:   none
859* Scope:    public termios API
860****************************************************************************/
861
862ssize_t SciPolledWrite(
863    int         minor,
864    const char *buf,
865    size_t      len
866)
867{
868    ssize_t written = 0;
869
870    if ( minor != SCI_MINOR )                   /* check minor device num */
871    {
872        return -1;
873    }
874
875    if ( SciOpened == DRIVER_OPENED )           /* is the driver api open? */
876    {
877        return -1;                              /* toss the data */
878    }
879
880    /* send each byte in the string out the port */
881
882    while ( written < len )
883    {
884        SciWriteCharWait(*buf++);               /* send a byte */
885
886        written++;                              /* increment counter */
887    }
888
889    return written;                             /* return count */
890}
891
892
893/*
894 *
895 *                              SECTION 4
896 *                 DEVICE DRIVER PUBLIC API ENTRY POINTS
897 */
898
899/****************************************************************************
900* Func:     SciInit
901* Desc:     Initialize the lasers device driver and hardware
902* Inputs:   major - the major device number which is assigned by rtems
903*           minor - the minor device number which is undefined at this point
904*           arg - ?????
905* Outputs:  RTEMS_SUCCESSFUL
906* Errors:   None.
907* Scope:    public API
908****************************************************************************/
909
910rtems_device_driver SciInitialize (
911    rtems_device_major_number major,
912    rtems_device_minor_number minor,
913    void * arg
914)
915{
916/*     rtems_status_code status; */
917
918/*printk("%s\r\n", __FUNCTION__); */
919
920    /* register the SCI device name for termios console i/o
921     * this is done over in console.c which doesn't seem exactly right
922     * but there were problems doing it here...
923     */
924
925/*  status = rtems_io_register_name( "/dev/sci", major, 0 ); */
926
927/*  if (status != RTEMS_SUCCESSFUL) */
928/*      rtems_fatal_error_occurred(status); */
929
930    SciMajor = major;                           /* save the rtems major number */
931
932    SciOpened = DRIVER_CLOSED;                  /* initial state is closed */
933
934    /* if you have an interrupt handler, install it here */
935
936    SciInited = 1;                              /* set the inited flag */
937
938    return RTEMS_SUCCESSFUL;
939}
940
941
942/****************************************************************************
943* Func:     SciOpen
944* Desc:     device driver open routine
945*           you must open a device before you can anything else
946*           only one process can have the device opened at a time
947*           you could look at the task id to restrict access if you want
948* Inputs:   major - the major device number assigned by rtems
949*           minor - the minor device number assigned by us
950*           arg - ?????
951* Outputs:  see below
952* Errors:   none
953* Scope:    public API
954****************************************************************************/
955
956rtems_device_driver SciOpen (
957    rtems_device_major_number major,
958    rtems_device_minor_number minor,
959    void * arg
960)
961{
962/*printk("%s major=%d minor=%d\r\n", __FUNCTION__,major,minor); */
963
964    if (SciInited == 0)                         /* must be initialized first! */
965    {
966        return RTEMS_NOT_CONFIGURED;
967    }
968
969    if (minor != SCI_MINOR)
970    {
971        return RTEMS_INVALID_NAME;              /* verify minor number */
972    }
973
974    if (SciOpened == DRIVER_OPENED)
975    {
976        return RTEMS_RESOURCE_IN_USE;           /* already opened! */
977    }
978
979    SciOpened = DRIVER_OPENED;                  /* set the opened flag */
980
981    return RTEMS_SUCCESSFUL;
982}
983
984
985/****************************************************************************
986* Func:     SciClose
987* Desc:     device driver close routine
988*           the device must be opened before you can close it
989*           the device must be closed before someone (else) can open it
990* Inputs:   major - the major device number
991*           minor - the minor device number
992*           arg - ?????
993* Outputs:  see below
994* Errors:   none
995* Scope:    public API
996****************************************************************************/
997
998rtems_device_driver SciClose (
999    rtems_device_major_number major,
1000    rtems_device_minor_number minor,
1001    void * arg
1002)
1003{
1004/*printk("%s major=%d minor=%d\r\n", __FUNCTION__,major,minor); */
1005
1006    if (minor != SCI_MINOR)
1007    {
1008        return RTEMS_INVALID_NAME;              /* check the minor number */
1009    }
1010
1011    if (SciOpened != DRIVER_OPENED)
1012    {
1013        return RTEMS_INCORRECT_STATE;           /* must be opened first */
1014    }
1015
1016    SciOpened = DRIVER_CLOSED;                  /* set the flag */
1017
1018    return RTEMS_SUCCESSFUL;
1019}
1020
1021
1022/****************************************************************************
1023* Func:     SciRead
1024* Desc:     device driver read routine
1025*           this function is not meaningful for the laser devices
1026* Inputs:   major - the major device number
1027*           minor - the minor device number
1028*           arg - read/write arguments
1029* Outputs:  see below
1030* Errors:   none
1031* Scope:    public API
1032****************************************************************************/
1033
1034rtems_device_driver SciRead (
1035    rtems_device_major_number major,
1036    rtems_device_minor_number minor,
1037    void *arg
1038)
1039{
1040    rtems_libio_rw_args_t *rw_args;             /* ptr to argument struct */
1041    char      *buffer;
1042
1043    rw_args = (rtems_libio_rw_args_t *) arg;    /* arguments to read() */
1044
1045    if (minor != SCI_MINOR)
1046    {
1047        return RTEMS_INVALID_NAME;              /* check the minor number */
1048    }
1049
1050    if (SciOpened == DRIVER_CLOSED)
1051    {
1052        return RTEMS_INCORRECT_STATE;           /* must be opened first */
1053    }
1054
1055    buffer = rw_args->buffer;                   /* points to user's buffer */
1056
1057/*  *buffer = SciReadCharWait();                   wait for a character */
1058
1059    /* if there isn't a character available, wait until one shows up */
1060    /* or the timeout period expires, which ever happens first */
1061
1062    if ( SciRcvBufCount == 0 )                  /* no chars */
1063    {
1064        /* wait for someone to wake me up... */
1065        /*rtems_task_wake_after(SciReadTimeout); */
1066    }
1067
1068    if ( SciRcvBufCount )                       /* any characters locally? */
1069    {
1070        *buffer = SciRcvBufGetChar();           /* get the character */
1071
1072        rw_args->bytes_moved = 1;               /* how many we actually read */
1073    }
1074
1075    return RTEMS_SUCCESSFUL;
1076}
1077
1078
1079/****************************************************************************
1080* Func:     SciWrite
1081* Desc:     device driver write routine
1082*           this function is not meaningful for the laser devices
1083* Inputs:   major - the major device number
1084*           minor - the minor device number
1085*           arg - read/write arguments
1086* Outputs:  see below
1087* Errors:   non3
1088* Scope:    public API
1089****************************************************************************/
1090
1091rtems_device_driver SciWrite (
1092    rtems_device_major_number major,
1093    rtems_device_minor_number minor,
1094    void * arg
1095)
1096{
1097    rtems_libio_rw_args_t *rw_args;             /* ptr to argument struct */
1098    uint8_t   *buffer;
1099    size_t     length;
1100
1101    rw_args = (rtems_libio_rw_args_t *) arg;
1102
1103    if (minor != SCI_MINOR)
1104    {
1105        return RTEMS_INVALID_NAME;              /* check the minor number */
1106    }
1107
1108    if (SciOpened == DRIVER_CLOSED)
1109    {
1110        return RTEMS_INCORRECT_STATE;           /* must be opened first */
1111    }
1112
1113    buffer = (uint8_t*)rw_args->buffer;       /* points to data */
1114
1115    length = rw_args->count;                    /* how many bytes */
1116
1117    while (length--)
1118    {
1119        SciWriteCharWait(*buffer++);            /* send the bytes out */
1120    }
1121
1122    rw_args->bytes_moved = rw_args->count;      /* how many we wrote */
1123
1124    return RTEMS_SUCCESSFUL;
1125}
1126
1127
1128/****************************************************************************
1129* Func:     SciControl
1130* Desc:     device driver control routine
1131*           see below for an example of how to use the ioctl interface
1132* Inputs:   major - the major device number
1133*           minor - the minor device number
1134*           arg - io control args
1135* Outputs:  see below
1136* Errors:   none
1137* Scope:    public API
1138****************************************************************************/
1139
1140rtems_device_driver SciControl (
1141    rtems_device_major_number major,
1142    rtems_device_minor_number minor,
1143    void * arg
1144)
1145{
1146    rtems_libio_ioctl_args_t *args = arg;       /* rtems arg struct */
1147    uint16_t   command;                         /* the cmd to execute */
1148
1149/*printk("%s major=%d minor=%d\r\n", __FUNCTION__,major,minor); */
1150
1151    /* do some sanity checking */
1152
1153    if (minor != SCI_MINOR)
1154    {
1155        return RTEMS_INVALID_NAME;              /* check the minor number */
1156    }
1157
1158    if (SciOpened == DRIVER_CLOSED)
1159    {
1160        return RTEMS_INCORRECT_STATE;           /* must be open first */
1161    }
1162
1163    if (args == 0)
1164    {
1165        return RTEMS_INVALID_ADDRESS;           /* must have args */
1166    }
1167
1168    args->ioctl_return = -1;                    /* assume an error */
1169
1170    command = args->command;                    /* get the command */
1171
1172    if (command == SCI_SEND_BREAK)              /* process the command */
1173    {
1174        SciSendBreak();                         /* send break char */
1175    }
1176
1177    args->ioctl_return = 0;                     /* return status */
1178
1179    return RTEMS_SUCCESSFUL;
1180}
1181
1182
1183/*
1184 *
1185 *                              SECTION 5
1186 *                       HARDWARE LEVEL ROUTINES
1187 */
1188
1189/****************************************************************************
1190* Func:     SciSetBaud
1191* Desc:     setup the uart based on the termios modules requests
1192* Inputs:   baud rate
1193* Outputs:  none
1194* Errors:   none
1195* Scope:    private
1196****************************************************************************/
1197
1198static void SciSetBaud(uint32_t   rate)
1199{
1200    uint16_t   value;
1201    uint16_t   save_sccr1;
1202
1203/* when you open the console you need to set the termio struct baud rate */
1204/* it has a default value of 9600, when someone calls tcsetattr it reverts! */
1205
1206    SciBaud = rate;                             /* save the rate */
1207
1208    /* calculate the register value as a float and convert to an int */
1209    /* set baud rate - you must define the system clock constant */
1210    /* see mrm332.h for an example */
1211
1212    value = ( (uint16_t) ( SYS_CLOCK / rate / 32.0 + 0.5 ) & 0x1fff );
1213
1214    save_sccr1 = *SCCR1;                        /* save register */
1215
1216    /* also turns off the xmtr and rcvr */
1217
1218    *SCCR1 &= SCI_DISABLE_INT_ALL;              /* disable interrupts */
1219
1220    *SCCR0 = value;                             /* write the register */
1221
1222    *SCCR1 = save_sccr1;                        /* restore register */
1223
1224    return;
1225}
1226
1227
1228/****************************************************************************
1229* Func:     SciSetParity
1230* Desc:     setup the uart based on the termios modules requests
1231* Inputs:   parity
1232* Outputs:  none
1233* Errors:   none
1234* Scope:    private
1235****************************************************************************/
1236
1237static void SciSetParity(uint16_t   parity)
1238{
1239    uint16_t   value;
1240
1241    value = *SCCR1;                             /* get the register */
1242
1243    if (parity == SCI_PARITY_ODD)
1244    {
1245        value |= SCI_PARITY_ENABLE;             /* parity enabled */
1246        value |= SCI_PARITY_ODD;                /* parity odd */
1247    }
1248
1249    else if (parity == SCI_PARITY_EVEN)
1250    {
1251        value |= SCI_PARITY_ENABLE;             /* parity enabled */
1252        value &= ~SCI_PARITY_ODD;               /* parity even */
1253    }
1254
1255    else if (parity == SCI_PARITY_NONE)
1256    {
1257        value &= ~SCI_PARITY_ENABLE;            /* disabled, most common */
1258    }
1259
1260    /* else no changes */
1261
1262    *SCCR1 = value;                             /* write the register */
1263
1264    return;
1265}
1266
1267
1268/****************************************************************************
1269* Func:     SciSetDataBits
1270* Desc:     setup the uart based on the termios modules requests
1271* Inputs:   data bits
1272* Outputs:  none
1273* Errors:   none
1274* Scope:    private
1275****************************************************************************/
1276
1277static void SciSetDataBits(uint16_t   bits)
1278{
1279    uint16_t   value;
1280
1281    value = *SCCR1;                             /* get the register */
1282
1283    /* note - the parity setting affects the number of data bits */
1284
1285    if (bits == SCI_9_DATA_BITS)
1286    {
1287        value |= SCI_9_DATA_BITS;               /* 9 data bits */
1288    }
1289
1290    else if (bits == SCI_8_DATA_BITS)
1291    {
1292        value &= SCI_8_DATA_BITS;               /* 8 data bits */
1293    }
1294
1295    /* else no changes */
1296
1297    *SCCR1 = value;                             /* write the register */
1298
1299    return;
1300}
1301
1302
1303/****************************************************************************
1304* Func:     SciDisableAllInterrupts
1305* Func:     SciEnableTransmitInterrupts
1306* Func:     SciEnableReceiveInterrupts
1307* Desc:     handles generation of interrupts by the sci module
1308* Inputs:   none
1309* Outputs:  none
1310* Errors:   none
1311* Scope:    private
1312****************************************************************************/
1313
1314static void inline SciDisableAllInterrupts( void )
1315{
1316    /* this also turns off the xmtr and rcvr */
1317
1318    *SCCR1 &= SCI_DISABLE_INT_ALL;
1319}
1320
1321static void inline SciEnableReceiveInterrupts( void )
1322{
1323    *SCCR1 |= SCI_ENABLE_INT_RX;
1324}
1325
1326static void inline SciDisableReceiveInterrupts( void )
1327{
1328    *SCCR1 &= SCI_DISABLE_INT_RX;
1329}
1330
1331static void inline SciEnableTransmitInterrupts( void )
1332{
1333    *SCCR1 |= SCI_ENABLE_INT_TX;
1334}
1335
1336static void inline SciDisableTransmitInterrupts( void )
1337{
1338    *SCCR1 &= SCI_DISABLE_INT_TX;
1339}
1340
1341
1342/****************************************************************************
1343* Func:     SciEnableTransmitter, SciDisableTransmitter
1344* Func:     SciEnableReceiver,    SciDisableReceiver
1345* Desc:     turns the transmitter and receiver on and off
1346* Inputs:   none
1347* Outputs:  none
1348* Errors:   none
1349* Scope:    private
1350****************************************************************************/
1351
1352static void inline SciEnableTransmitter( void )
1353{
1354    *SCCR1 |= SCI_ENABLE_XMTR;
1355}
1356
1357static void inline SciDisableTransmitter( void )
1358{
1359    *SCCR1 &= SCI_DISABLE_XMTR;
1360}
1361
1362static void inline SciEnableReceiver( void )
1363{
1364    *SCCR1 |= SCI_ENABLE_RCVR;
1365}
1366
1367static void inline SciDisableReceiver( void )
1368{
1369    *SCCR1 &= SCI_DISABLE_RCVR;
1370}
1371
1372
1373/****************************************************************************
1374* Func:     SciWriteCharWait
1375* Desc:     wait for room in the fifo and then put a char in
1376* Inputs:   a byte to send
1377* Outputs:  none
1378* Errors:   none
1379* Scope:    public
1380****************************************************************************/
1381
1382void SciWriteCharWait(uint8_t   c)
1383{
1384    /* poll the fifo, waiting for room for another character */
1385
1386    while ( ( *SCSR & SCI_XMTR_AVAILABLE ) != SCI_XMTR_AVAILABLE )
1387    {
1388        /* Either we are writing to the fifo faster than
1389         * the uart can clock bytes out onto the cable,
1390         * or we are in flow control (actually no, we
1391         * are ignoring flow control from the other end).
1392         * In the first case, higher baud rates will help.
1393         */
1394      /* relinquish processor while waiting */
1395      rtems_task_wake_after(RTEMS_YIELD_PROCESSOR);
1396    }
1397
1398    *SCDR = c;                                  /* send the charcter */
1399
1400    SciBytesOut++;                              /* increment the counter */
1401
1402    return;
1403}
1404
1405/****************************************************************************
1406* Func:     SciWriteCharNoWait
1407* Desc:     if no room in the fifo throw the char on the floor
1408* Inputs:   a byte to send
1409* Outputs:  none
1410* Errors:   none
1411* Scope:    public
1412****************************************************************************/
1413
1414void SciWriteCharNoWait(uint8_t   c)
1415{
1416    if ( ( *SCSR & SCI_XMTR_AVAILABLE ) == 0 )
1417    {
1418        return;                                 /* no room, throw it away */
1419    }
1420
1421    *SCDR = c;                                  /* put the char in the fifo */
1422
1423    SciBytesOut++;                              /* increment the counter */
1424
1425    return;
1426}
1427
1428
1429/****************************************************************************
1430* Func:     SciReadCharWait
1431* Desc:     read a character, waiting for one to show up, if need be
1432* Inputs:   none
1433* Outputs:  a character
1434* Errors:   none
1435* Scope:    public
1436****************************************************************************/
1437
1438static uint8_t   inline SciReadCharWait( void )
1439{
1440    uint8_t   ch;
1441
1442    while ( SciCharAvailable() == 0 )           /* anything there? */
1443    {
1444      /* relinquish processor while waiting */
1445      rtems_task_wake_after(RTEMS_YIELD_PROCESSOR);
1446    }
1447
1448    /* if you have rcv ints enabled, then the isr will probably */
1449    /* get the character before you will unless you turn off ints */
1450    /* ie polling and ints don't mix that well */
1451
1452    ch = *SCDR;                                 /* get the charcter */
1453
1454    SciBytesIn++;                               /* increment the counter */
1455
1456    return ch;                                  /* return the char */
1457}
1458
1459/****************************************************************************
1460* Func:     SciReadCharNoWait
1461* Desc:     try to get a char but dont wait for one
1462* Inputs:   none
1463* Outputs:  a character or -1 if none
1464* Errors:   none
1465* Scope:    public
1466****************************************************************************/
1467
1468static uint8_t   inline SciReadCharNoWait( void )
1469{
1470    uint8_t   ch;
1471
1472    if ( SciCharAvailable() == 0 )              /* anything there? */
1473        return -1;
1474
1475    ch = *SCDR;                                 /* get the character */
1476
1477    SciBytesIn++;                               /* increment the count */
1478
1479    return ch;                                  /* return the char */
1480}
1481
1482
1483/****************************************************************************
1484* Func:     SciCharAvailable
1485* Desc:     is there a receive character in the data register
1486* Inputs:   none
1487* Outputs:  false if no char available, else true
1488* Errors:   none
1489* Scope:    public
1490****************************************************************************/
1491
1492uint8_t   inline SciCharAvailable( void )
1493{
1494    return ( *SCSR & SCI_RCVR_READY );          /* char in data register? */
1495}
1496
1497
1498/****************************************************************************
1499* Func:     SciSendBreak
1500* Desc:     send 1 or tow breaks (all zero bits)
1501* Inputs:   none
1502* Outputs:  none
1503* Errors:   none
1504* Scope:    public
1505****************************************************************************/
1506
1507void SciSendBreak( void )
1508{
1509    /* From the Motorola QSM reference manual - */
1510
1511    /* "if SBK is toggled by writing it first to a one and then immediately */
1512    /* to a zero (in less than one serial frame interval), the transmitter */
1513    /* sends only one or two break frames before reverting to mark (idle) */
1514    /* or before commencing to send more data" */
1515
1516    *SCCR1 |=  SCI_SEND_BREAK;                  /* set the bit */
1517
1518    *SCCR1 &= ~SCI_SEND_BREAK;                  /* clear the bit */
1519
1520    return;
1521}
1522
1523
1524/*
1525 *
1526 *                             SECTION 6
1527 *                             TEST CODE
1528 */
1529
1530/****************************************************************************
1531* Func:     SciUnitTest
1532* Desc:     test the device driver
1533* Inputs:   nothing
1534* Outputs:  nothing
1535* Scope:    public
1536****************************************************************************/
1537
1538#if 0
1539void SciUnitTest()
1540{
1541    uint8_t   byte;                             /* a character */
1542    uint16_t   fd;                              /* file descriptor for device */
1543    uint16_t   result;                          /* result of ioctl */
1544
1545    fd = open("/dev/sci",O_RDWR);               /* open the device */
1546
1547printk("SCI open fd=%d\r\n",fd);
1548
1549    result = write(fd, "abcd\r\n", 6);          /* send a string */
1550
1551printk("SCI write result=%d\r\n",result);
1552
1553    result = read(fd, &byte, 1);                /* read a byte */
1554
1555printk("SCI read result=%d,byte=%x\r\n",result,byte);
1556
1557    return;
1558}
1559#endif
1560
1561
1562/****************************************************************************
1563* Func:     SciPrintStats
1564* Desc:     print out some driver information
1565* Inputs:   nothing
1566* Outputs:  nothing
1567* Scope:    public
1568****************************************************************************/
1569
1570void SciPrintStats ( void )
1571{
1572    printk("\r\n");
1573
1574    printk( "SYS_CLOCK is %2.6f Mhz\r\n\n", SYS_CLOCK / 1000000.0 );
1575
1576    printk( "Current baud rate is %d bps or %d cps\r\n\n", SciBaud, SciBaud / 10 );
1577
1578    printk( "SCI Uart chars in       %8" PRIu32 "\r\n", SciBytesIn       );
1579    printk( "SCI Uart chars out      %8" PRIu32 "\r\n", SciBytesOut      );
1580    printk( "SCI Uart framing errors %8" PRIu32 "\r\n", SciErrorsFraming );
1581    printk( "SCI Uart parity  errors %8" PRIu32 "\r\n", SciErrorsParity  );
1582    printk( "SCI Uart overrun errors %8" PRIu32 "\r\n", SciErrorsOverrun );
1583    printk( "SCI Uart noise   errors %8" PRIu32 "\r\n", SciErrorsNoise   );
1584
1585    return;
1586}
Note: See TracBrowser for help on using the repository browser.