source: rtems/c/src/lib/libbsp/i386/pc386/console/console.c @ cd66632

4.104.114.84.95
Last change on this file since cd66632 was cd66632, checked in by Joel Sherrill <joel.sherrill@…>, on Jul 16, 2002 at 10:32:54 PM

2002-07-16 Eric Norum <eric.norum@…>

  • console/console.c: Others on the rtems-users list have expressed concern about this run-time selection, so I've enclosed the changes in a #ifdef RTEMS_RUNTIME_CONSOLE_SELECT conditional.
  • Property mode set to 100644
File size: 14.6 KB
Line 
1/*-------------------------------------------------------------------------+
2| console.c v1.1 - PC386 BSP - 1997/08/07
3+--------------------------------------------------------------------------+
4| This file contains the PC386 console I/O package.
5+--------------------------------------------------------------------------+
6| (C) Copyright 1997 -
7| - NavIST Group - Real-Time Distributed Systems and Industrial Automation
8|
9| http://pandora.ist.utl.pt
10|
11| Instituto Superior Tecnico * Lisboa * PORTUGAL
12+--------------------------------------------------------------------------+
13| Disclaimer:
14|
15| This file is provided "AS IS" without warranty of any kind, either
16| expressed or implied.
17+--------------------------------------------------------------------------+
18| This code is based on:
19|   console.c,v 1.4 1995/12/19 20:07:23 joel Exp - go32 BSP
20| With the following copyright notice:
21| **************************************************************************
22| *  COPYRIGHT (c) 1989-1999.
23| *  On-Line Applications Research Corporation (OAR).
24| *
25| *  The license and distribution terms for this file may be
26| *  found in found in the file LICENSE in this distribution or at
27| *  http://www.OARcorp.com/rtems/license.html.
28| **************************************************************************
29|
30|  $Id$
31+--------------------------------------------------------------------------*/
32
33#include <stdio.h>
34#include <stdlib.h>
35#include <assert.h>
36#include <unistd.h>
37#undef __assert
38void __assert (const char *file, int line, const char *msg);
39
40#include <bsp.h>
41#include <irq.h>
42#include <rtems/libio.h>
43#include <termios.h>
44#include <uart.h>
45#include <libcpu/cpuModel.h>
46
47#include <rtems/mw_uid.h>
48#include "mouse_parser.h"
49
50/*
51 * Possible value for console input/output :
52 *      BSP_CONSOLE_PORT_CONSOLE
53 *      BSP_UART_COM1
54 *      BSP_UART_COM2
55 *
56 * Note:
57 *   1. Currently BSPPrintkPort, cannot be assigned to COM2,
58 *      it will be fixed soon.
59 *
60 *   2. If both BSPConsolePort and BSPPrintkport are assigned
61 *      to same serial device it does not work that great
62 */
63
64int BSPConsolePort = BSP_CONSOLE_PORT_CONSOLE;
65int BSPPrintkPort  = BSP_CONSOLE_PORT_CONSOLE;
66
67/* int BSPConsolePort = BSP_UART_COM2;  */
68int BSPBaseBaud    = 115200;
69
70extern BSP_polling_getchar_function_type BSP_poll_char;
71extern int getch( void );
72extern void kbd_init( void );
73
74/*-------------------------------------------------------------------------+
75| External Prototypes
76+--------------------------------------------------------------------------*/
77extern void keyboard_interrupt(void);
78extern char BSP_wait_polled_input(void);
79extern void _IBMPC_initVideo(void);
80
81static int  conSetAttr(int minor, const struct termios *);
82static void isr_on(const rtems_irq_connect_data *);
83static void isr_off(const rtems_irq_connect_data *);
84static int  isr_is_on(const rtems_irq_connect_data *);
85
86extern int rtems_kbpoll( void );
87
88static rtems_irq_connect_data console_isr_data = {BSP_KEYBOARD,
89                     keyboard_interrupt,
90                                                   isr_on,
91                                                   isr_off,
92                                                   isr_is_on};
93
94static void
95isr_on(const rtems_irq_connect_data *unused)
96{
97  return;
98}
99                                                   
100static void
101isr_off(const rtems_irq_connect_data *unused)
102{
103  return;
104}
105
106static int
107isr_is_on(const rtems_irq_connect_data *irq)
108{
109  return BSP_irq_enabled_at_i8259s(irq->name);
110}
111
112extern char _IBMPC_inch(void);
113extern int  rtems_kbpoll( void );
114
115static int
116ibmpc_console_write(int minor, const char *buf, int len)
117{
118  int count;
119  for (count = 0; count < len; count++)
120  {
121    _IBMPC_outch( buf[ count ] );
122    if( buf[ count ] == '\n')
123      _IBMPC_outch( '\r' );            /* LF = LF + CR */
124  }
125  return 0;
126}
127
128
129int kbd_poll_read( int minor )
130{
131  if( rtems_kbpoll() )
132  {
133     int c = getch();
134     return c;
135  }
136  return -1;
137}
138
139/*
140static void*         termios_ttyp_console         = NULL;
141void enq_key( char key )
142{
143  if( termios_ttyp_console )
144  {
145          rtems_termios_enqueue_raw_characters(termios_ttyp_console, &key,1 );
146  }
147}
148*/
149
150void __assert (const char *file, int line, const char *msg)
151{
152    static   char exit_msg[] = "EXECUTIVE SHUTDOWN! Any key to reboot...";
153  unsigned char  ch;
154   
155  /*
156   * Note we cannot call exit or printf from here,
157   * assert can fail inside ISR too
158   */
159
160   /*
161   * Close console
162   */
163  close(2);
164  close(1);
165  close(0);
166
167  printk("\nassert failed: %s: ", file);
168  printk("%d: ", line);
169  printk("%s\n\n", msg);
170  printk(exit_msg);
171  ch = BSP_poll_char();
172  printk("\n\n");
173  rtemsReboot();
174
175}
176
177
178/*-------------------------------------------------------------------------+
179| Console device driver INITIALIZE entry point.
180+--------------------------------------------------------------------------+
181| Initilizes the I/O console (keyboard + VGA display) driver.
182+--------------------------------------------------------------------------*/
183rtems_device_driver
184console_initialize(rtems_device_major_number major,
185                   rtems_device_minor_number minor,
186                   void                      *arg)
187{
188  rtems_status_code status;
189
190
191  /* Initialize the KBD interface */
192  kbd_init();
193
194  /*
195   * Set up TERMIOS
196   */
197  rtems_termios_initialize ();
198
199#ifdef RTEMS_RUNTIME_CONSOLE_SELECT
200  /*
201   * If no video card, fall back to serial port console
202   */
203#include <crt.h>
204  if((BSPConsolePort == BSP_CONSOLE_PORT_CONSOLE)
205   && (*(unsigned char*) NB_MAX_ROW_ADDR == 0)
206   && (*(unsigned short*)NB_MAX_COL_ADDR == 0)) {
207    BSPConsolePort = BSP_UART_COM2;
208    BSPPrintkPort  = BSP_UART_COM1;
209  }
210#endif
211
212  /*
213   *  The video was initialized in the start.s code and does not need
214   *  to be reinitialized.
215   */
216
217  if(BSPConsolePort == BSP_CONSOLE_PORT_CONSOLE)
218    {
219      /* Install keyboard interrupt handler */
220      status = BSP_install_rtems_irq_handler(&console_isr_data);
221 
222    if (!status)
223        {
224          printk("Error installing keyboard interrupt handler!\n");
225          rtems_fatal_error_occurred(status);
226        }
227     
228      status = rtems_io_register_name("/dev/console", major, 0);
229      if (status != RTEMS_SUCCESSFUL)
230        {
231          printk("Error registering console device!\n");
232          rtems_fatal_error_occurred(status);
233        }
234      printk("Initialized console on port CONSOLE\n\n");
235    }
236  else
237    {
238      /*
239       * Do device-specific initialization
240       */
241      /* 9600-8-N-1 */
242      BSP_uart_init(BSPConsolePort, 9600, CHR_8_BITS, 0, 0, 0);
243     
244     
245      /* Set interrupt handler */
246      if(BSPConsolePort == BSP_UART_COM1)
247        {
248             console_isr_data.name = BSP_UART_COM1_IRQ;
249        console_isr_data.hdl  = BSP_uart_termios_isr_com1;
250         
251        }
252      else
253           {
254          assert(BSPConsolePort == BSP_UART_COM2);
255          console_isr_data.name = BSP_UART_COM2_IRQ;
256          console_isr_data.hdl  = BSP_uart_termios_isr_com2;
257        }
258      status = BSP_install_rtems_irq_handler(&console_isr_data);
259
260      if (!status){
261          printk("Error installing serial console interrupt handler!\n");
262          rtems_fatal_error_occurred(status);
263      }
264      /*
265       * Register the device
266       */
267      status = rtems_io_register_name ("/dev/console", major, 0);
268      if (status != RTEMS_SUCCESSFUL)
269        {
270          printk("Error registering console device!\n");
271          rtems_fatal_error_occurred (status);
272        }
273
274      if(BSPConsolePort == BSP_UART_COM1)
275        {
276          printk("Initialized console on port COM1 9600-8-N-1\n\n");
277        }
278      else
279        {
280          printk("Initialized console on port COM2 9600-8-N-1\n\n");
281        }
282
283      if(BSPPrintkPort == BSP_UART_COM1)
284        {
285          printk("Warning : This will be the last message on console\n");
286
287          /*
288           * FIXME: cast below defeats the very idea of having
289           * function pointer types defined
290           */
291          BSP_output_char = (BSP_output_char_function_type)
292                              BSP_output_char_via_serial;
293          BSP_poll_char   = (BSP_polling_getchar_function_type)
294                              BSP_poll_char_via_serial;
295        }
296      else if(BSPPrintkPort != BSP_CONSOLE_PORT_CONSOLE)
297        {
298           printk("illegal assignement of projtk channel");
299         rtems_fatal_error_occurred (status);
300        }
301
302    }
303  return RTEMS_SUCCESSFUL;
304} /* console_initialize */
305
306
307static int console_open_count = 0;
308
309static int console_last_close(int major, int minor, void *arg)
310{
311  BSP_remove_rtems_irq_handler (&console_isr_data);
312
313  return 0;
314}
315
316/*-------------------------------------------------------------------------+
317| Console device driver OPEN entry point
318+--------------------------------------------------------------------------*/
319rtems_device_driver
320console_open(rtems_device_major_number major,
321                rtems_device_minor_number minor,
322                void                      *arg)
323{
324  rtems_status_code              status;
325  static rtems_termios_callbacks cb = 
326  {
327    NULL,                     /* firstOpen */
328    console_last_close,       /* lastClose */
329    NULL,          /* pollRead */
330    BSP_uart_termios_write_com1, /* write */
331    conSetAttr,               /* setAttributes */
332    NULL,                     /* stopRemoteTx */
333    NULL,                     /* startRemoteTx */
334    1                         /* outputUsesInterrupts */
335  };
336
337  if(BSPConsolePort == BSP_CONSOLE_PORT_CONSOLE)
338    {
339
340      /* Let's set the routines for termios to poll the
341       * Kbd queue for data
342       */
343      cb.pollRead = kbd_poll_read;
344      cb.outputUsesInterrupts = 0;
345      /* write the "echo" if it is on */
346      cb.write = ibmpc_console_write;
347
348      cb.setAttributes = NULL;
349      ++console_open_count;
350      status = rtems_termios_open (major, minor, arg, &cb);
351      if(status != RTEMS_SUCCESSFUL)
352      {
353         printk("Error openning console device\n");
354      }
355      return status;
356    }
357
358  if(BSPConsolePort == BSP_UART_COM2)
359    {
360      cb.write = BSP_uart_termios_write_com2;
361    }
362
363  status = rtems_termios_open (major, minor, arg, &cb);
364
365  if(status != RTEMS_SUCCESSFUL)
366    {
367      printk("Error openning console device\n");
368      return status;
369    }
370
371  /*
372   * Pass data area info down to driver
373   */
374  BSP_uart_termios_set(BSPConsolePort, 
375                         ((rtems_libio_open_close_args_t *)arg)->iop->data1);
376 
377  /* Enable interrupts  on channel */
378  BSP_uart_intr_ctrl(BSPConsolePort, BSP_UART_INTR_CTRL_TERMIOS);
379
380  return RTEMS_SUCCESSFUL;
381}
382
383/*-------------------------------------------------------------------------+
384| Console device driver CLOSE entry point
385+--------------------------------------------------------------------------*/
386rtems_device_driver
387console_close(rtems_device_major_number major,
388              rtems_device_minor_number minor,
389              void                      *arg)
390{
391   return rtems_termios_close (arg);
392} /* console_close */
393
394 
395/*-------------------------------------------------------------------------+
396| Console device driver READ entry point.
397+--------------------------------------------------------------------------+
398| Read characters from the I/O console. We only have stdin.
399+--------------------------------------------------------------------------*/
400rtems_device_driver
401console_read(rtems_device_major_number major,
402             rtems_device_minor_number minor,
403             void                      *arg)
404{
405 return rtems_termios_read( arg );
406} /* console_read */
407 
408
409/*-------------------------------------------------------------------------+
410| Console device driver WRITE entry point.
411+--------------------------------------------------------------------------+
412| Write characters to the I/O console. Stderr and stdout are the same.
413+--------------------------------------------------------------------------*/
414rtems_device_driver
415console_write(rtems_device_major_number major,
416              rtems_device_minor_number minor,
417              void                    * arg)
418{
419  rtems_libio_rw_args_t *rw_args = (rtems_libio_rw_args_t *)arg;
420  char                  *buffer  = rw_args->buffer;
421  int                    maximum  = rw_args->count;
422
423  if(BSPConsolePort != BSP_CONSOLE_PORT_CONSOLE)
424    {
425      return rtems_termios_write (arg);
426    }
427 
428  /* write data to VGA */
429  ibmpc_console_write( minor, buffer, maximum );
430  rw_args->bytes_moved = maximum;
431  return RTEMS_SUCCESSFUL;
432} /* console_write */
433
434
435extern int vt_ioctl( unsigned int cmd, unsigned long arg);
436 
437/*
438 * Handle ioctl request.
439 */
440rtems_device_driver
441console_control(rtems_device_major_number major,
442                rtems_device_minor_number minor,
443                void                      * arg
444)
445{ 
446        rtems_libio_ioctl_args_t *args = arg;
447        switch (args->command) 
448        {
449           default:
450      if( vt_ioctl( args->command, (unsigned long)args->buffer ) != 0 )
451          return rtems_termios_ioctl (arg);
452                break;
453
454      case MW_UID_REGISTER_DEVICE:
455      printk( "SerialMouse: reg=%s\n", args->buffer );
456      register_kbd_msg_queue( args->buffer, 0 );
457                break;
458
459      case MW_UID_UNREGISTER_DEVICE:
460      unregister_kbd_msg_queue( 0 );
461                break;
462   }
463        args->ioctl_return = 0;
464   return RTEMS_SUCCESSFUL;
465}
466
467static int
468conSetAttr(int minor, const struct termios *t)
469{
470  unsigned long baud, databits, parity, stopbits;
471
472  switch (t->c_cflag & CBAUD) 
473    {
474    case B50:   
475      baud = 50;
476      break;
477    case B75:   
478      baud = 75;       
479      break;
480    case B110: 
481      baud = 110;       
482      break;
483    case B134: 
484      baud = 134;       
485      break;
486    case B150: 
487      baud = 150;       
488      break;
489    case B200:
490      baud = 200;       
491      break;
492    case B300: 
493      baud = 300;
494      break;
495    case B600: 
496      baud = 600;       
497      break;
498    case B1200: 
499      baud = 1200;
500      break;
501    case B1800: 
502      baud = 1800;     
503      break;
504    case B2400: 
505      baud = 2400;
506      break;
507    case B4800: 
508      baud = 4800;
509      break;
510    case B9600: 
511      baud = 9600;
512      break;
513    case B19200:
514      baud = 19200;
515      break;
516    case B38400:
517      baud = 38400;
518      break;
519    case B57600:       
520      baud = 57600;
521      break;
522    case B115200:
523      baud = 115200;
524      break;
525    default:
526      rtems_fatal_error_occurred (RTEMS_INTERNAL_ERROR);
527      return 0;
528    }
529
530  if (t->c_cflag & PARENB) {
531    /* Parity is enabled */
532    if (t->c_cflag & PARODD) {
533      /* Parity is odd */
534      parity = PEN;
535    }
536    else {
537      /* Parity is even */
538      parity = PEN | EPS;
539    }
540  }
541  else {
542    /* No parity */
543    parity = 0;
544  }
545 
546  switch (t->c_cflag & CSIZE) {
547    case CS5: databits = CHR_5_BITS; break;
548    case CS6: databits = CHR_6_BITS; break;
549    case CS7: databits = CHR_7_BITS; break;
550    default: /* just to avoid warnings -- all cases are covered. */
551    case CS8: databits = CHR_8_BITS; break;
552   }
553
554  if (t->c_cflag & CSTOPB) {
555    /* 2 stop bits */
556    stopbits = STB;
557  }
558  else {
559    /* 1 stop bit */
560    stopbits = 0;
561  }
562
563  BSP_uart_set_attributes(BSPConsolePort, baud, databits, parity, stopbits);
564
565  return 0;
566}
567
568/*
569 * BSP initialization
570 */
571
572BSP_output_char_function_type BSP_output_char = 
573                       (BSP_output_char_function_type) _IBMPC_outch;
574
575BSP_polling_getchar_function_type BSP_poll_char = BSP_wait_polled_input;
576
577
Note: See TracBrowser for help on using the repository browser.