one-day research 였던 것(삽질일기)

1. 주제 선정

  • 평소 시스템 해킹 공부를 주로 하면서 일반적이고 기본적으로 자주 풀었던 문제가 Buffer overflow 를 이용해 shell을 획득하는 것이었다. 문제로 만들어진 바이너리에서는 비교적 간단했지만 real world에서 발생하는 BOF 취약점을 exploit 해보고 싶다는 생각이 들었고 실생활에서 자주 확인할 수 있는 BOF 취약점이 IoT 기기에서 자주 발생한다는 것을 확인하여 IoT 기기의 BOF 취약점으 로 RCE까지 exploit 하는 것을 이번 1-day research 목표로 설정하게 되었다.

2. CVE 선정

  • 이번 CVE 선정 기준은 다음과 같았다.
    1. BOF 취약점으로 DOS로 끝나는 것이 아닌 RCE 까지 exploit 할 수 있을 것.
    2. 취약점 지수가 6.0 이상일 것.
    3. 해당 기기의 펌웨어가 자사 홈페이지에 공개돼있을 것.
  • 위 기준으로 찾은 CVE가 CVE-2024-1179 이었다.
  • CVE-2024-1179
    • 펌웨어가 제공되었기 때문에 squashfs-root 파일을 추출 후 emulating을 진행
    • 펌웨어는 해당 취약점이 패치된 이전 버전의 펌웨어를 다운로드

    ### squashFS 추출

    • 보통 펌웨어 파일은 .img 나 .bin 의 확장자를 가짐.
    • 해당 파일을 binwalk를 이용해 추출

    Pasted image 20240806155605.png

    • 추출 후 extracted 파일 생성됨

    Pasted image 20240806155650.png

    • squashfs-root 파일 확인 가능

    Pasted image 20240806155825.png

    ### emulating

    • 이제 해당 squashfs-root 폴더 안의 system을 emulating 해야 한다.
    • bin 폴더 안의 바이너리를 file 명령어를 이용하여 어떤 아키텍쳐인지 확인 가능

    Pasted image 20240806160202.png

    • 해당 시스템은 MIPSEL(리틀엔디안) 아키텍쳐로 필자가 에뮬레이팅을 하려는 로컬 환경과 아키텍쳐가 다르므로 qemu를 사용하여 에뮬레이팅 해야 한다.

    Pasted image 20240806162219.png

    에뮬레이팅까지는 완료했지만 해당 바이너리에서 웹 서버를 실행하는 바이너리를 실행시키는데에 계속해서 이슈가 있어 해당 CVE를 진행하기에 어려움이 있었다.

  • CVE-2023-41184
  • 선정 이유
    • 일반적인 공유기가 아닌 IP cam 이었기 때문에 매력적이라고 생각했고, 현재 모델에 나와있는 CVE가 2개밖에 없었기 때문에 0-day 분석까지 가능할 것 같아 선택하게 되었음.
  • 따라서 해당 CVE로 변경하게 되었다. 하지만 해당 CVE는 펌웨어가 공개되어있지 않기 때문에 하드웨어 해킹을 진행해야 했다.

Hardware hacking

  • 우선 UART 통신을 이용해 셸을 획득하고자 했다.

IMG_0001 2.jpg

  • 해당 칩이 MCU 인것을 확인하고 datasheet와 multimeter 로 UART 포트를 탐색

    하지만 어디를 찍어도 UART 포트는 없었다… MCU의 핀에 바로 연결하기에는 핀이 너무 작아 UART 통신은 포기

  • SPI 포트도 없었고 JTAG 커넥터도 없었기 때문에 ROM을 분리하여 롬라이터에 장착하여 파일시스템을 읽어오는 방법을 선택

IMG_0002 2.jpg

IMG_0016.jpg

  • 하지만 해당 ROM은 SOP8로 해당 롬라이터와 호환되지 않았다. 따라서 SOP8 to DIP8 어댑터를 구매.(SOP8칩도 150mil, 208mil의 크기 차이가 있으므로 해당 칩의 크기에 맞게 어댑터를 구매해야 한다.)

IMG_0095.jpg

  • BIOS에 연결해야 하므로 어댑터는 BIOS쪽에 연결한다.

IMG_0094.jpg

  • 롬라이터 사진에는 칩 기준점이 왼쪽 상단에 위치해야 한다고 나와있었는데 반대로 오른쪽 하단에 위치해야 인식이 가능했다.

Pasted image 20240807151148.png

  • 롬라이터 소프트웨어를 이용하여 왼쪽 Detect 버튼으로 인식완료

Pasted image 20240807174205.png

  • read 버튼을 눌러 데이터를 읽어온 모습

Pasted image 20240807225530.png

  • 읽어온 데이터에서 binwalk를 이용하여 2개의 filesystem 확인
dd if=./origin.bin of=squashfs1 skip=1991168 count=2374426 bs=1
  • dd 명령어를 이용해 원하는 오프셋부터 파일시스템 추출
    • if : 추출할 대상 bin 파일 경로
    • of : 추출 결과 파일 경로 및 이름
    • skip : 해당 오프셋부터 읽음
    • count : 읽고자 하는 크기
    • bs : block-size(한번에 몇 바이트씩 읽을지)

Pasted image 20240807230123.png

  • unsquashfs를 이용하여 아까 추출한 squashfs-root 파일 획득

Pasted image 20240807175543.png

  • 원활한 분석을 위해 기기 부팅시 실행되는 etc/init.d/rcS 파일에 리버스셸 코드 삽입(위 그림과 같이 nc와 같은 바이너리가 실제로 있는지 확인 및 경로 확인) -> 실행중인 셸에 붙을 수 있다
sudo mksquashfs [파일시스템] [패치파일 이름] -comp xz
  • 위 명령어로 패치된 파일시스템 압축

Pasted image 20240809104554.png

Pasted image 20240809110911.png

Pasted image 20240809110942.png

  • 위에서 binwalk로 확인한 오프셋과 크기로 origin.bin의 파일시스템을 모두 0으로 변경

Pasted image 20240809111323.png

  • patch한 파일을 0으로 변경했던 부분에 삽입하고 해당 파일을 롬에 write

    rom을 보드에 다시 부착하면 되는데 인두기, 열풍기 이슈로 기기 손상.. 기기 재구매 후 셸 없이 분석 진행

또 다른 문제 발생

  • 받았을 당시의 펌웨어가 필자가 찾은 취약점 발생 업데이트 이후 버전이었다.

    다운그레이드는 불가하기 때문에 불가피하게 0-day 분석으로 변경

3. 0-Day 분석

nmap

  • 해당 기기를 연결 후 nmap을 통해 열려있는 포트 확인

Pasted image 20240809113924.png

  • 443포트로 접속하니 “Bad Request” 출력하는 것을 확인

Pasted image 20240809114522.png

  • 2020포트로 접속하니 “Please wait” 출력 후 죽는 것을 확인

Pasted image 20240809115007.png

Binary 분석

Pasted image 20240809131315.png

  • popen 함수로 이어지는 취약점 발견

Pasted image 20240809131252.png

  • param 변수를 받아서 해당 json 변수가 obj 형식이 아니면 -40209 오류를 출력
  • obj 형식이라면 param 변수를 json string으로 받은 후 sprintf로 command_1에 저장

Pasted image 20240809135609.png

  • json_object 변수는 사용자의 리퀘스트에서 json 데이터 값
  • json_object에서 ‘method’의 값이 ‘setLanguage’이고, ‘params’의 값이 command_1, 즉 popen으로 들어갈 문자열이다.
  • language_value는 params 값의 language 값.
  • json_data 형식

      json_data = {"method":"setLanguage","parmas":{"language":$language_value}}
    
  • '; sbin/poweroff; #와 같은 페이로드를 전송한다면
ubus call system_state-audio set_language '{"language":"'; sbin/poweroff; #"}'
  • 하지만 251 line에 single quote(‘) 를 필터링하고 있음

    해당 필터링 우회하는 것에 실패

4. 결과

  • 펌웨어 버전 이슈로 1-day 분석은 진행할 수 없었다. 0-day도 아직 찾지 못했음.
  • 하지만 IoT 해킹의 전반적인 과정을 모두 수행해보면서 평소에 잘 몰랐던 하드웨어에 대한 지식도 얻을 수 있었고 큰 바이너리를 분석해보면서 IoT 기기의 시스템이 어떻게 돌아가는지도 파악할 수 있었다.
  • 프로젝트 후에도 계속해서 0-day 취약점을 찾을 예정(돈 아까워서)

  • 얻은 것
    • 하드웨어 및 하드웨어 해킹 지식
    • 바이너리 분석 기초 지식
    • IoT 해킹의 전반적인 지식
    • 인두기와 열풍기
  • 잃은 것
    • 77,600원
    • 카메라 한 대