1 | /*
|
---|
2 | * TOPPERS/ASP Kernel
|
---|
3 | * Toyohashi Open Platform for Embedded Real-Time Systems/
|
---|
4 | * Advanced Standard Profile Kernel
|
---|
5 | *
|
---|
6 | * Copyright (C) 2008-2011 by Embedded and Real-Time Systems Laboratory
|
---|
7 | * Graduate School of Information Science, Nagoya Univ., JAPAN
|
---|
8 | *
|
---|
9 | * ãLì ÒÍCȺÌ(1)`(4)Ìðð½·êÉÀèC{\tgEF
|
---|
10 | * Ai{\tgEFAðüϵ½àÌðÜÞDȺ¯¶jðgpE¡»Eü
|
---|
11 | * ÏEÄzziȺCpÆÄÔj·é±Æð³Åø·éD
|
---|
12 | * (1) {\tgEFAð\[XR[hÌ`Åp·éêÉÍCãLÌì
|
---|
13 | * \¦C±Ìpð¨æѺL̳ÛØKèªC»ÌÜÜÌ`Å\[
|
---|
14 | * XR[hÉÜÜêÄ¢é±ÆD
|
---|
15 | * (2) {\tgEFAðCCu`®ÈÇC¼Ì\tgEFAJÉg
|
---|
16 | * pÅ«é`ÅÄzz·éêÉÍCÄzzɺ¤hL
|
---|
17 | gip
|
---|
18 | * Ò}j
|
---|
19 | AÈÇjÉCãLÌì \¦C±Ìpð¨æѺL
|
---|
20 | * ̳ÛØKèðfÚ·é±ÆD
|
---|
21 | * (3) {\tgEFAðC@íÉgÝÞÈÇC¼Ì\tgEFAJÉg
|
---|
22 | * pÅ«È¢`ÅÄzz·éêÉÍCÌ¢¸ê©Ìðð½·±
|
---|
23 | * ÆD
|
---|
24 | * (a) Äzzɺ¤hL
|
---|
25 | gipÒ}j
|
---|
26 | AÈÇjÉCãLÌ
|
---|
27 | * ì \¦C±Ìpð¨æѺL̳ÛØKèðfÚ·é±ÆD
|
---|
28 | * (b) ÄzzÌ`ÔðCÊÉèßéû@ÉæÁÄCTOPPERSvWFNgÉ
|
---|
29 | * ñ·é±ÆD
|
---|
30 | * (4) {\tgEFAÌpÉæè¼ÚIܽÍÔÚIɶ¶é¢©Èé¹
|
---|
31 | * Q©çàCãLì Ò¨æÑTOPPERSvWFNgðÆÓ·é±ÆD
|
---|
32 | * ܽC{\tgEFAÌ[UܽÍGh[U©çÌ¢©Èé
|
---|
33 | * RÉîÿ©çàCãLì Ò¨æÑTOPPERSvWFNgð
|
---|
34 | * ÆÓ·é±ÆD
|
---|
35 | *
|
---|
36 | * {\tgEFAÍC³ÛØÅñ³êÄ¢éàÌÅ éDãLì Ò¨
|
---|
37 | * æÑTOPPERSvWFNgÍC{\tgEFAÉÖµÄCÁèÌgpÚI
|
---|
38 | * ÉηéK«àÜßÄC¢©ÈéÛØàsíÈ¢DܽC{\tgEF
|
---|
39 | * AÌpÉæè¼ÚIܽÍÔÚIɶ¶½¢©Èé¹QÉÖµÄàC»
|
---|
40 | * ÌÓCðíÈ¢D
|
---|
41 | *
|
---|
42 | */
|
---|
43 |
|
---|
44 | /*
|
---|
45 | * VAI/OfoCXiSIOjhCo
|
---|
46 | */
|
---|
47 |
|
---|
48 | #include <kernel.h>
|
---|
49 | #include <t_syslog.h>
|
---|
50 | #include "target_serial.h"
|
---|
51 | #include "target_syssvc.h"
|
---|
52 |
|
---|
53 | /*
|
---|
54 | * WX^Ýèl
|
---|
55 | */
|
---|
56 | #define PORT2SIOPID(x) ((x) + 1)
|
---|
57 | #define INDEX_PORT(x) ((x) - 1)
|
---|
58 | #define GET_SIOPCB(x) (&siopcb_table[INDEX_PORT(x)])
|
---|
59 |
|
---|
60 | /*
|
---|
61 | * UARTWX^è`
|
---|
62 | */
|
---|
63 | #define UART_SMR(x) (x + 0x00)
|
---|
64 | #define UART_SCR(x) (x + 0x01)
|
---|
65 | #define UART_ESCR(x) (x + 0x04)
|
---|
66 | #define UART_SSR(x) (x + 0x05)
|
---|
67 | #define UART_RDR(x) (x + 0x08)
|
---|
68 | #define UART_TDR(x) (x + 0x08)
|
---|
69 | #define UART_BGR(x) (x + 0x0c)
|
---|
70 | #define UART_BGR0(x) (x + 0x0c)
|
---|
71 | #define UART_BGR1(x) (x + 0x0d)
|
---|
72 | #define UART_ISBA(x) (x + 0x10)
|
---|
73 | #define UART_ISMK(x) (x + 0x11)
|
---|
74 | #define UART_FCR0(x) (x + 0x14)
|
---|
75 | #define UART_FCR1(x) (x + 0x15)
|
---|
76 | #define UART_FBYTE1(x) (x + 0x18)
|
---|
77 | #define UART_FBYTE2(x) (x + 0x19)
|
---|
78 |
|
---|
79 | /*
|
---|
80 | * VAI/O|[gú»ubNÌè`
|
---|
81 | */
|
---|
82 | typedef struct sio_port_initialization_block {
|
---|
83 | uint32_t base;
|
---|
84 | INTNO intno_rx;
|
---|
85 | INTNO intno_tx;
|
---|
86 | uint16_t bps_setting; /* {[[gÌÝèl */
|
---|
87 | } SIOPINIB;
|
---|
88 |
|
---|
89 | /*
|
---|
90 | * pGPIO|[gú»ubNÌè`
|
---|
91 | */
|
---|
92 | typedef struct gpio_port_initialization_block {
|
---|
93 | uint32_t pfr; /* PFRxWX^AhX */
|
---|
94 | uint32_t pfr_set; /* PFRxWX^ðZbg·érbg */
|
---|
95 | uint32_t pcr; /* PCRxWX^AhX */
|
---|
96 | uint32_t pcr_set; /* PCRxWX^ðZbg·érbg */
|
---|
97 | uint32_t epfr; /* EPFRxxWX^AhX */
|
---|
98 | uint32_t epfr_clr; /* EPFRxxWX^ðNA·érbg */
|
---|
99 | uint32_t epfr_set; /* EPFRxxWX^ðZbg·érbg */
|
---|
100 | uint32_t ade; /* ADEWX^AhX */
|
---|
101 | uint32_t ade_clr; /* ADEWX^ðNA·érbg */
|
---|
102 | } GPIOINIB;
|
---|
103 |
|
---|
104 | /*
|
---|
105 | * VAI/O|[gÇubNÌè`
|
---|
106 | */
|
---|
107 | struct sio_port_control_block {
|
---|
108 | const SIOPINIB *p_siopinib; /* VAI/O|[gú»ubN */
|
---|
109 | const GPIOINIB *p_gpioinib; /* pGPIO|[gú»ubN */
|
---|
110 | intptr_t exinf; /* g£îñ */
|
---|
111 | bool_t opnflg; /* I[vÏÝtO */
|
---|
112 | };
|
---|
113 |
|
---|
114 | /*
|
---|
115 | * VAI/O|[gú»ubN
|
---|
116 | */
|
---|
117 | const SIOPINIB siopinib_table[TNUM_SIOP] = {
|
---|
118 | {(uint32_t)FM3_MFS4_UART_BASE, (INTNO)IRQ_VECTOR_MFS4RX, (INTNO)IRQ_VECTOR_MFS4TX, MFS4_BPS_SETTING},
|
---|
119 | {(uint32_t)FM3_MFS0_UART_BASE, (INTNO)IRQ_VECTOR_MFS0RX, (INTNO)IRQ_VECTOR_MFS0TX, MFS0_BPS_SETTING},
|
---|
120 | {(uint32_t)FM3_MFS3_UART_BASE, (INTNO)IRQ_VECTOR_MFS3RX, (INTNO)IRQ_VECTOR_MFS3TX, MFS3_BPS_SETTING},
|
---|
121 | };
|
---|
122 |
|
---|
123 | /*
|
---|
124 | * pGPIO|[gú»ubN
|
---|
125 | */
|
---|
126 | const GPIOINIB gpioinib_table[TNUM_SIOP] = {
|
---|
127 | {(uint32_t)FM3_GPIO_PFR0, (uint32_t)((1 << 5) | (1 << 6)), (uint32_t)FM3_GPIO_PCR0, (uint32_t)(1<<5), (uint32_t)FM3_GPIO_EPFR08, (uint32_t)~0x000000f0, (uint32_t)0x000000f0, (uint32_t)FM3_GPIO_ADE, (uint32_t)0},
|
---|
128 | {(uint32_t)FM3_GPIO_PFR2, (uint32_t)((1 << 1) | (1 << 2)), (uint32_t)FM3_GPIO_PCR2, (uint32_t)(1<<1), (uint32_t)FM3_GPIO_EPFR07, (uint32_t)~0x000000f0, (uint32_t)0x00000050, (uint32_t)FM3_GPIO_ADE, (uint32_t)(1 << 31)},
|
---|
129 | {(uint32_t)FM3_GPIO_PFR4, (uint32_t)((1 << 8) | (1 << 9)), (uint32_t)FM3_GPIO_PCR4, (uint32_t)(1<<8), (uint32_t)FM3_GPIO_EPFR07, (uint32_t)~0x03c00000, (uint32_t)0x03c00000, (uint32_t)FM3_GPIO_ADE, (uint32_t)0},
|
---|
130 | };
|
---|
131 |
|
---|
132 | /*
|
---|
133 | * VAI/O|[gÇubNÌGA
|
---|
134 | */
|
---|
135 | SIOPCB siopcb_table[TNUM_SIOP];
|
---|
136 |
|
---|
137 | /*
|
---|
138 | * VAI/O|[gID©çÇubNðæèo·½ßÌ}N
|
---|
139 | */
|
---|
140 | #define INDEX_SIOP(siopid) ((uint_t)((siopid) - 1))
|
---|
141 | #define get_siopcb(siopid) (&(siopcb_table[INDEX_SIOP(siopid)]))
|
---|
142 |
|
---|
143 | /*
|
---|
144 | * SIOhCoÌú»
|
---|
145 | */
|
---|
146 | void
|
---|
147 | sio_initialize(intptr_t exinf)
|
---|
148 | {
|
---|
149 | SIOPCB *p_siopcb;
|
---|
150 | uint_t i;
|
---|
151 |
|
---|
152 | /*
|
---|
153 | * VAI/O|[gÇubNÌú»
|
---|
154 | */
|
---|
155 | for (p_siopcb = siopcb_table, i = 0; i < TNUM_SIOP; p_siopcb++, i++) {
|
---|
156 | p_siopcb->p_siopinib = &(siopinib_table[i]);
|
---|
157 | p_siopcb->p_gpioinib = &(gpioinib_table[i]);
|
---|
158 | p_siopcb->opnflg = false;
|
---|
159 | }
|
---|
160 | }
|
---|
161 |
|
---|
162 |
|
---|
163 | /*
|
---|
164 | * VAI/O|[gÌI[v
|
---|
165 | */
|
---|
166 | SIOPCB *
|
---|
167 | sio_opn_por(ID siopid, intptr_t exinf)
|
---|
168 | {
|
---|
169 | SIOPCB *p_siopcb;
|
---|
170 | const SIOPINIB *p_siopinib;
|
---|
171 | const GPIOINIB *p_gpioinib;
|
---|
172 | bool_t opnflg;
|
---|
173 | ER ercd;
|
---|
174 |
|
---|
175 | p_siopcb = get_siopcb(siopid);
|
---|
176 | p_siopinib = p_siopcb->p_siopinib;
|
---|
177 | p_gpioinib = p_siopcb->p_gpioinib;
|
---|
178 |
|
---|
179 | /*
|
---|
180 | * I[vµ½|[gª é©ðopnflgÉÇñŨD
|
---|
181 | */
|
---|
182 | opnflg = p_siopcb->opnflg;
|
---|
183 |
|
---|
184 | p_siopcb->exinf = exinf;
|
---|
185 |
|
---|
186 | /*
|
---|
187 | * n[hEFAÌú»
|
---|
188 | */
|
---|
189 | sil_wrw_mem((uint32_t *)p_gpioinib->pfr, sil_rew_mem((uint32_t *)p_gpioinib->pfr) | p_gpioinib->pfr_set);
|
---|
190 | sil_wrw_mem((uint32_t *)p_gpioinib->pcr, sil_rew_mem((uint32_t *)p_gpioinib->pcr) | p_gpioinib->pcr_set);
|
---|
191 | sil_wrw_mem((uint32_t *)p_gpioinib->epfr, (sil_rew_mem((uint32_t *)p_gpioinib->epfr) & p_gpioinib->epfr_clr) | p_gpioinib->epfr_set);
|
---|
192 | sil_wrw_mem((uint32_t *)p_gpioinib->ade, sil_rew_mem((uint32_t *)p_gpioinib->ade) & ~p_gpioinib->ade_clr);
|
---|
193 |
|
---|
194 | uint32_t base = p_siopinib->base;
|
---|
195 |
|
---|
196 | sil_wrb_mem((uint8_t *)UART_SCR(base), 0);
|
---|
197 | sil_wrb_mem((uint8_t *)UART_SMR(base), SMR_MD_UART | SMR_SOE);
|
---|
198 | sil_wrh_mem((uint16_t *)UART_BGR(base), p_siopinib->bps_setting);
|
---|
199 | sil_wrb_mem((uint8_t *)UART_ESCR(base), ESCR_DATABITS_8);
|
---|
200 | sil_wrb_mem((uint8_t *)UART_SCR(base), SCR_RXE | SCR_TXE);
|
---|
201 |
|
---|
202 | /*
|
---|
203 | * VAI/OÝÌ}XNðð·éD
|
---|
204 | */
|
---|
205 | if (!opnflg) {
|
---|
206 | ercd = ena_int(p_siopinib->intno_rx);
|
---|
207 | assert(ercd == E_OK);
|
---|
208 | ercd = ena_int(p_siopinib->intno_tx);
|
---|
209 | assert(ercd == E_OK);
|
---|
210 | }
|
---|
211 |
|
---|
212 | return(p_siopcb);
|
---|
213 | }
|
---|
214 |
|
---|
215 | /*
|
---|
216 | * VAI/O|[gÌN[Y
|
---|
217 | */
|
---|
218 | void
|
---|
219 | sio_cls_por(SIOPCB *p_siopcb)
|
---|
220 | {
|
---|
221 | /*
|
---|
222 | * VAI/OÝð}XN·éD
|
---|
223 | */
|
---|
224 | if (!(p_siopcb->opnflg)) {
|
---|
225 | dis_int(p_siopcb->p_siopinib->intno_rx);
|
---|
226 | dis_int(p_siopcb->p_siopinib->intno_tx);
|
---|
227 | }
|
---|
228 | }
|
---|
229 |
|
---|
230 | /*
|
---|
231 | * SIOÌÝT[rX[`
|
---|
232 | */
|
---|
233 |
|
---|
234 | Inline bool_t
|
---|
235 | sio_putready(SIOPCB* p_siopcb)
|
---|
236 | {
|
---|
237 | return (sil_reb_mem((uint8_t *)UART_SSR(p_siopcb->p_siopinib->base)) & SSR_TDRE) != 0;
|
---|
238 | }
|
---|
239 |
|
---|
240 | Inline bool_t
|
---|
241 | sio_getready(SIOPCB* p_siopcb)
|
---|
242 | {
|
---|
243 | char ssr = sil_reb_mem((uint8_t *)UART_SSR(p_siopcb->p_siopinib->base));
|
---|
244 |
|
---|
245 | if ((ssr & (SSR_ORE | SSR_FRE | SSR_PE)) != 0)
|
---|
246 | {
|
---|
247 | sil_wrb_mem((uint8_t *)UART_SSR(p_siopcb->p_siopinib->base), ssr | SSR_REC);
|
---|
248 | return 0;
|
---|
249 | }
|
---|
250 | if ((ssr & SSR_RDRF) != 0)
|
---|
251 | {
|
---|
252 | return 1;
|
---|
253 | }
|
---|
254 | return 0;
|
---|
255 | }
|
---|
256 |
|
---|
257 | void
|
---|
258 | sio_tx_isr(intptr_t exinf)
|
---|
259 | {
|
---|
260 | SIOPCB *p_siopcb;
|
---|
261 |
|
---|
262 | p_siopcb = get_siopcb(exinf);
|
---|
263 |
|
---|
264 | if (sio_putready(p_siopcb)) {
|
---|
265 | sio_irdy_snd(p_siopcb->exinf);
|
---|
266 | }
|
---|
267 | }
|
---|
268 |
|
---|
269 | void
|
---|
270 | sio_rx_isr(intptr_t exinf)
|
---|
271 | {
|
---|
272 | SIOPCB *p_siopcb;
|
---|
273 |
|
---|
274 | p_siopcb = get_siopcb(exinf);
|
---|
275 |
|
---|
276 | if (sio_getready(p_siopcb)) {
|
---|
277 | sio_irdy_rcv(p_siopcb->exinf);
|
---|
278 | }
|
---|
279 | }
|
---|
280 |
|
---|
281 | /*
|
---|
282 | * VAI/O|[gÖ̶M
|
---|
283 | */
|
---|
284 | bool_t
|
---|
285 | sio_snd_chr(SIOPCB *p_siopcb, char c)
|
---|
286 | {
|
---|
287 | if (sio_putready(p_siopcb)) {
|
---|
288 | sil_wrh_mem((uint16_t *)UART_TDR(p_siopcb->p_siopinib->base), (uint16_t)c);
|
---|
289 |
|
---|
290 | return true;
|
---|
291 | }
|
---|
292 |
|
---|
293 | return false;
|
---|
294 | }
|
---|
295 |
|
---|
296 | /*
|
---|
297 | * VAI/O|[g©ç̶óM
|
---|
298 | */
|
---|
299 | int_t
|
---|
300 | sio_rcv_chr(SIOPCB *p_siopcb)
|
---|
301 | {
|
---|
302 | int_t c = -1;
|
---|
303 |
|
---|
304 | if (sio_getready(p_siopcb)) {
|
---|
305 | c = sil_reh_mem((uint16_t *)UART_RDR(p_siopcb->p_siopinib->base)) & 0xFF;
|
---|
306 | }
|
---|
307 |
|
---|
308 | return c;
|
---|
309 | }
|
---|
310 |
|
---|
311 | /*
|
---|
312 | * VAI/O|[g©çÌR[obNÌÂ
|
---|
313 | */
|
---|
314 | void
|
---|
315 | sio_ena_cbr(SIOPCB *p_siopcb, uint_t cbrtn)
|
---|
316 | {
|
---|
317 | switch (cbrtn) {
|
---|
318 | case SIO_RDY_SND:
|
---|
319 | sil_wrb_mem((uint8_t *)UART_SCR(p_siopcb->p_siopinib->base), sil_reb_mem((uint8_t *)UART_SCR(p_siopcb->p_siopinib->base)) | SCR_TIE);
|
---|
320 | break;
|
---|
321 | case SIO_RDY_RCV:
|
---|
322 | sil_wrb_mem((uint8_t *)UART_SCR(p_siopcb->p_siopinib->base), sil_reb_mem((uint8_t *)UART_SCR(p_siopcb->p_siopinib->base)) | SCR_RIE);
|
---|
323 | break;
|
---|
324 | }
|
---|
325 | }
|
---|
326 |
|
---|
327 | /*
|
---|
328 | * VAI/O|[g©çÌR[obNÌÖ~
|
---|
329 | */
|
---|
330 | void
|
---|
331 | sio_dis_cbr(SIOPCB *p_siopcb, uint_t cbrtn)
|
---|
332 | {
|
---|
333 | switch (cbrtn) {
|
---|
334 | case SIO_RDY_SND:
|
---|
335 | sil_wrb_mem((uint8_t *)UART_SCR(p_siopcb->p_siopinib->base), sil_reb_mem((uint8_t *)UART_SCR(p_siopcb->p_siopinib->base)) & ~SCR_TIE);
|
---|
336 | break;
|
---|
337 | case SIO_RDY_RCV:
|
---|
338 | sil_wrb_mem((uint8_t *)UART_SCR(p_siopcb->p_siopinib->base), sil_reb_mem((uint8_t *)UART_SCR(p_siopcb->p_siopinib->base)) & ~SCR_RIE);
|
---|
339 | break;
|
---|
340 | }
|
---|
341 | }
|
---|
342 |
|
---|
343 | /*
|
---|
344 | * 1¶oÍi|[OÅÌoÍj
|
---|
345 | */
|
---|
346 | void sio_pol_snd_chr(char c, ID siopid)
|
---|
347 | {
|
---|
348 | uint32_t base = siopinib_table[INDEX_PORT(siopid)].base;
|
---|
349 |
|
---|
350 | sil_wrh_mem((uint16_t *)UART_TDR(base), (uint16_t)c);
|
---|
351 | while(0 == (sil_reb_mem((uint8_t *)UART_SSR(base)) & (1 << 1)));
|
---|
352 |
|
---|
353 | /*
|
---|
354 | * oͪ®SÉIíéÜÅÒÂ
|
---|
355 | */
|
---|
356 | volatile int n = 300000000/BPS_SETTING;
|
---|
357 | while(n--);
|
---|
358 | }
|
---|
359 |
|
---|
360 | /*
|
---|
361 | * ^[QbgÌVAú»
|
---|
362 | */
|
---|
363 | void target_uart_init(ID siopid)
|
---|
364 | {
|
---|
365 | const SIOPINIB *p_siopinib = &siopinib_table[INDEX_PORT(siopid)];
|
---|
366 | const GPIOINIB *p_gpioinib = &gpioinib_table[INDEX_PORT(siopid)];
|
---|
367 |
|
---|
368 | sil_wrw_mem((uint32_t *)p_gpioinib->pfr, sil_rew_mem((uint32_t *)p_gpioinib->pfr) | p_gpioinib->pfr_set);
|
---|
369 | sil_wrw_mem((uint32_t *)p_gpioinib->pcr, sil_rew_mem((uint32_t *)p_gpioinib->pcr) | p_gpioinib->pcr_set);
|
---|
370 | sil_wrw_mem((uint32_t *)p_gpioinib->epfr, (sil_rew_mem((uint32_t *)p_gpioinib->epfr) & p_gpioinib->epfr_clr) | p_gpioinib->epfr_set);
|
---|
371 | sil_wrw_mem((uint32_t *)p_gpioinib->ade, sil_rew_mem((uint32_t *)p_gpioinib->ade) & ~p_gpioinib->ade_clr);
|
---|
372 |
|
---|
373 | uint32_t base = siopinib_table[INDEX_PORT(siopid)].base;
|
---|
374 |
|
---|
375 | sil_wrb_mem((uint8_t *)UART_SCR(base), 0);
|
---|
376 | sil_wrb_mem((uint8_t *)UART_SMR(base), SMR_MD_UART | SMR_SOE);
|
---|
377 | sil_wrh_mem((uint16_t *)UART_BGR(base), p_siopinib->bps_setting);
|
---|
378 | sil_wrb_mem((uint8_t *)UART_ESCR(base), ESCR_DATABITS_8);
|
---|
379 | sil_wrb_mem((uint8_t *)UART_SCR(base), SCR_TXE);
|
---|
380 | }
|
---|