ks12345
驱动小牛
驱动小牛
  • 注册日期2006-09-21
  • 最后登录2016-01-09
  • 粉丝0
  • 关注0
  • 积分7分
  • 威望223点
  • 贡献值0点
  • 好评度189点
  • 原创分0分
  • 专家分0分
阅读:5752回复:8

ZwCreateThread 的参数 ThreadContext 怎么初始化?

楼主#
更多 发布于:2007-01-08 10:25
  NTSTATUS NTAPI ZwCreateThread(
OUT PHANDLE         ThreadHandle,
IN    ACCESS_MASK               DesiredAccess,
IN    POBJECT_ATTRIBUTES   ObjectAttributes OPTIONAL,
IN    HANDLE                         ProcessHandle,
OUT PCLIENT_ID                   ClientId,
IN    PCONTEXT                     ThreadContext,
IN    PINITIAL_TEB                 InitialTeb,
IN    BOOLEAN                       CreateSuspended
);

PVOID NTAPI RtlInitializeContext(
IN HANDLE            ProcessHandle,
OUT PCONTEXT     ThreadContext,
IN PVOID              ThreadStartParam OPTIONAL,
IN PTHREAD_START_ROUTINE ThreadStartAddress,
IN PINITIAL_TEB   InitialTeb
);
------------------------------------------------------------------------------
ZwCreateThread 的参数 ThreadContext 不知道应该怎么初始化?
1,我调用 RtlInitializeContext 初始化返回 0(NULL),而且跟踪发现里面的值也与 HOOK 的正常调用很大不同,貌似初始化失败。
2,然后我在网上找到一段代码,用以初始化:
           //Initialize new thread context
    //similar to it's initialization by system
    ThreadContext.SegGs = 0;
    ThreadContext.SegFs = 0x38;
    ThreadContext.SegEs = 0x20;
    ThreadContext.SegDs = 0x20;
    ThreadContext.SegSs = 0x20;
    ThreadContext.SegCs = 0x18;
    ThreadContext.EFlags = 0x3000;
    ThreadContext.Esp = ULONG(InitialTeb.StackCommit) - 4;
    ThreadContext.Eip = ULONG(_ThreadProc);      // 函数入口地址
其中 ThreadContext 的 Eip 字段为函数入口地址,但是 HOOK 的正常调用该字段值却是一个固定值,并非函数入口地址,困惑。

以上两种初始化方法,或者结合两种方法的结果,都是失败: ZwCreateThread 返回 0xc0000005 内存非法访问!?
请大家指点指点,感激不尽!!
Thinking
ks12345
驱动小牛
驱动小牛
  • 注册日期2006-09-21
  • 最后登录2016-01-09
  • 粉丝0
  • 关注0
  • 积分7分
  • 威望223点
  • 贡献值0点
  • 好评度189点
  • 原创分0分
  • 专家分0分
沙发#
发布于:2007-01-08 10:32
由于涉及到非法访问内存,我把初始化栈的代码也贴上来:
//
// initialize the INITIAL_TEB structure
//
BOOL
InitUserStack(
    PINITIAL_TEB    pInitialTeb
    )
{
    ULONG StackPageSize = 0x1000;
    ULONG MaximumStackSize = 0x100000;

    pInitialTeb->StackBase = NULL;
    pInitialTeb->StackLimit = NULL;
    
    //
    // Reserve address space for the stack
    //
    pInitialTeb->StackReserved = VirtualAlloc(NULL, MaximumStackSize, MEM_RESERVE, PAGE_READWRITE);
    if (pInitialTeb->StackReserved == NULL)
    {
        return FALSE;
    }
    pInitialTeb->StackCommit = PCHAR(pInitialTeb->StackReserved) + MaximumStackSize;
    pInitialTeb->StackCommitMax = PCHAR(pInitialTeb->StackCommit) - StackPageSize;

    //
    // commit
    //
    LPVOID pStack = PCHAR(pInitialTeb->StackCommit) - 2*StackPageSize;
    if (!VirtualAlloc(pStack, 2*StackPageSize, MEM_COMMIT, PAGE_READWRITE))
    {
        VirtualFree(pInitialTeb->StackReserved, 0, MEM_RELEASE);
        return FALSE;
    }
    //
    // protect
    //
    DWORD dwOldProtect;
    if (!VirtualProtect(pStack, StackPageSize,
                PAGE_READWRITE | PAGE_GUARD, &dwOldProtect))
    {
        VirtualFree(pInitialTeb->StackReserved, 0, MEM_RELEASE);
        return FALSE;
    }
    
    return TRUE;
}

跟踪查看栈的地址值还是与正常调用一致的,貌似没有错误。
Thinking
ks12345
驱动小牛
驱动小牛
  • 注册日期2006-09-21
  • 最后登录2016-01-09
  • 粉丝0
  • 关注0
  • 积分7分
  • 威望223点
  • 贡献值0点
  • 好评度189点
  • 原创分0分
  • 专家分0分
板凳#
发布于:2007-01-09 09:22
以上初始化参数在应用层调用 ZwCreateThread 可以成功,线程结束时有非法访问内存。在核心层以这些初始化参数调用 ZwCreateThread 将会失败返回 0xC0000005 。阿门,貌似应用层内存地址到核心层的转化问题,看来我还是太菜了点,不知道怎样才能搞定。。。
Thinking
ks12345
驱动小牛
驱动小牛
  • 注册日期2006-09-21
  • 最后登录2016-01-09
  • 粉丝0
  • 关注0
  • 积分7分
  • 威望223点
  • 贡献值0点
  • 好评度189点
  • 原创分0分
  • 专家分0分
地板#
发布于:2007-01-26 15:26
500年过去了,不知道高手们是不屑回答如此简单的问题,还是都忙着搞服务器数据恢复去了。。。
Thinking
ks12345
驱动小牛
驱动小牛
  • 注册日期2006-09-21
  • 最后登录2016-01-09
  • 粉丝0
  • 关注0
  • 积分7分
  • 威望223点
  • 贡献值0点
  • 好评度189点
  • 原创分0分
  • 专家分0分
地下室#
发布于:2007-02-27 17:38
谢谢 killvxk  的回复,这个问题已经暂时搁下了
Thinking
游客

返回顶部