Esempio n. 1
0
        /// <summary>
        /// Get proc address from target process memory.
        /// This method can get address from 32bit and 64bit process if current process is 64bit.
        /// </summary>
        /// <param name="process"></param>
        /// <param name="dllName"></param>
        /// <param name="procName"></param>
        /// <returns></returns>
        public static IntPtr GetProcAddressFromProcessMemory(IntPtr process, string dllName, string procName)
        {
            uint needed;

            if (!NativeFunctions.EnumProcessModulesEx(process, null, 0, out needed, NativeFunctions.Consts.LIST_MODULES_ALL))
            {
                return(IntPtr.Zero);
            }

            var buffer = new byte[needed];

            if (!NativeFunctions.EnumProcessModulesEx(process, buffer, (uint)buffer.Length, out needed, NativeFunctions.Consts.LIST_MODULES_ALL))
            {
                return(IntPtr.Zero);
            }

            if (!dllName.Contains('.'))
            {
                dllName += ".dll";
            }

            var dllNameWithoutExtension = Path.GetFileNameWithoutExtension(dllName).ToLower();

            var nameBuffer = new byte[(dllName.Length + 1) * 2];

            for (var i = 0; i < buffer.Length; i += IntPtr.Size)
            {
                IntPtr module;
                if (IntPtr.Size == 4)
                {
                    module = new IntPtr(BitConverter.ToInt32(buffer, i));
                }
                else
                {
                    module = new IntPtr(BitConverter.ToInt64(buffer, i));
                }

                var len        = NativeFunctions.GetModuleBaseName(process, module, nameBuffer, (uint)(nameBuffer.Length / 2));
                var moduleName = Encoding.Unicode.GetString(nameBuffer, 0, (int)(len * 2));
                if (dllNameWithoutExtension != Path.GetFileNameWithoutExtension(moduleName).ToLower())
                {
                    continue;
                }

                NativeStructs.MODULEINFO moduleInfo;
                if (!NativeFunctions.GetModuleInformation(process, module, out moduleInfo, (uint)Marshal.SizeOf <NativeStructs.MODULEINFO>()))
                {
                    return(IntPtr.Zero);
                }

                using var pm = new ProcessMemoryMapper(process, moduleInfo.lpBaseOfDll, (int)moduleInfo.SizeOfImage);
                return(GetProcAddressFromProcessMemory(pm, procName.ToLower()));
            }

            return(IntPtr.Zero);
        }
Esempio n. 2
0
        private static IntPtr GetProcAddressFromProcessMemory(ProcessMemoryMapper processMemory, string procName)
        {
            var peBuffer = new byte[0x1000];

            if (!processMemory.Read(0, peBuffer, 0, peBuffer.Length))
            {
                return(IntPtr.Zero);
            }

            try
            {
                var pe = new PEImage(peBuffer);

                var exportTableRVA = pe.ImageNTHeaders.OptionalHeader.DataDirectories[0].VirtualAddress;
                if (!processMemory.Read((int)(exportTableRVA + 20), peBuffer, 0, 20))
                {
                    return(IntPtr.Zero);
                }

                var numberOfFunctions   = BitConverter.ToInt32(peBuffer, 0);
                var numberOfNames       = BitConverter.ToInt32(peBuffer, 4);
                var funcTableRVA        = BitConverter.ToInt32(peBuffer, 8);
                var nameTableRVA        = BitConverter.ToInt32(peBuffer, 12);
                var nameOrdinalTableRVA = BitConverter.ToInt32(peBuffer, 16);

                for (var i = 0; i < numberOfNames; i++)
                {
                    int nameRVA;
                    if (!processMemory.TryRead(nameTableRVA + i * 4, out nameRVA))
                    {
                        return(IntPtr.Zero);
                    }

                    string name;
                    if (!processMemory.TryReadCStrA(nameRVA, out name))
                    {
                        return(IntPtr.Zero);
                    }

                    if (name.ToLower() != procName)
                    {
                        continue;
                    }

                    short nameOrdinal;
                    if (!processMemory.TryRead(nameOrdinalTableRVA + i * 2, out nameOrdinal))
                    {
                        return(IntPtr.Zero);
                    }

                    if (nameOrdinal < 0 || nameOrdinal >= numberOfFunctions)
                    {
                        return(IntPtr.Zero);
                    }

                    int funcRVA;
                    if (!processMemory.TryRead(funcTableRVA + nameOrdinal * 4, out funcRVA))
                    {
                        return(IntPtr.Zero);
                    }

                    return(processMemory.BaseAddress + funcRVA);
                }
            }
            catch
            {
            }

            return(IntPtr.Zero);
        }