펌웨어와 eMMC
- 펌웨어(Firmware): 하드웨어를 제어하기 위해 장치 내부에 저장되어 실행되는 저수준 소프트웨어
- eMMC(embedded MultiMediaCard): NAND Flash 와 Flash Controller 를 하나의 패키지로 묶은 임베디드 저장 장치
- 일반적인 임베디드 장치에서는 펌웨어가 eMMC 같은 비휘발성 저장 장치에 저장되어 있고, 전원이 켜지면 SoC 가 해당 저장 장치에서 부트로더, 커널, 루트 파일시스템 등을 읽어 실행한다.
- 즉, 펌웨어는 장치가 어떻게 동작할지 정의하는 소프트웨어이고, eMMC 는 그 펌웨어를 저장하는 물리적인 저장 매체라고 볼 수 있다.
- 공유기, 스마트폰, IoT 장비, 임베디드 리눅스 장비 같은 시스템에서는 펌웨어와 eMMC 구조를 이해하는 것이 리버싱, 포렌식, 취약점 분석에서 매우 중요하다.
펌웨어
펌웨어(Firmware)는 하드웨어와 운영체제 사이에서 장치의 동작을 제어하는 소프트웨어이다.
일반적인 소프트웨어는 운영체제 위에서 실행되지만, 펌웨어는 보통 장치 내부의 Flash, eMMC, SPI Flash 같은 비휘발성 저장 장치에 저장되고 장치가 부팅될 때 가장 먼저 실행된다.
펌웨어는 하드웨어 초기화, 부팅, 장치 제어, 운영체제 로딩, 설정 관리 같은 역할을 수행한다.
예를 들어 공유기 전원을 켜면 CPU 가 바로 리눅스 커널을 실행하는 것이 아니라, 먼저 Boot ROM 또는 부트로더가 실행되고 그 다음 커널과 루트 파일시스템이 올라간다.
이 과정에서 사용되는 부트로더, 커널, 파일시스템, 설정 데이터 등을 넓게 펌웨어라고 부를 수 있다.
펌웨어의 구성 요소
펌웨어는 단일 파일처럼 보일 수 있지만 내부적으로는 여러 구성 요소로 나뉘는 경우가 많다.
일반적인 임베디드 리눅스 펌웨어는 다음과 같은 구성 요소를 포함한다.
- Bootloader
- Kernel
- Device Tree
- Root Filesystem
- 설정 파일
- 애플리케이션 바이너리
- 드라이버 또는 커널 모듈
- 복구 이미지
- 업데이트 메타데이터
예를 들어 펌웨어 이미지 하나가 있다고 하면 내부 구조는 대략 다음과 같이 나타날 수 있다.
firmware.bin
- header
- bootloader
- kernel
- device tree blob
- rootfs
- config
- checksum
- signature
펌웨어 분석을 할 때는 이 파일이 단순한 바이너리인지, 여러 영역이 붙어있는 이미지인지, 압축된 파일시스템을 포함하는지 확인해야 한다.
Bootloader
Bootloader 는 운영체제 커널을 실행하기 전에 먼저 실행되는 프로그램이다.
장치에 전원이 들어오면 CPU 는 정해진 부트 경로에 따라 Boot ROM 을 실행하고, Boot ROM 은 eMMC, SPI Flash, NAND Flash 같은 저장 장치에서 다음 단계의 부트로더를 읽어온다.
Bootloader 는 보통 다음과 같은 역할을 수행한다.
- CPU 초기화
- DRAM 초기화
- 저장 장치 초기화
- 커널 이미지 로드
- Device Tree 로드
- 커널 부팅 인자 전달
- 복구 모드 진입
- 펌웨어 업데이트 처리
임베디드 리눅스 장비에서는 U-Boot 이 많이 사용된다.
U-Boot 은 커널을 메모리에 올리고, 커널에 필요한 부팅 인자를 전달한 뒤 커널 실행 주소로 점프한다.
대략적인 부팅 흐름은 다음과 같이 볼 수 있다.
Power On
-> Boot ROM
-> Bootloader
-> Kernel
-> Root Filesystem
-> Init Process
-> User Application
즉, Bootloader 는 하드웨어와 운영체제 사이에서 초기 실행 흐름을 이어주는 역할을 한다.
Kernel
Kernel 은 운영체제의 핵심 부분이다.
펌웨어 안에 포함된 커널은 CPU, 메모리, 파일시스템, 네트워크, 프로세스, 디바이스 드라이버 등을 관리한다.
임베디드 장비에서는 보통 Linux Kernel 이 사용되는 경우가 많다.
커널은 단독으로 동작하지 않고, 장치의 하드웨어 정보를 알아야 한다.
이때 Device Tree 가 함께 사용된다.
Device Tree
Device Tree 는 임베디드 시스템의 하드웨어 구성을 커널에게 알려주기 위한 데이터 구조이다.
커널은 실행될 때 어떤 장치가 어느 주소에 연결되어 있는지, 어떤 인터럽트를 사용하는지, 어떤 드라이버와 매칭해야 하는지 알아야 한다.
이 정보를 코드에 직접 박아두면 보드마다 커널을 따로 수정해야 하기 때문에, 하드웨어 정보를 Device Tree 로 분리해서 관리한다.
Device Tree 는 보통 DTS 파일에서 작성되고, 컴파일되면 DTB 형태가 된다.
.dts -> .dtb
펌웨어 안에서는 보통 dtb, device tree blob 형태로 포함된다.
리버싱 관점에서는 Device Tree 를 보면 장치에 어떤 하드웨어가 연결되어 있는지 파악할 수 있다.
예를 들어 UART, GPIO, I2C, SPI, eMMC, Ethernet, Wi-Fi 칩 같은 정보를 확인할 수 있다.
Root Filesystem
Root Filesystem 은 리눅스 시스템에서 / 를 기준으로 하는 파일시스템이다.
펌웨어 안에는 커널만 있는 것이 아니라 실제 사용자 공간에서 실행되는 파일들도 포함된다.
일반적인 Root Filesystem 안에는 다음과 같은 디렉터리가 존재한다.
/bin
/sbin
/etc
/lib
/usr
/var
/www
/tmp
펌웨어 분석에서 Root Filesystem 은 매우 중요하다.
웹 서버 파일, 설정 파일, 기본 계정, init script, 실행 바이너리, 인증 로직, API 엔드포인트 등이 보통 Root Filesystem 안에 들어있기 때문이다.
예를 들어 공유기 펌웨어를 분석하면 /www 안에서 관리자 페이지 소스코드를 찾을 수 있고, /etc 안에서 기본 설정이나 서비스 실행 스크립트를 찾을 수 있다.
펌웨어 이미지
펌웨어 이미지는 장치에 설치되거나 업데이트되는 바이너리 파일이다.
제조사가 제공하는 업데이트 파일도 펌웨어 이미지이고, 장치 내부 저장 장치에서 추출한 바이너리 덤프도 펌웨어 이미지로 볼 수 있다.
펌웨어 이미지는 보통 다음과 같은 형태 중 하나이다.
- Raw binary image
- 압축된 이미지
- 여러 파티션이 결합된 이미지
- 파일시스템 이미지
- 암호화된 이미지
- 서명된 이미지
- 벤더 전용 포맷
예를 들어 단순한 펌웨어는 다음과 같이 커널과 파일시스템이 그대로 붙어있는 형태일 수 있다.
[ header ][ kernel ][ rootfs ]
조금 더 복잡한 장비에서는 여러 파티션 이미지가 하나의 업데이트 파일 안에 들어있을 수 있다.
[ boot ][ recovery ][ system ][ vendor ][ userdata ]
펌웨어 분석에서는 먼저 파일의 magic value, 헤더, 압축 방식, 파일시스템 형식 등을 확인해야 한다.
펌웨어 분석
펌웨어 분석은 펌웨어 이미지 내부의 구조와 동작을 분석하는 과정이다.
보통 다음과 같은 순서로 진행된다.
- 펌웨어 이미지 확보
- 파일 형식 확인
- 압축 또는 패킹 해제
- 파일시스템 추출
- 설정 파일 분석
- 실행 바이너리 분석
- 서비스 동작 구조 파악
- 취약점 분석
펌웨어 분석에서 자주 확인하는 요소는 다음과 같다.
- 기본 계정 정보
- 하드코딩된 비밀번호
- API Key
- SSH Key
- 인증 우회 로직
- 웹 관리 페이지
- init script
- 네트워크 서비스
- SUID 바이너리
- 오래된 라이브러리
- 취약한 CGI 바이너리
예를 들어 펌웨어 내부에 /etc/passwd, /etc/shadow, /etc/init.d, /www, /bin, /sbin 같은 경로가 있다면 해당 파일들을 우선적으로 확인하는 경우가 많다.
펌웨어는 장치의 실제 동작 로직이 담겨있기 때문에, 펌웨어를 분석하면 장치의 공격 표면을 비교적 명확하게 파악할 수 있다.
펌웨어 업데이트
펌웨어 업데이트는 장치 내부의 펌웨어 이미지를 새로운 버전으로 교체하는 과정이다.
업데이트는 기능 개선, 버그 수정, 보안 패치 등을 위해 수행된다.
하지만 펌웨어 업데이트 과정 자체도 보안적으로 중요한 공격 표면이 될 수 있다.
예를 들어 업데이트 파일의 서명을 검증하지 않는 장비라면 공격자가 변조된 펌웨어를 설치할 수 있다.
또는 암호화는 되어 있지만 무결성 검증이 약하면 펌웨어를 수정한 뒤 다시 패키징해서 장치에 올릴 수 있다.
안전한 펌웨어 업데이트에서는 보통 다음과 같은 요소가 필요하다.
- 서명 검증
- 무결성 검증
- 버전 검증
- Rollback 방지
- 복구 파티션
- 업데이트 실패 시 복원 처리
특히 Secure Boot 이 적용된 장비에서는 부팅 단계에서 실행되는 코드들이 신뢰할 수 있는지 검증한다.
Boot ROM 이 첫 번째 부트로더를 검증하고, 부트로더가 커널을 검증하고, 커널이 다음 구성 요소를 검증하는 식으로 신뢰 체인이 이어진다.
이것을 Chain of Trust 라고 부른다.
eMMC
eMMC(embedded MultiMediaCard)는 임베디드 장치에서 많이 사용되는 비휘발성 저장 장치이다.
eMMC 는 NAND Flash 와 Flash Controller 를 하나의 패키지로 묶은 형태이다.
일반적인 NAND Flash 는 저장 셀만 제공하기 때문에 Bad Block 관리, ECC, Wear Leveling 같은 처리를 외부 컨트롤러나 소프트웨어가 담당해야 한다.
반면 eMMC 는 내부에 컨트롤러가 포함되어 있기 때문에 이러한 관리를 eMMC 내부에서 처리한다.
즉, 호스트 입장에서는 eMMC 를 비교적 단순한 블록 장치처럼 사용할 수 있다.
eMMC 의 구성
eMMC 는 크게 다음과 같은 요소로 구성된다.
- NAND Flash
- Flash Controller
- MMC Interface
- Boot Partition
- User Area
- RPMB
- General Purpose Partition
NAND Flash 는 실제 데이터를 저장하는 영역이고, Flash Controller 는 NAND Flash 를 관리하는 역할을 한다.
Host 는 eMMC 내부 NAND 에 직접 접근하는 것이 아니라, eMMC Controller 와 MMC 프로토콜을 통해 통신한다.
대략적인 구조는 다음과 같이 볼 수 있다.
Host SoC
-> MMC Controller
-> eMMC Interface
-> eMMC Controller
-> NAND Flash
즉, eMMC 는 단순히 NAND 칩 하나가 아니라 저장 장치 컨트롤러까지 포함한 패키지이다.
eMMC 와 NAND Flash
eMMC 를 이해할 때 Raw NAND 와의 차이를 이해하는 것이 중요하다.
Raw NAND 는 NAND Flash 자체를 의미한다.
Raw NAND 를 사용하면 시스템이 직접 Bad Block 관리, ECC, Wear Leveling, 주소 변환 등을 처리해야 한다.
반면 eMMC 는 내부 Controller 가 이러한 처리를 담당한다.
- Raw NAND: 호스트가 NAND 관리를 직접 처리해야 한다.
- eMMC: eMMC 내부 Controller 가 NAND 관리를 처리한다.
그래서 eMMC 는 임베디드 시스템에서 저장 장치 구현을 단순하게 만들 수 있다.
하지만 내부 동작이 컨트롤러에 의해 추상화되기 때문에, 물리 NAND 레벨의 정확한 배치나 Wear Leveling 상태를 외부에서 직접 확인하기는 어렵다.
eMMC 와 SD Card
eMMC 는 이름상 MMC 계열이고, 동작 방식도 SD Card 와 유사한 부분이 있다.
하지만 사용 목적과 물리적 형태가 다르다.
SD Card 는 탈착식 저장 장치이고, eMMC 는 보통 보드에 납땜되어 있는 내장형 저장 장치이다.
- SD Card: 탈착식 저장 장치
- eMMC: 보드에 실장되는 내장형 저장 장치
eMMC 는 BGA 패키지 형태로 PCB 에 납땜되어 있는 경우가 많다.
그래서 일반 사용자가 쉽게 분리할 수 없고, 분석을 위해서는 ISP, JTAG, 칩 오프 같은 방식이 사용될 수 있다.
eMMC Partition
eMMC 는 내부적으로 여러 파티션 영역을 제공한다.
대표적인 영역은 다음과 같다.
- User Area
- Boot Partition 1
- Boot Partition 2
- RPMB
- General Purpose Partition
User Area 는 일반적인 데이터 저장 영역이다.
운영체제의 rootfs, system, vendor, userdata 같은 파티션이 보통 이 영역에 저장된다.
Boot Partition 은 부트로더 저장에 사용될 수 있는 작은 영역이다.
SoC 는 부팅 시 eMMC 의 Boot Partition 에서 초기 부트로더를 읽어올 수 있다.
RPMB 는 Replay Protected Memory Block 의 약자로, 재생 공격 방지를 위한 보호 저장 영역이다.
RPMB 는 보안 데이터 저장에 사용될 수 있고, 인증된 접근을 전제로 동작한다.
예를 들어 키, 카운터, 보안 상태, 무결성 관련 데이터가 RPMB 에 저장될 수 있다.
General Purpose Partition 은 필요에 따라 별도로 구성할 수 있는 범용 파티션 영역이다.
User Area
User Area 는 eMMC 에서 가장 일반적으로 사용되는 데이터 저장 영역이다.
리눅스에서는 eMMC User Area 가 보통 블록 디바이스로 인식된다.
예를 들어 다음과 같은 형태로 나타날 수 있다.
/dev/mmcblk0
이 안에 여러 파티션이 있으면 다음과 같이 나타난다.
/dev/mmcblk0p1
/dev/mmcblk0p2
/dev/mmcblk0p3
각 파티션에는 boot, rootfs, system, vendor, userdata 같은 파일시스템이 들어갈 수 있다.
임베디드 장비 분석에서는 /dev/mmcblk0 전체를 덤프하거나 특정 파티션만 덤프해서 파일시스템을 분석할 수 있다.
Boot Partition
eMMC 의 Boot Partition 은 부팅에 사용되는 전용 영역이다.
보통 다음과 같은 형태로 노출될 수 있다.
/dev/mmcblk0boot0
/dev/mmcblk0boot1
Boot Partition 에는 초기 부트로더나 부트 관련 데이터가 저장될 수 있다.
일부 시스템에서는 Boot ROM 이 eMMC Boot Partition 에서 부트로더를 읽고, 그 부트로더가 다시 User Area 에 있는 커널이나 다른 파티션을 로드한다.
대략적인 흐름은 다음과 같다.
Boot ROM
-> eMMC Boot Partition
-> First Stage Bootloader
-> Second Stage Bootloader
-> Kernel
-> Root Filesystem
Boot Partition 은 일반 User Area 와 다르게 보호 설정이 적용될 수 있고, 읽기 전용으로 설정되는 경우도 있다.
그래서 장비를 분석할 때는 User Area 뿐만 아니라 Boot Partition 도 함께 확인해야 한다.
RPMB
RPMB(Replay Protected Memory Block)는 eMMC 내부의 보안 저장 영역이다.
RPMB 는 단순히 데이터를 저장하는 영역이 아니라, 인증과 카운터를 이용해 재생 공격을 방지하는 구조를 가진다.
재생 공격은 이전에 유효했던 데이터를 다시 기록해서 시스템 상태를 과거로 되돌리는 공격이다.
예를 들어 장치가 보안 카운터나 잠금 상태를 저장한다고 할 때, 공격자가 예전 덤프를 다시 써서 잠금 상태를 우회하려고 할 수 있다.
RPMB 는 이러한 공격을 막기 위해 Write Counter 와 인증 메커니즘을 사용한다.
RPMB 는 보통 다음과 같은 데이터 저장에 사용될 수 있다.
- 보안 카운터
- 키 관련 데이터
- 장치 상태
- 무결성 검증 정보
- TEE 관련 데이터
리버싱이나 포렌식 관점에서 RPMB 는 일반 파티션처럼 단순히 덤프하고 수정하기 어려운 영역이다.
따라서 eMMC 전체 구조를 분석할 때 RPMB 의 존재 여부와 사용 여부를 함께 고려해야 한다.
Wear Leveling
NAND Flash 는 각 블록마다 쓰기 횟수에 제한이 있다.
특정 블록에만 계속 쓰기가 발생하면 해당 블록이 먼저 수명을 다할 수 있다.
Wear Leveling 은 쓰기 작업을 여러 블록에 분산시켜 NAND Flash 의 수명을 늘리는 기법이다.
eMMC 에서는 내부 Controller 가 Wear Leveling 을 처리한다.
Host 입장에서는 같은 논리 주소에 데이터를 쓰는 것처럼 보이지만, 실제 NAND 내부에서는 다른 물리 블록에 기록될 수 있다.
즉, eMMC 는 논리 주소와 물리 주소 사이를 내부적으로 매핑한다.
이 때문에 eMMC 를 분석할 때는 논리적으로 보이는 데이터 배치와 실제 NAND 내부 배치가 다를 수 있다.
Bad Block Management
NAND Flash 는 제조 과정이나 사용 과정에서 불량 블록이 발생할 수 있다.
Raw NAND 를 사용할 때는 시스템이 직접 Bad Block 을 관리해야 한다.
반면 eMMC 는 내부 Controller 가 Bad Block Management 를 수행한다.
불량 블록이 발생하면 컨트롤러는 해당 블록을 사용하지 않고, 예비 블록으로 대체한다.
Host 는 이러한 과정을 직접 알지 못하고, 정상적인 블록 장치처럼 접근한다.
즉, eMMC 는 NAND Flash 의 복잡한 특성을 내부에서 숨기고 추상화한다.
ECC
ECC(Error Correction Code)는 NAND Flash 에서 발생할 수 있는 bit error 를 검출하고 복구하기 위한 기법이다.
NAND Flash 는 저장 특성상 시간이 지나거나 사용 횟수가 증가하면 bit error 가 발생할 수 있다.
eMMC 는 내부적으로 ECC 를 사용해서 이러한 오류를 보정한다.
Host 는 보통 ECC 계산과 복구를 직접 수행하지 않고, eMMC Controller 가 처리한 결과를 블록 단위로 전달받는다.
이러한 구조 덕분에 eMMC 는 Raw NAND 보다 다루기 쉽지만, 내부 오류 보정 과정은 외부에서 자세히 관찰하기 어렵다.
eMMC 파티션 구조 예시
임베디드 리눅스 장비의 eMMC 파티션 구조는 대략 다음과 같이 나타날 수 있다.
/dev/mmcblk0
/dev/mmcblk0p1 boot
/dev/mmcblk0p2 kernel
/dev/mmcblk0p3 rootfs
/dev/mmcblk0p4 config
/dev/mmcblk0p5 userdata
/dev/mmcblk0boot0
bootloader
/dev/mmcblk0boot1
backup bootloader
스마트폰이나 Android 기반 장비에서는 더 많은 파티션이 존재할 수 있다.
boot
recovery
system
vendor
userdata
cache
misc
metadata
vbmeta
dtbo
각 파티션은 장치의 부팅, 복구, 시스템 파일, 사용자 데이터, 무결성 검증 등에 사용된다.
펌웨어 추출 방식
펌웨어를 분석하려면 먼저 펌웨어 이미지를 확보해야 한다.
펌웨어를 확보하는 방식은 여러 가지가 있다.
- 제조사 홈페이지에서 업데이트 파일 다운로드
- 모바일 앱 또는 업데이트 서버에서 펌웨어 URL 확인
- 장치 내부 파일시스템에서 추출
- UART Shell 을 통해 덤프
- JTAG 을 통해 메모리 또는 저장 장치 접근
- ISP 방식으로 eMMC 직접 접근
- 칩 오프 방식으로 eMMC 분리 후 덤프
가장 쉬운 방법은 제조사가 제공하는 업데이트 파일을 다운로드하는 것이다.
하지만 업데이트 파일이 암호화되어 있거나 서명되어 있거나 일부 파티션만 포함하는 경우에는 실제 장치의 eMMC 덤프가 필요할 수 있다.
eMMC 덤프를 확보하면 업데이트 파일에는 포함되지 않는 설정값, 로그, 사용자 데이터, 실제 파티션 상태를 확인할 수 있다.
eMMC Dump
eMMC Dump 는 eMMC 저장 장치의 내용을 읽어서 이미지 파일로 저장하는 작업이다.
리눅스에서 eMMC 가 /dev/mmcblk0 으로 인식되어 있다면 전체 User Area 를 이미지로 저장할 수 있다.
dd if=/dev/mmcblk0 of=emmc_user.img bs=4M
Boot Partition 은 별도의 장치 파일로 노출될 수 있다.
dd if=/dev/mmcblk0boot0 of=boot0.img bs=4M
dd if=/dev/mmcblk0boot1 of=boot1.img bs=4M
특정 파티션만 덤프할 수도 있다.
dd if=/dev/mmcblk0p3 of=rootfs.img bs=4M
이렇게 확보한 이미지에서 파티션 테이블, 파일시스템, 부트로더, 커널, 설정 파일 등을 분석할 수 있다.
펌웨어 파일시스템
펌웨어 분석에서 자주 만나는 파일시스템은 다음과 같다.
- SquashFS
- JFFS2
- UBIFS
- ext2
- ext3
- ext4
- cramfs
- YAFFS2
공유기나 IoT 장비에서는 SquashFS 가 많이 사용된다.
SquashFS 는 읽기 전용 압축 파일시스템이기 때문에 펌웨어 크기를 줄이고 무결성을 유지하기에 적합하다.
설정값처럼 변경이 필요한 데이터는 별도 파티션에 저장되는 경우가 많다.
예를 들어 rootfs 는 SquashFS 로 읽기 전용 구성하고, /overlay 나 /data 같은 영역을 쓰기 가능한 파티션으로 두는 방식이다.
rootfs -> read-only squashfs
overlay -> writable jffs2/ext4
userdata -> writable ext4
이 구조를 이해하면 장치가 어떤 파일을 기본 이미지에서 읽고, 어떤 파일을 런타임에 수정하는지 파악할 수 있다.
Secure Boot
Secure Boot 은 부팅 과정에서 실행되는 코드의 무결성과 신뢰성을 검증하는 보안 기법이다.
일반적인 부팅 과정에서는 Boot ROM, Bootloader, Kernel, Root Filesystem 순서로 실행 흐름이 이어진다.
Secure Boot 이 적용되면 각 단계에서 다음 단계의 서명을 검증한다.
Boot ROM
-> verify Bootloader
-> verify Kernel
-> verify Root Filesystem
이렇게 신뢰가 단계적으로 이어지는 구조를 Chain of Trust 라고 한다.
Secure Boot 이 제대로 적용되어 있으면 공격자가 eMMC 에 저장된 부트로더나 커널을 변조하더라도 부팅 과정에서 검증에 실패할 수 있다.
하지만 Secure Boot 이 비활성화되어 있거나, 검증 범위가 일부 영역에만 적용되거나, 롤백 방지가 없다면 우회 가능성이 생길 수 있다.
Verified Boot
Verified Boot 은 부팅 과정에서 시스템 파티션의 무결성을 검증하는 구조이다.
Android 장비에서는 vbmeta, boot, system, vendor 같은 파티션이 검증 체계에 포함될 수 있다.
Verified Boot 은 단순히 부트로더만 검증하는 것이 아니라, 커널과 시스템 파티션이 변조되었는지도 확인한다.
검증이 실패하면 장치가 부팅을 중단하거나 경고 상태로 진입할 수 있다.
eMMC 에 저장된 파티션을 수정할 때 Verified Boot 이 적용되어 있다면, 단순히 파일시스템만 수정해서는 정상 부팅되지 않을 수 있다.
따라서 펌웨어 분석이나 장치 수정에서는 Secure Boot, Verified Boot, dm-verity 같은 보호 기법의 적용 여부를 확인해야 한다.
정리
펌웨어는 장치 내부에서 하드웨어를 제어하고 운영체제를 부팅시키기 위해 사용되는 저수준 소프트웨어이다.
펌웨어에는 보통 Bootloader, Kernel, Device Tree, Root Filesystem, 설정 파일, 애플리케이션 바이너리 등이 포함된다.
eMMC 는 NAND Flash 와 Controller 를 하나의 패키지로 묶은 임베디드 저장 장치이다.
eMMC 는 내부 Controller 를 통해 Wear Leveling, Bad Block Management, ECC 같은 NAND 관리 기능을 처리한다.