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

4.104.114.84.95
Last change on this file since c0c6168 was c0c6168, checked in by Joel Sherrill <joel.sherrill@…>, on 01/20/03 at 20:33:17

2003-01-20 Duane Gustavus <duane@…>

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