SetWindowsHookEx,CBTProc和g ++ 3.4.5(mingw)

时间:2010-09-28 15:09:46

标签: windows dll g++ hook

我目前正在开发一个需要添加菜单的应用程序 到每个应用程序的系统菜单。我可以为现有的目标做到这一点 具有EnumWindows功能的窗口。 对于新窗口(应用程序启动后我的) 我试图用Windows钩子做这件事。更具体地说,CBTProc。 这就是我被困住的地方。 我已经删除了应用程序中的所有可能内容, 但我的印象是我的dll中的程序没有 完全被召唤。

这是dll的代码:

#include <string>
using std::string;

#include <fstream>
using std::ofstream;

#include <windows.h>

// ---------------------------------------------------
extern "C"
{
  void log(const string & msg)
  {
    ofstream out("out.log", std::ios_base::app);
    out << msg;
    out.flush();
    out.close();
  }
  // ---------------------------------------------------  
  LRESULT CALLBACK CBTProc(int nCode, WPARAM wParam, LPARAM lParam)
  {
    log("CBTProc");
    return CallNextHookEx(0, nCode, wParam, lParam);
  }
  // ---------------------------------------------------  
}

我在windows xp sp3 32bit机器上用g ++ 3.4.5编译它:

g++ -shared -otest.dll test_dll.cpp

这是应用程序的代码

#include <iostream>
using std::cout;
using std::cin;
using std::cerr;
using std::endl;

#include <string>
using std::string;

#include <windows.h>

typedef void (*func)();

void run()
{
  cout << "press enter to exit" << endl;
  cin.get();
}

void * loadProc(HMODULE mod, const char * procname)
{
  void * retval = (void *)GetProcAddress(mod, procname);
  if (retval == NULL)
    cerr << "GetProcAddress(" << procname << ") failed" << endl;
  return retval;
}

int main(int argc, char ** argv)
{
  HMODULE dll = LoadLibrary("test.dll");
  if (dll == NULL)
    {
      cerr << "LoadLibrary failed" << endl;
      return 1;
    }

  HOOKPROC proc = (HOOKPROC)loadProc(dll, "CBTProc@12");
  if (!proc)
    return 1;

  HHOOK callwnd = SetWindowsHookEx(WH_CBT, proc, dll, 0);
  if (callwnd == NULL)
    {
      cerr << "SetWindowsHookEx failed for CBTProc" << endl;
      return 1;
    }

  run();
  UnhookWindowsHookEx(callwnd);

  return 0;
}

我用相同的设置编译它:

g++ -otest.exe test.cpp

当我跑步时,我没有错误,但是当我启动新的应用程序时,我什么也得不到 在我的日志文件中。

有什么想法吗?

GR, LDX

编辑:拼写错误

1 个答案:

答案 0 :(得分:1)

我建议您检查以下内容:

  • 确保您的DLL具有导出功能 (可以使用dumpbin工具检查)。一世 不知道g ++,但在MSVC中呢 是必要的使用 __declspec(dllexport)或在DEF文件中显式声明导出。

  • 确保您的主机应用程序 使用正确的名称 导出函数(与...相同) “dumpbin / EXPORTS test.dll” 显示器)

  • 请记住,您正在使用相对文件名out.log - 当DLL被加载到其他进程时,它将相对于主机进程的当前目录进行编写。出于测试目的,最好使用OutputDebugString API并使用DbgView工具检查结果。

您的解决方案可能已经有效。

PS:在注入的DLL中使用STL通常不是一个好主意。确保您了解风险。