Frida ट्यूटोरियल

Reading time: 13 minutes

tip

AWS हैकिंग सीखें और अभ्यास करें:HackTricks Training AWS Red Team Expert (ARTE)
GCP हैकिंग सीखें और अभ्यास करें: HackTricks Training GCP Red Team Expert (GRTE) Azure हैकिंग सीखें और अभ्यास करें: HackTricks Training Azure Red Team Expert (AzRTE)

HackTricks का समर्थन करें

इंस्टॉलेशन

इंस्टॉल करें frida tools:

bash
pip install frida-tools
pip install frida

डाउनलोड और इंस्टॉल करें Android पर frida server (Download the latest release).
adb को root मोड में पुनरारंभ करने, उससे कनेक्ट होने, frida-server अपलोड करने, exec permissions देने और बैकग्राउंड में चलाने के लिए एक-लाइनर:

bash
adb root; adb connect localhost:6000; sleep 1; adb push frida-server /data/local/tmp/; adb shell "chmod 755 /data/local/tmp/frida-server"; adb shell "/data/local/tmp/frida-server &"

जांचें कि यह काम कर रहा है:

bash
frida-ps -U #List packages and processes
frida-ps -U | grep -i <part_of_the_package_name> #Get all the package name

Frida server vs. Gadget (root vs. no-root)

Android ऐप्स को Frida से इंस्ट्रूमेंट करने के दो सामान्य तरीके:

  • Frida server (rooted devices): एक native daemon push और run करें जो आपको किसी भी process से attach करने की अनुमति देता है।
  • Frida Gadget (no root): Frida को APK के अंदर एक shared library के रूप में bundle करें और इसे target process के भीतर auto-load करें।

Frida server (rooted)

bash
# Download the matching frida-server binary for your device's arch
# https://github.com/frida/frida/releases
adb root
adb push frida-server-<ver>-android-<arch> /data/local/tmp/frida-server
adb shell chmod 755 /data/local/tmp/frida-server
adb shell /data/local/tmp/frida-server &    # run at boot via init/magisk if desired

# From host, list processes and attach
frida-ps -Uai
frida -U -n com.example.app

Frida Gadget (no-root)

  1. APK को अनपैक करें, gadget .so और config जोड़ें:
  • libfrida-gadget.so को lib/<abi>/ में रखें (उदा., lib/arm64-v8a/)
  • अपने script loading settings के साथ assets/frida-gadget.config बनाएं

frida-gadget.config का उदाहरण

json
{
"interaction": { "type": "script", "path": "/sdcard/ssl-bypass.js" },
"runtime": { "logFile": "/sdcard/frida-gadget.log" }
}
  1. gadget को reference/load करें ताकि यह जल्दी initialize हो:
  • सबसे आसान: Application.onCreate() में System.loadLibrary("frida-gadget") को कॉल करने वाला एक छोटा Java stub जोड़ें, या पहले से मौजूद native lib loading का उपयोग करें।
  1. APK को पुनः पैक और साइन करें, फिर इंस्टॉल करें:
bash
apktool d app.apk -o app_m
# ... add gadget .so and config ...
apktool b app_m -o app_gadget.apk
uber-apk-signer -a app_gadget.apk -o out_signed
adb install -r out_signed/app_gadget-aligned-debugSigned.apk
  1. होस्ट से गैजेट प्रोसेस में Attach करें:
bash
frida-ps -Uai
frida -U -n com.example.app

नोट्स

  • कुछ सुरक्षा उपाय Gadget का पता लगा सकते हैं; नाम/पथ छिपा कर रखें और आवश्यकता होने पर इन्हें देर से/शर्तीय रूप से लोड करें।
  • कठोर सुरक्षा वाले ऐप्स पर, server के साथ rooted testing और late attach को प्राथमिकता दें, या Magisk/Zygisk hiding के साथ संयोजन करें।

JDWP-आधारित Frida इंजेक्शन बिना root/repackaging के (frida-jdwp-loader)

यदि APK debuggable है (android:debuggable="true"), तो आप JDWP के जरिए attach कर सकते हैं और Java breakpoint पर एक native library inject कर सकते हैं। बिना root और बिना APK repackaging।

  • Repo: https://github.com/frankheat/frida-jdwp-loader
  • आवश्यकताएँ: ADB, Python 3, USB/Wireless debugging. ऐप को debuggable होना चाहिए (emulator with ro.debuggable=1, rooted device with resetprop, or rebuild manifest).

त्वरित आरंभ

bash
git clone https://github.com/frankheat/frida-jdwp-loader.git
cd frida-jdwp-loader
# Inject frida-gadget.so into a debuggable target
python frida-jdwp-loader.py frida -n com.example.myapplication
# Keep the breakpoint thread suspended for early hooks
python frida-jdwp-loader.py frida -n com.example.myapplication -s
# Networkless: run a local agent script via Gadget "script" mode
python frida-jdwp-loader.py frida -n com.example.myapplication -i script -l script.js

नोट्स

  • मोड्स: spawn (break at Application.onCreate) या attach (break at Activity.onStart)। Use -b to set a specific Java method, -g to select Gadget version/path, -p to choose JDWP port.
  • Listen mode: यदि आवश्यक हो तो Gadget को फॉरवर्ड करें (default 127.0.0.1:27042): adb forward tcp:27042 tcp:27042; फिर frida-ps -H 127.0.0.1:27042
  • यह JDWP debugging का उपयोग करता है। जोखिम यह है कि debuggable builds भेजे जाने या JDWP के उजागर होने का हो सकता है।

Self-contained agent + Gadget embedding (Frida 17+; automated with Objection)

Frida 17 ने GumJS से built-in Java/ObjC bridges हटा दिए। यदि आपका agent Java को hook करता है, तो आपको अपने bundle के अंदर Java bridge शामिल करना होगा।

  1. एक Frida agent (TypeScript) बनाएँ और Java bridge शामिल करें
bash
# Scaffolding
frida-create -t agent -o mod
cd mod && npm install
# Install the Java bridge for Frida 17+
npm install frida-java-bridge
# Dev loop (optional live-reload via REPL)
npm run watch

न्यूनतम Java hook (पासे के रोल को 1 कर देता है):

ts
import Java from "frida-java-bridge";

Java.perform(function () {
var dicer = Java.use("org.secuso.privacyfriendlydicer.dicer.Dicer");
dicer.rollDice.implementation = function (numDice: number, numFaces: number) {
return Array(numDice).fill(1);
};
});

एम्बेडिंग के लिए एकल बंडल बनाएं:

bash
npm run build    # produces _agent.js via frida-compile

त्वरित USB परीक्षण (वैकल्पिक):

bash
frida -U -f org.secuso.privacyfriendlydicer -l _agent.js
  1. Gadget को अपने script को auto-load करने के लिए configure करें Objection का patcher एक Gadget config की अपेक्षा करता है; जब आप script mode का उपयोग कर रहे हों, तो APK lib dir के अंदर on-disk path निर्दिष्ट करें:
json
{
"interaction": {
"type": "script",
"path": "libfrida-gadget.script.so"
}
}
  1. Objection के साथ APK patching स्वचालित करें
bash
# Embed Gadget, config, and your compiled agent into the APK; rebuild and sign
objection patchapk -s org.secuso.privacyfriendlydicer.apk \
-c gadget-config.json \
-l mod/_agent.js \
--use-aapt2

patchapk क्या करता है (उच्च स्तर):

  • डिवाइस ABI (उदा., arm64-v8a) का पता लगाता है और मिलते-जुलते Gadget को फ़ेच/डाउनलोड करता है
  • आवश्यक होने पर वैकल्पिक रूप से android.permission.INTERNET जोड़ता है
  • लॉन्च activity में System.loadLibrary("frida-gadget") को कॉल करने वाला एक static class initializer इंजेक्ट करता है
  • निम्न को lib/<abi>/ के अंतर्गत रखता है:
  • libfrida-gadget.so
  • libfrida-gadget.config.so (serialized config)
  • libfrida-gadget.script.so (your _agent.js)

Example injected smali (static initializer):

smali
.method static constructor <clinit>()V
.locals 1
const-string v0, "frida-gadget"
invoke-static {v0}, Ljava/lang/System;->loadLibrary(Ljava/lang/String;)V
return-void
.end method
  1. repack सत्यापित करें
bash
apktool d org.secuso.privacyfriendlydicer.apk
apktool d org.secuso.privacyfriendlydicer.objection.apk
# Inspect differences
diff -r org.secuso.privacyfriendlydicer org.secuso.privacyfriendlydicer.objection

अपेक्षित परिवर्तन:

  • AndroidManifest.xml में <uses-permission android:name="android.permission.INTERNET"/> शामिल हो सकता है
  • New native libs lib/<abi>/ के अंतर्गत, जैसा ऊपर
  • Launchable activity smali में एक static <clinit> होता है जो System.loadLibrary("frida-gadget") को कॉल करता है
  1. Split APKs
  • base APK को पैच करें (वह जो MAIN/LAUNCHER activity घोषित करता है)
  • शेष splits को उसी key से re-sign करें:
bash
objection signapk split1.apk split2.apk ...
  • splits को एक साथ इंस्टॉल करें:
bash
adb install-multiple split1.apk split2.apk ...
  • वितरण के लिए, आप splits को APKEditor से एकल APK में मर्ज कर सकते हैं, फिर align/sign करें

ट्यूटोरियल्स

Tutorial 1

स्रोत: https://medium.com/infosec-adventures/introduction-to-frida-5a3f51595ca1
APK: https://github.com/t0thkr1s/frida-demo/releases
Source Code: https://github.com/t0thkr1s/frida-demo

पढ़ने के लिए link to read it.

Tutorial 2

स्रोत: https://11x256.github.io/Frida-hooking-android-part-2/ (Parts 2, 3 & 4)
APKs and Source code: https://github.com/11x256/frida-android-examples

पढ़ने के लिए link to read it.

Tutorial 3

स्रोत: https://joshspicer.com/android-frida-1
APK: https://github.com/OWASP/owasp-mstg/blob/master/Crackmes/Android/Level_01/UnCrackable-Level1.apk

पढ़ने के लिए link to read it.

आप यहाँ और अधिक Awesome Frida scripts पा सकते हैं: https://codeshare.frida.re/

त्वरित उदाहरण

कमांड लाइन से Frida को कॉल करना

bash
frida-ps -U

#Basic frida hooking
frida -l disableRoot.js -f owasp.mstg.uncrackable1

#Hooking before starting the app
frida -U --no-pause -l disableRoot.js -f owasp.mstg.uncrackable1
#The --no-pause and -f options allow the app to be spawned automatically,
#frozen so that the instrumentation can occur, and the automatically
#continue execution with our modified code.

बुनियादी Python स्क्रिप्ट

python
import frida, sys

jscode = open(sys.argv[0]).read()
process = frida.get_usb_device().attach('infosecadventures.fridademo')
script = process.create_script(jscode)
print('[ * ] Running Frida Demo application')
script.load()
sys.stdin.read()

पैरामीटर के बिना फ़ंक्शन्स को Hook करना

क्लास sg.vantagepoint.a.c के फ़ंक्शन a() को Hook करें

javascript
Java.perform(function () {
rootcheck1.a.overload().implementation = function() {
send("sg.vantagepoint.a.c.a()Z   Root check 1 HIT!  su.exists()")
return false;
};
});

Hook java exit()

javascript
var sysexit = Java.use("java.lang.System")
sysexit.exit.overload("int").implementation = function (var_0) {
send("java.lang.System.exit(I)V  // We avoid exiting the application  :)")
}

MainActivity के .onStart() और .onCreate() को Hook करें

javascript
var mainactivity = Java.use("sg.vantagepoint.uncrackable1.MainActivity")
mainactivity.onStart.overload().implementation = function () {
send("MainActivity.onStart() HIT!!!")
var ret = this.onStart.overload().call(this)
}
mainactivity.onCreate.overload("android.os.Bundle").implementation = function (
var_0
) {
send("MainActivity.onCreate() HIT!!!")
var ret = this.onCreate.overload("android.os.Bundle").call(this, var_0)
}

Android .onCreate() को Hook करें

javascript
var activity = Java.use("android.app.Activity")
activity.onCreate.overload("android.os.Bundle").implementation = function (
var_0
) {
send("Activity HIT!!!")
var ret = this.onCreate.overload("android.os.Bundle").call(this, var_0)
}

Hooking functions — पैरामीटर के साथ और मान प्राप्त करना

Hooking a decryption function. इनपुट को print करें, original function को कॉल करके इनपुट को decrypt करें और अंत में plain data print करें:

Hooking a decryption function (Java) — print inputs/outputs
javascript
function getString(data) {
var ret = ""
for (var i = 0; i < data.length; i++) {
ret += data[i].toString()
}
return ret
}
var aes_decrypt = Java.use("sg.vantagepoint.a.a")
aes_decrypt.a.overload("[B", "[B").implementation = function (var_0, var_1) {
send("sg.vantagepoint.a.a.a([B[B)[B   doFinal(enc)  // AES/ECB/PKCS7Padding")
send("Key       : " + getString(var_0))
send("Encrypted : " + getString(var_1))
var ret = this.a.overload("[B", "[B").call(this, var_0, var_1)
send("Decrypted : " + ret)

var flag = ""
for (var i = 0; i < ret.length; i++) {
flag += String.fromCharCode(ret[i])
}
send("Decrypted flag: " + flag)
return ret //[B
}

Hooking functions and calling them with our input

Hook a function जो एक string प्राप्त करता है और उसे किसी अन्य string के साथ कॉल करें (from here)

javascript
var string_class = Java.use("java.lang.String") // get a JS wrapper for java's String class

my_class.fun.overload("java.lang.String").implementation = function (x) {
//hooking the new function
var my_string = string_class.$new("My TeSt String#####") //creating a new String by using `new` operator
console.log("Original arg: " + x)
var ret = this.fun(my_string) // calling the original function with the new String, and putting its return value in ret variable
console.log("Return value: " + ret)
return ret
}

किसी क्लास के पहले से बनाए गए ऑब्जेक्ट को प्राप्त करना

यदि आप किसी बनाए गए ऑब्जेक्ट के किसी attribute को निकालना चाहते हैं तो आप यह तरीका इस्तेमाल कर सकते हैं।

इस उदाहरण में आप देखेंगे कि कैसे क्लास my_activity का ऑब्जेक्ट प्राप्त किया जाए और कैसे फ़ंक्शन .secret() को कॉल किया जाए जो ऑब्जेक्ट के एक निजी attribute को प्रिंट करेगा:

javascript
Java.choose("com.example.a11x256.frida_test.my_activity", {
onMatch: function (instance) {
//This function will be called for every instance found by frida
console.log("Found instance: " + instance)
console.log("Result of secret func: " + instance.secret())
},
onComplete: function () {},
})

अन्य Frida ट्यूटोरियल

संदर्भ

tip

AWS हैकिंग सीखें और अभ्यास करें:HackTricks Training AWS Red Team Expert (ARTE)
GCP हैकिंग सीखें और अभ्यास करें: HackTricks Training GCP Red Team Expert (GRTE) Azure हैकिंग सीखें और अभ्यास करें: HackTricks Training Azure Red Team Expert (AzRTE)

HackTricks का समर्थन करें