STM32 USART Interrupt - FabLabSeoul/WingProject GitHub Wiki
Stm32 Value line discovery ๋ณด๋ ์ ์ฉ ๊ธ์ ๋๋ค.
์๋ฆฌ์ผ ํต์ (USART)์ ์ธํฐ๋ฝํธ ๋ฐฉ์์ผ๋ก ์ฒ๋ฆฌํ๋ ๋ฐฉ๋ฒ์ ์ค๋ช ํ๋ค.
์์ ๋ STM32\stm32vldiscovery_package\Project\Examples\Serial_Interrupt ๊ฒฝ๋ก์ ์๋ค. ์์ ๋ PA10,9(Rx,Tx)๋ฅผ ์๋ฆฌ์ผํต์ ํฌํธ๋ก ์ค์ ํ๊ณ , ์ปดํจํฐ์ Serial port terminal ํ๋ก๊ทธ๋จ๊ณผ ํต์ ์ ์ฃผ๊ณ ๋ฐ๋๋ค. ์ด ์์ ๋ฅผ ์คํํด๋ณด๊ธฐ ์ํด์๋ Stm32vldiscovery ๋ณด๋์ serial to usb ๋ณด๋, ์๋ฆฌ์ผ ํฌํธ ํฐ๋ฏธ๋ ํ๋ก๊ทธ๋จ์ด ์์ด์ผ ํ๋ค. Stm32๋ณด๋์ ์๋ฆฌ์ผ ํฌํธ๋ฅผ serial to usb ๋ณด๋์ ์ฐ๊ฒฐํ๊ณ ํฐ๋ฏธ๋ ํ๋ก๊ทธ๋จ์ ์คํํ๋ฉด, ๋จผ์ Stm32๋ณด๋๋ก ๋ถํฐ ๋์ด์จ ์ ๋ณด๊ฐ ํ๋ฉด์ ํ์๋๋ค. ๊ทธ ํ ํฐ๋ฏธ๋ ํ๋ก๊ทธ๋จ์์ ์ ๋ณด๋ฅผ ์ก์ ํด์, ์ฝ 30๋ฌธ์๋ฅผ ๋์ด์๋ฉด Stm32๋ณด๋์์ ๋ฐ์ ๋ฌธ์์ด์ ๊ทธ๋๋ก ํฐ๋ฏธ๋์๊ฒ ์ ์กํ๋ค.
๋ณธ๋ก ์ผ๋ก ๋ค์ด๊ฐ๋ฉด, Stm32์์ ์๋ฆฌ์ผํต์ ์ ์ฒ๋ฆฌํ๋ ๋ฐฉ๋ฒ์ ํฌ๊ฒ Polling, Interrupt, DMA ๋ฐฉ์์ด ์๋ค. ์ด ๊ธ์์๋ Interrupt๋ฐฉ์์ ์ค๋ช ํ๋ค. ์ธํฐ๋ฝํธ ๋ฐฉ์์ ์๋ฆฌ์ผ๋ก ์ ๋ณด๋ฅผ ์ฃผ๊ณ ๋ฐ์ ๋๋ง๋ค ์ธํฐ๋ฝํธ๋ฅผ ๋ฐ์์์ผ ์ ๋ณด๋ฅผ ์ฃผ๊ฑฐ๋ ๋ฐ๊ฑฐ๋ ํ๋ ๋ฐฉ์์ ๋งํ๋ค. ์ต์ํด์ง๋ฉด ๋ค๋ฅธ ๋ฐฉ์๋ณด๋ค ํธํ๋ค๋ ๊ฒ์ ์ ์ ์๋ค. ์ธํฐ๋ฝํธ๋ ๊ฐ๋จํ ๋งํ๋ฉด, ํจ์๊ฐ ํธ์ถ๋๋ค๊ณ ์๊ฐํ๋ฉด ๋๋ค.
์๋ฆฌ์ผ ํฌํธ๋ฅผ ์ค์ ํ๋ ๊ฒ์ ๊ธฐ์กด ๋ฐฉ์๊ณผ ๋๊ฐ๋ค. ์์ธํ ๋ด์ฉ์ Stm32 UART ๋ฌธ์๋ฅผ ์ฐธ์กฐํ์. ๋ค๋ฅธ ์ ์ ์ธํฐ๋ฝํธ๋ฅผ ์ค์ ํด์ค์ผ ํ๋ ๋ถ๋ถ์ด๋ค. Stm32์์ ์ธํฐ๋ฝํธ๋ฅผ ๊ด์ฅํ๋ ํํธ๋ฅผ NVIC๋ผ๊ณ ํ๋ค. Nested Vectored Interrupt Controller์ ์ฝ์๋ค. 60๊ฐ์ ์ธํฐ๋ฝํธ ํ ์ด๋ธ์ด ์๊ณ , ๊ทธ ์ค์ USART ์ธํฐ๋ฝํธ๊ฐ ์๋ค. ์ด ํ๋๊ทธ๋ฅผ ํ์ฑํ ์ํค๋ฉด, USART์ ๊ด๋ จ๋ ์ธํฐ๋ฝํธ๋ฅผ ๋ฐ์ ์ ์๋ค. ์ฝ๋๋ ๊ฐ๋จํ๋ค.
/**
* @brief Configures the nested vectored interrupt controller.
* @param None
* @retval None
*/
void NVIC_Configuration(void)
{
NVIC_InitTypeDef NVIC_InitStructure;
/* Enable the USART1 Interrupt */
NVIC_InitStructure.NVIC_IRQChannel = USART1_IRQn;
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;
NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0;
NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
NVIC_Init(&NVIC_InitStructure);
}
Stm32์์๋ USART1_IRQn, USART2_IRQn, USART3_IRQn์ ์ธํฐ๋ฝํธ๋ฅผ ์ค์ ํ ์ ์๋ค. ์ธํฐ๋ฝํธ๋ ์ฐ์ ์์์ ๋ฐ๋ผ ๋ฌด์์ ๋จผ์ ํธ์ถ ํ ์ง๋ฅผ ๊ฒฐ์ ํ ์ ์๋ค. ์ผ๋ฐ์ ์ผ๋ก NVIC_IRQChannelPreemptionPriority ์๋ ๊ฐ์ ๋ถ๋ฅ๋ผ๋ฆฌ ๊ฐ์ ๊ฐ์ผ๋ก ์ค์ ํ๊ณ , NVIC_IRQChannelSubPriority ์์ ์ฐ์ ์์๋ฅผ ์ ํ๊ฒ ๋๋ค. ์์ ๊ฐ ์ผ์๋ก ๋จผ์ ํธ์ถ๋๋ค.
์ฐ์ ์์์ ๊ด๋ จ๋ ์์ธํ ๋ด์ฉ์ ์ด ๊ธ์ ์ฐธ์กฐํ์.
๊ทธ๋ฆฌ๊ณ , ์๋ฆฌ์ผ์ ๋ณด๋ผ ๋์ ๋ฐ์ ๋ ๊ฐ๊ฐ ๋ฐ๋ก ์ธํฐ๋ฝํธ๋ฅผ ๋ฐ์ ์ ์๋ค. ์ฝ๋๋ ๋ค์๊ณผ ๊ฐ๋ค.
/* Enable USART1 Receive and Transmit interrupts */
USART_ITConfig(USART1, USART_IT_RXNE, ENABLE);
USART_ITConfig(USART1, USART_IT_TXE, ENABLE);
###์ธํฐ๋ฝํธ
USART1 ์ธํฐ๋ฝํธ๊ฐ ๋ฐ์๋๋ฉด, void USART1_IRQHandler(void)
ํจ์๊ฐ ํธ์ถ๋๋ค. USART2 ์ธํฐ๋ฝํธ๊ฐ ๋ฐ์๋๋ฉด void USART2_IRQHandler(void)
ํจ์๊ฐ ํธ์ถ๋๋ค. USART3 ๋ ๋ง์ฐฌ๊ฐ์ง๋ค. ๊ฐ๋ฐ์๋ ์ด ํจ์๋ฅผ ๊ทธ๋๋ก ๊ตฌํํ๋ฉด ๋๋ค. ๊ฐํน stm32f10x_it.c ํ์ผ์ ์ด๋ฏธ ํจ์๊ฐ ๊ตฌํ๋ ๊ฒฝ์ฐ๊ฐ ์๋๋ฐ, ์ปดํ์ผ ์ค๋ฅ๋ฅผ ํผํ๋ ค๋ฉด, ๊ธฐ์กด ์ธํฐ๋ฝํธ ํจ์๋ ์ง์ฐ๊ณ , ์๋ก ๊ตฌํํ๋ฉด ๋๋ค.
์ธํฐ๋ฝํธ๋ USART_ITConfig()
ํจ์๋ฅผ ํธ์ถํด์ ์ธํฐ๋ฝํธ๋ฅผ ํ์ฑํํ๋ ์๊ฐ๋ถํฐ, Transmitter ์ธํฐ๋ฝํธ๋ ๋ฐ๋ก ํธ์ถ๋๋ค. ๋์ด์ ์ ๋ณด๋ฅผ ๋ณด๋ผ๊ฒ ์๋ค๋ฉด, USART_IT_TXE ์ธํฐ๋ฝํธ๋ ๋๋๊ฒ ์ข๋ค. ๋ฐ๋๋ก Receiver ์ธํฐ๋ฝํธ๋ ์ ๋ณด๋ฅผ ๋ฐ์ ๋๋ง ํธ์ถ๋๋ค. ๊ทธ๋ฌ๋ ํฐ ๋ฌธ์ ๊ฐ ์๋ค๋ฉด, USART_IT_RXNE ์ธํฐ๋ฝํธ๋ ๊ณ์ ์ผ๋๋๊ฒ ์ข๋ค.
/**
* @brief This function handles USARTy global interrupt request.
* @param None
* @retval None
*/
void USART1_IRQHandler(void)
{
// ์๋ฆฌ์ผ๋ก ๋ถํฐ ๋ฐ์ ์ ๋ณด๋ฅผ ๊ณ์ ์ ์ฅํ๋ค.
if(USART_GetITStatus(USART1, USART_IT_RXNE) != RESET)
{
/* Read one byte from the receive data register */
RxBuffer[RxCounter++] = USART_ReceiveData(USART1);
if(RxCounter == NbrOfDataToRead)
{
// NbrOfDataToRead ๋งํผ ์ ๋ณด๋ฅผ ๋ฐ์๋ค๋ฉด, ๊ทธ๋๋ก ์ ์กํ๋ค.
SendSerial(RxBuffer, RxCounter);
RxCounter = 0;
}
}
// ์๋ฆฌ์ผ๋ก ๋ฐ์ดํ๋ฅผ ๋ชจ๋ ๋ณด๋ด๋ฉด, ์ธํฐ๋ฝํธ๋ฅผ ๋๋ค.
if(USART_GetITStatus(USART1, USART_IT_TXE) != RESET)
{
/* Write one byte to the transmit data register */
USART_SendData(USART1, TxBuffer[TxCounter++]);
if(TxCounter == NbrOfDataToTransfer)
{
/* Disable the USART1 Transmit interrupt */
USART_ITConfig(USART1, USART_IT_TXE, DISABLE);
}
}
}
void SendSerial(uint8_t buffer[], uint8_t size)
{
int i=0;
TxCounter = 0;
NbrOfDataToTransfer = size;
for (i=0; i < size; ++i)
{
TxBuffer[ i] = buffer[ i];
}
USART_ITConfig(USART1, USART_IT_TXE, ENABLE);
}
USART_GetITStatus(USART1, USART_IT_RXNE)
ํจ์๋ฅผ ์ด์ฉํด ์๋ฆฌ์ผํต์ ์ ํตํด ์ ๋ณด๋ฅผ ๋ฐ์๋์ง ํ๋จ ํ ์ ์๋ค. ์ฝ๋์์๋ ์ ๋ณด๋ฅผ ๋ฐ์ ๋๋ง๋ค ๋ฒํผ์ ์ ์ฅํ๋ ๊ฒ์ ๋ณผ ์ ์๋ค.
USART_GetITStatus(USART1, USART_IT_TXE)
ํจ์๋ USART_ITConfig(USART1, USART_IT_TXE, ENABLE)
ํธ์ถ ๋์๋ค๋ฉด ํญ์ TRUE๋ฅผ ๋ฐํํ๊ธฐ ๋๋ฌธ์, ์ ๋ณด๋ฅผ ๋ชจ๋ ์ก์ ํ๋ฉด ์ธํฐ๋ฝํธ๋ฅผ ๋๋๊ฒ ์ข๋ค.
main()
ํจ์๋ ๋ค์๊ณผ ๊ฐ๋ค.
int main()
{
/* System Clocks Configuration */
RCC_Configuration();
/* NVIC configuration */
NVIC_Configuration();
/* Configure the GPIO ports */
GPIO_Configuration();
// USART1 ์ด๊ธฐํ
USART_InitStructure.USART_BaudRate = 9600;
USART_InitStructure.USART_WordLength = USART_WordLength_8b;
USART_InitStructure.USART_StopBits = USART_StopBits_1;
USART_InitStructure.USART_Parity = USART_Parity_No;
USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;
USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx;
USART_Init(USART1, &USART_InitStructure);
/* Enable USART1 Receive and Transmit interrupts */
USART_ITConfig(USART1, USART_IT_RXNE, ENABLE);
USART_ITConfig(USART1, USART_IT_TXE, ENABLE);
// Enable USART1
USART_Cmd(USART1, ENABLE);
while (1)
{
}
}
============================= ###๋ ํผ๋ฐ์ค
- ์์ STM32\STM32F10x_StdPeriph_Lib_V3.3.0\Project\STM32F10x_StdPeriph_Examples\USART\Interrupt
- http://poohyhoh.blogspot.kr/2010/08/arm-cortex-m3-stm32-nvic-priority-group.html