从DLL中导出变量学习

本文探讨了DLL文件中变量导出的原理,通过C和C++不同方式进行导出,并通过反汇编和依赖项查看工具进行分析。实验表明,C++导出的函数名会因多态性发生改变,而C方式导出保持原名。在导入时,若未正确匹配导出方式,会导致找不到符号的错误。
摘要由CSDN通过智能技术生成

本文的目的就是想探究dll文件中的变量是如何导出。借此了解ntoskrnl.exe 的导出到底是怎么实现的。
在前面的《SSDT HOOK》代码段中有这么一句话:

 extern "C"  PSERVICE_DESCRIPTOR_TALBE KeServiceDescriptorTable;

当时是说:这个符号是从ntoskrnl.exe 中导出的。从当时测试的时候改变符号名发现执行错误就可以看出来,这个符号绝对是从ntoskrnl.exe 文件中查找出来的。今天使用Depend walker 查看了一下,有这样的结果。
这里写图片描述

按键F10(c/c++ 符号形式) 转换,发现都是同一个函数名,因此可以判定这个符号是用C导出的。

这是因为如果使用的是c++符号形式导出,那么由于多态性的原因,其导出格式会发生改变。

为此我又做了一次测试。新建dll文件生成cpp 格式。源码如下:

FINAL.H
// The following ifdef block is the standard way of creating macros which make exporting 
// from a DLL simpler. All files within this DLL are compiled with the FINAL_EXPORTS
// symbol defined on the command line. this symbol should not be defined on any project
// that uses this DLL. This way any other project whose source files include this file see 
// FINAL_API functions as being imported from a DLL, wheras this DLL sees symbols
// defined with this macro as being exported.
#ifdef FINAL_EXPORTS
#define FINAL_API __declspec(dllexport)
#else
#define FINAL_API __declspec(dllimport)
#endif

// This class is exported from the FINAL.dll
class FINAL_API CFINAL {
   
public:
    CFINAL(void);
    // TODO: add your methods here.
};

extern FINAL_API int nFINAL;
extern FINAL_API int nTemp ;     //add here,others are default input.

FINAL_API int fnFINAL(void);

--------------
// FINAL.cpp : Defines the entry point for the DLL application.
//

#include "stdafx.h"
#include "FINAL.h"

BOOL APIENTRY DllMain( HANDLE hModule, 
                       DWORD  ul_reason_for_call, 
                       LPVOID lpReserved
                     )
{
    switch (ul_reason_for_call)
    {
        case DLL_PROCESS_ATTACH:
        case DLL_THREAD_ATTACH:
        case DLL_THREAD_DETACH:
        case DLL_PROCESS_DETACH:
            break;
    }
    return TRUE;
}


// This is an example of an exported variable
FINAL_API int nFINAL=0;
FINAL_API int nTemp = 0x10;        //add here.

// This is an example of an exported function.
FINAL_API int fnFINAL(void)
{
    return 42;
}

// This is the constructor of a class that has been exported.
// see FINAL.h for the class definition
CFINAL::CFINAL()
{ 
    return; 
}

程序很简单,

这时候打开depends 查看一下导出情况。
下图是c++默认的导出符号表(最左侧的C++ 表示是通过C++方式导出)
这里写图片描述

F10切换后,去掉装饰,不知道这个算不算变为C的方式呢?后期注意这个问题。
这里写图片描述

虽然用depends 可以切换,但是我更想知道编译器做了什么,用PEView 可以查看(导出表name段在.rdata段)。
这里写图片描述
由于PEView 不能复制结果出来,在这里我用十六进制查看器(Winhex)查看了一下,结果如下。

Offset      0  1  2  3  4  5  6  7   8  
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值