root / Version 1.8 / RS232_MUX.X / hardware_TL16C754C.h @ c82771d8
Historique | Voir | Annoter | Télécharger (20,707 ko)
1 | c82771d8 | Enzo Niro | /* Microchip Technology Inc. and its subsidiaries. You may use this software
|
---|---|---|---|
2 | * and any derivatives exclusively with Microchip products.
|
||
3 | *
|
||
4 | * THIS SOFTWARE IS SUPPLIED BY MICROCHIP "AS IS". NO WARRANTIES, WHETHER
|
||
5 | * EXPRESS, IMPLIED OR STATUTORY, APPLY TO THIS SOFTWARE, INCLUDING ANY IMPLIED
|
||
6 | * WARRANTIES OF NON-INFRINGEMENT, MERCHANTABILITY, AND FITNESS FOR A
|
||
7 | * PARTICULAR PURPOSE, OR ITS INTERACTION WITH MICROCHIP PRODUCTS, COMBINATION
|
||
8 | * WITH ANY OTHER PRODUCTS, OR USE IN ANY APPLICATION.
|
||
9 | *
|
||
10 | * IN NO EVENT WILL MICROCHIP BE LIABLE FOR ANY INDIRECT, SPECIAL, PUNITIVE,
|
||
11 | * INCIDENTAL OR CONSEQUENTIAL LOSS, DAMAGE, COST OR EXPENSE OF ANY KIND
|
||
12 | * WHATSOEVER RELATED TO THE SOFTWARE, HOWEVER CAUSED, EVEN IF MICROCHIP HAS
|
||
13 | * BEEN ADVISED OF THE POSSIBILITY OR THE DAMAGES ARE FORESEEABLE. TO THE
|
||
14 | * FULLEST EXTENT ALLOWED BY LAW, MICROCHIP'S TOTAL LIABILITY ON ALL CLAIMS
|
||
15 | * IN ANY WAY RELATED TO THIS SOFTWARE WILL NOT EXCEED THE AMOUNT OF FEES, IF
|
||
16 | * ANY, THAT YOU HAVE PAID DIRECTLY TO MICROCHIP FOR THIS SOFTWARE.
|
||
17 | *
|
||
18 | * MICROCHIP PROVIDES THIS SOFTWARE CONDITIONALLY UPON YOUR ACCEPTANCE OF THESE
|
||
19 | * TERMS.
|
||
20 | */
|
||
21 | |||
22 | /*
|
||
23 | * File: hardware_TL16C754C.h
|
||
24 | * Author: Enzo Niro
|
||
25 | * Comments: Library for MUX232 to handle TL16C754C chip
|
||
26 | * Revision history: 1.9
|
||
27 | */
|
||
28 | |||
29 | |||
30 | #ifndef RS232_HARDWARETL16_H
|
||
31 | #define RS232_HARDWARETL16_H
|
||
32 | |||
33 | #include <xc.h> // include processor files - each processor file is guarded. |
||
34 | #include "hardware_config.h" |
||
35 | |||
36 | |||
37 | ////////////////////////////////////////////////
|
||
38 | //Bytes array
|
||
39 | uint8_t _TL16C_invertAddr[] = { |
||
40 | 0x00, 0x04, 0x02, 0x06, 0x01, 0x05, 0x03, 0x07 |
||
41 | }; |
||
42 | |||
43 | uint8_t _TL16C_invertData[] = { |
||
44 | 0x00, 0x80, 0x40, 0xc0, 0x20, 0xa0, 0x60, 0xe0, |
||
45 | 0x10, 0x90, 0x50, 0xd0, 0x30, 0xb0, 0x70, 0xf0, |
||
46 | 0x08, 0x88, 0x48, 0xc8, 0x28, 0xa8, 0x68, 0xe8, |
||
47 | 0x18, 0x98, 0x58, 0xd8, 0x38, 0xb8, 0x78, 0xf8, |
||
48 | 0x04, 0x84, 0x44, 0xc4, 0x24, 0xa4, 0x64, 0xe4, |
||
49 | 0x14, 0x94, 0x54, 0xd4, 0x34, 0xb4, 0x74, 0xf4, |
||
50 | 0x0c, 0x8c, 0x4c, 0xcc, 0x2c, 0xac, 0x6c, 0xec, |
||
51 | 0x1c, 0x9c, 0x5c, 0xdc, 0x3c, 0xbc, 0x7c, 0xfc, |
||
52 | 0x02, 0x82, 0x42, 0xc2, 0x22, 0xa2, 0x62, 0xe2, |
||
53 | 0x12, 0x92, 0x52, 0xd2, 0x32, 0xb2, 0x72, 0xf2, |
||
54 | 0x0a, 0x8a, 0x4a, 0xca, 0x2a, 0xaa, 0x6a, 0xea, |
||
55 | 0x1a, 0x9a, 0x5a, 0xda, 0x3a, 0xba, 0x7a, 0xfa, |
||
56 | 0x06, 0x86, 0x46, 0xc6, 0x26, 0xa6, 0x66, 0xe6, |
||
57 | 0x16, 0x96, 0x56, 0xd6, 0x36, 0xb6, 0x76, 0xf6, |
||
58 | 0x0e, 0x8e, 0x4e, 0xce, 0x2e, 0xae, 0x6e, 0xee, |
||
59 | 0x1e, 0x9e, 0x5e, 0xde, 0x3e, 0xbe, 0x7e, 0xfe, |
||
60 | 0x01, 0x81, 0x41, 0xc1, 0x21, 0xa1, 0x61, 0xe1, |
||
61 | 0x11, 0x91, 0x51, 0xd1, 0x31, 0xb1, 0x71, 0xf1, |
||
62 | 0x09, 0x89, 0x49, 0xc9, 0x29, 0xa9, 0x69, 0xe9, |
||
63 | 0x19, 0x99, 0x59, 0xd9, 0x39, 0xb9, 0x79, 0xf9, |
||
64 | 0x05, 0x85, 0x45, 0xc5, 0x25, 0xa5, 0x65, 0xe5, |
||
65 | 0x15, 0x95, 0x55, 0xd5, 0x35, 0xb5, 0x75, 0xf5, |
||
66 | 0x0d, 0x8d, 0x4d, 0xcd, 0x2d, 0xad, 0x6d, 0xed, |
||
67 | 0x1d, 0x9d, 0x5d, 0xdd, 0x3d, 0xbd, 0x7d, 0xfd, |
||
68 | 0x03, 0x83, 0x43, 0xc3, 0x23, 0xa3, 0x63, 0xe3, |
||
69 | 0x13, 0x93, 0x53, 0xd3, 0x33, 0xb3, 0x73, 0xf3, |
||
70 | 0x0b, 0x8b, 0x4b, 0xcb, 0x2b, 0xab, 0x6b, 0xeb, |
||
71 | 0x1b, 0x9b, 0x5b, 0xdb, 0x3b, 0xbb, 0x7b, 0xfb, |
||
72 | 0x07, 0x87, 0x47, 0xc7, 0x27, 0xa7, 0x67, 0xe7, |
||
73 | 0x17, 0x97, 0x57, 0xd7, 0x37, 0xb7, 0x77, 0xf7, |
||
74 | 0x0f, 0x8f, 0x4f, 0xcf, 0x2f, 0xaf, 0x6f, 0xef, |
||
75 | 0x1f, 0x9f, 0x5f, 0xdf, 0x3f, 0xbf, 0x7f, 0xff, |
||
76 | }; |
||
77 | |||
78 | //////////////////////////////////////
|
||
79 | //prototypes functions
|
||
80 | |||
81 | |||
82 | //////////////////////////
|
||
83 | //High level functions
|
||
84 | |||
85 | void initPortA(uint8_t busSpeed, uint8_t dataBits, uint8_t parity, uint8_t stopBit);
|
||
86 | void initPortB(uint8_t busSpeed, uint8_t dataBits, uint8_t parity, uint8_t stopBit);
|
||
87 | void initPortC(uint8_t busSpeed, uint8_t dataBits, uint8_t parity, uint8_t stopBit);
|
||
88 | void initPortD(uint8_t busSpeed, uint8_t dataBits, uint8_t parity, uint8_t stopBit);
|
||
89 | |||
90 | //Send bytes throught serial port
|
||
91 | void txWriteA(uint8_t b);
|
||
92 | void txWriteB(uint8_t b);
|
||
93 | void txWriteC(uint8_t b);
|
||
94 | void txWriteD(uint8_t b);
|
||
95 | |||
96 | //Receive bytes from serial port
|
||
97 | uint8_t rxReadA(void);
|
||
98 | uint8_t rxReadB(void);
|
||
99 | uint8_t rxReadC(void);
|
||
100 | uint8_t rxReadD(void);
|
||
101 | |||
102 | //RX buffer control
|
||
103 | |||
104 | //available functions
|
||
105 | bool portA_available();
|
||
106 | bool portB_available();
|
||
107 | bool portC_available();
|
||
108 | bool portD_available();
|
||
109 | |||
110 | //parity functions
|
||
111 | |||
112 | bool getParitySetA();
|
||
113 | bool getParitySetB();
|
||
114 | bool getParitySetC();
|
||
115 | bool getParitySetD();
|
||
116 | |||
117 | /*
|
||
118 |
|
||
119 | TODO : Implement functions...
|
||
120 |
|
||
121 | */
|
||
122 | |||
123 | |||
124 | //////////////////////////
|
||
125 | //Low level functions
|
||
126 | |||
127 | |||
128 | void writePortA(uint8_t reg, uint8_t addr);
|
||
129 | void writePortB(uint8_t reg, uint8_t addr);
|
||
130 | void writePortC(uint8_t reg, uint8_t addr);
|
||
131 | void writePortD(uint8_t reg, uint8_t addr);
|
||
132 | uint8_t readPortA(uint8_t addr); |
||
133 | uint8_t readPortB(uint8_t addr); |
||
134 | uint8_t readPortC(uint8_t addr); |
||
135 | uint8_t readPortD(uint8_t addr); |
||
136 | |||
137 | |||
138 | void setWait(uint16_t cnt); //fast delay |
||
139 | |||
140 | |||
141 | //////////////////////////////////////////////////////////
|
||
142 | //Values definitions (not supposed to use it directly)
|
||
143 | |||
144 | #define DLAB_ERF_EN_BIT 0x80 |
||
145 | |||
146 | |||
147 | #define LCR_REG 0x3 //Static register |
||
148 | |||
149 | ///////////////////////////////////////////
|
||
150 | // READ Registers
|
||
151 | |||
152 | #define RHR_REG 0x0 |
||
153 | #define IIR_REG 0x2 |
||
154 | #define LSR_REG 0x5 |
||
155 | #define MSR_REG 0x6 |
||
156 | #define FIFORDY_REG 0x7 |
||
157 | |||
158 | ///////////////////////////////////////////
|
||
159 | // WRITE Registers
|
||
160 | |||
161 | #define THR_REG 0x0 |
||
162 | #define FCR_REG 0x2 |
||
163 | |||
164 | ///////////////////////////////////////////
|
||
165 | // READ/WRITE Registers
|
||
166 | |||
167 | #define IER_REG 0x1 |
||
168 | #define LCR_REG 0x3 |
||
169 | #define MCR_REG 0x4 |
||
170 | #define SPR_REG 0x7 |
||
171 | #define DLL_REG 0x0 |
||
172 | #define DLH_REG 0x1 |
||
173 | #define EFR_REG 0x2 |
||
174 | #define XON1_REG 0x4 |
||
175 | #define XON2_REG 0x5 |
||
176 | #define XOFF1_REG 0x6 |
||
177 | #define XOFF2_REG 0x7 |
||
178 | #define TCR_REG 0x6 |
||
179 | #define TLR_REG 0x7 |
||
180 | |||
181 | |||
182 | |||
183 | |||
184 | ///////////////////////////////////////////////////////
|
||
185 | //CTRL, ADDR and DATA buses
|
||
186 | |||
187 | //Data pins
|
||
188 | #define DATAWRITE(x) PORTD.OUT = _TL16C_invertData[x]
|
||
189 | #define DATADIR(x) PORTD.DIR = _TL16C_invertData[x]
|
||
190 | #define DATAREAD _TL16C_invertData[PORTD.IN]
|
||
191 | |||
192 | //Address pins
|
||
193 | #define ADDRWRITE(x) PORTE.OUT = _TL16C_invertAddr[x]
|
||
194 | #define ADDR_ENABLE PORTE.DIR |= 0x07 |
||
195 | |||
196 | |||
197 | //Controls pins
|
||
198 | #define ENABLE_POW_SUPPLY_PIN PORTF.DIR |= 0x01 |
||
199 | #define ENABLE_WR_RD_PINS PORTB.DIR |= 0x30 |
||
200 | #define ENABLE_CS_PINS PORTB.DIR |= 0x0F |
||
201 | #define ENABLE_RESET_PIN PORTE.DIR |= 0x08 |
||
202 | #define POWER_ON PORTF.OUT |= 0x01 |
||
203 | #define POWER_OFF PORTF.OUT &= ~(0x01) |
||
204 | #define SETRST PORTE.OUT |= 0x08 |
||
205 | #define SETWR PORTB.OUT |= 0x10 |
||
206 | #define SETRD PORTB.OUT |= 0x20 |
||
207 | #define SETCSA PORTB.OUT |= 0x01 |
||
208 | #define SETCSB PORTB.OUT |= 0x02 |
||
209 | #define SETCSC PORTB.OUT |= 0x04 |
||
210 | #define SETCSD PORTB.OUT |= 0x08 |
||
211 | #define CLRRST PORTE.OUT &= ~(0x08) |
||
212 | #define CLRWR PORTB.OUT &= ~(0x10) |
||
213 | #define CLRRD PORTB.OUT &= ~(0x20) |
||
214 | #define CLRCSA PORTB.OUT &= ~(0x01) |
||
215 | #define CLRCSB PORTB.OUT &= ~(0x02) |
||
216 | #define CLRCSC PORTB.OUT &= ~(0x04) |
||
217 | #define CLRCSD PORTB.OUT &= ~(0x08) |
||
218 | |||
219 | |||
220 | ///////////////////////////////////////////////////////////////////////////////
|
||
221 | //Private vars
|
||
222 | |||
223 | bool _portA_parity_set;
|
||
224 | bool _portB_parity_set;
|
||
225 | bool _portC_parity_set;
|
||
226 | bool _portD_parity_set;
|
||
227 | |||
228 | |||
229 | |||
230 | ///////////////////////////////////////////////////////////////////////////////
|
||
231 | //Functions
|
||
232 | |||
233 | //////////////////////////////////////
|
||
234 | //High level functions
|
||
235 | |||
236 | void initPortA(uint8_t busSpeed, uint8_t dataBits, uint8_t parity, uint8_t stopBit)
|
||
237 | { |
||
238 | |||
239 | uint16_t speedCfg[] = { DL_9600_BAUDS, DL_19200_BAUDS, DL_38400_BAUDS }; |
||
240 | uint8_t parityCfg[] = { TL16C_NO_PARITY, TL16C_EVEN_PARITY, TL16C_ODD_PARITY }; |
||
241 | uint8_t dataCfg[] = { F5BIT_MODE, F6BIT_MODE, F7BIT_MODE, F8BIT_MODE }; |
||
242 | uint8_t stopCfg[] = { ONE_STOPBIT, TWO_STOPBITS }; |
||
243 | |||
244 | |||
245 | uint8_t regVal = 0; //temp value for reading register and change it's value without clearing it |
||
246 | |||
247 | _portA_parity_set = (parity > 0); //Parity set (even or odd) ? |
||
248 | |||
249 | |||
250 | //Read register first...
|
||
251 | regVal = readPortA(LCR_REG); |
||
252 | //_delay_ms(1);
|
||
253 | setWait(20);
|
||
254 | regVal = DLAB_ERF_EN_BIT; //set LCR[7] = 1 -> enable divisor latch mode
|
||
255 | writePortA(regVal, LCR_REG); //switch Mode
|
||
256 | //_delay_ms(1);
|
||
257 | setWait(20);
|
||
258 | //Set bus speed (according of 8MHz OSC. -> DL = Fosc/(16*Fbauds*DIV));
|
||
259 | //DIV = 1 or 4 (see TL16C datasheet p.14), we use here DIV = 1
|
||
260 | writePortA(0x00, DLH_REG); //Always 0x00 in our cfg... MAX 12MHz |
||
261 | //_delay_ms(1);
|
||
262 | setWait(20);
|
||
263 | //writePortA(busSpeed > 2 ? DL_38400_BAUDS : baudsValues[busSpeed], DLL_REG);
|
||
264 | writePortA(speedCfg[busSpeed], DLL_REG); |
||
265 | //_delay_ms(1);
|
||
266 | setWait(20);
|
||
267 | |||
268 | regVal = readPortA(LCR_REG); |
||
269 | regVal &= ~(DLAB_ERF_EN_BIT); //set LCR[7] = 0 -> disable divisor latch mode
|
||
270 | |||
271 | //regVal |= dataBits > 3 ? TL16C_WORD_8BITS : wordValues[dataBits]; //set 8bits mode
|
||
272 | //regVal |= (stopBit > 1 ? TL16C_STOPBIT_TWO : stopBitValues[stopBit]) << 2; //set stop bits
|
||
273 | //regVal |= (parity > 2 ? TL16C_PARITY_EVEN : parityValues[parity]) << 3; //set stop bits
|
||
274 | regVal |= dataCfg[dataBits]; //set 8bits mode
|
||
275 | regVal |= stopCfg[stopBit] << 2; //set stop bits |
||
276 | regVal |= parityCfg[parity] << 3; //set stop bits |
||
277 | writePortA(regVal, LCR_REG); |
||
278 | //_delay_ms(1);
|
||
279 | setWait(20);
|
||
280 | writePortA(0x01, FCR_REG); //enable FIFO |
||
281 | setWait(20);
|
||
282 | } |
||
283 | |||
284 | |||
285 | void initPortB(uint8_t busSpeed, uint8_t dataBits, uint8_t parity, uint8_t stopBit)
|
||
286 | { |
||
287 | |||
288 | uint16_t speedCfg[] = { DL_9600_BAUDS, DL_19200_BAUDS, DL_38400_BAUDS }; |
||
289 | uint8_t parityCfg[] = { TL16C_NO_PARITY, TL16C_EVEN_PARITY, TL16C_ODD_PARITY }; |
||
290 | uint8_t dataCfg[] = { F5BIT_MODE, F6BIT_MODE, F7BIT_MODE, F8BIT_MODE }; |
||
291 | uint8_t stopCfg[] = { ONE_STOPBIT, TWO_STOPBITS }; |
||
292 | |||
293 | |||
294 | uint8_t regVal = 0; //temp value for reading register and change it's value without clearing it |
||
295 | |||
296 | _portB_parity_set = (parity > 0); //Parity set (even or odd) ? |
||
297 | |||
298 | |||
299 | //Read register first...
|
||
300 | regVal = readPortB(LCR_REG); |
||
301 | //_delay_ms(1);
|
||
302 | setWait(20);
|
||
303 | regVal = DLAB_ERF_EN_BIT; //set LCR[7] = 1 -> enable divisor latch mode
|
||
304 | writePortB(regVal, LCR_REG); //switch Mode
|
||
305 | //_delay_ms(1);
|
||
306 | setWait(20);
|
||
307 | //Set bus speed (according of 8MHz OSC. -> DL = Fosc/(16*Fbauds*DIV));
|
||
308 | //DIV = 1 or 4 (see TL16C datasheet p.14), we use here DIV = 1
|
||
309 | writePortB(0x00, DLH_REG); //Always 0x00 in our cfg... MAX 12MHz |
||
310 | //_delay_ms(1);
|
||
311 | setWait(20);
|
||
312 | //writePortA(busSpeed > 2 ? DL_38400_BAUDS : baudsValues[busSpeed], DLL_REG);
|
||
313 | writePortB(speedCfg[busSpeed], DLL_REG); |
||
314 | //_delay_ms(1);
|
||
315 | setWait(20);
|
||
316 | |||
317 | regVal = readPortB(LCR_REG); |
||
318 | regVal &= ~(DLAB_ERF_EN_BIT); //set LCR[7] = 0 -> disable divisor latch mode
|
||
319 | |||
320 | //regVal |= dataBits > 3 ? TL16C_WORD_8BITS : wordValues[dataBits]; //set 8bits mode
|
||
321 | //regVal |= (stopBit > 1 ? TL16C_STOPBIT_TWO : stopBitValues[stopBit]) << 2; //set stop bits
|
||
322 | //regVal |= (parity > 2 ? TL16C_PARITY_EVEN : parityValues[parity]) << 3; //set stop bits
|
||
323 | regVal |= dataCfg[dataBits]; //set 8bits mode
|
||
324 | regVal |= stopCfg[stopBit] << 2; //set stop bits |
||
325 | regVal |= parityCfg[parity] << 3; //set stop bits |
||
326 | writePortB(regVal, LCR_REG); |
||
327 | //_delay_ms(1);
|
||
328 | setWait(20);
|
||
329 | writePortB(0x01, FCR_REG); //enable FIFO |
||
330 | setWait(20);
|
||
331 | } |
||
332 | |||
333 | |||
334 | void initPortC(uint8_t busSpeed, uint8_t dataBits, uint8_t parity, uint8_t stopBit)
|
||
335 | { |
||
336 | |||
337 | uint16_t speedCfg[] = { DL_9600_BAUDS, DL_19200_BAUDS, DL_38400_BAUDS }; |
||
338 | uint8_t parityCfg[] = { TL16C_NO_PARITY, TL16C_EVEN_PARITY, TL16C_ODD_PARITY }; |
||
339 | uint8_t dataCfg[] = { F5BIT_MODE, F6BIT_MODE, F7BIT_MODE, F8BIT_MODE }; |
||
340 | uint8_t stopCfg[] = { ONE_STOPBIT, TWO_STOPBITS }; |
||
341 | |||
342 | uint8_t regVal = 0; //temp value for reading register and change it's value without clearing it |
||
343 | |||
344 | _portC_parity_set = (parity > 0); //Parity set (even or odd) ? |
||
345 | |||
346 | |||
347 | //Read register first...
|
||
348 | regVal = readPortC(LCR_REG); |
||
349 | //_delay_ms(1);
|
||
350 | setWait(20);
|
||
351 | regVal = DLAB_ERF_EN_BIT; //set LCR[7] = 1 -> enable divisor latch mode
|
||
352 | writePortC(regVal, LCR_REG); //switch Mode
|
||
353 | //_delay_ms(1);
|
||
354 | setWait(20);
|
||
355 | //Set bus speed (according of 8MHz OSC. -> DL = Fosc/(16*Fbauds*DIV));
|
||
356 | //DIV = 1 or 4 (see TL16C datasheet p.14), we use here DIV = 1
|
||
357 | writePortC(0x00, DLH_REG); //Always 0x00 in our cfg... MAX 12MHz |
||
358 | //_delay_ms(1);
|
||
359 | setWait(20);
|
||
360 | //writePortA(busSpeed > 2 ? DL_38400_BAUDS : baudsValues[busSpeed], DLL_REG);
|
||
361 | writePortC(speedCfg[busSpeed], DLL_REG); |
||
362 | //_delay_ms(1);
|
||
363 | setWait(20);
|
||
364 | |||
365 | regVal = readPortC(LCR_REG); |
||
366 | regVal &= ~(DLAB_ERF_EN_BIT); //set LCR[7] = 0 -> disable divisor latch mode
|
||
367 | |||
368 | //regVal |= dataBits > 3 ? TL16C_WORD_8BITS : wordValues[dataBits]; //set 8bits mode
|
||
369 | //regVal |= (stopBit > 1 ? TL16C_STOPBIT_TWO : stopBitValues[stopBit]) << 2; //set stop bits
|
||
370 | //regVal |= (parity > 2 ? TL16C_PARITY_EVEN : parityValues[parity]) << 3; //set stop bits
|
||
371 | regVal |= dataCfg[dataBits]; //set 8bits mode
|
||
372 | regVal |= stopCfg[stopBit] << 2; //set stop bits |
||
373 | regVal |= parityCfg[parity] << 3; //set stop bits |
||
374 | writePortC(regVal, LCR_REG); |
||
375 | //_delay_ms(1);
|
||
376 | setWait(20);
|
||
377 | writePortC(0x01, FCR_REG); //enable FIFO |
||
378 | setWait(20);
|
||
379 | } |
||
380 | |||
381 | |||
382 | |||
383 | void initPortD(uint8_t busSpeed, uint8_t dataBits, uint8_t parity, uint8_t stopBit)
|
||
384 | { |
||
385 | |||
386 | uint16_t speedCfg[] = { DL_9600_BAUDS, DL_19200_BAUDS, DL_38400_BAUDS }; |
||
387 | uint8_t parityCfg[] = { TL16C_NO_PARITY, TL16C_EVEN_PARITY, TL16C_ODD_PARITY }; |
||
388 | uint8_t dataCfg[] = { F5BIT_MODE, F6BIT_MODE, F7BIT_MODE, F8BIT_MODE }; |
||
389 | uint8_t stopCfg[] = { ONE_STOPBIT, TWO_STOPBITS }; |
||
390 | |||
391 | uint8_t regVal = 0; //temp value for reading register and change it's value without clearing it |
||
392 | |||
393 | _portD_parity_set = (parity > 0); //Parity set (even or odd) ? |
||
394 | |||
395 | |||
396 | //Read register first...
|
||
397 | regVal = readPortD(LCR_REG); |
||
398 | //_delay_ms(1);
|
||
399 | setWait(20);
|
||
400 | regVal = DLAB_ERF_EN_BIT; //set LCR[7] = 1 -> enable divisor latch mode
|
||
401 | writePortD(regVal, LCR_REG); //switch Mode (and clear default cfg...)
|
||
402 | //_delay_ms(1);
|
||
403 | setWait(20);
|
||
404 | //Set bus speed (according of 8MHz OSC. -> DL = Fosc/(16*Fbauds*DIV));
|
||
405 | //DIV = 1 or 4 (see TL16C datasheet p.14), we use here DIV = 1
|
||
406 | writePortD(0x00, DLH_REG); //Always 0x00 in our cfg... MAX 12MHz |
||
407 | //_delay_ms(1);
|
||
408 | setWait(20);
|
||
409 | //writePortA(busSpeed > 2 ? DL_38400_BAUDS : baudsValues[busSpeed], DLL_REG);
|
||
410 | writePortD(speedCfg[busSpeed], DLL_REG); |
||
411 | //_delay_ms(1);
|
||
412 | setWait(20);
|
||
413 | |||
414 | regVal = readPortD(LCR_REG); |
||
415 | regVal &= ~(DLAB_ERF_EN_BIT); //set LCR[7] = 0 -> disable divisor latch mode
|
||
416 | |||
417 | //regVal |= dataBits > 3 ? TL16C_WORD_8BITS : wordValues[dataBits]; //set 8bits mode
|
||
418 | //regVal |= (stopBit > 1 ? TL16C_STOPBIT_TWO : stopBitValues[stopBit]) << 2; //set stop bits
|
||
419 | //regVal |= (parity > 2 ? TL16C_PARITY_EVEN : parityValues[parity]) << 3; //set stop bits
|
||
420 | regVal |= dataCfg[dataBits]; //set 8bits mode
|
||
421 | regVal |= stopCfg[stopBit] << 2; //set stop bits |
||
422 | regVal |= parityCfg[parity] << 3; //set stop bits |
||
423 | writePortD(regVal, LCR_REG); |
||
424 | //_delay_ms(1);
|
||
425 | setWait(20);
|
||
426 | writePortD(0x01, FCR_REG); //enable FIFO |
||
427 | setWait(20);
|
||
428 | } |
||
429 | |||
430 | |||
431 | |||
432 | //////////////////////////////////////////////
|
||
433 | //UART send/reiceive
|
||
434 | |||
435 | void txWriteA(uint8_t b)
|
||
436 | { |
||
437 | writePortA(b, THR_REG); //write to Transmit Holding (that goes into TX FIFO buffer)
|
||
438 | } |
||
439 | |||
440 | |||
441 | void txWriteB(uint8_t b)
|
||
442 | { |
||
443 | writePortB(b, THR_REG); //write to Transmit Holding (that goes into TX FIFO buffer)
|
||
444 | } |
||
445 | |||
446 | |||
447 | void txWriteC(uint8_t b)
|
||
448 | { |
||
449 | writePortC(b, THR_REG); //write to Transmit Holding (that goes into TX FIFO buffer)
|
||
450 | } |
||
451 | |||
452 | |||
453 | void txWriteD(uint8_t b)
|
||
454 | { |
||
455 | writePortD(b, THR_REG); //write to Transmit Holding (that goes into TX FIFO buffer)
|
||
456 | } |
||
457 | |||
458 | |||
459 | |||
460 | uint8_t rxReadA(void)
|
||
461 | { |
||
462 | return readPortA(RHR_REG); //read Receive Holding (from RX FIFO buffer) |
||
463 | } |
||
464 | |||
465 | |||
466 | uint8_t rxReadB(void)
|
||
467 | { |
||
468 | return readPortB(RHR_REG); //read Receive Holding (from RX FIFO buffer) |
||
469 | } |
||
470 | |||
471 | |||
472 | uint8_t rxReadC(void)
|
||
473 | { |
||
474 | return readPortC(RHR_REG); //read Receive Holding (from RX FIFO buffer) |
||
475 | } |
||
476 | |||
477 | |||
478 | uint8_t rxReadD(void)
|
||
479 | { |
||
480 | return readPortD(RHR_REG); //read Receive Holding (from RX FIFO buffer) |
||
481 | } |
||
482 | |||
483 | |||
484 | ////////////////////////////////////////
|
||
485 | //RX buf state functions
|
||
486 | |||
487 | bool portA_available()
|
||
488 | { |
||
489 | return (readPortA(LSR_REG) & 0x01); //check if RX FIFO buffer has at least one byte available |
||
490 | } |
||
491 | |||
492 | |||
493 | bool portB_available()
|
||
494 | { |
||
495 | return (readPortB(LSR_REG) & 0x01); //check if RX FIFO buffer has at least one byte available |
||
496 | } |
||
497 | |||
498 | |||
499 | bool portC_available()
|
||
500 | { |
||
501 | return (readPortC(LSR_REG) & 0x01); //check if RX FIFO buffer has at least one byte available |
||
502 | } |
||
503 | |||
504 | |||
505 | bool portD_available()
|
||
506 | { |
||
507 | return (readPortD(LSR_REG) & 0x01); //check if RX FIFO buffer has at least one byte available |
||
508 | } |
||
509 | |||
510 | |||
511 | ///////////////////////////////////////////////////////////////////////
|
||
512 | //Parity configuration status
|
||
513 | |||
514 | //get status if port has been configured with a parity into the frame
|
||
515 | bool getParitySetA()
|
||
516 | { |
||
517 | return _portA_parity_set;
|
||
518 | } |
||
519 | |||
520 | bool getParitySetB()
|
||
521 | { |
||
522 | return _portB_parity_set;
|
||
523 | } |
||
524 | |||
525 | bool getParitySetC()
|
||
526 | { |
||
527 | return _portC_parity_set;
|
||
528 | } |
||
529 | |||
530 | bool getParitySetD()
|
||
531 | { |
||
532 | return _portD_parity_set;
|
||
533 | } |
||
534 | |||
535 | |||
536 | |||
537 | //Get parity/stopbit error status when frame received on port
|
||
538 | |||
539 | bool getErrorStatusA()
|
||
540 | { |
||
541 | return ((readPortA(LSR_REG) & 0x80) == 0x80); |
||
542 | } |
||
543 | |||
544 | bool getErrorStatusB()
|
||
545 | { |
||
546 | return ((readPortB(LSR_REG) & 0x80) == 0x80); |
||
547 | } |
||
548 | |||
549 | bool getErrorStatusC()
|
||
550 | { |
||
551 | return ((readPortC(LSR_REG) & 0x80) == 0x80); |
||
552 | } |
||
553 | |||
554 | bool getErrorStatusD()
|
||
555 | { |
||
556 | return ((readPortD(LSR_REG) & 0x80) == 0x80); |
||
557 | } |
||
558 | |||
559 | |||
560 | ///////////////////////////////////////////////////////
|
||
561 | //write functions
|
||
562 | |||
563 | |||
564 | |||
565 | void writePortA(uint8_t reg, uint8_t addr)
|
||
566 | { |
||
567 | DATADIR(0xFF); //set I/O on write mode |
||
568 | ADDRWRITE(addr); //search uartn register
|
||
569 | DATAWRITE(reg); //write data
|
||
570 | CLRCSA; //enable uartA call
|
||
571 | setWait(3);
|
||
572 | CLRWR; //enable write mode
|
||
573 | setWait(3);
|
||
574 | SETWR; //disable write mode
|
||
575 | setWait(3);
|
||
576 | SETCSA; //disable uartA call
|
||
577 | DATADIR(0x00); //set input mode (to reduce power consumption) |
||
578 | } |
||
579 | |||
580 | void writePortB(uint8_t reg, uint8_t addr)
|
||
581 | { |
||
582 | DATADIR(0xFF); //set I/O on write mode |
||
583 | ADDRWRITE(addr); //search uartn register
|
||
584 | DATAWRITE(reg); //write data
|
||
585 | CLRCSB; //enable uartA call
|
||
586 | setWait(3);
|
||
587 | CLRWR; //enable write mode
|
||
588 | setWait(3);
|
||
589 | SETWR; //disable write mode
|
||
590 | setWait(3);
|
||
591 | SETCSB; //disable uartA call
|
||
592 | DATADIR(0x00); //set input mode (to reduce power consumption) |
||
593 | } |
||
594 | |||
595 | void writePortC(uint8_t reg, uint8_t addr)
|
||
596 | { |
||
597 | DATADIR(0xFF); //set I/O on write mode |
||
598 | ADDRWRITE(addr); //search uartn register
|
||
599 | DATAWRITE(reg); //write data
|
||
600 | CLRCSC; //enable uartA call
|
||
601 | setWait(3);
|
||
602 | CLRWR; //enable write mode
|
||
603 | setWait(3);
|
||
604 | SETWR; //disable write mode
|
||
605 | setWait(3);
|
||
606 | SETCSC; //disable uartA call
|
||
607 | DATADIR(0x00); //set input mode (to reduce power consumption) |
||
608 | } |
||
609 | |||
610 | void writePortD(uint8_t reg, uint8_t addr)
|
||
611 | { |
||
612 | DATADIR(0xFF); //set I/O on write mode |
||
613 | ADDRWRITE(addr); //search uartn register
|
||
614 | DATAWRITE(reg); //write data
|
||
615 | CLRCSD; //enable uartA call
|
||
616 | setWait(3);
|
||
617 | CLRWR; //enable write mode
|
||
618 | setWait(3);
|
||
619 | SETWR; //disable write mode
|
||
620 | setWait(3);
|
||
621 | SETCSD; //disable uartA call
|
||
622 | DATADIR(0x00); //set input mode (to reduce power consumption) |
||
623 | } |
||
624 | |||
625 | |||
626 | ///////////////////////////////////////////////////////
|
||
627 | //read functions
|
||
628 | |||
629 | |||
630 | uint8_t readPortA(uint8_t addr) |
||
631 | { |
||
632 | uint8_t result; |
||
633 | DATADIR(0x00); //set I/O on read mode |
||
634 | ADDRWRITE(addr); //search uartn register
|
||
635 | CLRCSA; //enable uartA call
|
||
636 | setWait(3);
|
||
637 | CLRRD; //enable read mode
|
||
638 | setWait(3);
|
||
639 | result = DATAREAD; //set I/O on read mode
|
||
640 | setWait(3);
|
||
641 | SETRD; //disable read mode
|
||
642 | setWait(3);
|
||
643 | SETCSA; //hang up uartA call
|
||
644 | return result;
|
||
645 | } |
||
646 | |||
647 | uint8_t readPortB(uint8_t addr) |
||
648 | { |
||
649 | uint8_t result; |
||
650 | DATADIR(0x00); //set I/O on read mode |
||
651 | ADDRWRITE(addr); //search uartn register
|
||
652 | CLRCSB; //enable uartB call
|
||
653 | setWait(3);
|
||
654 | CLRRD; //enable read mode
|
||
655 | setWait(3);
|
||
656 | result = DATAREAD; //set I/O on read mode
|
||
657 | setWait(3);
|
||
658 | SETRD; //disable read mode
|
||
659 | setWait(3);
|
||
660 | SETCSB; //hang up uartB call
|
||
661 | return result;
|
||
662 | } |
||
663 | |||
664 | uint8_t readPortC(uint8_t addr) |
||
665 | { |
||
666 | uint8_t result; |
||
667 | DATADIR(0x00); //set I/O on read mode |
||
668 | ADDRWRITE(addr); //search uartn register
|
||
669 | CLRCSC; //enable uartC call
|
||
670 | setWait(3);
|
||
671 | CLRRD; //enable read mode
|
||
672 | setWait(3);
|
||
673 | result = DATAREAD; //set I/O on read mode
|
||
674 | setWait(3);
|
||
675 | SETRD; //disable read mode
|
||
676 | setWait(3);
|
||
677 | SETCSC; //hang up uartC call
|
||
678 | return result;
|
||
679 | } |
||
680 | |||
681 | uint8_t readPortD(uint8_t addr) |
||
682 | { |
||
683 | uint8_t result; |
||
684 | DATADIR(0x00); //set I/O on read mode |
||
685 | ADDRWRITE(addr); //search uartn register
|
||
686 | CLRCSD; //enable uartD call
|
||
687 | setWait(3);
|
||
688 | CLRRD; //enable read mode
|
||
689 | setWait(3);
|
||
690 | result = DATAREAD; //set I/O on read mode
|
||
691 | setWait(3);
|
||
692 | SETRD; //disable read mode
|
||
693 | setWait(3);
|
||
694 | SETCSD; //hang up uartD call
|
||
695 | return result;
|
||
696 | } |
||
697 | |||
698 | |||
699 | |||
700 | |||
701 | |||
702 | ///////////////////////////////////////////
|
||
703 | //Miscellaneous functions
|
||
704 | |||
705 | void setWait(uint16_t cnt)
|
||
706 | { |
||
707 | uint16_t k = 0;
|
||
708 | while(k < cnt)
|
||
709 | { |
||
710 | asm("nop"); |
||
711 | k++; |
||
712 | } |
||
713 | } |
||
714 | |||
715 | |||
716 | |||
717 | |||
718 | |||
719 | #endif /* XC_HEADER_TEMPLATE_H */ |