• 线程上下文数据结构


    WINDOWS 中定义了一个CONTEXT 结构,该结构包含了特定处理器上的寄存器数据。系统使用CONTEXT 结构执行各种内部操作。目前,已经存在为IntelMIPSAlphaPowerPC 处理器定义的CONTEXT 结构。若要了解这些结构的定义,可以去看WinNT.h

    该结构并没有说明结构体内的成员,也没有描述这些成员是谁,因为这些成员要取决于WINDOWS 运行在哪个平台上。在WINDOWS 定义的所有数据结构中,CONTEXT 结构是特定于CPU 的唯一结构。

     

    CONTEXT 结构中,它包含了主机CPU 上的每个寄存器的数据结构。在X86 计算机上,数据成员是EAXEBXECXEDX 等等。如果是Alpha 处理器,那么数据成员包括IntV0,IntT0,IntT1,IntS0,IntRaIntZero 等等。下面的代码演示了X86 CPU 完整的CONTEXT 结构。

     

    typedef struct _CONTEXT

    {

        DWORD ContextFlags;

     

        // 调试寄存器

       DWORD Dr0;

       DWORD Dr1;

       DWORD Dr2;

       DWORD Dr3;

       DWORD Dr6;

       DWORD Dr7;

     

      // 浮点寄存器

       FLOATING_SAVE_AREA FloatSave;

     

    // 栈寄存器

       DWORD SegGs;

       DWORD SegFs;

       DWROD SegEs;

       DWORD SegDs;

     

    // 整型寄存器

       DWORD Edi;

       DWORD Esi;

       DWORD Ebx;

       DWORD Edx;

       DWORD Ecx;

       DWORD Eax;

     

    // 控制寄存器

       DWORD Ebp;

       DWORD Eip;

       DWORD SegCs;

       DWORD EFlags;

       DWORD Esp;

       DWORD SegSs;

     

    // 扩展寄存器

       BYTE ExtendedRegisters[MAXIMUM_SUPPORTED_EXTENSION];

    }CONTEXT;

     

    可以使用 BOOL GetThreadContext(HANDLE,PCONTEXT); 函数来取得一个线程的上下文。

    ContextFlags 用于指定你关注此数据结构中哪些寄存器值。可以是如下定义

    CONTEXT_CONTROL

    CONTEXT_INTEGER

    CONTEXT_SEGMENTS

    CONTEXT_FLOATING_POINT

    CONTEXT_DEBUG_REGISTERS

    CONTEXT_EXTENDED_REGISTERS;

     

    另外,在WinNT.h 中还定义了一个CONTEXT_FULL 定义如下

     

    #ifdefine _X86

    #define CONTEXT_FULL \

    CONTEXT_CONTROL|CONTEXT_INTEGER|CONTEXT_SEGMENTS

     

    #endif

     

    #ifdefine _ALPHA

     

    #define CONTEXT_FULL \ CONTEXT_CONTROL|CONTEXT_FLOATING_POINT|CONTEXT_INTEGER

     

    #endif

     

     

    同样我们可以通过SetThreadContext(HANDLE,PCONTEXT); 来修改一个线程的寄存器值。步骤如下。

    1、  将要操作的线程挂起。

    2、    定义一个CONTEXT 结构变量,将其ContextFlags 初始化,标记你关注哪些值。

    3、    使用GetThreadContext 取得上下文。

    4、    修改你想修改的寄存器值。

    5、    SetThreadContext 更新系统中线程的上下文。

    6、    唤醒线程

     

    另外,对于指令指针和堆栈指针寄存器X86ALPHA 机器上是不一样的。

    X86EIPESP ,而ALPHA 中是FirIntSp 。在使用的时候,应该根据具体情况分析。。当然,上面的操作在一般的应用程序中不会使用。若你想编写调试程序,调试器等才有可能用到。


  • 相关阅读:
    小程序自动更新版本
    js深浅拷贝理解
    小程序模仿toast效果
    小程序button默认border
    Java利用POI 读取Excel行列数,坑
    Nginx 极简入门教程
    七、SpringBoot整合持久化层,配置多数据源(SpringBoot系列)
    六、SpringBoot整合aop(SpringBoot系列)
    五、SpringBoot随系统启动任务的方式(SpringBoot系列)
    四、SpringBoot通过CORS解决跨域问题(SpringBoot系列)
  • 原文地址:https://www.cnblogs.com/qilinzi/p/1940484.html
Copyright © 2020-2023  润新知