Kak ot idThread da izwadq ThreadHandle?
3 отговора
121 прегледа
Kak ot idThread da izwadq ThreadHandle?
Ami to drugo mai nqma po wyprosa - imam identifikator, trqbwa mi Handle.
Re: Kak ot idThread da izwadq ThreadHandle?
OpenThread bi trabvalo da ti svurshi rabota, no raboti samo za W2K.
Za 9x, NT edinstvenia nachin mai e chrez Debug API-to, vij Platform SDK: Debugging and Error Handling v MSDN.
Za 9x, NT edinstvenia nachin mai e chrez Debug API-to, vij Platform SDK: Debugging and Error Handling v MSDN.
Re: Kak ot idThread da izwadq ThreadHandle?
Za NT probvai tova nesto, v momenta ne moga da go probvam no ima goliama veroiatnost da raboti.
#include <windows.h>
HANDLE (__stdcall *NtOpenThread)(
IN ULONG dwDesiredAccess,
IN int bInheritHandle,
IN ULONG dwThreadId);
HANDLE OpenThread(ULONG ThreadId)
{
HINSTANCE hNtDll;
HANDLE hThread;
hNtDll = LoadLibrary ("NTDLL");
if (!hNtDll)
return 0;
NtOpenThread = (void*)GetProcAddress (hNtDll, "NtOpenThread");
if (!NtOpenThread)
return 0;
hThread = NtOpenThread(THREAD_ALL_ACCESS, 0, ThreadId);
FreeLibrary (hNtDll);
return hThread;
}
#include <windows.h>
HANDLE (__stdcall *NtOpenThread)(
IN ULONG dwDesiredAccess,
IN int bInheritHandle,
IN ULONG dwThreadId);
HANDLE OpenThread(ULONG ThreadId)
{
HINSTANCE hNtDll;
HANDLE hThread;
hNtDll = LoadLibrary ("NTDLL");
if (!hNtDll)
return 0;
NtOpenThread = (void*)GetProcAddress (hNtDll, "NtOpenThread");
if (!NtOpenThread)
return 0;
hThread = NtOpenThread(THREAD_ALL_ACCESS, 0, ThreadId);
FreeLibrary (hNtDll);
return hThread;
}
Re: Kak ot idThread da izwadq ThreadHandle?
from wisdom.txt:
typedef struct tagPDB
{
WORD Type;
WORD Refcount;
DWORD Unk0;
DWORD Unk1;
DWORD Unk2;
DWORD TermStatus;
DWORD Unk3;
DWORD DefaultHeap;
DWORD MemContext; /* Yes, use this with ContextSwitch :) */
DWORD Flags;
DWORD pPsp;
WORD PSPSelector;
WORD MTEIndex;
WORD nThreads;
WORD nThreadsNotTerm;
WORD Unk5;
WORD nR0Threads;
DWORD HeapHandle;
WORD K16TDBSel;
WORD Unk6;
DWORD Unk7;
DWORD pEDB;
DWORD pHandleTable;
struct t PDB *ParentPDB;
DWORD MODREFList;
DWORD ThreadList;
DWORD DebugeeCB;
DWORD LHFreeHead;
DWORD InitialR0ID;
}PDB, *PPDB;
typedef struct tagTCB
{
WORD Type;
WORD RefCount;
DWORD Unk1;
DWORD pvExcept;
DWORD TopOfStack;
DWORD BaseOfStack;
WORD K16TDB;
WORD StackSel16;
DWORD Unk2;
DWORD UserPointer;
DWORD pTIB;
WORD TIBflags;
WORD Win16MutxCnt;
DWORD DebugContext;
DWORD PtrToCurPri;
DWORD MsgQueue;
DWORD pTLSarray;
PPDB pParentPDB;
DWORD SelmanList;
DWORD Unk3;
DWORD Flags;
DWORD Status;
WORD TIBsel;
WORD EmulatorSel;
DWORD HandleCount;
DWORD WaitNodeList;
DWORD R0hThread;
DWORD ptdbx;
}TCB, *PTCB;
typedef DWORD (WINAPI*OTFUNC)(HANDLE*,DWORD,void*,void*);
typedef LPVOID (WINAPI *OBFUNC)(DWORD dwPTID);
/* just use OpenThread2 because it will detect wether you are on NT or
not */
HANDLE WINAPI OpenThread2(DWORD dwThreadID, BOOL bInherit, DWORD
dwAccess);
HANDLE WINAPI OpenThreadNT(DWORD dwThreadID, BOOL bInherit, DWORD
dwAccess);
LPVOID WINAPI GetTrueProcAddress(LPSTR lpMod, LPTSTR lpFunc);
LPVOID WINAPI XORProcessThreadID(DWORD dwPTID);
/*********************************************************/
/* And yes, the Thread ID and Process ID use the same obfuscation
pointer. */
LPVOID WINAPI XORProcessThreadID(DWORD dwPTID)
{
OBFUNC obfuscate;
DWORD dwMain,*lpdw,dw1;
dwMain = (DWORD)GetTrueProcAddress( T("KERNEL32"),
T("GetCurrentThreadId"));
/*
* this retreives the address and runs
* the obfuscation function directly
* using GetCurrentThreadId.. since in
* win98 you don't seem to have access to
* the randomized obfuscation pointer.
* Yes, works with all versions of 98/95 :)
*/
lpdw = (LPDWORD)((DWORD)dwMain + 8);
dw1 = ((DWORD)dwMain + 12);
obfuscate = (OBFUNC)(dw1+*lpdw);
return(obfuscate(dwPTID));
}
HANDLE WINAPI OpenThread2(DWORD dwThreadID, BOOL bInherit, DWORD
dwAccess)
{
HANDLE hThread,hprc;
LPDWORD lp1;
DWORD dwProcessID,dwWhere,dwTable;
BOOL b1;
PTCB lpThreadObj;
PPDB ppdb;
OSVERSIONINFO osvi;
osvi.dwOSVersionInfoSize = sizeof(OSVERSIONINFO);
GetVersionEx(&osvi);
SetLastError(50);
if(osvi.dwPlatformId == VER PLATFORM WIN32 NT)
return OpenThreadNT(dwThreadID, bInherit);
ppdb = (PPDB)XORProcessThreadID(GetCurrentProcessId());
lpThreadObj = XORProcessThreadID(dwThreadID);
/* check to make sure its valid */
if(IsBadReadPtr(lpThreadObj, sizeof(TCB))) return NULL;
/* check object type */
if(*(LPBYTE)lpThreadObj != 7) return NULL;
dwProcessID =
(DWORD)XORProcessThreadID((DWORD)lpThreadObj->pParentPDB);
if(dwProcessID == GetCurrentProcessId())
hprc = GetCurrentProcess();
else
{
hprc = OpenProcess(PROCESS ALL ACCESS,
FALSE, dwProcessID);
if(!hprc) return NULL;
}
/*
* 4 is the lowest handle in the table.
* All processes have this handle.
*/
b1 = DuplicateHandle(hprc,
(HANDLE)4,
GetCurrentProcess(),
&hThread,
dwAccess,
bInherit, 0);
if(hprc != GetCurrentProcess())
CloseHandle(hprc);
if(!b1) return NULL;
dwWhere = ((DWORD)hThread) >> 2;
dwTable = ppdb->pHandleTable;
lp1 = (LPDWORD)(dwTable+(dwWhere*8)+8);
*lp1 = (DWORD)lpThreadObj;
return(hThread);
}
HANDLE WINAPI OpenThreadNT(DWORD dwThreadID, BOOL bInherit, DWORD
dwAccess)
{
HANDLE hThread = NULL;
DWORD struct1[] = {0x18, 0, 0, 0, 0, 0};
DWORD struct2[] = {0,dwThreadID};
HMODULE hLib = LoadLibrary( T("ntdll.dll"));
OTFUNC OpenThatNTThread =
(OTFUNC)GetProcAddress(hLib, T("NtOpenThread"));
struct1[3] = bInherit;
OpenThatNTThread(&hThread, dwAccess, struct1, struct2);
FreeLibrary(hLib);
return hThread;
}
/*
* Note: The assembly for GetCurrentThreadId
* (not to mention probably every other
* kernel32 function) in all the versions
* does not start with 68h (push dword data).
* The reason I do this is because sometimes
* the GetProcAddress will not return the
* exact address of the actual function.
* The address it returns is used for
* pre-processing, and is probably only used
* for tracing the functions or debugging.
* It isn't needed to run the function,
* so don't worry.
*/
LPVOID WINAPI GetTrueProcAddress(LPSTR lpMod, LPTSTR lpFunc)
{
LPVOID bla = GetProcAddress(GetModuleHandle(lpMod), lpFunc);
if(!bla) return NULL;
if(*(LPBYTE)bla == 0x68)
bla = (LPVOID)*(LPDWORD)((DWORD)bla + 1);
return bla;
}
typedef struct tagPDB
{
WORD Type;
WORD Refcount;
DWORD Unk0;
DWORD Unk1;
DWORD Unk2;
DWORD TermStatus;
DWORD Unk3;
DWORD DefaultHeap;
DWORD MemContext; /* Yes, use this with ContextSwitch :) */
DWORD Flags;
DWORD pPsp;
WORD PSPSelector;
WORD MTEIndex;
WORD nThreads;
WORD nThreadsNotTerm;
WORD Unk5;
WORD nR0Threads;
DWORD HeapHandle;
WORD K16TDBSel;
WORD Unk6;
DWORD Unk7;
DWORD pEDB;
DWORD pHandleTable;
struct t PDB *ParentPDB;
DWORD MODREFList;
DWORD ThreadList;
DWORD DebugeeCB;
DWORD LHFreeHead;
DWORD InitialR0ID;
}PDB, *PPDB;
typedef struct tagTCB
{
WORD Type;
WORD RefCount;
DWORD Unk1;
DWORD pvExcept;
DWORD TopOfStack;
DWORD BaseOfStack;
WORD K16TDB;
WORD StackSel16;
DWORD Unk2;
DWORD UserPointer;
DWORD pTIB;
WORD TIBflags;
WORD Win16MutxCnt;
DWORD DebugContext;
DWORD PtrToCurPri;
DWORD MsgQueue;
DWORD pTLSarray;
PPDB pParentPDB;
DWORD SelmanList;
DWORD Unk3;
DWORD Flags;
DWORD Status;
WORD TIBsel;
WORD EmulatorSel;
DWORD HandleCount;
DWORD WaitNodeList;
DWORD R0hThread;
DWORD ptdbx;
}TCB, *PTCB;
typedef DWORD (WINAPI*OTFUNC)(HANDLE*,DWORD,void*,void*);
typedef LPVOID (WINAPI *OBFUNC)(DWORD dwPTID);
/* just use OpenThread2 because it will detect wether you are on NT or
not */
HANDLE WINAPI OpenThread2(DWORD dwThreadID, BOOL bInherit, DWORD
dwAccess);
HANDLE WINAPI OpenThreadNT(DWORD dwThreadID, BOOL bInherit, DWORD
dwAccess);
LPVOID WINAPI GetTrueProcAddress(LPSTR lpMod, LPTSTR lpFunc);
LPVOID WINAPI XORProcessThreadID(DWORD dwPTID);
/*********************************************************/
/* And yes, the Thread ID and Process ID use the same obfuscation
pointer. */
LPVOID WINAPI XORProcessThreadID(DWORD dwPTID)
{
OBFUNC obfuscate;
DWORD dwMain,*lpdw,dw1;
dwMain = (DWORD)GetTrueProcAddress( T("KERNEL32"),
T("GetCurrentThreadId"));
/*
* this retreives the address and runs
* the obfuscation function directly
* using GetCurrentThreadId.. since in
* win98 you don't seem to have access to
* the randomized obfuscation pointer.
* Yes, works with all versions of 98/95 :)
*/
lpdw = (LPDWORD)((DWORD)dwMain + 8);
dw1 = ((DWORD)dwMain + 12);
obfuscate = (OBFUNC)(dw1+*lpdw);
return(obfuscate(dwPTID));
}
HANDLE WINAPI OpenThread2(DWORD dwThreadID, BOOL bInherit, DWORD
dwAccess)
{
HANDLE hThread,hprc;
LPDWORD lp1;
DWORD dwProcessID,dwWhere,dwTable;
BOOL b1;
PTCB lpThreadObj;
PPDB ppdb;
OSVERSIONINFO osvi;
osvi.dwOSVersionInfoSize = sizeof(OSVERSIONINFO);
GetVersionEx(&osvi);
SetLastError(50);
if(osvi.dwPlatformId == VER PLATFORM WIN32 NT)
return OpenThreadNT(dwThreadID, bInherit);
ppdb = (PPDB)XORProcessThreadID(GetCurrentProcessId());
lpThreadObj = XORProcessThreadID(dwThreadID);
/* check to make sure its valid */
if(IsBadReadPtr(lpThreadObj, sizeof(TCB))) return NULL;
/* check object type */
if(*(LPBYTE)lpThreadObj != 7) return NULL;
dwProcessID =
(DWORD)XORProcessThreadID((DWORD)lpThreadObj->pParentPDB);
if(dwProcessID == GetCurrentProcessId())
hprc = GetCurrentProcess();
else
{
hprc = OpenProcess(PROCESS ALL ACCESS,
FALSE, dwProcessID);
if(!hprc) return NULL;
}
/*
* 4 is the lowest handle in the table.
* All processes have this handle.
*/
b1 = DuplicateHandle(hprc,
(HANDLE)4,
GetCurrentProcess(),
&hThread,
dwAccess,
bInherit, 0);
if(hprc != GetCurrentProcess())
CloseHandle(hprc);
if(!b1) return NULL;
dwWhere = ((DWORD)hThread) >> 2;
dwTable = ppdb->pHandleTable;
lp1 = (LPDWORD)(dwTable+(dwWhere*8)+8);
*lp1 = (DWORD)lpThreadObj;
return(hThread);
}
HANDLE WINAPI OpenThreadNT(DWORD dwThreadID, BOOL bInherit, DWORD
dwAccess)
{
HANDLE hThread = NULL;
DWORD struct1[] = {0x18, 0, 0, 0, 0, 0};
DWORD struct2[] = {0,dwThreadID};
HMODULE hLib = LoadLibrary( T("ntdll.dll"));
OTFUNC OpenThatNTThread =
(OTFUNC)GetProcAddress(hLib, T("NtOpenThread"));
struct1[3] = bInherit;
OpenThatNTThread(&hThread, dwAccess, struct1, struct2);
FreeLibrary(hLib);
return hThread;
}
/*
* Note: The assembly for GetCurrentThreadId
* (not to mention probably every other
* kernel32 function) in all the versions
* does not start with 68h (push dword data).
* The reason I do this is because sometimes
* the GetProcAddress will not return the
* exact address of the actual function.
* The address it returns is used for
* pre-processing, and is probably only used
* for tracing the functions or debugging.
* It isn't needed to run the function,
* so don't worry.
*/
LPVOID WINAPI GetTrueProcAddress(LPSTR lpMod, LPTSTR lpFunc)
{
LPVOID bla = GetProcAddress(GetModuleHandle(lpMod), lpFunc);
if(!bla) return NULL;
if(*(LPBYTE)bla == 0x68)
bla = (LPVOID)*(LPDWORD)((DWORD)bla + 1);
return bla;
}