How To Bypass SSL Pinning in Android




What is SSL Pinning ?

Description:-

As per OWASP, SSL Pinning can be defined as process of associating a host with their expected X509 certificate or public key. Once a certificate or public key is known or seen for a host, the certificate or public key is associated or 'pinned' to the host.
A host or service's certificate or public key can be added to an application at development time, or it can be added upon first encountering the certificate or public key.
Applications communicating over HTTPS and using SSL Pinning makes it non-trivial to perform Man-In-The-Middle attack and grab the network traffic in clear text using the proxy tools.

Note: - In cryptography, X.509 is a standard that defines the format of public key certificates. ... An X.509 certificate contains a public key and an identity (a hostname, or an organization, or an individual), and is either signed by a certificate authority or self-signed.

Now what developers thinks when it comes to Pinning the application (.apk)


IMPLEMENTING SSL PINNING 





What Should Be Pinned?
You can (1) pin the certificate; or (2) pin the public key
If you choose public keys, you have two additional choices: (a) pin the subjectPublicKeyInfo; or (b) pin one of the concrete types such as RSAPublicKey or DSAPublicKey.

Note 1: - I would encourage you to pin the subjectPublicKeyInfo because it has the public parameters (such as {e,n} for an RSA public key) and contextual information such as an algorithm and OID.
Note 2: - A certificate is an object which binds an entity (such as a person or organization) to a public key via a signature. The certificate is DER encoded, and has associated data or attributes such as Subject (who is identified or bound), Issuer (who signed it), Validity (NotBefore and NotAfter), and a Public Key.

Final takeaways:
(1) A certificate binds an entity to a public key;
(2) A certificate has a subjectPublicKeyInfo; and
(3) A subjectPublicKeyInfo has an concrete public key.


Pinning via – Certificate   
1.      The certificate is easiest to pin.
2.      You can fetch the certificate out of band for the website, have the IT folks email your company certificate to you, use openssl s_client to retrieve the certificate etc.
3.      When the certificate expires, you would update your application. Assuming your application has no bugs or security defects, the application would be updated every year or two.
4.      At runtime, you retrieve the website or server's certificate in the callback. Within the callback, you compare the retrieved certificate with the certificate embedded within the program. If the comparison fails, then fail the method or function.
5.      There is a downside to pinning a certificate.
6.      If the site rotates its certificate on a regular basis, then your application would need to be updated regularly. For example, Google rotates its certificates, so you will need to update your application about once a month (if it depended on Google services). Even though Google rotates its certificates, the underlying public keys (within the certificate) remain static.

Pinning via – Public Key
1.      Public key pinning is more flexible but a little trickier due to the extra steps necessary to extract the public key from a certificate.
2.      As with a certificate, the program checks the extracted public key with its embedded copy of the public key.
3.      There are two downsides to public key pinning.
3.1         First, it’s harder to work with keys (versus certificates) since you usually must extract the key from the certificate. Extraction is a minor inconvenience in Java and .Net, buts its uncomfortable in Cocoa/CocoaTouch and OpenSSL.
3.2         Second, the key is static and may violate key rotation policies.

Reference: - https://www.owasp.org/index.php/Certificate_and_Public_Key_Pinning



Certificate pinning is used by many popular applications for e.g Facebook,Twitter, Square etc.
So the question that arises is, how do you bypass this certificate validation that is happening on the client side ?

The important thing to note here is all that all the validation is happening on the client side.
And since there are frameworks like Mobile Substrate that allow us to patch any method during runtime and modify its implementation,
it is possible to disable the certificate validation that is happening in the application.

HOW TO CHECK SSL PINNING IS THERE OR NOT 




How to check whether SSL pinning is implemented or not ?  

- If you are not able to intercept the traffic then
  • You may have done the wrong setup for interception 
  • Developer has implemented SSL Pinning 
1] If you have done the incorrect setup
Verify the same by simply following the steps of setting up mobile application testing environment from this link.

2] Developer has implemented SSL Pinning or not

Below is the few test cases which I know till now

PS:- If anyone know any other way to check if SSL pinning is implemented or not then do DM me, I love to add and share the knowledge.

2.1 :-  You will be able to intercept the first request and not other request.

2.2 :-  If code is obfuscated then under source code => Press Ctrl + Shift + S  and search for the keyword searching for strings like "checkClientTrusted" or "checkServerTrusted", it would show you piece of code with pinning.

2.3 :- 
User MOBSF security framework. - My all time favorite
- Scan your application with MOBSF,  and then a static analysis report will be appeared.
- Check left hand side of report, then go to
  Security Analysis tab ==> click on File Analysis.
- If you find "Certificate/Key Files Hard-coded inside the App"  or "Hardcoded Keystore Found"  keywords,  it means application has SSL pinning.  OR
- If you find  .bks and .key files then there is SSL Pinning
- If  no .bks and .key files are observed then there is no SSL Pinning.

OR 

- Scan your application with MOBSF,  and then a static analysis report will be appeared.
- If MobSF detects SSL Pinning from code, it will show the finding under Code Analysis.





BREAKING THE SSL PINNING 



How To Bypass SSL Pinning ?


After confirming that android application having SSL Pinning the next step is to bypass SSL Pinning


SSL Pinning in case of Android can be performed either in the
1.      Java layer, using the Android API, OR
2.      In the native C/C++ layer.

Let’s look into each of the cases one at a time:

Java Layer:
To implement SSL Pinning, Android API exposes multiple functions to do so.
In order to bypass the SSL Pinning in Java layer one can use existing tools or can patch the APK file manually.

Xposed Framework:
If the device is rooted, one can install XposedFramework and use one of the multiple modules available to disable SSL Pinning. One such module is SSL Unpinning.
Using the module is straight forward and I would leave the details of usage to the readers to figure out.

Manual Patching: 
In order to use Xposed Framework we requires the device to be rooted. In such a case we cannot use the tools discussed above to bypass the SSL checks.
In such a situation we can patch the APK file manually. Patching the file manually requires some extra effort, this can be done with ease.

The steps involved are following:
1.      Decompile the application using Apktool or any other similar tool. Apktool gives Smali code for the application.
2.      Patch the relevant functions in the Smali code.
3.      Compile the application back using apktool, sign it using jarsign and run zipalign over it.
4.      Installed the patched APK generated above.

What if above two approach fails?

Native Layer:
If the above approaches fail, you can fairly be confident that the SSL Pinning checks are being performed in the native layer. FBM is doing exactly same. To make things a bit obscure, the FBM application do have SSL Pinning logic in Java layer as well, but patching it does not work.
To get started, simply run APKTool and get the decompiled/unzipped version of the APK. More read.


Note:-
Android Mobile OS dependency :- 

1]  For Android 4.2.2 and below version you can install in your rooted device to bypass SSL
Pinning :- Cydia substrate +  Android-SSL-TrustKiller

2] For Android 4.2.2 and above version you can use  
 Xposed framework with JustTrustMe


NOTE - 1:- 

Weird problem when you get below error:- 
(When you are not able to intercept the mobile application traffic)

In this you will learn how to
  • Decompile the .apk  file
  • Re-compile the apk
  • Signing the Apk File




While capturing the traffic of mobile application if you getting any sort of response like this then do the troubleshooting as below:-


=> Decompiling the Apk File

1 -  Decompile the .apk  file by using command
      apktool d "name_of_app.apk"

2 - you will find the folder where there is different certificates are placed

3- Put your burp-suite certificate insider this directory (convert .der to .cer )


=> Recompiling the Apk File

4-  Now Re-compile the apk

 4.1 - Type command as apktool b filename (filename is the folder with your edited files)

 4.2 - After that, it will generate a final modded apk which will be inside a folder named “dist”.
        The “dist” folder is located inside the original app folder.

4.3 - Now your new .apk is ready with burp suite certificate in it.
         Next step will be Signing the Apk File


=> Signing the Apk File

5 - Signing the Apk File
Now that we have our modded apk, it is still not complete yet. We have to add it back to the original apk file in order to keep its proper signature.

5.1- Download SignApk.

5.2- Copy the “modded apk” from the “dist” folder to the SignApk folder.


5.3- Type command as
   signapk.jar certificate.pem key.pk8 filename.apk newfilename.apk

PS:-
The filename.apk refers to the modded apk file and the newfilename.apk refers to the
new final modified recompiled apk file. You can change the “newfilename” to any file name
 that you want.








Once compiled, the resulting signed apk will be generated on the same folder. This is the FINAL APK(new_app.apk).

Just rename it, and push it in your Android device.


NOTE - 2:- 

Problems which you might face:

1) If you are not able to intercept the traffic then may be firewall is blocking - In this case turn off your firewall and try again.
2) Anti-virus is blocking your traffic - Turn off anti-virus and try again.


Last but not least, If you are facing difficulties in capturing traffic then switch to fiddler.
(Remember Fiddler is a savior) Refer this blog how to use fiddler if you are new.



NOTE - 3:-  Good Read 

1] SSL Pinning and Basic

2] Cydia Substrate

3] SSL Pinning bypass in Android 

4] Intercept all HTTP + SSL Android traffic and bypass SSL Pinning




Share this

Related Posts

Previous
Next Post »

2 comments

Write comments
16 November 2017 at 06:35 delete

Very nice blog for beginners, simple language best to understand!!!! keep writing such helpful blogs...

Reply
avatar