Frida的Stalker中transform的逻辑

除了官网文档介绍了内部具体实现机制和过程之外:

对于,想要搞懂如何利用transform去调试代码来说:

需要明白的逻辑是:

此处代码:

Interceptor.attach(funcRealStartAddr, {
    onEnter: function(args) {
...
        var curTid = Process.getCurrentThreadId();
        console.log("curTid=", curTid);
        Stalker.follow(curTid, {
            events: {
                call: true, // CALL instructions: yes please            
                ret: false, // RET instructions
                exec: false, // all instructions: not recommended as it's
                block: false, // block executed: coarse execution trace
                compile: false // block compiled: useful for coverage
            },
            // transform: (iterator: StalkerArm64Iterator) => {
            transform: function (iterator) {
                ...

触发到的transform的iterator来说:

  • 每次触发=每个iterator:都(对应着)单个block=(basic)代码块
  • 此处代码块有2种
    • 非原始函数代码 == isAppCode=false
      • 对应着应该是Stalker内部实现原理说的,copy拷贝出的代码
        • 其中会额外加上很多逻辑,用于实现Stalker的功能和逻辑
        • 估计就是这里说的这些内容
          • [原创] sktrace:基于 Frida Stalker 的 trace 工具-Android安全-看雪-安全社区|安全招聘|kanxue.com
            • 每当执行到一个基本块,Stalker都会做以下几件事:
              1. 对于方法调用,保存lr等必要信息
              2. 重定位位置相关指令,例如:ADR Xd, label
              3. 建立此块的索引,如果此块在达到可信阈值后,内容未曾变化,下次将不再重新编译(为了加快速度)
              4. 根据 transform 函数,编译生成一个新的基本块 GumExecBlock ,保存到 GumSlabvoid transform(GumStalkerIterator iterator, GumStalkerOutput output, gpointer user_data) 可以控制读取,改动,写入指令。
              5. transform 过程中还可通过 void gum_stalker_iterator_put_callout (GumStalkerIterator self,GumStalkerCallout callout, gpointer data, GDestroyNotify data_destroy) 来设置一个当此位置被执行到时的callout。通过此void callout(GumCpuContext cpu_context, gpointer user_data)获取cpu信息。
              6. 执行一个基本快GumExecBlock,开始下一个基本快
      • 所以无需操作具体内部过程,直接忽略即可
    • 原始函数代码 == isAppCode=true
      • 是实际运行的代码,才是我们所要关注的代码
        • 才会真正的去处理:比如判断是否是对应的(某个偏移量的)代码,然后去打印查看调试寄存器的值等等

此处去通过计算是否是 原始函数代码isAppCode 决定是否处理

具体详见示例代码:

results matching ""

    No results matching ""