본문 바로가기
하만 세미콘 아카데미/Embedded (STM32)

[Embedded] STM32 - UART

by smileww 2024. 5. 31.

이번 프로젝트는 UART 인터럽트를 활용한 통신 시스템을 구현하여 UART를 통해 데이터를 송수신하면서 사용자의 입력을 실시간으로 받아 처리하는 방식으로 구현해보도록 하겠습니다.

 

UART(Universal Asynchronous Receiver/Transmitter)는 마이크로컨트롤러, 컴퓨터, 통신 장비 등에서 널리 사용되는 직렬 통신 인터페이스입니다. UART는 데이터를 직렬 형태로 전송하기 때문에, 단 두 개의 전선(송신선 TX와 수신선 RX)만으로 두 기기 간의 통신을 가능하게 합니다. 이는 데이터를 한 비트씩 순차적으로 보내고 받는 방식입니다.

 

 

 

USART2를 사용할거고 global interrupt를 체크해줍니다.

 

USART2 글로벌 인터럽트 설정은 USART2 통신과 관련된 여러 이벤트에 대한 인터럽트 요청(IRQ)을 처리할 수 있도록 마이크로컨트롤러에 알리는 역할을 합니다. 이 설정을 통해 USART2에서 발생하는 특정 이벤트들이 마이크로컨트롤러의 중앙 처리 단계에 자동으로 전달됩니다. 글로벌 인터럽트가 활성화되면, USART2로부터 데이터 수신, 데이터 전송 완료, 오류 발생 등의 이벤트가 마이크로컨트롤러에 의해 인식되고 적절한 처리 함수로 이어집니다.

 

주요 역할:

  • 데이터 수신 완료 인터럽트: USART2로 데이터가 성공적으로 수신되었을 때 인터럽트를 발생시키며, 이를 통해 데이터를 즉시 처리할 수 있습니다.
  • 데이터 전송 완료 인터럽트: 데이터가 전송 버퍼에서 모두 전송되었을 때 인터럽트를 발생시켜 다음 데이터를 전송 준비하거나 다른 작업을 실행할 수 있습니다.
  • 에러 인터럽트: 프레임 에러, 버퍼 오버런, 패리티 에러 등과 같은 통신 오류가 발생했을 때 인터럽트를 통해 에러를 신속히 감지하고 처리할 수 있습니다.

 

 

/* Private user code ---------------------------------------------------------*/
/* USER CODE BEGIN 0 */
char buf[500];
char dum;
int idx1=0;
int cmdOk = 1;
void HAL_UART_RxCpltCallback(UART_HandleTypeDef *huart)
{
	HAL_UART_Transmit(&huart2, &dum, 1, 10);
	if(dum == '\r')
	{
		HAL_UART_Transmit(&huart2, "\n", 1, 10);
		cmdOk = 1;
	}
	else cmdOk = 0;
	buf[idx1++] = dum;
	buf[idx1] = 0; // NULL
	HAL_UART_Receive_IT(&huart2, &dum, 1);
}

/* USER CODE END 0 */

 

 

  • buf[500]: 사용자로부터 입력 받은 문자들을 저장하는 버퍼입니다.
  • dum: UART로부터 받은 단일 문자를 임시 저장하는 변수입니다.
  • idx1: 현재 버퍼에 저장된 문자의 인덱스를 추적합니다.
  • cmdOk: 커맨드의 완료 상태를 나타내며, 새로운 줄이 시작될 때 리셋됩니다.

 

 

HAL_UART_RxCpltCallback: UART에서 문자가 수신될 때마다 호출됩니다.

  • 수신된 문자를 dum 변수를 통해 받고, UART를 통해 즉시 에코(반사)합니다.
  • 만약 수신된 문자가 개행 문자('\r')라면, 새로운 줄로 이동하고 (HAL_UART_Transmit을 통해 "\n" 전송), cmdOk 플래그를 1로 설정합니다.
  • 수신된 문자를 buf 배열에 추가하고, idx1 인덱스를 증가시킵니다.
  • HAL_UART_Receive_IT 함수를 호출하여 다음 문자 수신을 위한 인터럽트를 다시 설정합니다.
int main(void)
{
  /* USER CODE BEGIN 1 */

  /* USER CODE END 1 */

  /* MCU Configuration--------------------------------------------------------*/

  /* Reset of all peripherals, Initializes the Flash interface and the Systick. */
  HAL_Init();

  /* USER CODE BEGIN Init */

  /* USER CODE END Init */

  /* Configure the system clock */
  SystemClock_Config();

  /* USER CODE BEGIN SysInit */

  /* USER CODE END SysInit */

  /* Initialize all configured peripherals */
  MX_GPIO_Init();
  MX_USART2_UART_Init();
  /* USER CODE BEGIN 2 */

  ProgramStart("UART Rx-Interrupt"); Cursor(1);
  HAL_UART_Receive_IT(&huart2, &dum, 1);  // one time interrupt
  /* USER CODE END 2 */

  /* Infinite loop */
  /* USER CODE BEGIN WHILE */
  while (1)
  {
    /* USER CODE END WHILE */

    /* USER CODE BEGIN 3 */
	  if(cmdOk > 0)
	  {
		  printf("%s\r\n>\033[A\n", buf); idx1 = 0; cmdOk = 0;
	  }
	  HAL_Delay(10);
  }
  /* USER CODE END 3 */
}

 

 

GPIO, USART2 UART를 초기화하고, HAL_UART_Receive_IT을 호출하여 UART 수신 인터럽트를 활성화합니다.

 

 

cmdOk 플래그를 검사하여 1인 경우(즉, 사용자가 입력을 완료했을 경우), 버퍼의 내용을 출력하고 프롬프트를 표시합니다. idx1을 0으로 리셋하고, cmdOk 플래그를 0으로 설정하여 다음 명령을 준비합니다. HAL_Delay(10)을 호출하여 다음 루프까지 약간의 지연을 줍니다.

 

 

이 프로그램은 비동기적으로 문자를 수신하고 처리하여, 실시간으로 사용자의 입력을 받고 반응할 수 있습니다.

수신된 각 문자는 즉시 처리되며, 명령어 라인 인터페이스와 유사한 환경을 제공합니다.

 

 

 

 

 

'하만 세미콘 아카데미 > Embedded (STM32)' 카테고리의 다른 글

[Embedded] STM32 - UART DMA  (0) 2024.05.31
[Embedded] STM32 - UART Bluetooth  (0) 2024.05.31
[Embedded] STM32 ADC - Interrupt  (0) 2024.05.31
[Embedded] STM32 ADC - DMA  (0) 2024.05.31
[Embedded] STM32 - ADC - 1  (0) 2024.05.31