mbed library sources modified for open wear
Dependents: openwear-lifelogger-example
Fork of mbed-src by
targets/hal/TARGET_Freescale/TARGET_KPSDK_MCUS/TARGET_K64F/serial_api.c@267:8673334f2cbe, 2014-07-29 (annotated)
- Committer:
- mbed_official
- Date:
- Tue Jul 29 18:45:06 2014 +0100
- Revision:
- 267:8673334f2cbe
- Parent:
- 265:9632ea190e16
Synchronized with git revision 1d586e1f8df5e4ff9eb4b8420095fd3f74426163
Full URL: https://github.com/mbedmicro/mbed/commit/1d586e1f8df5e4ff9eb4b8420095fd3f74426163/
Had duplicate set of api drivers in the directory - deleted
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
mbed_official | 146:f64d43ff0c18 | 1 | /* mbed Microcontroller Library |
mbed_official | 146:f64d43ff0c18 | 2 | * Copyright (c) 2006-2013 ARM Limited |
mbed_official | 146:f64d43ff0c18 | 3 | * |
mbed_official | 146:f64d43ff0c18 | 4 | * Licensed under the Apache License, Version 2.0 (the "License"); |
mbed_official | 146:f64d43ff0c18 | 5 | * you may not use this file except in compliance with the License. |
mbed_official | 146:f64d43ff0c18 | 6 | * You may obtain a copy of the License at |
mbed_official | 146:f64d43ff0c18 | 7 | * |
mbed_official | 146:f64d43ff0c18 | 8 | * http://www.apache.org/licenses/LICENSE-2.0 |
mbed_official | 146:f64d43ff0c18 | 9 | * |
mbed_official | 146:f64d43ff0c18 | 10 | * Unless required by applicable law or agreed to in writing, software |
mbed_official | 146:f64d43ff0c18 | 11 | * distributed under the License is distributed on an "AS IS" BASIS, |
mbed_official | 146:f64d43ff0c18 | 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
mbed_official | 146:f64d43ff0c18 | 13 | * See the License for the specific language governing permissions and |
mbed_official | 146:f64d43ff0c18 | 14 | * limitations under the License. |
mbed_official | 146:f64d43ff0c18 | 15 | */ |
mbed_official | 146:f64d43ff0c18 | 16 | #include "serial_api.h" |
mbed_official | 146:f64d43ff0c18 | 17 | |
mbed_official | 267:8673334f2cbe | 18 | #if DEVICE_SERIAL |
mbed_official | 267:8673334f2cbe | 19 | |
mbed_official | 146:f64d43ff0c18 | 20 | // math.h required for floating point operations for baud rate calculation |
mbed_official | 146:f64d43ff0c18 | 21 | #include <math.h> |
mbed_official | 227:7bd0639b8911 | 22 | #include "mbed_assert.h" |
mbed_official | 146:f64d43ff0c18 | 23 | |
mbed_official | 146:f64d43ff0c18 | 24 | #include <string.h> |
mbed_official | 146:f64d43ff0c18 | 25 | |
mbed_official | 146:f64d43ff0c18 | 26 | #include "cmsis.h" |
mbed_official | 146:f64d43ff0c18 | 27 | #include "pinmap.h" |
mbed_official | 146:f64d43ff0c18 | 28 | #include "fsl_uart_hal.h" |
mbed_official | 146:f64d43ff0c18 | 29 | #include "fsl_clock_manager.h" |
mbed_official | 146:f64d43ff0c18 | 30 | #include "fsl_uart_features.h" |
mbed_official | 265:9632ea190e16 | 31 | #include "PeripheralPins.h" |
mbed_official | 146:f64d43ff0c18 | 32 | |
mbed_official | 146:f64d43ff0c18 | 33 | /* TODO: |
mbed_official | 146:f64d43ff0c18 | 34 | putchar/getchar 9 and 10 bits support |
mbed_official | 146:f64d43ff0c18 | 35 | */ |
mbed_official | 146:f64d43ff0c18 | 36 | |
mbed_official | 146:f64d43ff0c18 | 37 | #define UART_NUM 4 |
mbed_official | 146:f64d43ff0c18 | 38 | |
mbed_official | 146:f64d43ff0c18 | 39 | static uint32_t serial_irq_ids[UART_NUM] = {0}; |
mbed_official | 146:f64d43ff0c18 | 40 | static uart_irq_handler irq_handler; |
mbed_official | 146:f64d43ff0c18 | 41 | |
mbed_official | 146:f64d43ff0c18 | 42 | int stdio_uart_inited = 0; |
mbed_official | 146:f64d43ff0c18 | 43 | serial_t stdio_uart; |
mbed_official | 146:f64d43ff0c18 | 44 | |
mbed_official | 146:f64d43ff0c18 | 45 | static uint32_t serial_get_clock(uint32_t uart_instance) |
mbed_official | 146:f64d43ff0c18 | 46 | { |
mbed_official | 146:f64d43ff0c18 | 47 | uint32_t uartSourceClock; |
mbed_official | 146:f64d43ff0c18 | 48 | |
mbed_official | 146:f64d43ff0c18 | 49 | if ((uart_instance == 0) || (uart_instance == 1)) { |
mbed_official | 146:f64d43ff0c18 | 50 | clock_manager_get_frequency(kSystemClock, &uartSourceClock); |
mbed_official | 146:f64d43ff0c18 | 51 | } else { |
mbed_official | 146:f64d43ff0c18 | 52 | clock_manager_get_frequency(kBusClock, &uartSourceClock); |
mbed_official | 146:f64d43ff0c18 | 53 | } |
mbed_official | 146:f64d43ff0c18 | 54 | return uartSourceClock; |
mbed_official | 146:f64d43ff0c18 | 55 | } |
mbed_official | 146:f64d43ff0c18 | 56 | |
mbed_official | 146:f64d43ff0c18 | 57 | void serial_init(serial_t *obj, PinName tx, PinName rx) { |
mbed_official | 146:f64d43ff0c18 | 58 | uint32_t uart_tx = pinmap_peripheral(tx, PinMap_UART_TX); |
mbed_official | 146:f64d43ff0c18 | 59 | uint32_t uart_rx = pinmap_peripheral(rx, PinMap_UART_RX); |
mbed_official | 146:f64d43ff0c18 | 60 | obj->index = (UARTName)pinmap_merge(uart_tx, uart_rx); |
mbed_official | 227:7bd0639b8911 | 61 | MBED_ASSERT((int)obj->index != NC); |
mbed_official | 146:f64d43ff0c18 | 62 | |
mbed_official | 146:f64d43ff0c18 | 63 | uart_config_t uart_config; |
mbed_official | 146:f64d43ff0c18 | 64 | uart_config.baudRate = 9600; |
mbed_official | 146:f64d43ff0c18 | 65 | uart_config.bitCountPerChar = kUart8BitsPerChar; |
mbed_official | 146:f64d43ff0c18 | 66 | uart_config.parityMode = kUartParityDisabled; |
mbed_official | 146:f64d43ff0c18 | 67 | uart_config.rxDataInvert = 0; |
mbed_official | 146:f64d43ff0c18 | 68 | uart_config.stopBitCount = kUartOneStopBit; |
mbed_official | 146:f64d43ff0c18 | 69 | uart_config.txDataInvert = 0; |
mbed_official | 146:f64d43ff0c18 | 70 | |
mbed_official | 146:f64d43ff0c18 | 71 | uart_config.uartSourceClockInHz = serial_get_clock(obj->index); |
mbed_official | 146:f64d43ff0c18 | 72 | |
mbed_official | 146:f64d43ff0c18 | 73 | clock_manager_set_gate(kClockModuleUART, obj->index, true); |
mbed_official | 146:f64d43ff0c18 | 74 | uart_hal_init(obj->index, &uart_config); |
mbed_official | 146:f64d43ff0c18 | 75 | |
mbed_official | 146:f64d43ff0c18 | 76 | pinmap_pinout(tx, PinMap_UART_TX); |
mbed_official | 146:f64d43ff0c18 | 77 | pinmap_pinout(rx, PinMap_UART_RX); |
mbed_official | 146:f64d43ff0c18 | 78 | |
mbed_official | 146:f64d43ff0c18 | 79 | pin_mode(tx, PullUp); |
mbed_official | 146:f64d43ff0c18 | 80 | pin_mode(rx, PullUp); |
mbed_official | 146:f64d43ff0c18 | 81 | |
mbed_official | 146:f64d43ff0c18 | 82 | if (obj->index == STDIO_UART) { |
mbed_official | 146:f64d43ff0c18 | 83 | stdio_uart_inited = 1; |
mbed_official | 146:f64d43ff0c18 | 84 | memcpy(&stdio_uart, obj, sizeof(serial_t)); |
mbed_official | 146:f64d43ff0c18 | 85 | } |
mbed_official | 146:f64d43ff0c18 | 86 | } |
mbed_official | 146:f64d43ff0c18 | 87 | |
mbed_official | 146:f64d43ff0c18 | 88 | void serial_free(serial_t *obj) { |
mbed_official | 146:f64d43ff0c18 | 89 | serial_irq_ids[obj->index] = 0; |
mbed_official | 146:f64d43ff0c18 | 90 | } |
mbed_official | 146:f64d43ff0c18 | 91 | |
mbed_official | 146:f64d43ff0c18 | 92 | void serial_baud(serial_t *obj, int baudrate) { |
mbed_official | 146:f64d43ff0c18 | 93 | uart_hal_set_baud_rate(obj->index, serial_get_clock(obj->index), (uint32_t)baudrate); |
mbed_official | 146:f64d43ff0c18 | 94 | } |
mbed_official | 146:f64d43ff0c18 | 95 | |
mbed_official | 146:f64d43ff0c18 | 96 | void serial_format(serial_t *obj, int data_bits, SerialParity parity, int stop_bits) { |
mbed_official | 146:f64d43ff0c18 | 97 | uart_hal_configure_bit_count_per_char(obj->index, (uart_bit_count_per_char_t)data_bits); |
mbed_official | 146:f64d43ff0c18 | 98 | uart_hal_configure_parity_mode(obj->index, (uart_parity_mode_t)parity); |
mbed_official | 146:f64d43ff0c18 | 99 | uart_hal_configure_stop_bit_count(obj->index, (uart_stop_bit_count_t)stop_bits); |
mbed_official | 146:f64d43ff0c18 | 100 | } |
mbed_official | 146:f64d43ff0c18 | 101 | |
mbed_official | 146:f64d43ff0c18 | 102 | /****************************************************************************** |
mbed_official | 146:f64d43ff0c18 | 103 | * INTERRUPTS HANDLING |
mbed_official | 146:f64d43ff0c18 | 104 | ******************************************************************************/ |
mbed_official | 146:f64d43ff0c18 | 105 | static inline void uart_irq(uint32_t transmit_empty, uint32_t receive_full, uint32_t index) { |
mbed_official | 146:f64d43ff0c18 | 106 | if (serial_irq_ids[index] != 0) { |
mbed_official | 146:f64d43ff0c18 | 107 | if (transmit_empty) |
mbed_official | 146:f64d43ff0c18 | 108 | irq_handler(serial_irq_ids[index], TxIrq); |
mbed_official | 146:f64d43ff0c18 | 109 | |
mbed_official | 146:f64d43ff0c18 | 110 | if (receive_full) |
mbed_official | 146:f64d43ff0c18 | 111 | irq_handler(serial_irq_ids[index], RxIrq); |
mbed_official | 146:f64d43ff0c18 | 112 | } |
mbed_official | 146:f64d43ff0c18 | 113 | } |
mbed_official | 146:f64d43ff0c18 | 114 | |
mbed_official | 146:f64d43ff0c18 | 115 | void uart0_irq() { |
mbed_official | 146:f64d43ff0c18 | 116 | uart_irq(uart_hal_is_transmit_data_register_empty(0), uart_hal_is_receive_data_register_full(0), 0); |
mbed_official | 146:f64d43ff0c18 | 117 | if (uart_hal_is_receive_overrun_detected(0)) |
mbed_official | 146:f64d43ff0c18 | 118 | uart_hal_clear_status_flag(0, kUartReceiveOverrun); |
mbed_official | 146:f64d43ff0c18 | 119 | } |
mbed_official | 146:f64d43ff0c18 | 120 | void uart1_irq() { |
mbed_official | 146:f64d43ff0c18 | 121 | uart_irq(uart_hal_is_transmit_data_register_empty(1), uart_hal_is_receive_data_register_full(1), 1); |
mbed_official | 146:f64d43ff0c18 | 122 | } |
mbed_official | 146:f64d43ff0c18 | 123 | |
mbed_official | 146:f64d43ff0c18 | 124 | void uart2_irq() { |
mbed_official | 146:f64d43ff0c18 | 125 | uart_irq(uart_hal_is_transmit_data_register_empty(2), uart_hal_is_receive_data_register_full(2), 2); |
mbed_official | 146:f64d43ff0c18 | 126 | } |
mbed_official | 146:f64d43ff0c18 | 127 | |
mbed_official | 146:f64d43ff0c18 | 128 | void uart3_irq() { |
mbed_official | 146:f64d43ff0c18 | 129 | uart_irq(uart_hal_is_transmit_data_register_empty(3), uart_hal_is_receive_data_register_full(3), 3); |
mbed_official | 146:f64d43ff0c18 | 130 | } |
mbed_official | 146:f64d43ff0c18 | 131 | |
mbed_official | 146:f64d43ff0c18 | 132 | void uart4_irq() { |
mbed_official | 146:f64d43ff0c18 | 133 | uart_irq(uart_hal_is_transmit_data_register_empty(4), uart_hal_is_receive_data_register_full(4), 4); |
mbed_official | 146:f64d43ff0c18 | 134 | } |
mbed_official | 146:f64d43ff0c18 | 135 | |
mbed_official | 146:f64d43ff0c18 | 136 | void serial_irq_handler(serial_t *obj, uart_irq_handler handler, uint32_t id) { |
mbed_official | 146:f64d43ff0c18 | 137 | irq_handler = handler; |
mbed_official | 146:f64d43ff0c18 | 138 | serial_irq_ids[obj->index] = id; |
mbed_official | 146:f64d43ff0c18 | 139 | } |
mbed_official | 146:f64d43ff0c18 | 140 | |
mbed_official | 146:f64d43ff0c18 | 141 | void serial_irq_set(serial_t *obj, SerialIrq irq, uint32_t enable) { |
mbed_official | 146:f64d43ff0c18 | 142 | IRQn_Type irq_n = (IRQn_Type)0; |
mbed_official | 146:f64d43ff0c18 | 143 | uint32_t vector = 0; |
mbed_official | 146:f64d43ff0c18 | 144 | |
mbed_official | 146:f64d43ff0c18 | 145 | switch (obj->index) { |
mbed_official | 146:f64d43ff0c18 | 146 | case 0: irq_n=UART0_RX_TX_IRQn; vector = (uint32_t)&uart0_irq; break; |
mbed_official | 146:f64d43ff0c18 | 147 | case 1: irq_n=UART1_RX_TX_IRQn; vector = (uint32_t)&uart1_irq; break; |
mbed_official | 146:f64d43ff0c18 | 148 | case 2: irq_n=UART2_RX_TX_IRQn; vector = (uint32_t)&uart2_irq; break; |
mbed_official | 146:f64d43ff0c18 | 149 | case 3: irq_n=UART3_RX_TX_IRQn; vector = (uint32_t)&uart3_irq; break; |
mbed_official | 146:f64d43ff0c18 | 150 | case 4: irq_n=UART4_RX_TX_IRQn; vector = (uint32_t)&uart4_irq; break; |
mbed_official | 146:f64d43ff0c18 | 151 | } |
mbed_official | 146:f64d43ff0c18 | 152 | |
mbed_official | 146:f64d43ff0c18 | 153 | if (enable) { |
mbed_official | 146:f64d43ff0c18 | 154 | switch (irq) { |
mbed_official | 146:f64d43ff0c18 | 155 | case RxIrq: uart_hal_enable_rx_data_register_full_interrupt(obj->index); break; |
mbed_official | 146:f64d43ff0c18 | 156 | case TxIrq: uart_hal_enable_tx_data_register_empty_interrupt(obj->index); break; |
mbed_official | 146:f64d43ff0c18 | 157 | } |
mbed_official | 146:f64d43ff0c18 | 158 | NVIC_SetVector(irq_n, vector); |
mbed_official | 146:f64d43ff0c18 | 159 | NVIC_EnableIRQ(irq_n); |
mbed_official | 146:f64d43ff0c18 | 160 | |
mbed_official | 146:f64d43ff0c18 | 161 | } else { // disable |
mbed_official | 146:f64d43ff0c18 | 162 | int all_disabled = 0; |
mbed_official | 146:f64d43ff0c18 | 163 | SerialIrq other_irq = (irq == RxIrq) ? (TxIrq) : (RxIrq); |
mbed_official | 146:f64d43ff0c18 | 164 | switch (irq) { |
mbed_official | 146:f64d43ff0c18 | 165 | case RxIrq: uart_hal_disable_rx_data_register_full_interrupt(obj->index); break; |
mbed_official | 188:e2558dbb5ee5 | 166 | case TxIrq: uart_hal_disable_tx_data_register_empty_interrupt(obj->index); break; |
mbed_official | 146:f64d43ff0c18 | 167 | } |
mbed_official | 146:f64d43ff0c18 | 168 | switch (other_irq) { |
mbed_official | 146:f64d43ff0c18 | 169 | case RxIrq: all_disabled = uart_hal_is_receive_data_full_interrupt_enabled(obj->index) == 0; break; |
mbed_official | 146:f64d43ff0c18 | 170 | case TxIrq: all_disabled = uart_hal_is_tx_data_register_empty_interrupt_enabled(obj->index) == 0; break; |
mbed_official | 146:f64d43ff0c18 | 171 | } |
mbed_official | 146:f64d43ff0c18 | 172 | if (all_disabled) |
mbed_official | 146:f64d43ff0c18 | 173 | NVIC_DisableIRQ(irq_n); |
mbed_official | 146:f64d43ff0c18 | 174 | } |
mbed_official | 146:f64d43ff0c18 | 175 | } |
mbed_official | 146:f64d43ff0c18 | 176 | |
mbed_official | 146:f64d43ff0c18 | 177 | int serial_getc(serial_t *obj) { |
mbed_official | 146:f64d43ff0c18 | 178 | while (!serial_readable(obj)); |
mbed_official | 146:f64d43ff0c18 | 179 | uint8_t data; |
mbed_official | 146:f64d43ff0c18 | 180 | uart_hal_getchar(obj->index, &data); |
mbed_official | 146:f64d43ff0c18 | 181 | |
mbed_official | 146:f64d43ff0c18 | 182 | return data; |
mbed_official | 146:f64d43ff0c18 | 183 | } |
mbed_official | 146:f64d43ff0c18 | 184 | |
mbed_official | 146:f64d43ff0c18 | 185 | void serial_putc(serial_t *obj, int c) { |
mbed_official | 146:f64d43ff0c18 | 186 | while (!serial_writable(obj)); |
mbed_official | 146:f64d43ff0c18 | 187 | uart_hal_putchar(obj->index, (uint8_t)c); |
mbed_official | 146:f64d43ff0c18 | 188 | } |
mbed_official | 146:f64d43ff0c18 | 189 | |
mbed_official | 146:f64d43ff0c18 | 190 | int serial_readable(serial_t *obj) { |
mbed_official | 146:f64d43ff0c18 | 191 | if (uart_hal_is_receive_overrun_detected(obj->index)) |
mbed_official | 146:f64d43ff0c18 | 192 | uart_hal_clear_status_flag(obj->index, kUartReceiveOverrun); |
mbed_official | 146:f64d43ff0c18 | 193 | return uart_hal_is_receive_data_register_full(obj->index); |
mbed_official | 146:f64d43ff0c18 | 194 | } |
mbed_official | 146:f64d43ff0c18 | 195 | |
mbed_official | 146:f64d43ff0c18 | 196 | int serial_writable(serial_t *obj) { |
mbed_official | 146:f64d43ff0c18 | 197 | if (uart_hal_is_receive_overrun_detected(obj->index)) |
mbed_official | 146:f64d43ff0c18 | 198 | uart_hal_clear_status_flag(obj->index, kUartReceiveOverrun); |
mbed_official | 146:f64d43ff0c18 | 199 | |
mbed_official | 146:f64d43ff0c18 | 200 | return uart_hal_is_transmit_data_register_empty(obj->index); |
mbed_official | 146:f64d43ff0c18 | 201 | } |
mbed_official | 146:f64d43ff0c18 | 202 | |
mbed_official | 146:f64d43ff0c18 | 203 | void serial_clear(serial_t *obj) { |
mbed_official | 146:f64d43ff0c18 | 204 | } |
mbed_official | 146:f64d43ff0c18 | 205 | |
mbed_official | 146:f64d43ff0c18 | 206 | void serial_pinout_tx(PinName tx) { |
mbed_official | 146:f64d43ff0c18 | 207 | pinmap_pinout(tx, PinMap_UART_TX); |
mbed_official | 146:f64d43ff0c18 | 208 | } |
mbed_official | 146:f64d43ff0c18 | 209 | |
mbed_official | 146:f64d43ff0c18 | 210 | void serial_break_set(serial_t *obj) { |
mbed_official | 146:f64d43ff0c18 | 211 | uart_hal_queue_break_char_to_send(obj->index, true); |
mbed_official | 146:f64d43ff0c18 | 212 | } |
mbed_official | 146:f64d43ff0c18 | 213 | |
mbed_official | 146:f64d43ff0c18 | 214 | void serial_break_clear(serial_t *obj) { |
mbed_official | 146:f64d43ff0c18 | 215 | uart_hal_queue_break_char_to_send(obj->index, false); |
mbed_official | 146:f64d43ff0c18 | 216 | } |
mbed_official | 146:f64d43ff0c18 | 217 | |
mbed_official | 267:8673334f2cbe | 218 | #endif |