第一课:来源于_ Po学校
动态连接库 c++
extern "C"//把c++函数转换成c的方式 (也就是函数名不惨料)编程
概念 :windows
(窗口)
findwindow ---存在于 Uer32.dll
kernel32.dll (内核)函数
当代码用到dll的时候 用它的copy指向 达到节约内存操作系统
dll是一个能被其余程序加载的程序 (如可让QQ加载本身写的dll)
操做系统对任何的动态连接库,只会保存一份 (修改将会是全局的)线程
dll能进行动态调节、动态进行加载指针
/////////////调试
Dllmain //打破只能被调用的命运,今后掌握主动大权
主动:
case DLL_PROCESS_ATTACH: //被其余程序加载的时候
case DLL_THREAD_ATTACH: //当其余程序有新线程启动的时候
case DLL_THREAD_DETACH: //当其余程序某个线程终止(卸载)的时候
case DLL_PROCESS_DETACH: //被其余程序卸载code
因为ascii不能表示中文,因此就有了unicode,utf-8之类的多字节的字符 L宏就是把ascii的字符串转成多字节的。视频
MessageBox(NULL, L"DLL被加载!被线程加载", L"I Love..!", MB_OK); //这句是建立小对话框的
由于dll只能被其余程序加载, 因此不能直接按F5调试 或设为启动项目便可
注意: //先找当前文件夹-》若是当前文件夹没有-》咱们就去system32下查找-》64位 windows/system32 // 32位 windows/SysWoW64
360检测不到SysWOW64
//user32.dll -> 若是我在他的本地文件里创建一个假的user32.dll -》 他会不会加载这个假的dll
//这是DLL劫持 听说之前用的不少
------------------
DLL导出函数 、 内部函数
DLL导出函数----》 新建一个项目 dll 勾选导出
加载里面的int fnDllExportDemo(void)函数 HMODULE hModule=::LoadLibrary(L"DllExprotDemo.dll"); //加载的时候写上名字就能够了
使用fnDllExportDemo(void)函数的两种方法:
=======================================================================================
1.动态连接---
typedef int(*FUNC)(void);//这是一个函数类型
先要知道它的原型:
//HMODULE至关于当前这个dll的身份证号 定位到dll上面 //L宏就是把ascii的字符串转成多字节的。
HMODULE hModule=::LoadLibrary(L"DllExprotDemo.dll"); //加载的时候写上名字就能够了
//先找当前文件夹-》若是当前文件夹没有-》咱们就去system32下查找-》64位 windows/system32 // 32位 windows/SysWoW64
if (hModule == NULL) //当加载不到dll的时候 hModule的值会为空
{
MessageBox(NULL, L"加载DLL失败!", L"I Love mark!",MB_OK);
}
FUNC dllFunc=(FUNC)::GetProcAddress(hModule, "fnDllExprotDemo");//使用windows的API:GetProcAddress 得到句柄(把要使用的函数名传进去 会返回一个指针,用刚定义的接住),强转
printf("%d", dllFunc()); //调用 :好比printf 跟普通函数一毛同样
//当前使用的是c++编译出来的, 它有一个命名粉碎机制
//也就是 c++支持重载,它将你全部的函数名称都加点料
//要使用 得用c的方式进行编译 在
//DLLEXPROTDEMO_API int fnDllExprotDemo(void); //(DLLEXPROTDEMO_H目录下)
//更改为:
extern "C" DLLEXPROTDEMO_API int fnDllExprotDemo(void);
========================================================================================
2.静态连接---
1.拷贝它的头文件 ,放在要使用它的工程下面 (当前的也就是LoadDllDemo)
2.拷贝它的.lib ,也放在要使用它的工程下面
3.包含头文件 #include"DllExportDemo.h" #pragma comment(lib,"DllExportDemo.lib")
而后就能够直接调用了 printf("%d",fnDllExportDemo());
typedef int(*FUNC)(void);//这是一个函数类型
//当前使用的是c++编译出来的, 它有一个命名粉碎机制
//也就是 c++支持重载,它将你全部的函数名称都加点料
//要使用 得用c的方式进行编译 在
//DLLEXPROTDEMO_API int fnDllExprotDemo(void);
//更改为:
extern "C" DLLEXPROTDEMO_API int fnDllExprotDemo(void);
------------------------------------------------------------------------------------------------
CreateProcess function //建立进程函数
-----
//当前使用的是c++编译出来的, 它有一个命名粉碎机制
//也就是 c++支持重载,它将你全部的函数名称都加点料
//要使用 得用c的方式进行编译 在
//DLLEXPROTDEMO_API int fnDllExprotDemo(void);
//更改为:
extern "C" DLLEXPROTDEMO_API int fnDllExprotDemo(void);
---------------------------------
小结:导出函数 不管用哪一种方式 都要用extern "C"方式编译
extern"C" EXPORTDLL_API int fnExportDll(void); //c模式 #include "stdafx.h" #include<Windows.h> #include"ExportDll.h" #pragma comment(lib,"ExportDll.lib") typedef int(*FUNC)(void); // int main() { //HMODULE hModule = ::LoadLibrary(L"Practicedll_1.dll"); //加载 (这个呢,是没有导出的) HMODULE hModule=::LoadLibrary(L"ExportDll.dll"); //加载 (导出的) if (hModule == NULL) { MessageBox(NULL, L"加载失败", L"Mark", MB_OK); } //printf("%d", fnExportDll()); //静态导出的 (.h 和lib拷贝到执行程序下) //********如下是动态连接 FUNC dllFunc = (FUNC)::GetProcAddress(hModule, "fnExportDll");// 使用windows的API:GetProcAddress 得到句柄 (会返回一个指针) printf("%d", dllFunc()); return 0; }
感谢鹿鸣老师,还有Linda老师 ,还有Mark老师课讲得很是好 通俗易懂并且很是详细!
欢迎加 c++讨论群484983958 免费领视频哦 来 编程/黑客 爱好者