
Frida intercepting SSL certificate validation
The Problem
Before you can intercept HTTPS traffic from a modern Android app using Burp Suite, you need to defeat:
- System CA restrictions (Android 7+ no longer trusts user-installed CAs for apps)
- Certificate pinning — the app validates the server certificate against a hardcoded hash or certificate
This post covers all current bypass techniques as of 2026, including apps using the latest OkHttp versions, Conscrypt, and custom TrustManager implementations.
Environment Setup
1
2
3
| Host: Kali Linux / macOS
Device: Rooted Android 13 emulator (AVD) or physical device
Tools: Frida 16.x, Objection, Burp Suite Pro, apktool, jadx
|
1
2
3
4
5
6
7
8
9
| # Install Frida
pip3 install frida-tools --break-system-packages
# Push frida-server to device
adb push frida-server-16.x.x-android-x86_64 /data/local/tmp/frida-server
adb shell "chmod 755 /data/local/tmp/frida-server && /data/local/tmp/frida-server &"
# Verify
frida-ps -U | grep -i target-app
|
Technique 1 — Objection (Quick Win)
Objection wraps Frida with pre-built hooks. Try this first:
1
2
3
4
| objection --gadget "com.target.app" explore
# Inside objection shell:
android sslpinning disable
|
This patches the most common OkHttp, TrustManager, and WebView pinning in one command. Works on ~60% of apps.
Technique 2 — Frida Universal Script
For apps where Objection fails, use this maintained universal script:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
| // universal-ssl-bypass.js
// Covers: OkHttp 3/4, Conscrypt, custom TrustManagers, WebViewClient
Java.perform(function() {
// ── OkHttp 3 ─────────────────────────────────────────────
try {
var okhttp3 = Java.use("okhttp3.CertificatePinner");
okhttp3.check.overload("java.lang.String", "java.util.List").implementation = function() {
console.log("[+] OkHttp3 CertificatePinner.check bypassed");
};
} catch(e) {}
// ── OkHttp 4 (Kotlin) ────────────────────────────────────
try {
var okhttp4 = Java.use("okhttp3.internal.tls.OkHostnameVerifier");
okhttp4.verify.overload("java.lang.String", "javax.net.ssl.SSLSession").implementation = function() {
console.log("[+] OkHttp4 hostname verifier bypassed");
return true;
};
} catch(e) {}
// ── Custom TrustManager (X509TrustManager) ───────────────
try {
var X509 = Java.use("javax.net.ssl.X509TrustManager");
var TrustManagerImpl = Java.use("com.android.org.conscrypt.TrustManagerImpl");
TrustManagerImpl.checkTrusted.implementation = function() {
console.log("[+] Conscrypt TrustManagerImpl.checkTrusted bypassed");
};
} catch(e) {}
// ── SSLContext / HttpsURLConnection ──────────────────────
try {
var SSLContext = Java.use("javax.net.ssl.SSLContext");
SSLContext.init.overload(
"[Ljavax.net.ssl.KeyManager;",
"[Ljavax.net.ssl.TrustManager;",
"java.security.SecureRandom"
).implementation = function(km, tm, sr) {
console.log("[+] SSLContext.init hooked — injecting permissive TrustManager");
this.init(km, [TrustAllManager.$new()], sr);
};
} catch(e) {}
});
|
1
2
| # Run it
frida -U -l universal-ssl-bypass.js -f com.target.app --no-pause
|
When runtime hooking is detected (some apps check for Frida):
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
| # Decompile APK
apktool d target-app.apk -o target-decompiled/
# Locate network security config
cat target-decompiled/res/xml/network_security_config.xml
# Remove pin-set entries:
# <pin-set expiration="2026-01-01">
# <pin digest="SHA-256">AAABBBCCC...</pin> ← delete these
# </pin-set>
# Recompile and sign
apktool b target-decompiled/ -o target-patched.apk
apksigner sign --ks debug.keystore target-patched.apk
adb install target-patched.apk
|
Technique 4 — Defeating Frida Detection
Apps using libraries like libfrida-detect or checking for /proc/self/maps entries:
1
2
3
4
5
6
7
8
9
| # Use Frida Gadget injection (embedded mode — no frida-server process)
# Or use Magisk Hide + Frida with process name spoofing
# Check what the app is detecting
frida -U -e "Process.enumerateModules().forEach(m => console.log(m.name))" -f com.target.app
# Patch detection with custom spawn gating
frida -U --pause -f com.target.app
# Then attach your bypass script before execution resumes
|
MASVS Checklist
After bypassing pinning, test these OWASP MASVS-L2 controls in Burp:
| Test | MASVS | Method |
|---|
| Sensitive data in transit unencrypted | MASVS-NETWORK-1 | Burp proxy |
| Auth tokens in URL parameters | MASVS-NETWORK-2 | Burp proxy |
| Hardcoded credentials in traffic | MASVS-CRYPTO-1 | Search responses |
| Session fixation after logout | MASVS-AUTH-3 | Replay tokens |
| IDOR in user-specific endpoints | MASVS-AUTH-4 | Change IDs |
References