In the previous guide (here), we took a look how to configure the UART to transmit single character. In this guide, we shall use UART to receive a character and echo the received character.
In this guide, we shall cover the following:
- Configure the pin to work in UART mode.
- Configure the UART in receiver mode.
- Receive a character.
- Code.
- Demo.
1. Configure the pin to work in UART mode:
From the previous guide, we concluded that PA2 is for TX and PA3 is for RX. Hence, we shall configure PA3.
For the pin to work in UART RX mode, we need to configure it as input floating as following:
/*Set mode to be input*/ GPIOA->CRL &=~(GPIO_CRL_MODE3); GPIOA->CRL|=GPIO_CRL_CNF3_0; GPIOA->CRL&=~GPIO_CRL_CNF3_1;
Thats all for the GPIO configuration.
2. Configure UART in Receiver mode:
In order to configure the UART to work in receiver mode, we need to enable the receiver bit in CR1 (Control Register 1):
//Enable receiver USART2->CR1 |= USART_CR1_RE;
3. Receive a character:
In order to receive a character, we need to wait for the character to arrive by checking the status register and the bit Read data register not empty and then read the data register:
char uart2_read(void) { /*Make sure the receive data register is not empty*/ while(!(USART2->SR & USART_SR_RXNE)){} /*Read data*/ return USART2->DR; }
4. Code:
The entire code for both Tx and Rx as follows:
#include "stm32f1xx.h" #define Perpher_CLK 8000000 #define Baudrate 115200 static uint16_t compute_uart_bd(uint32_t PeriphClk, uint32_t BaudRate) { return ((PeriphClk + (BaudRate/2U))/BaudRate); } static void uart_set_baudrate(USART_TypeDef *USARTx, uint32_t PeriphClk, uint32_t BaudRate) { USARTx->BRR = compute_uart_bd(PeriphClk,BaudRate); } void uart2_write(int ch) { /*Make sure the transmit data register is empty*/ while(!(USART2->SR & USART_SR_TXE)){} /*Write to transmit data register*/ USART2->DR = (ch & 0xFF); } char uart2_read(void) { /*Make sure the receive data register is not empty*/ while(!(USART2->SR & USART_SR_RXNE)){} /*Read data*/ return USART2->DR; } int main(void) { /*UART2 Pin configures*/ //enable clock access to GPIOA RCC->APB2ENR|=RCC_APB2ENR_IOPAEN; //Enable clock access to alternate function RCC->APB2ENR|=RCC_APB2ENR_AFIOEN; /*Confgiure PA2 as output maximum speed to 50MHz * and alternate output push-pull mode*/ GPIOA->CRL|=GPIO_CRL_MODE2; GPIOA->CRL|=GPIO_CRL_CNF2_1; GPIOA->CRL&=~GPIO_CRL_CNF2_0; /*Configure PA3 as Input floating*/ /*Set mode to be input*/ GPIOA->CRL &=~(GPIO_CRL_MODE3); GPIOA->CRL|=GPIO_CRL_CNF3_0; GPIOA->CRL&=~GPIO_CRL_CNF3_1; /*Don't remap the pins*/ AFIO->MAPR&=~AFIO_MAPR_USART2_REMAP; /*USART2 configuration*/ //enable clock access to USART2 RCC->APB1ENR|=RCC_APB1ENR_USART2EN; //Transmit Enable USART2->CR1 |= USART_CR1_TE; //Enable receiver USART2->CR1 |= USART_CR1_RE; /*Set baudrate */ uart_set_baudrate(USART2,Perpher_CLK,Baudrate); //Enable UART USART2->CR1 |= USART_CR1_UE; while(1) { char c; c=uart2_read(); uart2_write(c); uart2_write('\r'); uart2_write('\n'); } }
5. Results:
Open you favourite serial terminal and set the buadrate to be 115200 and send any character and you should receive the same sent character:
Happy coding 🙂
6 Comments
CAN U PLEASE PROVIDE HEADER FILE stm32f1xx.h. IT WOULD BE HELPFUL.
Hi,
please check this topic:
https://blog.embeddedexpert.io/?p=1332
Can i use that .h file for https://blog.embeddedexpert.io/?p=356 for this example
you can’t since the two MCU are totally different.
Can I get the Header .h files for STM32F4 series?
check this:
https://blog.embeddedexpert.io/?p=1255
Add Comment