DexPatcher: Java를 사용하여 Android APK 패치

click fraud protection

DexPatcher를 사용하면 개발자가 Java를 사용하여 APK를 패치할 수 있습니다. 여기에는 여러 가지 장점이 있으며 DexPatcher를 사용하는 것이 기존 Smali 접근 방식보다 훨씬 쉽습니다.

아마도 수정된 애플리케이션을 보거나 설치한 적이 있을 것입니다. 해상도에 맞게 패치된 다이얼러이거나 추가 기능이 포함된 사용자 정의 WhatsApp 버전일 수 있습니다. 그러면 개발자는 어떻게 그렇게 합니까? 애플리케이션의 소스 코드를 사용할 수 없는 경우가 많은데 어떻게 작동합니까? 먼저 이를 살펴본 다음 프로세스를 훨씬 쉽게 만드는 것을 목표로 하는 새로운 도구를 살펴보고 마지막으로 인기 있는 Xposed 프레임워크와 비교하여 어떻게 다른지 살펴보겠습니다.

APK가 일반적으로 수정되는 방식에 대해 들어보셨을 것입니다. 개발자는 APK에 직접 연결합니다. Smali의 모든 것을 보기 시작하고 Smali의 힘을 사용하여 사물을 수정할 수 있는 능력을 얻습니다. 원천. 작업이 완료되면 전화 통화만으로 충분하며, 그 시점에서 반짝이는 새 APK를 공유할 준비가 됩니다.

좀 더 진지하게… 처음부터 시작해 보겠습니다. Android 애플리케이션 모딩에 익숙하지 않다면 smali가 무엇인지 궁금할 것입니다. 개발자는 일반적으로 Java 프로그래밍 언어를 사용하여 Android 앱을 코딩합니다. 그러면 프로그램(컴파일러)이 해당 코드를 장치에 적합한 다른 형식으로 "변환"하여 애플리케이션 패키지(또는 APK) 내에 .dex 파일이 포함됩니다.

그 시점에서는 더 이상 원본 소스 코드에 액세스할 수 없습니다(개발자이거나 애플리케이션이 오픈 소스인 경우 제외). 그러나 APK는 기기에 설치되어 있기 때문에 가지고 있는 것입니다. 여기에서 dex 파일(보통 class.dex)을 가져온 다음 이를 이해할 수 있는 형식으로 다시 번역해 볼 수 있습니다. 더 읽기 쉽지만 충실한 번역으로서 smali가 등장하는 곳이 바로 여기입니다. 한 단계 더 나아가서 Java로 다시 변환할 수 있지만 해당 프로세스는 충분히 충실하지 않습니다. 결과는 이해할 수 있지만 일부 세부정보가 손실되므로 다시 반대 방향으로 번역할 수는 없습니다. 길을 따라. 즉, 기기에 설치하기 위해 APK로 다시 되돌릴 수 없기 때문에 어떤 수정을 가해도 소용이 없습니다. 적어도 많은 노력 없이는 불가능합니다.

smali/baksmali는 실제로 dex 형식의 어셈블러/디스어셈블러입니다. 이것이 바로 아이슬란드어에서 문자 그대로 의미하는 것입니다. 그러나 우리는 일반적으로 'Smali'라고 말할 때 smali가 이해하는 형식을 참조합니다. 모든 작은 세부 사항을 정의하는 것은 우리 인간에게 전부 필요하지 않더라도 따라서 정의하는 것보다 더 장황합니다. 자바). 또한 위의 설명은 약간 단순화되었지만 여전히 이해하기 쉬우면서도 밀접한 비유여야 합니다.

그러면 개발자가 (소스에 접근하지 않고) 앱을 수정하려면 어떻게 해야 할까요? 프로세스는 대략 다음과 같습니다.

  1. (웹이나 기기에서) APK를 받으세요.
  2. 다음과 같은 것을 사용하십시오 apktool APK를 Smali로 디컴파일합니다. (apktool smali/baksmali를 사용하지만 APK를 디컴파일하고 다시 빌드하는 것이 훨씬 쉬워지며 XML 파일과 같은 디코딩 리소스도 관리합니다.)
  3. APK에서classes.dex를 추출한 후 사용하세요. dex2jar 마지막으로 (불완전하고 종종 깨졌지만 대부분 이해할 수 있는) Java 코드를 얻기 위한 Java 디컴파일러입니다. (이것은 선택 사항이지만 Smali는 이해하기가 훨씬 어렵기 때문에 도움이 될 수 있습니다.)
  4. 수정할 내용을 식별합니다.
  5. 실제로 Smali 코드를 직접 편집하여 수정해 보세요.
  6. 또는 Java로 수정 사항을 작성하고 컴파일한 다음 Smali로 다시 디컴파일한 다음 결과 Smali 코드를 복사합니다.
  7. 모든 것이 끝나면 사용하십시오. apktool 다시 APK를 다시 빌드합니다.
  8. APK에 서명합니다(저자의 신원을 확인하기 위해). 모든 패키지에 서명해야 함) 마지막으로 설치합니다.

Smali 코드를 작성하는 것은 매우 어렵고 오류가 발생하기 쉽습니다. Smali에서는 작은 변경이 가능하지만 새로운 기능을 추가하는 것은 더 어렵습니다. 또한 컴파일 시간 오류가 발생하지 않으므로 오타도 런타임에만 감지될 수 있습니다. Smali 패치를 확장하고 공유하는 것도 문제가 될 수 있습니다. 차이점은 특정 APK 버전에 따라 매우 특정한 경향이 있기 때문입니다. 위에 설명된 프로세스의 일부를 더 쉽게 만드는 일부 도구가 있지만(버츄어스텐 스튜디오 생각해보면) 여전히 지루할 수 있습니다.

XDA 수석 회원의 DexPatcher 란촌 프로세스를 더 단순하게 만들고 개발자가 Smali를 다루는 것을 완전히 피할 수 있도록 하여 이러한 문제를 해결하는 것을 목표로 합니다. 대신 개발자는 Java만으로 패치를 작성하고 DexPatcher가 다른 모든 것을 처리하도록 할 수 있습니다.

이는 패치 파일을 쉽게 읽고 관리할 수 있다는 주요 이점이 있습니다. APK 패치도 일반적으로 더욱 편리해졌습니다. DexPatcher를 사용하는 방법에 대한 전체 예를 잠시 살펴보겠습니다. 먼저 DexPatcher가 제공하는 기능에 대한 간략한 개요는 다음과 같습니다.

  • 오픈 소스.
  • 크로스 플랫폼: Linux, Mac 및 Windows에서 실행되어야 합니다.
  • 패치 파일: 수정 사항은 독립적으로 공유할 수 있는 Java 패치 파일에 포함됩니다.
  • 자바: Smali가 아닙니다.

또한 빌드 시간 오류 검사의 이점을 얻을 수 있으므로 개발 주기 초기에 버그가 나타납니다. 컴파일된 Java는 일반적인 컴파일 시간 확인(원래 APK 기호에 대한 액세스 포함)을 제공하며 DexPatcher는 다음을 시행합니다. 패치 시 소스와 패치의 호환성, 유용한 정보 제공, 무언가를 하고 있는 것처럼 보일 때 경고 제공 합법적이지만 수상해요.

그 외에도 DexPatcher에는 다음과 같은 세트가 함께 제공됩니다. 도우미 스크립트 (Linux에서만 사용할 수 있지만 다른 플랫폼으로도 이식할 수 있습니다.) 이는 작업공간 설정, 대상 APK의 클래스 및 리소스 추출, 클래스를 Java( CFR 자바 디컴파일러 후자에 사용됨) 완료되면 마지막으로 패치된 APK를 빌드하고 서명합니다.

(Linux의 경우) 예를 살펴보겠습니다.

DexPatcher 스크립트 설치

$# Make a directory where we can test stuff out and enter it. 

$ mkdir xda-test

$cd xda-test

$ git clone https://github.com/Lanchon/DexPatcher-scripts.git dexpatcher # Clone the DexPatcher helper scripts repo.

$cd dexpatcher

$ chmod +x dxp-* # Not necessary, but for clarity: we need to make sure the files we'll call later are executable.

DexPatcher 스크립트 구성

열려 있는 dxp.config 즐겨 사용하는 텍스트 편집기에서 시스템에 맞게 필요한 변수를 변경했는지 확인하세요. 대신 Android SDK의 설치 위치를 가리키도록 다음 줄만 변경하면 됩니다.

dxp_android_sdk_dir=(~/android/sdk)

(DexPatcher는 사용 가능한 가장 높은 플랫폼 버전을 자동으로 선택합니다. 또한 번들로 제공되는 기본값 대신 일부 도구의 자체 버전을 사용하도록 다른 구성 옵션을 수정할 수도 있습니다.)

쉽게 접근할 수 있도록 다음을 추가할 수 있습니다. 파견자 우리의 디렉토리 , 또는 심지어 다른 심볼릭 링크 dxp-* 이미 있는 위치에 스크립트를 , 와 같은 ~/빈:

export PATH=$PWD:$PATH

애플리케이션 수정

이 예에서는 간단한 오픈 소스 애플리케이션을 사용합니다. 물론 이런 특별한 경우에는 소스 코드를 직접 패치하는 것도 가능하겠지만, 그건 전혀 재미가 없습니다!

귀하의 장치에 대한 몇 가지 세부 정보를 보여주는 응용 프로그램인 Basil2style의 "ID 받기" 응용 프로그램을 사용하겠습니다. 우리의 목표는 "장치 ID"에 대한 "복사" 버튼을 수정하고 대신 이 ID를 공유하도록 하는 것입니다.

  • 먼저 수정할 APK를 다운로드하겠습니다. 신분증 받기.
  • 응용 프로그램을 디컴파일합니다.
  • 나중에 APK에 서명하는 데 사용할 서명 키를 만듭니다.

도우미 스크립트를 사용하여 셸을 통해 이 모든 작업을 수행할 수도 있습니다.

$cd dexpatcher # Go to our working directory. 

$ curl -O https://f-droid.org/repo/makeinfo.com.getid_1.apk # Download the APK.

$ dxp-setup-for-apk makeinfo.com.getid_1.apk # Unpack and decompile the APK.

$cd makeinfo.com.getid_1 # Go to the newly created directory where everything is unpacked/decompiled to.

$ dxp-create-keystore # Create the APK signing key. Press 6 times (or fill out the info), then "yes".

거기에는 몇 가지 다른 디렉토리가 있습니다.

  • 풀다: 여기서 디코딩된 리소스와 Smali를 찾을 수 있습니다. apktool.
  • 소스: 디렉토리가 비어 있습니다. 여기에 패치 파일을 배치할 것입니다.
  • src-cfr: 여기가 바로 여기야 CFR 앱을 디컴파일했습니다(오류와 함께). 무엇을 변경할지 결정하기 위해 살펴보는 것이 좋습니다(위의 디코드 디렉터리에서 리소스와 해당 ID가 필요할 수도 있지만 이 특정 예에서는 필요하지 않음).
  • src-cfr-노드코드: 위와 동일하지만 빈 스텁(코드 없음, 뼈대만 포함)만 포함합니다. 잠시 후에 살펴보겠지만 이 파일을 패치의 기초로 사용할 수 있습니다.

이전에 언급했듯이 장치 ID "복사" 버튼을 대신 ID 텍스트를 공유하도록 변경하려고 합니다. 소스 코드를 살펴보면 장치 ID 복사 버튼(device_copy) 클릭 시 이벤트는 익명 클래스에 의해 처리됩니다. src-cfr/makeinfo/com/getid/MainActivity.java. 여기에서 수정할 수 있지만 일반적으로 익명 클래스에는 숫자 이름(MainClassName$SomeNumber, 예를 들어 메인활동$3) 버전 간에 예기치 않게 변경될 수 있습니다.

대신, 우리는 주요 활동 수업. 먼저 "스켈레톤" 버전을 복사해 보겠습니다. src-cfr-nocode/makeinfo/com/getid/MainActivity.java 에게 src/makeinfo/com/getid/MainActivity.java (기억 소스 우리 패치가 있을 곳입니다). (원하는 경우 전체 코드가 포함된 버전을 복사할 수도 있습니다. 이는 순전히 취향의 문제입니다.)

이제 다음과 같이 편집할 수 있습니다.

  • DexPatcher 주석에 필요한 가져오기를 추가합니다.
importlanchon.dexpatcher.annotation.*;
  • 수업을 편집하고 있음을 나타내는 태그를 추가합니다. 또한 패치 클래스 구성원의 기본 작업을 다음과 같이 설정했습니다. 무시하다즉, 멤버는 Java 컴파일 중에 코드에서 참조되지만 DexPatcher에서는 무시됩니다.
@DexEdit(defaultAction=DexAction.IGNORE)

publicclassMainActivity

// The reference to ActionBarActivity will be satisfied by symbols

// extracted from the app when we build the patch.

extendsActionBarActivity{

  • 또한 생성자에 빈 본문을 추가하고 onCreate method 및 우리가 사용할 다른 모든 방법(패치가 실제로 적용될 때 무시된다는 점을 기억하십시오. 필요한 경우 여기에서 참조할 수 있도록 추가하는 것뿐입니다). 당신은 또한 토종의 대신 키워드.
  • 궁금하다면 이 시점에서 이미 패치를 빌드할 수 있습니다.
    $ dxp-make # Output: `patched.apk`.
    아주 간단하죠? 하지만 계속 진행해 보세요. 아직 끝나지 않았습니다.
  • 편집하자 onCreate 이제 자신의 것을 설정 OnClickListener 그러면 장치 ID를 클립보드에 복사하는 대신 공유할 수 있습니다.
    // Rename the target method so that we can still call it (the original)// if needed.@DexEdit(target="onCreate")protectedvoidsource_onCreate(Bundlevar1){}// Add our new custom method.@Override@DexAddprotectedvoidonCreate(Bundlevar1){// Call the original method:source_onCreate(var1);// Replace the text and handler:device_copy.setText("Share");device_copy.setOnClickListener(newDeviceCopyOnClick());}// Note that we don't use an anonymous class to avoid nameclashing with// MainActivity$1, which already exists.// We also could've defined a nested MainActivity.Patch class and used// an anonymous class in MainActivity.Patch.onCreate(), and then called// MainActivity.Patch.onCreate() from MainActivity.onCreate().@DexAddclassDeviceCopyOnClickimplementsView.OnClickListener{@OverridepublicvoidonClick(Viewobject){if(MainActivity.this.val){Intentintent=newIntent(Intent.ACTION_SEND);intent.setType("text/plain");intent.putExtra(Intent.EXTRA_SUBJECT,"Device ID");intent.putExtra(Intent.EXTRA_TEXT,device.getText().toString());startActivity(Intent.createChooser(intent,"Share Device ID"));}else{Toast.makeText(MainActivity.this.getApplicationContext(),"Nothing to Share",0).show();}}}
  • 이제 끝난 것 같습니다! 전체 패치는 다음과 같습니다. 이것. 이제 패치된 APK를 빌드하고 설치할 수 있습니다.
    $ dxp-make$ adb install patched.apk
  • 결과를 살펴보겠습니다.

(샘플 코드에 도움을 주신 Lanchon에게 감사드립니다!)

Xposed는 엄청난 인기를 누리고 있으며, 그럴 만한 이유가 있습니다. Xposed를 사용하면 개발자와 사용자 모두가 모드를 훨씬 쉽게 구축, 공유 및 설치할 수 있습니다. DexPatcher와 Xposed 사이에는 몇 가지 차이점이 있어 일부는 다른 것보다 선호할 수 있습니다.

  1. Xposed는 런타임에 메서드를 연결하고 개발자가 메서드 전, 후 또는 대신에 작업을 수행할 수 있도록 함으로써 마술을 부립니다. 반면 DexPatcher는 런타임에 앞서 모든 것을 수정하고 독립형 수정 APK를 생성합니다. -- 메소드 전, 후 또는 대신에 코드를 실행하는 것이 여전히 가능하며 실제로는 추가 작업이 있습니다. 자유.
  2. 독립형 APK를 생성한다는 것은 외부 프레임워크에 의존하지 않는다는 것을 의미합니다. 이는 또한 사용자 앱을 수정하는 데 루트가 필요하지 않음을 의미합니다.
  3. DexPatcher를 사용하여 새 APK를 생성했으므로 다르게 서명됩니다. 이는 사용자가 원본 작성자로부터 공식 업데이트를 받을 수 없으며 서명이 확인되면 Google Apps와 같은 앱에 일부 문제가 발생할 수 있음을 의미합니다.
  4. 모듈과 DexPatcher 패치의 소스 코드는 모두 쉽게 배포하고 수정할 수 있습니다. 또한 각각에 대해 조금 익숙해지면 많은 유사점을 공유합니다.

우리는 DexPatcher에 대해 충분히 이야기했습니다. 이제 당신이 시험해 볼 차례입니다. DexPatcher 포럼 스레드 바로 시작하려면!