2

GetProcAddress 返回一个函数指针。假设我们得到函数 Beep 的地址(它的声明可以在 WinBase.h 中找到(当包括 Windows.h 时))

BOOL WINAPI Beep(
  _In_  DWORD dwFreq,
  _In_  DWORD dwDuration
);

那么经典代码可能看起来像

typedef BOOL(__stdcall *pbeep)(DWORD , DWORD );
pbeep beep = NULL;
FARPROC fptr = GetProcAddress(Hnd,"Beep");
beep = reinterpret_cast<pbeep>(fptr);
if( beep != NULL ) {
   beep( 440, 1200 ); //this generates a beep for 1.2 secs...
      }

一切看起来都很好并且工作正常。我的问题:

考虑到编译器可以“以某种方式”从 WinBase.h 中包含的 Beep() 声明中获取函数指针“信息”,有什么方法可以避免 typedef 声明。我的目标是以某种方式重新使用已经包含在已包含的 .h 文件中的信息(返回/参数/等),其中声明了 Beep() 函数,而不必在 typedef 上手动重复所有这些信息。为一个函数执行此操作时没关系,但是当函数数量增加时,这些 typedef 确实是一种痛苦和错误的一大来源。可以这样做吗?

编辑; 我很快就会迁移到 VS 2013,但到目前为止仍在使用 VS2008,那么我的想法是不使用 C++11

4

5 回答 5

4

您可以在 C++11 中创建一个函数来执行此操作(或者如果您可以让 Boost.Typeof 出价,则可能是 C++03):

template<typename F>
F GetKnownProcAddress(HMODULE hmod, const char *name, F) {
    auto proc = reinterpret_cast<F>(GetProcAddress(hmod, name));
    if (!proc) {/*throw or something*/}
    return proc;
}

int main() {
    auto beep = GetKnownProcAddress(Hnd, "Beep", Beep);
}

如果你愿意使用宏,你可以更进一步:

//where GetKnownProcAddressImpl is the above; also consider the usual STRINGIFY
#define GetKnownProcAddress(hmod, func) GetKnownProcAddressImpl(hmod, #func, func);
auto beep = GetKnownAddressProc(Hnd, Beep);
于 2014-02-02T23:08:35.970 回答
2

在 c++11 中,您可以编写

decltype (&Beep) beep_ptr = reinterpret_cast<decltype (&Beep)>GetProcAddress(Hnd,"Beep");

但我不明白你为什么要这样做——如果你已经有一个指向函数的指针,为什么要手动加载它?

于 2014-02-02T22:58:56.530 回答
2
#include <windows.h>

int main()
{
    decltype(Beep)* beep = (decltype(Beep)*)GetProcAddress(GetModuleHandle("Kernel32.dll"), "Beep");
    beep(440, 1200);
}
于 2014-02-02T23:01:18.477 回答
0

或尝试:-

typedef BOOL (*pbeep)(DWORD, DWORD);
FARPROC fptr = GetProcAddress(Hnd,"Beep");
((pbeep)fptr)( 440, 1200);
于 2015-11-26T04:38:44.507 回答
-1
BOOL (__stdcall *beep)(DWORD, DWORD); // beep - pointer to function with parameters (DWORD, DWORD) and result of type bool
(FARPROC)beep = GetProcAddress(Hnd,"Beep");
if( beep != NULL ) {
     beep( 440, 1200 ); //this generates a beep for 1.2 secs...
}
于 2014-04-28T11:19:25.667 回答