⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 inject.c

📁 键盘锁
💻 C
📖 第 1 页 / 共 3 页
字号:
/***********************************************************
 * Restore the subclassed remote process window procedure. *
 * Return: 0=failure, 1=success                            *
 ***********************************************************/

#pragma optimize("", off)
#pragma check_stack(off)

static DWORD WINAPI EjectFunc (INJDATA *pData) 
{
	return (pData->fnSetWindowLong(pData->hwnd, GWL_WNDPROC, (long)pData->fnOldSASWndProc) != 0);
}


static int AfterEjectFunc(void) {return 3;}



/**************************************************************
 * Return the window handle of the remote process (Winlogon). *
 **************************************************************/

#pragma optimize("", off)
#pragma check_stack(off)

static HWND WINAPI GetSASWnd (INJDATA *pData) 
{
	return (pData->fnFindWindow(pData->szClassName, pData->szWindowName));
}


static int AfterGetSASWnd(void) {return 4;}



/***************************************************************************
 * Copies InjectFunc(), GetSASWnd() , SASWindowProc() and INJDATA to the   *
 * remote process.                                                         *
 * Starts the execution of the remote InjectFunc(), which subclasses the   *
 * remote process default window procedure handler.                        *
 *                                                                         *
 * Return value: 0=failure, 1=success                                      *
 ***************************************************************************/

int InjectCode ()
{
	HANDLE		hProcess = 0;			// Process handle
	HMODULE		hUser32  = 0;			// Handle of user32.dll
	BYTE		*pCodeRemote;			// Address of InjectFunc() in the remote process.
	BYTE		*pGetSASWndRemote;		// Address of GetSASWnd() in the remote process.
	HANDLE		hThread	= 0;			// The handle and ID of the thread executing
	DWORD		dwThreadId = 0;			//   the remote InjectFunc().
	INJDATA		DataLocal;				// INJDATA structure
	BOOL		fUnicode;				// TRUE if remote process is Unicode
	int			nSuccess = 0;			// Subclassing succeded?
	DWORD		dwNumBytesCopied = 0;	// Number of bytes written to the remote process.
	DWORD		size;					// Calculated function size (= AfterFunc() - Func())
	int			SearchSize;				// SASWindowProc() dummy addr. search size
	int			nDummyOffset;			// Offset in SASWindowProc() of dummy addr.
	BOOL		FoundDummyAddr;			// Dummy INJDATA reference found in SASWindowProc() ?
	HWND		hSASWnd;				// Window handle of Winlogon process
	BYTE		*p;

	// Enable Debug privilege (needed for some processes)
    if (!EnablePrivilege(SE_DEBUG_NAME, TRUE))
		return 0;

	// Get handle of "USER32.DLL"
	hUser32 = GetModuleHandle("user32");
	if (!hUser32)
		return 0;

	// Get remote process ID
    PID = GetPIDFromName(szProcessName);
    if (PID == -1)
		return 0;

	// Open remote process
	hProcess = OpenProcess(PROCESS_ALL_ACCESS, FALSE, PID);
	if (!hProcess)
		return 0;

	__try 
	{
		// Initialize INJDATA for GetSASWnd() call
		strcpy(DataLocal.szClassName, "SAS Window class");
		strcpy(DataLocal.szWindowName, "SAS window");
		DataLocal.fnFindWindow = (FINDWINDOW) GetProcAddress(hUser32, "FindWindowA");
		if (DataLocal.fnFindWindow == NULL)
			__leave;

		// Allocate memory in the remote process and write a copy of initialized INJDATA into it
		size = sizeof(INJDATA);
		pDataRemote = (PBYTE) VirtualAllocEx(hProcess, 0, size, MEM_COMMIT, PAGE_EXECUTE_READWRITE);		
		if (!pDataRemote)
			__leave;
		if (!WriteProcessMemory(hProcess, pDataRemote, &DataLocal, size, &dwNumBytesCopied) || dwNumBytesCopied != size)
			__leave;

		// Allocate memory in remote process and write a copy of GetSASWnd() into it
		size = (PBYTE)AfterGetSASWnd - (PBYTE)GetSASWnd;
		pGetSASWndRemote = (PBYTE) VirtualAllocEx(hProcess, 0, size, MEM_COMMIT, PAGE_EXECUTE_READWRITE);		
		if (!pGetSASWndRemote)
			__leave;
		if (!WriteProcessMemory(hProcess, pGetSASWndRemote, &GetSASWnd, size, &dwNumBytesCopied) || dwNumBytesCopied != size)
			__leave;
		
		// Start execution of remote GetSASWnd()
		hThread = CreateRemoteThread(hProcess, 
									 NULL, 
									 0, 
									 (LPTHREAD_START_ROUTINE) pGetSASWndRemote,
									 pDataRemote, 
									 0 , 
									 &dwThreadId);
		// Failed
		if (!hThread)
			__leave;

		// Wait for GetSASWnd() to terminate and get return code (SAS Wnd handle)
		WaitForSingleObject(hThread, INFINITE);
		GetExitCodeThread(hThread, (PDWORD) &hSASWnd);

		// Didn't found "SAS window"
		if (!hSASWnd)
			__leave;

		// Cleanup
		VirtualFreeEx(hProcess, pGetSASWndRemote, 0, MEM_RELEASE);
		VirtualFreeEx(hProcess, pDataRemote, 0, MEM_RELEASE);
		pGetSASWndRemote = NULL;
		pDataRemote = NULL;
		
		// Allocate memory in remote process and write a copy of SASWindowProc() into it
		size = (PBYTE)AfterSASWindowProc - (PBYTE)SASWindowProc;
		pSASWinProcRemote = (PBYTE) VirtualAllocEx(hProcess, 0, size, MEM_COMMIT, PAGE_EXECUTE_READWRITE);		
		if (!pSASWinProcRemote)
			__leave;
		if (!WriteProcessMemory(hProcess, pSASWinProcRemote, &SASWindowProc, size, &dwNumBytesCopied) || dwNumBytesCopied != size)
			__leave;

		// Is remote process unicode ?
		fUnicode = IsWindowUnicode(hSASWnd);

		// Initialize the INJDATA structure
		DataLocal.fnSetWindowLong = (SETWINDOWLONG)  GetProcAddress(hUser32, fUnicode ? "SetWindowLongW" : "SetWindowLongA");
		DataLocal.fnCallWindowProc = (CALLWINDOWPROC) GetProcAddress(hUser32, fUnicode ? "CallWindowProcW": "CallWindowProcA");
		DataLocal.fnSASWndProc = (WNDPROC) pSASWinProcRemote;
		DataLocal.hwnd = hSASWnd;

		if (DataLocal.fnSetWindowLong  == NULL || 			
			DataLocal.fnCallWindowProc == NULL)
		{
			__leave;		
		}

		// Allocate memory in the remote process and write a copy of initialized INJDATA into it
		size = sizeof(INJDATA);
		pDataRemote = (PBYTE) VirtualAllocEx(hProcess, 0, size, MEM_COMMIT, PAGE_EXECUTE_READWRITE);		
		if (!pDataRemote)
			__leave;
		if (!WriteProcessMemory(hProcess, pDataRemote, &DataLocal, size, &dwNumBytesCopied) || dwNumBytesCopied != size)
			__leave;

		// Change dummy INJDATA address in SASWindowProc() by the real INJDATA pointer
		p = (PBYTE)&SASWindowProc;
		size = (PBYTE)AfterSASWindowProc - (PBYTE)SASWindowProc;
		SearchSize = size - sizeof(DWORD) + 1;
		FoundDummyAddr = FALSE;

		for (; SearchSize > 0; p++, SearchSize--)
		{
			if (*(DWORD *)p == DUMMY_ADDR)	// Found 
			{
				nDummyOffset = p - (PBYTE)&SASWindowProc; 
				if (!WriteProcessMemory(hProcess, pSASWinProcRemote + nDummyOffset, &pDataRemote, sizeof(pDataRemote), &dwNumBytesCopied) ||
					dwNumBytesCopied != sizeof(pDataRemote))
				{
					__leave;
				}
				FoundDummyAddr = TRUE;
				break;
			}
		}

		// Couldn't change the dummy INJDATA addr. by the real addr. in SASWindowProc() !?!
		// Don't execute the remote copy of SASWindowProc() because the pData pointer is invalid !
		if (!FoundDummyAddr)
		{
			__leave;
		}

		// Allocate memory in the remote process and write a copy of InjectFunc() to the allocated memory
		size = (PBYTE)AfterInjectFunc - (PBYTE)InjectFunc;
		pCodeRemote = (PBYTE) VirtualAllocEx(hProcess, 0, size, MEM_COMMIT, PAGE_EXECUTE_READWRITE);
		if (!pCodeRemote)
			__leave;
		if (!WriteProcessMemory(hProcess, pCodeRemote, &InjectFunc, size, &dwNumBytesCopied) || dwNumBytesCopied != size)
			__leave;

		// Start execution of remote InjectFunc()
		hThread = CreateRemoteThread(hProcess, 
									 NULL, 
									 0, 
									 (LPTHREAD_START_ROUTINE) pCodeRemote,
									 pDataRemote, 
									 0 , 
									 &dwThreadId);
		if (!hThread)
			__leave;

		// Wait for InjectFunc() to terminate and get return code
		WaitForSingleObject(hThread, INFINITE);
		GetExitCodeThread(hThread, (PDWORD) &nSuccess);

		// InjectFunc() successfull
//		if (nSuccess)
//			MessageBeep(0);
	}

	__finally 
	{
		// Failed ?
		if (!nSuccess)
		{
			// Release memory for INJDATA and SASWindowProc()
			if (pDataRemote)
				VirtualFreeEx(hProcess, pDataRemote, 0, MEM_RELEASE);
			if (pSASWinProcRemote)
				VirtualFreeEx(hProcess, pSASWinProcRemote, 0, MEM_RELEASE);
			pDataRemote = NULL;
			pSASWinProcRemote = NULL;
		}

		// Release remote GetSASWnd()
		if (pGetSASWndRemote)	
			VirtualFreeEx(hProcess, pGetSASWndRemote, 0, MEM_RELEASE);

		// Release remote InjectFunc() (no longer needed)
		if (pCodeRemote)	
			VirtualFreeEx(hProcess, pCodeRemote, 0, MEM_RELEASE);

		if (hThread)			
			CloseHandle(hThread);

	}

	CloseHandle(hProcess);

	// Disable the DEBUG privilege
	EnablePrivilege(SE_DEBUG_NAME, FALSE);

	return nSuccess;	// 0=failure; 1=success
}


/**********************************************************************
 * Copies EjectFunc() to the remote process and starts its execution. *
 * The remote EjectFunc() restores the old window procedure.          *
 *                                                                    *
 *	Return value: 0=failure, 1=success                                *
 **********************************************************************/

int EjectCode ()
{
	HANDLE		hProcess;				// Remote process handle
	DWORD		*pCodeRemote;			// Address of EjectFunc() in the remote process
	HANDLE		hThread = NULL;			// The handle and ID of the thread executing
	DWORD		dwThreadId = 0;			//   the remote EjectFunc().
	int			nSuccess	= 0;		// EjectFunc() success ?
	DWORD		dwNumBytesCopied = 0;	// Number of bytes written to the remote process. 
	DWORD		size;					// Calculated function size (= AfterFunc() - Func())

	// Enable Debug privilege (needed for some processes)
	EnablePrivilege(SE_DEBUG_NAME, TRUE);

	// Remote INDATA and SASWindowProc() must exist 
	if (!pDataRemote || !pSASWinProcRemote)
		return 0;

	// Open the process
	hProcess = OpenProcess(PROCESS_ALL_ACCESS, FALSE, PID);
	if (hProcess == NULL)
		return 0;

	// Allocate memory in the remote process and write a copy of EjectFunc() to the allocated memory
	size = (PBYTE)AfterEjectFunc - (PBYTE)EjectFunc;
	pCodeRemote = (PDWORD) VirtualAllocEx(hProcess, 0, size, MEM_COMMIT, PAGE_EXECUTE_READWRITE);
	if (!pCodeRemote)
	{
		CloseHandle(hProcess);
		return 0;
	}
	if (!WriteProcessMemory(hProcess, pCodeRemote, &EjectFunc, size, &dwNumBytesCopied) || dwNumBytesCopied != size)
	{
		VirtualFreeEx(hProcess, pCodeRemote, 0, MEM_RELEASE);
		CloseHandle(hProcess);
		return 0;
	}

	// Start execution of the remote EjectFunc()
	hThread = CreateRemoteThread(hProcess, 
								 NULL, 
								 0, 
								 (LPTHREAD_START_ROUTINE) pCodeRemote,
								 pDataRemote, 
								 0 , 
								 &dwThreadId);
	// Failed
	if (!hThread)
	{
		goto END;
	}

	// Wait for EjectFunc() to terminate and get return code
	WaitForSingleObject(hThread, INFINITE);	
	GetExitCodeThread(hThread, (PDWORD) &nSuccess);	

	// Failed to restore old window procedure ?
	// Then leave INJDATA and the SASWindowProc()
	if (nSuccess == 0)		
		goto END;			
							
	// Release memory for remote INJDATA and SASWindowProc()
	if (pDataRemote)
		VirtualFreeEx(hProcess, pDataRemote, 0, MEM_RELEASE);
	if (pSASWinProcRemote)
		VirtualFreeEx(hProcess, pSASWinProcRemote, 0, MEM_RELEASE);
	pDataRemote = NULL;
	pSASWinProcRemote = NULL;

//	MessageBeep(0);		// success

END:		
	if (hThread)
		CloseHandle(hThread);

	// Release EjectFunc() memory
	if (pCodeRemote)
		VirtualFreeEx(hProcess, pCodeRemote, 0, MEM_RELEASE);

	CloseHandle(hProcess);

	// Disable the DEBUG privilege
	EnablePrivilege(SE_DEBUG_NAME, FALSE);

	return nSuccess;	// 0=failure; 1=success
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -