mirror of
https://github.com/HackTricks-wiki/hacktricks.git
synced 2025-10-10 18:36:50 +00:00
Translated ['src/mobile-pentesting/android-app-pentesting/smali-changes.
This commit is contained in:
parent
9509870c89
commit
d005dc1e3c
@ -2,7 +2,7 @@
|
||||
|
||||
{{#include ../../banners/hacktricks-training.md}}
|
||||
|
||||
## CheatSheets de Forense
|
||||
## Hojas de referencia forense
|
||||
|
||||
[https://www.jaiminton.com/cheatsheet/DFIR/#](https://www.jaiminton.com/cheatsheet/DFIR/)
|
||||
|
||||
@ -14,7 +14,7 @@
|
||||
- [Intezer](https://analyze.intezer.com)
|
||||
- [Any.Run](https://any.run/)
|
||||
|
||||
## Herramientas de antivirus y detección sin conexión
|
||||
## Herramientas antivirus y de detección sin conexión
|
||||
|
||||
### Yara
|
||||
|
||||
@ -36,7 +36,7 @@ python malware_yara_rules.py
|
||||
yara -w malware_rules.yar image #Scan 1 file
|
||||
yara -w malware_rules.yar folder #Scan the whole folder
|
||||
```
|
||||
#### YaraGen: Detectar malware y crear reglas
|
||||
#### YaraGen: Comprobar malware y crear reglas
|
||||
|
||||
Puedes usar la herramienta [**YaraGen**](https://github.com/Neo23x0/yarGen) para generar yara rules a partir de un binario. Consulta estos tutoriales: [**Part 1**](https://www.nextron-systems.com/2015/02/16/write-simple-sound-yara-rules/), [**Part 2**](https://www.nextron-systems.com/2015/10/17/how-to-write-simple-but-sound-yara-rules-part-2/), [**Part 3**](https://www.nextron-systems.com/2016/04/15/how-to-write-simple-but-sound-yara-rules-part-3/)
|
||||
```bash
|
||||
@ -57,20 +57,20 @@ clamscan folderpath #Scan the whole folder
|
||||
```
|
||||
### [Capa](https://github.com/mandiant/capa)
|
||||
|
||||
**Capa** detecta potencialmente maliciosas **capabilities** en ejecutables: PE, ELF, .NET. Así que encontrará cosas como Att\&ck tactics, o capacidades sospechosas como:
|
||||
**Capa** detecta **capacidades** potencialmente maliciosas en ejecutables: PE, ELF, .NET. Por lo tanto encontrará cosas como Att\&ck tactics, o capacidades sospechosas como:
|
||||
|
||||
- check for OutputDebugString error
|
||||
- run as a service
|
||||
- create process
|
||||
- comprobar error de OutputDebugString
|
||||
- ejecutarse como un servicio
|
||||
- crear proceso
|
||||
|
||||
Consíguelo en el [**Github repo**](https://github.com/mandiant/capa).
|
||||
|
||||
### IOCs
|
||||
|
||||
IOC means Indicator Of Compromise. Un IOC es un conjunto de **condiciones que identifican** algún software potencialmente no deseado o confirmado **malware**. Blue Teams usan este tipo de definiciones para **buscar este tipo de archivos maliciosos** en sus **sistemas** y **redes**.\
|
||||
IOC significa Indicator Of Compromise. Un IOC es un conjunto de **condiciones que identifican** algún software potencialmente no deseado o confirmado **malware**. Los Blue Teams usan este tipo de definiciones para **buscar este tipo de archivos maliciosos** en sus **sistemas** y **redes**.\
|
||||
Compartir estas definiciones es muy útil, ya que cuando se identifica malware en un equipo y se crea un IOC para ese malware, otros Blue Teams pueden usarlo para identificar el malware más rápido.
|
||||
|
||||
A tool to create or modify IOCs is [**IOC Editor**](https://www.fireeye.com/services/freeware/ioc-editor.html)**.**\
|
||||
Una herramienta para crear o modificar IOCs es [**IOC Editor**](https://www.fireeye.com/services/freeware/ioc-editor.html)**.**\
|
||||
Puedes usar herramientas como [**Redline**](https://www.fireeye.com/services/freeware/redline.html) para **buscar IOCs definidos en un dispositivo**.
|
||||
|
||||
### Loki
|
||||
@ -92,41 +92,41 @@ Compares process connection endpoints with C2 IOCs (new since version v.10)
|
||||
```
|
||||
### Linux Malware Detect
|
||||
|
||||
[**Linux Malware Detect (LMD)**](https://www.rfxn.com/projects/linux-malware-detect/) es un escáner de malware para Linux publicado bajo la licencia GNU GPLv2, diseñado en torno a las amenazas que se enfrentan en entornos de hosting compartido. Utiliza datos de amenazas de sistemas de detección de intrusiones en el perímetro de la red para extraer malware que se está usando activamente en ataques y genera firmas para su detección. Además, los datos de amenazas también se derivan de envíos de usuarios mediante la LMD checkout feature y de recursos comunitarios de malware.
|
||||
[**Linux Malware Detect (LMD)**](https://www.rfxn.com/projects/linux-malware-detect/) es un escáner de malware para Linux publicado bajo la licencia GNU GPLv2, diseñado en torno a las amenazas que se enfrentan en entornos de hosting compartido. Utiliza datos de amenazas procedentes de sistemas de detección de intrusiones en el perímetro de la red para extraer malware que se está usando activamente en ataques y genera firmas para su detección. Además, los datos de amenazas también provienen de envíos de usuarios mediante la función LMD checkout y de recursos de la comunidad de malware.
|
||||
|
||||
### rkhunter
|
||||
|
||||
Herramientas como [**rkhunter**](http://rkhunter.sourceforge.net) pueden usarse para comprobar el filesystem en busca de posibles **rootkits** y malware.
|
||||
Herramientas como [**rkhunter**](http://rkhunter.sourceforge.net) pueden usarse para revisar el sistema de archivos en busca de posibles **rootkits** y malware.
|
||||
```bash
|
||||
sudo ./rkhunter --check -r / -l /tmp/rkhunter.log [--report-warnings-only] [--skip-keypress]
|
||||
```
|
||||
### FLOSS
|
||||
|
||||
[**FLOSS**](https://github.com/mandiant/flare-floss) es una herramienta que intentará encontrar obfuscated strings dentro de executables utilizando diferentes técnicas.
|
||||
[**FLOSS**](https://github.com/mandiant/flare-floss) es una herramienta que intentará encontrar cadenas ofuscadas dentro de ejecutables usando diferentes técnicas.
|
||||
|
||||
### PEpper
|
||||
|
||||
[PEpper ](https://github.com/Th3Hurrican3/PEpper) comprueba algunas cosas básicas dentro del executable (binary data, entropy, URLs and IPs, algunas yara rules).
|
||||
[PEpper ](https://github.com/Th3Hurrican3/PEpper) comprueba algunas cosas básicas dentro del ejecutable (datos binarios, entropía, URLs e IPs, algunas yara rules).
|
||||
|
||||
### PEstudio
|
||||
|
||||
[PEstudio](https://www.winitor.com/download) es una herramienta que permite obtener información de Windows executables como imports, exports y headers, pero también consultará virus total y encontrará posibles Att\&ck techniques.
|
||||
[PEstudio](https://www.winitor.com/download) es una herramienta que permite obtener información de ejecutables de Windows como imports, exports, headers, pero también consultará virus total y encontrará posibles técnicas Att\&ck.
|
||||
|
||||
### Detect It Easy(DiE)
|
||||
|
||||
[**DiE**](https://github.com/horsicq/Detect-It-Easy/) es una herramienta para detectar si un archivo está **encrypted** y también encontrar **packers**.
|
||||
[**DiE**](https://github.com/horsicq/Detect-It-Easy/) es una herramienta para detectar si un archivo está **cifrado** y también encontrar **packers**.
|
||||
|
||||
### NeoPI
|
||||
|
||||
[**NeoPI** ](https://github.com/CiscoCXSecurity/NeoPI) es un script Python que utiliza una variedad de **statistical methods** para detectar contenido **obfuscated** y **encrypted** dentro de text/script files. El propósito de NeoPI es ayudar en la **detection of hidden web shell code**.
|
||||
[**NeoPI** ](https://github.com/CiscoCXSecurity/NeoPI) es un script Python que utiliza una variedad de **métodos estadísticos** para detectar contenido **ofuscado** y **cifrado** dentro de archivos de texto/script. El propósito previsto de NeoPI es ayudar en la **detección de código de web shell oculto**.
|
||||
|
||||
### **php-malware-finder**
|
||||
|
||||
[**PHP-malware-finder**](https://github.com/nbs-system/php-malware-finder) hace todo lo posible para detectar **obfuscated**/**dodgy code** así como archivos que usan **PHP** functions frecuentemente usadas en **malwares**/webshells.
|
||||
[**PHP-malware-finder**](https://github.com/nbs-system/php-malware-finder) hace todo lo posible por detectar **ofuscado**/**código sospechoso** así como archivos que usan funciones **PHP** frecuentemente usadas en **malwares**/webshells.
|
||||
|
||||
### Apple Binary Signatures
|
||||
|
||||
Al revisar alguna **malware sample** siempre deberías **check the signature** del binary, ya que el **developer** que lo firmó puede ya estar **related** con **malware.**
|
||||
Al analizar alguna **malware sample** siempre deberías **comprobar la firma** del binario, ya que el **desarrollador** que lo firmó puede ya estar **relacionado** con **malware.**
|
||||
```bash
|
||||
#Get signer
|
||||
codesign -vv -d /bin/ls 2>&1 | grep -E "Authority|TeamIdentifier"
|
||||
@ -141,7 +141,7 @@ spctl --assess --verbose /Applications/Safari.app
|
||||
|
||||
### File Stacking
|
||||
|
||||
Si sabes que una carpeta que contiene los **archivos** de un servidor web fue **actualizada por última vez en una fecha determinada**. **Comprueba** la **fecha** en que todos los **archivos** del **servidor web** fueron creados y modificados y si alguna fecha es **sospechosa**, revisa ese archivo.
|
||||
Si sabes que alguna carpeta que contiene los **archivos** de un **servidor web** fue **actualizada por última vez en cierta fecha**, **comprueba** la **fecha** en la que todos los **archivos** en el **servidor web** fueron creados y modificados; si alguna fecha es **sospechosa**, revisa ese archivo.
|
||||
|
||||
### Baselines
|
||||
|
||||
@ -149,15 +149,15 @@ Si los archivos de una carpeta **no deberían haber sido modificados**, puedes c
|
||||
|
||||
### Statistical Analysis
|
||||
|
||||
Cuando la información se guarda en logs puedes **comprobar estadísticas como cuántas veces se accedió a cada archivo del servidor web**, ya que un web shell podría ser uno de los más accedidos.
|
||||
Cuando la información se guarda en logs puedes **verificar estadísticas como cuántas veces se accedió a cada archivo del servidor web, ya que un web shell podría ser uno de los más**.
|
||||
|
||||
---
|
||||
|
||||
### Android in-app native telemetry (no root)
|
||||
### Android: telemetría nativa dentro de la app (sin root)
|
||||
|
||||
En Android, puedes instrumentar código nativo dentro del proceso de la app objetivo precargando una pequeña librería logger antes de que otras libs JNI se inicialicen. Esto proporciona visibilidad temprana del comportamiento nativo sin hooks a nivel de sistema ni root. Un enfoque popular es SoTap: coloca libsotap.so para el ABI adecuado dentro del APK e inyecta una llamada System.loadLibrary("sotap") de forma temprana (p. ej., en un inicializador estático o en Application.onCreate), luego recoge logs desde rutas internas/externas o, como fallback, desde Logcat.
|
||||
En Android, puedes instrumentar código nativo dentro del proceso de la app objetivo precargando una pequeña librería logger antes de que otras librerías JNI se inicialicen. Esto ofrece visibilidad temprana del comportamiento nativo sin hooks a nivel de sistema ni root. Un enfoque popular es SoTap: coloca libsotap.so para el ABI correcto dentro del APK e injerta una llamada System.loadLibrary("sotap") temprano (p. ej., en un static initializer o Application.onCreate), luego recoge logs desde rutas internas/externas o, como fallback, Logcat.
|
||||
|
||||
Consulta la página de reversing nativo para Android para detalles de configuración y rutas de logs:
|
||||
See the Android native reversing page for setup details and log paths:
|
||||
|
||||
{{#ref}}
|
||||
../../mobile-pentesting/android-app-pentesting/reversing-native-libraries.md
|
||||
@ -165,13 +165,13 @@ Consulta la página de reversing nativo para Android para detalles de configurac
|
||||
|
||||
---
|
||||
|
||||
## Desofuscación del flujo de control dinámico (JMP/CALL RAX Dispatchers)
|
||||
## Deobfuscating Dynamic Control-Flow (JMP/CALL RAX Dispatchers)
|
||||
|
||||
Las familias de malware modernas abusan intensamente de la ofuscación del Control-Flow Graph (CFG): en lugar de un salto/llamada directo calculan el destino en tiempo de ejecución y ejecutan un `jmp rax` o `call rax`. Un pequeño *dispatcher* (típicamente nueve instrucciones) establece el objetivo final dependiendo de las banderas `ZF`/`CF` de la CPU, rompiendo por completo la recuperación estática del CFG.
|
||||
Modern malware families heavily abuse Control-Flow Graph (CFG) obfuscation: instead of a direct jump/call they compute the destination at run-time and execute a `jmp rax` or `call rax`. A small *dispatcher* (typically nine instructions) sets the final target depending on the CPU `ZF`/`CF` flags, completely breaking static CFG recovery.
|
||||
|
||||
La técnica —demostrada por el loader SLOW#TEMPEST— puede ser derrotada con un flujo de trabajo de tres pasos que sólo requiere IDAPython y el emulador CPU Unicorn.
|
||||
The technique – showcased by the SLOW#TEMPEST loader – can be defeated with a three-step workflow that only relies on IDAPython and the Unicorn CPU emulator.
|
||||
|
||||
### 1. Localizar cada salto/llamada indirecta
|
||||
### 1. Localiza todos los saltos/llamadas indirectos
|
||||
```python
|
||||
import idautils, idc
|
||||
|
||||
@ -180,7 +180,7 @@ mnem = idc.print_insn_mnem(ea)
|
||||
if mnem in ("jmp", "call") and idc.print_operand(ea, 0) == "rax":
|
||||
print(f"[+] Dispatcher found @ {ea:X}")
|
||||
```
|
||||
### 2. Extraer el byte-code del dispatcher
|
||||
### 2. Extraer el dispatcher byte-code
|
||||
```python
|
||||
import idc
|
||||
|
||||
@ -211,9 +211,9 @@ mu.reg_write(UC_X86_REG_RAX, 0)
|
||||
mu.emu_start(BASE, BASE+len(code))
|
||||
return mu.reg_read(UC_X86_REG_RAX)
|
||||
```
|
||||
Ejecute `run(code,0,0)` y `run(code,1,1)` para obtener los objetivos de las ramas *false* y *true*.
|
||||
Ejecuta `run(code,0,0)` y `run(code,1,1)` para obtener los objetivos de las ramas *falsa* y *verdadera*.
|
||||
|
||||
### 4. Parchear de nuevo un jump / call directo
|
||||
### 4. Parchear de nuevo un salto/llamada directa
|
||||
```python
|
||||
import struct, ida_bytes
|
||||
|
||||
@ -222,12 +222,12 @@ op = 0xE8 if is_call else 0xE9 # CALL rel32 or JMP rel32
|
||||
disp = target - (ea + 5) & 0xFFFFFFFF
|
||||
ida_bytes.patch_bytes(ea, bytes([op]) + struct.pack('<I', disp))
|
||||
```
|
||||
Después de parchear, fuerza a IDA a reanalizar la función para que se restauren el CFG completo y la salida de Hex-Rays:
|
||||
Después de parchear, fuerza a IDA a volver a analizar la función para que se restaure el CFG completo y la salida de Hex-Rays:
|
||||
```python
|
||||
import ida_auto, idaapi
|
||||
idaapi.reanalyze_function(idc.get_func_attr(ea, idc.FUNCATTR_START))
|
||||
```
|
||||
### 5. Etiquetar llamadas indirectas a la API
|
||||
### 5. Etiquetar llamadas API indirectas
|
||||
|
||||
Una vez que se conoce el destino real de cada `call rax`, puedes indicarle a IDA cuál es para que los tipos de parámetros y los nombres de variables se recuperen automáticamente:
|
||||
```python
|
||||
@ -236,14 +236,14 @@ idc.set_callee_name(call_ea, resolved_addr, 0) # IDA 8.3+
|
||||
### Beneficios prácticos
|
||||
|
||||
* Restaura el CFG real → la decompilación pasa de *10* líneas a miles.
|
||||
* Permite string-cross-reference & xrefs, haciendo trivial la reconstrucción del comportamiento.
|
||||
* Scripts son reutilizables: insértalos en cualquier loader protegido por el mismo truco.
|
||||
* Habilita string-cross-reference & xrefs, haciendo la reconstrucción del comportamiento trivial.
|
||||
* Los scripts son reutilizables: colócalos en cualquier loader protegido por el mismo truco.
|
||||
|
||||
---
|
||||
|
||||
## Referencias
|
||||
## References
|
||||
|
||||
- [Unit42 – Evolving Tactics of SLOW#TEMPEST: A Deep Dive Into Advanced Malware Techniques](https://unit42.paloaltonetworks.com/slow-tempest-malware-obfuscation/)
|
||||
- SoTap: Lightweight in-app JNI (.so) behavior logger – [github.com/RezaArbabBot/SoTap](https://github.com/RezaArbabBot/SoTap)
|
||||
- SoTap: Lightweight in-app JNI (.so) behavior logger – [github.com/RezaArbabBot/SoTap](https://github.com/RezaArbabBot/SoTap")
|
||||
|
||||
{{#include ../../banners/hacktricks-training.md}}
|
||||
|
||||
@ -1,12 +1,12 @@
|
||||
# Ingeniería inversa de bibliotecas nativas
|
||||
# Revirtiendo bibliotecas nativas
|
||||
|
||||
{{#include ../../banners/hacktricks-training.md}}
|
||||
|
||||
|
||||
**Para más información consulta:** [**https://maddiestone.github.io/AndroidAppRE/reversing_native_libs.html**](https://maddiestone.github.io/AndroidAppRE/reversing_native_libs.html)
|
||||
|
||||
Las apps Android pueden usar bibliotecas nativas, típicamente escritas en C o C++, para tareas críticas de rendimiento. Los creadores de malware también abusan de estas bibliotecas porque los objetos compartidos ELF siguen siendo más difíciles de decompilar que el byte-code DEX/OAT.
|
||||
Esta página se centra en flujos de trabajo *prácticos* y en mejoras recientes de herramientas (2023-2025) que facilitan la ingeniería inversa de archivos `.so` de Android.
|
||||
Las apps Android pueden usar bibliotecas nativas, típicamente escritas en C o C++, para tareas críticas de rendimiento. Los creadores de malware también abusan de estas bibliotecas porque los objetos compartidos ELF siguen siendo más difíciles de descompilar que el byte-code DEX/OAT.
|
||||
Esta página se centra en flujos de trabajo *prácticos* y mejoras *recientes* de herramientas (2023-2025) que facilitan el reversing de archivos `.so` de Android.
|
||||
|
||||
---
|
||||
|
||||
@ -25,26 +25,26 @@ file libfoo.so # arm64 or arm32 / x86
|
||||
readelf -h libfoo.so # OS ABI, PIE, NX, RELRO, etc.
|
||||
checksec --file libfoo.so # (peda/pwntools)
|
||||
```
|
||||
3. **Listar símbolos exportados y vínculos JNI**
|
||||
3. **Listar símbolos exportados y enlaces JNI**
|
||||
```bash
|
||||
readelf -s libfoo.so | grep ' Java_' # dynamic-linked JNI
|
||||
strings libfoo.so | grep -i "RegisterNatives" -n # static-registered JNI
|
||||
```
|
||||
4. **Cargar en un decompilador** (Ghidra ≥ 11.0, IDA Pro, Binary Ninja, Hopper or Cutter/Rizin) y ejecutar análisis automático.
|
||||
Las versiones recientes de Ghidra introdujeron un decompilador AArch64 que reconoce stubs PAC/BTI y etiquetas MTE, mejorando considerablemente el análisis de bibliotecas compiladas con el NDK de Android 14.
|
||||
5. **Decidir entre reversing estático o dinámico:** el código sin símbolos (stripped) u ofuscado a menudo necesita *instrumentación* (Frida, ptrace/gdbserver, LLDB).
|
||||
Las versiones más recientes de Ghidra introdujeron un decompilador AArch64 que reconoce stubs PAC/BTI y etiquetas MTE, mejorando considerablemente el análisis de bibliotecas construidas con el NDK de Android 14.
|
||||
5. **Decidir entre reversing estático o dinámico:** el código stripped u ofuscado a menudo necesita *instrumentación* (Frida, ptrace/gdbserver, LLDB).
|
||||
|
||||
---
|
||||
|
||||
### Instrumentación dinámica (Frida ≥ 16)
|
||||
|
||||
La serie 16 de Frida introdujo varias mejoras específicas para Android que ayudan cuando el objetivo usa optimizaciones modernas de Clang/LLD:
|
||||
La serie 16 de Frida trajo varias mejoras específicas para Android que ayudan cuando el objetivo usa optimizaciones modernas de Clang/LLD:
|
||||
|
||||
* `thumb-relocator` ahora puede *hook tiny ARM/Thumb functions* generadas por el alineamiento agresivo de LLD (`--icf=all`).
|
||||
* La enumeración y re-enlace de *ELF import slots* funciona en Android, permitiendo parchear por módulo con `dlopen()`/`dlsym()` cuando los inline hooks son rechazados.
|
||||
* `thumb-relocator` ahora puede *hook tiny ARM/Thumb functions* generadas por la alineación agresiva de LLD (`--icf=all`).
|
||||
* La enumeración y re-binding de *ELF import slots* funciona en Android, permitiendo parcheo por módulo con `dlopen()`/`dlsym()` cuando los inline hooks son rechazados.
|
||||
* Se corrigió Java hooking para el nuevo **ART quick-entrypoint** usado cuando las apps se compilan con `--enable-optimizations` en Android 14.
|
||||
|
||||
Ejemplo: enumerando todas las funciones registradas a través de `RegisterNatives` y volcando sus direcciones en tiempo de ejecución:
|
||||
Ejemplo: enumerando todas las funciones registradas mediante `RegisterNatives` y volcando sus direcciones en tiempo de ejecución:
|
||||
```javascript
|
||||
Java.perform(function () {
|
||||
var Runtime = Java.use('java.lang.Runtime');
|
||||
@ -61,22 +61,22 @@ console.log('[+] RegisterNatives on ' + clazz.getName() + ' -> ' + count + ' met
|
||||
});
|
||||
});
|
||||
```
|
||||
Frida funcionará sin configuración adicional en dispositivos con PAC/BTI (Pixel 8/Android 14+) siempre que uses frida-server 16.2 o posterior – versiones anteriores no conseguían localizar el padding para inline hooks.
|
||||
Frida will work out of the box on PAC/BTI-enabled devices (Pixel 8/Android 14+) as long as you use frida-server 16.2 or later – earlier versions failed to locate padding for inline hooks.
|
||||
|
||||
### Telemetría JNI local al proceso mediante .so precargado (SoTap)
|
||||
### Telemetría JNI local al proceso vía .so precargado (SoTap)
|
||||
|
||||
Cuando la instrumentación completa es excesiva o está bloqueada, aún puedes obtener visibilidad a nivel nativo precargando un pequeño logger dentro del proceso objetivo. SoTap es una biblioteca nativa ligera de Android (.so) que registra el comportamiento en tiempo de ejecución de otras bibliotecas JNI (.so) dentro del mismo proceso de la app (no se requiere root).
|
||||
Cuando la instrumentación completa es excesiva o está bloqueada, aún puedes obtener visibilidad a nivel nativo precargando un pequeño logger dentro del proceso objetivo. SoTap es una librería nativa ligera de Android (.so) que registra el comportamiento en tiempo de ejecución de otras librerías JNI (.so) dentro del mismo proceso de la app (no se requiere root).
|
||||
|
||||
Key properties:
|
||||
- Se inicializa temprano y observa las interacciones JNI/nativas dentro del proceso que la carga.
|
||||
- Persiste logs usando múltiples rutas escribibles con graceful fallback a Logcat cuando el almacenamiento está restringido.
|
||||
- Source-customizable: edita sotap.c para ampliar/ajustar lo que se registra y recompila por ABI.
|
||||
Propiedades clave:
|
||||
- Se inicializa temprano y observa las interacciones JNI/nativas dentro del proceso que lo carga.
|
||||
- Persiste logs usando múltiples rutas escribibles con una degradación elegante a Logcat cuando el almacenamiento está restringido.
|
||||
- Personalizable desde el código fuente: edita sotap.c para ampliar/ajustar qué se registra y recompila por ABI.
|
||||
|
||||
Setup (repack the APK):
|
||||
1) Drop the proper ABI build into the APK so the loader can resolve libsotap.so:
|
||||
1) Coloca la compilación adecuada por ABI dentro del APK para que el loader pueda resolver libsotap.so:
|
||||
- lib/arm64-v8a/libsotap.so (for arm64)
|
||||
- lib/armeabi-v7a/libsotap.so (for arm32)
|
||||
2) Ensure SoTap loads before other JNI libs. Inject a call early (e.g., Application subclass static initializer or onCreate) so the logger is initialized first. Smali snippet example:
|
||||
2) Asegura que SoTap se cargue antes que otras libs JNI. Injerta una llamada temprano (por ejemplo, Application subclass static initializer or onCreate) para que el logger se inicialice primero. Smali snippet example:
|
||||
```smali
|
||||
const-string v0, "sotap"
|
||||
invoke-static {v0}, Ljava/lang/System;->loadLibrary(Ljava/lang/String;)V
|
||||
@ -92,45 +92,45 @@ Log paths (checked in order):
|
||||
# If all fail: fallback to Logcat only
|
||||
```
|
||||
Notas y solución de problemas:
|
||||
- ABI alignment is mandatory. A mismatch will raise UnsatisfiedLinkError and the logger won’t load.
|
||||
- Storage constraints are common on modern Android; if file writes fail, SoTap will still emit via Logcat.
|
||||
- Behavior/verbosity is intended to be customized; rebuild from source after editing sotap.c.
|
||||
- La alineación de ABI es obligatoria. Un desajuste provocará UnsatisfiedLinkError y el logger no se cargará.
|
||||
- Las restricciones de almacenamiento son comunes en Android moderno; si las escrituras de archivos fallan, SoTap seguirá emitiendo vía Logcat.
|
||||
- El comportamiento y el nivel de verbosidad están pensados para personalizarse; recompila desde la fuente después de editar sotap.c.
|
||||
|
||||
This approach is useful for triage de malware and JNI debugging where observing native call flows from process start is critical but root/system-wide hooks aren’t available.
|
||||
This approach is useful for malware triage and JNI debugging where observing native call flows from process start is critical but root/system-wide hooks aren’t available.
|
||||
|
||||
---
|
||||
|
||||
### Vulnerabilidades recientes que vale la pena buscar en APKs
|
||||
### Recent vulnerabilities worth hunting for in APKs
|
||||
|
||||
| Año | CVE | Librería afectada | Notas |
|
||||
| Year | CVE | Affected library | Notes |
|
||||
|------|-----|------------------|-------|
|
||||
|2023|CVE-2023-4863|`libwebp` ≤ 1.3.1|Desbordamiento de búfer en el heap accesible desde código nativo que decodifica imágenes WebP. Varias apps Android incluyen versiones vulnerables. Cuando veas un `libwebp.so` dentro de un APK, comprueba su versión e intenta explotarlo o parchearlo.| |
|
||||
|2024|Multiple|OpenSSL 3.x series|Varios problemas de seguridad de memoria y padding-oracle. Muchos bundles de Flutter & ReactNative incluyen su propio `libcrypto.so`.|
|
||||
|2023|CVE-2023-4863|`libwebp` ≤ 1.3.1|Desbordamiento de heap alcanzable desde código nativo que decodifica imágenes WebP. Varias apps de Android incluyen versiones vulnerables. Cuando veas un `libwebp.so` dentro de un APK, verifica su versión e intenta explotarlo o parchearlo.| |
|
||||
|2024|Multiple|OpenSSL 3.x series|Varios problemas de memory-safety y padding-oracle. Muchos bundles de Flutter & ReactNative incluyen su propio `libcrypto.so`.| |
|
||||
|
||||
Cuando detectes archivos `.so` de *terceros* dentro de un APK, siempre verifica su hash contra los avisos upstream. SCA (Software Composition Analysis) es poco común en móvil, por lo que las compilaciones vulnerables y desactualizadas son frecuentes.
|
||||
When you spot *third-party* `.so` files inside an APK, always cross-check their hash against upstream advisories. SCA (Software Composition Analysis) is uncommon on mobile, so outdated vulnerable builds are rampant.
|
||||
|
||||
---
|
||||
|
||||
### Tendencias de Anti-Reversing y Hardening (Android 13-15)
|
||||
### Anti-Reversing & Hardening trends (Android 13-15)
|
||||
|
||||
* **Pointer Authentication (PAC) & Branch Target Identification (BTI):** Android 14 habilita PAC/BTI en las bibliotecas del sistema en silicio ARMv8.3+ compatible. Los decompiladores ahora muestran pseudo-instrucciones relacionadas con PAC; para análisis dinámico Frida inyecta trampolines *after* stripping PAC, pero tus trampolines personalizados deben llamar a `pacda`/`autibsp` cuando sea necesario.
|
||||
* **MTE & Scudo hardened allocator:** memory-tagging is opt-in but many Play-Integrity aware apps build with `-fsanitize=memtag`; use `setprop arm64.memtag.dump 1` plus `adb shell am start ...` to capture tag faults.
|
||||
* **LLVM Obfuscator (opaque predicates, control-flow flattening):** los packers comerciales (p. ej., Bangcle, SecNeo) protegen cada vez más código *nativo*, no solo Java; espera bogus control-flow y blobs de strings encriptados en `.rodata`.
|
||||
* **Pointer Authentication (PAC) & Branch Target Identification (BTI):** Android 14 enables PAC/BTI in system libraries on supported ARMv8.3+ silicon. Decompilers now display PAC‐related pseudo-instructions; for dynamic analysis Frida injects trampolines *after* stripping PAC, but your custom trampolines should call `pacda`/`autibsp` where necessary.
|
||||
* **MTE & Scudo hardened allocator:** el memory-tagging es opcional pero muchas apps conscientes de Play-Integrity se compilan con `-fsanitize=memtag`; usa `setprop arm64.memtag.dump 1` junto con `adb shell am start ...` para capturar fallos de etiqueta.
|
||||
* **LLVM Obfuscator (opaque predicates, control-flow flattening):** los packers comerciales (p. ej., Bangcle, SecNeo) protegen cada vez más el *native* code, no solo Java; espera control-flow falso y blobs de strings cifrados en `.rodata`.
|
||||
|
||||
---
|
||||
|
||||
### Recursos
|
||||
### Resources
|
||||
|
||||
- **Aprender ARM Assembly:** [Azeria Labs – ARM Assembly Basics](https://azeria-labs.com/writing-arm-assembly-part-1/)
|
||||
- **Documentación JNI & NDK:** [Oracle JNI Spec](https://docs.oracle.com/javase/7/docs/technotes/guides/jni/spec/jniTOC.html) · [Android JNI Tips](https://developer.android.com/training/articles/perf-jni) · [NDK Guides](https://developer.android.com/ndk/guides/)
|
||||
- **Depuración de librerías nativas:** [Debug Android Native Libraries Using JEB Decompiler](https://medium.com/@shubhamsonani/how-to-debug-android-native-libraries-using-jeb-decompiler-eec681a22cf3)
|
||||
|
||||
### Referencias
|
||||
### References
|
||||
|
||||
- Registro de cambios de Frida 16.x (Android hooking, tiny-function relocation) – [frida.re/news](https://frida.re/news/)
|
||||
- Aviso NVD para el overflow de `libwebp` CVE-2023-4863 – [nvd.nist.gov](https://nvd.nist.gov/vuln/detail/CVE-2023-4863)
|
||||
- SoTap: Logger ligero in-app de comportamiento JNI (.so) – [github.com/RezaArbabBot/SoTap](https://github.com/RezaArbabBot/SoTap)
|
||||
- Lanzamientos de SoTap – [github.com/RezaArbabBot/SoTap/releases](https://github.com/RezaArbabBot/SoTap/releases)
|
||||
- Aviso NVD para el desbordamiento de `libwebp` CVE-2023-4863 – [nvd.nist.gov](https://nvd.nist.gov/vuln/detail/CVE-2023-4863)
|
||||
- SoTap: logger ligero in-app para comportamiento JNI (.so) – [github.com/RezaArbabBot/SoTap](https://github.com/RezaArbabBot/SoTap)
|
||||
- Releases de SoTap – [github.com/RezaArbabBot/SoTap/releases](https://github.com/RezaArbabBot/SoTap/releases)
|
||||
- ¿Cómo trabajar con SoTap? – [t.me/ForYouTillEnd/13](https://t.me/ForYouTillEnd/13)
|
||||
|
||||
{{#include ../../banners/hacktricks-training.md}}
|
||||
|
||||
@ -1,38 +1,38 @@
|
||||
# Smali - Descompilando/[Modificando]/Compilando
|
||||
# Smali - Descompilar/[Modificar]/Compilar
|
||||
|
||||
{{#include ../../banners/hacktricks-training.md}}
|
||||
|
||||
|
||||
A veces es interesante modificar el código de la aplicación para acceder a información oculta para ti (quizá contraseñas bien ofuscadas o flags). Entonces, puede ser interesante descompilar el apk, modificar el código y recompilarlo.
|
||||
A veces es interesante modificar el código de la aplicación para acceder a información oculta para ti (quizá contraseñas bien ofuscadas o flags). Entonces, puede ser interesante descompilar el APK, modificar el código y recompilarlo.
|
||||
|
||||
**Referencia de opcodes:** [http://pallergabor.uw.hu/androidblog/dalvik_opcodes.html](http://pallergabor.uw.hu/androidblog/dalvik_opcodes.html)
|
||||
**Opcodes reference:** [http://pallergabor.uw.hu/androidblog/dalvik_opcodes.html](http://pallergabor.uw.hu/androidblog/dalvik_opcodes.html)
|
||||
|
||||
## Forma rápida
|
||||
## Método rápido
|
||||
|
||||
Usando **Visual Studio Code** y la extensión [APKLab](https://github.com/APKLab/APKLab), puedes **descompilar automáticamente**, modificar, **recompilar**, firmar e instalar la aplicación sin ejecutar ningún comando.
|
||||
|
||||
Otro **script** que facilita mucho esta tarea es [**https://github.com/ax/apk.sh**](https://github.com/ax/apk.sh)
|
||||
|
||||
## Descompilar el APK
|
||||
## Descompile el APK
|
||||
|
||||
Usando APKTool puedes acceder al **código smali y a los recursos**:
|
||||
Usando APKTool puedes acceder al **código smali y los recursos**:
|
||||
```bash
|
||||
apktool d APP.apk
|
||||
```
|
||||
Si **apktool** te da algún error, prueba [installing the **latest version**](https://ibotpeaches.github.io/Apktool/install/)
|
||||
Si **apktool** te da algún error, intenta [ installing the **latest version**](https://ibotpeaches.github.io/Apktool/install/)
|
||||
|
||||
Algunos **archivos interesantes que deberías revisar son**:
|
||||
Algunos **archivos interesantes que deberías revisar** son:
|
||||
|
||||
- _res/values/strings.xml_ (y todos los xml dentro de res/values/*)
|
||||
- _res/values/strings.xml_ (and all xmls inside res/values/*)
|
||||
- _AndroidManifest.xml_
|
||||
- Cualquier archivo con extensión _.sqlite_ o _.db_
|
||||
- Any file with extension _.sqlite_ or _.db_
|
||||
|
||||
Si `apktool` tiene **problemas decodificando la aplicación** echa un vistazo a [https://ibotpeaches.github.io/Apktool/documentation/#framework-files](https://ibotpeaches.github.io/Apktool/documentation/#framework-files) o prueba usando el argumento **`-r`** (No decodificar recursos). Entonces, si el problema estaba en un recurso y no en el código fuente, no tendrás el problema (tampoco decompilarás los recursos).
|
||||
Si `apktool` tiene **problemas decoding the application** echa un vistazo a [https://ibotpeaches.github.io/Apktool/documentation/#framework-files](https://ibotpeaches.github.io/Apktool/documentation/#framework-files) o prueba usando el argumento **`-r`** (No decodificar los recursos). Entonces, si el problema estaba en un recurso y no en el código fuente, no tendrás ese problema (tampoco decompilarás los recursos).
|
||||
|
||||
## Cambiar código smali
|
||||
|
||||
Puedes **cambiar** **instrucciones**, modificar el **valor** de algunas variables o **añadir** nuevas instrucciones. Yo modifico el código Smali usando [**VS Code**](https://code.visualstudio.com), luego instalas la **smalise extension** y el editor te dirá si alguna **instrucción es incorrecta**.\
|
||||
Algunos **ejemplos** se pueden encontrar aquí:
|
||||
Puedes **change** **instructions**, cambiar el **value** de algunas variables o **add** nuevas instrucciones. Yo modifico el código Smali usando [**VS Code**](https://code.visualstudio.com), luego instalas la **smalise extension** y el editor te dirá si alguna **instruction is incorrect**.\
|
||||
Some **examples** can be found here:
|
||||
|
||||
- [Smali changes examples](smali-changes.md)
|
||||
- [Google CTF 2018 - Shall We Play a Game?](google-ctf-2018-shall-we-play-a-game.md)
|
||||
@ -41,17 +41,17 @@ O puedes [**check below some Smali changes explained**](smali-changes.md#modifyi
|
||||
|
||||
## Recompilar el APK
|
||||
|
||||
Después de modificar el código puedes **recompilar** el código usando:
|
||||
Después de modificar el código puedes **recompile** el código usando:
|
||||
```bash
|
||||
apktool b . #In the folder generated when you decompiled the application
|
||||
```
|
||||
Esto va a **compilar** el nuevo APK **dentro** de la carpeta _**dist**_.
|
||||
Se compilará el nuevo APK dentro de la carpeta _**dist**_.
|
||||
|
||||
Si **apktool** lanza un **error**, intenta[ instalar la **última versión**](https://ibotpeaches.github.io/Apktool/install/)
|
||||
Si **apktool** lanza un **error**, prueba[ installing the **latest version**](https://ibotpeaches.github.io/Apktool/install/)
|
||||
|
||||
### **Firmar el nuevo APK**
|
||||
|
||||
Luego, necesitas **generar una clave** (se te pedirá una contraseña y cierta información que puedes completar aleatoriamente):
|
||||
Luego, necesitas **generar una clave** (se te pedirá una contraseña y algunos datos que puedes rellenar aleatoriamente):
|
||||
```bash
|
||||
keytool -genkey -v -keystore key.jks -keyalg RSA -keysize 2048 -validity 10000 -alias <your-alias>
|
||||
```
|
||||
@ -61,12 +61,12 @@ jarsigner -keystore key.jks path/to/dist/* <your-alias>
|
||||
```
|
||||
### Optimizar la nueva aplicación
|
||||
|
||||
**zipalign** es una herramienta de alineación de archivos que proporciona una optimización importante a los archivos APK de las aplicaciones Android. [Más información aquí](https://developer.android.com/studio/command-line/zipalign).
|
||||
zipalign es una herramienta de alineación de archivos que proporciona una optimización importante a los archivos de aplicación Android (APK). [More information here](https://developer.android.com/studio/command-line/zipalign).
|
||||
```bash
|
||||
zipalign [-f] [-v] <alignment> infile.apk outfile.apk
|
||||
zipalign -v 4 infile.apk
|
||||
```
|
||||
### **Firmar el nuevo APK (¿otra vez?)**
|
||||
### **Firma el nuevo APK (¿otra vez?)**
|
||||
|
||||
Si **prefieres** usar [**apksigner**](https://developer.android.com/studio/command-line/) en lugar de jarsigner, **deberías firmar el apk** después de aplicar **la optimización con** zipaling. PERO TEN EN CUENTA QUE SOLO TIENES QUE **FIRMAR LA APLICACIÓN UNA VEZ** CON jarsigner (antes de zipalign) O CON aspsigner (después de zipaling).
|
||||
```bash
|
||||
@ -74,7 +74,7 @@ apksigner sign --ks key.jks ./dist/mycompiled.apk
|
||||
```
|
||||
## Modificando Smali
|
||||
|
||||
Para el siguiente código Java de Hello World:
|
||||
Para el siguiente código Java Hello World:
|
||||
```java
|
||||
public static void printHelloWorld() {
|
||||
System.out.println("Hello World")
|
||||
@ -90,13 +90,13 @@ invoke-virtual {v0,v1}, Ljava/io/PrintStream;->println(Ljava/lang/String;)V
|
||||
return-void
|
||||
.end method
|
||||
```
|
||||
The Smali instruction set is available [here](https://source.android.com/devices/tech/dalvik/dalvik-bytecode#instructions).
|
||||
El conjunto de instrucciones de Smali está disponible [here](https://source.android.com/devices/tech/dalvik/dalvik-bytecode#instructions).
|
||||
|
||||
### Cambios ligeros
|
||||
|
||||
### Modificar los valores iniciales de una variable dentro de una función
|
||||
|
||||
Algunas variables se definen al comienzo de la función usando el opcode _const_, puedes modificar sus valores, o puedes definir nuevas:
|
||||
Algunas variables se definen al principio de la función usando el opcode _const_; puedes modificar sus valores o definir nuevas:
|
||||
```bash
|
||||
#Number
|
||||
const v9, 0xf4240
|
||||
@ -141,16 +141,16 @@ invoke-static {v5, v1}, Landroid/util/Log;->d(Ljava/lang/String;Ljava/lang/Strin
|
||||
Recomendaciones:
|
||||
|
||||
- Si vas a usar variables declaradas dentro de la función (declaradas v0,v1,v2...) coloca estas líneas entre la _.local <number>_ y las declaraciones de las variables (_const v0, 0x1_)
|
||||
- Si quieres poner el código de logging en medio del código de una función:
|
||||
- Suma 2 al número de variables declaradas: Ex: de _.locals 10_ a _.locals 12_
|
||||
- Las nuevas variables deben ser los números siguientes de las variables ya declaradas (en este ejemplo deben ser _v10_ y _v11_, recuerda que empieza en v0).
|
||||
- Cambia el código de la función de logging y usa _v10_ y _v11_ en lugar de _v5_ y _v1_.
|
||||
- Si quieres poner el logging en medio del código de una función:
|
||||
- Suma 2 al número de variables declaradas: Ej: de _.locals 10_ a _.locals 12_
|
||||
- Las nuevas variables deben ser los siguientes números de las ya declaradas (en este ejemplo deben ser _v10_ y _v11_, recuerda que empieza en v0).
|
||||
- Cambia el código de la función de logging y usa _v10_ y _v11_ en lugar de _v5_ y _v1_.
|
||||
|
||||
### Toasting
|
||||
|
||||
Recuerda añadir 3 al número de _.locals_ al principio de la función.
|
||||
Recuerda sumar 3 al número de _.locals_ al inicio de la función.
|
||||
|
||||
Este código está preparado para insertarse en el **medio de una función** (**cambia** el número de las **variables** según sea necesario). Tomará el **valor de this.o**, lo **transformará** a **String** y luego **hará** un **toast** con su valor.
|
||||
Este código está preparado para ser insertado en el **medio de una función** (**cambia** el número de las **variables** según sea necesario). Tomará el **valor de this.o**, lo **transformará** a **String** y luego **hará** un **toast** con su valor.
|
||||
```bash
|
||||
const/4 v10, 0x1
|
||||
const/4 v11, 0x1
|
||||
@ -162,9 +162,9 @@ invoke-static {p0, v11, v12}, Landroid/widget/Toast;->makeText(Landroid/content/
|
||||
move-result-object v12
|
||||
invoke-virtual {v12}, Landroid/widget/Toast;->show()V
|
||||
```
|
||||
### Cargar una biblioteca nativa al inicio (System.loadLibrary)
|
||||
### Cargar una librería nativa al iniciar (System.loadLibrary)
|
||||
|
||||
A veces necesitas precargar una biblioteca nativa para que se inicialice antes que otras libs JNI (p. ej., para habilitar process-local telemetry/logging). Puedes inyectar una llamada a System.loadLibrary() en un inicializador estático o temprano en Application.onCreate(). Ejemplo smali para un inicializador estático de clase (<clinit>):
|
||||
A veces necesitas precargar una librería nativa para que se inicialice antes que otras JNI libs (p. ej., para habilitar telemetría/registro local del proceso). Puedes inyectar una llamada a System.loadLibrary() en un inicializador estático o al inicio de Application.onCreate(). Ejemplo smali para un inicializador de clase estática (<clinit>):
|
||||
```smali
|
||||
.class public Lcom/example/App;
|
||||
.super Landroid/app/Application;
|
||||
@ -176,7 +176,7 @@ invoke-static {v0}, Ljava/lang/System;->loadLibrary(Ljava/lang/String;)V
|
||||
return-void
|
||||
.end method
|
||||
```
|
||||
Alternativamente, coloca las mismas dos instrucciones al inicio de tu Application.onCreate() para asegurarte de que la librería se cargue lo antes posible:
|
||||
Como alternativa, coloca las mismas dos instrucciones al inicio de tu Application.onCreate() para asegurar que la biblioteca se cargue lo antes posible:
|
||||
```smali
|
||||
.method public onCreate()V
|
||||
.locals 1
|
||||
@ -190,10 +190,10 @@ return-void
|
||||
```
|
||||
Notas:
|
||||
- Asegúrate de que la variante ABI correcta de la biblioteca exista bajo lib/<abi>/ (p. ej., arm64-v8a/armeabi-v7a) para evitar UnsatisfiedLinkError.
|
||||
- Cargarla muy temprano (class static initializer) garantiza que el logger nativo pueda observar la actividad JNI posterior.
|
||||
- Cargar muy pronto (inicializador estático de clase) garantiza que el logger nativo pueda observar la actividad JNI posterior.
|
||||
|
||||
## Referencias
|
||||
|
||||
- SoTap: Logger ligero in-app de comportamiento de JNI (.so) – [github.com/RezaArbabBot/SoTap](https://github.com/RezaArbabBot/SoTap)
|
||||
- SoTap: logger ligero in-app de comportamiento JNI (.so) – [github.com/RezaArbabBot/SoTap](https://github.com/RezaArbabBot/SoTap)
|
||||
|
||||
{{#include ../../banners/hacktricks-training.md}}
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user