📄 main.cpp
字号:
// MainMfc.cpp : Defines the class behaviors for the application.
//
#include <stdio.h>
#include <windows.h>
#include <Delayimp.h>
#pragma comment(lib, "Delayimp.lib")
// MainDLL testing
extern "C" int fnLib();
extern "C" int fnLib2();
#include "..\MainDll\MainClass.h"
// Test.dll Testing
#include "..\Test\Test.h"
#pragma comment(linker, "/DelayLoad:Test.dll")
#pragma comment(linker, "/DelayLoad:MainDLL.dll")
#pragma comment(linker, "/Delay:unload")
#pragma comment(lib,"..\\test\\debug\\test.lib")
#pragma comment(lib,"..\\maindll\\debug\\maindll.lib")
FARPROC WINAPI DliHook(unsigned dliNotify, PDelayLoadInfo pdli);
// This looks nicer
#ifdef __cplusplus
extern "C"
{
#endif
#include "CheckCpu.h"
// Type of compiler
typedef enum tagCompilerTypes
{
DELAYDLL_COMP_MS = 0,
DELAYDLL_COMP_VECTORC,
DELAYDLL_COMP_INTEL,
DELAYDLL_COMP_METROWORKS,
DELAYDLL_COMP_BCHECKER,
DELAYDLL_COMP_MAX
} DLLCompilerTypes;
// Processor needed for dll
typedef enum tagProcessorTypes
{
DELAYDLL_PROC_PIV = 0,
DELAYDLL_PROC_ATHLON_XP,
DELAYDLL_PROC_PIII,
DELAYDLL_PROC_ATHLON,
DELAYDLL_PROC_PII,
DELAYDLL_PROC_K6_2,
DELAYDLL_PROC_K6,
DELAYDLL_PROC_PPRO,
DELAYDLL_PROC_PENTIUM_MMX,
DELAYDLL_PROC_PENTIUM,
DELAYDLL_PROC_MAX
} DLLProcessorTypes;
int IsValidDllForProcessor ( DLLProcessorTypes dllproctype );
typedef struct tagDLLDescriptor
{
// 判断是否列表结束
int iInUse;
// 动态链接库调用时的替换名称
char* pDllName;
// 动态链接库调用时的替换扩展名
char* pDllExtension;
// 需要的处理器类型
DLLProcessorTypes Processor;
// 采用的编译器
DLLCompilerTypes Compiler;
} DLLDescriptor;
typedef struct tagDLLCollection
{
char* pDllName;
DLLDescriptor* pDLLDescriptors;
} DLLCollection;
extern DLLCollection pDelayLoadedDLLs[];
int UnloadDelayedDLL ( LPCSTR pDLL );
typedef int (__cdecl *isTypeProcessor) (void);
static isTypeProcessor TestFunctions[] =
{
isPentium4,
isAthlonXP,
isPentiumIII,
isAthlon,
isPentiumII,
isAMDK62,
isAMDK6,
isPentiumPro,
isPentiumMMX,
isPentium,
NULL
};
int IsValidDllForProcessor ( DLLProcessorTypes dllproctype )
{
int iReturn = 0;
if ( dllproctype >= 0 && dllproctype < DELAYDLL_PROC_MAX )
{
if ( TestFunctions[dllproctype] )
{
iReturn = TestFunctions[dllproctype]();
}
}
return iReturn;
}
int UnloadDelayedDLL ( LPCSTR pDLL )
{
return __FUnloadDelayLoadedDLL(pDLL);
}
#ifdef __cplusplus
}
#endif
// 这是一个延迟加载的回调函数框架
FARPROC WINAPI DliHook(unsigned dliNotify, PDelayLoadInfo pdli) {
FARPROC fp = NULL; // 缺省返回值,为零时意味着由系统处理加载
// pdli 指向的PDelayLoadInfo结构用于描述到目前为止的进度结果
switch (dliNotify) {
case dliStartProcessing:
// 这个通知码在__delayLoadHelper函数尝试查找DLL/function时触发
// 返回0,让系统自己处理,返回非0,手工处理,这时仍会收到dliNoteEndProcessing通知
break;
case dliNotePreLoadLibrary:
//在调用LoadLibrary时触发
// 如果返回NULL,标识让__delayLoadHelper 自己加载动态链接库,否则需要手工加载
//该动态链接库,并返回模块句柄
//这里首先判断是否时要处理优化的动态链接库名称
fp = (FARPROC)(HMODULE) NULL;
{
int iNr = 0;
BOOL bFoundCollection = FALSE;
while ( pDelayLoadedDLLs[iNr].pDllName && bFoundCollection == FALSE )
{
if ( strcmp( pdli->szDll, pDelayLoadedDLLs[iNr].pDllName ) == 0 )
{
bFoundCollection = TRUE;
}
else
{
iNr++;
}
}
if ( bFoundCollection )
{
// 判断列表中的动态链接库名称是否完整,并判断是否符合当前的处理器类型
if ( pDelayLoadedDLLs[iNr].pDLLDescriptors )
{
int iNrDescriptor = 0;
while ( pDelayLoadedDLLs[iNr].pDLLDescriptors[iNrDescriptor].iInUse )
{
DLLProcessorTypes dllproctype =
pDelayLoadedDLLs[iNr].pDLLDescriptors[iNrDescriptor].Processor;
if ( IsValidDllForProcessor ( dllproctype ) )
{
TCHAR s[1024];
strcpy( s , pDelayLoadedDLLs[iNr].pDllName);
// Test for Complete DLL name or just an extension
if ( pDelayLoadedDLLs[iNr].pDLLDescriptors[iNrDescriptor].pDllName )
{
strcpy(s , pDelayLoadedDLLs[iNr].pDLLDescriptors[iNrDescriptor].pDllName);
}
else
{
// Make Just DLL name
char* szFound=strrchr(s,'.');
if ( szFound )
{
// Just DLL, without .dll
*szFound=0;
strcat(s,pDelayLoadedDLLs[iNr].pDLLDescriptors[iNrDescriptor].pDllExtension );
}
}
// 满足条件的话采用优化版本的动态链接库替换原默认的动态链接库
fp = (FARPROC)(HMODULE) ::LoadLibrary( s );
if ( fp )
{
#ifdef _DEBUG
OutputDebugString ( "Loading optimized dll named :" );
OutputDebugString ( s );
OutputDebugString ( "\n" );
#endif
break;
}
}
// If not found check next
iNrDescriptor++;
}
}
}
}
break;
case dliFailLoadLib:
// 加载失败处理,这里还可以手工调用LoadLibrary函数进行补救,并返回一个
//动态链接库模块句柄,如果返NULL值,__delayLoadHelper 函数会抛出一个
// ERROR_MOD_NOT_FOUND 异常
fp = (FARPROC)(HMODULE) NULL;
break;
case dliNotePreGetProcAddress:
// 在调用GetProcAddress函数之前调用,如果NULL,__delayLoadHelper会替用户调用
// GetProcAddress函数。用户也可以在这里调用GetProcAddress并返回地址
fp = (FARPROC) NULL;
break;
case dliFailGetProc:
// 当调用GetProcAddress 失败时被触发
// 用户可以手工调用GetProcAddress 返回一个地址进行补救。
// 如果返回一个NULL值, __delayLoadHelper 函数会抛出一个
// ERROR_PROC_NOT_FOUND 异常
fp = (FARPROC) NULL;
break;
case dliNoteEndProcessing:
// __delayLoadHelper 完成通知
//用户可以检查DelayLoadInfo成员自己抛出异常
break;
}
return(fp);
}
DLLDescriptor TestDLL[] =
{
1, NULL, "Pentium.dll", DELAYDLL_PROC_PENTIUM, DELAYDLL_COMP_INTEL,
NULL
};
DLLDescriptor MainDLL[] =
{
1, "MainDLL.PIV.dll", NULL, DELAYDLL_PROC_PIV, DELAYDLL_COMP_VECTORC,
1, "MainDLL.Athlon.dll", NULL, DELAYDLL_PROC_ATHLON, DELAYDLL_COMP_VECTORC,
1, NULL, "PII.dll", DELAYDLL_PROC_PII, DELAYDLL_COMP_VECTORC,
NULL
};
// Only these DelayLoaded DLL will be checked for there Optimized versions
DLLCollection pDelayLoadedDLLs[] =
{
"Test.dll", TestDLL,
"MainDLL.dll", MainDLL,
NULL
};
DWORD ExceptFilter(struct _EXCEPTION_POINTERS* ep)
{
return TRUE;
}
int main()
{
__pfnDliNotifyHook = DliHook;
__pfnDliFailureHook = DliHook;
// 测试 MainDll.dll
__try
{
int x = fnLib();
x = fnLib();
x = fnLib2();
// 测试 test.dll
}
__except(ExceptFilter(GetExceptionInformation()))
{
}
return 1;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -