繁体   English   中英

如何在 Windows 上获取线程堆栈信息?

[英]How to get thread stack information on Windows?

我通过CreateToolhelp32Snapshot函数枚举进程中的所有线程。 我想为每个线程获取一些基本的堆栈信息。 更具体地说,我想获得堆栈底部地址,如果可能的话,我想获得当前的堆栈顶部地址。 基本上这是在 WinDbg 中用~*k命令显示的信息。 那么如何从线程的 ID 或 HANDLE 中获取堆栈信息呢?

(定义可以在这里找到。)

获取堆栈边界:

THREAD_BASIC_INFORMATION basicInfo;
NT_TIB tib;

// Get TEB address
NtQueryInformationThread(YOUR_THREAD_HANDLE, ThreadBasicInformation, &basicInfo, sizeof(THREAD_BASIC_INFORMATION), NULL);
// Read TIB
NtReadVirtualMemory(YOUR_PROCESS_HANDLE, basicInfo.TebBaseAddress, &tib, sizeof(NT_TIB), NULL);
// Check tib.StackBase and tib.StackLimit

要获取esp的值,只需使用GetThreadContext

无需涉及 Windows 驱动程序工具包的更简单方法如下:

NT_TIB* tib = (NT_TIB*)__readfsdword(0x18);
size_t* stackBottom = (size_t*)tib->StackLimit;
size_t* stackTop = (size_t*)tib->StackBase;

__readfsdword() 仅适用于当前线程。 因此,带有 NtQueryInformationThread() 的变体更加灵活。

添加了一些在 ntdll.h 中遗漏的声明:

typedef enum _THREADINFOCLASS {
    ThreadBasicInformation = 0,
} THREADINFOCLASS;

typedef LONG KPRIORITY;

typedef struct _CLIENT_ID {
    HANDLE UniqueProcess;
    HANDLE UniqueThread;
} CLIENT_ID;
typedef CLIENT_ID *PCLIENT_ID;

typedef struct _THREAD_BASIC_INFORMATION
{
  NTSTATUS                ExitStatus;
  PVOID                   TebBaseAddress;
  CLIENT_ID               ClientId;
  KAFFINITY               AffinityMask;
  KPRIORITY               Priority;
  KPRIORITY               BasePriority;
} THREAD_BASIC_INFORMATION, *PTHREAD_BASIC_INFORMATION;

据我所知,Toolhelp 通过复制堆、模块、进程和线程的基本信息来工作。 这不包括包含堆栈底部地址的 TEB 块。 我认为您需要使用另一个 API,即调试器引擎 API,它提供检查堆栈的功能

这是当前线程的简单方法(便携式 Win32 x86/x64 版本):

#include <intrin.h>

NT_TIB* getTIB() {
#ifdef _M_IX86
  return (NT_TIB*)__readfsdword(0x18);
#elif _M_AMD64
  return (NT_TIB*)__readgsqword(0x30);
#else
#error unsupported architecture
#endif
}

  NT_TIB* tib = getTIB();
  void* stackBase = tib->StackBase;
  void* stackLimit = tib->StackLimit;

注意: stackLimit < stackBase (随着堆栈向下增长)。

有关更多详细信息,请参阅Win32 TIB

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM