Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- /*
- * This script combines, fixes & extends a long list of other scripts, most notably including:
- *
- * - https://codeshare.frida.re/@akabe1/frida-multiple-unpinning/
- * - https://codeshare.frida.re/@avltree9798/universal-android-ssl-pinning-bypass/
- * - https://pastebin.com/TVJD63uM
- * - https://codeshare.frida.re/@dzonerzy/fridantiroot/
- * - https://github.com/AshenOneYe/FridaAntiRootDetection/blob/main/antiroot.js
- */
- setTimeout(function () {
- Java.perform(function () {
- console.log("---");
- console.log("Unpinning Android app...");
- /// -- Generic hook to protect against SSLPeerUnverifiedException -- ///
- // In some cases, with unusual cert pinning approaches, or heavy obfuscation, we can't
- // match the real method & package names. This is a problem! Fortunately, we can still
- // always match built-in types, so here we spot all failures that use the built-in cert
- // error type (notably this includes OkHttp), and after the first failure, we dynamically
- // generate & inject a patch to completely disable the method that threw the error.
- try {
- const UnverifiedCertError = Java.use('javax.net.ssl.SSLPeerUnverifiedException');
- UnverifiedCertError.$init.implementation = function (str) {
- console.log(' --> Unexpected SSL verification failure, adding dynamic patch...');
- try {
- const stackTrace = Java.use('java.lang.Thread').currentThread().getStackTrace();
- const exceptionStackIndex = stackTrace.findIndex(stack =>
- stack.getClassName() === "javax.net.ssl.SSLPeerUnverifiedException"
- );
- const callingFunctionStack = stackTrace[exceptionStackIndex + 1];
- const className = callingFunctionStack.getClassName();
- const methodName = callingFunctionStack.getMethodName();
- console.log(` Thrown by ${className}->${methodName}`);
- const callingClass = Java.use(className);
- const callingMethod = callingClass[methodName];
- if (callingMethod.implementation) return; // Already patched by Frida - skip it
- console.log(' Attempting to patch automatically...');
- const returnTypeName = callingMethod.returnType.type;
- callingMethod.implementation = function () {
- console.log(` --> Bypassing ${className}->${methodName} (automatic exception patch)`);
- // This is not a perfect fix! Most unknown cases like this are really just
- // checkCert(cert) methods though, so doing nothing is perfect, and if we
- // do need an actual return value then this is probably the best we can do,
- // and at least we're logging the method name so you can patch it manually:
- if (returnTypeName === 'void') {
- return;
- } else {
- return null;
- }
- };
- console.log(` [+] ${className}->${methodName} (automatic exception patch)`);
- } catch (e) {
- console.log(' [ ] Failed to automatically patch failure');
- }
- return this.$init(str);
- };
- console.log('[+] SSLPeerUnverifiedException auto-patcher');
- } catch (err) {
- console.log('[ ] SSLPeerUnverifiedException auto-patcher');
- }
- /// -- Specific targeted hooks: -- ///
- // HttpsURLConnection
- try {
- const HttpsURLConnection = Java.use("javax.net.ssl.HttpsURLConnection");
- HttpsURLConnection.setDefaultHostnameVerifier.implementation = function (hostnameVerifier) {
- console.log(' --> Bypassing HttpsURLConnection (setDefaultHostnameVerifier)');
- return; // Do nothing, i.e. don't change the hostname verifier
- };
- console.log('[+] HttpsURLConnection (setDefaultHostnameVerifier)');
- } catch (err) {
- console.log('[ ] HttpsURLConnection (setDefaultHostnameVerifier)');
- }
- try {
- const HttpsURLConnection = Java.use("javax.net.ssl.HttpsURLConnection");
- HttpsURLConnection.setSSLSocketFactory.implementation = function (SSLSocketFactory) {
- console.log(' --> Bypassing HttpsURLConnection (setSSLSocketFactory)');
- return; // Do nothing, i.e. don't change the SSL socket factory
- };
- console.log('[+] HttpsURLConnection (setSSLSocketFactory)');
- } catch (err) {
- console.log('[ ] HttpsURLConnection (setSSLSocketFactory)');
- }
- try {
- const HttpsURLConnection = Java.use("javax.net.ssl.HttpsURLConnection");
- HttpsURLConnection.setHostnameVerifier.implementation = function (hostnameVerifier) {
- console.log(' --> Bypassing HttpsURLConnection (setHostnameVerifier)');
- return; // Do nothing, i.e. don't change the hostname verifier
- };
- console.log('[+] HttpsURLConnection (setHostnameVerifier)');
- } catch (err) {
- console.log('[ ] HttpsURLConnection (setHostnameVerifier)');
- }
- // SSLContext
- try {
- const X509TrustManager = Java.use('javax.net.ssl.X509TrustManager');
- const SSLContext = Java.use('javax.net.ssl.SSLContext');
- const TrustManager = Java.registerClass({
- // Implement a custom TrustManager
- name: 'dev.asd.test.TrustManager',
- implements: [X509TrustManager],
- methods: {
- checkClientTrusted: function (chain, authType) { },
- checkServerTrusted: function (chain, authType) { },
- getAcceptedIssuers: function () { return []; }
- }
- });
- // Prepare the TrustManager array to pass to SSLContext.init()
- const TrustManagers = [TrustManager.$new()];
- // Get a handle on the init() on the SSLContext class
- const SSLContext_init = SSLContext.init.overload(
- '[Ljavax.net.ssl.KeyManager;', '[Ljavax.net.ssl.TrustManager;', 'java.security.SecureRandom'
- );
- // Override the init method, specifying the custom TrustManager
- SSLContext_init.implementation = function (keyManager, trustManager, secureRandom) {
- console.log(' --> Bypassing Trustmanager (Android < 7) request');
- SSLContext_init.call(this, keyManager, TrustManagers, secureRandom);
- };
- console.log('[+] SSLContext');
- } catch (err) {
- console.log('[ ] SSLContext');
- }
- // TrustManagerImpl (Android > 7)
- try {
- const array_list = Java.use("java.util.ArrayList");
- const TrustManagerImpl = Java.use('com.android.org.conscrypt.TrustManagerImpl');
- // This step is notably what defeats the most common case: network security config
- TrustManagerImpl.checkTrustedRecursive.implementation = function(a1, a2, a3, a4, a5, a6) {
- console.log(' --> Bypassing TrustManagerImpl checkTrusted ');
- return array_list.$new();
- }
- TrustManagerImpl.verifyChain.implementation = function (untrustedChain, trustAnchorChain, host, clientAuth, ocspData, tlsSctData) {
- console.log(' --> Bypassing TrustManagerImpl verifyChain: ' + host);
- return untrustedChain;
- };
- console.log('[+] TrustManagerImpl');
- } catch (err) {
- console.log('[ ] TrustManagerImpl');
- }
- // OkHTTPv3 (quadruple bypass)
- try {
- // Bypass OkHTTPv3 {1}
- const okhttp3_Activity_1 = Java.use('okhttp3.CertificatePinner');
- okhttp3_Activity_1.check.overload('java.lang.String', 'java.util.List').implementation = function (a, b) {
- console.log(' --> Bypassing OkHTTPv3 (list): ' + a);
- return;
- };
- console.log('[+] OkHTTPv3 (list)');
- } catch (err) {
- console.log('[ ] OkHTTPv3 (list)');
- }
- try {
- // Bypass OkHTTPv3 {2}
- // This method of CertificatePinner.check could be found in some old Android app
- const okhttp3_Activity_2 = Java.use('okhttp3.CertificatePinner');
- okhttp3_Activity_2.check.overload('java.lang.String', 'java.security.cert.Certificate').implementation = function (a, b) {
- console.log(' --> Bypassing OkHTTPv3 (cert): ' + a);
- return;
- };
- console.log('[+] OkHTTPv3 (cert)');
- } catch (err) {
- console.log('[ ] OkHTTPv3 (cert)');
- }
- try {
- // Bypass OkHTTPv3 {3}
- const okhttp3_Activity_3 = Java.use('okhttp3.CertificatePinner');
- okhttp3_Activity_3.check.overload('java.lang.String', '[Ljava.security.cert.Certificate;').implementation = function (a, b) {
- console.log(' --> Bypassing OkHTTPv3 (cert array): ' + a);
- return;
- };
- console.log('[+] OkHTTPv3 (cert array)');
- } catch (err) {
- console.log('[ ] OkHTTPv3 (cert array)');
- }
- try {
- // Bypass OkHTTPv3 {4}
- const okhttp3_Activity_4 = Java.use('okhttp3.CertificatePinner');
- okhttp3_Activity_4['check$okhttp'].implementation = function (a, b) {
- console.log(' --> Bypassing OkHTTPv3 ($okhttp): ' + a);
- return;
- };
- console.log('[+] OkHTTPv3 ($okhttp)');
- } catch (err) {
- console.log('[ ] OkHTTPv3 ($okhttp)');
- }
- // Trustkit (triple bypass)
- try {
- // Bypass Trustkit {1}
- const trustkit_Activity_1 = Java.use('com.datatheorem.android.trustkit.pinning.OkHostnameVerifier');
- trustkit_Activity_1.verify.overload('java.lang.String', 'javax.net.ssl.SSLSession').implementation = function (a, b) {
- console.log(' --> Bypassing Trustkit OkHostnameVerifier(SSLSession): ' + a);
- return true;
- };
- console.log('[+] Trustkit OkHostnameVerifier(SSLSession)');
- } catch (err) {
- console.log('[ ] Trustkit OkHostnameVerifier(SSLSession)');
- }
- try {
- // Bypass Trustkit {2}
- const trustkit_Activity_2 = Java.use('com.datatheorem.android.trustkit.pinning.OkHostnameVerifier');
- trustkit_Activity_2.verify.overload('java.lang.String', 'java.security.cert.X509Certificate').implementation = function (a, b) {
- console.log(' --> Bypassing Trustkit OkHostnameVerifier(cert): ' + a);
- return true;
- };
- console.log('[+] Trustkit OkHostnameVerifier(cert)');
- } catch (err) {
- console.log('[ ] Trustkit OkHostnameVerifier(cert)');
- }
- try {
- // Bypass Trustkit {3}
- const trustkit_PinningTrustManager = Java.use('com.datatheorem.android.trustkit.pinning.PinningTrustManager');
- trustkit_PinningTrustManager.checkServerTrusted.implementation = function () {
- console.log(' --> Bypassing Trustkit PinningTrustManager');
- };
- console.log('[+] Trustkit PinningTrustManager');
- } catch (err) {
- console.log('[ ] Trustkit PinningTrustManager');
- }
- // Appcelerator Titanium
- try {
- const appcelerator_PinningTrustManager = Java.use('appcelerator.https.PinningTrustManager');
- appcelerator_PinningTrustManager.checkServerTrusted.implementation = function () {
- console.log(' --> Bypassing Appcelerator PinningTrustManager');
- };
- console.log('[+] Appcelerator PinningTrustManager');
- } catch (err) {
- console.log('[ ] Appcelerator PinningTrustManager');
- }
- // OpenSSLSocketImpl Conscrypt
- try {
- const OpenSSLSocketImpl = Java.use('com.android.org.conscrypt.OpenSSLSocketImpl');
- OpenSSLSocketImpl.verifyCertificateChain.implementation = function (certRefs, JavaObject, authMethod) {
- console.log(' --> Bypassing OpenSSLSocketImpl Conscrypt');
- };
- console.log('[+] OpenSSLSocketImpl Conscrypt');
- } catch (err) {
- console.log('[ ] OpenSSLSocketImpl Conscrypt');
- }
- // OpenSSLEngineSocketImpl Conscrypt
- try {
- const OpenSSLEngineSocketImpl_Activity = Java.use('com.android.org.conscrypt.OpenSSLEngineSocketImpl');
- OpenSSLEngineSocketImpl_Activity.verifyCertificateChain.overload('[Ljava.lang.Long;', 'java.lang.String').implementation = function (a, b) {
- console.log(' --> Bypassing OpenSSLEngineSocketImpl Conscrypt: ' + b);
- };
- console.log('[+] OpenSSLEngineSocketImpl Conscrypt');
- } catch (err) {
- console.log('[ ] OpenSSLEngineSocketImpl Conscrypt');
- }
- // OpenSSLSocketImpl Apache Harmony
- try {
- const OpenSSLSocketImpl_Harmony = Java.use('org.apache.harmony.xnet.provider.jsse.OpenSSLSocketImpl');
- OpenSSLSocketImpl_Harmony.verifyCertificateChain.implementation = function (asn1DerEncodedCertificateChain, authMethod) {
- console.log(' --> Bypassing OpenSSLSocketImpl Apache Harmony');
- };
- console.log('[+] OpenSSLSocketImpl Apache Harmony');
- } catch (err) {
- console.log('[ ] OpenSSLSocketImpl Apache Harmony');
- }
- // PhoneGap sslCertificateChecker (https://github.com/EddyVerbruggen/SSLCertificateChecker-PhoneGap-Plugin)
- try {
- const phonegap_Activity = Java.use('nl.xservices.plugins.sslCertificateChecker');
- phonegap_Activity.execute.overload('java.lang.String', 'org.json.JSONArray', 'org.apache.cordova.CallbackContext').implementation = function (a, b, c) {
- console.log(' --> Bypassing PhoneGap sslCertificateChecker: ' + a);
- return true;
- };
- console.log('[+] PhoneGap sslCertificateChecker');
- } catch (err) {
- console.log('[ ] PhoneGap sslCertificateChecker');
- }
- // IBM MobileFirst pinTrustedCertificatePublicKey (double bypass)
- try {
- // Bypass IBM MobileFirst {1}
- const WLClient_Activity_1 = Java.use('com.worklight.wlclient.api.WLClient');
- WLClient_Activity_1.getInstance().pinTrustedCertificatePublicKey.overload('java.lang.String').implementation = function (cert) {
- console.log(' --> Bypassing IBM MobileFirst pinTrustedCertificatePublicKey (string): ' + cert);
- return;
- };
- console.log('[+] IBM MobileFirst pinTrustedCertificatePublicKey (string)');
- } catch (err) {
- console.log('[ ] IBM MobileFirst pinTrustedCertificatePublicKey (string)');
- }
- try {
- // Bypass IBM MobileFirst {2}
- const WLClient_Activity_2 = Java.use('com.worklight.wlclient.api.WLClient');
- WLClient_Activity_2.getInstance().pinTrustedCertificatePublicKey.overload('[Ljava.lang.String;').implementation = function (cert) {
- console.log(' --> Bypassing IBM MobileFirst pinTrustedCertificatePublicKey (string array): ' + cert);
- return;
- };
- console.log('[+] IBM MobileFirst pinTrustedCertificatePublicKey (string array)');
- } catch (err) {
- console.log('[ ] IBM MobileFirst pinTrustedCertificatePublicKey (string array)');
- }
- // IBM WorkLight (ancestor of MobileFirst) HostNameVerifierWithCertificatePinning (quadruple bypass)
- try {
- // Bypass IBM WorkLight {1}
- const worklight_Activity_1 = Java.use('com.worklight.wlclient.certificatepinning.HostNameVerifierWithCertificatePinning');
- worklight_Activity_1.verify.overload('java.lang.String', 'javax.net.ssl.SSLSocket').implementation = function (a, b) {
- console.log(' --> Bypassing IBM WorkLight HostNameVerifierWithCertificatePinning (SSLSocket): ' + a);
- return;
- };
- console.log('[+] IBM WorkLight HostNameVerifierWithCertificatePinning (SSLSocket)');
- } catch (err) {
- console.log('[ ] IBM WorkLight HostNameVerifierWithCertificatePinning (SSLSocket)');
- }
- try {
- // Bypass IBM WorkLight {2}
- const worklight_Activity_2 = Java.use('com.worklight.wlclient.certificatepinning.HostNameVerifierWithCertificatePinning');
- worklight_Activity_2.verify.overload('java.lang.String', 'java.security.cert.X509Certificate').implementation = function (a, b) {
- console.log(' --> Bypassing IBM WorkLight HostNameVerifierWithCertificatePinning (cert): ' + a);
- return;
- };
- console.log('[+] IBM WorkLight HostNameVerifierWithCertificatePinning (cert)');
- } catch (err) {
- console.log('[ ] IBM WorkLight HostNameVerifierWithCertificatePinning (cert)');
- }
- try {
- // Bypass IBM WorkLight {3}
- const worklight_Activity_3 = Java.use('com.worklight.wlclient.certificatepinning.HostNameVerifierWithCertificatePinning');
- worklight_Activity_3.verify.overload('java.lang.String', '[Ljava.lang.String;', '[Ljava.lang.String;').implementation = function (a, b) {
- console.log(' --> Bypassing IBM WorkLight HostNameVerifierWithCertificatePinning (string string): ' + a);
- return;
- };
- console.log('[+] IBM WorkLight HostNameVerifierWithCertificatePinning (string string)');
- } catch (err) {
- console.log('[ ] IBM WorkLight HostNameVerifierWithCertificatePinning (string string)');
- }
- try {
- // Bypass IBM WorkLight {4}
- const worklight_Activity_4 = Java.use('com.worklight.wlclient.certificatepinning.HostNameVerifierWithCertificatePinning');
- worklight_Activity_4.verify.overload('java.lang.String', 'javax.net.ssl.SSLSession').implementation = function (a, b) {
- console.log(' --> Bypassing IBM WorkLight HostNameVerifierWithCertificatePinning (SSLSession): ' + a);
- return true;
- };
- console.log('[+] IBM WorkLight HostNameVerifierWithCertificatePinning (SSLSession)');
- } catch (err) {
- console.log('[ ] IBM WorkLight HostNameVerifierWithCertificatePinning (SSLSession)');
- }
- // Conscrypt CertPinManager
- try {
- const conscrypt_CertPinManager_Activity = Java.use('com.android.org.conscrypt.CertPinManager');
- conscrypt_CertPinManager_Activity.isChainValid.overload('java.lang.String', 'java.util.List').implementation = function (a, b) {
- console.log(' --> Bypassing Conscrypt CertPinManager: ' + a);
- return true;
- };
- console.log('[+] Conscrypt CertPinManager');
- } catch (err) {
- console.log('[ ] Conscrypt CertPinManager');
- }
- // CWAC-Netsecurity (unofficial back-port pinner for Android<4.2) CertPinManager
- try {
- const cwac_CertPinManager_Activity = Java.use('com.commonsware.cwac.netsecurity.conscrypt.CertPinManager');
- cwac_CertPinManager_Activity.isChainValid.overload('java.lang.String', 'java.util.List').implementation = function (a, b) {
- console.log(' --> Bypassing CWAC-Netsecurity CertPinManager: ' + a);
- return true;
- };
- console.log('[+] CWAC-Netsecurity CertPinManager');
- } catch (err) {
- console.log('[ ] CWAC-Netsecurity CertPinManager');
- }
- // Worklight Androidgap WLCertificatePinningPlugin
- try {
- const androidgap_WLCertificatePinningPlugin_Activity = Java.use('com.worklight.androidgap.plugin.WLCertificatePinningPlugin');
- androidgap_WLCertificatePinningPlugin_Activity.execute.overload('java.lang.String', 'org.json.JSONArray', 'org.apache.cordova.CallbackContext').implementation = function (a, b, c) {
- console.log(' --> Bypassing Worklight Androidgap WLCertificatePinningPlugin: ' + a);
- return true;
- };
- console.log('[+] Worklight Androidgap WLCertificatePinningPlugin');
- } catch (err) {
- console.log('[ ] Worklight Androidgap WLCertificatePinningPlugin');
- }
- // Netty FingerprintTrustManagerFactory
- try {
- const netty_FingerprintTrustManagerFactory = Java.use('io.netty.handler.ssl.util.FingerprintTrustManagerFactory');
- netty_FingerprintTrustManagerFactory.checkTrusted.implementation = function (type, chain) {
- console.log(' --> Bypassing Netty FingerprintTrustManagerFactory');
- };
- console.log('[+] Netty FingerprintTrustManagerFactory');
- } catch (err) {
- console.log('[ ] Netty FingerprintTrustManagerFactory');
- }
- // Squareup CertificatePinner [OkHTTP<v3] (double bypass)
- try {
- // Bypass Squareup CertificatePinner {1}
- const Squareup_CertificatePinner_Activity_1 = Java.use('com.squareup.okhttp.CertificatePinner');
- Squareup_CertificatePinner_Activity_1.check.overload('java.lang.String', 'java.security.cert.Certificate').implementation = function (a, b) {
- console.log(' --> Bypassing Squareup CertificatePinner (cert): ' + a);
- return;
- };
- console.log('[+] Squareup CertificatePinner (cert)');
- } catch (err) {
- console.log('[ ] Squareup CertificatePinner (cert)');
- }
- try {
- // Bypass Squareup CertificatePinner {2}
- const Squareup_CertificatePinner_Activity_2 = Java.use('com.squareup.okhttp.CertificatePinner');
- Squareup_CertificatePinner_Activity_2.check.overload('java.lang.String', 'java.util.List').implementation = function (a, b) {
- console.log(' --> Bypassing Squareup CertificatePinner (list): ' + a);
- return;
- };
- console.log('[+] Squareup CertificatePinner (list)');
- } catch (err) {
- console.log('[ ] Squareup CertificatePinner (list)');
- }
- // Squareup OkHostnameVerifier [OkHTTP v3] (double bypass)
- try {
- // Bypass Squareup OkHostnameVerifier {1}
- const Squareup_OkHostnameVerifier_Activity_1 = Java.use('com.squareup.okhttp.internal.tls.OkHostnameVerifier');
- Squareup_OkHostnameVerifier_Activity_1.verify.overload('java.lang.String', 'java.security.cert.X509Certificate').implementation = function (a, b) {
- console.log(' --> Bypassing Squareup OkHostnameVerifier (cert): ' + a);
- return true;
- };
- console.log('[+] Squareup OkHostnameVerifier (cert)');
- } catch (err) {
- console.log('[ ] Squareup OkHostnameVerifier (cert)');
- }
- try {
- // Bypass Squareup OkHostnameVerifier {2}
- const Squareup_OkHostnameVerifier_Activity_2 = Java.use('com.squareup.okhttp.internal.tls.OkHostnameVerifier');
- Squareup_OkHostnameVerifier_Activity_2.verify.overload('java.lang.String', 'javax.net.ssl.SSLSession').implementation = function (a, b) {
- console.log(' --> Bypassing Squareup OkHostnameVerifier (SSLSession): ' + a);
- return true;
- };
- console.log('[+] Squareup OkHostnameVerifier (SSLSession)');
- } catch (err) {
- console.log('[ ] Squareup OkHostnameVerifier (SSLSession)');
- }
- // Android WebViewClient (double bypass)
- try {
- // Bypass WebViewClient {1} (deprecated from Android 6)
- const AndroidWebViewClient_Activity_1 = Java.use('android.webkit.WebViewClient');
- AndroidWebViewClient_Activity_1.onReceivedSslError.overload('android.webkit.WebView', 'android.webkit.SslErrorHandler', 'android.net.http.SslError').implementation = function (obj1, obj2, obj3) {
- console.log(' --> Bypassing Android WebViewClient (SslErrorHandler)');
- };
- console.log('[+] Android WebViewClient (SslErrorHandler)');
- } catch (err) {
- console.log('[ ] Android WebViewClient (SslErrorHandler)');
- }
- try {
- // Bypass WebViewClient {2}
- const AndroidWebViewClient_Activity_2 = Java.use('android.webkit.WebViewClient');
- AndroidWebViewClient_Activity_2.onReceivedSslError.overload('android.webkit.WebView', 'android.webkit.WebResourceRequest', 'android.webkit.WebResourceError').implementation = function (obj1, obj2, obj3) {
- console.log(' --> Bypassing Android WebViewClient (WebResourceError)');
- };
- console.log('[+] Android WebViewClient (WebResourceError)');
- } catch (err) {
- console.log('[ ] Android WebViewClient (WebResourceError)');
- }
- // Apache Cordova WebViewClient
- try {
- const CordovaWebViewClient_Activity = Java.use('org.apache.cordova.CordovaWebViewClient');
- CordovaWebViewClient_Activity.onReceivedSslError.overload('android.webkit.WebView', 'android.webkit.SslErrorHandler', 'android.net.http.SslError').implementation = function (obj1, obj2, obj3) {
- console.log(' --> Bypassing Apache Cordova WebViewClient');
- obj3.proceed();
- };
- } catch (err) {
- console.log('[ ] Apache Cordova WebViewClient');
- }
- // Boye AbstractVerifier
- try {
- const boye_AbstractVerifier = Java.use('ch.boye.httpclientandroidlib.conn.ssl.AbstractVerifier');
- boye_AbstractVerifier.verify.implementation = function (host, ssl) {
- console.log(' --> Bypassing Boye AbstractVerifier: ' + host);
- };
- } catch (err) {
- console.log('[ ] Boye AbstractVerifier');
- }
- // Appmattus
- try {
- const appmatus_Activity = Java.use('com.appmattus.certificatetransparency.internal.verifier.CertificateTransparencyInterceptor');
- appmatus_Activity['intercept'].implementation = function (a) {
- console.log(' --> Bypassing Appmattus (Transparency)');
- return a.proceed(a.request());
- };
- console.log('[+] Appmattus (CertificateTransparencyInterceptor)');
- } catch (err) {
- console.log('[ ] Appmattus (CertificateTransparencyInterceptor)');
- }
- try {
- const CertificateTransparencyTrustManager = Java.use(
- 'com.appmattus.certificatetransparency.internal.verifier.CertificateTransparencyTrustManager'
- );
- CertificateTransparencyTrustManager['checkServerTrusted'].overload(
- '[Ljava.security.cert.X509Certificate;',
- 'java.lang.String'
- ).implementation = function (x509CertificateArr, str) {
- console.log(' --> Bypassing Appmattus (CertificateTransparencyTrustManager)');
- };
- CertificateTransparencyTrustManager['checkServerTrusted'].overload(
- '[Ljava.security.cert.X509Certificate;',
- 'java.lang.String',
- 'java.lang.String'
- ).implementation = function (x509CertificateArr, str, str2) {
- console.log(' --> Bypassing Appmattus (CertificateTransparencyTrustManager)');
- return Java.use('java.util.ArrayList').$new();
- };
- console.log('[+] Appmattus (CertificateTransparencyTrustManager)');
- } catch (err) {
- console.log('[ ] Appmattus (CertificateTransparencyTrustManager)');
- }
- console.log("Unpinning setup completed");
- console.log("---");
- });
- }, 0);
- Java.perform(function() {
- var RootPackages = ["com.noshufou.android.su", "com.noshufou.android.su.elite", "eu.chainfire.supersu",
- "com.koushikdutta.superuser", "com.thirdparty.superuser", "com.yellowes.su", "com.koushikdutta.rommanager",
- "com.koushikdutta.rommanager.license", "com.dimonvideo.luckypatcher", "com.chelpus.lackypatch",
- "com.ramdroid.appquarantine", "com.ramdroid.appquarantinepro", "com.devadvance.rootcloak", "com.devadvance.rootcloakplus",
- "de.robv.android.xposed.installer", "com.saurik.substrate", "com.zachspong.temprootremovejb", "com.amphoras.hidemyroot",
- "com.amphoras.hidemyrootadfree", "com.formyhm.hiderootPremium", "com.formyhm.hideroot", "me.phh.superuser",
- "eu.chainfire.supersu.pro", "com.kingouser.com", "com.topjohnwu.magisk"
- ];
- var RootBinaries = ["su", "busybox", "supersu", "Superuser.apk", "KingoUser.apk", "SuperSu.apk", "magisk"];
- var RootProperties = {
- "ro.build.selinux": "1",
- "ro.debuggable": "0",
- "service.adb.root": "0",
- "ro.secure": "1"
- };
- var RootPropertiesKeys = [];
- for (var k in RootProperties) RootPropertiesKeys.push(k);
- var PackageManager = Java.use("android.app.ApplicationPackageManager");
- var Runtime = Java.use('java.lang.Runtime');
- var NativeFile = Java.use('java.io.File');
- var String = Java.use('java.lang.String');
- var SystemProperties = Java.use('android.os.SystemProperties');
- var BufferedReader = Java.use('java.io.BufferedReader');
- var ProcessBuilder = Java.use('java.lang.ProcessBuilder');
- var StringBuffer = Java.use('java.lang.StringBuffer');
- var loaded_classes = Java.enumerateLoadedClassesSync();
- send("Loaded " + loaded_classes.length + " classes!");
- var useKeyInfo = false;
- var useProcessManager = false;
- send("loaded: " + loaded_classes.indexOf('java.lang.ProcessManager'));
- if (loaded_classes.indexOf('java.lang.ProcessManager') != -1) {
- try {
- //useProcessManager = true;
- //var ProcessManager = Java.use('java.lang.ProcessManager');
- } catch (err) {
- send("ProcessManager Hook failed: " + err);
- }
- } else {
- send("ProcessManager hook not loaded");
- }
- var KeyInfo = null;
- if (loaded_classes.indexOf('android.security.keystore.KeyInfo') != -1) {
- try {
- //useKeyInfo = true;
- //var KeyInfo = Java.use('android.security.keystore.KeyInfo');
- } catch (err) {
- send("KeyInfo Hook failed: " + err);
- }
- } else {
- send("KeyInfo hook not loaded");
- }
- PackageManager.getPackageInfo.overload('java.lang.String', 'int').implementation = function(pname, flags) {
- var shouldFakePackage = (RootPackages.indexOf(pname) > -1);
- if (shouldFakePackage) {
- send("Bypass root check for package: " + pname);
- pname = "set.package.name.to.a.fake.one.so.we.can.bypass.it";
- }
- return this.getPackageInfo.overload('java.lang.String', 'int').call(this, pname, flags);
- };
- NativeFile.exists.implementation = function() {
- var name = NativeFile.getName.call(this);
- var shouldFakeReturn = (RootBinaries.indexOf(name) > -1);
- if (shouldFakeReturn) {
- send("Bypass return value for binary: " + name);
- return false;
- } else {
- return this.exists.call(this);
- }
- };
- var exec = Runtime.exec.overload('[Ljava.lang.String;');
- var exec1 = Runtime.exec.overload('java.lang.String');
- var exec2 = Runtime.exec.overload('java.lang.String', '[Ljava.lang.String;');
- var exec3 = Runtime.exec.overload('[Ljava.lang.String;', '[Ljava.lang.String;');
- var exec4 = Runtime.exec.overload('[Ljava.lang.String;', '[Ljava.lang.String;', 'java.io.File');
- var exec5 = Runtime.exec.overload('java.lang.String', '[Ljava.lang.String;', 'java.io.File');
- exec5.implementation = function(cmd, env, dir) {
- if (cmd.indexOf("getprop") != -1 || cmd == "mount" || cmd.indexOf("build.prop") != -1 || cmd == "id" || cmd == "sh") {
- var fakeCmd = "grep";
- send("Bypass " + cmd + " command");
- return exec1.call(this, fakeCmd);
- }
- if (cmd == "su") {
- var fakeCmd = "justafakecommandthatcannotexistsusingthisshouldthowanexceptionwheneversuiscalled";
- send("Bypass " + cmd + " command");
- return exec1.call(this, fakeCmd);
- }
- return exec5.call(this, cmd, env, dir);
- };
- exec4.implementation = function(cmdarr, env, file) {
- for (var i = 0; i < cmdarr.length; i = i + 1) {
- var tmp_cmd = cmdarr[i];
- if (tmp_cmd.indexOf("getprop") != -1 || tmp_cmd == "mount" || tmp_cmd.indexOf("build.prop") != -1 || tmp_cmd == "id" || tmp_cmd == "sh") {
- var fakeCmd = "grep";
- send("Bypass " + cmdarr + " command");
- return exec1.call(this, fakeCmd);
- }
- if (tmp_cmd == "su") {
- var fakeCmd = "justafakecommandthatcannotexistsusingthisshouldthowanexceptionwheneversuiscalled";
- send("Bypass " + cmdarr + " command");
- return exec1.call(this, fakeCmd);
- }
- }
- return exec4.call(this, cmdarr, env, file);
- };
- exec3.implementation = function(cmdarr, envp) {
- for (var i = 0; i < cmdarr.length; i = i + 1) {
- var tmp_cmd = cmdarr[i];
- if (tmp_cmd.indexOf("getprop") != -1 || tmp_cmd == "mount" || tmp_cmd.indexOf("build.prop") != -1 || tmp_cmd == "id" || tmp_cmd == "sh") {
- var fakeCmd = "grep";
- send("Bypass " + cmdarr + " command");
- return exec1.call(this, fakeCmd);
- }
- if (tmp_cmd == "su") {
- var fakeCmd = "justafakecommandthatcannotexistsusingthisshouldthowanexceptionwheneversuiscalled";
- send("Bypass " + cmdarr + " command");
- return exec1.call(this, fakeCmd);
- }
- }
- return exec3.call(this, cmdarr, envp);
- };
- exec2.implementation = function(cmd, env) {
- if (cmd.indexOf("getprop") != -1 || cmd == "mount" || cmd.indexOf("build.prop") != -1 || cmd == "id" || cmd == "sh") {
- var fakeCmd = "grep";
- send("Bypass " + cmd + " command");
- return exec1.call(this, fakeCmd);
- }
- if (cmd == "su") {
- var fakeCmd = "justafakecommandthatcannotexistsusingthisshouldthowanexceptionwheneversuiscalled";
- send("Bypass " + cmd + " command");
- return exec1.call(this, fakeCmd);
- }
- return exec2.call(this, cmd, env);
- };
- exec.implementation = function(cmd) {
- for (var i = 0; i < cmd.length; i = i + 1) {
- var tmp_cmd = cmd[i];
- if (tmp_cmd.indexOf("getprop") != -1 || tmp_cmd == "mount" || tmp_cmd.indexOf("build.prop") != -1 || tmp_cmd == "id" || tmp_cmd == "sh") {
- var fakeCmd = "grep";
- send("Bypass " + cmd + " command");
- return exec1.call(this, fakeCmd);
- }
- if (tmp_cmd == "su") {
- var fakeCmd = "justafakecommandthatcannotexistsusingthisshouldthowanexceptionwheneversuiscalled";
- send("Bypass " + cmd + " command");
- return exec1.call(this, fakeCmd);
- }
- }
- return exec.call(this, cmd);
- };
- exec1.implementation = function(cmd) {
- if (cmd.indexOf("getprop") != -1 || cmd == "mount" || cmd.indexOf("build.prop") != -1 || cmd == "id" || cmd == "sh") {
- var fakeCmd = "grep";
- send("Bypass " + cmd + " command");
- return exec1.call(this, fakeCmd);
- }
- if (cmd == "su") {
- var fakeCmd = "justafakecommandthatcannotexistsusingthisshouldthowanexceptionwheneversuiscalled";
- send("Bypass " + cmd + " command");
- return exec1.call(this, fakeCmd);
- }
- return exec1.call(this, cmd);
- };
- String.contains.implementation = function(name) {
- if (name == "test-keys") {
- send("Bypass test-keys check");
- return false;
- }
- return this.contains.call(this, name);
- };
- var get = SystemProperties.get.overload('java.lang.String');
- get.implementation = function(name) {
- if (RootPropertiesKeys.indexOf(name) != -1) {
- send("Bypass " + name);
- return RootProperties[name];
- }
- return this.get.call(this, name);
- };
- Interceptor.attach(Module.findExportByName("libc.so", "fopen"), {
- onEnter: function(args) {
- var path = Memory.readCString(args[0]);
- path = path.split("/");
- var executable = path[path.length - 1];
- var shouldFakeReturn = (RootBinaries.indexOf(executable) > -1)
- if (shouldFakeReturn) {
- Memory.writeUtf8String(args[0], "/notexists");
- send("Bypass native fopen");
- }
- },
- onLeave: function(retval) {
- }
- });
- Interceptor.attach(Module.findExportByName("libc.so", "system"), {
- onEnter: function(args) {
- var cmd = Memory.readCString(args[0]);
- send("SYSTEM CMD: " + cmd);
- if (cmd.indexOf("getprop") != -1 || cmd == "mount" || cmd.indexOf("build.prop") != -1 || cmd == "id") {
- send("Bypass native system: " + cmd);
- Memory.writeUtf8String(args[0], "grep");
- }
- if (cmd == "su") {
- send("Bypass native system: " + cmd);
- Memory.writeUtf8String(args[0], "justafakecommandthatcannotexistsusingthisshouldthowanexceptionwheneversuiscalled");
- }
- },
- onLeave: function(retval) {
- }
- });
- /*
- TO IMPLEMENT:
- Exec Family
- int execl(const char *path, const char *arg0, ..., const char *argn, (char *)0);
- int execle(const char *path, const char *arg0, ..., const char *argn, (char *)0, char *const envp[]);
- int execlp(const char *file, const char *arg0, ..., const char *argn, (char *)0);
- int execlpe(const char *file, const char *arg0, ..., const char *argn, (char *)0, char *const envp[]);
- int execv(const char *path, char *const argv[]);
- int execve(const char *path, char *const argv[], char *const envp[]);
- int execvp(const char *file, char *const argv[]);
- int execvpe(const char *file, char *const argv[], char *const envp[]);
- */
- BufferedReader.readLine.overload('boolean').implementation = function() {
- var text = this.readLine.overload('boolean').call(this);
- if (text === null) {
- // just pass , i know it's ugly as hell but test != null won't work :(
- } else {
- var shouldFakeRead = (text.indexOf("ro.build.tags=test-keys") > -1);
- if (shouldFakeRead) {
- send("Bypass build.prop file read");
- text = text.replace("ro.build.tags=test-keys", "ro.build.tags=release-keys");
- }
- }
- return text;
- };
- var executeCommand = ProcessBuilder.command.overload('java.util.List');
- ProcessBuilder.start.implementation = function() {
- var cmd = this.command.call(this);
- var shouldModifyCommand = false;
- for (var i = 0; i < cmd.size(); i = i + 1) {
- var tmp_cmd = cmd.get(i).toString();
- if (tmp_cmd.indexOf("getprop") != -1 || tmp_cmd.indexOf("mount") != -1 || tmp_cmd.indexOf("build.prop") != -1 || tmp_cmd.indexOf("id") != -1) {
- shouldModifyCommand = true;
- }
- }
- if (shouldModifyCommand) {
- send("Bypass ProcessBuilder " + cmd);
- this.command.call(this, ["grep"]);
- return this.start.call(this);
- }
- if (cmd.indexOf("su") != -1) {
- send("Bypass ProcessBuilder " + cmd);
- this.command.call(this, ["justafakecommandthatcannotexistsusingthisshouldthowanexceptionwheneversuiscalled"]);
- return this.start.call(this);
- }
- return this.start.call(this);
- };
- if (useProcessManager) {
- var ProcManExec = ProcessManager.exec.overload('[Ljava.lang.String;', '[Ljava.lang.String;', 'java.io.File', 'boolean');
- var ProcManExecVariant = ProcessManager.exec.overload('[Ljava.lang.String;', '[Ljava.lang.String;', 'java.lang.String', 'java.io.FileDescriptor', 'java.io.FileDescriptor', 'java.io.FileDescriptor', 'boolean');
- ProcManExec.implementation = function(cmd, env, workdir, redirectstderr) {
- var fake_cmd = cmd;
- for (var i = 0; i < cmd.length; i = i + 1) {
- var tmp_cmd = cmd[i];
- if (tmp_cmd.indexOf("getprop") != -1 || tmp_cmd == "mount" || tmp_cmd.indexOf("build.prop") != -1 || tmp_cmd == "id") {
- var fake_cmd = ["grep"];
- send("Bypass " + cmdarr + " command");
- }
- if (tmp_cmd == "su") {
- var fake_cmd = ["justafakecommandthatcannotexistsusingthisshouldthowanexceptionwheneversuiscalled"];
- send("Bypass " + cmdarr + " command");
- }
- }
- return ProcManExec.call(this, fake_cmd, env, workdir, redirectstderr);
- };
- ProcManExecVariant.implementation = function(cmd, env, directory, stdin, stdout, stderr, redirect) {
- var fake_cmd = cmd;
- for (var i = 0; i < cmd.length; i = i + 1) {
- var tmp_cmd = cmd[i];
- if (tmp_cmd.indexOf("getprop") != -1 || tmp_cmd == "mount" || tmp_cmd.indexOf("build.prop") != -1 || tmp_cmd == "id") {
- var fake_cmd = ["grep"];
- send("Bypass " + cmdarr + " command");
- }
- if (tmp_cmd == "su") {
- var fake_cmd = ["justafakecommandthatcannotexistsusingthisshouldthowanexceptionwheneversuiscalled"];
- send("Bypass " + cmdarr + " command");
- }
- }
- return ProcManExecVariant.call(this, fake_cmd, env, directory, stdin, stdout, stderr, redirect);
- };
- }
- if (useKeyInfo) {
- KeyInfo.isInsideSecureHardware.implementation = function() {
- send("Bypass isInsideSecureHardware");
- return true;
- }
- }
- });
- const commonPaths = [
- "/data/local/bin/su",
- "/data/local/su",
- "/data/local/xbin/su",
- "/dev/com.koushikdutta.superuser.daemon/",
- "/sbin/su",
- "/system/app/Superuser.apk",
- "/system/bin/failsafe/su",
- "/system/bin/su",
- "/su/bin/su",
- "/system/etc/init.d/99SuperSUDaemon",
- "/system/sd/xbin/su",
- "/system/xbin/busybox",
- "/system/xbin/daemonsu",
- "/system/xbin/su",
- "/system/sbin/su",
- "/vendor/bin/su",
- "/cache/su",
- "/data/su",
- "/dev/su",
- "/system/bin/.ext/su",
- "/system/usr/we-need-root/su",
- "/system/app/Kinguser.apk",
- "/data/adb/magisk",
- "/sbin/.magisk",
- "/cache/.disable_magisk",
- "/dev/.magisk.unblock",
- "/cache/magisk.log",
- "/data/adb/magisk.img",
- "/data/adb/magisk.db",
- "/data/adb/magisk_simple",
- "/init.magisk.rc",
- "/system/xbin/ku.sud",
- "/data/adb/ksu",
- "/data/adb/ksud"
- ];
- const ROOTmanagementApp = [
- "com.noshufou.android.su",
- "com.noshufou.android.su.elite",
- "eu.chainfire.supersu",
- "com.koushikdutta.superuser",
- "com.thirdparty.superuser",
- "com.yellowes.su",
- "com.koushikdutta.rommanager",
- "com.koushikdutta.rommanager.license",
- "com.dimonvideo.luckypatcher",
- "com.chelpus.lackypatch",
- "com.ramdroid.appquarantine",
- "com.ramdroid.appquarantinepro",
- "com.topjohnwu.magisk",
- "me.weishu.kernelsu"
- ];
- function stackTraceHere(isLog){
- var Exception = Java.use('java.lang.Exception');
- var Log = Java.use('android.util.Log');
- var stackinfo = Log.getStackTraceString(Exception.$new())
- if(isLog){
- console.log(stackinfo)
- }else{
- return stackinfo
- }
- }
- function stackTraceNativeHere(isLog){
- var backtrace = Thread.backtrace(this.context, Backtracer.ACCURATE)
- .map(DebugSymbol.fromAddress)
- .join("\n\t");
- console.log(backtrace)
- }
- function bypassJavaFileCheck(){
- var UnixFileSystem = Java.use("java.io.UnixFileSystem")
- UnixFileSystem.checkAccess.implementation = function(file,access){
- var stack = stackTraceHere(false)
- const filename = file.getAbsolutePath();
- if (filename.indexOf("magisk") >= 0) {
- console.log("Anti Root Detect - check file: " + filename)
- return false;
- }
- if (commonPaths.indexOf(filename) >= 0) {
- console.log("Anti Root Detect - check file: " + filename)
- return false;
- }
- return this.checkAccess(file,access)
- }
- }
- function bypassNativeFileCheck(){
- var fopen = Module.findExportByName("libc.so","fopen")
- Interceptor.attach(fopen,{
- onEnter:function(args){
- this.inputPath = args[0].readUtf8String()
- },
- onLeave:function(retval){
- if(retval.toInt32() != 0){
- if (commonPaths.indexOf(this.inputPath) >= 0) {
- console.log("Anti Root Detect - fopen : " + this.inputPath)
- retval.replace(ptr(0x0))
- }
- }
- }
- })
- var access = Module.findExportByName("libc.so","access")
- Interceptor.attach(access,{
- onEnter:function(args){
- this.inputPath = args[0].readUtf8String()
- },
- onLeave:function(retval){
- if(retval.toInt32()==0){
- if(commonPaths.indexOf(this.inputPath) >= 0){
- console.log("Anti Root Detect - access : " + this.inputPath)
- retval.replace(ptr(-1))
- }
- }
- }
- })
- }
- function setProp(){
- var Build = Java.use("android.os.Build")
- var TAGS = Build.class.getDeclaredField("TAGS")
- TAGS.setAccessible(true)
- TAGS.set(null,"release-keys")
- var FINGERPRINT = Build.class.getDeclaredField("FINGERPRINT")
- FINGERPRINT.setAccessible(true)
- FINGERPRINT.set(null,"google/crosshatch/crosshatch:10/QQ3A.200805.001/6578210:user/release-keys")
- // Build.deriveFingerprint.inplementation = function(){
- // var ret = this.deriveFingerprint() //该函数无法通过反射调用
- // console.log(ret)
- // return ret
- // }
- var system_property_get = Module.findExportByName("libc.so", "__system_property_get")
- Interceptor.attach(system_property_get,{
- onEnter(args){
- this.key = args[0].readCString()
- this.ret = args[1]
- },
- onLeave(ret){
- if(this.key == "ro.build.fingerprint"){
- var tmp = "google/crosshatch/crosshatch:10/QQ3A.200805.001/6578210:user/release-keys"
- var p = Memory.allocUtf8String(tmp)
- Memory.copy(this.ret,p,tmp.length+1)
- }
- }
- })
- }
- //android.app.PackageManager
- function bypassRootAppCheck(){
- var ApplicationPackageManager = Java.use("android.app.ApplicationPackageManager")
- ApplicationPackageManager.getPackageInfo.overload('java.lang.String', 'int').implementation = function(str,i){
- // console.log(str)
- if (ROOTmanagementApp.indexOf(str) >= 0) {
- console.log("Anti Root Detect - check package : " + str)
- str = "ashen.one.ye.not.found"
- }
- return this.getPackageInfo(str,i)
- }
- //shell pm check
- }
- function bypassShellCheck(){
- var String = Java.use('java.lang.String')
- var ProcessImpl = Java.use("java.lang.ProcessImpl")
- ProcessImpl.start.implementation = function(cmdarray,env,dir,redirects,redirectErrorStream){
- if(cmdarray[0] == "mount"){
- console.log("Anti Root Detect - Shell : " + cmdarray.toString())
- arguments[0] = Java.array('java.lang.String',[String.$new("")])
- return ProcessImpl.start.apply(this,arguments)
- }
- if(cmdarray[0] == "getprop"){
- console.log("Anti Root Detect - Shell : " + cmdarray.toString())
- const prop = [
- "ro.secure",
- "ro.debuggable"
- ];
- if(prop.indexOf(cmdarray[1]) >= 0){
- arguments[0] = Java.array('java.lang.String',[String.$new("")])
- return ProcessImpl.start.apply(this,arguments)
- }
- }
- if(cmdarray[0].indexOf("which") >= 0){
- const prop = [
- "su"
- ];
- if(prop.indexOf(cmdarray[1]) >= 0){
- console.log("Anti Root Detect - Shell : " + cmdarray.toString())
- arguments[0] = Java.array('java.lang.String',[String.$new("")])
- return ProcessImpl.start.apply(this,arguments)
- }
- }
- return ProcessImpl.start.apply(this,arguments)
- }
- }
- console.log("Attach")
- bypassNativeFileCheck()
- bypassJavaFileCheck()
- setProp()
- bypassRootAppCheck()
- bypassShellCheck()
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement