]> git.sur5r.net Git - freertos/blob - Demo/CORTEX_STM32F103_Keil/serial/serial.c
Update to V5.4.2. See http://www.freertos.org/History.txt .
[freertos] / Demo / CORTEX_STM32F103_Keil / serial / serial.c
1 /*\r
2         FreeRTOS V5.4.2 - Copyright (C) 2009 Real Time Engineers Ltd.\r
3 \r
4         This file is part of the FreeRTOS distribution.\r
5 \r
6         FreeRTOS is free software; you can redistribute it and/or modify it     under \r
7         the terms of the GNU General Public License (version 2) as published by the \r
8         Free Software Foundation and modified by the FreeRTOS exception.\r
9         **NOTE** The exception to the GPL is included to allow you to distribute a\r
10         combined work that includes FreeRTOS without being obliged to provide the \r
11         source code for proprietary components outside of the FreeRTOS kernel.  \r
12         Alternative commercial license and support terms are also available upon \r
13         request.  See the licensing section of http://www.FreeRTOS.org for full \r
14         license details.\r
15 \r
16         FreeRTOS is distributed in the hope that it will be useful,     but WITHOUT\r
17         ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or\r
18         FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for\r
19         more details.\r
20 \r
21         You should have received a copy of the GNU General Public License along\r
22         with FreeRTOS; if not, write to the Free Software Foundation, Inc., 59\r
23         Temple Place, Suite 330, Boston, MA  02111-1307  USA.\r
24 \r
25 \r
26         ***************************************************************************\r
27         *                                                                         *\r
28         * Looking for a quick start?  Then check out the FreeRTOS eBook!          *\r
29         * See http://www.FreeRTOS.org/Documentation for details                   *\r
30         *                                                                         *\r
31         ***************************************************************************\r
32 \r
33         1 tab == 4 spaces!\r
34 \r
35         Please ensure to read the configuration and relevant port sections of the\r
36         online documentation.\r
37 \r
38         http://www.FreeRTOS.org - Documentation, latest information, license and\r
39         contact details.\r
40 \r
41         http://www.SafeRTOS.com - A version that is certified for use in safety\r
42         critical systems.\r
43 \r
44         http://www.OpenRTOS.com - Commercial support, development, porting,\r
45         licensing and training services.\r
46 */\r
47 \r
48 /*\r
49         BASIC INTERRUPT DRIVEN SERIAL PORT DRIVER FOR UART0.\r
50 */\r
51 \r
52 /* Scheduler includes. */\r
53 #include "FreeRTOS.h"\r
54 #include "queue.h"\r
55 #include "semphr.h"\r
56 \r
57 /* Library includes. */\r
58 #include "stm32f10x_lib.h"\r
59 \r
60 /* Demo application includes. */\r
61 #include "serial.h"\r
62 /*-----------------------------------------------------------*/\r
63 \r
64 /* Misc defines. */\r
65 #define serINVALID_QUEUE                                ( ( xQueueHandle ) 0 )\r
66 #define serNO_BLOCK                                             ( ( portTickType ) 0 )\r
67 #define serTX_BLOCK_TIME                                ( 40 / portTICK_RATE_MS )\r
68 \r
69 /*-----------------------------------------------------------*/\r
70 \r
71 /* The queue used to hold received characters. */\r
72 static xQueueHandle xRxedChars;\r
73 static xQueueHandle xCharsForTx;\r
74 \r
75 /*-----------------------------------------------------------*/\r
76 \r
77 /* UART interrupt handler. */\r
78 void vUARTInterruptHandler( void );\r
79 \r
80 /*-----------------------------------------------------------*/\r
81 \r
82 /*\r
83  * See the serial2.h header file.\r
84  */\r
85 xComPortHandle xSerialPortInitMinimal( unsigned portLONG ulWantedBaud, unsigned portBASE_TYPE uxQueueLength )\r
86 {\r
87 xComPortHandle xReturn;\r
88 USART_InitTypeDef USART_InitStructure;\r
89 NVIC_InitTypeDef NVIC_InitStructure;\r
90 GPIO_InitTypeDef GPIO_InitStructure;\r
91 \r
92         /* Create the queues used to hold Rx/Tx characters. */\r
93         xRxedChars = xQueueCreate( uxQueueLength, ( unsigned portBASE_TYPE ) sizeof( signed portCHAR ) );\r
94         xCharsForTx = xQueueCreate( uxQueueLength + 1, ( unsigned portBASE_TYPE ) sizeof( signed portCHAR ) );\r
95         \r
96         /* If the queue/semaphore was created correctly then setup the serial port\r
97         hardware. */\r
98         if( ( xRxedChars != serINVALID_QUEUE ) && ( xCharsForTx != serINVALID_QUEUE ) )\r
99         {\r
100                 /* Enable USART1 clock */\r
101                 RCC_APB2PeriphClockCmd( RCC_APB2Periph_USART1 | RCC_APB2Periph_GPIOA, ENABLE ); \r
102 \r
103                 /* Configure USART1 Rx (PA10) as input floating */\r
104                 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_10;\r
105                 GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;\r
106                 GPIO_Init( GPIOA, &GPIO_InitStructure );\r
107                 \r
108                 /* Configure USART1 Tx (PA9) as alternate function push-pull */\r
109                 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9;\r
110                 GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;\r
111                 GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF_PP;\r
112                 GPIO_Init( GPIOA, &GPIO_InitStructure );\r
113 \r
114                 USART_InitStructure.USART_BaudRate = ulWantedBaud;\r
115                 USART_InitStructure.USART_WordLength = USART_WordLength_8b;\r
116                 USART_InitStructure.USART_StopBits = USART_StopBits_1;\r
117                 USART_InitStructure.USART_Parity = USART_Parity_No ;\r
118                 USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;\r
119                 USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx;\r
120                 USART_InitStructure.USART_Clock = USART_Clock_Disable;\r
121                 USART_InitStructure.USART_CPOL = USART_CPOL_Low;\r
122                 USART_InitStructure.USART_CPHA = USART_CPHA_2Edge;\r
123                 USART_InitStructure.USART_LastBit = USART_LastBit_Disable;\r
124                 \r
125                 USART_Init( USART1, &USART_InitStructure );\r
126                 \r
127                 USART_ITConfig( USART1, USART_IT_RXNE, ENABLE );\r
128                 \r
129                 NVIC_InitStructure.NVIC_IRQChannel = USART1_IRQChannel;\r
130                 NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = configLIBRARY_KERNEL_INTERRUPT_PRIORITY;\r
131                 NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0;\r
132                 NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;\r
133                 NVIC_Init( &NVIC_InitStructure );\r
134                 \r
135                 USART_Cmd( USART1, ENABLE );            \r
136         }\r
137         else\r
138         {\r
139                 xReturn = ( xComPortHandle ) 0;\r
140         }\r
141 \r
142         /* This demo file only supports a single port but we have to return\r
143         something to comply with the standard demo header file. */\r
144         return xReturn;\r
145 }\r
146 /*-----------------------------------------------------------*/\r
147 \r
148 signed portBASE_TYPE xSerialGetChar( xComPortHandle pxPort, signed portCHAR *pcRxedChar, portTickType xBlockTime )\r
149 {\r
150         /* The port handle is not required as this driver only supports one port. */\r
151         ( void ) pxPort;\r
152 \r
153         /* Get the next character from the buffer.  Return false if no characters\r
154         are available, or arrive before xBlockTime expires. */\r
155         if( xQueueReceive( xRxedChars, pcRxedChar, xBlockTime ) )\r
156         {\r
157                 return pdTRUE;\r
158         }\r
159         else\r
160         {\r
161                 return pdFALSE;\r
162         }\r
163 }\r
164 /*-----------------------------------------------------------*/\r
165 \r
166 void vSerialPutString( xComPortHandle pxPort, const signed portCHAR * const pcString, unsigned portSHORT usStringLength )\r
167 {\r
168 signed portCHAR *pxNext;\r
169 \r
170         /* A couple of parameters that this port does not use. */\r
171         ( void ) usStringLength;\r
172         ( void ) pxPort;\r
173 \r
174         /* NOTE: This implementation does not handle the queue being full as no\r
175         block time is used! */\r
176 \r
177         /* The port handle is not required as this driver only supports UART1. */\r
178         ( void ) pxPort;\r
179 \r
180         /* Send each character in the string, one at a time. */\r
181         pxNext = ( signed portCHAR * ) pcString;\r
182         while( *pxNext )\r
183         {\r
184                 xSerialPutChar( pxPort, *pxNext, serNO_BLOCK );\r
185                 pxNext++;\r
186         }\r
187 }\r
188 /*-----------------------------------------------------------*/\r
189 \r
190 signed portBASE_TYPE xSerialPutChar( xComPortHandle pxPort, signed portCHAR cOutChar, portTickType xBlockTime )\r
191 {\r
192 signed portBASE_TYPE xReturn;\r
193 \r
194         if( xQueueSend( xCharsForTx, &cOutChar, xBlockTime ) == pdPASS )\r
195         {\r
196                 xReturn = pdPASS;\r
197                 USART_ITConfig( USART1, USART_IT_TXE, ENABLE );\r
198         }\r
199         else\r
200         {\r
201                 xReturn = pdFAIL;\r
202         }\r
203 \r
204         return xReturn;\r
205 }\r
206 /*-----------------------------------------------------------*/\r
207 \r
208 void vSerialClose( xComPortHandle xPort )\r
209 {\r
210         /* Not supported as not required by the demo application. */\r
211 }\r
212 /*-----------------------------------------------------------*/\r
213 \r
214 void vUARTInterruptHandler( void )\r
215 {\r
216 portBASE_TYPE xHigherPriorityTaskWoken = pdFALSE;\r
217 portCHAR cChar;\r
218 \r
219         if( USART_GetITStatus( USART1, USART_IT_TXE ) == SET )\r
220         {\r
221                 /* The interrupt was caused by the THR becoming empty.  Are there any\r
222                 more characters to transmit? */\r
223                 if( xQueueReceiveFromISR( xCharsForTx, &cChar, &xHigherPriorityTaskWoken ) == pdTRUE )\r
224                 {\r
225                         /* A character was retrieved from the queue so can be sent to the\r
226                         THR now. */\r
227                         USART_SendData( USART1, cChar );\r
228                 }\r
229                 else\r
230                 {\r
231                         USART_ITConfig( USART1, USART_IT_TXE, DISABLE );                \r
232                 }               \r
233         }\r
234         \r
235         if( USART_GetITStatus( USART1, USART_IT_RXNE ) == SET )\r
236         {\r
237                 cChar = USART_ReceiveData( USART1 );\r
238                 xQueueSendFromISR( xRxedChars, &cChar, &xHigherPriorityTaskWoken );\r
239         }       \r
240         \r
241         portEND_SWITCHING_ISR( xHigherPriorityTaskWoken );\r
242 }\r
243 \r
244 \r
245 \r
246 \r
247 \r
248         \r