You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何使用Frida脚本提取AES密钥及解决‘device not found’报错问题

解决Frida "device not found" 报错及提取AES密钥的实用方案

一、先搞定 "device not found" 报错

这个报错说白了就是Frida找不到你的USB设备,别慌,按下面的步骤逐一排查:

  • 确认设备连接和调试状态
    • 先把手机和电脑用靠谱的USB线连好,确保手机已经开启开发者模式,并且打开了USB调试(部分手机还需要开启“USB调试(安全设置)”以允许调试权限)。
    • 打开命令行执行 adb devices,查看列表中是否有你的设备。如果没显示,要么更换USB口/数据线,要么检查手机驱动,或者重启调试开关重试。
  • 确保Frida服务在设备上正常运行
    • 先在电脑上查看Frida版本:frida --version,然后下载对应版本的frida-server(需匹配手机架构,比如arm64架构选择android-arm64版本)。
    • 将server推送到手机:adb push frida-server-xxx-android-arm64 /data/local/tmp/
    • 赋予执行权限:adb shell chmod 755 /data/local/tmp/frida-server-xxx-android-arm64
    • 后台启动服务:adb shell /data/local/tmp/frida-server-xxx-android-arm64 &
  • 修正脚本中的设备调用逻辑
    • 如果是多设备或模拟器环境,直接用get_usb_device()可能会识别失败,可以添加超时时间或指定设备ID:
      # 给设备连接添加30秒超时,避免因识别过慢报错
      device = frida.get_usb_device(timeout=30)
      # 或者通过adb devices获取的设备ID指定设备
      # device = frida.get_device("你的设备ID")
      session = device.attach('com.example.a11x256.frida_test')
      
    • 务必确认包名正确!执行adb shell pm list packages可以查看设备上所有应用包名,确保com.example.a11x256.frida_test确实存在。

二、用Frida提取AES密钥的有效方法

AES密钥通常会在加密API调用、密钥生成或存储环节暴露,我们可以通过Hook关键节点捕获密钥,分两种场景给出方案:

1. 针对Java/Kotlin编写的APP

这类APP大多依赖javax.crypto包,Hook密钥相关的构造方法即可直接获取:

// hook_java_aes.js
Java.perform(function() {
    // Hook SecretKeySpec构造方法,密钥会在此处传入
    var SecretKeySpec = Java.use('javax.crypto.spec.SecretKeySpec');
    SecretKeySpec.$init.overload('[B', 'java.lang.String').implementation = function(keyBytes, algorithm) {
        console.log("[+] AES密钥(字节数组): " + Array.prototype.slice.call(keyBytes));
        console.log("[+] AES密钥(十六进制): " + bytesToHex(keyBytes));
        console.log("[+] 加密算法: " + algorithm);
        // 必须调用原方法,否则应用会崩溃
        return this.$init(keyBytes, algorithm);
    };

    // 辅助函数:将字节数组转换为十六进制格式,便于阅读
    function bytesToHex(arr) {
        return arr.map(function(byte) {
            return ('0' + (byte & 0xFF).toString(16)).slice(-2);
        }).join('');
    }
});

运行脚本的命令:frida -U -f com.example.a11x256.frida_test -l hook_java_aes.js --no-pause

2. 针对使用Native层加密的APP

如果APP依赖OpenSSL或自定义Native AES逻辑,直接Hook对应的Native函数:

// hook_native_aes.js
Interceptor.attach(Module.findExportByName('libcrypto.so', 'EVP_EncryptInit_ex'), {
    onEnter: function(args) {
        // 判断是否为AES算法
        var cipherName = ptr(args[2]).readCString();
        if (cipherName && cipherName.includes("AES")) {
            // args[3]为密钥指针,长度根据AES类型调整:16=AES-128,24=AES-192,32=AES-256
            var keyLength = 32;
            var keyBytes = args[3].readByteArray(keyLength);
            console.log("[+] Native层AES密钥(十六进制): " + hexdump(keyBytes, { offset: 0, length: keyLength, header: false, ansi: false }));
        }
    }
});

运行脚本的命令:frida -U com.example.a11x256.frida_test -l hook_native_aes.js

3. 内存扫描兜底方案

如果Hook不到密钥,还可以通过内存扫描查找(适合已知密钥部分特征的场景):

// scan_memory.js
Java.perform(function() {
    var mainModule = Process.enumerateModules()[0];
    var startAddr = mainModule.base;
    var endAddr = startAddr.add(mainModule.size);
    // 将此处十六进制替换为你猜测的密钥片段,比如已知的部分密钥内容
    Memory.scan(startAddr, endAddr.sub(startAddr), 'a1b2c3d4e5f6a7b8', {
        onMatch: function(address, size) {
            console.log("[+] 找到疑似AES密钥的地址: " + address.toString());
            console.log("[+] 密钥内容: " + hexdump(address, { offset: 0, length: 32, header: false, ansi: false }));
        },
        onComplete: function() {
            console.log("[+] 内存扫描完成");
        }
    });
});

内容的提问来源于stack exchange,提问作者umer siddique

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.04.30 07:22:34