Windows Phone 8加载外部动态链接库DLL(非安装包内的)

Windows Phone 8加载外部动态链接库DLL(非安装包内的)

在《动态加载与插件化》中大概介绍了下,wp8加载非安装包的下动态链接库,这次详细梳理下。

加载外部DLL主要的原理:

  1. 通过NtCurrentTeb获得线程环境块
  2. 从线程环境块中获得进程环境块
  3. 在进程环境块中加载过得DLL链表
  4. 从链表中找到kernelbase.dll的模块句柄
  5. 从kernelbase.dll中获得LoadLibraryEx函数地址
  6. 加载指定地址下的DLL

相关的结构体:

typedef struct _CLIENT_ID

{

PVOID UniqueProcess;

PVOID UniqueThread;

} CLIENT_ID;

//模块链表实体

typedef struct _MODULE_LIST_ENTRY

{

struct  _MODULE_LIST_ENTRY* Flink;

struct  _MODULE_LIST_ENTRY* Blink;

DWORD* baseAddress;

}MODULE_LIST_ENTRY;

//进程加载的模块信息

typedef struct _PEB_LDR_DATA

{

//    BYTE fill[0x1c]; x86

ULONG Length;

BOOLEAN Initialized;

PVOID SsHandle ;

LIST_ENTRY InLoadOrderModuleList;

LIST_ENTRY InMemoryOrderModuleList;

MODULE_LIST_ENTRY* initModuleList;

}PEB_LDR_DATA;

//进程环境块

typedef struct _PEB

{

//    BYTE fill[0x0c]; x86

BYTE Reserved1[2];

BYTE BeingDebugged;

BYTE Reserved2[1];

PVOID Reserved3[2];

PEB_LDR_DATA* ldr;

}PEB;

//线程环境块

typedef struct _TEB

{

//BYTE fill[0x30]; x86

NT_TIB nt_tib;

PVOID EnvironmentPointer;

CLIENT_ID id;

PVOID ActiveRpcHandle;

PVOID ThreadLocalStoragePointer;

PEB* currentPEB;

}TEB;

typedef HMODULE(*LoadLibraryEx)(

LPCTSTR lpLibFileName,

HANDLE hFile,

DWORD dwFlags

);

获取kernelbase.dll模块句柄的类定义

namespace Anye
{
    namespace Native
    {
        public ref class DllHandle sealed
        {
            friend ref class NativeInterop;
            friend class NativeHelper;
        public:
            int GetModule();
        private:
            HMODULE _handle;
            DllHandle(HMODULE handle);
                //获取指定名称的函数地址
            void* GetFunction(LPCSTR name);
        };
        public ref class NativeInterop sealed
        {
        public:
            NativeInterop();
            //加载指定路径下的DLL
            DllHandle^ LoadLibrary(Platform::String^ name);
    //获取KernelBase.dll的模块句柄
            DllHandle^ GetKernel();
            int GetModule();
        private:
            DllHandle^ _kernel;
            LoadLibraryEx _loadLibrary;
            HMODULE getKernelModule();
        };
        class NativeHelper
        {
        public:
            NativeHelper(const wchar_t* path);
            void* GetFunction(LPCSTR name);
        private:
            DllHandle^ _interop;
        };
        
    }
}

主要的加载逻辑

HMODULE NativeInterop::getKernelModule()
{
    //获取线程环境快
    TEB* teb = NtCurrentTeb();
    获取KernelBase.dll的模块句柄PS:保险点的方法市历遍DLL初始化链表通过模块名称确定
    return (HMODULE) teb->currentPEB->ldr->initModuleList->Flink->baseAddress;
}
DllHandle^ NativeInterop::LoadLibrary(Platform::String^ name)
{
    if (_loadLibrary == nullptr)//获取LoadLibraryExW函数地址
        _loadLibrary = (LoadLibraryEx)_kernel->GetFunction("LoadLibraryExW");
    
    HMODULE module = _loadLibrary(name->Data(), nullptr, 0);
    if (module != nullptr)
        return ref new DllHandle(module);
    return nullptr;
}
void* DllHandle::GetFunction(LPCSTR name)
{
    return GetProcAddress(_handle, name);
}

NativeHelper

NativeHelper::NativeHelper(const wchar_t* path)
{
    auto inter = ref new NativeInterop();
    String^ pathString = (Platform::String^)Platform::StringReference(path);
    _interop = inter->LoadLibrary(pathString);
}
void* NativeHelper::GetFunction(LPCSTR name)
{
    return _interop->GetFunction(name);
}

下面是加载wp手机SD卡上的plugin.dll的例子

动态库项目

动态链接库逻辑

extern "C"
{
    __declspec(dllexport) void* Create();
}
namespace Plugin
{
    class IPlugin
    {
    public:
        virtual void Show(Platform::String^ msg) = 0;
    };
    class TestPlugin : public IPlugin
    {
    public:
        TestPlugin()
        {
    }
        void Show(Platform::String^ msg)
        {
        (ref new Windows::UI::Popups::MessageDialog(msg))->ShowAsync();
        }
    };
}
void* Create()
{
    return new Plugin::TestPlugin();
}

加载外部动态链接库

class IPlugin
{
public:
    virtual void Show(Platform::String^ msg) = 0;
};
void NativeEntry::Load(Platform::String^ path)
{    //path 是 D:\\Downloads\\plugin.dll,D盘就是sd
    Anye::Native::NativeHelper* h = new Anye::Native::NativeHelper(path->Data());
    CreateFunc func; 
    func = (CreateFunc)h->GetFunction("Create");
    IPlugin* plugin = (IPlugin*)func();
    plugin->Show("我是"+path+"里的插件^_^");
}

好了例子就到这了,我们获得了LoadLibraryExW函数,不局限于加载外部DLL,也可以去加载系统的DLL,去访问一些微软未公开的API,如只读访问注册表信息

Anye::Native::NativeInterop interop;
    auto h = interop.LoadLibrary("ADVAPI32LEGACY.DLL");
    Anye_RegCreateKeyEx = (RegCreateKeyFunc)GetFunc(h->GetModule(), "RegCreateKeyW");
    Anye_RegSetValueEx = (RegSetValueFunc)GetFunc(h->GetModule(), "RegSetValueW");
    Anye_RegQueryValueEx = (RegQueryValueFunc)GetFunc(h->GetModule(), "RegQueryValueW");
    Anye_RegCloseKey = (RegCloseKeyFunc)GetFunc(h->GetModule(), "RegCloseKey");
    Anye_RegOpenKey = (RegOpenKeyFunc)GetFunc(h->GetModule(), "RegOpenKeyW");
    Anye_RegEnumKey = (RegEnumKeyFunc)GetFunc(h->GetModule(), "RegEnumKeyW");

Windows Phone 8加载外部动态链接库DLL(非安装包内的),布布扣,bubuko.com

时间: 2024-10-03 23:10:15

Windows Phone 8加载外部动态链接库DLL(非安装包内的)的相关文章

PhoneGap 白名单安全机制 navigator.app 加载外部页面返回以及退出介绍

一. Phonegap 白名单安全机制 Phonegap应用的页面大多存在于本地,但有时需要加载外部的Web页面到应用内置的浏览器 视图中已完成特定的应用功能,出于安全性考虑,PhoneGap 设立了白名单安全机制,通过它来 控制能够加载到内置浏览器视图的内容来源. Android 不通过白名单安全机制的话调用外部浏览器 IOS 不通过白名单安全的话 会直接拒绝 二.Android 配置白名单 在res/xml/config.xml这个文件里进行配置 三.IOS 配置 以及 Wp7/wp8配置白

PhoneGap 白名单安全机制 navigator.app 加载外部页面返回

学习要点: 1. Phonegap 白名单安全机制 2. Navigator.app 对象加载外部页面 返回上级页面 一. Phonegap 白名单安全机制 Phonegap应用的页面大多存在于本地,但有时需要加载外部的Web页面到应用内置的浏览器 视图中已完成特定的应用功能,出于安全性考虑,PhoneGap 设立了白名单安全机制,通过它来 控制能够加载到内置浏览器视图的内容来源. Android 不通过白名单安全机制的话调用外部浏览器 IOS 不通过白名单安全的话会直接拒绝. Android

背水一战 Windows 10 (11) - 资源: CustomResource, ResourceDictionary, 加载外部的 ResourceDictionary 文件

[源码下载] 作者:webabcd 介绍背水一战 Windows 10 之 资源 CustomResource ResourceDictionary 加载外部的 ResourceDictionary 文件 示例1.演示“CustomResource”相关知识点CustomResourceTest.cs /* * 本例是一个自定义 CustomXamlResourceLoader,用于演示 CustomResource 的使用 */ using Windows.UI.Xaml.Resources;

未能加载 Oracle.ManagedDataAccessDTC.dll 或它的依赖项

第一个项目做完了,交付给测试进行测试,碰到一堆问题,当然不是程序上的,而是环境上的! 这个项目是用 EF 5 + MVC5 + Oracle 11 开发的. 驱动用的是 Oracle.ManagedDataAccess ,本地WIN7/8.1运行一点问题都没有.今天下午打包到 WIN 2008 上,解决了一堆环境问题后,一个大难题出现了: Could not load file or assembly 'Oracle.ManagedDataAccessDTC.dll',什么 PSPManager

Windows Live Writer加载代码着色插件步骤

博客园内置支持SyntaxHighlighter代码着色,代码着色语法:<pre class='brush:编程语言'>代码</pre>. 需要注意的是:如何你使用SyntaxHighlighter代码着色,需要将默认编辑器改为TinyMCE.如果使用CuteEditor,CuteEditor会自动去除代码中的空格,造成代码格式破坏.还有需要注意的是,加载完插件后,在Live Writer中是看不到代码着色效果的,发布后就可以看到了. 如果您使用Windows Live Write

资源: CustomResource, ResourceDictionary, 加载外部的 ResourceDictionary 文件

CustomResource ResourceDictionary 加载外部的 ResourceDictionary 文件 示例1.演示“CustomResource”相关知识点Resource/CustomResourceTest.cs /* * 本例是一个自定义 CustomXamlResourceLoader,用于演示 CustomResource 的使用 */ using Windows.UI.Xaml.Resources; namespace Windows10.Resource {

转载:Flash AS3.0 加载外部资源(图片,MP3,SWF)的两种方式

Flash AS3.0 加载外部资源(图片,MP3,SWF)的两种方式 出自:http://www.cnblogs.com/top5/archive/2012/08/04/2623464.html 关于AS3加载图片等外部资源,我常用的有两种方式:Loader和Embed,各自的特点,总结如下: Embed:在Flash编译阶段就将资源嵌入,也就是说图片资源是会被编译进swf文件里面去的:这样子的好处是代码比较简洁,使用方便,也不存在加载顺序的问题,缺点是会增大swf文件的体积 Loader:在

Microsoft Corporation 去掉 windows 修改 启动加载 版权

windows 修改 开机界面 boot启动界面 windows 修改 启动加载 版权 windows 系统如何修改开机画面的版权文字"Microsoft Corporation ... ◎Microsoft Corporation Microsoft Corporation 去掉 作者:韩梦飞沙 Author:han_meng_fei_sha 邮箱:[email protected] E-mail: 313134555 @qq.com 通过16进制的编辑器(我用的是winhex)打开winlo

C#中动态加载和卸载DLL

在C++中加载和卸载DLL是一件很容易的事,LoadLibrary和FreeLibrary让你能够轻易的在程序中加载DLL,然后在任何地方 卸载.在C#中我们也能使用Assembly.LoadFile实现动态加载DLL,但是当你试图卸载时,你会很惊讶的发现Assembly没有提供任何 卸载的方法.这是由于托管代码的自动垃圾回收机制会做这件事情,所以C#不提供释放资源的函数,一切由垃圾回收来做.  这引发了一个问题,用Assembly加载的DLL可能只在程序结束的时候才会被释放,这也意味着在程序运