[PAPER REVIEW] Toward Fast and Scalable Firmware Fuzzing With Dual-Level Peripheral Modeling
하드웨어 의존성 때문에 firmware fuzzing이 제한적이다. 가장 최근의 접근법은 하드웨어 독립적인 firmware fuzzing으로 진행하는 것인데, 많은 개선이 필요하다. firmware fuzzing은 아직 확장성과 효과성 면에서 어려움이 있다.
firmware fuzzing의 어려움을 해결하기 위해, register level 모델링과 선택적 function level 모델링의 dual-level 접근 방안을 제안한다.
register level에서 firmware fuzzing을 시작하고 hardware abstraction layer 함수를 실행하는 동안 주변장치 핸들러를 연결한다.
4개의 firmware를 대상으로 방법론의 효율성, 확장성, 효과성를 평가하고, 두 개의 level을 사용하여 빠르고 확장성 있는 firmware fuzzing이 가능함을 입증한다.
임베디드 시스템의 빠른 증가로 펌웨어 취약점이 상당히 증가했고, 펌웨어 취약점은 치명적인 보안 문제이다. 펌웨어는 low-level이기 때문에 OS나 application-level 취약점보다 더 높은 영향이 있다. 하지만, 보안 측면에서 펌웨어를 테스트하는건 귀찮고 어려운 일이다.
fuzzing은 현대 소프트웨어에서 취약점을 탐지하는데 보편적으로 사용되는 효과적이고 확장성있는 테스트 방법이다. AFL과 같은 coverage-guided fuzzer는 여러 소프트웨어에서 많은 버그를 찾는데 성공해왔기 때문에 MCU 펌웨어에 coverage-guided fuzzing을 적용의 필요성이 높아졌지만 이는 어려운 일이다.
펌웨어 퍼징이 어려운 이유
Muench
P2IM
HAL-Fuzzer
두 도구 모두 확장성과 효율성 측면에서 개선이 필요하다.
dual-level approach
firmware fuzzing에서의 확장성과 효과성 문제를 해결하는데 register level 주변장치 모델링과 function level 주변장치 모델링을 하는 dual-level 접근법을 제안한다.
hybrid emulation for firmware fuzzing(HEFF)
연구의 프로토타입 시스템은 hybrid emulation for firmware fuzzing(HEFF)으로, register level에서 firmware fuzzing을 시작하고 HAL 함수를 실행하느 동안 주변장치 핸들러와 연결한다. 두 level은 firmware fuzzing에서 빠르고 확장성이 있다.
P2IM, HAL-Fuzz 기반으로 구현되었으며, 효율성, 확장성, 효과성 측면에서 평가를 진행한다.
Dual-Level Peripheral Modeling
하드웨어 독립적인 firmware fuzzing을 개선하기 위해 peripheral modeling 접근을 제안한다.
빠르고 확장성 있는 firmware fuzzing
prototype system을 구현했으며 fuzzing 실험을 진행했다.
버그 탐지에서의 효과
prototype system은 많은 버그를 빠르게 찾을 수 있다.
Section II: 관련 연구
Section III: firmware fuzzing 배경지식과 실험
Section IV: system 설계 소개
Section V: 평가
Section VI: discussion
Section VII: conclusion
범용 OS 기반 기기에서는 kernel에서 하드웨어 통신이 일어나기 때문에 kernel을 에뮬레이드해서 하드웨어 통신을 지원할 수 있다.
Firmadyne, Costin, FirmFuzz
FIRM-AFL
embedded-OS나 OS가 없는 abstraction 기반 기기는 peripheral emulation이 필요하다.
QEMU_STM32
Panda
펌웨어의 full emulation 통해 찾은 취약점 탐지 정확도는 높다.
full emulator를 구현하는데 필요한 하드웨어 지식이 부족할 수 있다.
full emulation은 느리다.
HEFF의 경우, embedded-OS, no-OS abstraction-based 기기를 타겟팅하여 취약점을 찾을 때 full emulation 한계를 극복하기 위해 partial emulation 기술을 사용했다.
Avatar
emulator의 모든 메모리와 CPU register 상태 변화를 실제 기기에 보내는 방식으로 firmware emulation을 구현해서 harware 자원 문제를 해결했다.
PROSPECT
가상 머신에서 임베디드 시스템으로 peripheral 접근하는 통로인 proxy를 제공한다.
SURROGATES
연산에서의 오버헤드를 줄이고 복잡한 시스템 분석을 제공하기 위해 호스트와 타겟 사이 FPGA bridge를 제공한다.
Avatar2
Avatar를 확장하여 여러 플랫폼 지원
펌웨어를 작동하는데 emulator나 분석 도구 사이 Avatar2 사용
GDB, QEMU, angr, OpenOCD, PANDA, WYCINWYC, PRETENDER, Unicorefuzz, HALucinator 와 같은 도구 사이 상태 전달 가능
full emulation 한계 극복 가능하고 물리적 기기를 에뮬레이트하는 구현에 대한 노력을 줄일 수 있다.
임베디드 기기에 다양한 peripheral이 사용되기 때문에 emulation 위한 물리적 기기 제공이 어렵다.
HEFF는 partial emulation 시 모델링된 peripheral을 사용해서 HITL에서의 주변장치 의존성을 제거했다.
PRETENDER
P2IM
HALucinator
DICE
Conware
펌웨어는 여러 임베디드 기기에서 하드웨어 제어 기능을 제공하는 low-level 소프트웨어이다.
Muench는 embedded 기기를 OS 종류(범용 OS, 임베디드 OS, no OS)에 따라 분류했다.
81%의 임베디드 기기는 OS가 없거나 적은 OS 추상화로 MCU firmware를 통해
작동해서 연구에 가장 큰 문제였다.
fuzzing
fuzzing은 랜덤으로 변형된 입력을 통해 주로 소프트웨어에서 버그를 찾는 동적 테스팅 기술이다.
firmware fuzzing에서 firmware emulation
펌웨어 emulation 없이 instrumentation 도구를 사용할 수 없다.
하드웨어 다양성 때문에 full emulation은 실용적이지 않다.
HITL emulation은 실제 하드웨어 기기와 통신이 필요하기 때문에 fuzzing 성능이 좋지 않다. 따라서 firmware fuzzing에 이 emulation을 사용하기엔 느리고 확장성이 없다.
peripheral modeling을 하는 partial emulation은 firmware fuzzing에 유망한 접근법인데, peripheral을 가상으로 모델링해서 전체가 에뮬레이트된 프로세서를 제공하기 때문이다. 이 방법으로 실제 기기와 전체 peripheral 에뮬레이트 필요 없이 emulator에서 펌웨어가 실행될 수 있다. 하지만 on-chip peripheral만 가능한데, off-chip peripheral에 직접적으로 접근할 수 없기 때문이다. peripheral modeling을 사용한 도구로는 P2IM과 HAL-Fuzz가 있다.
peripheral modeling을 통한 partial emulation이 fuzzing을 위한 빠르고 확장성 있는지에 대한 것이 논점이다. 따라서 연구 논점을 명확히 하기 위해 2개의 실험을 진행했다.
P2IM
peripheral을 에뮬레이트하는 대신 peripheral에 대한 memory-mapped register를 조작해서 peripheral을 black box로 취급했다.
ARM Cortex-M MCU의 경우, peripheral register는 대부분 0x40000000-0x5fffffff 메모리 영역에 매핑되므로 P2IM은 이 메모리 영역이 잠재적인 memory-mapped register로 간주한다. P2IM은 펌웨어 정보를 위해 인터페이스 모델을 인스턴스화하고, peripheral register에 대한 모든 접근을 모니터링한다.
P2IM가 firmware fuzzing로 사용하기에 확장성이 있지만, register-level에서 속도 면에서 더 향상된 걸 확인할 수 있었다. (테이블 1 참고)
P2IM, HAL-Fuzz 성능 비교
테이블 1은 HAL 함수를 포함한 펌웨어를 대상으로 fuzzing 성능 측면에서 P2IM과 HAL-Fuzz의 속도와 code coverage(실행된 basic block 수)를 측정한 결과이다. P2IM의 code coverage가 HAL-Fuzz보다 훨씬 좋지만, 속도 면에서는 더 느리다.
HAL-Fuzz
HALucinator는 펌웨어에서 library matching 기술을 통해 HAL 함수를 대체한다. peripheral emulation 없이 에뮬레이트된 펌웨어와 관련 peripheral model 사이 외부 통신을 처리한다. HAL-Fuzz는 LibMatch 도구를 사용하여 펌웨어에 HAL 함수를 위치시킨다. abstract function-level에서 적은 문법성으로 firmware fuzzing을 빠르게 할 수 있지만, library matching 위한 철저한 준비가 필요하다.
그림 1은 HAL 목적 파일은 GCC의 -O0, -O2, -O3, -Os, -Og optimization level에서 컴파일한 6개의 bare-metal 펌웨어에 LibMatch 기술을 사용한 결과를 보여준다. 95%의 HAL 함수를 식별할 수 있었지만, 컴파일러 버전이 달라지거나 optimization level이 달라지면 매칭 비율이 낮아진다.
HAL-Fuzz는 함수 후킹 기반 접근이므로 LibMatch를 사용한 HAL 함수 식별이 필요하다.
dual-level approach in peripheral modeling
peripheral modeling에서 register level과 function level의 장점이 있기 때문에, peripheral modeling에 register level과 function level 둘다 사용한 dual-level approach를 사용한다.
HEFF 구현에 P2IM과 HAL-Fuzz의 사용
HEFF 이름의 P2IM과 HAL-Fuzz 기반 firmware fuzzer를 구현했다.
HEFF는 P2IM의 확장성과 자동이란 장점으로 peripheral modeling을 register level에서 시작한다. HAL 함수 호출이 탐지되면, HAL-Fuzz에서 peripheral 핸들러를 연결해서 function-level peripheral modeling이 시작된다. peripheral 핸들러 구현에 기술적 노력이 필요하지만 fuzzing 속도를 높일 수 있다.
HEFF는 HAL 함수와 HAL가 아닌 함수가 호출되었을 때에도 빠른 firmware fuzzing이 가능하다.
입력
preprocessing
dual-level modeling
fuzzing
Pre-built QEMU와 변형된 펌웨어 필요하다.
Pre-built QEMU
Modified firmware
function-level과 register-level에 따라 각각 입력 방식을 제공해서 fuzzing을 수행한다. (알고리즘 1의 11-15라인)
register-level에서 peripheral modeling 후, AFL에서 만든 입력이 데이터 값을 저장하는 DR(data register)로 전달된다.
function-level peripheral modeling 이후에는 AFL이 만든 입력이 function handler로 전달된다. handler에 fuzzing 입력을 전달하기 위해서 입력을 저장할 변수와 입력값 길이가 필요하다.
평가 기준
실험 대상 (펌웨어)
P2IM의 경우 랜덤 seed 값을 사용하고, HAL-Fuzz는 특정 길이의 입력이 필요하다. 따라서 HAL-Fuzz에서 사용된 입력을 P2IM에서 사용했다.
가상머신: Intel R Xeon(R) Gold 6134 CPU, 16GB RAM의 Ubuntu 18.04 64bit 시스템
5시간 씩 firmware fuzzing 10번 진행
퍼징 실행 속도를 P2IM, HAL-Fuzz와 비교하여 퍼징 효율성 비교
빠른 퍼저는 더 많은 입력으로 더 많이 실행될 수 있다. → 빠른 퍼저일수록 취약점을 발견할 가능성이 높다.
P2IM은 register level에서 실행해서 다른 두 퍼저와 비교했을 때 느리고 실행 횟수가 적다.
HAL-Fuzz는 function-level에서 수행되어 퍼징 속도가 빠르고, 펌웨어가 가장 많이 실행될 수 있었다.
HEFF의 경우 P2IM, HAL-Fuzz를 결합하여 P2IM보다 0.9배 덜 실행되었고 HAL-Fuzz보다는 2-4배 더 실행되었다.
그림 3은 P2IM보다 적어도 2.7%, 최대 9.6%까지 더 실행될 수 있음을 보여준다.
동일한 함수를 처리할 때 HEFF의 핸들러는 P2IM보다 400배 더 빠르게 처리할 수 있다. 이것으로 HEFF에서 더 많은 handler를 처리할 수 있음을 알 수 있다.
테이블 7에서 알 수 있듯이, HEFF의 펌웨어 재작성 과정으로 register level에서 모델 인스턴스화 시간을 21초까지 줄일 수 있다.
따라서 적은 수의 handler로도 속도를 향상시킬 수 있고 모델 인스턴스화 시간을 줄일 수 있기 때문에 HEFF는 효율적이다.
basic block coverage를 HAL-Fuzz, P2IM과 비교
테이블 6는 HEFF, P2IM, HAL-Fuzz 퍼저의 basic block 수를 보여준다.
HEFF와 P2IM는 차이가 근소하지만, HAL-Fuzz와 비교했을 때 HAL-Fuzz는 가장 적은 basic block coverage를 보였다. HEFF는 각 펌웨어에서 10%의 HAL 함수만 처리했음에도 HAL-Fuzz와 비교했을 때 가장 많은 basic block을 커버할 수 있었다.
그림 4는 HEFF와 HAL-Fuzz 퍼저의 basic block coverage를 보여준다. HEFF가 HAL-Fuzz보다 훨씬 많은 basic block을 커버할 수 있음을 알 수 있고 이는 HEFF가 HAL-Fuzz보다 훨씬 확장성이 있음을 의미한다.
특히, CNC의 경우 USART_putc 함수가 함수 리스트에 존재하지 않아서 HAL-Fuzz 퍼저로는 실행할 수 없었는데, HEFF는 함수가 함수 리스트에 존재하지 않아도 register level에서 계속 펌웨어를 실행하며 퍼징을 수행할 수 있다.
따라서 HEFF가 더 확장성 있는 퍼징이 가능함을 확인할 수 있다.
4개 펌웨어에 10번의 퍼징 수행하여 P2IM, HAL-Fuzz, HEFF 비교
HEFF, P2IM, HAL-Fuzz 모두 4개의 펌웨어에서 PLC에서만 버그를 탐지할 수 있었다.
그림 5는 5시간 동안 퍼징을 진행했을 때 memory corruption에 의한 크래시 발생 수를 보여준다. 크래시 수는 테스트 케이스에서 마지막 basic block에서 발생한 크래시로 카운팅을 했다.
HAL-Fuzz는 하나의 크래시만 발견할 수 있었고, P2IM보다 HEFF가 6배 더 많은 크래시를 찾을 수 있었다.
따라서 빠른 시간에 더 많은 크래시를 탐지한다는 점에서 HEFF는 효과적이다.
퍼징 가속화
31개의 HAL 함수 handler 중 19개(61%)는 return-zero handler이다. 이는 60% 정도의 HAL 함수는 퍼징 성능에 영향을 주지 않는다는 것이다. HAL-Fuzz와 다르게, HEFF는 펌웨어 수행에 영향이 없는 함수 연결 시 함수 handler를 구현하지 않고 return-zero handler를 구현하여 퍼징을 더 가속화할 수 있다.
실험에 사용한 펌웨어에서는 전체 HAL 함수 중 10%만 HAL 함수를 호출해서 HEFF의 퍼징 속도가 향상된 것을 확인할 수 있다. (테이블 4 참고)
하지만 HAL-Fuzz의 경우 많은 handler를 사용하기 때문에 더 빠른 속도 향상을 예상할 수 있다.
더 많은 handler가 처리될수록, 더 크게 속도 향상을 기대할 수 있다. 이 향상으로 더 많은 버그를 탐지할 가능성을 높일 수 있다.
model instantiation
테이블 7은 HEFF와 P2IM의 모델 인스턴스화 시간을 보여준다. 변형된 펌웨어를 실행했을 때, HEFF는 모델 인스턴스화 시간을 그렇지 않는 P2IM보다 줄일 수 있다. CNC에서 P2IM보다 모델 인스턴스화 시간이 느리지만, 다른 펌웨어에서 그 차이는 작다.
이 모델 인스턴스화 시간이 느려짐에도 전체 퍼징 속도가 향상되었다.
빠르고 확장성 있는 펌웨어 퍼징을 위해 dual-level peripheral modeling이란 새로운 접근을 제안했고 P2IM 위에 HEFF이라는 프로토타입 시스템을 구현했다.
P2IM, HAL-Fuzz와 비교하여 HEFF의 효율성, 확장 가능성, 효과성을 입증했다.
프로토타입 구현 시, HAL-Fuzz의 function-level의 LibMatch와 function handler를 적용했다. 그 결과, HEFF이 P2IM보다 더 빠르고, HAL-Fuzz보다는 더 확장성이 있음을 확인할 수 있었다.
abstract function level에서의 function matching 기술 LibMath 적용 시, function level에서만 HAL 함수들을 처리할 수 있었어서 확장성이 제한된다. 따라서 abstract function level에서 더 많음 함수를 처리할 수 있도록 function matching 메커니즘을 더 개발할 계획이다.
register level에서의 mis-categorization 문제
function level에서의 function matching 기술을 개선하면 register level에서의 잘못된 카테고리화 문제도 해결할 수 있다.
return zero handler
“write”이라는 함수가 어떤 레지스터에 접근하는지 여부 확인 없이 퍼징에 필요없는 함수로 return-zero handler로 처리한다. 이 부분도 앞으로 개선할 사항이다.