示例#1
0
        internal TDelegate CreateDelegateForSyscall <TDelegate>() where TDelegate : class
        {
            // Get the address of the function

            var functionAddress = _ntDllAddress + (int)_ntDllFunctions.Find(function => function.Name == typeof(TDelegate).Name.Replace("Definition", "")).Offset;

            // Copy the first 8 bytes of the function

            var functionBytes = new byte[8];

            Marshal.Copy(functionAddress, functionBytes, 0, 8);

            // Retrieve the syscall index from the bytes

            var syscallIndexBytes = Environment.Is64BitProcess ? functionBytes.Skip(4).Take(4) : functionBytes.Skip(1).Take(4);

            var syscallIndex = BitConverter.ToUInt32(syscallIndexBytes.ToArray(), 0);

            // Create the shellcode used to perform the syscall

            var shellcode = Environment.Is64BitProcess ? SyscallX64.GetShellcode(syscallIndex) : SyscallX86.GetShellcode(syscallIndex);

            // Store the shellcode in a buffer

            var shellcodeBuffer = MemoryTools.AllocateMemoryForBuffer(shellcode.Length);

            _shellcodeAddresses.Add(shellcodeBuffer);

            Marshal.Copy(shellcode, 0, shellcodeBuffer, shellcode.Length);

            // Create a delegate to perform the syscall

            return(Marshal.GetDelegateForFunctionPointer <TDelegate>(shellcodeBuffer));
        }
        // Since some items don't stack, it's possible to have several of the target item in your inventory. The state
        // of each one is tracked and returned when the split becomes relevant.
        public ItemState[] GetItemStates(int baseId, int category)
        {
            ItemId id = new ItemId(baseId, category);

            // It's assumed that an item ID will only be queried if it was present in the list of saved splits
            // (although it may not have been acquired yet).
            if (!tracker.TryGetValue(id, out List <IntPtr> list) || list.Count == 0)
            {
                return(new ItemState[0]);
            }

            ItemState[] states = new ItemState[list.Count];

            for (int i = 0; i < list.Count; i++)
            {
                IntPtr address = list[i];

                int rawId         = ComputeRawId(address);
                int count         = MemoryTools.ReadByte(Handle, address + countOffset);
                int mods          = 0;
                int reinforcement = 0;

                if (rawId / 10000 > 0)
                {
                    ComputeUpgrades(rawId, out mods, out reinforcement);
                }

                states[i] = new ItemState(mods, reinforcement, count);
            }

            return(states);
        }
        internal Enumerations.MemoryProtectionType Invoke(SafeProcessHandle processHandle, IntPtr baseAddress, int protectionSize, Enumerations.MemoryProtectionType newProtectionType)
        {
            // Store the base address of the memory region to protect in a buffer

            var baseAddressBuffer = MemoryTools.StoreStructureInBuffer(baseAddress);

            // Store the protection size in a buffer

            var protectionSizeBuffer = MemoryTools.StoreStructureInBuffer(protectionSize);

            // Initialise a buffer to store the returned old protection of the memory region

            var oldProtectionBuffer = MemoryTools.AllocateMemoryForBuffer(sizeof(ulong));

            // Perform the syscall

            var syscallResult = _ntProtectVirtualMemoryDelegate(processHandle, baseAddressBuffer, protectionSizeBuffer, newProtectionType, oldProtectionBuffer);

            if (syscallResult != Enumerations.NtStatus.Success)
            {
                ExceptionHandler.ThrowWin32Exception("Failed to protect memory in the target process", syscallResult);
            }

            // Marshal the returned old protection of the memory region from the buffer

            var oldProtection = (Enumerations.MemoryProtectionType)Marshal.PtrToStructure <ulong>(oldProtectionBuffer);

            MemoryTools.FreeMemoryForBuffer(baseAddressBuffer);

            MemoryTools.FreeMemoryForBuffer(protectionSizeBuffer);

            MemoryTools.FreeMemoryForBuffer(oldProtectionBuffer);

            return(oldProtection);
        }
示例#4
0
        public override void SetItems(List <ItemId> itemIds)
        {
            SetItems(itemIds, DefaultSlots, DefaultSlots);

            IntPtr address = Start + (DefaultSlots - 1) * Step;

            if (OpenSlots.Count == 0)
            {
                return;
            }

            // Since the item count above isn't accurate (just a default value large enough to reasonably accommodate
            // most scenarios), fake slots at the end of the list must be removed in order for the initial state to be
            // correct.
            for (int i = 0; i < DefaultSlots; i++)
            {
                int rawId = MemoryTools.ReadInt(Handle, address);

                address -= Step;

                if (rawId == -1)
                {
                    OpenSlots.RemoveLast();
                    TotalSlots--;
                }
                else
                {
                    break;
                }
            }
        }
示例#5
0
        internal IntPtr Invoke(SafeProcessHandle processHandle, int allocationSize, Enumerations.MemoryProtectionType protectionType)
        {
            // Initialise a buffer to store the returned address of the allocated memory region

            var memoryRegionAddressBuffer = MemoryTools.AllocateMemoryForBuffer(IntPtr.Size);

            // Store the size of the allocation in a buffer

            var allocationSizeBuffer = MemoryTools.StoreStructureInBuffer(allocationSize);

            // Perform the syscall

            const Enumerations.MemoryAllocationType allocationType = Enumerations.MemoryAllocationType.Commit | Enumerations.MemoryAllocationType.Reserve;

            var syscallResult = _ntAllocateVirtualMemoryDelegate(processHandle, memoryRegionAddressBuffer, 0, allocationSizeBuffer, allocationType, protectionType);

            if (syscallResult != Enumerations.NtStatus.Success)
            {
                ExceptionHandler.ThrowWin32Exception("Failed to allocate memory in the target process", syscallResult);
            }

            // Marshal the returned address of the memory region from the buffer

            var memoryRegionAddress = Marshal.PtrToStructure <IntPtr>(memoryRegionAddressBuffer);

            MemoryTools.FreeMemoryForBuffer(memoryRegionAddressBuffer);

            MemoryTools.FreeMemoryForBuffer(allocationSizeBuffer);

            return(memoryRegionAddress);
        }
示例#6
0
        internal SafeThreadHandle Invoke(SafeProcessHandle processHandle, IntPtr startAddress, IntPtr parameter)
        {
            // Initialise a buffer to store the returned thread handle

            var threadHandleBuffer = MemoryTools.AllocateMemoryForBuffer(IntPtr.Size);

            // Perform the syscall

            const Enumerations.ThreadAccessMask desiredAccess = Enumerations.ThreadAccessMask.SpecificRightsAll | Enumerations.ThreadAccessMask.StandardRightsAll;

            var syscallResult = _ntCreateThreadExDelegate(threadHandleBuffer, desiredAccess, IntPtr.Zero, processHandle, startAddress, parameter, Enumerations.ThreadCreationType.HideFromDebugger, IntPtr.Zero, IntPtr.Zero, IntPtr.Zero, IntPtr.Zero);

            if (syscallResult != Enumerations.NtStatus.Success)
            {
                ExceptionHandler.ThrowWin32Exception("Failed to create a thread in the target process", syscallResult);
            }

            // Marshal the returned thread handle from the buffer

            var threadHandle = new SafeThreadHandle(Marshal.PtrToStructure <IntPtr>(threadHandleBuffer), true);

            MemoryTools.FreeMemoryForBuffer(threadHandleBuffer);

            return(threadHandle);
        }
        public override void Refresh()
        {
            int newTotal = MemoryTools.ReadInt(Handle, itemCount);

            if (newTotal != totalItems)
            {
                if (newTotal > totalItems)
                {
                    // It's pretty common to acquire multiple items at once (such as an entire armor set).
                    int pickupCount = newTotal - totalItems;

                    AddItems(pickupCount);
                }
                // This means that items were lost (dropped, sold, etc.).
                else
                {
                    // I'm fairly certain that only one item can be removed from the inventory at one time (via drop or
                    // giving items to an NPC), but I'm not completely sure. A loop guarantees that the autosplitter's
                    // internal inventory state remains correct.
                    int dropCount = totalItems - newTotal;

                    RemoveItems(dropCount);
                }

                totalItems = newTotal;
            }
        }
示例#8
0
        internal PortableExecutableParser(byte[] dllBytes)
        {
            _dllBuffer = MemoryTools.StoreBytesInBuffer(dllBytes);

            _peHeaders = new PeHeaders();

            ReadHeaders();
        }
示例#9
0
        internal PortableExecutableParser(string dllPath)
        {
            _dllBuffer = MemoryTools.StoreBytesInBuffer(File.ReadAllBytes(dllPath));

            _peHeaders = new PeHeaders();

            ReadHeaders();
        }
示例#10
0
        public void Dispose()
        {
            foreach (var shellcodeAddress in _shellcodeAddresses)
            {
                // Free the memory allocated for the shellcode

                MemoryTools.FreeMemoryForBuffer(shellcodeAddress);
            }
        }
示例#11
0
        protected override int ComputeRawId(IntPtr address)
        {
            // Data is stored in the bottomless box a little differently than the main inventory. In the main
            // inventory, raw ID is stored as an integer (four bytes), with category as a single byte at a different
            // address. In contrast, the bottomless box stores both raw ID and category in a single integer, with three
            // bytes devoted to the ID and the fourth representing category.
            byte[] bytes = MemoryTools.ReadBytes(Handle, address, 4);

            return(TrimLastByte(bytes));
        }
示例#12
0
        internal TStructure ReadVirtualMemory <TStructure>(IntPtr baseAddress) where TStructure : struct
        {
            // Read the bytes of the structure from the memory region

            var structureBytes = ReadVirtualMemory(baseAddress, Marshal.SizeOf <TStructure>());

            // Marshal the bytes into a structure

            var structureBytesBuffer = MemoryTools.StoreBytesInBuffer(structureBytes);

            var structure = Marshal.PtrToStructure <TStructure>(structureBytesBuffer);

            MemoryTools.FreeMemoryForBuffer(structureBytesBuffer);

            return(structure);
        }
示例#13
0
        internal IntPtr Invoke(SafeProcessHandle processHandle, IntPtr baseAddress)
        {
            // Initialise a buffer to store the returned memory basic information structure in

            var memoryBasicInformationBuffer = MemoryTools.AllocateMemoryForBuffer(Marshal.SizeOf <Structures.MemoryBasicInformation>());

            // Perform the syscall

            var syscallResult = _ntQueryVirtualMemoryDelegate(processHandle, baseAddress, Enumerations.MemoryInformationClass.BasicInformation, memoryBasicInformationBuffer, (ulong)Marshal.SizeOf <Structures.MemoryBasicInformation>(), IntPtr.Zero);

            if (syscallResult != Enumerations.NtStatus.Success)
            {
                ExceptionHandler.ThrowWin32Exception("Failed to query memory in the target process", syscallResult);
            }

            return(memoryBasicInformationBuffer);
        }
示例#14
0
        internal IntPtr Invoke(SafeProcessHandle processHandle, IntPtr baseAddress, int bytesToRead)
        {
            // Initialise a buffer to store the returned bytes read

            var bytesReadBuffer = MemoryTools.AllocateMemoryForBuffer(bytesToRead);

            // Perform the syscall

            var syscallResult = _ntReadVirtualMemoryDelegate(processHandle, baseAddress, bytesReadBuffer, (ulong)bytesToRead, IntPtr.Zero);

            if (syscallResult != Enumerations.NtStatus.Success)
            {
                ExceptionHandler.ThrowWin32Exception("Failed to read memory from the target process", syscallResult);
            }

            return(bytesReadBuffer);
        }
示例#15
0
        internal void WriteVirtualMemory <TStructure>(IntPtr baseAddress, TStructure structureToWrite) where TStructure : struct
        {
            // Store the structure in a buffer

            var structureBuffer = MemoryTools.StoreStructureInBuffer(structureToWrite);

            // Convert the structure into bytes

            var structureSize = Marshal.SizeOf <TStructure>();

            var structureBytes = new byte[structureSize];

            Marshal.Copy(structureBuffer, structureBytes, 0, structureSize);

            // Write the bytes of the structure into the target process

            WriteVirtualMemory(baseAddress, structureBytes);
        }
示例#16
0
        internal IntPtr Invoke(SafeProcessHandle processHandle, Enumerations.ProcessInformationClass processInformationClass)
        {
            // Initialise a buffer to store the returned process information structure

            var bufferSize = processInformationClass == Enumerations.ProcessInformationClass.BasicInformation ? Marshal.SizeOf <Structures.ProcessBasicInformation>() : sizeof(ulong);

            var processInformationBuffer = MemoryTools.AllocateMemoryForBuffer(bufferSize);

            // Perform the syscall

            var syscallResult = _ntQueryInformationProcessDelegate(processHandle, processInformationClass, processInformationBuffer, (ulong)bufferSize, IntPtr.Zero);

            if (syscallResult != Enumerations.NtStatus.Success)
            {
                ExceptionHandler.ThrowWin32Exception("Failed to query the information of the target process", syscallResult);
            }

            return(processInformationBuffer);
        }
示例#17
0
        internal bool Call()
        {
            var localDllBaseAddress = MemoryTools.StoreBytesInBuffer(_propertyWrapper.DllBytes);

            var peHeaders = _propertyWrapper.PeParser.GetHeaders();

            // Build the import table of the DLL in the local process

            BuildImportTable(localDllBaseAddress);

            // Allocate memory for the DLL in the target process

            var dllSize = _propertyWrapper.TargetProcess.IsWow64 ? peHeaders.NtHeaders32.OptionalHeader.SizeOfImage : peHeaders.NtHeaders64.OptionalHeader.SizeOfImage;

            var remoteDllAddress = _propertyWrapper.MemoryManager.AllocateVirtualMemory((int)dllSize, Enumerations.MemoryProtectionType.ExecuteReadWrite);

            // Perform the needed relocations in the local process

            PerformRelocations(localDllBaseAddress, remoteDllAddress);

            // Map the sections of the DLL into the target process

            MapSections(localDllBaseAddress, remoteDllAddress);

            // Call any TLS callbacks

            CallTlsCallbacks(remoteDllAddress);

            // Call the entry point of the DLL

            var dllEntryPointAddress = _propertyWrapper.TargetProcess.IsWow64
                                     ? (uint)remoteDllAddress + peHeaders.NtHeaders32.OptionalHeader.AddressOfEntryPoint
                                     : (ulong)remoteDllAddress + peHeaders.NtHeaders64.OptionalHeader.AddressOfEntryPoint;

            if (dllEntryPointAddress != 0)
            {
                CallEntryPoint(remoteDllAddress, (IntPtr)dllEntryPointAddress);
            }

            MemoryTools.FreeMemoryForBuffer(localDllBaseAddress);

            return(true);
        }
示例#18
0
        public override void Refresh()
        {
            IntPtr nextSlot = Start + (OpenSlots.Count > 0 ? OpenSlots.First.Value : TotalSlots) * Step;

            int value = MemoryTools.ReadInt(Handle, nextSlot);

            // Unlike the main inventory, there's no memory location that directly stores the number of items in the
            // bottomless box (or at least I wasn't able to find one). As such, item addition/removal must be detected
            // by checking slots directly. Also note that only one item can be put into the bottomless box at a time
            // (as opposed to picking up multiple items at once off the ground).
            if (value != -1)
            {
                AddItems(1);

                return;
            }

            LinkedListNode <int> slot = OpenSlots.First;

            // Since the bottomless box can't track count directly, all non-empty slots must be scanned each tick in
            // order to detect when one of them becomes empty.
            for (int i = 0; i < TotalSlots; i++)
            {
                if (slot != null && i == slot.Value)
                {
                    slot = slot.Next;

                    continue;
                }

                IntPtr address = Start + i * Step;

                value = MemoryTools.ReadInt(Handle, address);

                if (value == -1)
                {
                    RemoveItems(1, address);

                    return;
                }
            }
        }
示例#19
0
        internal List <Structures.LdrDataTableEntry32> GetWow64PebEntries()
        {
            var pebEntries = new List <Structures.LdrDataTableEntry32>();

            // Query the target process for the base address of the WOW64 PEB

            var pebBaseAddressBuffer = (IntPtr)_syscallManager.InvokeSyscall <NtQueryInformationProcess>(Handle, Enumerations.ProcessInformationClass.Wow64Information);

            var pebBaseAddress = Marshal.PtrToStructure <ulong>(pebBaseAddressBuffer);

            // Read the WOW64 PEB of the target process

            var peb = _memoryManager.ReadVirtualMemory <Structures.Peb32>((IntPtr)pebBaseAddress);

            // Read the loader data of the WOW64 PEB

            var pebLoaderData = _memoryManager.ReadVirtualMemory <Structures.PebLdrData32>((IntPtr)peb.Ldr);

            var currentPebEntry = pebLoaderData.InLoadOrderModuleList.Flink;

            while (true)
            {
                if (currentPebEntry == pebLoaderData.InLoadOrderModuleList.Blink)
                {
                    break;
                }

                // Read the current entry from the InLoadOrder doubly linked list

                var pebEntry = _memoryManager.ReadVirtualMemory <Structures.LdrDataTableEntry32>((IntPtr)currentPebEntry);

                pebEntries.Add(pebEntry);

                // Get the address of the next entry in the InLoadOrder doubly linked list

                currentPebEntry = pebEntry.InLoadOrderLinks.Flink;
            }

            MemoryTools.FreeMemoryForBuffer(pebBaseAddressBuffer);

            return(pebEntries);
        }
示例#20
0
        internal void WriteVirtualMemory(IntPtr baseAddress, byte[] bytesToWrite)
        {
            // Store the bytes to write in a buffer

            var bytesBuffer = MemoryTools.StoreBytesInBuffer(bytesToWrite);

            // Adjust the protection of the memory region to ensure it has write privileges

            var oldProtectionType = ProtectVirtualMemory(baseAddress, bytesToWrite.Length, Enumerations.MemoryProtectionType.ReadWrite);

            // Write the bytes into the memory region

            _syscallManager.InvokeSyscall <NtWriteVirtualMemory>(_processHandle, baseAddress, bytesBuffer, bytesToWrite.Length);

            // Restore the protection of the memory region

            ProtectVirtualMemory(baseAddress, bytesToWrite.Length, oldProtectionType);

            MemoryTools.FreeMemoryForBuffer(bytesBuffer);
        }
示例#21
0
        protected override ItemId ComputeItemId(IntPtr address)
        {
            // Data is stored in the bottomless box a little differently than the main inventory. In the main
            // inventory, raw ID is stored as an integer (four bytes), with category as a single byte at a different
            // address. In contrast, the bottomless box stores both raw ID and category in a single integer, with three
            // bytes devoted to the ID and the fourth representing category.
            byte[] bytes = MemoryTools.ReadBytes(Handle, address, 4);

            int category = bytes[3];

            // This means that the slot is empty.
            if (category == byte.MaxValue)
            {
                return(null);
            }

            int rawId = TrimLastByte(bytes);

            return(ComputeItemId(rawId, Utilities.ToHex(category)));
        }
示例#22
0
        internal IntPtr Invoke(SafeThreadHandle threadHandle)
        {
            // Store a context structure in a buffer

            var context = new Structures.Context {
                ContextFlags = Enumerations.ContextFlags.Control
            };

            var contextBuffer = MemoryTools.StoreStructureInBuffer(context);

            // Perform the syscall

            var syscallResult = _ntGetContextThreadDelegate(threadHandle, contextBuffer);

            if (syscallResult != Enumerations.NtStatus.Success)
            {
                ExceptionHandler.ThrowWin32Exception("Failed to get the context of a thread in the target process", syscallResult);
            }

            return(contextBuffer);
        }
示例#23
0
        internal SafeProcessHandle Invoke(int processId)
        {
            // Initialise a buffer to store the returned process handle

            var processHandleBuffer = MemoryTools.AllocateMemoryForBuffer(IntPtr.Size);

            // Store an empty object attributes structure in a buffer

            var objectAttributesBuffer = MemoryTools.StoreStructureInBuffer(new Structures.ObjectAttributes());

            // Store a client id structure in a buffer

            var clientId = new Structures.ClientId {
                UniqueProcess = new IntPtr(processId), UniqueThread = IntPtr.Zero
            };

            var clientIdBuffer = MemoryTools.StoreStructureInBuffer(clientId);

            // Perform the syscall

            var syscallResult = _ntOpenProcessDelegate(processHandleBuffer, Enumerations.ProcessAccessMask.AllAccess, objectAttributesBuffer, clientIdBuffer);

            if (syscallResult != Enumerations.NtStatus.Success)
            {
                ExceptionHandler.ThrowWin32Exception("Failed to open a handle to the target process", syscallResult);
            }

            // Marshal the returned process handle from the buffer

            var processHandle = new SafeProcessHandle(Marshal.PtrToStructure <IntPtr>(processHandleBuffer), true);

            MemoryTools.FreeMemoryForBuffer(processHandleBuffer);

            MemoryTools.FreeMemoryForBuffer(objectAttributesBuffer);

            MemoryTools.FreeMemoryForBuffer(clientIdBuffer);

            return(processHandle);
        }
示例#24
0
        internal byte[] ReadVirtualMemory(IntPtr baseAddress, int bytesToRead)
        {
            // Adjust the protection of the memory region to ensure it has read privileges

            var oldProtectionType = ProtectVirtualMemory(baseAddress, bytesToRead, Enumerations.MemoryProtectionType.ReadWrite);

            // Read the specified number of bytes from the memory region

            var bytesReadBuffer = (IntPtr)_syscallManager.InvokeSyscall <NtReadVirtualMemory>(_processHandle, baseAddress, bytesToRead);

            var bytesRead = new byte[bytesToRead];

            Marshal.Copy(bytesReadBuffer, bytesRead, 0, bytesToRead);

            // Restore the protection of the memory region

            ProtectVirtualMemory(baseAddress, bytesToRead, oldProtectionType);

            MemoryTools.FreeMemoryForBuffer(bytesReadBuffer);

            return(bytesRead);
        }
示例#25
0
        internal void Invoke(SafeProcessHandle processHandle, IntPtr baseAddress)
        {
            // Store the base address of memory region to free in a buffer

            var baseAddressBuffer = MemoryTools.StoreStructureInBuffer(baseAddress);

            // Store the free size in a buffer

            var freeSizeBuffer = MemoryTools.StoreStructureInBuffer(0);

            // Perform the syscall

            var syscallResult = _ntFreeVirtualMemoryDelegate(processHandle, baseAddressBuffer, freeSizeBuffer, Enumerations.MemoryFreeType.Release);

            if (syscallResult != Enumerations.NtStatus.Success)
            {
                ExceptionHandler.ThrowWin32Exception("Failed to free memory in the target process", syscallResult);
            }

            MemoryTools.FreeMemoryForBuffer(baseAddressBuffer);

            MemoryTools.FreeMemoryForBuffer(freeSizeBuffer);
        }
示例#26
0
 public void Dispose()
 {
     MemoryTools.FreeMemoryForBuffer(_dllBuffer);
 }
示例#27
0
        internal bool Call()
        {
            // Get the address of the LoadLibraryW function

            var loadLibraryAddress = _propertyWrapper.TargetProcess.GetFunctionAddress("kernel32.dll", "LoadLibraryW");

            // Write the DLL path into the target process

            var dllPathBuffer = _propertyWrapper.MemoryManager.AllocateVirtualMemory(_propertyWrapper.DllPath.Length, Enumerations.MemoryProtectionType.ExecuteReadWrite);

            var dllPathBytes = Encoding.Unicode.GetBytes(_propertyWrapper.DllPath + "\0");

            _propertyWrapper.MemoryManager.WriteVirtualMemory(dllPathBuffer, dllPathBytes);

            // Open a handle to the first thread in the target process

            var threadHandle = (SafeThreadHandle)_propertyWrapper.SyscallManager.InvokeSyscall <NtOpenThread>(_propertyWrapper.TargetProcess.Process.Threads[0].Id);

            if (_propertyWrapper.TargetProcess.IsWow64)
            {
                // Suspend the thread

                if (PInvoke.Wow64SuspendThread(threadHandle) == -1)
                {
                    ExceptionHandler.ThrowWin32Exception("Failed to suspend a thread in the target process");
                }

                // Get the context of the thread

                var threadContextBuffer = MemoryTools.StoreStructureInBuffer(new Structures.Wow64Context {
                    ContextFlags = Enumerations.ContextFlags.Control
                });

                if (PInvoke.Wow64GetThreadContext(threadHandle, threadContextBuffer) == 0)
                {
                    ExceptionHandler.ThrowWin32Exception("Failed to get the context of a thread in the target process");
                }

                var threadContext = Marshal.PtrToStructure <Structures.Wow64Context>(threadContextBuffer);

                // Write the shellcode used to call LoadLibraryW from the thread into the target process

                var shellcode = ThreadHijackX86.GetShellcode((IntPtr)threadContext.Eip, dllPathBuffer, loadLibraryAddress);

                var shellcodeBuffer = _propertyWrapper.MemoryManager.AllocateVirtualMemory(shellcode.Length, Enumerations.MemoryProtectionType.ExecuteReadWrite);

                _propertyWrapper.MemoryManager.WriteVirtualMemory(shellcodeBuffer, shellcode);

                // Overwrite the instruction pointer of the thread with the shellcode buffer

                threadContext.Eip = (uint)shellcodeBuffer;

                // Set the context of the thread

                threadContextBuffer = MemoryTools.StoreStructureInBuffer(threadContext);

                if (PInvoke.Wow64SetThreadContext(threadHandle, threadContextBuffer) == 0)
                {
                    ExceptionHandler.ThrowWin32Exception("Failed to set the context of a thread in the target process");
                }

                MemoryTools.FreeMemoryForBuffer(threadContextBuffer);
            }

            else
            {
                // Suspend the thread

                _propertyWrapper.SyscallManager.InvokeSyscall <NtSuspendThread>(threadHandle);

                // Get the context of the thread

                var threadContextBuffer = (IntPtr)_propertyWrapper.SyscallManager.InvokeSyscall <NtGetContextThread>(threadHandle);

                var threadContext = Marshal.PtrToStructure <Structures.Context>(threadContextBuffer);

                // Write the shellcode used to call LoadLibraryW from the thread into the target process

                var shellcode = ThreadHijackX64.GetShellcode((IntPtr)threadContext.Rip, dllPathBuffer, loadLibraryAddress);

                var shellcodeBuffer = _propertyWrapper.MemoryManager.AllocateVirtualMemory(shellcode.Length, Enumerations.MemoryProtectionType.ExecuteReadWrite);

                _propertyWrapper.MemoryManager.WriteVirtualMemory(shellcodeBuffer, shellcode);

                // Overwrite the instruction pointer of the thread with the shellcode buffer

                threadContext.Rip = (ulong)shellcodeBuffer;

                // Set the context of the thread

                threadContextBuffer = MemoryTools.StoreStructureInBuffer(threadContext);

                _propertyWrapper.SyscallManager.InvokeSyscall <NtSetThreadContext>(threadHandle, threadContextBuffer);

                MemoryTools.FreeMemoryForBuffer(threadContextBuffer);
            }

            // Resume the thread

            _propertyWrapper.SyscallManager.InvokeSyscall <NtResumeThread>(threadHandle);

            PInvoke.SwitchToThisWindow(_propertyWrapper.TargetProcess.Process.MainWindowHandle, true);

            threadHandle.Dispose();

            return(true);
        }
示例#28
0
        private int GetCategory(IntPtr address)
        {
            int value = MemoryTools.ReadByte(Handle, address - 0x1);

            return(Utilities.ToHex(value));
        }
示例#29
0
 protected override int ComputeRawId(IntPtr address)
 {
     return(MemoryTools.ReadInt(Handle, address));
 }
示例#30
0
        public override void SetItems(List <ItemId> itemIds)
        {
            totalItems = MemoryTools.ReadInt(Handle, itemCount);

            SetItems(itemIds, totalItems);
        }