Example #1
0
        private void CreateSyscall <TSyscall>() where TSyscall : class
        {
            // Get the address of the function to syscall

            var functionAddress = PInvoke.GetProcAddress(_ntDllAddress, typeof(TSyscall).Name.Replace("Definition", ""));

            // 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);

            // Write the shellcode used to perform the syscall into the local process

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

            var shellcodeBuffer = LocalMemoryTools.StoreBytesInBuffer(shellcode);

            // Create an instance of the syscall class

            var syscallInstance = Activator.CreateInstance(typeof(TSyscall), BindingFlags.Instance | BindingFlags.NonPublic, null, new object[] { shellcodeBuffer }, null);

            // Get the parameter and return types of the syscall method

            var methodInformation = typeof(TSyscall).GetMethod("Invoke", BindingFlags.Instance | BindingFlags.NonPublic);

            var methodTypes = new List <Type>(methodInformation.GetParameters().Select(parameter => parameter.ParameterType))
            {
                methodInformation.ReturnType
            };

            // Create the delegate type to represent the syscall method

            Type delegateType;

            if (methodTypes.Last() == typeof(void))
            {
                methodTypes.RemoveAt(methodTypes.Count - 1);

                delegateType = Expression.GetActionType(methodTypes.ToArray());
            }

            else
            {
                delegateType = Expression.GetFuncType(methodTypes.ToArray());
            }

            // Create a delegate for the syscall method

            var syscallDelegate = Delegate.CreateDelegate(delegateType, syscallInstance, "Invoke");

            _syscallCache.Add(typeof(TSyscall).Name, new SyscallInstance(syscallDelegate, shellcodeBuffer));
        }
Example #2
0
        internal PeParser(byte[] dllBytes)
        {
            _dllBuffer = LocalMemoryTools.StoreBytesInBuffer(dllBytes);

            _peHeaders = new PeHeaders();

            ReadPeHeaders();
        }
Example #3
0
        internal PeParser(string dllPath)
        {
            _dllBuffer = LocalMemoryTools.StoreBytesInBuffer(File.ReadAllBytes(dllPath));

            _peHeaders = new PeHeaders();

            ReadPeHeaders();
        }
Example #4
0
        public bool Call(InjectionProperties injectionProperties)
        {
            var localDllAddress = injectionProperties.DllPath is null
                                ? LocalMemoryTools.StoreBytesInBuffer(injectionProperties.DllBytes)
                                : LocalMemoryTools.StoreBytesInBuffer(File.ReadAllBytes(injectionProperties.DllPath));

            // Build the import table of the DLL

            BuildImportTable(injectionProperties, localDllAddress);

            var peHeaders = injectionProperties.PeParser.GetHeaders();

            // Allocate memory for the DLL in the target process

            var allocationBaseAddress = injectionProperties.RemoteProcess.IsWow64
                                      ? peHeaders.NtHeaders32.OptionalHeader.ImageBase
                                      : peHeaders.NtHeaders64.OptionalHeader.ImageBase;

            var dllSize = injectionProperties.RemoteProcess.IsWow64
                        ? peHeaders.NtHeaders32.OptionalHeader.SizeOfImage
                        : peHeaders.NtHeaders64.OptionalHeader.SizeOfImage;

            IntPtr remoteDllAddress;

            try
            {
                remoteDllAddress = injectionProperties.MemoryManager.AllocateVirtualMemory((IntPtr)allocationBaseAddress, (int)dllSize, Enumerations.MemoryProtectionType.ExecuteReadWrite);
            }

            catch (Win32Exception)
            {
                remoteDllAddress = injectionProperties.MemoryManager.AllocateVirtualMemory(IntPtr.Zero, (int)dllSize, Enumerations.MemoryProtectionType.ExecuteReadWrite);
            }

            // Perform any needed relocations

            PerformRelocations(injectionProperties, localDllAddress, remoteDllAddress);

            // Map the sections of the DLL

            MapSections(injectionProperties, localDllAddress, remoteDllAddress);

            // Map randomised PE headers

            MapHeaders(injectionProperties, remoteDllAddress);

            // Call any TLS callbacks

            CallTlsCallbacks(injectionProperties, remoteDllAddress);

            // Call the entry point of the DLL

            var dllEntryPointAddress = injectionProperties.RemoteProcess.IsWow64
                                     ? remoteDllAddress.AddOffset(peHeaders.NtHeaders32.OptionalHeader.AddressOfEntryPoint)
                                     : remoteDllAddress.AddOffset(peHeaders.NtHeaders64.OptionalHeader.AddressOfEntryPoint);

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

            LocalMemoryTools.FreeMemoryForBuffer(localDllAddress);

            return(true);
        }