
androidqf (Android Quick Forensics)는 Android 기기에서 포렌식 증거를 신속하게 수집하여 잠재적인 침해 흔적을 식별하는 데 도움을 줍니다.
androidqf(Android Quick Forensics)는 Android 기기에서 관련 포렌식 데이터를 손쉽게 수집할 수 있도록 단순화한 휴대용 도구입니다.
androidqf는 Android 기기에서 데이터를 신속하게 수집할 수 있는 간단하고 휴대 가능한 크로스 플랫폼 유틸리티를 제공하는 것을 목표로 합니다. 기능 면에서 mvt-android와 유사합니다. 그러나 MVT와 달리 androidqf는 기술에 익숙하지 않은 사용자도 쉽게 실행할 수 있도록 설계되었습니다. androidqf로 추출한 데이터는 MVT로 분석할 수 있습니다.
이 저장소는 Amnesty International의 Security Lab에서 유지 관리하는 androidqf의 포크입니다. androidqf 도구는 원래 Claudio Guarnieri가 개발했습니다.

Linux, Windows 및 Mac용 실행 파일 바이너리는 최신 릴리스에서 제공됩니다. 바이너리 실행에 문제가 있는 경우 직접 빌드할 수 있습니다.
이 프로젝트는 자동화된 빌드 및 릴리스를 위해 GoReleaser를 사용합니다. 로컬에서 빌드하려면:
GoReleaser 설치:
go install github.com/goreleaser/goreleaser/[email protected]
스냅샷 빌드 실행(게시 없음):
./build_locally.sh
이렇게 하면 dist/ 디렉터리에 모든 플랫폼용 바이너리가 생성되며, Intel과 Apple Silicon 모두에서 작동하는 macOS용 유니버설 바이너리도 포함됩니다.
기존의 Makefile 방식을 여전히 사용할 수 있습니다. Go 1.26.5+가 설치되어 있어야 하며, make, git, unzip, curl도 필요합니다. AndroidQF에는 대상 기기에서 실행되어 포렌식 관련 정보를 보다 안정적으로 추출하는 크로스 컴파일된 collector가 포함되어 있습니다.
먼저 collector 모듈을 빌드합니다:
make collector
그런 다음 원하는 플랫폼용으로 AndroidQF를 컴파일합니다:
make linux
make darwin
make windows
이 명령들은 build/ 폴더에 바이너리를 생성합니다.
배포 패키지는 unbundle 빌드 태그로 빌드하여 번들된 ADB 및 collector 바이너리 포함을 제외하도록 선택할 수 있습니다:
go build -tags unbundle -o build/
이 태그가 활성화되면 androidqf는 다음을 기대합니다:
PATH에서 adb를 사용할 수 있어야 합니다./usr/lib/androidqf/android-collector/ 아래에 androidqf가 기대하는
이름(예: collector_arm, collector_arm64)으로 설치되어 있어야 합니다.패키저는 빌드 전에 assets/에서 번들된 바이너리 자산을 제거할 수 있지만,
assets/ 패키지 디렉터리와 그 Go 소스 파일은 반드시 남아 있어야 합니다.
unbundle 빌드는 여전히 assets 패키지를 임포트하며, assets/ 디렉터리
전체가 삭제되면 빌드가 실패합니다.
릴리스 컨테이너 이미지는 GitHub Container Registry에 게시됩니다:
docker pull ghcr.io/mvt-project/androidqf:latest
Linux에서 USB로 연결된 Android 기기에서 수집하려면 USB 버스를 통과시키고 출력 디렉터리를 마운트하세요:
docker run --rm -it --privileged \
-v /dev/bus/usb:/dev/bus/usb \
-v "$(pwd)/output:/output" \
ghcr.io/mvt-project/androidqf:latest -fast -output /output
릴리스된 버전의 이미지를 로컬에서 직접 빌드할 수도 있습니다:
docker build --build-arg VERSION=1.8.3 -t androidqf .
[!TIP] 아카이브 형식, 무결성 해시, 암호화 및 대용량 파일 처리에 대해서는 수집 아카이브를 참조하십시오. 수집된 파일의 사전은 서드파티 SocialTIC AndroidQF 출력 파일 사전을 참조하십시오.
androidqf를 실행하기 전에 대상 Android 기기를 USB로 컴퓨터에 연결해야 하며, USB 디버깅을 활성화해야 합니다. 이 작업을 수행하는 방법은 공식 문서를 참조하십시오. 다만 제조사가 다른 Android 휴대폰은 기본값과 다른 탐색 단계가 필요할 수 있다는 점에 유의하십시오.
USB 디버깅이 활성화되면 androidqf 실행을 진행할 수 있습니다. 먼저 USB 브리지를 통해 기기에 연결을 시도하며, 그러면 Android 휴대폰에 호스트 키를 수동으로 승인하라는 메시지가 표시됩니다. 반드시 승인하십시오. 이상적으로는 영구적으로 승인하여 메시지가 다시 나타나지 않도록 하십시오.
이제 androidqf가 실행되어 현재 작업 디렉터리 또는 -output으로 지정한 디렉터리에 수집 zip 아카이브를 생성합니다. 실행 중 어느 시점에서 androidqf가 몇 가지 선택 사항을 묻습니다. 이 프롬프트는 선택을 제공할 때까지 수집을 일시 중지하므로 주의를 기울이십시오. 모든 프롬프트는 명령줄 플래그로 미리 응답할 수도 있습니다. 무인 수집을 참조하십시오.
다음 데이터를 추출할 수 있습니다:
| 데이터 | 선택 사항? | 출력 경로 |
|---|---|---|
| 전체 백업 또는 SMS 및 MMS 메시지 백업. | ✅ | backup.ab |
| 빌드 정보와 구성 매개변수를 제공하는 getprop 셸 명령의 출력. | getprop.txt | |
| 모든 시스템 설정 | settings_*.txt | |
| 실행 중인 모든 프로세스 목록을 제공하는 ps 셸 명령의 출력. | 수집기를 사용할 수 있는 경우 processes.json, 그렇지 않으면 processes.txt | |
| 시스템 서비스 목록. | services.txt | |
| 시스템의 모든 로그 사본. | logs/, logcat.txt | |
| 기기에 대한 진단 정보를 제공하는 dumpsys 셸 명령의 출력. | dumpsys.txt | |
| 설치된 모든 패키지 및 관련 배포 파일 목록. | packages.json | |
| 설치된 모든 APK 또는 시스템 앱으로 표시되지 않은 APK만의 사본. | ✅ | apks/* |
| 오프라인 분석을 위한 APEX 인벤토리 및 완전한 팩토리 및 설치된 APEX 컨테이너. | apex/* | |
| 침입 로깅 로그. 탐색 기록과 같은 개인 데이터를 포함합니다. | ✅ | intrusion_logs/* |
| 기존 루트 액세스가 가능한 경우 설치된 Magisk 모듈 메타데이터 및 상태 마커. | ✅ | magisk_modules/* |
기존 루트 액세스가 가능한 경우 /system/etc/init.d의 파일. | init_scripts/* | |
| 시스템의 파일 목록으로, 선택적으로 기기 내 해시를 포함합니다. | ✅ | files.json |
| 임시 폴더에서 사용 가능한 파일의 사본. | tmp/* | |
| 개인 데이터가 포함되지 않은 시스템 및 앱별 로그를 담은 버그 리포트. | bugreport.zip | |
새 리포트를 생성하기 전에 수집된 /bugreports/의 기존 버그 리포트 및 동반 파일. | bugreports/ |
기존 버그 리포트 수집은 ADB 셸의 권한을 사용하여 /bugreports/를 통해
접근 가능한 파일로 제한됩니다. 해당 디렉터리의 심볼릭 링크는 따라가지만,
그 내부의 심볼릭 링크는 따라가지 않습니다. 공유 저장소 및 제조사별 위치에
내보낸 사본은 검색하지 않습니다. Android는 보존 정책에 따라 이미 오래된
리포트를 삭제했을 수 있으므로, 디렉터리가 비어 있거나 없더라도 리포트가
한 번도 생성되지 않았다는 의미는 아닙니다. 기존 파일은 기기에서 삭제하지
않고 복사됩니다.
init_scripts 모듈은 /system/etc/init.d에 접근하기 전에 su를 사용하여 기존 루트 접근 권한을 확인합니다. 숨김 파일을 포함한 일반 파일을 재귀적으로 수집하여 상대 경로를 유지한 채 init_scripts/에 저장합니다. 스크립트는 절대 실행되지 않으며, 디렉터리 내의 심볼릭 링크는 따라가지 않습니다. 루트 접근 권한이 작동하지 않거나 해당 디렉터리가 없는 기기는 건너뜁니다. 이 파일들만 수집하려면 -module init_scripts를 사용하십시오.
apex 모듈은 완전한 .apex 및 .capex 파일과 기기의 APEX 인벤토리를 수집합니다. 이는 이후 MVT에서 분석할 수 있도록 서명 인증서, 공개 키 및 서명을 보존합니다. AndroidQF는 APEX 서명을 검증하거나, 키를 알려진 테스트 키와 비교하거나, 취약점을 평가하지 않습니다. 수집은 APK 다운로드 및 신뢰할 수 있는 인증서 제거 옵션과 독립적으로 실행되며, 아카이브 크기와 획득 시간을 상당히 증가시킬 수 있습니다. APEX 증거만 수집하려면 -module apex를 사용하십시오. 출력 형식, 루트 접근 권한 및 수집 제한 사항은 APEX 증거를 참조하십시오.
모든 획득에는 acquisition.json, 로그 출력이 생성된 경우 command.log, 그리고 hashes.csv도 포함됩니다. 해시 목록은 앞서 나온 각 평문 아카이브 항목의 SHA-256 다이제스트를 기록하며 자기 자신은 포함하지 않습니다. 실패한 기기 전송은 아카이브 항목으로 커밋되지 않습니다. acquisition.json은 실행된 모든 모듈의 상태(completed, partial 또는 failed), 타이밍 및 오류(있는 경우)를 기록합니다. 수집기가 배포된 경우, collector.sha256은 선택된 수집기 바이트의 SHA-256입니다(표준 빌드에 내장됨). 이는 files.json의 수집기 경로에 대한 선택적 기기 내 해시와 비교할 수 있으나, 그 자체로 기기 사본을 검증하지는 않습니다. 최종화된 부분 획득은 정상 완료 메시지를 출력하는 대신 실패 상태로 종료됩니다. 자세한 내용은 획득 아카이브를 참조하십시오.
androidqf 수집을 실행할 때 다음 옵션이 표시됩니다:
Would you like to take a backup of the device?
...
? Backup:
▸ Only SMS
Everything
No backup
이 옵션들은 백그라운드에서 adb backup 명령을 실행하여 기기에서 수집된 데이터를 나타냅니다. No backup을 선택하면 adb backup 명령이 실행되지 않습니다.
| 옵션 | 설명 |
|---|---|
| Only SMS | adb backup com.android.providers.telephony가 실행됩니다. com.android.providers.telephony의 데이터만 수집됩니다. 여기에는 SMS 데이터베이스가 포함됩니다. |
| Everything | adb backup -all이 실행됩니다. 이는 이 방법을 통해 데이터 백업을 명시적으로 허용한 앱만 백업하도록 요청합니다. Android 12+부터는 이 방법으로 거의 모든 앱에 대해 아무것도 추출하지 않습니다. |
| No backup | adb backup이 실행되지 않습니다 |
packages 모듈은 pm list users로 Android 사용자를 열거한 다음, 명시적인
--user 인수를 사용하여 패키지 UID, 설치 상태, 활성화 상태 및 APK 경로를
조회합니다. 기기의 포그라운드 사용자는 활성 상태로 유지됩니다. AndroidQF는
사용자를 시작, 잠금 해제 또는 전환하지 않습니다. 여러 사용자가 공유하는
패키지는 packages.json에서 user_id로 식별되는 사용자별 레코드를 하나씩
가집니다. installed 필드는 설치된 앱과 -u가 반환한 이전 기록을 구분합니다.
설치 상태를 조회할 수 없는 경우 이 필드는 생략됩니다.
package_users.json은 열거된 사용자 ID, 이름, 플래그, 실행 상태 및 패키지
인벤토리 결과를 기록합니다. 접근할 수 없는 사용자는 보고되며, 다른 사용자의
결과를 폐기하지 않습니다. 사용자 열거가 실패하면 AndroidQF는 명시적으로
식별된 현재 사용자를 시도하고 누락된 범위를 부분 수집으로 보고합니다.
사용자의 inventory_status가 partial인 경우 패키지 상태 불리언 값이
불완전할 수 있으므로 해당 error 필드를 참조하십시오.