본문 바로가기
# Semiconductor/- Semicon Academy

[Harman 세미콘 아카데미] 30일차 - STM32(LED_Extern, Switch_Extern, UART)

by Graffitio 2023. 7. 28.
[Harman 세미콘 아카데미] 30일차 - STM32(LED_Extern, Switch_Extern, UART)
728x90
반응형
[LED_Extern]

 

LD1 : 통신에 관련된 LED

LD3 : 전원이 연결되면 해당 LED On(Red)

 

Extern LED setting
D8 은 PA9 Pin에 연결되어 있다.
GPIO_Output으로 Pin 할당
Code genetation
헤더파일에 define 된 것을 확인할 수 있다.
main.c 에 Extern LED code 작성
Build & Debug

 

 

[Switch_Extern]

 

신호 1 줬을 때, 동작하도록 하기 위해서 Pull-Down 저항 사용함

 

  while (1)
  {
    /* USER CODE END WHILE */

    /* USER CODE BEGIN 3 */
  int i = HAL_GPIO_ReadPin(B1_GPIO_Port, B1_Pin);
  int j = HAL_GPIO_ReadPin(Switch_Extern_GPIO_Port, Switch_Extern_Pin);
 	  if((i == 0) || (j == 1))
  	  {
  		  // Extern LED Green
  		  HAL_GPIO_WritePin(LED_Extern_Green_GPIO_Port, LED_Extern_Green_Pin, 1);
  		  HAL_Delay(200);
  		  HAL_GPIO_WritePin(LED_Extern_Green_GPIO_Port, LED_Extern_Green_Pin, 0);
  		  HAL_Delay(200);
  	  }
  }
  /* USER CODE END 3 */

 

 

[STM32 Mission #1]

 

Mission #1

 

① Red, Green, Yellow 세 가지 LED를 이용하여 회로를 구성하라.

② Sw1 ~Sw3의 3 개의 Sw 회로를 구성하라.

③ 각 LED 회로와 Sw 회로를 STM32 보드의 Pin에 Assign하고 각 스위치를 누를 때마다 

    각각의 LED가 200ms 간격으로 점멸되도록 프로그램 구성하여라.

 

LED에는 220Ω, Switch에는 1㏀ 사용

 while (1)
  {
    /* USER CODE END WHILE */

    /* USER CODE BEGIN 3 */
  int i = HAL_GPIO_ReadPin(Switch_Extern_1_GPIO_Port, Switch_Extern_1_Pin);
  int j = HAL_GPIO_ReadPin(Switch_Extern_2_GPIO_Port, Switch_Extern_2_Pin);
  int k = HAL_GPIO_ReadPin(Switch_Extern_3_GPIO_Port, Switch_Extern_3_Pin);
 	  if(i == 1)
  	  {
  		  // Extern LED Green & Switch_1
  		  HAL_GPIO_WritePin(LED_Extern_Green_GPIO_Port, LED_Extern_Green_Pin, 1);
  		  HAL_Delay(200);
  		  HAL_GPIO_WritePin(LED_Extern_Green_GPIO_Port, LED_Extern_Green_Pin, 0);
  		  HAL_Delay(200);
  	  }
 	  if(j == 1)
  	  {
  		  // Extern LED Green & Switch_1
  		  HAL_GPIO_WritePin(LED_Extern_Red_GPIO_Port, LED_Extern_Red_Pin, 1);
  		  HAL_Delay(200);
  		  HAL_GPIO_WritePin(LED_Extern_Red_GPIO_Port, LED_Extern_Red_Pin, 0);
  		  HAL_Delay(200);
  	  }
 	  if(k == 1)
  	  {
  		  // Extern LED Green & Switch_1
  		  HAL_GPIO_WritePin(LED_Extern_Yellow_GPIO_Port, LED_Extern_Yellow_Pin, 1);
  		  HAL_Delay(200);
  		  HAL_GPIO_WritePin(LED_Extern_Yellow_GPIO_Port, LED_Extern_Yellow_Pin, 0);
  		  HAL_Delay(200);
  	  }
  }
  /* USER CODE END 3 */

 

 

[UART]

 

STM32 Board 에서는 총 2개의 UART Pin을 제공한다.

PA2, PA3 (시리얼 포트로 연결되어 있음)

 

UART Setting

Hardware Flow Control

ctsrtos 에 관한 건데, 지금은 안 쓸 거니까 Disable

 

Basic Parameter

UART 통신 시, 사용되는 기본 Parameter들을 볼 수 있다.

여담이지만, LAM의 속도를 얘기할 때, bps를 쓴다.

이때 bps는 byte / sec도 아니고, bit / sec는 좀 부족하고, Baud Rate로 알고 있으면 된다.

 

Terminal Program

 

Teraterm

: 시리얼 쪽에 좀 더 특화되어 있고

 

putty

: 보통 얘를 많이 쓴다.

 

PuTTY 다운로드 링크

https://www.chiark.greenend.org.uk/~sgtatham/putty/latest.html

 

Download PuTTY: latest release (0.78)

This page contains download links for the latest released version of PuTTY. Currently this is 0.78, released on 2022-10-29. When new releases come out, this page will update to contain the latest, so this is a good page to bookmark or link to. Alternativel

www.chiark.greenend.org.uk

 

PuTTY 실행

 

 while (1)
  {
    /* USER CODE END WHILE */

    /* USER CODE BEGIN 3 */
	HAL_UART_Transmit(&huart2, "Hello Harman!", 13, 100); // Serial funcrion, Transmit
	HAL_Delay(1000);
  }
  /* USER CODE END 3 */

원래는 문자열의 크기를 세서 써야 되는데, 그냥 적당히 13을 쓰자.

13, 100 : 각각의 문자열의 크기(Byte 수) , Time out(100ms 동안만 통신을 기다려라)

Timeout을 안 해주면, 오매불망 통신만 기다리기 때문에 blocking 에 걸려서 다른 기능을 쓸 수 없다.

 

Serial로 setting

 

처음에는 까만 화면만 출력된다.
Board에서 Reset 눌러주면, 문자열이 출력됨.

 

Button을 활용한 UART

 

버튼을 누르면, UART를 통해 PuTTY로 문자열 출력

눌렀을 때, 한 번만 출력되고

계속 누르고 있어도 한 번만 출력되도록 코딩하여라.

 

 /* Infinite loop */
  /* USER CODE BEGIN WHILE */
  int j = 0;
  while (1)
  {
    /* USER CODE END WHILE */

    /* USER CODE BEGIN 3 */
	int i = HAL_GPIO_ReadPin(B1_GPIO_Port, B1_Pin);
	if (i == 0 && j == 0)
	{
		HAL_UART_Transmit(&huart2, "Hello Harman!", 13, 100);
		HAL_Delay(1000);
		j++;
	}
	else if(i == 1)
	{
		i = 0;
		j = 0;
	}
  }
  /* USER CODE END 3 */
}

 

※ 이스케이프 시퀀스를 사용하여 좀 더 깔끔하게 출력해보자. 

단, \n, \r, \0 과 같은 이스케이프 시퀀스를 쓸 때는 문자열 크기가 그만큼 커진다는 것을 감안할 것.

ex) \n은 ASCII Code로 0a = LF(Line Feed) 이며 일정한 크기를 갖는다.

 

 

원래는 가상의 함수로 정의되어 있고, 사용 시 실체화를 해주면 된다.

char a = ch;

int 변수를 char에 넣으면, 앞에 불필요한 데이터는 다 날라가고 맨 마지막 byte만 남게 된다.

 

int j = 0;
  while (1)
  {
    /* USER CODE END WHILE */

    /* USER CODE BEGIN 3 */
	int i = HAL_GPIO_ReadPin(B1_GPIO_Port, B1_Pin);
	if (i == 0 && j == 0)
	{
//		HAL_UART_Transmit(&huart2, "Hello Harman!\r\n", 13, 100);
		printf("Hello Harman!\n");
		HAL_Delay(1000);
		j++;
	}
	else if(i == 1)
	{
		i = 0;
		j = 0;
	}
  }
  /* USER CODE END 3 */
}

int __io_putchar(int ch) // console 함수를 UART 기능 함수의 실체 구현
{
	char a = ch;
	HAL_UART_Transmit(&huart2, &a, 1, 100);
}

이렇게 했더니, 그냥 출력된 자리에서 줄바꿈만 함.

캐리지 리턴(\r)도 해줘야 한다.

int j = 0;
  while (1)
  {
    /* USER CODE END WHILE */

    /* USER CODE BEGIN 3 */
	int i = HAL_GPIO_ReadPin(B1_GPIO_Port, B1_Pin);
	if (i == 0 && j == 0)
	{
//		HAL_UART_Transmit(&huart2, "Hello Harman!\r\n", 13, 100);
		printf("Hello Harman!\r\n");
		HAL_Delay(1000);
		j++;
	}
	else if(i == 1)
	{
		i = 0;
		j = 0;
	}
  }
  /* USER CODE END 3 */
}

int __io_putchar(int ch) // console 함수를 UART 기능 함수의 실체 구현
{
	char a = ch;
	HAL_UART_Transmit(&huart2, &a, 1, 100);
}

깔끔하게 잘 정렬되어 출력된다.

 

몇 번 썼는지 카운트도 가능

int j = 0;
  int k = 0;
  while (1)
  {
    /* USER CODE END WHILE */

    /* USER CODE BEGIN 3 */
	int i = HAL_GPIO_ReadPin(B1_GPIO_Port, B1_Pin);
	if (i == 0 && j == 0)
	{
//		HAL_UART_Transmit(&huart2, "Hello Harman!\r\n", 13, 100);
		printf("Hello Harman!(%08x)\r\n", k);
		HAL_Delay(1000);
		j++;
		k++;
	}
	else if(i == 1)
	{
		i = 0;
		j = 0;
	}
  }
  /* USER CODE END 3 */
}

int __io_putchar(int ch) // console 함수를 UART 기능 함수의 실체 구현
{
	char a = ch;
	HAL_UART_Transmit(&huart2, &a, 1, 100);
}

 

728x90
반응형