본문 바로가기
보안 및 개발/MOBILE

[Android] OWASP UnCrackable 1

by CH@3M 2020. 1. 17.

apk는 다음링크에서 다운받을 수 있다.

https://github.com/OWASP/owasp-mstg/tree/master/Crackmes/Android/Level_01

app을 실행하면 루팅탐지 로직이 동작한다. 우선, 루팅탐지를 bypass 하는 방법을 찾아야한다.

JEB를 이용하여 MainActivity를 보면 다음과 같이 rooting 탐지하는 곳을 발견할 수 있다.

여기서 if((c.a()) || (c.b()) || (c.c())) 문을 false로 만족시켜 주거나, System.exit(0); 을 실행시키지 않거나 하는 방법이 있다. if문을 false로 맞췄는데 왜인지 되지않아서, System.exit 함수를 실행시키지 않는 방법으로 진행하려고 한다.

java에서 system 함수를 사용하기 위해서는 "java.lang.System" 클래스를 이용해야한다. 따라서 다음과 같은 스크립트를 작성할 수 있다. 

Java.perform(function () {
    var ex = Java.use("java.lang.System");

    ex.exit.implementation = function (v) {
    }
  });

hooking 후 OK 버튼을 클릭하면 앱이 종료되지 않고 그대로 살아있다!

이제 다음 단계이다.

여기서 Nope이 아니라 Success!가 뜨도록 해야한다. 

if(a.a(v4))를 만족해야하니, a.a클래스를 보도록 하자. a.a클래스에서 return 하는 것은 arg5.equals(new String(v0_2)) 이다. hooking 방법 중 한가지로, 이 값을 무조건 true로 변조하는 방법도 있다.

하지만 좀 더 보면, v0_2은 sg.vantagepoint.a.a.a(a.b(v0), v1); 값이다.

sg.vantagepoint.a.a.a() 에서 암호화 또는 복호화 해주는 것으로 보인다.

이 함수의 return 값을 한번 봐보면, 문자열을 발견할 수 있다. byte 형식으로 보이기 때문에 string으로 변환시켜주면 다음과 같이 코드를 짤 수 있다.

Java.perform(function () {
    var a = Java.use('sg.vantagepoint.a.a');
    var ex = Java.use("java.lang.System");

    ex.exit.implementation = function (v) {
        console.log("system exit bypass");
    }

    a.a.implementation = function(v1, v2) {
        var retval = this.a(v1, v2);

        var result='';
        for(var i=0; i<retval.length; i++) {
            result += String.fromCharCode(retval[i]);
        }
        console.log(result);

        return retval;  
    }
  });

smali 코드로 직접 수정하는 경우는 다음과 같이 쓸 수 있다고한다.

const-string v3, "ZZZZZZZZZZZZZZZZZZZZZZZZZZZZZ"
new-instance v4, Ljava/lang/String;
invoke-direct {v4,v0}, Ljava/lang/String;-><init>([B)V
invoke-static {v3,v4}, Landroid/util/Log;->d(Ljava/lang/String;Ljava/lang/String;)I

출처: https://rootable.tistory.com/entry/OWASP-UnCrackable-App-for-Android-Level-1 [Always Practice]

코드를 실행시키면 다음과 같이 문자열을 출력해준다.

이걸 입력하면 Success!

반응형