一个程序,可以动态的加载动态连接库,写动态连接库的人可以给你一个文本来描述动态连接库的名 函数原型,注意是文本的,所以你的程序里不知道对方会给你一个什么样的函数、函数有几个参数,要求能够调用他的程序,假设参数是window标志的,没有用户自定义的类型。我已经实现了一半,就差函数参数的处理了
谢谢

解决方案 »

  1.   

    你们没有过这样的需求吗?配置文件:
    “acc.dll”
    “int function1(int a, int b)”
    “a=5”
    “b=6”
    要求在你的程序里调用
      

  2.   

    我相信是可以实现的,因为com中的invoke就是这样调用的,vb和其他的解释语音也应该是这样的
      

  3.   

    够了;
    用LoadLibrary和GetProcAddress可以实现了
      

  4.   

    你把问题想的简单了,我传给你的时候是将函数和参数传给你了,但是是以串的形式传的,
    在你写程序的时候,根本不知道dll中函数的原型。
      

  5.   

    先GetProcAddress(),然后把参数 push 入栈,CALL 函数即可。
      

  6.   

    HMODULE hMod = LoadLibrary("***");
    void *proc = GetProcAddress(hMod, "***");
    *** Result;
    __asm
    {
        push    ***;
        push    ***;
        push    ***;
    ......
        mov     eax, proc;
        call    eax;
        mov     Result, eax;
    }
      

  7.   

    是的,我也这么想,但是
    1 call方法不是c、c++的内置函数
    2 怎样push参数?就是这里不太明白,谢谢指教
      

  8.   

    __asm
    {
    这就表示用汇编语言,PUSH ,CALL都是汇编。至于用汇编实现循环,从书上引用一段就可以了,用不了多少时间。
      

  9.   

    我用你写的方法是可以实现,但是报错:
    #include "stdafx.h"
    #include <iostream>using namespace std;typedef void* (*pFunction)(...);int Func(int nParam1,int nParam2)
    {
    cout<<"yes :a"<< nParam1 <<" b "<< nParam2<<endl;
    return 3;
    }int _tmain(int argc, _TCHAR* argv[])
    { pFunction pf = (pFunction)Func;
        int a=1,b=2; //void* c = (*pf)(a,b);
    int c;
    __asm
    {
    push a;
    push b;
    mov     eax, pf;
    call    eax;
    mov     c, eax;
    } cout<< "c="<<c<<endl;
    return 0;
    }
    runt-time check failure# 0 the value of esp was not properly saved across a function call.
    我的msn:[email protected]
    欢迎指正。
      

  10.   

    NTDLL.DLL!77f97704() 
      DllLoader.exe!_RTC_Failure(void * retaddr=0x004324ac, int errnum=0)  + 0x2e C++
      DllLoader.exe!_RTC_CheckEsp()  + 0x19 C++
    > DllLoader.exe!main(int argc=1, char * * argv=0x00341678)  行40 + 0x10 C++
      DllLoader.exe!mainCRTStartup()  行259 + 0x19 C
      KERNEL32.DLL!77e7ca90() 
      

  11.   

    你的Func是 __cdecl 格式的。我举例的函数是__stdcall 格式。
    你调用FUNC需要自己清理栈。
    __asm {
        push b;//先B后A
        push a;
        mov  eax, pf;
        call eax;
        mov  c, eax;
        add esp,08h
    }
      

  12.   

    CDECL 是由调用者负责清理栈的,所以要最后一句。别的方法,不知道。
      

  13.   

    everandforever(Forever)  :你有msn吗?我们通过msn来交流好吗?谢谢
      

  14.   

    噢,我明白了,谢谢你。
    对于数组怎么处理,push的时候只写数组的地址(也就是数组名)就可以?
      

  15.   

    靜態鏈接不行嗎?
    你可以根據DLL文件獲得Lib導入庫
    要用到DumpBin.exe /exports xxx.dll>xxx.def
          修改為常見的def 文件。
    再用lib .exe /def:xxx.def 生成xxx.lib .
    接下來就不用說了吧。
      

  16.   

    不行,我要写的是一个可以动态加载并运行指定dll的程序,但是我事先不知道dll中的函数原型,写dll的人要做的只是用文本将dll中要调用的函数类型告诉我就可以了。而我的程序不用有任何变化
      

  17.   

    force_eagle(战鹰) :能够再给的具体一点吗类的成员函数指针我知道 ->*
    但是如何用模板来包装?谢谢提供思路
      

  18.   

    不知道你说的是什么问题,我试了一下是可以传数组的。 这个是用来测试的DLL导出函数定义,__cdecl调用方式:
    __declspec(dllexport) void print(int* array,int size)
    {
    for(int i=0;i<size;i++)
    cout<<array[i]<<endl;
    }
    下面是调用代码:
    HMODULE hMod=LoadLibrary("dll.dll");
    PROC pfn=GetProcAddress(hMod,"print");
    int array[5]={1,2,3,4,5};
    int ** address=(int**)&array;
    __asm
    {
    push 5;
    push address;//注意这里不能直接把数组名压到栈里,不知道你遇到的是不是这个问题
    call pfn;
    add esp,8;  //如果导出函数是__stdcall的,这个就不要了。
    }
    经测试一切正常。
      

  19.   

    webber84(***闭关修炼中***)  :
    谢谢你,这不是我遇到的问题,我是想将参数放到数组,然后循环压栈,因为dll的函数中的参数个数可能是不同的类型,所以我要用一个variant 数组来存放收到到参数变量,然后压栈。不知道你是否明白了我的意思。