[求助]MemoryLoadLibrary 加载MFC 易语言 DLL 失败

2011-10-6 13:32

13431

[求助]MemoryLoadLibrary 加载MFC 易语言 DLL 失败

2011-10-6 13:32

13431

接着昨天发的求助 DLL补丁,网上找了一份代码, Memory DLL loading code

模拟LoadLibrary ,经过调用发现对win32 DLL有效,但是加载MFC DLL

发现 停止在 调用 DLLMAIN 处,易语言直接 报错,我把代码发下,大家帮忙

分析下。

可以直接在MFC 程序上用,UNICODE,此代码是最新的支持64位

//"MemoryModule.h"

#ifndef __MEMORY_MODULE_HEADER

#define __MEMORY_MODULE_HEADER

#include

typedef void *HMEMORYMODULE;

#ifdef __cplusplus

extern "C" {

#endif

HMEMORYMODULE MemoryLoadLibrary(const void *);

FARPROC MemoryGetProcAddress(HMEMORYMODULE, const char *);

void MemoryFreeLibrary(HMEMORYMODULE);

#ifdef __cplusplus

}

#endif

#endif  // __MEMORY_MODULE_HEADER

//"MemoryModule.cpp"

/*@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@

【】【】【】【】【】【】【】【】【】【】【】【】【】【】【】【】【】【】【】【】【】

@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@

**  FileName    :   MemoryModule.cpp

**  Version     :   0.10

**  Author      :   joachim

**  Date        :   2011-03-22

**  Comment     :   加载模块,下载地址:http://www.joachim-bauch.de

@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@

【】【】【】【】【】【】【】【】【】【】【】【】【】【】【】【】【】【】【】【】【】

@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@*/

#include "stdafx.h"

#include

#include

#include "Print.h"

#include "MemoryModule.h"

#ifndef __GNUC__

// disable warnings about pointer DWORD conversions

#pragma warning( disable : 4311 4312 )

#endif

#ifdef _WIN64

#define POINTER_TYPE ULONGLONG

#else

#define POINTER_TYPE DWORD

#endif

#ifdef DEBUG_OUTPUT

#include

#endif

#ifndef IMAGE_SIZEOF_BASE_RELOCATION

#define IMAGE_SIZEOF_BASE_RELOCATION (sizeof(IMAGE_BASE_RELOCATION))

#endif

typedef struct

{

PIMAGE_NT_HEADERS headers;

unsigned char *codeBase;

HMODULE *modules;

int numModules;

int initialized;

} MEMORYMODULE, *PMEMORYMODULE;

typedef BOOL (WINAPI *DllEntryProc)(HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpReserved);

#define GET_HEADER_DICTIONARY(module, idx)        &(module)->headers->OptionalHeader.DataDirectory[idx]

static void CopySections(const unsigned char *data, PIMAGE_NT_HEADERS old_headers, PMEMORYMODULE module)

{

int i, size;

unsigned char *codeBase = module->codeBase;

unsigned char *dest;

PIMAGE_SECTION_HEADER section = IMAGE_FIRST_SECTION(module->headers);

for (i=0; iheaders->FileHeader.NumberOfSections; i++, section++)

{

if (section->SizeOfRawData == 0)

{

size = old_headers->OptionalHeader.SectionAlignment;

if (size > 0)

{

dest = (unsigned char *)VirtualAlloc(codeBase + section->VirtualAddress,size,MEM_COMMIT,PAGE_READWRITE);

section->Misc.PhysicalAddress = (POINTER_TYPE)dest;

memset(dest, 0, size);

}

continue;

}

dest = (unsigned char *)VirtualAlloc(codeBase + section->VirtualAddress,section->SizeOfRawData,MEM_COMMIT,PAGE_READWRITE);

memcpy(dest, data + section->PointerToRawData, section->SizeOfRawData);

section->Misc.PhysicalAddress = (POINTER_TYPE)dest;

}

}

static int ProtectionFlags[2][2][2] = {

{

{PAGE_NOACCESS, PAGE_WRITECOPY},

{PAGE_READONLY, PAGE_READWRITE},

},

{

{PAGE_EXECUTE, PAGE_EXECUTE_WRITECOPY},

{PAGE_EXECUTE_READ, PAGE_EXECUTE_READWRITE},

},

};

static void FinalizeSections(PMEMORYMODULE module)

{

int i;

PIMAGE_SECTION_HEADER section = IMAGE_FIRST_SECTION(module->headers);

#ifdef _WIN64

POINTER_TYPE imageOffset = (module->headers->OptionalHeader.ImageBase & 0xffffffff00000000);

#else

#define imageOffset 0

#endif

for (i=0; iheaders->FileHeader.NumberOfSections; i++, section++)

{

DWORD protect, oldProtect, size;

int executable = (section->Characteristics & IMAGE_SCN_MEM_EXECUTE) != 0;

int readable =   (section->Characteristics & IMAGE_SCN_MEM_READ) != 0;

int writeable =  (section->Characteristics & IMAGE_SCN_MEM_WRITE) != 0;

if (section->Characteristics & IMAGE_SCN_MEM_DISCARDABLE)

{

VirtualFree((LPVOID)((POINTER_TYPE)section->Misc.PhysicalAddress | imageOffset), section->SizeOfRawData, MEM_DECOMMIT);

continue;

}

protect = ProtectionFlags[executable][readable][writeable];

if (section->Characteristics & IMAGE_SCN_MEM_NOT_CACHED)

{

protect |= PAGE_NOCACHE;

}

size = section->SizeOfRawData;

if (size == 0)

{

if (section->Characteristics & IMAGE_SCN_CNT_INITIALIZED_DATA)

{

size = module->headers->OptionalHeader.SizeOfInitializedData;

} else if (section->Characteristics & IMAGE_SCN_CNT_UNINITIALIZED_DATA)

{

size = module->headers->OptionalHeader.SizeOfUninitializedData;

}

}

if (size > 0)

{

if (VirtualProtect((LPVOID)((POINTER_TYPE)section->Misc.PhysicalAddress | imageOffset), size, protect, &oldProtect) == 0)

{

dPrintf("Error protecting memory page");

}

}

}

#ifndef _WIN64

#undef imageOffset

#endif

}

static void PerformBaseRelocation(PMEMORYMODULE module, SIZE_T delta)

{

DWORD i;

unsigned char *codeBase = module->codeBase;

PIMAGE_DATA_DIRECTORY directory = GET_HEADER_DICTIONARY(module, IMAGE_DIRECTORY_ENTRY_BASERELOC);

if (directory->Size > 0)

{

PIMAGE_BASE_RELOCATION relocation = (PIMAGE_BASE_RELOCATION) (codeBase + directory->VirtualAddress);

for (; relocation->VirtualAddress > 0; )

{

unsigned char *dest = codeBase + relocation->VirtualAddress;

unsigned short *relInfo = (unsigned short *)((unsigned char *)relocation + IMAGE_SIZEOF_BASE_RELOCATION);

for (i=0; iSizeOfBlock-IMAGE_SIZEOF_BASE_RELOCATION) / 2); i++, relInfo++)

{

DWORD *patchAddrHL;

#ifdef _WIN64

ULONGLONG *patchAddr64;

#endif

int type, offset;

type = *relInfo >> 12;

offset = *relInfo & 0xfff;

switch (type)

{

case IMAGE_REL_BASED_ABSOLUTE:

break;

case IMAGE_REL_BASED_HIGHLOW:

// change complete 32 bit address

patchAddrHL = (DWORD *) (dest + offset);

*patchAddrHL += delta;

break;

#ifdef _WIN64

case IMAGE_REL_BASED_DIR64:

patchAddr64 = (ULONGLONG *) (dest + offset);

*patchAddr64 += delta;

break;

#endif

default:

break;

}

}

relocation = (PIMAGE_BASE_RELOCATION) (((char *) relocation) + relocation->SizeOfBlock);

}

}

}

static int BuildImportTable(PMEMORYMODULE module)

{

int result = 1;

unsigned char *codeBase = module->codeBase;

PIMAGE_DATA_DIRECTORY directory = GET_HEADER_DICTIONARY(module, IMAGE_DIRECTORY_ENTRY_IMPORT);

if (directory->Size > 0)

{

PIMAGE_IMPORT_DESCRIPTOR importDesc = (PIMAGE_IMPORT_DESCRIPTOR) (codeBase + directory->VirtualAddress);

for (; !IsBadReadPtr(importDesc, sizeof(IMAGE_IMPORT_DESCRIPTOR)) && importDesc->Name; importDesc++)

{

POINTER_TYPE *thunkRef;

FARPROC *funcRef;

HMODULE handle = LoadLibraryA((LPCSTR) (codeBase + importDesc->Name));

if (handle == INVALID_HANDLE_VALUE)

{

dPrintf("Can't load library");

result = 0;

break;

}

module->modules = (HMODULE *)realloc(module->modules, (module->numModules+1)*(sizeof(HMODULE)));

if (module->modules == NULL)

{

result = 0;

break;

}

module->modules[module->numModules++] = handle;

if (importDesc->OriginalFirstThunk)

{

thunkRef = (POINTER_TYPE *) (codeBase + importDesc->OriginalFirstThunk);

funcRef = (FARPROC *) (codeBase + importDesc->FirstThunk);

}

else

{

thunkRef = (POINTER_TYPE *) (codeBase + importDesc->FirstThunk);

funcRef = (FARPROC *) (codeBase + importDesc->FirstThunk);

}

for (; *thunkRef; thunkRef++, funcRef++)

{

if (IMAGE_SNAP_BY_ORDINAL(*thunkRef))

{

*funcRef = (FARPROC)GetProcAddress(handle, (LPCSTR)IMAGE_ORDINAL(*thunkRef));

}

else

{

PIMAGE_IMPORT_BY_NAME thunkData = (PIMAGE_IMPORT_BY_NAME) (codeBase + (*thunkRef));

*funcRef = (FARPROC)GetProcAddress(handle, (LPCSTR)&thunkData->Name);

}

if (*funcRef == 0)

{

result = 0;

break;

}

}

if (!result)

{

break;

}

}

}

return result;

}

//##############################################################################################################

//功能:加载模块

//##############################################################################################################

HMEMORYMODULE MemoryLoadLibrary(const void *data)

{

PMEMORYMODULE result;

PIMAGE_DOS_HEADER dos_header;

PIMAGE_NT_HEADERS old_header;

unsigned char *code, *headers;

SIZE_T locationDelta;

DllEntryProc DllEntry;

BOOL successfull;

dos_header = (PIMAGE_DOS_HEADER)data;

if (dos_header->e_magic != IMAGE_DOS_SIGNATURE)

{

dPrintf("Not a valid executable file.\n");

return NULL;

}

old_header = (PIMAGE_NT_HEADERS)&((const unsigned char *)(data))[dos_header->e_lfanew];

if (old_header->Signature != IMAGE_NT_SIGNATURE)

{

dPrintf("No PE header found.\n");

return NULL;

}

code = (unsigned char *)VirtualAlloc((LPVOID)(old_header->OptionalHeader.ImageBase),old_header->OptionalHeader.SizeOfImage,MEM_RESERVE,PAGE_READWRITE);

if (code == NULL)

{

code = (unsigned char *)VirtualAlloc(NULL,old_header->OptionalHeader.SizeOfImage,MEM_RESERVE,PAGE_READWRITE);

if (code == NULL)

{

dPrintf("Can't reserve memory");

return NULL;

}

}

result = (PMEMORYMODULE)HeapAlloc(GetProcessHeap(), 0, sizeof(MEMORYMODULE));

result->codeBase = code;

result->numModules = 0;

result->modules = NULL;

result->initialized = 0;

VirtualAlloc(code,old_header->OptionalHeader.SizeOfImage,MEM_COMMIT,PAGE_READWRITE);

headers = (unsigned char *)VirtualAlloc(code,old_header->OptionalHeader.SizeOfHeaders,MEM_COMMIT,PAGE_READWRITE);

// 复制 PE文件头到代码

memcpy(headers, dos_header, dos_header->e_lfanew + old_header->OptionalHeader.SizeOfHeaders);

result->headers = (PIMAGE_NT_HEADERS)&((const unsigned char *)(headers))[dos_header->e_lfanew];

// 更新位置

result->headers->OptionalHeader.ImageBase = (POINTER_TYPE)code;

// 复制DLL数据到新的内存

CopySections((const unsigned char*)data, old_header, result);

// 处理输入数据基址

locationDelta = (SIZE_T)(code - old_header->OptionalHeader.ImageBase);

if (locationDelta != 0)

{

PerformBaseRelocation(result, locationDelta);

}

// 处理输入表

if (!BuildImportTable(result))

{

goto error;

}

FinalizeSections(result);

//调用DLL入口函数 DllMain

if (result->headers->OptionalHeader.AddressOfEntryPoint != 0)

{

DllEntry = (DllEntryProc) (code + result->headers->OptionalHeader.AddressOfEntryPoint);

if (DllEntry == 0)

{

dPrintf("Library has no entry point.\n");

goto error;

}

successfull = (*DllEntry)((HINSTANCE)code, DLL_PROCESS_ATTACH, 0); //调试发现加载MFC DLL直接停在这里,不向下运行了

if (!successfull)

{

dPrintf("Can't attach library.\n");

goto error;

}

result->initialized = 1;

}

return (HMEMORYMODULE)result;

error:

MemoryFreeLibrary(result);

return NULL;

}

//##############################################################################################################

//功能:获取模块函数地址

//##############################################################################################################

FARPROC MemoryGetProcAddress(HMEMORYMODULE module, const char *name)

{

unsigned char *codeBase = ((PMEMORYMODULE)module)->codeBase;

int idx = -1;

DWORD i,*nameRef;

WORD *ordinal;

PIMAGE_EXPORT_DIRECTORY exports;

PIMAGE_DATA_DIRECTORY directory = GET_HEADER_DICTIONARY((PMEMORYMODULE)module, IMAGE_DIRECTORY_ENTRY_EXPORT);

if (directory->Size == 0)

{

return NULL;

}

exports = (PIMAGE_EXPORT_DIRECTORY) (codeBase + directory->VirtualAddress);

if (exports->NumberOfNames == 0 || exports->NumberOfFunctions == 0)

{

return NULL;

}

nameRef = (DWORD *) (codeBase + exports->AddressOfNames);

ordinal = (WORD *) (codeBase + exports->AddressOfNameOrdinals);

for (i=0; iNumberOfNames; i++, nameRef++, ordinal++)

{

if (stricmp(name, (const char *) (codeBase + (*nameRef))) == 0)

{

idx = *ordinal;

break;

}

}

if (idx == -1)

{

return NULL;

}

if ((DWORD)idx > exports->NumberOfFunctions)

{

return NULL;

}

return (FARPROC) (codeBase + (*(DWORD *) (codeBase + exports->AddressOfFunctions + (idx*4))));

}

//##############################################################################################################

//功能:卸载模块

//##############################################################################################################

void MemoryFreeLibrary(HMEMORYMODULE mod)

{

int i;

PMEMORYMODULE module = (PMEMORYMODULE)mod;

if (module != NULL)

{

if (module->initialized != 0)

{

DllEntryProc DllEntry = (DllEntryProc) (module->codeBase + module->headers->OptionalHeader.AddressOfEntryPoint);

(*DllEntry)((HINSTANCE)module->codeBase, DLL_PROCESS_DETACH, 0);

module->initialized = 0;

}

if (module->modules != NULL)

{

for (i=0; inumModules; i++)

{

if (module->modules[i] != INVALID_HANDLE_VALUE)

{

FreeLibrary(module->modules[i]);

}

}

free(module->modules);

}

if (module->codeBase != NULL)

{

VirtualFree(module->codeBase, 0, MEM_RELEASE);

}

HeapFree(GetProcessHeap(), 0, module);

}

}

c 内存加载易语言dll,[求助]MemoryLoadLibrary 加载MFC 易语言 DLL 失败相关推荐

  1. 静态链接库(LIB)和动态链接库(DLL),DLL的静态加载和动态加载,两种LIB文件。

    静态链接库(LIB)和动态链接库(DLL),DLL的静态加载和动态加载,两种LIB文件. 一. 静态链接库(LIB,也简称"静态库")与动态链接库(DLL,也简称"动态库 ...

  2. c# 无法加载oraops.dll_Robotstudio软件二次开发:基于C#语言的Smart组件开发基础

    Robotstudio软件除了支持Add-Ins插件的二次开发以外,还支持Smart组件的二次开发.开发语言同样是基于.NET框架的C#语言或VB语言.Smart组件是Robotstudio软件中实现 ...

  3. java web配置dll文件_JavaWeb项目中dll文件动态加载方法解析(详细步骤)

    相信很多做Java的朋友都有过用Java调用JNI实现调用C或C++方法的经历,那么Java Web中又如何实现DLL/SO文件的动态加载方法呢.今天就给大家带来一篇JAVA Web项目中DLL/SO ...

  4. 白话Elasticsearch52-深入聚合数据分析之fielddata内存控制、circuit breaker短路器、fielddata filter、预加载机制以及序号标记预加载

    文章目录 概述 官网 fielddata核心原理 fielddata内存限制 监控fielddata内存使用 circuit breaker fielddata filter的细粒度内存加载控制 fi ...

  5. go语言 不支持动态加载_动态语言支持

    go语言 不支持动态加载 本文是我们名为" 高级Java "的学院课程的一部分. 本课程旨在帮助您最有效地使用Java. 它讨论了高级主题,包括对象创建,并发,序列化,反射等. 它 ...

  6. VB 文件未找到: 'C:\WINDOWS\system32\ieframe.dll\1'--继续加载工程吗?

    引用:http://blog.sina.com.cn/s/blog_5542b9c90100xsm8.html 文件未找到: 'C:\WINDOWS\system32\ieframe.dll\1'-- ...

  7. VC静态加载DLL和动态加载DLL

    VC静态加载DLL和动态加载DLL 1. 静态加载DLL 如果你有a.dll和a.lib,两个文件都有的话可以用静态加载的方式: message函数的声明你应该知道吧,把它的声明和下面的语句写到一个头 ...

  8. 使用Process Explorer和Dependency Walker排查C++程序中dll库动态加载失败问题

    目录 1.exe主程序启动时的库加载流程说明 2.加载dll库两种方式 2.1.dll库的隐式引用

  9. WinDBG详解进程初始化dll是如何加载的

    一:背景 1.讲故事 有朋友咨询个问题,他每次在调试 WinDbg 的时候,进程初始化断点之前都会有一些 dll 加载到进程中,比如下面这样: Microsoft (R) Windows Debugg ...

最新文章

  1. 厦门理工计算机研究生调剂,2018年厦门理工大学考研预调剂信息公布
  2. oracle精度制的数据类型,ORACLE 中NUMBER 类型 低精度转换成高精度
  3. 超详细中文预训练模型ERNIE使用指南
  4. python笔记2(函数 面向对象 文件编程 上下文管理器)
  5. 【NLP】图解 Attention完整版
  6. 互联网1分钟 |1214
  7. 黑马程序员—————— 多线程
  8. Struts2中动态的指定返回的结果集
  9. linux环境c语言课程设计,linux环境下c语言编程课程设计
  10. c语言ip地址转16进制,点分十进制形式的ip地址转化为十六进制数
  11. 超图(idesktop iserver10) 处理osgb倾斜摄影和tif并 发布 加载 ---1---连续更新
  12. IP地址聚合-路由汇聚_共同前缀(1.相似部分2.最后一组二进制比较,取相同,算位数3.转十进制,加位数)
  13. 在VS中如何生成moc文件
  14. VUE调用WEB3.0实现代币查询,批量转账功能
  15. c语言编程编写计算器图形,c语言编写的图形计算器.DOC
  16. 三维重建技术(2)各种方法简介
  17. 测试技术-测试策略与类型
  18. asp mysql查询_asp的 条件查询
  19. 如何让空调少用电,空气能热泵控制系统是这样实现的
  20. bigemap如何导入矢量边界范围下载地图(KML/KMZ/SHP)

热门文章

  1. 分布式一致性算法2PC和3PC
  2. Linux下无需按下回车(无阻塞)读取输入键值
  3. Crazypony四轴飞行器代码框架
  4. CXF整合Spring开发WebService
  5. Android开发者指南24难点各个击破—来自androi中文翻译组
  6. 测试Flex代码覆盖率工具---FlexCover
  7. 打印屏蔽部分内容window.print()
  8. ef mysql code first_关于ef+codefirst+mysql(入门)
  9. sql 2008 每次打开一个表都要登录_如何实现一个简易的orm
  10. tushare数据存入mysql代码_下载股票的历史日交易数据并存入数据库——基于tushare...