如何在Windows中以编程方式从调用堆栈帧中读取函数参数?

sta*_*yli 9 c++ windows winapi callstack windbg

我试图遍历调用堆栈帧并从中提取一些信息.我能够通过使用提取的文件名,行号,和函数名StackWalk64,SymGetSymFromAddr64以及SymGetLineFromAddr64从WinDBG的的API.

但是,DWORD64 Params[4]in STACKFRAME64,它是一个返回值StackWalk64,仅支持从帧中读回四个64位函数参数.更糟糕的是,在32位系统上,只使用低32位Params[4],因此超过32位的单个参数需要两个或更多元素.

typedef struct _tagSTACKFRAME64 {
  ADDRESS64 AddrPC;
  ADDRESS64 AddrReturn;
  ADDRESS64 AddrFrame;
  ADDRESS64 AddrStack;
  ADDRESS64 AddrBStore;
  PVOID     FuncTableEntry;
  DWORD64   Params[4];
  BOOL      Far;
  BOOL      Virtual;
  DWORD64   Reserved[3];
  KDHELP64  KdHelp;
} STACKFRAME64, *LPSTACKFRAME64;
Run Code Online (Sandbox Code Playgroud)

我找不到任何API来从堆栈框架中读取所有参数而没有限制.

我正在考虑使用ebp/ rbp从堆栈(x86/x64)和寄存器(x64)中提取值.但是,如果我这样做,只能获得参数的"可能"值.

我可以使用任何API来获得准确的值吗?如果我能得到参数的类型和名称会更好.

Rom*_*sky 1

没有适用于它的 API。为什么现代操作系统对某些人玩这些东西不感兴趣呢?如前所述,编译器可以自由地进行优化,因此您不能使用任何确定性工具来执行此操作。但是,有启发法!如果在调用前解析汇编或在调用后返回,你可以知道函数中有多少参数,你总是有返回地址,你可以检查它是否在CS中。

最重要的是 - 您应该阅读术语“堆栈展开”。