SimpleLib_03272011
Embed:
(wiki syntax)
Show/hide line numbers
serial.h
00001 /* 00002 * Copyright or � or Copr. 2010, Thomas SOETE 00003 * 00004 * Author e-mail: thomas@soete.org 00005 * Library website : http://mbed.org/users/Alkorin/libraries/SimpleLib/ 00006 * 00007 * This software is governed by the CeCILL license under French law and 00008 * abiding by the rules of distribution of free software. You can use, 00009 * modify and/ or redistribute the software under the terms of the CeCILL 00010 * license as circulated by CEA, CNRS and INRIA at the following URL 00011 * "http://www.cecill.info". 00012 * 00013 * As a counterpart to the access to the source code and rights to copy, 00014 * modify and redistribute granted by the license, users are provided only 00015 * with a limited warranty and the software's author, the holder of the 00016 * economic rights, and the successive licensors have only limited 00017 * liability. 00018 * 00019 * In this respect, the user's attention is drawn to the risks associated 00020 * with loading, using, modifying and/or developing or reproducing the 00021 * software by the user in light of its specific status of free software, 00022 * that may mean that it is complicated to manipulate, and that also 00023 * therefore means that it is reserved for developers and experienced 00024 * professionals having in-depth computer knowledge. Users are therefore 00025 * encouraged to load and test the software's suitability as regards their 00026 * requirements in conditions enabling the security of their systems and/or 00027 * data to be ensured and, more generally, to use and operate it in the 00028 * same conditions as regards security. 00029 * 00030 * The fact that you are presently reading this means that you have had 00031 * knowledge of the CeCILL license and that you accept its terms. 00032 */ 00033 00034 #ifndef __SIMPLELIB_SERIAL_H__ 00035 #define __SIMPLELIB_SERIAL_H__ 00036 00037 #include "mbed_globals.h" 00038 #include "interrupts.h" 00039 00040 /********************************** 00041 * Simple Serial Managment * 00042 ********************************** 00043 * The interrupt handler is : * 00044 * SERIAL_INTERRUPT_HANDLER(void) * 00045 * UART0 : Serial over USB * 00046 * UART1 : TX p13, RX p14 * 00047 * UART2 : TX p28, RX p27 * 00048 * UART3 : TX p9, RX p10 * 00049 **********************************/ 00050 00051 /** Registers **/ 00052 // Serial port (Choose UARTn (0,1,2,3)) 00053 #define UART_NUMBER UART0 00054 #define UART_BASE TOKENPASTE2(LPC_,UART_NUMBER) 00055 00056 // Peripheral Clock Selection registers (See 4.7.3 p56) 00057 #define UART0_PCLK_REG (LPC_SC->PCLKSEL0) 00058 #define UART1_PCLK_REG (LPC_SC->PCLKSEL0) 00059 #define UART2_PCLK_REG (LPC_SC->PCLKSEL1) 00060 #define UART3_PCLK_REG (LPC_SC->PCLKSEL1) 00061 #define UART_PCLK_REG TOKENPASTE2(UART_NUMBER,_PCLK_REG) 00062 00063 #define UART0_PCLK_OFFSET 6 00064 #define UART1_PCLK_OFFSET 8 00065 #define UART2_PCLK_OFFSET 16 00066 #define UART3_PCLK_OFFSET 18 00067 #define UART_PCLK_OFFSET TOKENPASTE2(UART_NUMBER,_PCLK_OFFSET) 00068 00069 #define UART0_PCLK ((LPC_SC->PCLKSEL0 >> 6) & 0x03) 00070 #define UART1_PCLK ((LPC_SC->PCLKSEL0 >> 8) & 0x03) 00071 #define UART2_PCLK ((LPC_SC->PCLKSEL1 >> 16) & 0x03) 00072 #define UART3_PCLK ((LPC_SC->PCLKSEL1 >> 18) & 0x03) 00073 #define UART_PCLK TOKENPASTE2(UART_NUMBER,_PCLK) 00074 00075 // Pin Function Select register (See 8.5.1-8 p108) 00076 #define UART0RX_PINSEL_REG (LPC_PINCON->PINSEL0) 00077 #define UART1RX_PINSEL_REG (LPC_PINCON->PINSEL1) 00078 #define UART2RX_PINSEL_REG (LPC_PINCON->PINSEL0) 00079 #define UART3RX_PINSEL_REG (LPC_PINCON->PINSEL0) 00080 #define UARTRX_PINSEL_REG TOKENPASTE2(UART_NUMBER,RX_PINSEL_REG) 00081 00082 #define UART0TX_PINSEL_REG (LPC_PINCON->PINSEL0) 00083 #define UART1TX_PINSEL_REG (LPC_PINCON->PINSEL0) 00084 #define UART2TX_PINSEL_REG (LPC_PINCON->PINSEL0) 00085 #define UART3TX_PINSEL_REG (LPC_PINCON->PINSEL0) 00086 #define UARTTX_PINSEL_REG TOKENPASTE2(UART_NUMBER,TX_PINSEL_REG) 00087 00088 #define UART0RX_PINSEL_OFFSET 6 00089 #define UART1RX_PINSEL_OFFSET 0 00090 #define UART2RX_PINSEL_OFFSET 22 00091 #define UART3RX_PINSEL_OFFSET 2 00092 #define UARTRX_PINSEL_OFFSET TOKENPASTE2(UART_NUMBER,RX_PINSEL_OFFSET) 00093 00094 #define UART0TX_PINSEL_OFFSET 4 00095 #define UART1TX_PINSEL_OFFSET 30 00096 #define UART2TX_PINSEL_OFFSET 20 00097 #define UART3TX_PINSEL_OFFSET 0 00098 #define UARTTX_PINSEL_OFFSET TOKENPASTE2(UART_NUMBER,TX_PINSEL_OFFSET) 00099 00100 #define UART0_PINSEL_VALUE 1U 00101 #define UART1_PINSEL_VALUE 1U 00102 #define UART2_PINSEL_VALUE 1U 00103 #define UART3_PINSEL_VALUE 2U 00104 #define UART_PINSEL_VALUE TOKENPASTE2(UART_NUMBER,_PINSEL_VALUE) 00105 00106 /** Interrupt handlers **/ 00107 #define SERIAL_INTERRUPT_HANDLER EXTERN_C void __IRQ TOKENPASTE2(UART_NUMBER,_IRQHandler) 00108 00109 /** Bits **/ 00110 // RBR Interrupt Enable (UnIER, 14.4.4 p302) 00111 #define RBR_INT_BIT 0 00112 // Receiver Data Ready (UnLSR, 14.4.8 p306) 00113 #define RDR_BIT 0 00114 // Transmitter Holding Register Empty (UnLSR, 14.4.8 p306) 00115 #define THRE_BIT 5 00116 // RBR Interrupt Enable (UnIER, 14.4.4 p302) 00117 #define SERIAL_INT_RX 1 00118 // THRE Interrupt Enable (UnIER, 14.4.4 p302) 00119 #define SERIAL_INT_TX 2 00120 // Divisor Latch Access Bit (UnLCR, 14.4.7 p306) 00121 #define DLA_BIT 7 00122 // Power Control for Peripherals (PCONP, 4.8.7.1 p63) 00123 #define UART0_PCONP_BIT 3 00124 #define UART1_PCONP_BIT 4 00125 #define UART2_PCONP_BIT 24 00126 #define UART3_PCONP_BIT 25 00127 00128 /** Macros **/ 00129 #define SERIAL_PUTCHAR(c) do { \ 00130 while (GET_BIT_VALUE(UART_BASE->LSR, THRE_BIT) == 0); \ 00131 UART_BASE->THR = c; \ 00132 } while(0) 00133 00134 #define SERIAL_DATA_TO_READ() (GET_BIT_VALUE(UART_BASE->LSR, RDR_BIT) == 1) 00135 00136 #define SERIAL_GETCHAR() (UART_BASE->RBR) 00137 00138 // Enable interrupt for RX or TX (SERIAL_INT_RX and SERIAL_INT_TX) 00139 #define SERIAL_ENABLE_INTERRUPT(value) do { \ 00140 UART_BASE->IER = value; \ 00141 ENABLE_INTERRUPT(TOKENPASTE2(UART_NUMBER,_IRQn)); \ 00142 } while(0) 00143 00144 extern __INLINE void SERIAL_INIT() 00145 { 00146 // Enable UARTn 00147 SET_BIT_VALUE(LPC_SC->PCONP, TOKENPASTE2(UART_NUMBER,_PCONP_BIT) , 1); 00148 // Enable FIFO and reset RX/TX FIFO (See 14.4.6 p305) 00149 UART_BASE->FCR = 0x07; 00150 // 8-bits, No Parity, 1 stop bit (See 14.4.7 p306) 00151 UART_BASE->LCR = 0x03; 00152 // Set CCLK as Peripheral Clock for UART (96MHz with mbed library) 00153 UART_PCLK_REG = (UART_PCLK_REG & (~(3UL << UART_PCLK_OFFSET))) | (1U << UART_PCLK_OFFSET); 00154 // Define Pin's functions as UART 00155 UARTRX_PINSEL_REG = (UARTRX_PINSEL_REG & (~(3U << UARTRX_PINSEL_OFFSET))) | (UART_PINSEL_VALUE << UARTRX_PINSEL_OFFSET); 00156 UARTTX_PINSEL_REG = (UARTTX_PINSEL_REG & (~(3U << UARTTX_PINSEL_OFFSET))) | (UART_PINSEL_VALUE << UARTTX_PINSEL_OFFSET); 00157 } 00158 00159 // See 14.4.5 p303 00160 extern __INLINE int SERIAL_CHECK_INTERRUPT(void) { 00161 uint32_t serialStatus = UART_BASE->IIR; 00162 00163 if (serialStatus & 1) // IntStatus, 1 = No Interrupt is pending. 00164 return 0; 00165 00166 serialStatus = (serialStatus >> 1) & 0x3; // IntId, 2 = More than threshold data to read, 6 = Some caracters to read 00167 if (serialStatus != 2 && serialStatus != 6) 00168 return 0; 00169 00170 return 1; 00171 } 00172 00173 extern __INLINE void SERIAL_SETBAUD(unsigned int baud) { 00174 // Peripheral Clock Selection register bit values (See Table 42, p57) 00175 uint16_t divisorValue = (SystemCoreClock / 16 / baud); 00176 #if 0 00177 // Peripheral Clock for UART is set to CCLK in SERIAL_INIT. Divisor is then 1. 00178 // Else, use code below 00179 static int divisors[4] = { 4, 1, 2, 8 }; 00180 uint16_t divisorValue = ((SystemCoreClock / 16 / baud) / divisors[UART_PCLK]); 00181 #endif 00182 00183 UART_BASE->LCR |= (1 << DLA_BIT); 00184 UART_BASE->DLM = (uint8_t) (divisorValue >> 8); 00185 UART_BASE->DLL = (uint8_t) divisorValue; 00186 UART_BASE->LCR &= ~(1 << DLA_BIT); 00187 } 00188 00189 #endif
Generated on Fri Jul 15 2022 15:25:50 by
1.7.2