

Qt 프로젝트가 끝나고 본격적인 임베디드 시스템 과정이 시작되었다.

라즈베리파이4 키트랑 STM32 보드를 받았다.
오늘은 임베디드 시스템의 이해와 기초 개념에 관해 다루어 볼 예정이다.
보드 발전 흐름
Embedded 보드 → Micro Controller Unit (MCU, 32bit) → System on Chip (SoC, 64bit)
MCU는 32비트 기반의 단일 칩 제어기, SoC는 여러 기능을 하나의 칩에 통합한 고성능 칩
프로세서 아키텍처 종류와 용도
x86 / i386, x86-64 / i586
주로 PC용 아키텍처
네트워크 장비 등 일부 임베디드 기기에서도 사용됨
ARM
소비자 시장 모바일 디바이스(스마트폰), 가전제품(냉장고 등)에 많이 채택됨
국내보다는 중국 등 해외 시장에서 우세
PPC (PowerPC)
PC용으로 사용되기도 하지만, 주로 임베디드 시장(네트워크, 항공우주, 방위산업, 산업용, 의료, 게임)에 집중
미국과 유럽에서 많이 채택
MIPS
PC → 네트워크 → 휴대폰 등 다양한 임베디드 분야로 확장
TriCore
자동차용을 타깃으로 개발되었으나 ARM 아키텍처에 점차 밀리는 추세
SoC와 MCU 구성 요소
SoC는 MCU를 포함한 전체 시스템이 하나의 칩에 집적된 형태
MCU (ARM 계열) 예시
32bit: STM32F401RE (Nucleo 보드)
64bit: BCM7112 (Raspberry Pi 4b+)
주요 구성
Core: 프로세서 코어(명령어 처리)
ROM: 프로그램 저장용 비휘발성 메모리
RAM: 데이터 임시 저장용 메모리
Devices/Peripherals: 주변 장치(타이머, ADC, UART 등)
임베디드 시스템 정의
특수한 기능을 수행하도록 설계된 컴퓨터 시스템 (Dedicated function)
일반적인 PC와는 달리, 내장된 하드웨어와 소프트웨어가 결합되어 한 가지 특정 목적만을 수행
대형 기계나 전자 장치의 일부로서 탑재되며, 시스템 전체의 핵심 기능을 담당하기도 함
임베디드란?
임베디드(embedded)는 더 큰 시스템의 일부로 내장되는 것
한 기기 안에 여러 개의 임베디드 시스템이 존재할 수 있음
PC(general-purpose computer)는 여러 프로그램 설치가 가능하지만, 임베디드 시스템은 정해진 역할만 수행
임베디드 시스템의 특징
특정 기능에 맞춰 하드웨어와 소프트웨어가 최적화되어 있음
하드웨어 변경이 어렵고, 자원의 제약(메모리/연산능력/전력 등)이 적용
전력소비가 적고, 고신뢰성/실시간성이 요구됨
다양한 응용 분야: 휴대폰, 자동차, 우주항공, 자동화, 게임기, 디지털 가전, 네트워크 장비 등
입력(센서 등) → 프로세서(처리) ↔ 메모리 → 출력(모터, 화면 등) 구조를 가짐.
임베디드 시스템의 발전
과거: 간단한 산업용/가정용 컨트롤러 중심
현재: 군사, 디지털 가전, 자동 센서 시스템 등 첨단 분야까지 확장
미래: 엣지 디바이스 → 엣지 노드 → 클라우드로 진화
임베디드 시스템 개발 프로세스 예
[요구분석] → [설계] → [HW/SW 개발] → [통합 테스팅] → [평가 인수] → [유지보수] → [생산 판매]
├ 인터페이스
└ 응용SW
임베디드 시스템 설계 및 구현 과정
System Goal
↓
┌─────────┴─────────┐
│ │
Hardware Software
├ Peripherals ├ Program Memory (SoC)
└ ... ├ Data Memory
└ I/O Interface
임베디드 시스템 하드웨어 구성
Memory(ROM/RAM)
↓↑
입력(센서/키보드/네트워크) → [Processor] → 출력(LED/LCD/네트워크)
마이크로 컴퓨터, CPU 및 연산 유닛
인텔 칩셋(4004, 8008, 8086 등)처럼 연산, 제어를 담당하는 장치로 발전
ALU(정수 연산), FPU(부동소수점 연산), SIMD(동시 다중 데이터 연산) 등으로 분화
FPU/SIMD/GPU 등은 멀티미디어, 신호 처리, 병렬 연산에 필수적
CPU Operating Mode
USR (User Mode) : 일반 애플리케이션이 실행되는 모드
SVC (Supervisor Mode) : 커널 모드 또는 운영체제 모드로, 하드웨어와 직접 상호작용하며 시스템 자원 관리 수행
HYP (Hypervisor Mode) : 고차원 가상화 계층 모드로, 여러 운영체제를 동시에 실행시키는 가상 머신 관리 기능 수행
Ring, Kernel : 권한 수준을 나타내며, Ring 0은 커널(최고 권한), 사용자 영역은 Ring 3 등으로 구분
SMP와 AMP 멀티코어 구조
SMP (Symmetric Multi-Processing)
모든 코어가 동일한 OS를 공유하며 대칭적으로 작업 수행
[Core 1][Core 2]...[Core N]
↓
단일 OS (Nucleus SMP)
↓
Thread 1...Thread M
예: Multicore Processor (Core 1..N) → Nucleus SMP → Middleware → Application Thread (1..M)
AMP (Asymmetric Multi-Processing)
각 코어가 독립적으로 OS를 실행하며 특정 역할 분담
[Core 1] [Core 2] [Core N]
↓ ↓ ↓
Android Linux Nucleus
↓ ↓ ↓
App 1 App 2 App 3
(UI) (제어)
예: Multicore Processor (Core 1..N)
Core1: Android + Middleware + App1(UI)
Core2: Linux + Nucleus RTOS + App2(Control)
코어별로 Windows, RTOS 등을 나눠 UI와 제어 처리 가능
FPU와 SIMD
ALU (Arithmetic Logic Unit) : 정수 연산 전담
FPU (Floating Point Unit) : 실수 연산 전담, 고비용 자원
SIMD (Single Instruction Multiple Data) : 여러 데이터를 동시에 처리하는 병렬 처리 방식
GPU 연산에 사용, 복소수 연산 시 실수부와 허수부 각기 계산
예: coordinate(x, y, z), color(r, g, b, a) 등의 벡터 데이터 처리에 적합
VFPU (Vector Floating Point Unit) : ARM 코어의 벡터 실수 연산 가속기
SIMD programming
ARM 메인 프로세서는 CP1부터 CP15까지 여러 코프로세서(Coprocessor)를 가짐
코프로세서(Coprocessor)
프로세서 핵심 연산 이외에 특수 연산(예: 부동소수점, 벡터 연산)을 담당하는 하드웨어 모듈
SIMD 확장 명령어 집합을 이용하여 벡터 연산 효율 극대화
GPU Computing
연산 집약적인 작업(그래픽, 과학 계산 등)을 GPU로 분산 처리
나머지 제어 및 일반 연산은 CPU가 담당하는 가속 컴퓨팅 방식
NAND Memory
비휘발성 저장용 메모리로, 임베디드 시스템의 데이터 저장에 광범위하게 사용됨
임베디드 시스템 소프트웨어 구성
하드웨어: 프로세서, 메모리, 입출력(I/O) 장치
소프트웨어: OS(리눅스, RTOS 등), 하이퍼바이저, VM, 애플리케이션 등으로 구성
개발 환경: Host(개발 PC), Target(임베디드 보드), Toolchain(컴파일러 등 툴), IDE, 디버거 등 필요
실시간 시스템(Real-Time System)
정해진 시간 내 반드시 또는 가급적 작업을 완료해야 하는 결정적(deterministic) 시스템
정해진 시간에 작업 수행이 보장되는 것, 외부 이벤트를 일정한 시간 내에 처리해야 하는 시스템
작업 완료 기준 : 일정 시간 내에 작업 완료, 작업 시작 기준 : 일정 시간 내에 작업 시작
요구하는 시간 내 작업 완료 여부에 따라 경성(hard), 연성(soft) 실시간 시스템으로 구분
경성(hard) 실시간 시스템
시간 제약의 위반이 심각한 결과를 초래, 시간 제약은 반드시 지켜져야 함
(예: 무기 체계 시스템, 발전 제어 시스템)
연성(soft) 실시간 시스템
시간 제약의 위반이 QoS(서비스 품질)의 저하를 유발, 시간 제약은 가급적 지켜져야 함
(예: 오디오, 통신기기)
실시간 시스템을 구현하기 위해 필요한 요소
하드웨어 (HW)
빠르고 예측 가능한 반응 속도를 보장할 수 있는 프로세서 및 주변 장치
인터럽트 처리, 타이머 등 실시간 이벤트 관리 기능 포함
메모리 및 입출력 장치의 신뢰성과 속도 보장
운영체제 (OS)
실시간 운영체제 (RTOS)
우선순위 기반 스케줄링으로 태스크의 실행 시점을 엄격히 제어
대표 예: FreeRTOS, vxWorks, QNX, ThreadX 등
RTOS는 멀티태스킹, 동기화, 인터럽트 응답, 타이밍 제어 기능이 뛰어남
커널이 경량화되어 예측 가능한 시간 내에 태스크 전환과 인터럽트 처리를 수행
애플리케이션 (App)
실시간 요구 사항에 맞춰 설계 및 구현
타이밍 제약을 준수하는 이벤트 처리, 응답 속도 개선
리소스 최소화 및 오류 처리 강화로 안정성 확보
실시간 운영체제 (RTOS)의 특징
우선순위 기반 스케줄링
가장 높은 우선순위 태스크가 CPU 사용권을 받음
선점형 스케줄링
우선순위가 높은 태스크가 언제든 실행 중인 태스크를 중단 가능
최소한의 지연 시간
태스크 응답 시간과 처리 지연을 극소화하여 실시간 동작 실현
동기화 및 통신 메커니즘
세마포어, 뮤텍스, 메시지 큐를 통해 태스크 간 안전한 데이터 공유 가능
실시간 타이머 및 이벤트 관리
정확한 시간 제어와 이벤트 기반 처리 지원
임베디드 리눅스 및 RTOS
GPL 라이선스 기반 리눅스 커널, 포팅 및 디바이스 드라이버 작성 필수
대표적 RTOS: FreeRTOS, vxWorks, QNX 등
CFS(Completely Fair Scheduler), RT(Real-Time), DEADLINE 기반 스케줄링
리눅스 운영체제 다운로드
PC용 Application 개발 환경 vs Embedded System 개발 환경
PC용 앱은 일반적으로 동일한 HW, OS 환경(Windows, Linux 등)에서 개발/실행함
임베디드 앱 개발은 다양한 아키텍처, 커스텀 보드 등 특수 환경에서 동작
런타임 환경(HW, OS, 부트로더, 메모리 등)에 대한 이해가 필수적
임베디드 소프트웨어 개발 환경의 구성 요소
호스트 시스템(Host System)
실제 개발을 진행하는 PC (윈도우 또는 리눅스)
코드를 작성하고, 컴파일·링크·디버깅 등 필요한 툴을 실행하는 환경
툴체인(Toolchain)
소스코드를 타겟용 실행파일로 만드는 소프트웨어 도구 집합 (C/C++ 컴파일러, 어셈블러, 링커 등)
예: GNU ARM Toolchain, Keil uVision, IAR Embedded Workbench 등
디버거(Debugger)
작성한 프로그램을 타겟 보드에서 분석/수정/테스트하는 도구 (JTAG, Trace32 등)
타겟 시스템(Target System)
실제 소프트웨어가 동작할 임베디드 하드웨어 보드
Toolchain을 사용한 임베디드 실행 파일 생성 과정
컴파일
.h(헤더), .c(소스) → 전처리·컴파일러 → .s(어셈블리)
헤더파일은 전처리 과정을 통해 소스에 포함됨
어셈블(Assemble)
.s → 어셈블러 → .o(오브젝트 파일)
링크(Link, Locate)
.o, .a(라이브러리) → 링커 → .out(리눅스), .exe(윈도우)
이미지 변환 및 다운로드
objcopy로 .out(ELF) → .bin(binary file)로 변환
bin2hex로 .bin → .hex(ROM writer가 인식 가능한 형태)
.hex 파일을 ROM writer로 플래시에 기록
CubeMX, Keil uVision 등 개발 툴
STM32CubeMX
MCU 보드 핀, 시스템 클럭 등 초기화 설정을 GUI로 설계해 코드(.c) 자동생성
Keil uVision
CubeMX가 자동생성한 프로젝트(코드)를 불러와 빌드/디버깅 및 프로젝트 관리 진행
USER 스위치를 누르면 LD2가 켜지게 된다.
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 */
/* USER CODE END 2 */
/* Infinite loop */
/* USER CODE BEGIN WHILE */
while (1)
{
// 스위치를 누르면 LED가 켜지는 코드
if (HAL_GPIO_ReadPin(GPIOC, GPIO_PIN_13) == 0)
{
HAL_GPIO_WritePin(GPIOA, GPIO_PIN_5, GPIO_PIN_SET); // LED ON
}
else
{
HAL_GPIO_WritePin(GPIOA, GPIO_PIN_5, GPIO_PIN_RESET); // LED OFF
}
HAL_Delay(100);
/* USER CODE END WHILE */
/* USER CODE BEGIN 3 */
}
/* USER CODE END 3 */
}
C랑 C++할 때는 아는 맛이었는데, 임베디드 기초로 넘어오니까 갑자기 전부 모르는 맛이 됐다.
개념 정리를 하긴 했으나 정말 기초적인 부분이라, 보드를 다루어 보면서 더 많이 배워야 할 것 같다.
이제부터는 STM32Cube로 프로젝트를 생성하고, Keil uVision에서 코드를 짜게 될 것..!
정말,,, 공부의 세계는 끝이 없구나,,,

라즈베리파이4 귀엽다 🍓