added prescaler for 16 bit pwm in LPC1347 target

Fork of mbed-dev by mbed official

Committer:
<>
Date:
Fri Sep 02 15:07:44 2016 +0100
Revision:
144:ef7eb2e8f9f7
Parent:
141:a2b798ec44f6
This updates the lib to the mbed lib v125

Who changed what in which revision?

UserRevisionLine numberNew contents of line
<> 144:ef7eb2e8f9f7 1 /* mbed Microcontroller Library
<> 144:ef7eb2e8f9f7 2 * Copyright (c) 2006-2015 ARM Limited
<> 144:ef7eb2e8f9f7 3 *
<> 144:ef7eb2e8f9f7 4 * Licensed under the Apache License, Version 2.0 (the "License");
<> 144:ef7eb2e8f9f7 5 * you may not use this file except in compliance with the License.
<> 144:ef7eb2e8f9f7 6 * You may obtain a copy of the License at
<> 144:ef7eb2e8f9f7 7 *
<> 144:ef7eb2e8f9f7 8 * http://www.apache.org/licenses/LICENSE-2.0
<> 144:ef7eb2e8f9f7 9 *
<> 144:ef7eb2e8f9f7 10 * Unless required by applicable law or agreed to in writing, software
<> 144:ef7eb2e8f9f7 11 * distributed under the License is distributed on an "AS IS" BASIS,
<> 144:ef7eb2e8f9f7 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
<> 144:ef7eb2e8f9f7 13 * See the License for the specific language governing permissions and
<> 144:ef7eb2e8f9f7 14 * limitations under the License.
<> 144:ef7eb2e8f9f7 15 */
<> 144:ef7eb2e8f9f7 16 // math.h required for floating point operations for baud rate calculation
<> 144:ef7eb2e8f9f7 17 #include "mbed_assert.h"
<> 144:ef7eb2e8f9f7 18 #include <math.h>
<> 144:ef7eb2e8f9f7 19 #include <string.h>
<> 144:ef7eb2e8f9f7 20 #include <stdlib.h>
<> 144:ef7eb2e8f9f7 21
<> 144:ef7eb2e8f9f7 22 #include "serial_api.h"
<> 144:ef7eb2e8f9f7 23 #include "cmsis.h"
<> 144:ef7eb2e8f9f7 24 #include "pinmap.h"
<> 144:ef7eb2e8f9f7 25 #include "gpio_api.h"
<> 144:ef7eb2e8f9f7 26
<> 144:ef7eb2e8f9f7 27 #include "scif_iodefine.h"
<> 144:ef7eb2e8f9f7 28 #include "cpg_iodefine.h"
<> 144:ef7eb2e8f9f7 29
<> 144:ef7eb2e8f9f7 30 /******************************************************************************
<> 144:ef7eb2e8f9f7 31 * INITIALIZATION
<> 144:ef7eb2e8f9f7 32 ******************************************************************************/
<> 144:ef7eb2e8f9f7 33 #define PCLK (66666666) // Define the peripheral clock P1 frequency.
<> 144:ef7eb2e8f9f7 34
<> 144:ef7eb2e8f9f7 35 #define UART_NUM 8
<> 144:ef7eb2e8f9f7 36 #define IRQ_NUM 4
<> 144:ef7eb2e8f9f7 37
<> 144:ef7eb2e8f9f7 38 static void uart0_tx_irq(void);
<> 144:ef7eb2e8f9f7 39 static void uart1_tx_irq(void);
<> 144:ef7eb2e8f9f7 40 static void uart2_tx_irq(void);
<> 144:ef7eb2e8f9f7 41 static void uart3_tx_irq(void);
<> 144:ef7eb2e8f9f7 42 static void uart4_tx_irq(void);
<> 144:ef7eb2e8f9f7 43 static void uart5_tx_irq(void);
<> 144:ef7eb2e8f9f7 44 static void uart6_tx_irq(void);
<> 144:ef7eb2e8f9f7 45 static void uart7_tx_irq(void);
<> 144:ef7eb2e8f9f7 46 static void uart0_rx_irq(void);
<> 144:ef7eb2e8f9f7 47 static void uart1_rx_irq(void);
<> 144:ef7eb2e8f9f7 48 static void uart2_rx_irq(void);
<> 144:ef7eb2e8f9f7 49 static void uart3_rx_irq(void);
<> 144:ef7eb2e8f9f7 50 static void uart4_rx_irq(void);
<> 144:ef7eb2e8f9f7 51 static void uart5_rx_irq(void);
<> 144:ef7eb2e8f9f7 52 static void uart6_rx_irq(void);
<> 144:ef7eb2e8f9f7 53 static void uart7_rx_irq(void);
<> 144:ef7eb2e8f9f7 54 static void uart0_er_irq(void);
<> 144:ef7eb2e8f9f7 55 static void uart1_er_irq(void);
<> 144:ef7eb2e8f9f7 56 static void uart2_er_irq(void);
<> 144:ef7eb2e8f9f7 57 static void uart3_er_irq(void);
<> 144:ef7eb2e8f9f7 58 static void uart4_er_irq(void);
<> 144:ef7eb2e8f9f7 59 static void uart5_er_irq(void);
<> 144:ef7eb2e8f9f7 60 static void uart6_er_irq(void);
<> 144:ef7eb2e8f9f7 61 static void uart7_er_irq(void);
<> 144:ef7eb2e8f9f7 62
<> 144:ef7eb2e8f9f7 63 static void serial_put_done(serial_t *obj);
<> 144:ef7eb2e8f9f7 64 static uint8_t serial_available_buffer(serial_t *obj);
<> 144:ef7eb2e8f9f7 65 static void serial_irq_err_set(serial_t *obj, uint32_t enable);
<> 144:ef7eb2e8f9f7 66
<> 144:ef7eb2e8f9f7 67 static const PinMap PinMap_UART_TX[] = {
<> 144:ef7eb2e8f9f7 68 {P2_14 , UART0, 6},
<> 144:ef7eb2e8f9f7 69 {P2_5 , UART1, 6},
<> 144:ef7eb2e8f9f7 70 {P4_12 , UART1, 7},
<> 144:ef7eb2e8f9f7 71 {P6_3 , UART2, 7},
<> 144:ef7eb2e8f9f7 72 {P4_14 , UART2, 7},
<> 144:ef7eb2e8f9f7 73 {P5_3 , UART3, 5},
<> 144:ef7eb2e8f9f7 74 {P8_8 , UART3, 7},
<> 144:ef7eb2e8f9f7 75 {P5_0 , UART4, 5},
<> 144:ef7eb2e8f9f7 76 {P8_14 , UART4, 7},
<> 144:ef7eb2e8f9f7 77 {P8_13 , UART5, 5},
<> 144:ef7eb2e8f9f7 78 {P11_10, UART5, 3},
<> 144:ef7eb2e8f9f7 79 {P6_6 , UART5, 5},
<> 144:ef7eb2e8f9f7 80 {P5_6 , UART6, 5},
<> 144:ef7eb2e8f9f7 81 {P11_1 , UART6, 4},
<> 144:ef7eb2e8f9f7 82 {P7_4 , UART7, 4},
<> 144:ef7eb2e8f9f7 83 {NC , NC , 0}
<> 144:ef7eb2e8f9f7 84 };
<> 144:ef7eb2e8f9f7 85
<> 144:ef7eb2e8f9f7 86 static const PinMap PinMap_UART_RX[] = {
<> 144:ef7eb2e8f9f7 87 {P2_15 , UART0, 6},
<> 144:ef7eb2e8f9f7 88 {P2_6 , UART1, 6},
<> 144:ef7eb2e8f9f7 89 {P4_13 , UART1, 7},
<> 144:ef7eb2e8f9f7 90 {P6_2 , UART2, 7},
<> 144:ef7eb2e8f9f7 91 {P4_15 , UART2, 7},
<> 144:ef7eb2e8f9f7 92 {P5_4 , UART3, 5},
<> 144:ef7eb2e8f9f7 93 {P8_9 , UART3, 7},
<> 144:ef7eb2e8f9f7 94 {P5_1 , UART4, 5},
<> 144:ef7eb2e8f9f7 95 {P8_15 , UART4, 7},
<> 144:ef7eb2e8f9f7 96 {P8_11 , UART5, 5},
<> 144:ef7eb2e8f9f7 97 {P11_11, UART5, 3},
<> 144:ef7eb2e8f9f7 98 {P6_7 , UART5, 5},
<> 144:ef7eb2e8f9f7 99 {P5_7 , UART6, 5},
<> 144:ef7eb2e8f9f7 100 {P11_2 , UART6, 4},
<> 144:ef7eb2e8f9f7 101 {P7_5 , UART7, 4},
<> 144:ef7eb2e8f9f7 102 {NC , NC , 0}
<> 144:ef7eb2e8f9f7 103 };
<> 144:ef7eb2e8f9f7 104
<> 144:ef7eb2e8f9f7 105 static const PinMap PinMap_UART_CTS[] = {
<> 144:ef7eb2e8f9f7 106 {P2_3 , UART1, 6},
<> 144:ef7eb2e8f9f7 107 {P11_7 , UART5, 3},
<> 144:ef7eb2e8f9f7 108 {P7_6 , UART7, 4},
<> 144:ef7eb2e8f9f7 109 {NC , NC , 0}
<> 144:ef7eb2e8f9f7 110 };
<> 144:ef7eb2e8f9f7 111 static const PinMap PinMap_UART_RTS[] = {
<> 144:ef7eb2e8f9f7 112 {P2_7 , UART1, 6},
<> 144:ef7eb2e8f9f7 113 {P11_8 , UART5, 3},
<> 144:ef7eb2e8f9f7 114 {P7_7 , UART7, 4},
<> 144:ef7eb2e8f9f7 115 {NC , NC , 0}
<> 144:ef7eb2e8f9f7 116 };
<> 144:ef7eb2e8f9f7 117
<> 144:ef7eb2e8f9f7 118
<> 144:ef7eb2e8f9f7 119
<> 144:ef7eb2e8f9f7 120 static const struct st_scif *SCIF[] = SCIF_ADDRESS_LIST;
<> 144:ef7eb2e8f9f7 121 static uart_irq_handler irq_handler;
<> 144:ef7eb2e8f9f7 122
<> 144:ef7eb2e8f9f7 123 int stdio_uart_inited = 0;
<> 144:ef7eb2e8f9f7 124 serial_t stdio_uart;
<> 144:ef7eb2e8f9f7 125
<> 144:ef7eb2e8f9f7 126 struct serial_global_data_s {
<> 144:ef7eb2e8f9f7 127 uint32_t serial_irq_id;
<> 144:ef7eb2e8f9f7 128 gpio_t sw_rts, sw_cts;
<> 144:ef7eb2e8f9f7 129 uint8_t rx_irq_set_flow, rx_irq_set_api;
<> 144:ef7eb2e8f9f7 130 serial_t *tranferring_obj, *receiving_obj;
<> 144:ef7eb2e8f9f7 131 uint32_t async_tx_callback, async_rx_callback;
<> 144:ef7eb2e8f9f7 132 int event, wanted_rx_events;
<> 144:ef7eb2e8f9f7 133 };
<> 144:ef7eb2e8f9f7 134
<> 144:ef7eb2e8f9f7 135 static struct serial_global_data_s uart_data[UART_NUM];
<> 144:ef7eb2e8f9f7 136
<> 144:ef7eb2e8f9f7 137 static const IRQn_Type irq_set_tbl[UART_NUM][IRQ_NUM] = {
<> 144:ef7eb2e8f9f7 138 {SCIFRXI0_IRQn, SCIFTXI0_IRQn, SCIFBRI0_IRQn, SCIFERI0_IRQn},
<> 144:ef7eb2e8f9f7 139 {SCIFRXI1_IRQn, SCIFTXI1_IRQn, SCIFBRI1_IRQn, SCIFERI1_IRQn},
<> 144:ef7eb2e8f9f7 140 {SCIFRXI2_IRQn, SCIFTXI2_IRQn, SCIFBRI2_IRQn, SCIFERI2_IRQn},
<> 144:ef7eb2e8f9f7 141 {SCIFRXI3_IRQn, SCIFTXI3_IRQn, SCIFBRI3_IRQn, SCIFERI3_IRQn},
<> 144:ef7eb2e8f9f7 142 {SCIFRXI4_IRQn, SCIFTXI4_IRQn, SCIFBRI4_IRQn, SCIFERI4_IRQn},
<> 144:ef7eb2e8f9f7 143 {SCIFRXI5_IRQn, SCIFTXI5_IRQn, SCIFBRI5_IRQn, SCIFERI5_IRQn},
<> 144:ef7eb2e8f9f7 144 {SCIFRXI6_IRQn, SCIFTXI6_IRQn, SCIFBRI6_IRQn, SCIFERI6_IRQn},
<> 144:ef7eb2e8f9f7 145 {SCIFRXI7_IRQn, SCIFTXI7_IRQn, SCIFBRI7_IRQn, SCIFERI7_IRQn}
<> 144:ef7eb2e8f9f7 146 };
<> 144:ef7eb2e8f9f7 147
<> 144:ef7eb2e8f9f7 148 static const IRQHandler hander_set_tbl[UART_NUM][IRQ_NUM] = {
<> 144:ef7eb2e8f9f7 149 {uart0_rx_irq, uart0_tx_irq, uart0_er_irq, uart0_er_irq},
<> 144:ef7eb2e8f9f7 150 {uart1_rx_irq, uart1_tx_irq, uart1_er_irq, uart1_er_irq},
<> 144:ef7eb2e8f9f7 151 {uart2_rx_irq, uart2_tx_irq, uart2_er_irq, uart2_er_irq},
<> 144:ef7eb2e8f9f7 152 {uart3_rx_irq, uart3_tx_irq, uart3_er_irq, uart3_er_irq},
<> 144:ef7eb2e8f9f7 153 {uart4_rx_irq, uart4_tx_irq, uart4_er_irq, uart4_er_irq},
<> 144:ef7eb2e8f9f7 154 {uart5_rx_irq, uart5_tx_irq, uart5_er_irq, uart5_er_irq},
<> 144:ef7eb2e8f9f7 155 {uart6_rx_irq, uart6_tx_irq, uart6_er_irq, uart6_er_irq},
<> 144:ef7eb2e8f9f7 156 {uart7_rx_irq, uart7_tx_irq, uart7_er_irq, uart7_er_irq}
<> 144:ef7eb2e8f9f7 157 };
<> 144:ef7eb2e8f9f7 158
<> 144:ef7eb2e8f9f7 159 static __IO uint16_t *SCSCR_MATCH[] = {
<> 144:ef7eb2e8f9f7 160 &SCSCR_0,
<> 144:ef7eb2e8f9f7 161 &SCSCR_1,
<> 144:ef7eb2e8f9f7 162 &SCSCR_2,
<> 144:ef7eb2e8f9f7 163 &SCSCR_3,
<> 144:ef7eb2e8f9f7 164 &SCSCR_4,
<> 144:ef7eb2e8f9f7 165 &SCSCR_5,
<> 144:ef7eb2e8f9f7 166 &SCSCR_6,
<> 144:ef7eb2e8f9f7 167 &SCSCR_7,
<> 144:ef7eb2e8f9f7 168 };
<> 144:ef7eb2e8f9f7 169
<> 144:ef7eb2e8f9f7 170 static __IO uint16_t *SCFSR_MATCH[] = {
<> 144:ef7eb2e8f9f7 171 &SCFSR_0,
<> 144:ef7eb2e8f9f7 172 &SCFSR_1,
<> 144:ef7eb2e8f9f7 173 &SCFSR_2,
<> 144:ef7eb2e8f9f7 174 &SCFSR_3,
<> 144:ef7eb2e8f9f7 175 &SCFSR_4,
<> 144:ef7eb2e8f9f7 176 &SCFSR_5,
<> 144:ef7eb2e8f9f7 177 &SCFSR_6,
<> 144:ef7eb2e8f9f7 178 &SCFSR_7,
<> 144:ef7eb2e8f9f7 179 };
<> 144:ef7eb2e8f9f7 180
<> 144:ef7eb2e8f9f7 181
<> 144:ef7eb2e8f9f7 182 void serial_init(serial_t *obj, PinName tx, PinName rx) {
<> 144:ef7eb2e8f9f7 183 volatile uint8_t dummy ;
<> 144:ef7eb2e8f9f7 184 int is_stdio_uart = 0;
<> 144:ef7eb2e8f9f7 185 // determine the UART to use
<> 144:ef7eb2e8f9f7 186 uint32_t uart_tx = pinmap_peripheral(tx, PinMap_UART_TX);
<> 144:ef7eb2e8f9f7 187 uint32_t uart_rx = pinmap_peripheral(rx, PinMap_UART_RX);
<> 144:ef7eb2e8f9f7 188 uint32_t uart = pinmap_merge(uart_tx, uart_rx);
<> 144:ef7eb2e8f9f7 189
<> 144:ef7eb2e8f9f7 190 MBED_ASSERT((int)uart != NC);
<> 144:ef7eb2e8f9f7 191
<> 144:ef7eb2e8f9f7 192 obj->serial.uart = (struct st_scif *)SCIF[uart];
<> 144:ef7eb2e8f9f7 193 // enable power
<> 144:ef7eb2e8f9f7 194 switch (uart) {
<> 144:ef7eb2e8f9f7 195 case UART0:
<> 144:ef7eb2e8f9f7 196 CPG.STBCR4 &= ~(1 << 7);
<> 144:ef7eb2e8f9f7 197 break;
<> 144:ef7eb2e8f9f7 198 case UART1:
<> 144:ef7eb2e8f9f7 199 CPG.STBCR4 &= ~(1 << 6);
<> 144:ef7eb2e8f9f7 200 break;
<> 144:ef7eb2e8f9f7 201 case UART2:
<> 144:ef7eb2e8f9f7 202 CPG.STBCR4 &= ~(1 << 5);
<> 144:ef7eb2e8f9f7 203 break;
<> 144:ef7eb2e8f9f7 204 case UART3:
<> 144:ef7eb2e8f9f7 205 CPG.STBCR4 &= ~(1 << 4);
<> 144:ef7eb2e8f9f7 206 break;
<> 144:ef7eb2e8f9f7 207 case UART4:
<> 144:ef7eb2e8f9f7 208 CPG.STBCR4 &= ~(1 << 3);
<> 144:ef7eb2e8f9f7 209 break;
<> 144:ef7eb2e8f9f7 210 case UART5:
<> 144:ef7eb2e8f9f7 211 CPG.STBCR4 &= ~(1 << 2);
<> 144:ef7eb2e8f9f7 212 break;
<> 144:ef7eb2e8f9f7 213 case UART6:
<> 144:ef7eb2e8f9f7 214 CPG.STBCR4 &= ~(1 << 1);
<> 144:ef7eb2e8f9f7 215 break;
<> 144:ef7eb2e8f9f7 216 case UART7:
<> 144:ef7eb2e8f9f7 217 CPG.STBCR4 &= ~(1 << 0);
<> 144:ef7eb2e8f9f7 218 break;
<> 144:ef7eb2e8f9f7 219 }
<> 144:ef7eb2e8f9f7 220 dummy = CPG.STBCR4;
<> 144:ef7eb2e8f9f7 221
<> 144:ef7eb2e8f9f7 222 /* ==== SCIF initial setting ==== */
<> 144:ef7eb2e8f9f7 223 /* ---- Serial control register (SCSCR) setting ---- */
<> 144:ef7eb2e8f9f7 224 /* B'00 : Internal CLK */
<> 144:ef7eb2e8f9f7 225 obj->serial.uart->SCSCR = 0x0000u; /* SCIF transmitting and receiving operations stop */
<> 144:ef7eb2e8f9f7 226
<> 144:ef7eb2e8f9f7 227 /* ---- FIFO control register (SCFCR) setting ---- */
<> 144:ef7eb2e8f9f7 228 /* Transmit FIFO reset & Receive FIFO data register reset */
<> 144:ef7eb2e8f9f7 229 obj->serial.uart->SCFCR = 0x0006;
<> 144:ef7eb2e8f9f7 230
<> 144:ef7eb2e8f9f7 231 /* ---- Serial status register (SCFSR) setting ---- */
<> 144:ef7eb2e8f9f7 232 dummy = obj->serial.uart->SCFSR;
<> 144:ef7eb2e8f9f7 233 obj->serial.uart->SCFSR = (dummy & 0xFF6Cu); /* ER,BRK,DR bit clear */
<> 144:ef7eb2e8f9f7 234
<> 144:ef7eb2e8f9f7 235 /* ---- Line status register (SCLSR) setting ---- */
<> 144:ef7eb2e8f9f7 236 /* ORER bit clear */
<> 144:ef7eb2e8f9f7 237 obj->serial.uart->SCLSR = 0;
<> 144:ef7eb2e8f9f7 238
<> 144:ef7eb2e8f9f7 239 /* ---- Serial extension mode register (SCEMR) setting ----
<> 144:ef7eb2e8f9f7 240 b7 BGDM - Baud rate generator double-speed mode : Normal mode
<> 144:ef7eb2e8f9f7 241 b0 ABCS - Base clock select in asynchronous mode : Base clock is 16 times the bit rate */
<> 144:ef7eb2e8f9f7 242 obj->serial.uart->SCEMR = 0x0000u;
<> 144:ef7eb2e8f9f7 243
<> 144:ef7eb2e8f9f7 244 /* ---- Bit rate register (SCBRR) setting ---- */
<> 144:ef7eb2e8f9f7 245 serial_baud (obj, 9600);
<> 144:ef7eb2e8f9f7 246 serial_format(obj, 8, ParityNone, 1);
<> 144:ef7eb2e8f9f7 247
<> 144:ef7eb2e8f9f7 248 /* ---- FIFO control register (SCFCR) setting ---- */
<> 144:ef7eb2e8f9f7 249 obj->serial.uart->SCFCR = 0x0030u;
<> 144:ef7eb2e8f9f7 250
<> 144:ef7eb2e8f9f7 251 /* ---- Serial port register (SCSPTR) setting ----
<> 144:ef7eb2e8f9f7 252 b1 SPB2IO - Serial port break output : disabled
<> 144:ef7eb2e8f9f7 253 b0 SPB2DT - Serial port break data : High-level */
<> 144:ef7eb2e8f9f7 254 obj->serial.uart->SCSPTR = 0x0003u; // SPB2IO = 1, SPB2DT = 1
<> 144:ef7eb2e8f9f7 255
<> 144:ef7eb2e8f9f7 256 /* ---- Line status register (SCLSR) setting ----
<> 144:ef7eb2e8f9f7 257 b0 ORER - Overrun error detect : clear */
<> 144:ef7eb2e8f9f7 258
<> 144:ef7eb2e8f9f7 259 if (obj->serial.uart->SCLSR & 0x0001) {
<> 144:ef7eb2e8f9f7 260 obj->serial.uart->SCLSR = 0u; // ORER clear
<> 144:ef7eb2e8f9f7 261 }
<> 144:ef7eb2e8f9f7 262
<> 144:ef7eb2e8f9f7 263 // pinout the chosen uart
<> 144:ef7eb2e8f9f7 264 pinmap_pinout(tx, PinMap_UART_TX);
<> 144:ef7eb2e8f9f7 265 pinmap_pinout(rx, PinMap_UART_RX);
<> 144:ef7eb2e8f9f7 266
<> 144:ef7eb2e8f9f7 267 switch (uart) {
<> 144:ef7eb2e8f9f7 268 case UART0:
<> 144:ef7eb2e8f9f7 269 obj->serial.index = 0;
<> 144:ef7eb2e8f9f7 270 break;
<> 144:ef7eb2e8f9f7 271 case UART1:
<> 144:ef7eb2e8f9f7 272 obj->serial.index = 1;
<> 144:ef7eb2e8f9f7 273 break;
<> 144:ef7eb2e8f9f7 274 case UART2:
<> 144:ef7eb2e8f9f7 275 obj->serial.index = 2;
<> 144:ef7eb2e8f9f7 276 break;
<> 144:ef7eb2e8f9f7 277 case UART3:
<> 144:ef7eb2e8f9f7 278 obj->serial.index = 3;
<> 144:ef7eb2e8f9f7 279 break;
<> 144:ef7eb2e8f9f7 280 case UART4:
<> 144:ef7eb2e8f9f7 281 obj->serial.index = 4;
<> 144:ef7eb2e8f9f7 282 break;
<> 144:ef7eb2e8f9f7 283 case UART5:
<> 144:ef7eb2e8f9f7 284 obj->serial.index = 5;
<> 144:ef7eb2e8f9f7 285 break;
<> 144:ef7eb2e8f9f7 286 case UART6:
<> 144:ef7eb2e8f9f7 287 obj->serial.index = 6;
<> 144:ef7eb2e8f9f7 288 break;
<> 144:ef7eb2e8f9f7 289 case UART7:
<> 144:ef7eb2e8f9f7 290 obj->serial.index = 7;
<> 144:ef7eb2e8f9f7 291 break;
<> 144:ef7eb2e8f9f7 292 }
<> 144:ef7eb2e8f9f7 293 uart_data[obj->serial.index].sw_rts.pin = NC;
<> 144:ef7eb2e8f9f7 294 uart_data[obj->serial.index].sw_cts.pin = NC;
<> 144:ef7eb2e8f9f7 295
<> 144:ef7eb2e8f9f7 296 /* ---- Serial control register (SCSCR) setting ---- */
<> 144:ef7eb2e8f9f7 297 /* Setting the TE and RE bits enables the TxD and RxD pins to be used. */
<> 144:ef7eb2e8f9f7 298 obj->serial.uart->SCSCR = 0x0070;
<> 144:ef7eb2e8f9f7 299
<> 144:ef7eb2e8f9f7 300 is_stdio_uart = (uart == STDIO_UART) ? (1) : (0);
<> 144:ef7eb2e8f9f7 301
<> 144:ef7eb2e8f9f7 302 if (is_stdio_uart) {
<> 144:ef7eb2e8f9f7 303 stdio_uart_inited = 1;
<> 144:ef7eb2e8f9f7 304 memcpy(&stdio_uart, obj, sizeof(serial_t));
<> 144:ef7eb2e8f9f7 305 }
<> 144:ef7eb2e8f9f7 306 }
<> 144:ef7eb2e8f9f7 307
<> 144:ef7eb2e8f9f7 308 void serial_free(serial_t *obj) {
<> 144:ef7eb2e8f9f7 309 uart_data[obj->serial.index].serial_irq_id = 0;
<> 144:ef7eb2e8f9f7 310 }
<> 144:ef7eb2e8f9f7 311
<> 144:ef7eb2e8f9f7 312 // serial_baud
<> 144:ef7eb2e8f9f7 313 // set the baud rate, taking in to account the current SystemFrequency
<> 144:ef7eb2e8f9f7 314 void serial_baud(serial_t *obj, int baudrate) {
<> 144:ef7eb2e8f9f7 315 uint16_t DL;
<> 144:ef7eb2e8f9f7 316
<> 144:ef7eb2e8f9f7 317 obj->serial.uart->SCSMR &= ~0x0003;
<> 144:ef7eb2e8f9f7 318
<> 144:ef7eb2e8f9f7 319 if (baudrate > 32552) {
<> 144:ef7eb2e8f9f7 320 obj->serial.uart->SCEMR = 0x0081; // BGDM = 1, ABCS = 1
<> 144:ef7eb2e8f9f7 321 DL = PCLK / (8 * baudrate);
<> 144:ef7eb2e8f9f7 322 if (DL > 0) {
<> 144:ef7eb2e8f9f7 323 DL--;
<> 144:ef7eb2e8f9f7 324 }
<> 144:ef7eb2e8f9f7 325 obj->serial.uart->SCBRR = (uint8_t)DL;
<> 144:ef7eb2e8f9f7 326 } else if (baudrate > 16276) {
<> 144:ef7eb2e8f9f7 327 obj->serial.uart->SCEMR = 0x0080; // BGDM = 1
<> 144:ef7eb2e8f9f7 328 obj->serial.uart->SCBRR = PCLK / (16 * baudrate) - 1;
<> 144:ef7eb2e8f9f7 329 } else if (baudrate > 8138) {
<> 144:ef7eb2e8f9f7 330 obj->serial.uart->SCEMR = 0x0000;
<> 144:ef7eb2e8f9f7 331 obj->serial.uart->SCBRR = PCLK / (32 * baudrate) - 1;
<> 144:ef7eb2e8f9f7 332 } else if (baudrate > 4169) {
<> 144:ef7eb2e8f9f7 333 obj->serial.uart->SCSMR |= 0x0001;
<> 144:ef7eb2e8f9f7 334 obj->serial.uart->SCEMR = 0x0080; // BGDM = 1
<> 144:ef7eb2e8f9f7 335 obj->serial.uart->SCBRR = PCLK / (64 * baudrate) - 1;
<> 144:ef7eb2e8f9f7 336 } else if (baudrate > 2034) {
<> 144:ef7eb2e8f9f7 337 obj->serial.uart->SCSMR |= 0x0001;
<> 144:ef7eb2e8f9f7 338 obj->serial.uart->SCEMR = 0x0000;
<> 144:ef7eb2e8f9f7 339 obj->serial.uart->SCBRR = PCLK / (128 * baudrate) - 1;
<> 144:ef7eb2e8f9f7 340 } else if (baudrate > 1017) {
<> 144:ef7eb2e8f9f7 341 obj->serial.uart->SCSMR |= 0x0002;
<> 144:ef7eb2e8f9f7 342 obj->serial.uart->SCEMR = 0x0080; // BGDM = 1
<> 144:ef7eb2e8f9f7 343 obj->serial.uart->SCBRR = PCLK / (256 * baudrate) - 1;
<> 144:ef7eb2e8f9f7 344 } else if (baudrate > 508) {
<> 144:ef7eb2e8f9f7 345 obj->serial.uart->SCSMR |= 0x0002;
<> 144:ef7eb2e8f9f7 346 obj->serial.uart->SCEMR = 0x0000;
<> 144:ef7eb2e8f9f7 347 obj->serial.uart->SCBRR = PCLK / (512 * baudrate) - 1;
<> 144:ef7eb2e8f9f7 348 } else if (baudrate > 254) {
<> 144:ef7eb2e8f9f7 349 obj->serial.uart->SCSMR |= 0x0003;
<> 144:ef7eb2e8f9f7 350 obj->serial.uart->SCEMR = 0x0080; // BGDM = 1
<> 144:ef7eb2e8f9f7 351 obj->serial.uart->SCBRR = PCLK / (1024 * baudrate) - 1;
<> 144:ef7eb2e8f9f7 352 } else if (baudrate > 127) {
<> 144:ef7eb2e8f9f7 353 obj->serial.uart->SCSMR |= 0x0003;
<> 144:ef7eb2e8f9f7 354 obj->serial.uart->SCEMR = 0x0000;
<> 144:ef7eb2e8f9f7 355 obj->serial.uart->SCBRR = PCLK / (2048 * baudrate) - 1;
<> 144:ef7eb2e8f9f7 356 } else {
<> 144:ef7eb2e8f9f7 357 obj->serial.uart->SCSMR |= 0x0003;
<> 144:ef7eb2e8f9f7 358 obj->serial.uart->SCEMR = 0x0000;
<> 144:ef7eb2e8f9f7 359 obj->serial.uart->SCBRR = 0xFFu;
<> 144:ef7eb2e8f9f7 360 }
<> 144:ef7eb2e8f9f7 361 }
<> 144:ef7eb2e8f9f7 362
<> 144:ef7eb2e8f9f7 363 void serial_format(serial_t *obj, int data_bits, SerialParity parity, int stop_bits) {
<> 144:ef7eb2e8f9f7 364 int parity_enable;
<> 144:ef7eb2e8f9f7 365 int parity_select;
<> 144:ef7eb2e8f9f7 366
<> 144:ef7eb2e8f9f7 367 MBED_ASSERT((stop_bits == 1) || (stop_bits == 2)); // 0: 1 stop bits, 1: 2 stop bits
<> 144:ef7eb2e8f9f7 368 MBED_ASSERT((data_bits > 4) && (data_bits < 9)); // 5: 5 data bits ... 3: 8 data bits
<> 144:ef7eb2e8f9f7 369 MBED_ASSERT((parity == ParityNone) || (parity == ParityOdd) || (parity == ParityEven) ||
<> 144:ef7eb2e8f9f7 370 (parity == ParityForced1) || (parity == ParityForced0));
<> 144:ef7eb2e8f9f7 371
<> 144:ef7eb2e8f9f7 372 stop_bits = (stop_bits == 1)? 0:
<> 144:ef7eb2e8f9f7 373 (stop_bits == 2)? 1:
<> 144:ef7eb2e8f9f7 374 0; // must not to be
<> 144:ef7eb2e8f9f7 375
<> 144:ef7eb2e8f9f7 376 data_bits = (data_bits == 8)? 0:
<> 144:ef7eb2e8f9f7 377 (data_bits == 7)? 1:
<> 144:ef7eb2e8f9f7 378 0; // must not to be
<> 144:ef7eb2e8f9f7 379
<> 144:ef7eb2e8f9f7 380 switch (parity) {
<> 144:ef7eb2e8f9f7 381 case ParityNone:
<> 144:ef7eb2e8f9f7 382 parity_enable = 0;
<> 144:ef7eb2e8f9f7 383 parity_select = 0;
<> 144:ef7eb2e8f9f7 384 break;
<> 144:ef7eb2e8f9f7 385 case ParityOdd:
<> 144:ef7eb2e8f9f7 386 parity_enable = 1;
<> 144:ef7eb2e8f9f7 387 parity_select = 1;
<> 144:ef7eb2e8f9f7 388 break;
<> 144:ef7eb2e8f9f7 389 case ParityEven:
<> 144:ef7eb2e8f9f7 390 parity_enable = 1;
<> 144:ef7eb2e8f9f7 391 parity_select = 0;
<> 144:ef7eb2e8f9f7 392 break;
<> 144:ef7eb2e8f9f7 393 case ParityForced1:
<> 144:ef7eb2e8f9f7 394 case ParityForced0:
<> 144:ef7eb2e8f9f7 395 default:
<> 144:ef7eb2e8f9f7 396 parity_enable = 0;
<> 144:ef7eb2e8f9f7 397 parity_select = 0;
<> 144:ef7eb2e8f9f7 398 break;
<> 144:ef7eb2e8f9f7 399 }
<> 144:ef7eb2e8f9f7 400
<> 144:ef7eb2e8f9f7 401 obj->serial.uart->SCSMR = data_bits << 6
<> 144:ef7eb2e8f9f7 402 | parity_enable << 5
<> 144:ef7eb2e8f9f7 403 | parity_select << 4
<> 144:ef7eb2e8f9f7 404 | stop_bits << 3;
<> 144:ef7eb2e8f9f7 405 }
<> 144:ef7eb2e8f9f7 406
<> 144:ef7eb2e8f9f7 407 /******************************************************************************
<> 144:ef7eb2e8f9f7 408 * INTERRUPTS HANDLING
<> 144:ef7eb2e8f9f7 409 ******************************************************************************/
<> 144:ef7eb2e8f9f7 410
<> 144:ef7eb2e8f9f7 411 static void uart_tx_irq(IRQn_Type irq_num, uint32_t index) {
<> 144:ef7eb2e8f9f7 412 __IO uint16_t *dmy_rd_scscr;
<> 144:ef7eb2e8f9f7 413 __IO uint16_t *dmy_rd_scfsr;
<> 144:ef7eb2e8f9f7 414 serial_t *obj;
<> 144:ef7eb2e8f9f7 415 int i;
<> 144:ef7eb2e8f9f7 416
<> 144:ef7eb2e8f9f7 417 dmy_rd_scscr = SCSCR_MATCH[index];
<> 144:ef7eb2e8f9f7 418 *dmy_rd_scscr &= 0x007B; // Clear TIE and Write to bit15~8,2 is always 0
<> 144:ef7eb2e8f9f7 419 dmy_rd_scfsr = SCFSR_MATCH[index];
<> 144:ef7eb2e8f9f7 420 *dmy_rd_scfsr = (*dmy_rd_scfsr & ~0x0020); // Set TEND
<> 144:ef7eb2e8f9f7 421
<> 144:ef7eb2e8f9f7 422 obj = uart_data[index].tranferring_obj;
<> 144:ef7eb2e8f9f7 423 if (obj) {
<> 144:ef7eb2e8f9f7 424 i = obj->tx_buff.length - obj->tx_buff.pos;
<> 144:ef7eb2e8f9f7 425 if (0 < i) {
<> 144:ef7eb2e8f9f7 426 if (serial_available_buffer(obj) < i) {
<> 144:ef7eb2e8f9f7 427 i = serial_available_buffer(obj);
<> 144:ef7eb2e8f9f7 428 }
<> 144:ef7eb2e8f9f7 429 do {
<> 144:ef7eb2e8f9f7 430 uint8_t c = *(uint8_t *)obj->tx_buff.buffer;
<> 144:ef7eb2e8f9f7 431 obj->tx_buff.buffer = (uint8_t *)obj->tx_buff.buffer + 1;
<> 144:ef7eb2e8f9f7 432 ++obj->tx_buff.pos;
<> 144:ef7eb2e8f9f7 433 obj->serial.uart->SCFTDR = c;
<> 144:ef7eb2e8f9f7 434 } while (--i);
<> 144:ef7eb2e8f9f7 435 serial_put_done(obj);
<> 144:ef7eb2e8f9f7 436 } else {
<> 144:ef7eb2e8f9f7 437 uart_data[index].tranferring_obj = NULL;
<> 144:ef7eb2e8f9f7 438 uart_data[index].event = SERIAL_EVENT_TX_COMPLETE;
<> 144:ef7eb2e8f9f7 439 ((void (*)())uart_data[index].async_tx_callback)();
<> 144:ef7eb2e8f9f7 440 }
<> 144:ef7eb2e8f9f7 441 }
<> 144:ef7eb2e8f9f7 442
<> 144:ef7eb2e8f9f7 443 irq_handler(uart_data[index].serial_irq_id, TxIrq);
<> 144:ef7eb2e8f9f7 444 }
<> 144:ef7eb2e8f9f7 445
<> 144:ef7eb2e8f9f7 446 static void uart_rx_irq(IRQn_Type irq_num, uint32_t index) {
<> 144:ef7eb2e8f9f7 447 __IO uint16_t *dmy_rd_scscr;
<> 144:ef7eb2e8f9f7 448 __IO uint16_t *dmy_rd_scfsr;
<> 144:ef7eb2e8f9f7 449 serial_t *obj;
<> 144:ef7eb2e8f9f7 450 int c;
<> 144:ef7eb2e8f9f7 451
<> 144:ef7eb2e8f9f7 452 dmy_rd_scscr = SCSCR_MATCH[index];
<> 144:ef7eb2e8f9f7 453 *dmy_rd_scscr &= 0x00B3; // Clear RIE,REIE and Write to bit15~8,2 is always 0
<> 144:ef7eb2e8f9f7 454 dmy_rd_scfsr = SCFSR_MATCH[index];
<> 144:ef7eb2e8f9f7 455 *dmy_rd_scfsr = (*dmy_rd_scfsr & ~0x0003); // Clear RDF,DR
<> 144:ef7eb2e8f9f7 456
<> 144:ef7eb2e8f9f7 457 obj = uart_data[index].receiving_obj;
<> 144:ef7eb2e8f9f7 458 if (obj) {
<> 144:ef7eb2e8f9f7 459 if (obj->serial.uart->SCLSR & 1) {
<> 144:ef7eb2e8f9f7 460 if (uart_data[index].wanted_rx_events & SERIAL_EVENT_RX_OVERRUN_ERROR) {
<> 144:ef7eb2e8f9f7 461 serial_rx_abort_asynch(obj);
<> 144:ef7eb2e8f9f7 462 uart_data[index].event = SERIAL_EVENT_RX_OVERRUN_ERROR;
<> 144:ef7eb2e8f9f7 463 ((void (*)())uart_data[index].async_rx_callback)();
<> 144:ef7eb2e8f9f7 464 }
<> 144:ef7eb2e8f9f7 465 return;
<> 144:ef7eb2e8f9f7 466 }
<> 144:ef7eb2e8f9f7 467 c = serial_getc(obj);
<> 144:ef7eb2e8f9f7 468 if (c != -1) {
<> 144:ef7eb2e8f9f7 469 ((uint8_t *)obj->rx_buff.buffer)[obj->rx_buff.pos] = c;
<> 144:ef7eb2e8f9f7 470 ++obj->rx_buff.pos;
<> 144:ef7eb2e8f9f7 471 if (c == obj->char_match && ! obj->char_found) {
<> 144:ef7eb2e8f9f7 472 obj->char_found = 1;
<> 144:ef7eb2e8f9f7 473 if (obj->rx_buff.pos == obj->rx_buff.length) {
<> 144:ef7eb2e8f9f7 474 if (uart_data[index].wanted_rx_events & SERIAL_EVENT_RX_COMPLETE) {
<> 144:ef7eb2e8f9f7 475 uart_data[index].event = SERIAL_EVENT_RX_COMPLETE;
<> 144:ef7eb2e8f9f7 476 }
<> 144:ef7eb2e8f9f7 477 }
<> 144:ef7eb2e8f9f7 478 if (uart_data[index].wanted_rx_events & SERIAL_EVENT_RX_CHARACTER_MATCH) {
<> 144:ef7eb2e8f9f7 479 uart_data[index].event |= SERIAL_EVENT_RX_CHARACTER_MATCH;
<> 144:ef7eb2e8f9f7 480 }
<> 144:ef7eb2e8f9f7 481 if (uart_data[index].event) {
<> 144:ef7eb2e8f9f7 482 uart_data[index].receiving_obj = NULL;
<> 144:ef7eb2e8f9f7 483 ((void (*)())uart_data[index].async_rx_callback)();
<> 144:ef7eb2e8f9f7 484 }
<> 144:ef7eb2e8f9f7 485 } else if (obj->rx_buff.pos == obj->rx_buff.length) {
<> 144:ef7eb2e8f9f7 486 uart_data[index].receiving_obj = NULL;
<> 144:ef7eb2e8f9f7 487 if (uart_data[index].wanted_rx_events & SERIAL_EVENT_RX_COMPLETE) {
<> 144:ef7eb2e8f9f7 488 uart_data[index].event = SERIAL_EVENT_RX_COMPLETE;
<> 144:ef7eb2e8f9f7 489 ((void (*)())uart_data[index].async_rx_callback)();
<> 144:ef7eb2e8f9f7 490 }
<> 144:ef7eb2e8f9f7 491 }
<> 144:ef7eb2e8f9f7 492 } else {
<> 144:ef7eb2e8f9f7 493 serial_rx_abort_asynch(obj);
<> 144:ef7eb2e8f9f7 494 if (uart_data[index].wanted_rx_events & (SERIAL_EVENT_RX_PARITY_ERROR | SERIAL_EVENT_RX_FRAMING_ERROR)) {
<> 144:ef7eb2e8f9f7 495 uart_data[index].event = SERIAL_EVENT_RX_PARITY_ERROR | SERIAL_EVENT_RX_FRAMING_ERROR;
<> 144:ef7eb2e8f9f7 496 if (obj->serial.uart->SCFSR & 1 << 2) {
<> 144:ef7eb2e8f9f7 497 uart_data[index].event = SERIAL_EVENT_RX_PARITY_ERROR;
<> 144:ef7eb2e8f9f7 498 } else if (obj->serial.uart->SCFSR & 1 << 3) {
<> 144:ef7eb2e8f9f7 499 uart_data[index].event = SERIAL_EVENT_RX_FRAMING_ERROR;
<> 144:ef7eb2e8f9f7 500 }
<> 144:ef7eb2e8f9f7 501 ((void (*)())uart_data[index].async_rx_callback)();
<> 144:ef7eb2e8f9f7 502 }
<> 144:ef7eb2e8f9f7 503 return;
<> 144:ef7eb2e8f9f7 504 }
<> 144:ef7eb2e8f9f7 505 }
<> 144:ef7eb2e8f9f7 506
<> 144:ef7eb2e8f9f7 507 irq_handler(uart_data[index].serial_irq_id, RxIrq);
<> 144:ef7eb2e8f9f7 508 }
<> 144:ef7eb2e8f9f7 509
<> 144:ef7eb2e8f9f7 510 static void uart_err_irq(IRQn_Type irq_num, uint32_t index) {
<> 144:ef7eb2e8f9f7 511 serial_t *obj = uart_data[index].receiving_obj;
<> 144:ef7eb2e8f9f7 512 int was_masked, err_read;
<> 144:ef7eb2e8f9f7 513
<> 144:ef7eb2e8f9f7 514 if (obj) {
<> 144:ef7eb2e8f9f7 515 serial_irq_err_set(obj, 0);
<> 144:ef7eb2e8f9f7 516 if (uart_data[index].wanted_rx_events & (SERIAL_EVENT_RX_PARITY_ERROR | SERIAL_EVENT_RX_FRAMING_ERROR)) {
<> 144:ef7eb2e8f9f7 517 uart_data[index].event = SERIAL_EVENT_RX_PARITY_ERROR | SERIAL_EVENT_RX_FRAMING_ERROR;
<> 144:ef7eb2e8f9f7 518 if (obj->serial.uart->SCFSR & 1 << 2) {
<> 144:ef7eb2e8f9f7 519 uart_data[index].event = SERIAL_EVENT_RX_PARITY_ERROR;
<> 144:ef7eb2e8f9f7 520 } else if (obj->serial.uart->SCFSR & 1 << 3) {
<> 144:ef7eb2e8f9f7 521 uart_data[index].event = SERIAL_EVENT_RX_FRAMING_ERROR;
<> 144:ef7eb2e8f9f7 522 }
<> 144:ef7eb2e8f9f7 523 ((void (*)())uart_data[index].async_rx_callback)();
<> 144:ef7eb2e8f9f7 524 }
<> 144:ef7eb2e8f9f7 525 serial_rx_abort_asynch(obj);
<> 144:ef7eb2e8f9f7 526
<> 144:ef7eb2e8f9f7 527 #if defined ( __ICCARM__ )
<> 144:ef7eb2e8f9f7 528 was_masked = __disable_irq_iar();
<> 144:ef7eb2e8f9f7 529 #else
<> 144:ef7eb2e8f9f7 530 was_masked = __disable_irq();
<> 144:ef7eb2e8f9f7 531 #endif /* __ICCARM__ */
<> 144:ef7eb2e8f9f7 532 if (obj->serial.uart->SCFSR & 0x93) {
<> 144:ef7eb2e8f9f7 533 err_read = obj->serial.uart->SCFSR;
<> 144:ef7eb2e8f9f7 534 obj->serial.uart->SCFSR = (err_read & ~0x93);
<> 144:ef7eb2e8f9f7 535 }
<> 144:ef7eb2e8f9f7 536 if (obj->serial.uart->SCLSR & 1) {
<> 144:ef7eb2e8f9f7 537 obj->serial.uart->SCLSR = 0;
<> 144:ef7eb2e8f9f7 538 }
<> 144:ef7eb2e8f9f7 539 if (!was_masked) {
<> 144:ef7eb2e8f9f7 540 __enable_irq();
<> 144:ef7eb2e8f9f7 541 }
<> 144:ef7eb2e8f9f7 542 }
<> 144:ef7eb2e8f9f7 543 }
<> 144:ef7eb2e8f9f7 544
<> 144:ef7eb2e8f9f7 545 /* TX handler */
<> 144:ef7eb2e8f9f7 546 static void uart0_tx_irq(void) {
<> 144:ef7eb2e8f9f7 547 uart_tx_irq(SCIFTXI0_IRQn, 0);
<> 144:ef7eb2e8f9f7 548 }
<> 144:ef7eb2e8f9f7 549 static void uart1_tx_irq(void) {
<> 144:ef7eb2e8f9f7 550 uart_tx_irq(SCIFTXI1_IRQn, 1);
<> 144:ef7eb2e8f9f7 551 }
<> 144:ef7eb2e8f9f7 552 static void uart2_tx_irq(void) {
<> 144:ef7eb2e8f9f7 553 uart_tx_irq(SCIFTXI2_IRQn, 2);
<> 144:ef7eb2e8f9f7 554 }
<> 144:ef7eb2e8f9f7 555 static void uart3_tx_irq(void) {
<> 144:ef7eb2e8f9f7 556 uart_tx_irq(SCIFTXI3_IRQn, 3);
<> 144:ef7eb2e8f9f7 557 }
<> 144:ef7eb2e8f9f7 558 static void uart4_tx_irq(void) {
<> 144:ef7eb2e8f9f7 559 uart_tx_irq(SCIFTXI4_IRQn, 4);
<> 144:ef7eb2e8f9f7 560 }
<> 144:ef7eb2e8f9f7 561 static void uart5_tx_irq(void) {
<> 144:ef7eb2e8f9f7 562 uart_tx_irq(SCIFTXI5_IRQn, 5);
<> 144:ef7eb2e8f9f7 563 }
<> 144:ef7eb2e8f9f7 564 static void uart6_tx_irq(void) {
<> 144:ef7eb2e8f9f7 565 uart_tx_irq(SCIFTXI6_IRQn, 6);
<> 144:ef7eb2e8f9f7 566 }
<> 144:ef7eb2e8f9f7 567 static void uart7_tx_irq(void) {
<> 144:ef7eb2e8f9f7 568 uart_tx_irq(SCIFTXI7_IRQn, 7);
<> 144:ef7eb2e8f9f7 569 }
<> 144:ef7eb2e8f9f7 570 /* RX handler */
<> 144:ef7eb2e8f9f7 571 static void uart0_rx_irq(void) {
<> 144:ef7eb2e8f9f7 572 uart_rx_irq(SCIFRXI0_IRQn, 0);
<> 144:ef7eb2e8f9f7 573 }
<> 144:ef7eb2e8f9f7 574 static void uart1_rx_irq(void) {
<> 144:ef7eb2e8f9f7 575 uart_rx_irq(SCIFRXI1_IRQn, 1);
<> 144:ef7eb2e8f9f7 576 }
<> 144:ef7eb2e8f9f7 577 static void uart2_rx_irq(void) {
<> 144:ef7eb2e8f9f7 578 uart_rx_irq(SCIFRXI2_IRQn, 2);
<> 144:ef7eb2e8f9f7 579 }
<> 144:ef7eb2e8f9f7 580 static void uart3_rx_irq(void) {
<> 144:ef7eb2e8f9f7 581 uart_rx_irq(SCIFRXI3_IRQn, 3);
<> 144:ef7eb2e8f9f7 582 }
<> 144:ef7eb2e8f9f7 583 static void uart4_rx_irq(void) {
<> 144:ef7eb2e8f9f7 584 uart_rx_irq(SCIFRXI4_IRQn, 4);
<> 144:ef7eb2e8f9f7 585 }
<> 144:ef7eb2e8f9f7 586 static void uart5_rx_irq(void) {
<> 144:ef7eb2e8f9f7 587 uart_rx_irq(SCIFRXI5_IRQn, 5);
<> 144:ef7eb2e8f9f7 588 }
<> 144:ef7eb2e8f9f7 589 static void uart6_rx_irq(void) {
<> 144:ef7eb2e8f9f7 590 uart_rx_irq(SCIFRXI6_IRQn, 6);
<> 144:ef7eb2e8f9f7 591 }
<> 144:ef7eb2e8f9f7 592 static void uart7_rx_irq(void) {
<> 144:ef7eb2e8f9f7 593 uart_rx_irq(SCIFRXI7_IRQn, 7);
<> 144:ef7eb2e8f9f7 594 }
<> 144:ef7eb2e8f9f7 595 /* Error handler */
<> 144:ef7eb2e8f9f7 596 static void uart0_er_irq(void)
<> 144:ef7eb2e8f9f7 597 {
<> 144:ef7eb2e8f9f7 598 uart_err_irq(SCIFERI0_IRQn, 0);
<> 144:ef7eb2e8f9f7 599 }
<> 144:ef7eb2e8f9f7 600 static void uart1_er_irq(void)
<> 144:ef7eb2e8f9f7 601 {
<> 144:ef7eb2e8f9f7 602 uart_err_irq(SCIFERI0_IRQn, 1);
<> 144:ef7eb2e8f9f7 603 }
<> 144:ef7eb2e8f9f7 604 static void uart2_er_irq(void)
<> 144:ef7eb2e8f9f7 605 {
<> 144:ef7eb2e8f9f7 606 uart_err_irq(SCIFERI0_IRQn, 2);
<> 144:ef7eb2e8f9f7 607 }
<> 144:ef7eb2e8f9f7 608 static void uart3_er_irq(void)
<> 144:ef7eb2e8f9f7 609 {
<> 144:ef7eb2e8f9f7 610 uart_err_irq(SCIFERI0_IRQn, 3);
<> 144:ef7eb2e8f9f7 611 }
<> 144:ef7eb2e8f9f7 612 static void uart4_er_irq(void)
<> 144:ef7eb2e8f9f7 613 {
<> 144:ef7eb2e8f9f7 614 uart_err_irq(SCIFERI0_IRQn, 4);
<> 144:ef7eb2e8f9f7 615 }
<> 144:ef7eb2e8f9f7 616 static void uart5_er_irq(void)
<> 144:ef7eb2e8f9f7 617 {
<> 144:ef7eb2e8f9f7 618 uart_err_irq(SCIFERI0_IRQn, 5);
<> 144:ef7eb2e8f9f7 619 }
<> 144:ef7eb2e8f9f7 620 static void uart6_er_irq(void)
<> 144:ef7eb2e8f9f7 621 {
<> 144:ef7eb2e8f9f7 622 uart_err_irq(SCIFERI0_IRQn, 6);
<> 144:ef7eb2e8f9f7 623 }
<> 144:ef7eb2e8f9f7 624 static void uart7_er_irq(void)
<> 144:ef7eb2e8f9f7 625 {
<> 144:ef7eb2e8f9f7 626 uart_err_irq(SCIFERI0_IRQn, 7);
<> 144:ef7eb2e8f9f7 627 }
<> 144:ef7eb2e8f9f7 628
<> 144:ef7eb2e8f9f7 629 void serial_irq_handler(serial_t *obj, uart_irq_handler handler, uint32_t id) {
<> 144:ef7eb2e8f9f7 630 irq_handler = handler;
<> 144:ef7eb2e8f9f7 631 uart_data[obj->serial.index].serial_irq_id = id;
<> 144:ef7eb2e8f9f7 632 }
<> 144:ef7eb2e8f9f7 633
<> 144:ef7eb2e8f9f7 634 static void serial_irq_set_irq(IRQn_Type IRQn, IRQHandler handler, uint32_t enable)
<> 144:ef7eb2e8f9f7 635 {
<> 144:ef7eb2e8f9f7 636 if (enable) {
<> 144:ef7eb2e8f9f7 637 InterruptHandlerRegister(IRQn, (void (*)(uint32_t))handler);
<> 144:ef7eb2e8f9f7 638 GIC_SetPriority(IRQn, 5);
<> 144:ef7eb2e8f9f7 639 GIC_EnableIRQ(IRQn);
<> 144:ef7eb2e8f9f7 640 } else {
<> 144:ef7eb2e8f9f7 641 GIC_DisableIRQ(IRQn);
<> 144:ef7eb2e8f9f7 642 }
<> 144:ef7eb2e8f9f7 643 }
<> 144:ef7eb2e8f9f7 644
<> 144:ef7eb2e8f9f7 645 static void serial_irq_set_internal(serial_t *obj, SerialIrq irq, uint32_t enable) {
<> 144:ef7eb2e8f9f7 646 IRQn_Type IRQn;
<> 144:ef7eb2e8f9f7 647 IRQHandler handler;
<> 144:ef7eb2e8f9f7 648
<> 144:ef7eb2e8f9f7 649 IRQn = irq_set_tbl[obj->serial.index][irq];
<> 144:ef7eb2e8f9f7 650 handler = hander_set_tbl[obj->serial.index][irq];
<> 144:ef7eb2e8f9f7 651
<> 144:ef7eb2e8f9f7 652 if ((obj->serial.index >= 0) && (obj->serial.index <= 7)) {
<> 144:ef7eb2e8f9f7 653 serial_irq_set_irq(IRQn, handler, enable);
<> 144:ef7eb2e8f9f7 654 }
<> 144:ef7eb2e8f9f7 655 }
<> 144:ef7eb2e8f9f7 656
<> 144:ef7eb2e8f9f7 657 static void serial_irq_err_set(serial_t *obj, uint32_t enable)
<> 144:ef7eb2e8f9f7 658 {
<> 144:ef7eb2e8f9f7 659 serial_irq_set_irq(irq_set_tbl[obj->serial.index][2], hander_set_tbl[obj->serial.index][2], enable);
<> 144:ef7eb2e8f9f7 660 serial_irq_set_irq(irq_set_tbl[obj->serial.index][3], hander_set_tbl[obj->serial.index][3], enable);
<> 144:ef7eb2e8f9f7 661 }
<> 144:ef7eb2e8f9f7 662
<> 144:ef7eb2e8f9f7 663 void serial_irq_set(serial_t *obj, SerialIrq irq, uint32_t enable) {
<> 144:ef7eb2e8f9f7 664 if (RxIrq == irq) {
<> 144:ef7eb2e8f9f7 665 uart_data[obj->serial.index].rx_irq_set_api = enable;
<> 144:ef7eb2e8f9f7 666 }
<> 144:ef7eb2e8f9f7 667 serial_irq_set_internal(obj, irq, enable);
<> 144:ef7eb2e8f9f7 668 }
<> 144:ef7eb2e8f9f7 669
<> 144:ef7eb2e8f9f7 670 static void serial_flow_irq_set(serial_t *obj, uint32_t enable) {
<> 144:ef7eb2e8f9f7 671 uart_data[obj->serial.index].rx_irq_set_flow = enable;
<> 144:ef7eb2e8f9f7 672 serial_irq_set_internal(obj, RxIrq, enable);
<> 144:ef7eb2e8f9f7 673 }
<> 144:ef7eb2e8f9f7 674
<> 144:ef7eb2e8f9f7 675 /******************************************************************************
<> 144:ef7eb2e8f9f7 676 * READ/WRITE
<> 144:ef7eb2e8f9f7 677 ******************************************************************************/
<> 144:ef7eb2e8f9f7 678 int serial_getc(serial_t *obj) {
<> 144:ef7eb2e8f9f7 679 uint16_t err_read;
<> 144:ef7eb2e8f9f7 680 int data;
<> 144:ef7eb2e8f9f7 681 int was_masked;
<> 144:ef7eb2e8f9f7 682
<> 144:ef7eb2e8f9f7 683 #if defined ( __ICCARM__ )
<> 144:ef7eb2e8f9f7 684 was_masked = __disable_irq_iar();
<> 144:ef7eb2e8f9f7 685 #else
<> 144:ef7eb2e8f9f7 686 was_masked = __disable_irq();
<> 144:ef7eb2e8f9f7 687 #endif /* __ICCARM__ */
<> 144:ef7eb2e8f9f7 688 if (obj->serial.uart->SCFSR & 0x93) {
<> 144:ef7eb2e8f9f7 689 err_read = obj->serial.uart->SCFSR;
<> 144:ef7eb2e8f9f7 690 obj->serial.uart->SCFSR = (err_read & ~0x93);
<> 144:ef7eb2e8f9f7 691 }
<> 144:ef7eb2e8f9f7 692 obj->serial.uart->SCSCR |= 0x0040; // Set RIE
<> 144:ef7eb2e8f9f7 693 if (!was_masked) {
<> 144:ef7eb2e8f9f7 694 __enable_irq();
<> 144:ef7eb2e8f9f7 695 }
<> 144:ef7eb2e8f9f7 696
<> 144:ef7eb2e8f9f7 697 if (obj->serial.uart->SCLSR & 0x0001) {
<> 144:ef7eb2e8f9f7 698 obj->serial.uart->SCLSR = 0u; // ORER clear
<> 144:ef7eb2e8f9f7 699 }
<> 144:ef7eb2e8f9f7 700
<> 144:ef7eb2e8f9f7 701 while (!serial_readable(obj));
<> 144:ef7eb2e8f9f7 702 data = obj->serial.uart->SCFRDR & 0xff;
<> 144:ef7eb2e8f9f7 703
<> 144:ef7eb2e8f9f7 704 #if defined ( __ICCARM__ )
<> 144:ef7eb2e8f9f7 705 was_masked = __disable_irq_iar();
<> 144:ef7eb2e8f9f7 706 #else
<> 144:ef7eb2e8f9f7 707 was_masked = __disable_irq();
<> 144:ef7eb2e8f9f7 708 #endif /* __ICCARM__ */
<> 144:ef7eb2e8f9f7 709 err_read = obj->serial.uart->SCFSR;
<> 144:ef7eb2e8f9f7 710 obj->serial.uart->SCFSR = (err_read & 0xfffD); // Clear RDF
<> 144:ef7eb2e8f9f7 711 if (!was_masked) {
<> 144:ef7eb2e8f9f7 712 __enable_irq();
<> 144:ef7eb2e8f9f7 713 }
<> 144:ef7eb2e8f9f7 714
<> 144:ef7eb2e8f9f7 715 if (err_read & 0x80) {
<> 144:ef7eb2e8f9f7 716 data = -1; //err
<> 144:ef7eb2e8f9f7 717 }
<> 144:ef7eb2e8f9f7 718 return data;
<> 144:ef7eb2e8f9f7 719 }
<> 144:ef7eb2e8f9f7 720
<> 144:ef7eb2e8f9f7 721 void serial_putc(serial_t *obj, int c) {
<> 144:ef7eb2e8f9f7 722 while (!serial_writable(obj));
<> 144:ef7eb2e8f9f7 723 obj->serial.uart->SCFTDR = c;
<> 144:ef7eb2e8f9f7 724 serial_put_done(obj);
<> 144:ef7eb2e8f9f7 725 }
<> 144:ef7eb2e8f9f7 726
<> 144:ef7eb2e8f9f7 727 static void serial_put_done(serial_t *obj)
<> 144:ef7eb2e8f9f7 728 {
<> 144:ef7eb2e8f9f7 729 int was_masked;
<> 144:ef7eb2e8f9f7 730 volatile uint16_t dummy_read;
<> 144:ef7eb2e8f9f7 731
<> 144:ef7eb2e8f9f7 732 #if defined ( __ICCARM__ )
<> 144:ef7eb2e8f9f7 733 was_masked = __disable_irq_iar();
<> 144:ef7eb2e8f9f7 734 #else
<> 144:ef7eb2e8f9f7 735 was_masked = __disable_irq();
<> 144:ef7eb2e8f9f7 736 #endif /* __ICCARM__ */
<> 144:ef7eb2e8f9f7 737 dummy_read = obj->serial.uart->SCFSR;
<> 144:ef7eb2e8f9f7 738 obj->serial.uart->SCFSR = (dummy_read & 0xff9f); // Clear TEND/TDFE
<> 144:ef7eb2e8f9f7 739 obj->serial.uart->SCSCR |= 0x0080; // Set TIE
<> 144:ef7eb2e8f9f7 740 if (!was_masked) {
<> 144:ef7eb2e8f9f7 741 __enable_irq();
<> 144:ef7eb2e8f9f7 742 }
<> 144:ef7eb2e8f9f7 743 }
<> 144:ef7eb2e8f9f7 744
<> 144:ef7eb2e8f9f7 745 int serial_readable(serial_t *obj) {
<> 144:ef7eb2e8f9f7 746 return ((obj->serial.uart->SCFSR & 0x02) != 0); // RDF
<> 144:ef7eb2e8f9f7 747 }
<> 144:ef7eb2e8f9f7 748
<> 144:ef7eb2e8f9f7 749 int serial_writable(serial_t *obj) {
<> 144:ef7eb2e8f9f7 750 return ((obj->serial.uart->SCFSR & 0x20) != 0); // TDFE
<> 144:ef7eb2e8f9f7 751 }
<> 144:ef7eb2e8f9f7 752
<> 144:ef7eb2e8f9f7 753 void serial_clear(serial_t *obj) {
<> 144:ef7eb2e8f9f7 754 int was_masked;
<> 144:ef7eb2e8f9f7 755 #if defined ( __ICCARM__ )
<> 144:ef7eb2e8f9f7 756 was_masked = __disable_irq_iar();
<> 144:ef7eb2e8f9f7 757 #else
<> 144:ef7eb2e8f9f7 758 was_masked = __disable_irq();
<> 144:ef7eb2e8f9f7 759 #endif /* __ICCARM__ */
<> 144:ef7eb2e8f9f7 760
<> 144:ef7eb2e8f9f7 761 obj->serial.uart->SCFCR |= 0x06; // TFRST = 1, RFRST = 1
<> 144:ef7eb2e8f9f7 762 obj->serial.uart->SCFCR &= ~0x06; // TFRST = 0, RFRST = 0
<> 144:ef7eb2e8f9f7 763 obj->serial.uart->SCFSR &= ~0x0093u; // ER, BRK, RDF, DR = 0
<> 144:ef7eb2e8f9f7 764
<> 144:ef7eb2e8f9f7 765 if (!was_masked) {
<> 144:ef7eb2e8f9f7 766 __enable_irq();
<> 144:ef7eb2e8f9f7 767 }
<> 144:ef7eb2e8f9f7 768 }
<> 144:ef7eb2e8f9f7 769
<> 144:ef7eb2e8f9f7 770 void serial_pinout_tx(PinName tx) {
<> 144:ef7eb2e8f9f7 771 pinmap_pinout(tx, PinMap_UART_TX);
<> 144:ef7eb2e8f9f7 772 }
<> 144:ef7eb2e8f9f7 773
<> 144:ef7eb2e8f9f7 774 void serial_break_set(serial_t *obj) {
<> 144:ef7eb2e8f9f7 775 int was_masked;
<> 144:ef7eb2e8f9f7 776 #if defined ( __ICCARM__ )
<> 144:ef7eb2e8f9f7 777 was_masked = __disable_irq_iar();
<> 144:ef7eb2e8f9f7 778 #else
<> 144:ef7eb2e8f9f7 779 was_masked = __disable_irq();
<> 144:ef7eb2e8f9f7 780 #endif /* __ICCARM__ */
<> 144:ef7eb2e8f9f7 781 // TxD Output(L)
<> 144:ef7eb2e8f9f7 782 obj->serial.uart->SCSPTR &= ~0x0001u; // SPB2DT = 0
<> 144:ef7eb2e8f9f7 783 obj->serial.uart->SCSCR &= ~0x0020u; // TE = 0 (Output disable)
<> 144:ef7eb2e8f9f7 784 if (!was_masked) {
<> 144:ef7eb2e8f9f7 785 __enable_irq();
<> 144:ef7eb2e8f9f7 786 }
<> 144:ef7eb2e8f9f7 787 }
<> 144:ef7eb2e8f9f7 788
<> 144:ef7eb2e8f9f7 789 void serial_break_clear(serial_t *obj) {
<> 144:ef7eb2e8f9f7 790 int was_masked;
<> 144:ef7eb2e8f9f7 791 #if defined ( __ICCARM__ )
<> 144:ef7eb2e8f9f7 792 was_masked = __disable_irq_iar();
<> 144:ef7eb2e8f9f7 793 #else
<> 144:ef7eb2e8f9f7 794 was_masked = __disable_irq();
<> 144:ef7eb2e8f9f7 795 #endif /* __ICCARM__ */
<> 144:ef7eb2e8f9f7 796 obj->serial.uart->SCSCR |= 0x0020u; // TE = 1 (Output enable)
<> 144:ef7eb2e8f9f7 797 obj->serial.uart->SCSPTR |= 0x0001u; // SPB2DT = 1
<> 144:ef7eb2e8f9f7 798 if (!was_masked) {
<> 144:ef7eb2e8f9f7 799 __enable_irq();
<> 144:ef7eb2e8f9f7 800 }
<> 144:ef7eb2e8f9f7 801 }
<> 144:ef7eb2e8f9f7 802
<> 144:ef7eb2e8f9f7 803 void serial_set_flow_control(serial_t *obj, FlowControl type, PinName rxflow, PinName txflow) {
<> 144:ef7eb2e8f9f7 804 // determine the UART to use
<> 144:ef7eb2e8f9f7 805 int was_masked;
<> 144:ef7eb2e8f9f7 806
<> 144:ef7eb2e8f9f7 807 serial_flow_irq_set(obj, 0);
<> 144:ef7eb2e8f9f7 808
<> 144:ef7eb2e8f9f7 809 if (type == FlowControlRTSCTS) {
<> 144:ef7eb2e8f9f7 810 #if defined ( __ICCARM__ )
<> 144:ef7eb2e8f9f7 811 was_masked = __disable_irq_iar();
<> 144:ef7eb2e8f9f7 812 #else
<> 144:ef7eb2e8f9f7 813 was_masked = __disable_irq();
<> 144:ef7eb2e8f9f7 814 #endif /* __ICCARM__ */
<> 144:ef7eb2e8f9f7 815 obj->serial.uart->SCFCR = 0x0008u; // CTS/RTS enable
<> 144:ef7eb2e8f9f7 816 if (!was_masked) {
<> 144:ef7eb2e8f9f7 817 __enable_irq();
<> 144:ef7eb2e8f9f7 818 }
<> 144:ef7eb2e8f9f7 819 pinmap_pinout(rxflow, PinMap_UART_RTS);
<> 144:ef7eb2e8f9f7 820 pinmap_pinout(txflow, PinMap_UART_CTS);
<> 144:ef7eb2e8f9f7 821 } else {
<> 144:ef7eb2e8f9f7 822 #if defined ( __ICCARM__ )
<> 144:ef7eb2e8f9f7 823 was_masked = __disable_irq_iar();
<> 144:ef7eb2e8f9f7 824 #else
<> 144:ef7eb2e8f9f7 825 was_masked = __disable_irq();
<> 144:ef7eb2e8f9f7 826 #endif /* __ICCARM__ */
<> 144:ef7eb2e8f9f7 827 obj->serial.uart->SCFCR = 0x0000u; // CTS/RTS diable
<> 144:ef7eb2e8f9f7 828 if (!was_masked) {
<> 144:ef7eb2e8f9f7 829 __enable_irq();
<> 144:ef7eb2e8f9f7 830 }
<> 144:ef7eb2e8f9f7 831 }
<> 144:ef7eb2e8f9f7 832 }
<> 144:ef7eb2e8f9f7 833
<> 144:ef7eb2e8f9f7 834 static uint8_t serial_available_buffer(serial_t *obj)
<> 144:ef7eb2e8f9f7 835 {
<> 144:ef7eb2e8f9f7 836 return 1;
<> 144:ef7eb2e8f9f7 837 /* Faster but unstable way */
<> 144:ef7eb2e8f9f7 838 /*
<> 144:ef7eb2e8f9f7 839 uint16_t ret = 16 - ((obj->serial.uart->SCFDR >> 8) & 0x1F);
<> 144:ef7eb2e8f9f7 840 while (ret == 0) {
<> 144:ef7eb2e8f9f7 841 ret = 16 - ((obj->serial.uart->SCFDR >> 8) & 0x1F);
<> 144:ef7eb2e8f9f7 842 }
<> 144:ef7eb2e8f9f7 843 MBED_ASSERT(0 < ret && ret <= 16);
<> 144:ef7eb2e8f9f7 844 return ret;
<> 144:ef7eb2e8f9f7 845 */
<> 144:ef7eb2e8f9f7 846 }
<> 144:ef7eb2e8f9f7 847
<> 144:ef7eb2e8f9f7 848 #if DEVICE_SERIAL_ASYNCH
<> 144:ef7eb2e8f9f7 849
<> 144:ef7eb2e8f9f7 850 /******************************************************************************
<> 144:ef7eb2e8f9f7 851 * ASYNCHRONOUS HAL
<> 144:ef7eb2e8f9f7 852 ******************************************************************************/
<> 144:ef7eb2e8f9f7 853
<> 144:ef7eb2e8f9f7 854 int serial_tx_asynch(serial_t *obj, const void *tx, size_t tx_length, uint8_t tx_width, uint32_t handler, uint32_t event, DMAUsage hint)
<> 144:ef7eb2e8f9f7 855 {
<> 144:ef7eb2e8f9f7 856 int i;
<> 144:ef7eb2e8f9f7 857 buffer_t *buf = &obj->tx_buff;
<> 144:ef7eb2e8f9f7 858 struct serial_global_data_s *data = uart_data + obj->serial.index;
<> 144:ef7eb2e8f9f7 859
<> 144:ef7eb2e8f9f7 860 if (tx_length == 0) {
<> 144:ef7eb2e8f9f7 861 return 0;
<> 144:ef7eb2e8f9f7 862 }
<> 144:ef7eb2e8f9f7 863
<> 144:ef7eb2e8f9f7 864 buf->buffer = (void *)tx;
<> 144:ef7eb2e8f9f7 865 buf->length = tx_length * tx_width / 8;
<> 144:ef7eb2e8f9f7 866 buf->pos = 0;
<> 144:ef7eb2e8f9f7 867 buf->width = tx_width;
<> 144:ef7eb2e8f9f7 868 data->tranferring_obj = obj;
<> 144:ef7eb2e8f9f7 869 data->async_tx_callback = handler;
<> 144:ef7eb2e8f9f7 870 serial_irq_set(obj, TxIrq, 1);
<> 144:ef7eb2e8f9f7 871
<> 144:ef7eb2e8f9f7 872 while (!serial_writable(obj));
<> 144:ef7eb2e8f9f7 873 i = buf->length;
<> 144:ef7eb2e8f9f7 874 if (serial_available_buffer(obj) < i) {
<> 144:ef7eb2e8f9f7 875 i = serial_available_buffer(obj);
<> 144:ef7eb2e8f9f7 876 }
<> 144:ef7eb2e8f9f7 877 do {
<> 144:ef7eb2e8f9f7 878 uint8_t c = *(uint8_t *)buf->buffer;
<> 144:ef7eb2e8f9f7 879 obj->tx_buff.buffer = (uint8_t *)obj->tx_buff.buffer + 1;
<> 144:ef7eb2e8f9f7 880 ++buf->pos;
<> 144:ef7eb2e8f9f7 881 obj->serial.uart->SCFTDR = c;
<> 144:ef7eb2e8f9f7 882 } while (--i);
<> 144:ef7eb2e8f9f7 883 serial_put_done(obj);
<> 144:ef7eb2e8f9f7 884
<> 144:ef7eb2e8f9f7 885 return buf->length;
<> 144:ef7eb2e8f9f7 886 }
<> 144:ef7eb2e8f9f7 887
<> 144:ef7eb2e8f9f7 888 void serial_rx_asynch(serial_t *obj, void *rx, size_t rx_length, uint8_t rx_width, uint32_t handler, uint32_t event, uint8_t char_match, DMAUsage hint)
<> 144:ef7eb2e8f9f7 889 {
<> 144:ef7eb2e8f9f7 890 buffer_t *buf = &obj->rx_buff;
<> 144:ef7eb2e8f9f7 891 struct serial_global_data_s *data = uart_data + obj->serial.index;
<> 144:ef7eb2e8f9f7 892
<> 144:ef7eb2e8f9f7 893 if (rx_length == 0) {
<> 144:ef7eb2e8f9f7 894 return;
<> 144:ef7eb2e8f9f7 895 }
<> 144:ef7eb2e8f9f7 896
<> 144:ef7eb2e8f9f7 897 buf->buffer = rx;
<> 144:ef7eb2e8f9f7 898 buf->length = rx_length * rx_width / 8;
<> 144:ef7eb2e8f9f7 899 buf->pos = 0;
<> 144:ef7eb2e8f9f7 900 buf->width = rx_width;
<> 144:ef7eb2e8f9f7 901 obj->char_match = char_match;
<> 144:ef7eb2e8f9f7 902 obj->char_found = 0;
<> 144:ef7eb2e8f9f7 903 data->receiving_obj = obj;
<> 144:ef7eb2e8f9f7 904 data->async_rx_callback = handler;
<> 144:ef7eb2e8f9f7 905 data->event = 0;
<> 144:ef7eb2e8f9f7 906 data->wanted_rx_events = event;
<> 144:ef7eb2e8f9f7 907
<> 144:ef7eb2e8f9f7 908 serial_irq_set(obj, RxIrq, 1);
<> 144:ef7eb2e8f9f7 909 serial_irq_err_set(obj, 1);
<> 144:ef7eb2e8f9f7 910 }
<> 144:ef7eb2e8f9f7 911
<> 144:ef7eb2e8f9f7 912 uint8_t serial_tx_active(serial_t *obj)
<> 144:ef7eb2e8f9f7 913 {
<> 144:ef7eb2e8f9f7 914 return uart_data[obj->serial.index].tranferring_obj != NULL;
<> 144:ef7eb2e8f9f7 915 }
<> 144:ef7eb2e8f9f7 916
<> 144:ef7eb2e8f9f7 917 uint8_t serial_rx_active(serial_t *obj)
<> 144:ef7eb2e8f9f7 918 {
<> 144:ef7eb2e8f9f7 919 return uart_data[obj->serial.index].receiving_obj != NULL;
<> 144:ef7eb2e8f9f7 920 }
<> 144:ef7eb2e8f9f7 921
<> 144:ef7eb2e8f9f7 922 int serial_irq_handler_asynch(serial_t *obj)
<> 144:ef7eb2e8f9f7 923 {
<> 144:ef7eb2e8f9f7 924 return uart_data[obj->serial.index].event;
<> 144:ef7eb2e8f9f7 925 }
<> 144:ef7eb2e8f9f7 926
<> 144:ef7eb2e8f9f7 927 void serial_tx_abort_asynch(serial_t *obj)
<> 144:ef7eb2e8f9f7 928 {
<> 144:ef7eb2e8f9f7 929 uart_data[obj->serial.index].tranferring_obj = NULL;
<> 144:ef7eb2e8f9f7 930 obj->serial.uart->SCFCR |= 1 << 2;
<> 144:ef7eb2e8f9f7 931 obj->serial.uart->SCFCR &= ~(1 << 2);
<> 144:ef7eb2e8f9f7 932 }
<> 144:ef7eb2e8f9f7 933
<> 144:ef7eb2e8f9f7 934 void serial_rx_abort_asynch(serial_t *obj)
<> 144:ef7eb2e8f9f7 935 {
<> 144:ef7eb2e8f9f7 936 uart_data[obj->serial.index].receiving_obj = NULL;
<> 144:ef7eb2e8f9f7 937 obj->serial.uart->SCFCR |= 1 << 1;
<> 144:ef7eb2e8f9f7 938 obj->serial.uart->SCFCR &= ~(1 << 1);
<> 144:ef7eb2e8f9f7 939 }
<> 144:ef7eb2e8f9f7 940
<> 144:ef7eb2e8f9f7 941 #endif