Windows通用线程类(C++)

特点:

完全适用于VC和BCB;

按照BCB的TThread类接口开发,可以代替TThread类;

适用Hook消息同步线程,不依靠窗体;

 

/********************************************************************************
文件名 : esThread.h
功  能 : 用API实现类似BCB中TThread的一个类, 可以用于VC和BCB
--------------------------------------------------------------------------------
备  注 : 完全适用于VC和BCB
         按照BCB的TThread类接口开发,可以代替TThread类
         适用Hook消息同步线程,不依靠窗体
--------------------------------------------------------------------------------
修改记录 :
日 期               版本     修改人              修改内容
2007/05/30 - 6/25   0.1      cczlp               创建
*******************************************************************************
*/

#ifndef _CESTHREAD_H_
#define  _CESTHREAD_H_

#include 
< windows.h >
#include 
< process.h >
#include 
< tlhelp32.h >

namespace  CESTHREAD
{

class CesThread
{
/// 类型定义
#ifdef __BORLANDC__
    typedef 
void __fastcall(__closure *ThreadMethod)(void);
    typedef 
void __fastcall(__closure *OnTerminateFun)(void);
#else
    typedef 
void(__stdcall  *ThreadMethod)(void);
    typedef 
void(__stdcall  *OnTerminateFun)(void);
#endif

private:
/// 属性
    unsigned         m_Handle;                    //
    unsigned         m_ThreadID;
    
bool             m_bCreateSuspended;
    
bool             m_bSuspended;
    
bool             m_FreeOnTerminate;
    
bool             m_Finished;

    
static HHOOK     m_hHookMsg;
    
static DWORD     m_MainThreadID;
    
static HWND      m_MainWnd;
    
static LONG      m_HookCount;

    HANDLE           m_hMsgEvt;
    ThreadMethod     m_Method;

private:
/ 私有的方法
    /********************************************************************************
    函数名   : GetMainThreadID
    功能     : 取得主线程ID
    参数     : IN dwOwnerPID -  进程的PID, 指出取哪个进程的主线程ID
    返回值   : 失败返回0, 否则返回主线程ID
    ******************************************************************************
*/

    DWORD __fastcall GetMainThreadID(DWORD dwOwnerPID)
    
{
        HANDLE hThreadSnap 
= INVALID_HANDLE_VALUE;
        THREADENTRY32 te32;
        DWORD dwThreadID 
= 0;

        hThreadSnap 
= CreateToolhelp32Snapshot(TH32CS_SNAPTHREAD, 0);
        
if (hThreadSnap == INVALID_HANDLE_VALUE)
        
{
            
return 0;
        }


        te32.dwSize 
= sizeof(THREADENTRY32);
        
if (!Thread32First(hThreadSnap, &te32))
        
{
            CloseHandle(hThreadSnap);
        }


        
do
        
{
            
if (te32.th32OwnerProcessID == dwOwnerPID)
            
{
                
//返回找到的第一个线程, 不知道这个线程是否一定是主线程(WinMain所在线程)
                dwThreadID = te32.th32ThreadID;
                
break;
            }

        }

        
while (Thread32Next(hThreadSnap, &te32));

        CloseHandle(hThreadSnap);
        
return(dwThreadID);
    }


    
/*******************************************************************************
    函数名   : EnumWindowsProc
    功能     : 枚举窗口函数
    参数     : IN hwnd -  进窗口句柄
               IN lParam - 参数
    返回值   : 返回FALSE停止枚举
    ******************************************************************************
*/

    
static BOOL CALLBACK EnumWindowsProc(HWND hwnd, LPARAM lParam)
    
{
        CesThread 
*thread = (CesThread *)lParam;
        
if (GetWindowThreadProcessId(hwnd, NULL) == thread->m_MainThreadID)
        
{
            thread
->m_MainWnd = hwnd;
            
return FALSE;
        }

        
return TRUE;
    }


    
/*******************************************************************************
    函数名   : ThreadProc
    功能     : 线程执行函数
    参数     : IN p -  传递过来的参数
    返回值   : 返回线程结束码
    ******************************************************************************
*/

    
static unsigned  __stdcall ThreadProc(void *p)
    
{
        
bool bFreeThread;
        
int Result;
        CesThread 
*Thread = (CesThread *)p;
        __try
        
{
            
if (!Thread->Terminated)
        
{
            Thread
->Execute();
            }

        }

        __finally
        
{
            bFreeThread 
= Thread->m_FreeOnTerminate;
            Result 
= Thread->ReturnValue;
            Thread
->m_Finished = true;
            Thread
->DoTerminate();
            
if (bFreeThread)
        
{
            delete Thread;
        }

        _endthreadex(Result);
    }

    
return Result;
}


/*******************************************************************************
函数名   : GetMsgProc
功能     : 消息钩子执行函数, 用来同步处理用户指定函数
参数     : 详见MSDN
返回值   : 详见MSDN
******************************************************************************
*/

static LRESULT CALLBACK GetMsgProc(
    
int code,       // hook code
    WPARAM wParam,  // removal flag
    LPARAM lParam   // address of structure with message
)
    
{
        MSG 
*pMsg = (MSG *)lParam;

        
if (code == HC_ACTION && pMsg->message == WM_NULL)
        
{
            CesThread 
*Thread = (CesThread *)(pMsg->lParam);
            
if (Thread != NULL)
            
{
                
try
                
{
                    
if (Thread->m_Method != NULL)
                    
{
                        Thread
->m_Method();
                    }

                }

                
catch (...)
                
{}
                SetEvent(Thread
->m_hMsgEvt);
            }

            
return 1;
        }

        
return CallNextHookEx(m_hHookMsg, code, wParam, lParam);
    }


protected:
/// 保护方法
    /*******************************************************************************
    函数名   : DoTerminate
    功能     : 线程退出时调用
    参数     : 无
    返回值   : 无
    ******************************************************************************
*/

    
virtual void __fastcall DoTerminate(void)
    
{
        
if (OnTerminate != NULL)
        
{
            Synchronize(OnTerminate);
        }

    }


    
/*******************************************************************************
    函数名   : Execute
    功能     : 线程执行体, 虚函数, 需要用户重载
    参数     : 无
    返回值   : 无
    ******************************************************************************
*/

    
virtual void __fastcall Execute(void= 0;
    
/*******************************************************************************
    函数名   : Synchronize
    功能     : 线程中同步执行用户函数, 使用了消息机制
    参数     : IN Method - 同步执行的函数, 用户指定
               IN ThreadID - 需要同步线程的ID,默认为主线程
    返回值   : 无
    ******************************************************************************
*/

    
void __fastcall Synchronize(ThreadMethod Method,
                                DWORD ThreadID 
= m_MainThreadID)
    
{
        
if (m_hHookMsg == NULL)
        
{
            m_hHookMsg 
= SetWindowsHookEx(WH_GETMESSAGE,
                                          (HOOKPROC)GetMsgProc, NULL, ThreadID);
            
if (m_hHookMsg == NULL)
            
{
                
return;  //可能ThreadID错误或者其它原因
            }

            PostThreadMessage(ThreadID, WM_NULL, 
0, NULL);
            Sleep(
1);
        }


        m_Method 
= Method;
        m_hMsgEvt  
= CreateEvent(NULL, falsefalse, NULL);

        
if (PostThreadMessage(ThreadID, WM_NULL, 0, (LPARAM)this))
        
{
            WaitForSingleObject(m_hMsgEvt, INFINITE);
            
//while (WaitForSingleObject(m_hMsgEvt, 100) != WAIT_OBJECT_0 && !Terminated);
        }

        
else //ThreadID对应线程没有消息队列
        {
            Method(); 
//注意:由调用者自己保证同步
        }


        CloseHandle(m_hMsgEvt);
    }


protected:
/// 保护属性
    int ReturnValue;
    
bool Terminated;

public:
/// 公用属性
    bool FreeOnTerminate;
    OnTerminateFun OnTerminate;


public:
/// 公用方法
    /*******************************************************************************
    函数名   : CesThread
    功能     : 类构造函数
    参数     : IN CreateSuspended - 线程创建的后是否挂起
    返回值   : 无
    ******************************************************************************
*/

#ifdef __BORLANDC__
    __fastcall CesThread(
bool CreateSuspended = false)
#else
    CesThread(
bool CreateSuspended = false)
#endif
    
{
        m_bCreateSuspended 
=  CreateSuspended;
        m_bSuspended 
= CreateSuspended;
        m_Finished 
= false;
        Terminated 
= false;
        ReturnValue 
= 0;

        m_Method 
= NULL;
        m_FreeOnTerminate 
= false;
        OnTerminate 
= NULL;

        
if (m_MainThreadID == 0)
        
{
            m_MainThreadID 
= GetMainThreadID(GetCurrentProcessId());
        }

        InterlockedIncrement(
&m_HookCount);

        m_Handle 
= _beginthreadex(NULL, 0, ThreadProc, this,
                                  CreateSuspended 
? CREATE_SUSPENDED : 0,
                                  
&m_ThreadID);
        
if (m_Handle == 0)
        
{
            m_Finished 
= true;
            m_bSuspended 
= false;
        }

    }


    
/*******************************************************************************
    函数名   : ~CesThread
    功能     : 类析构函数
    参数     : 无
    返回值   : 无
    ******************************************************************************
*/

#ifdef __BORLANDC__
    
virtual __fastcall ~CesThread(void)
#else
    
virtual ~CesThread(void)
#endif
    
{
        
if (m_ThreadID != 0 && !m_Finished)
        
{
            Terminate();
            
if (m_bCreateSuspended)
            
{
                Resume();
            }

            WaitFor();
        }

        
if (m_Handle != 0)
        
{
            CloseHandle((HANDLE)m_Handle);
            m_Handle 
= 0;
        }

        InterlockedDecrement(
&m_HookCount);
        
if (m_hHookMsg != NULL && m_HookCount <= 0)
        
{
            UnhookWindowsHookEx(m_hHookMsg);
            m_hHookMsg 
= NULL;
        }

    }


    
/*******************************************************************************
    函数名   : Resume
    功能     : 继续线程的执行
    参数     : 无
    返回值   : 无
    ******************************************************************************
*/

    
void __fastcall Resume(void)
    
{
        
if (m_bSuspended)
        
{
            
if (ResumeThread((HANDLE)m_Handle) == 1)
            
{
                m_bSuspended 
= false;
            }

        }

    }


    
/*******************************************************************************
    函数名   : Suspend
    功能     : 暂停线程的执行
    参数     : 无
    返回值   : 无
    ******************************************************************************
*/

    
void __fastcall Suspend(void)
    
{
        
if (!m_bSuspended)
        
{
            
if (SuspendThread((HANDLE)m_Handle) != 0xFFFFFFFF)
            
{
                m_bSuspended 
= true;
            }

        }

    }


    
/*******************************************************************************
    函数名   : Terminate
    功能     : 终止线程的执行
    参数     : 无
    返回值   : 无
    ******************************************************************************
*/

    
void __fastcall Terminate(void)
    
{
        Terminated 
= true;
    }


    
/*******************************************************************************
    函数名   : WaitFor
    功能     : 等待线程完全退出
    参数     : 无
    返回值   : 线程退出码
    ******************************************************************************
*/

    unsigned __fastcall WaitFor(
void)
    
{
        DWORD Result 
= 0;
        MSG Msg;
        HANDLE  H ;

        H 
= (HANDLE)m_Handle;
        
if (GetCurrentThreadId() == m_MainThreadID)
        
{
            
while (::MsgWaitForMultipleObjects(1&H, false, INFINITE,
                                               QS_SENDMESSAGE) 
== WAIT_OBJECT_0 + 1)
            
{
                ::PeekMessage(
&Msg, 000, PM_NOREMOVE);
            }

        }

        
else
        
{
            WaitForSingleObject(H, INFINITE);
        }

        GetExitCodeThread(H, 
&Result);

        
return Result;
    }


    
/*******************************************************************************
    函数名   : GetHandle
    功能     : 返回线程句柄
    参数     : 无
    返回值   : 线程句柄
    ******************************************************************************
*/

    inline unsigned __fastcall GetHandle(
void)
    
{
        
return m_Handle;
    }
;

    inline unsigned __fastcall GetThreadId(
void)
    
{
        
return m_ThreadID;
    }


    
/*******************************************************************************
    函数名   : SetPriority
    功能     : 设置线程优先级
    参数     : IN Value - 优先级别, 参考 MSDN 中SetThreadPriority函数
    返回值   : 无
    ******************************************************************************
*/

    
void __fastcall SetPriority(int Value)
    
{
        SetThreadPriority((HANDLE)m_Handle, Value);
    }

    
/*******************************************************************************
    函数名   : GetPriority
    功能     : 读取线程优先级
    参数     : 无
    返回值   : 优先级别, 参考 MSDN 中SetThreadPriority函数
    ******************************************************************************
*/

    
int __fastcall GetPriority(void)
    
{
        
return GetThreadPriority((HANDLE)m_Handle);
    }


    
/*******************************************************************************
    函数名   : IsSuspended
    功能     : 线程是否暂停
    参数     : 无
    返回值   : 暂停返回TRUE
    ******************************************************************************
*/

    
bool __fastcall IsSuspended(void)
    
{
        
return m_bSuspended;
    }


    
/*******************************************************************************
    函数名   : GetMainWnd
    功能     : 取主线程中的窗体, 如果多个窗体, 返回其中的一个
    参数     : 无
    返回值   : 窗体句柄
    ******************************************************************************
*/

    HWND __fastcall GetMainWnd(
void)
    
{
        
if (m_MainWnd != NULL && IsWindow(m_MainWnd))
        
{
            
return m_MainWnd;
        }


        EnumWindows((WNDENUMPROC)EnumWindowsProc, (LPARAM)
this);
        
return m_MainWnd;
    }

}
;
/// 静态变量
HHOOK    CesThread::m_hHookMsg  = 0;
DWORD    CesThread::m_MainThreadID 
= 0;
HWND     CesThread::m_MainWnd 
= NULL;
LONG     CesThread::m_HookCount 
= 0;

}

using   namespace  CESTHREAD;


#endif   // _CESTHREAD_H_
  • 0
    点赞
  • 0
    收藏
  • 打赏
    打赏
  • 5
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
©️2022 CSDN 皮肤主题:大白 设计师:CSDN官方博客 返回首页
评论 5

打赏作者

cczlp

你的鼓励将是我创作的最大动力

¥2 ¥4 ¥6 ¥10 ¥20
输入1-500的整数
余额支付 (余额:-- )
扫码支付
扫码支付:¥2
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、C币套餐、付费专栏及课程。

余额充值