Changeset 3179 for trunk/src/kmk/kmkbuiltin
- Timestamp:
- Mar 22, 2018, 8:50:04 PM (7 years ago)
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/kmk/kmkbuiltin/redirect.c
r3173 r3179 40 40 # include <process.h> 41 41 #endif 42 #if defined(KBUILD_OS_WINDOWS) || defined(KBUILD_OS_OS2)42 #ifdef KBUILD_OS_WINDOWS 43 43 # include <Windows.h> 44 # include <Winternl.h>45 44 #endif 46 45 #if defined(_MSC_VER) … … 67 66 #include "err.h" 68 67 #include "kbuild_version.h" 68 #ifdef KBUILD_OS_WINDOWS 69 # include "nt/nt_child_inject_standard_handles.h" 70 #endif 69 71 #if defined(__gnu_hurd__) && !defined(kmk_builtin_redirect) /* need constant */ 70 72 # undef GET_PATH_MAX … … 791 793 } 792 794 795 793 796 /** 794 797 * Alternative approach on windows that use CreateProcess and doesn't require … … 805 808 * @param phProcess Where to return process handle. 806 809 */ 807 static kRedirectCreateProcessWindows(const char *pszExecutable, int cArgs, char **papszArgs, char **papszEnvVars,808 const char *pszCwd, unsigned cOrders, REDIRECTORDERS *paOrders, HANDLE *phProcess)810 static int kRedirectCreateProcessWindows(const char *pszExecutable, int cArgs, char **papszArgs, char **papszEnvVars, 811 const char *pszCwd, unsigned cOrders, REDIRECTORDERS *paOrders, HANDLE *phProcess) 809 812 { 810 static NTSTATUS (NTAPI *s_pfnNtQueryInformationProcess)(HANDLE, PROCESSINFOCLASS, PVOID, ULONG, PULONG) = NULL;811 813 size_t cbArgs; 812 814 char *pszCmdLine; … … 816 818 int i; 817 819 int rc; 818 819 /*820 * Determin host bitness and APIs while we can still easily return.821 */822 #if K_ARCH_BITS == 32823 BOOL f64BitHost = TRUE;824 if (!IsWow64Process(GetCurrentProcess(), &f64BitHost))825 return errx(9, "IsWow64Process failed: %u", GetLastError());826 #elif K_ARCH_BITS == 64827 BOOL const f64BitHost = TRUE;828 #else829 # error "K_ARCH_BITS is bad/missing"830 #endif831 if (cOrders > 0 && !s_pfnNtQueryInformationProcess)832 {833 *(FARPROC *)&s_pfnNtQueryInformationProcess = GetProcAddress(GetModuleHandleA("NTDLL.DLL"), "NtQueryInformationProcess");834 if (!s_pfnNtQueryInformationProcess)835 return errx(9, "NtQueryInformationProcess not found!");836 }837 820 838 821 /* … … 962 945 FALSE /*fInheritHandles*/, CREATE_SUSPENDED, pszzEnv, pszCwd, &StartupInfo, &ProcInfo)) 963 946 { 964 /* 965 * Figure out where we need to write the handles. 966 */ 967 ULONG cbActual1 = 0; 968 PROCESS_BASIC_INFORMATION BasicInfo = { 0, 0, }; 969 NTSTATUS rcNt = s_pfnNtQueryInformationProcess(ProcInfo.hProcess, ProcessBasicInformation, 970 &BasicInfo, sizeof(BasicInfo), &cbActual1); 971 if (NT_SUCCESS(rcNt)) 972 { 973 BOOL const f32BitPeb = !f64BitHost; 974 ULONG const cbChildPtr = f32BitPeb ? 4 : 8; 975 PVOID pvSrcInPeb = (char *)BasicInfo.PebBaseAddress + (f32BitPeb ? 0x10 : 0x20); 976 char * pbDst = 0; 977 SIZE_T cbActual2 = 0; 978 if (ReadProcessMemory(ProcInfo.hProcess, pvSrcInPeb, &pbDst, cbChildPtr, &cbActual2)) 979 { 980 union 981 { 982 KU32 au32[3]; 983 KU64 au64[3]; 984 } uBuf; 985 memset(&uBuf, 0, sizeof(uBuf)); 986 pbDst += f32BitPeb ? 0x18 : 0x20; 987 if ( (afReplace[0] && afReplace[1] && afReplace[2]) 988 || ReadProcessMemory(ProcInfo.hProcess, pbDst, &uBuf, cbChildPtr * 3, &cbActual2)) 989 { 990 for (i = 0; i < 3; i++) 991 if (afReplace[i]) 992 { 993 HANDLE hInChild = INVALID_HANDLE_VALUE; 994 if ( ahChild[i] == NULL /* just closed*/ 995 || DuplicateHandle(GetCurrentProcess(), ahChild[i], ProcInfo.hProcess, &hInChild, 996 0, TRUE /*fInheriable*/, DUPLICATE_SAME_ACCESS)) 997 { 998 if (f32BitPeb) 999 uBuf.au32[i] = (KU32)(uintptr_t)hInChild; 1000 else 1001 uBuf.au64[i] = (uintptr_t)hInChild; 1002 } 1003 else 1004 rc = errx(10, "Error duplicating %p into the child: %u", ahChild[i], GetLastError()); 1005 } 1006 if ( rc == 0 1007 && !WriteProcessMemory(ProcInfo.hProcess, pbDst, &uBuf, cbChildPtr * 3, &cbActual2)) 1008 rc = errx(10, "Error writing standard handles at %p LB %u in the child: %u", 1009 pbDst, cbChildPtr * 3, GetLastError()); 1010 } 1011 else 1012 rc = errx(10, "Error reading %p LB %u from the child: %u", 1013 pbDst, cbChildPtr * 3, GetLastError()); 1014 } 1015 else 1016 rc = errx(10, "Error reading %p LB %u from the child: %u", pvSrcInPeb, cbChildPtr); 1017 } 1018 else 1019 rc = errx(10, "NtQueryInformationProcess failed: %#x", rcNt); 1020 1021 /* Resume the bugger... */ 1022 if ( rc == 0 1023 && !ResumeThread(ProcInfo.hThread)) 947 /* Inject the handles and try make it start executing. */ 948 char szErrMsg[128]; 949 rc = nt_child_inject_standard_handles(ProcInfo.hProcess, afReplace, ahChild, szErrMsg, sizeof(szErrMsg)); 950 if (rc) 951 rc = errx(10, "%s", szErrMsg); 952 else if (!ResumeThread(ProcInfo.hThread)) 1024 953 rc = errx(10, "ResumeThread failed: %u", GetLastError()); 1025 954 1026 /* .. or kill it. */955 /* Kill it if any of that fails. */ 1027 956 if (rc != 0) 1028 957 TerminateProcess(ProcInfo.hProcess, rc);
Note:
See TracChangeset
for help on using the changeset viewer.