anais-apk-forensic 1.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -0
- package/README.md +249 -0
- package/anais.sh +669 -0
- package/analysis_tools/__pycache__/apk_basic_info.cpython-313.pyc +0 -0
- package/analysis_tools/__pycache__/apk_basic_info.cpython-314.pyc +0 -0
- package/analysis_tools/__pycache__/check_zip_encryption.cpython-313.pyc +0 -0
- package/analysis_tools/__pycache__/check_zip_encryption.cpython-314.pyc +0 -0
- package/analysis_tools/__pycache__/detect_obfuscation.cpython-313.pyc +0 -0
- package/analysis_tools/__pycache__/detect_obfuscation.cpython-314.pyc +0 -0
- package/analysis_tools/__pycache__/dex_payload_hunter.cpython-314.pyc +0 -0
- package/analysis_tools/__pycache__/entropy_analyzer.cpython-314.pyc +0 -0
- package/analysis_tools/__pycache__/error_logger.cpython-313.pyc +0 -0
- package/analysis_tools/__pycache__/error_logger.cpython-314.pyc +0 -0
- package/analysis_tools/__pycache__/find_encrypted_payload.cpython-314.pyc +0 -0
- package/analysis_tools/__pycache__/fix_apk_headers.cpython-313.pyc +0 -0
- package/analysis_tools/__pycache__/fix_apk_headers.cpython-314.pyc +0 -0
- package/analysis_tools/__pycache__/manifest_analyzer.cpython-313.pyc +0 -0
- package/analysis_tools/__pycache__/manifest_analyzer.cpython-314.pyc +0 -0
- package/analysis_tools/__pycache__/network_analyzer.cpython-313.pyc +0 -0
- package/analysis_tools/__pycache__/network_analyzer.cpython-314.pyc +0 -0
- package/analysis_tools/__pycache__/report_generator.cpython-313.pyc +0 -0
- package/analysis_tools/__pycache__/report_generator.cpython-314.pyc +0 -0
- package/analysis_tools/__pycache__/report_generator_modular.cpython-314.pyc +0 -0
- package/analysis_tools/__pycache__/sast_scanner.cpython-313.pyc +0 -0
- package/analysis_tools/__pycache__/sast_scanner.cpython-314.pyc +0 -0
- package/analysis_tools/__pycache__/so_string_analyzer.cpython-314.pyc +0 -0
- package/analysis_tools/__pycache__/yara_enhanced_analyzer.cpython-314.pyc +0 -0
- package/analysis_tools/__pycache__/yara_results_processor.cpython-314.pyc +0 -0
- package/analysis_tools/apk_basic_info.py +85 -0
- package/analysis_tools/check_zip_encryption.py +142 -0
- package/analysis_tools/detect_obfuscation.py +650 -0
- package/analysis_tools/dex_payload_hunter.py +734 -0
- package/analysis_tools/entropy_analyzer.py +335 -0
- package/analysis_tools/error_logger.py +75 -0
- package/analysis_tools/find_encrypted_payload.py +485 -0
- package/analysis_tools/fix_apk_headers.py +154 -0
- package/analysis_tools/manifest_analyzer.py +214 -0
- package/analysis_tools/network_analyzer.py +287 -0
- package/analysis_tools/report_generator.py +506 -0
- package/analysis_tools/report_generator_modular.py +885 -0
- package/analysis_tools/sast_scanner.py +412 -0
- package/analysis_tools/so_string_analyzer.py +406 -0
- package/analysis_tools/yara_enhanced_analyzer.py +330 -0
- package/analysis_tools/yara_results_processor.py +368 -0
- package/analyzer_config.json +113 -0
- package/apkid/__init__.py +32 -0
- package/apkid/__pycache__/__init__.cpython-313.pyc +0 -0
- package/apkid/__pycache__/__init__.cpython-314.pyc +0 -0
- package/apkid/__pycache__/apkid.cpython-313.pyc +0 -0
- package/apkid/__pycache__/apkid.cpython-314.pyc +0 -0
- package/apkid/__pycache__/main.cpython-313.pyc +0 -0
- package/apkid/__pycache__/main.cpython-314.pyc +0 -0
- package/apkid/__pycache__/output.cpython-313.pyc +0 -0
- package/apkid/__pycache__/rules.cpython-313.pyc +0 -0
- package/apkid/apkid.py +266 -0
- package/apkid/main.py +98 -0
- package/apkid/output.py +177 -0
- package/apkid/rules/apk/common.yara +68 -0
- package/apkid/rules/apk/obfuscators.yara +118 -0
- package/apkid/rules/apk/packers.yara +1197 -0
- package/apkid/rules/apk/protectors.yara +301 -0
- package/apkid/rules/dex/abnormal.yara +104 -0
- package/apkid/rules/dex/anti-vm.yara +568 -0
- package/apkid/rules/dex/common.yara +60 -0
- package/apkid/rules/dex/compilers.yara +434 -0
- package/apkid/rules/dex/obfuscators.yara +602 -0
- package/apkid/rules/dex/packers.yara +761 -0
- package/apkid/rules/dex/protectors.yara +520 -0
- package/apkid/rules/dll/common.yara +38 -0
- package/apkid/rules/dll/obfuscators.yara +43 -0
- package/apkid/rules/elf/anti-vm.yara +43 -0
- package/apkid/rules/elf/common.yara +54 -0
- package/apkid/rules/elf/obfuscators.yara +991 -0
- package/apkid/rules/elf/packers.yara +1128 -0
- package/apkid/rules/elf/protectors.yara +794 -0
- package/apkid/rules/res/common.yara +43 -0
- package/apkid/rules/res/obfuscators.yara +46 -0
- package/apkid/rules/res/protectors.yara +46 -0
- package/apkid/rules.py +77 -0
- package/bin/anais +3 -0
- package/dist/cli.js +82 -0
- package/dist/index.js +123 -0
- package/dist/types/index.js +2 -0
- package/dist/utils/index.js +21 -0
- package/dist/utils/output.js +44 -0
- package/dist/utils/paths.js +107 -0
- package/docs/ARCHITECTURE.txt +353 -0
- package/docs/Workflow and Reference.md +445 -0
- package/package.json +70 -0
- package/rules/yara_general_rules.yar +323 -0
- package/scripts/dynamic_analysis_helper.sh +334 -0
- package/scripts/frida/dpt_dex_dumper.js +145 -0
- package/scripts/frida/frida_dex_dump.js +145 -0
- package/scripts/frida/frida_hooks.js +437 -0
- package/scripts/frida/frida_websocket_extractor.js +154 -0
- package/scripts/setup.sh +206 -0
- package/scripts/validate_framework.sh +224 -0
- package/src/cli.ts +91 -0
- package/src/index.ts +123 -0
- package/src/types/index.ts +44 -0
- package/src/utils/index.ts +6 -0
- package/src/utils/output.ts +50 -0
- package/src/utils/paths.ts +72 -0
- package/tsconfig.json +14 -0
|
@@ -0,0 +1,437 @@
|
|
|
1
|
+
// ============================================
|
|
2
|
+
// M-Pajak Malware Frida Instrumentation Script
|
|
3
|
+
// ============================================
|
|
4
|
+
// Usage: frida -U -f comeliest.metempsychosis.pokelogan -l frida_hooks.js --no-pause
|
|
5
|
+
|
|
6
|
+
console.log("[*] Starting M-Pajak Malware Analysis...");
|
|
7
|
+
console.log("[*] Target Package: comeliest.metempsychosis.pokelogan");
|
|
8
|
+
console.log("=".repeat(60));
|
|
9
|
+
|
|
10
|
+
// ============================================
|
|
11
|
+
// 1. WEBSOCKET URL CAPTURE (MOST IMPORTANT)
|
|
12
|
+
// ============================================
|
|
13
|
+
Java.perform(function () {
|
|
14
|
+
console.log("\n[+] Hooking WebSocket Connection...");
|
|
15
|
+
|
|
16
|
+
// Hook OkHttp WebSocket creation
|
|
17
|
+
try {
|
|
18
|
+
var OkHttpClient = Java.use("okhttp3.OkHttpClient");
|
|
19
|
+
var Request = Java.use("okhttp3.Request");
|
|
20
|
+
|
|
21
|
+
OkHttpClient.newWebSocket.overload('okhttp3.Request', 'okhttp3.WebSocketListener').implementation = function (request, listener) {
|
|
22
|
+
console.log("\n" + "=".repeat(60));
|
|
23
|
+
console.log("[!] WEBSOCKET CONNECTION INTERCEPTED");
|
|
24
|
+
console.log("=".repeat(60));
|
|
25
|
+
|
|
26
|
+
var url = request.url().toString();
|
|
27
|
+
console.log("[WS] Full URL: " + url);
|
|
28
|
+
|
|
29
|
+
// Extract query parameters
|
|
30
|
+
var uri = request.url();
|
|
31
|
+
console.log("[WS] Scheme: " + uri.scheme());
|
|
32
|
+
console.log("[WS] Host: " + uri.host());
|
|
33
|
+
console.log("[WS] Path: " + uri.encodedPath());
|
|
34
|
+
console.log("[WS] Query: " + uri.encodedQuery());
|
|
35
|
+
|
|
36
|
+
// Extract timestamp and signature
|
|
37
|
+
var timestamp = uri.queryParameter("timeStamp");
|
|
38
|
+
var signature = uri.queryParameter("sign");
|
|
39
|
+
if (timestamp) console.log("[WS] Timestamp: " + timestamp);
|
|
40
|
+
if (signature) console.log("[WS] Signature: " + signature);
|
|
41
|
+
|
|
42
|
+
// Extract device ID from URL
|
|
43
|
+
var pathMatch = url.match(/DEVICE_([a-f0-9]+m2p6)/);
|
|
44
|
+
if (pathMatch) {
|
|
45
|
+
console.log("[WS] Device ID: " + pathMatch[1]);
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
console.log("=".repeat(60) + "\n");
|
|
49
|
+
|
|
50
|
+
return this.newWebSocket(request, listener);
|
|
51
|
+
};
|
|
52
|
+
console.log("[ā] WebSocket hook installed");
|
|
53
|
+
} catch (e) {
|
|
54
|
+
console.log("[!] WebSocket hook failed: " + e);
|
|
55
|
+
}
|
|
56
|
+
});
|
|
57
|
+
|
|
58
|
+
// ============================================
|
|
59
|
+
// 2. DEVICE ID GENERATION
|
|
60
|
+
// ============================================
|
|
61
|
+
Java.perform(function () {
|
|
62
|
+
console.log("\n[+] Hooking Device ID Generation...");
|
|
63
|
+
|
|
64
|
+
try {
|
|
65
|
+
// Hook the device ID generation method
|
|
66
|
+
var C1814a = Java.use("p068k3.C1814a");
|
|
67
|
+
|
|
68
|
+
C1814a.m2375c.implementation = function (context) {
|
|
69
|
+
var deviceId = this.m2375c(context);
|
|
70
|
+
console.log("\n[DEVICE] Generated Device ID: " + deviceId);
|
|
71
|
+
|
|
72
|
+
// Extract Android ID
|
|
73
|
+
var androidId = deviceId.replace("m2p6", "");
|
|
74
|
+
console.log("[DEVICE] Android ID: " + androidId);
|
|
75
|
+
console.log("[DEVICE] Campaign Tag: m2p6\n");
|
|
76
|
+
|
|
77
|
+
return deviceId;
|
|
78
|
+
};
|
|
79
|
+
console.log("[ā] Device ID hook installed");
|
|
80
|
+
} catch (e) {
|
|
81
|
+
console.log("[!] Device ID hook failed: " + e);
|
|
82
|
+
}
|
|
83
|
+
});
|
|
84
|
+
|
|
85
|
+
// ============================================
|
|
86
|
+
// 3. API COMMUNICATION INTERCEPTION
|
|
87
|
+
// ============================================
|
|
88
|
+
Java.perform(function () {
|
|
89
|
+
console.log("\n[+] Hooking API Communication...");
|
|
90
|
+
|
|
91
|
+
try {
|
|
92
|
+
var C1822i = Java.use("p068k3.C1822i");
|
|
93
|
+
|
|
94
|
+
// Hook the main API call method
|
|
95
|
+
C1822i.m2427a.implementation = function (data, callback) {
|
|
96
|
+
console.log("\n" + "=".repeat(60));
|
|
97
|
+
console.log("[!] API CALL INTERCEPTED");
|
|
98
|
+
console.log("=".repeat(60));
|
|
99
|
+
|
|
100
|
+
// Convert data to JSON string for inspection
|
|
101
|
+
try {
|
|
102
|
+
var JSONObject = Java.use("org.json.JSONObject");
|
|
103
|
+
var jsonStr = data.toString();
|
|
104
|
+
console.log("[API] Payload:\n" + jsonStr);
|
|
105
|
+
|
|
106
|
+
// Try to extract specific fields
|
|
107
|
+
if (data.has("action")) {
|
|
108
|
+
console.log("[API] Action: " + data.getString("action"));
|
|
109
|
+
}
|
|
110
|
+
if (data.has("deviceId")) {
|
|
111
|
+
console.log("[API] Device ID: " + data.getString("deviceId"));
|
|
112
|
+
}
|
|
113
|
+
if (data.has("mnemoId")) {
|
|
114
|
+
console.log("[API] šØ MNEMONIC THEFT DETECTED!");
|
|
115
|
+
console.log("[API] Mnemonic: " + data.getString("mnemoId"));
|
|
116
|
+
console.log("[API] Wallet Package: " + data.getString("packageName"));
|
|
117
|
+
}
|
|
118
|
+
} catch (e) {
|
|
119
|
+
console.log("[API] Data: " + data);
|
|
120
|
+
}
|
|
121
|
+
|
|
122
|
+
console.log("=".repeat(60) + "\n");
|
|
123
|
+
|
|
124
|
+
return this.m2427a(data, callback);
|
|
125
|
+
};
|
|
126
|
+
console.log("[ā] API communication hook installed");
|
|
127
|
+
} catch (e) {
|
|
128
|
+
console.log("[!] API hook failed: " + e);
|
|
129
|
+
}
|
|
130
|
+
});
|
|
131
|
+
|
|
132
|
+
// ============================================
|
|
133
|
+
// 4. MNEMONIC STEALING DETECTION
|
|
134
|
+
// ============================================
|
|
135
|
+
Java.perform(function () {
|
|
136
|
+
console.log("\n[+] Hooking Mnemonic Theft Functions...");
|
|
137
|
+
|
|
138
|
+
try {
|
|
139
|
+
var C1819f = Java.use("p068k3.C1819f");
|
|
140
|
+
|
|
141
|
+
// Hook the saveMnemonics method
|
|
142
|
+
C1819f.m2422t.implementation = function (context) {
|
|
143
|
+
console.log("\n" + "šØ".repeat(30));
|
|
144
|
+
console.log("[!!!] MNEMONIC EXFILTRATION ATTEMPT DETECTED");
|
|
145
|
+
console.log("šØ".repeat(30) + "\n");
|
|
146
|
+
|
|
147
|
+
return this.m2422t(context);
|
|
148
|
+
};
|
|
149
|
+
console.log("[ā] Mnemonic theft hook installed");
|
|
150
|
+
} catch (e) {
|
|
151
|
+
console.log("[!] Mnemonic hook failed: " + e);
|
|
152
|
+
}
|
|
153
|
+
|
|
154
|
+
// Hook all InputWords activities
|
|
155
|
+
var wallets = [
|
|
156
|
+
"com.superbock.p020ui.custom.InputWordsImActivity",
|
|
157
|
+
"com.superbock.p020ui.custom.InputWordsTpActivity",
|
|
158
|
+
"com.superbock.p020ui.custom.InputWordsTrustActivity",
|
|
159
|
+
"com.superbock.p020ui.custom.InputWordsMetaActivity",
|
|
160
|
+
"com.superbock.p020ui.custom.InputWordsWalletActivity",
|
|
161
|
+
"com.superbock.p020ui.custom.InputWordsBinanceActivity",
|
|
162
|
+
"com.superbock.p020ui.custom.InputWordsOkxActivity",
|
|
163
|
+
"com.superbock.p020ui.custom.InputWordsTronlinkActivity",
|
|
164
|
+
"com.superbock.p020ui.custom.InputWordsTronglobalActivity"
|
|
165
|
+
];
|
|
166
|
+
|
|
167
|
+
wallets.forEach(function (className) {
|
|
168
|
+
try {
|
|
169
|
+
var WalletActivity = Java.use(className);
|
|
170
|
+
console.log("[ā] Hooked: " + className.split(".").pop());
|
|
171
|
+
} catch (e) {
|
|
172
|
+
// Class not loaded yet
|
|
173
|
+
}
|
|
174
|
+
});
|
|
175
|
+
});
|
|
176
|
+
|
|
177
|
+
// ============================================
|
|
178
|
+
// 5. SHAREDPREFERENCES MONITORING
|
|
179
|
+
// ============================================
|
|
180
|
+
Java.perform(function () {
|
|
181
|
+
console.log("\n[+] Hooking SharedPreferences...");
|
|
182
|
+
|
|
183
|
+
try {
|
|
184
|
+
var SPUtils = Java.use("com.blankj.utilcode.util.SPUtils");
|
|
185
|
+
|
|
186
|
+
// Hook put(String, String)
|
|
187
|
+
SPUtils.put.overload('java.lang.String', 'java.lang.String').implementation = function (key, value) {
|
|
188
|
+
if (key.includes("Domain") || key.includes("Url") || key.includes("deviceId") ||
|
|
189
|
+
key.includes("thumbSnap") || key.includes("host") || key.includes("ws")) {
|
|
190
|
+
console.log("\n[SP] PUT: " + key + " = " + value);
|
|
191
|
+
}
|
|
192
|
+
return this.put(key, value);
|
|
193
|
+
};
|
|
194
|
+
|
|
195
|
+
// Hook getString
|
|
196
|
+
SPUtils.getString.overload('java.lang.String').implementation = function (key) {
|
|
197
|
+
var value = this.getString(key);
|
|
198
|
+
if (key.includes("Domain") || key.includes("Url") || key.includes("deviceId") ||
|
|
199
|
+
key.includes("thumbSnap") || key.includes("host") || key.includes("ws")) {
|
|
200
|
+
console.log("[SP] GET: " + key + " = " + value);
|
|
201
|
+
}
|
|
202
|
+
return value;
|
|
203
|
+
};
|
|
204
|
+
|
|
205
|
+
console.log("[ā] SharedPreferences hook installed");
|
|
206
|
+
} catch (e) {
|
|
207
|
+
console.log("[!] SharedPreferences hook failed: " + e);
|
|
208
|
+
}
|
|
209
|
+
});
|
|
210
|
+
|
|
211
|
+
// ============================================
|
|
212
|
+
// 6. NETWORK TRAFFIC (OkHttp Interceptor)
|
|
213
|
+
// ============================================
|
|
214
|
+
Java.perform(function () {
|
|
215
|
+
console.log("\n[+] Hooking Network Traffic...");
|
|
216
|
+
|
|
217
|
+
try {
|
|
218
|
+
var Call = Java.use("okhttp3.Call");
|
|
219
|
+
var Request = Java.use("okhttp3.Request");
|
|
220
|
+
|
|
221
|
+
// Hook execute() for synchronous calls
|
|
222
|
+
Call.execute.implementation = function () {
|
|
223
|
+
var request = this.request();
|
|
224
|
+
var url = request.url().toString();
|
|
225
|
+
var method = request.method();
|
|
226
|
+
|
|
227
|
+
if (url.includes("a2decxd8syw7k") || url.includes("thumbsnap")) {
|
|
228
|
+
console.log("\n[NET] " + method + " " + url);
|
|
229
|
+
|
|
230
|
+
// Try to log headers
|
|
231
|
+
var headers = request.headers();
|
|
232
|
+
if (headers.size() > 0) {
|
|
233
|
+
console.log("[NET] Headers: " + headers.toString());
|
|
234
|
+
}
|
|
235
|
+
}
|
|
236
|
+
|
|
237
|
+
return this.execute();
|
|
238
|
+
};
|
|
239
|
+
|
|
240
|
+
console.log("[ā] Network traffic hook installed");
|
|
241
|
+
} catch (e) {
|
|
242
|
+
console.log("[!] Network hook failed: " + e);
|
|
243
|
+
}
|
|
244
|
+
});
|
|
245
|
+
|
|
246
|
+
// ============================================
|
|
247
|
+
// 7. ACCESSIBILITY SERVICE MONITORING
|
|
248
|
+
// ============================================
|
|
249
|
+
Java.perform(function () {
|
|
250
|
+
console.log("\n[+] Hooking Accessibility Service...");
|
|
251
|
+
|
|
252
|
+
try {
|
|
253
|
+
var BaseService = Java.use("com.superbock.auto.BaseService");
|
|
254
|
+
|
|
255
|
+
// Hook onAccessibilityEvent
|
|
256
|
+
BaseService.onAccessibilityEvent.implementation = function (event) {
|
|
257
|
+
var eventType = event.getEventType();
|
|
258
|
+
var packageName = event.getPackageName();
|
|
259
|
+
|
|
260
|
+
if (packageName && packageName.toString().includes("wallet") ||
|
|
261
|
+
packageName.toString().includes("metamask") ||
|
|
262
|
+
packageName.toString().includes("trust") ||
|
|
263
|
+
packageName.toString().includes("token")) {
|
|
264
|
+
console.log("\n[A11Y] šÆ Target App Detected: " + packageName);
|
|
265
|
+
console.log("[A11Y] Event Type: " + eventType);
|
|
266
|
+
}
|
|
267
|
+
|
|
268
|
+
return this.onAccessibilityEvent(event);
|
|
269
|
+
};
|
|
270
|
+
|
|
271
|
+
console.log("[ā] Accessibility Service hook installed");
|
|
272
|
+
} catch (e) {
|
|
273
|
+
console.log("[!] Accessibility hook failed: " + e);
|
|
274
|
+
}
|
|
275
|
+
});
|
|
276
|
+
|
|
277
|
+
// ============================================
|
|
278
|
+
// 8. SMS INTERCEPTION
|
|
279
|
+
// ============================================
|
|
280
|
+
Java.perform(function () {
|
|
281
|
+
console.log("\n[+] Hooking SMS Operations...");
|
|
282
|
+
|
|
283
|
+
try {
|
|
284
|
+
var SmsManager = Java.use("android.telephony.SmsManager");
|
|
285
|
+
|
|
286
|
+
// Hook sendTextMessage
|
|
287
|
+
SmsManager.sendTextMessage.implementation = function (dest, scAddr, text, sentIntent, deliveryIntent) {
|
|
288
|
+
console.log("\n[SMS] šØ SMS BEING SENT!");
|
|
289
|
+
console.log("[SMS] To: " + dest);
|
|
290
|
+
console.log("[SMS] Text: " + text);
|
|
291
|
+
|
|
292
|
+
// Optionally block the SMS
|
|
293
|
+
// return; // Uncomment to block
|
|
294
|
+
|
|
295
|
+
return this.sendTextMessage(dest, scAddr, text, sentIntent, deliveryIntent);
|
|
296
|
+
};
|
|
297
|
+
|
|
298
|
+
console.log("[ā] SMS hook installed");
|
|
299
|
+
} catch (e) {
|
|
300
|
+
console.log("[!] SMS hook failed: " + e);
|
|
301
|
+
}
|
|
302
|
+
});
|
|
303
|
+
|
|
304
|
+
// ============================================
|
|
305
|
+
// 9. C2 DOMAIN CHANGES
|
|
306
|
+
// ============================================
|
|
307
|
+
Java.perform(function () {
|
|
308
|
+
console.log("\n[+] Hooking C2 Configuration...");
|
|
309
|
+
|
|
310
|
+
try {
|
|
311
|
+
var C1755j0 = Java.use("p064k.C1755j0");
|
|
312
|
+
|
|
313
|
+
// Hook domain setter
|
|
314
|
+
C1755j0.m2316p.implementation = function (domainList) {
|
|
315
|
+
console.log("\n[C2] š Domain Configuration Update");
|
|
316
|
+
console.log("[C2] New Domains: " + domainList);
|
|
317
|
+
return this.m2316p(domainList);
|
|
318
|
+
};
|
|
319
|
+
|
|
320
|
+
// Hook API host setter
|
|
321
|
+
C1755j0.m2325y.implementation = function (domain) {
|
|
322
|
+
console.log("[C2] New API Host: https://" + domain + "/appapi");
|
|
323
|
+
return this.m2325y(domain);
|
|
324
|
+
};
|
|
325
|
+
|
|
326
|
+
// Hook WebSocket URL setter
|
|
327
|
+
C1755j0.m2301D.implementation = function (domain) {
|
|
328
|
+
console.log("[C2] New WebSocket URL: wss://" + domain + "/websocket/message/DEVICE_");
|
|
329
|
+
return this.m2301D(domain);
|
|
330
|
+
};
|
|
331
|
+
|
|
332
|
+
console.log("[ā] C2 configuration hook installed");
|
|
333
|
+
} catch (e) {
|
|
334
|
+
console.log("[!] C2 hook failed: " + e);
|
|
335
|
+
}
|
|
336
|
+
});
|
|
337
|
+
|
|
338
|
+
// ============================================
|
|
339
|
+
// 10. CRYPTO SIGNATURE CALCULATION
|
|
340
|
+
// ============================================
|
|
341
|
+
Java.perform(function () {
|
|
342
|
+
console.log("\n[+] Hooking Signature Generation...");
|
|
343
|
+
|
|
344
|
+
try {
|
|
345
|
+
// Hook MessageDigest for hash calculation
|
|
346
|
+
var MessageDigest = Java.use("java.security.MessageDigest");
|
|
347
|
+
var originalDigest = MessageDigest.digest.overload('[B');
|
|
348
|
+
|
|
349
|
+
MessageDigest.digest.overload('[B').implementation = function (input) {
|
|
350
|
+
var result = originalDigest.call(this, input);
|
|
351
|
+
var algorithm = this.getAlgorithm();
|
|
352
|
+
|
|
353
|
+
if (algorithm.includes("MD5") || algorithm.includes("SHA")) {
|
|
354
|
+
var inputStr = "";
|
|
355
|
+
try {
|
|
356
|
+
inputStr = Java.use("java.lang.String").$new(input);
|
|
357
|
+
} catch (e) { }
|
|
358
|
+
|
|
359
|
+
console.log("\n[HASH] Algorithm: " + algorithm);
|
|
360
|
+
if (inputStr.length < 200) {
|
|
361
|
+
console.log("[HASH] Input: " + inputStr);
|
|
362
|
+
}
|
|
363
|
+
|
|
364
|
+
// Convert result to hex
|
|
365
|
+
var hex = "";
|
|
366
|
+
for (var i = 0; i < result.length && i < 32; i++) {
|
|
367
|
+
var b = result[i];
|
|
368
|
+
hex += ("0" + (b & 0xFF).toString(16)).slice(-2);
|
|
369
|
+
}
|
|
370
|
+
console.log("[HASH] Output: " + hex);
|
|
371
|
+
}
|
|
372
|
+
|
|
373
|
+
return result;
|
|
374
|
+
};
|
|
375
|
+
|
|
376
|
+
console.log("[ā] Signature generation hook installed");
|
|
377
|
+
} catch (e) {
|
|
378
|
+
console.log("[!] Signature hook failed: " + e);
|
|
379
|
+
}
|
|
380
|
+
});
|
|
381
|
+
|
|
382
|
+
// ============================================
|
|
383
|
+
// 11. FILE UPLOAD MONITORING (Thumbsnap)
|
|
384
|
+
// ============================================
|
|
385
|
+
Java.perform(function () {
|
|
386
|
+
console.log("\n[+] Hooking File Uploads...");
|
|
387
|
+
|
|
388
|
+
try {
|
|
389
|
+
var C1815b = Java.use("p068k3.C1815b");
|
|
390
|
+
|
|
391
|
+
// Hook upload method
|
|
392
|
+
C1815b.m2383a.implementation = function (context, file, callback) {
|
|
393
|
+
console.log("\n[UPLOAD] šø File Upload to Thumbsnap");
|
|
394
|
+
console.log("[UPLOAD] File: " + file);
|
|
395
|
+
console.log("[UPLOAD] API Key: 000461e4aa61d5ddb037f501186ea825");
|
|
396
|
+
console.log("[UPLOAD] Endpoint: https://thumbsnap.com/api/upload");
|
|
397
|
+
|
|
398
|
+
return this.m2383a(context, file, callback);
|
|
399
|
+
};
|
|
400
|
+
|
|
401
|
+
console.log("[ā] File upload hook installed");
|
|
402
|
+
} catch (e) {
|
|
403
|
+
console.log("[!] Upload hook failed: " + e);
|
|
404
|
+
}
|
|
405
|
+
});
|
|
406
|
+
|
|
407
|
+
// ============================================
|
|
408
|
+
// 12. RUNTIME ACTIVITY MONITORING
|
|
409
|
+
// ============================================
|
|
410
|
+
Java.perform(function () {
|
|
411
|
+
console.log("\n[+] Hooking Activity Lifecycle...");
|
|
412
|
+
|
|
413
|
+
try {
|
|
414
|
+
var Activity = Java.use("android.app.Activity");
|
|
415
|
+
|
|
416
|
+
Activity.onCreate.overload('android.os.Bundle').implementation = function (bundle) {
|
|
417
|
+
var activityName = this.getClass().getName();
|
|
418
|
+
if (activityName.includes("superbock") || activityName.includes("InputWords")) {
|
|
419
|
+
console.log("\n[ACTIVITY] š± Launched: " + activityName);
|
|
420
|
+
}
|
|
421
|
+
return this.onCreate(bundle);
|
|
422
|
+
};
|
|
423
|
+
|
|
424
|
+
console.log("[ā] Activity monitoring hook installed");
|
|
425
|
+
} catch (e) {
|
|
426
|
+
console.log("[!] Activity hook failed: " + e);
|
|
427
|
+
}
|
|
428
|
+
});
|
|
429
|
+
|
|
430
|
+
// ============================================
|
|
431
|
+
// FINAL STATUS
|
|
432
|
+
// ============================================
|
|
433
|
+
console.log("\n" + "=".repeat(60));
|
|
434
|
+
console.log("[ā] Frida instrumentation complete!");
|
|
435
|
+
console.log("[*] Monitoring in real-time...");
|
|
436
|
+
console.log("[*] Trigger malware activities to see intercepted data");
|
|
437
|
+
console.log("=".repeat(60) + "\n");
|
|
@@ -0,0 +1,154 @@
|
|
|
1
|
+
// ============================================
|
|
2
|
+
// M-Pajak WebSocket URL Extractor (Focused)
|
|
3
|
+
// ============================================
|
|
4
|
+
// This script specifically extracts the COMPLETE WebSocket URL
|
|
5
|
+
// with timestamp and signature for sandbox testing
|
|
6
|
+
//
|
|
7
|
+
// Usage: frida -U -f comeliest.metempsychosis.pokelogan -l frida_websocket_extractor.js --no-pause
|
|
8
|
+
|
|
9
|
+
console.log("=".repeat(70));
|
|
10
|
+
console.log("M-PAJAK WEBSOCKET URL EXTRACTOR");
|
|
11
|
+
console.log("=".repeat(70));
|
|
12
|
+
|
|
13
|
+
var completeUrl = null;
|
|
14
|
+
var deviceId = null;
|
|
15
|
+
var timestamp = null;
|
|
16
|
+
var signature = null;
|
|
17
|
+
|
|
18
|
+
// ============================================
|
|
19
|
+
// 1. Extract Device ID First
|
|
20
|
+
// ============================================
|
|
21
|
+
Java.perform(function () {
|
|
22
|
+
try {
|
|
23
|
+
var C1814a = Java.use("p068k3.C1814a");
|
|
24
|
+
|
|
25
|
+
C1814a.m2375c.implementation = function (context) {
|
|
26
|
+
deviceId = this.m2375c(context);
|
|
27
|
+
console.log("\n[1/3] Device ID Extracted:");
|
|
28
|
+
console.log(" " + deviceId);
|
|
29
|
+
return deviceId;
|
|
30
|
+
};
|
|
31
|
+
} catch (e) {
|
|
32
|
+
console.log("[!] Could not hook device ID: " + e);
|
|
33
|
+
}
|
|
34
|
+
});
|
|
35
|
+
|
|
36
|
+
// ============================================
|
|
37
|
+
// 2. Capture Signature Calculation
|
|
38
|
+
// ============================================
|
|
39
|
+
Java.perform(function () {
|
|
40
|
+
try {
|
|
41
|
+
// Hook the point where signature is calculated (around line 2990 in C1355i.java)
|
|
42
|
+
var C1355i = Java.use("p038f3.C1355i");
|
|
43
|
+
|
|
44
|
+
// Find the method that builds the WebSocket connection
|
|
45
|
+
// This is tricky, we need to hook the actual signature building
|
|
46
|
+
|
|
47
|
+
// Alternative: Hook MessageDigest to capture the signature
|
|
48
|
+
var MessageDigest = Java.use("java.security.MessageDigest");
|
|
49
|
+
var originalDigest = MessageDigest.digest.overload('[B');
|
|
50
|
+
|
|
51
|
+
MessageDigest.digest.overload('[B').implementation = function (input) {
|
|
52
|
+
var result = originalDigest.call(this, input);
|
|
53
|
+
|
|
54
|
+
// Convert to hex string
|
|
55
|
+
var hex = "";
|
|
56
|
+
for (var i = 0; i < result.length; i++) {
|
|
57
|
+
var b = result[i];
|
|
58
|
+
hex += ("0" + (b & 0xFF).toString(16)).slice(-2);
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
// If this looks like a signature (MD5 = 32 chars, SHA256 = 64 chars)
|
|
62
|
+
if (hex.length >= 32 && hex.length <= 64) {
|
|
63
|
+
console.log("\n[2/3] Possible Signature Detected:");
|
|
64
|
+
console.log(" Algorithm: " + this.getAlgorithm());
|
|
65
|
+
console.log(" Hash: " + hex);
|
|
66
|
+
signature = hex;
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
return result;
|
|
70
|
+
};
|
|
71
|
+
} catch (e) {
|
|
72
|
+
console.log("[!] Could not hook signature: " + e);
|
|
73
|
+
}
|
|
74
|
+
});
|
|
75
|
+
|
|
76
|
+
// ============================================
|
|
77
|
+
// 3. Intercept Complete WebSocket URL
|
|
78
|
+
// ============================================
|
|
79
|
+
Java.perform(function () {
|
|
80
|
+
try {
|
|
81
|
+
var OkHttpClient = Java.use("okhttp3.OkHttpClient");
|
|
82
|
+
|
|
83
|
+
OkHttpClient.newWebSocket.overload('okhttp3.Request', 'okhttp3.WebSocketListener').implementation = function (request, listener) {
|
|
84
|
+
var url = request.url().toString();
|
|
85
|
+
|
|
86
|
+
if (url.includes("websocket/message/DEVICE_")) {
|
|
87
|
+
completeUrl = url;
|
|
88
|
+
|
|
89
|
+
var uri = request.url();
|
|
90
|
+
timestamp = uri.queryParameter("timeStamp");
|
|
91
|
+
var sign = uri.queryParameter("sign");
|
|
92
|
+
|
|
93
|
+
console.log("\n" + "=".repeat(70));
|
|
94
|
+
console.log("šÆ COMPLETE WEBSOCKET URL CAPTURED!");
|
|
95
|
+
console.log("=".repeat(70));
|
|
96
|
+
console.log("\nFull URL:");
|
|
97
|
+
console.log(url);
|
|
98
|
+
console.log("\n" + "-".repeat(70));
|
|
99
|
+
console.log("Components:");
|
|
100
|
+
console.log("-".repeat(70));
|
|
101
|
+
console.log("Base URL: wss://" + uri.host() + uri.encodedPath());
|
|
102
|
+
console.log("Device ID: " + (deviceId || "Already captured above"));
|
|
103
|
+
console.log("Timestamp: " + timestamp);
|
|
104
|
+
console.log("Signature: " + sign);
|
|
105
|
+
console.log("-".repeat(70));
|
|
106
|
+
|
|
107
|
+
// Save to file (Frida can't write files, but we can log it)
|
|
108
|
+
console.log("\nš COPY THIS FOR SANDBOX TESTING:");
|
|
109
|
+
console.log("-".repeat(70));
|
|
110
|
+
console.log(url);
|
|
111
|
+
console.log("-".repeat(70));
|
|
112
|
+
|
|
113
|
+
// Also provide wscat command
|
|
114
|
+
console.log("\nš» WSCAT COMMAND:");
|
|
115
|
+
console.log("-".repeat(70));
|
|
116
|
+
console.log('wscat -c "' + url + '"');
|
|
117
|
+
console.log("-".repeat(70));
|
|
118
|
+
|
|
119
|
+
// Python command
|
|
120
|
+
console.log("\nš PYTHON COMMAND:");
|
|
121
|
+
console.log("-".repeat(70));
|
|
122
|
+
console.log("import websocket");
|
|
123
|
+
console.log('ws = websocket.create_connection("' + url + '")');
|
|
124
|
+
console.log("print(ws.recv())");
|
|
125
|
+
console.log("-".repeat(70));
|
|
126
|
+
|
|
127
|
+
console.log("\nā
WebSocket URL extraction complete!\n");
|
|
128
|
+
}
|
|
129
|
+
|
|
130
|
+
return this.newWebSocket(request, listener);
|
|
131
|
+
};
|
|
132
|
+
} catch (e) {
|
|
133
|
+
console.log("[!] Could not hook WebSocket: " + e);
|
|
134
|
+
}
|
|
135
|
+
});
|
|
136
|
+
|
|
137
|
+
// ============================================
|
|
138
|
+
// 4. Monitor when WebSocket sends data
|
|
139
|
+
// ============================================
|
|
140
|
+
Java.perform(function () {
|
|
141
|
+
try {
|
|
142
|
+
var WebSocket = Java.use("okhttp3.WebSocket");
|
|
143
|
+
|
|
144
|
+
// Hook send method if available
|
|
145
|
+
console.log("[*] Attempting to hook WebSocket send methods...");
|
|
146
|
+
|
|
147
|
+
} catch (e) {
|
|
148
|
+
console.log("[!] Could not hook WebSocket send: " + e);
|
|
149
|
+
}
|
|
150
|
+
});
|
|
151
|
+
|
|
152
|
+
console.log("\n[*] Hooks installed. Waiting for WebSocket connection...");
|
|
153
|
+
console.log("[*] Trigger the malware to connect (open app, trigger notification, etc.)");
|
|
154
|
+
console.log("[*] The complete URL will be displayed when connection is made\n");
|