hacktricks/mobile-pentesting/android-app-pentesting/install-burp-certificate.md

11 KiB

Burp 인증서 설치

htARTE (HackTricks AWS Red Team Expert)에서 **제로부터 영웅까지 AWS 해킹 배우기**!

HackTricks를 지원하는 다른 방법:

가상 머신에서

먼저 Burp에서 Der 인증서를 다운로드해야 합니다. 이 작업은 Proxy --> Options --> Import / Export CA certificate 에서 수행할 수 있습니다.

Der 형식으로 인증서를 내보내고, 이를 Android가 이해할 수 있는 형식으로 변환해야 합니다. AVD의 Android 기계에 Burp 인증서를 구성하려면 이 기계를 -writable-system 옵션으로 실행해야 합니다.
예를 들어 다음과 같이 실행할 수 있습니다:

{% code overflow="wrap" %}

C:\Users\<UserName>\AppData\Local\Android\Sdk\tools\emulator.exe -avd "AVD9" -http-proxy 192.168.1.12:8080 -writable-system

{% endcode %}

그런 다음, 버프 인증서를 구성하려면:

{% code overflow="wrap" %}

openssl x509 -inform DER -in burp_cacert.der -out burp_cacert.pem
CERTHASHNAME="`openssl x509 -inform PEM -subject_hash_old -in burp_cacert.pem | head -1`.0"
mv burp_cacert.pem $CERTHASHNAME #Correct name
adb root && sleep 2 && adb remount #Allow to write on /syste
adb push $CERTHASHNAME /sdcard/ #Upload certificate
adb shell mv /sdcard/$CERTHASHNAME /system/etc/security/cacerts/ #Move to correct location
adb shell chmod 644 /system/etc/security/cacerts/$CERTHASHNAME #Assign privileges
adb reboot #Now, reboot the machine

{% endcode %}

기계가 다시 부팅을 완료하면 버프 인증서가 사용됩니다!

Magisc 사용

만약 Magisc로 기기를 루팅했고(어쩌면 에뮬레이터), 이전 단계를 따를 수 없는 경우에는 Burp 인증서를 설치할 수 없는데 파일 시스템이 읽기 전용이기 때문에 쓰기 가능하게 다시 마운트할 수 없는 경우 다른 방법이 있습니다.

이 비디오에서 설명된대로:

  1. CA 인증서 설치: DER Burp 인증서를 .crt로 확장자를 변경하여 모바일에 저장하고 인증서 설치 -> CA 인증서로 이동하여 Downloads 폴더에 저장합니다.
  • Trusted credentials -> USER로 이동하여 인증서가 올바르게 저장되었는지 확인합니다.
  1. 시스템 신뢰 설정: Magisc 모듈 MagiskTrustUserCerts (.zip 파일)을 다운로드하고, 폰에 드래그 앤 드롭하여 폰의 Magics 앱으로 이동하여 Modules 섹션으로 이동한 후 Install from storage를 클릭하여 .zip 모듈을 선택하고 설치한 후 폰을 재부팅합니다.
  • 재부팅 후 Trusted credentials -> SYSTEM으로 이동하여 Postswigger 인증서가 있는지 확인합니다.

Android 14 이후

최신 Android 14 릴리스에서 시스템 신뢰 CA 인증서의 처리 방식에 중요한 변화가 관찰되었습니다. 이전에는 이러한 인증서가 **/system/etc/security/cacerts/**에 위치하여 루트 권한을 가진 사용자가 접근 및 수정할 수 있어 시스템 전체에 즉시 적용할 수 있었습니다. 그러나 Android 14에서는 저장 위치가 **/apex/com.android.conscrypt/cacerts**로 이동되었는데, 이는 /apex 경로 내의 디렉토리로서 기본적으로 변경할 수 없습니다.

APEX cacerts 경로를 쓰기 가능하게 다시 마운트하려는 시도는 실패로 끝나며 시스템이 이러한 작업을 허용하지 않습니다. 심지어 디렉토리를 임시 파일 시스템(tmpfs)으로 언마운트하거나 오버레이하더라도 변경 사항이 시스템 전체에 적용되지 않고 애플리케이션이 파일 시스템 수준에서 변경되더라도 원래의 인증서 데이터에 계속 액세스합니다. 이러한 강건함은 /apex 마운트가 PRIVATE 전파로 구성되어 있기 때문에 발생하며, 이는 /apex 디렉토리 내의 변경 사항이 다른 프로세스에 영향을 미치지 않도록 보장합니다.

Android의 초기화는 init 프로세스를 포함하며, 운영 체제를 시작할 때 Zygote 프로세스도 시작됩니다. 이 프로세스는 새로운 마운트 네임스페이스를 사용하여 애플리케이션 프로세스를 시작하는데, 이는 /apex 마운트를 포함하고 있어 이 디렉토리의 변경 사항을 다른 프로세스와 격리시킵니다.

그러나 /apex 디렉토리 내의 시스템 신뢰 CA 인증서를 수정해야 하는 경우 해결책이 존재합니다. 이는 **/apex**를 수동으로 다시 마운트하여 PRIVATE 전파를 제거하여 쓰기 가능하게 만드는 것을 포함합니다. 이 프로세스에는 **/apex/com.android.conscrypt**의 내용을 다른 위치로 복사하고, /apex/com.android.conscrypt 디렉토리를 언마운트하여 읽기 전용 제약을 제거한 후 내용을 /apex 내의 원래 위치로 복원하는 것이 포함됩니다. 이 접근 방식은 시스템 충돌을 피하기 위해 신속한 조치가 필요합니다. 이러한 변경 사항을 시스템 전체에 적용하기 위해 system_server를 다시 시작하는 것이 권장됩니다. 이는 모든 애플리케이션을 다시 시작하고 시스템을 일관된 상태로 가져오기 때문입니다.

# Create a separate temp directory, to hold the current certificates
# Otherwise, when we add the mount we can't read the current certs anymore.
mkdir -p -m 700 /data/local/tmp/tmp-ca-copy

# Copy out the existing certificates
cp /apex/com.android.conscrypt/cacerts/* /data/local/tmp/tmp-ca-copy/

# Create the in-memory mount on top of the system certs folder
mount -t tmpfs tmpfs /system/etc/security/cacerts

# Copy the existing certs back into the tmpfs, so we keep trusting them
mv /data/local/tmp/tmp-ca-copy/* /system/etc/security/cacerts/

# Copy our new cert in, so we trust that too
mv $CERTIFICATE_PATH /system/etc/security/cacerts/

# Update the perms & selinux context labels
chown root:root /system/etc/security/cacerts/*
chmod 644 /system/etc/security/cacerts/*
chcon u:object_r:system_file:s0 /system/etc/security/cacerts/*

# Deal with the APEX overrides, which need injecting into each namespace:

# First we get the Zygote process(es), which launch each app
ZYGOTE_PID=$(pidof zygote || true)
ZYGOTE64_PID=$(pidof zygote64 || true)
# N.b. some devices appear to have both!

# Apps inherit the Zygote's mounts at startup, so we inject here to ensure
# all newly started apps will see these certs straight away:
for Z_PID in "$ZYGOTE_PID" "$ZYGOTE64_PID"; do
if [ -n "$Z_PID" ]; then
nsenter --mount=/proc/$Z_PID/ns/mnt -- \
/bin/mount --bind /system/etc/security/cacerts /apex/com.android.conscrypt/cacerts
fi
done

# Then we inject the mount into all already running apps, so they
# too see these CA certs immediately:

# Get the PID of every process whose parent is one of the Zygotes:
APP_PIDS=$(
echo "$ZYGOTE_PID $ZYGOTE64_PID" | \
xargs -n1 ps -o 'PID' -P | \
grep -v PID
)

# Inject into the mount namespace of each of those apps:
for PID in $APP_PIDS; do
nsenter --mount=/proc/$PID/ns/mnt -- \
/bin/mount --bind /system/etc/security/cacerts /apex/com.android.conscrypt/cacerts &
done
wait # Launched in parallel - wait for completion here

echo "System certificate injected"

NSEnter를 통한 바인드 마운트

  1. 쓰기 가능한 디렉토리 설정: 먼저, 기존의 APEX 시스템 인증서 디렉토리 위에 tmpfs를 마운트하여 쓰기 가능한 디렉토리를 설정합니다. 다음 명령을 사용하여 이를 달성할 수 있습니다:
mount -t tmpfs tmpfs /system/etc/security/cacerts
  1. CA 인증서 준비: 쓰기 가능한 디렉토리 설정 후, 사용할 CA 인증서를 이 디렉토리로 복사해야 합니다. 이는 /apex/com.android.conscrypt/cacerts/에서 기본 인증서를 복사하는 것을 포함할 수 있습니다. 이 인증서들의 권한과 SELinux 레이블을 적절히 조정하는 것이 중요합니다.
  2. Zygote를 위한 Bind Mounting: nsenter를 활용하여 Zygote의 마운트 네임스페이스에 진입합니다. Android 애플리케이션을 시작하는 프로세스인 Zygote는 이 단계를 통해 앞으로 시작되는 모든 애플리케이션이 새로 구성된 CA 인증서를 사용하도록 보장합니다. 사용되는 명령어는 다음과 같습니다:
nsenter --mount=/proc/$ZYGOTE_PID/ns/mnt -- /bin/mount --bind /system/etc/security/cacerts /apex/com.android.conscrypt/cacerts

이렇게하면 시작된 모든 새 앱이 업데이트된 CA 인증서 설정을 준수합니다.

  1. 실행 중인 앱에 변경 사항 적용하기: 이미 실행 중인 애플리케이션에 변경 사항을 적용하려면 nsenter를 다시 사용하여 각 앱의 네임스페이스에 개별적으로 들어가서 유사한 바인드 마운트를 수행합니다. 필요한 명령어는 다음과 같습니다:
nsenter --mount=/proc/$APP_PID/ns/mnt -- /bin/mount --bind /system/etc/security/cacerts /apex/com.android.conscrypt/cacerts
  1. 대체 접근 방법 - 소프트 리부팅: 대체 방법은 init 프로세스 (PID 1)에서 bind 마운트를 수행한 후 stop && start 명령으로 운영 체제를 소프트 리부팅하는 것을 포함합니다. 이 접근 방법은 모든 네임스페이스에 변경 사항을 전파하여 각 실행 중인 앱을 개별적으로 처리할 필요가 없게 합니다. 그러나 이 방법은 재부팅의 불편함 때문에 일반적으로 선호되지 않습니다.

참고 자료