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

Subversion Repositories openrisc

[/] [openrisc/] [trunk/] [rtos/] [rtems/] [c/] [src/] [lib/] [libbsp/] [m68k/] [idp/] [console/] [duart.c] - Blame information for rev 773

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 30 unneback
/*
2
 *  $Id: duart.c,v 1.2 2001-09-27 12:00:09 chris Exp $
3
 */
4
 
5
/*#########################################################
6
#
7
# This code is a modified version of what you will find at the
8
# end of the IDP User's manual.  The original code is copyrighted
9
# by Motorola and Motorola Semiconductor Products as well as
10
# Motorola Software products group.
11
#
12
# Modifications to the original IDP code by Doug McBride, Colorado
13
# Space Grant College.  Modifications include a means of accessing
14
# port B of the duart as well as port A as well as modifications for
15
# buffering and RTEMS support.  Modifications are provided
16
# as is and may not be correct.
17
#
18
# Rob Savoye provided the format for the mc68681 header file
19
#
20
# Joel Sherrill provided inspiration for recoding my original assembly
21
# for this file into C (a good idea)
22
#
23
##########################################################*/
24
 
25
#include <bsp.h>
26
#include <ringbuf.h>
27
 
28
rtems_isr C_Receive_ISR(rtems_vector_number vector);
29
extern Ring_buffer_t  Console_Buffer[];
30
 
31
extern unsigned char inbuf[];
32
extern unsigned char inbuf_portb[];
33
extern unsigned tail;
34
extern unsigned tail_portb;
35
unsigned char Pit_initialized = 0;
36
 
37
/*#####################################################################
38
# The volatile routine to initialize the duart -- port a and port b
39
######################################################################*/
40
volatile void init_pit()
41
{
42
  /*
43
   *  ports A & B while configuring PIT by:
44
   *
45
   *    + disable Interrupt Mask Register
46
   *    + disable port A transmitter
47
   *    + disable port A receiver
48
   *    + disable port B transmitter
49
   *    + disable port B receiver
50
   */
51
 
52
  MC68681_WRITE(DUART_ADDR, MC68681_INTERRUPT_MASK_REG, 0x00);
53
  MC68681_WRITE(DUART_ADDR, MC68681_COMMAND_REG_A ,MC68681_MODE_REG_DISABLE_TX);
54
  MC68681_WRITE(DUART_ADDR, MC68681_COMMAND_REG_A, MC68681_MODE_REG_DISABLE_RX);
55
  MC68681_WRITE(DUART_ADDR, MC68681_COMMAND_REG_B, MC68681_MODE_REG_DISABLE_TX);
56
  MC68681_WRITE(DUART_ADDR, MC68681_COMMAND_REG_B, MC68681_MODE_REG_DISABLE_RX);
57
 
58
  /*
59
   *  install ISR for ports A and B
60
   */
61
  set_vector(C_Receive_ISR, (VECT+H3VECT), 1);
62
 
63
  /*
64
   *  initialize pit
65
   *
66
   *  set mode to 0 -- disable all ports
67
   *  set up pirq and piack
68
   *  all pins on port b are input
69
   *  submode 1x, h3 interrupt enabled
70
   *  setup pivr
71
   *  turn on all ports
72
   */
73
  MC68230_WRITE(PGCR, 0x00);
74
  MC68230_WRITE(PSRR, 0x18);
75
  MC68230_WRITE(PBDDR, 0x00);
76
  MC68230_WRITE(PBCR, 0x82);
77
  MC68230_WRITE(PIVR, VECT);
78
  MC68230_WRITE(PGCR, 0x20);
79
 
80
  /*
81
   *  For some reason, the reset of receiver/transmitter only works for
82
   *  the first time around -- it garbles the output otherwise
83
   *  (e.g., sp21)
84
   */
85
  if (!Pit_initialized)
86
  {
87
    /*
88
     * initialize the duart registers on port b
89
     * WARNING:OPTIMIZER MAY ONLY EXECUTE THIRD STATEMENT IF NOT VOLATILE
90
     *
91
     *  reset tx, channel b
92
     *  reset rx, channel b
93
     *  reset mr pointer, ch
94
     */
95
     MC68681_WRITE(DUART_ADDR, MC68681_COMMAND_REG_B, MC68681_MODE_REG_RESET_TX);
96
     MC68681_WRITE(DUART_ADDR, MC68681_COMMAND_REG_B, MC68681_MODE_REG_RESET_RX);
97
     MC68681_WRITE(DUART_ADDR, MC68681_COMMAND_REG_B, MC68681_MODE_REG_RESET_MR_PTR);
98
 
99
    /*
100
     * initialize the duart registers on port a
101
     * WARNING:OPTIMIZER MAY ONLY EXECUTE THIRD STATEMENT IF NOT VOLATILE
102
     *
103
     *  reset tx, channel a
104
     *  reset rx, channel a
105
     *  reset mr pointer, ch
106
     */
107
     MC68681_WRITE(DUART_ADDR, MC68681_COMMAND_REG_A, MC68681_MODE_REG_RESET_TX);
108
     MC68681_WRITE(DUART_ADDR, MC68681_COMMAND_REG_A, MC68681_MODE_REG_RESET_RX);
109
     MC68681_WRITE(DUART_ADDR, MC68681_COMMAND_REG_A, MC68681_MODE_REG_RESET_MR_PTR);
110
 
111
     Pit_initialized = 1;
112
  }
113
 
114
  /*
115
   * Init the general registers of the duart
116
   *
117
   * init ivr
118
   * init imr
119
   * init acr
120
   * init ctur
121
   * init ctlr
122
   * init opcr
123
   * init cts
124
   */
125
  MC68681_WRITE(DUART_ADDR, MC68681_INTERRUPT_VECTOR_REG,
126
                MC68681_INTERRUPT_VECTOR_INIT);
127
  MC68681_WRITE(DUART_ADDR, MC68681_INTERRUPT_MASK_REG,
128
                MC68681_IR_RX_READY_A | MC68681_IR_RX_READY_B);
129
  MC68681_WRITE(DUART_ADDR, MC68681_AUX_CTRL_REG, MC68681_CLEAR);
130
  MC68681_WRITE(DUART_ADDR, MC68681_COUNTER_TIMER_UPPER_REG, 0x00);
131
  MC68681_WRITE(DUART_ADDR, MC68681_COUNTER_TIMER_LOWER_REG, 0x02);
132
  MC68681_WRITE(DUART_ADDR, MC68681_OUTPUT_PORT_CONFIG_REG, MC68681_CLEAR);
133
  MC68681_WRITE(DUART_ADDR, MC68681_OUTPUT_PORT_SET_REG, 0x01);
134
 
135
  /*
136
   * init the actual serial port for port a
137
   *
138
   * Set Baud Rate to 9600
139
   * Set Stop bit length of 1
140
   * enable Transmit and receive
141
   */
142
  MC68681_WRITE(DUART_ADDR, MC68681_CLOCK_SELECT_REG_A, MC68681_BAUD_RATE_MASK_9600);
143
  MC68681_WRITE(DUART_ADDR, MC68681_MODE_REG_1A,
144
                (MC68681_8BIT_CHARS | MC68681_NO_PARITY));
145
  MC68681_WRITE(DUART_ADDR, MC68681_MODE_REG_2A,MC68681_STOP_BIT_LENGTH_1);
146
  MC68681_WRITE(DUART_ADDR, MC68681_COMMAND_REG_A,
147
                (MC68681_MODE_REG_ENABLE_TX | MC68681_MODE_REG_ENABLE_RX));
148
 
149
  /*
150
   * init the actual serial port for port b
151
   * init csrb -- 9600 baud
152
   */
153
  MC68681_WRITE(DUART_ADDR, MC68681_CLOCK_SELECT_REG_B, MC68681_BAUD_RATE_MASK_9600);
154
 
155
 
156
#define EIGHT_BITS_NO_PARITY
157
#ifdef EIGHT_BITS_NO_PARITY
158
  /*
159
   * Set 8 Bit characters with no parity
160
   */
161
  MC68681_WRITE(DUART_ADDR, MC68681_MODE_REG_1B,
162
                (MC68681_NO_PARITY | MC68681_8BIT_CHARS) );
163
#else 
164
  /*
165
   * Set 7 Bit Characters with parity
166
   */
167
  MC68681_WRITE(DUART_ADDR, MC68681_MODE_REG_1B,
168
                (MC68681_WITH_PARITY |  MC68681_7BIT_CHARS) );
169
#endif
170
 
171
 
172
  /*
173
   * Set Stop Bit length to 1
174
   * Disable Recieve and transmit on B
175
   */
176
  MC68681_WRITE(DUART_ADDR, MC68681_MODE_REG_2B,MC68681_STOP_BIT_LENGTH_1);
177
  MC68681_WRITE(DUART_ADDR, MC68681_COMMAND_REG_B,
178
                (MC68681_MODE_REG_ENABLE_TX | MC68681_MODE_REG_ENABLE_RX) );
179
}
180
 
181
/*#####################################################################
182
# interrupt handler for receive of character from duart on ports A & B
183
#####################################################################*/
184
rtems_isr C_Receive_ISR(rtems_vector_number vector)
185
{
186
  volatile unsigned char *_addr;
187
 
188
  /*
189
   *  Clear pit interrupt.
190
   */
191
  _addr = (unsigned char *) (PIT_ADDR + PITSR);
192
  *_addr = 0x04;
193
 
194
  /*
195
   *  check port A first for input
196
   *     extract rcvrdy on port B
197
   *     set ptr to recieve buffer and read character into ring buffer
198
   */
199
  _addr = (unsigned char *) (DUART_ADDR + MC68681_STATUS_REG_A);
200
  if (*_addr & MC68681_RX_READY)  /* extract rcvrdy on port A */
201
  {
202
    _addr = (unsigned char *) (DUART_ADDR + MC68681_RECEIVE_BUFFER_A);
203
    Ring_buffer_Add_character( &Console_Buffer[ 0 ], *_addr );
204
  }
205
 
206
  /*
207
   *  If not on port A, let's check port B
208
   *     extract rcvrdy on port B
209
   *     set ptr to recieve buffer and read character into ring buffer
210
   */
211
  else
212
  {
213
    _addr = (unsigned char *) (DUART_ADDR + MC68681_STATUS_REG_B);
214
    if (*_addr & MC68681_RX_READY)  /* extract rcvrdy on port B */
215
    {
216
      _addr = (unsigned char *) (DUART_ADDR + MC68681_RECEIVE_BUFFER_B);
217
      Ring_buffer_Add_character( &Console_Buffer[ 1 ], *_addr );
218
    }
219
 
220
    /*
221
     * if not ready on port A or port B, must be an error
222
     * if error, get out so that fifo is undisturbed
223
     */
224
  }
225
}
226
 
227
/*#####################################################################
228
# This is the routine that actually transmits a character one at a time
229
# This routine transmits on port A of the IDP board
230
#####################################################################*/
231
void transmit_char(char ch)
232
{
233
  volatile unsigned char *_addr;
234
 
235
  /*
236
   * Get SRA (extract txrdy)
237
   */
238
  _addr = (unsigned char *) (DUART_ADDR + MC68681_STATUS_REG_A);
239
  while (!(*_addr & MC68681_TX_READY))
240
  {
241
  }
242
 
243
  /*
244
   * transmit character over port A
245
   */
246
  MC68681_WRITE(DUART_ADDR, MC68681_TRANSMIT_BUFFER_A, ch);
247
}
248
 
249
 
250
/*#####################################################################
251
# This is the routine that actually transmits a character one at a time
252
# This routine transmits on port B of the IDP board
253
#####################################################################*/
254
void transmit_char_portb(char ch)
255
{
256
  volatile unsigned char *_addr;
257
 
258
  /*
259
   * Get SRB (extract txrdy)
260
   */
261
  _addr = (unsigned char *) (DUART_ADDR + MC68681_STATUS_REG_B);
262
  while (!(*_addr &  MC68681_TX_READY))
263
  {
264
  }
265
 
266
  /*
267
   * transmit character over port B
268
   */
269
  MC68681_WRITE(DUART_ADDR, MC68681_TRANSMIT_BUFFER_B, ch);
270
}

powered by: WebSVN 2.1.0

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