ACE程序入口函数替换机制分析(收藏)
ACE程序入口函数替换机制分析
(hardcorn 写于2005.10.27)
我们从一个ACE例子进行分析:
ACE程序中的ACE_TMAIN宏说明:
大家注意看我代码中的注释
先看原代码:
//--------------------------------------
//copy from: ACE_ROOT/ace/OS_main.h
//ACE_TMAIN define
# define ACE_TMAIN /
ace_tmain_i (int, ACE_TCHAR *[]); / //***我们自己的代码会添加到这个函数中,进行调用
ACE_Export int ace_os_wintmain_i (ACE_Main_Base&, HINSTANCE, HINSTANCE, LPWSTR, int); /* forward declaration */ /
class ACE_Main : public ACE_Main_Base {int run_i (int argc, ACE_TCHAR *argv[]);}; /
inline int ACE_Main::run_i (int argc, ACE_TCHAR *argv[]) /
{ /
return ace_tmain_i (argc, argv); / //***调用我们编写的代码
} /
int WINAPI WinMain (HINSTANCE hInstance, HINSTANCE hPrevInstance, LPWSTR lpCmdLine, int nCmdShow) / //***程序真实的入口
{ /
ACE_Main m; / //***定义一个ACE_Main对象,并传给ace_os_wintmain_i,在ace_os_wintmain_i中,会调用m.run_i()
return ace_os_wintmain_i (m, hInstance, hPrevInstance, lpCmdLine, nCmdShow); /
} /
int ace_tmain_i //***ACE为们提供一个函数头,函数体由我们自己来写。
//ACE_TMAIN end.
//-------------------------------------
//-------------------------------------
// copy form ACE_ROOT/ace/OS_main.cpp
//ace_os_wintmain_i define
int WINAPI ace_os_wintmain_i (ACE_Main_Base &mbase, HINSTANCE hInstance,
HINSTANCE hPrevInstance, LPWSTR lpCmdLine, int nCmdShow)
{
ACE_TCHAR cmdline[1024];
ACE_OS::strcpy (cmdline, ACE_LIB_TEXT ("program "));
ACE_OS::strcat (cmdline, lpCmdLine);
ACE_ARGV ce_argv (cmdline);
ACE::init (); //***注意,对ACE环境时行初始化
ACE_MAIN_OBJECT_MANAGER
//***注意下边这行代码。mbase.run()中,会去调用我们在外边定义的run_i(),这是一个虚函数
//***而run_i()中会调用ace_tmain_i(),这才是我们要自己要运行的代码
int i = mbase.run (ce_argv.argc (), ce_argv.argv ());
ACE::fini (); //***注意,释放ACE环境
return i;
}
//ace_os_wintmain_i end
//-------------------------------------
例子:
//我写一ACE的代码,并将宏进行还原:
//ACE代码:
int ACE_TMAIN(int args, ACE_TCHAR *argv[])
{
int a = 0;
int b = 1;
a = a + b;
}
//将宏还原后的真实代码:
int /*ACE_TMAIN strat*/ ace_tmain_i (int, ACE_TCHAR *[]);
//注:ace_os_wintmain_i是从ace库中导出的函数,直接用函数体来代替这个声明:
//ACE_Export int ace_os_wintmain_i (ACE_Main_Base&, HINSTANCE, HINSTANCE, LPWSTR, int);
int WINAPI ace_os_wintmain_i (ACE_Main_Base &mbase, HINSTANCE hInstance,
HINSTANCE hPrevInstance, LPWSTR lpCmdLine, int nCmdShow)
{
ACE_TCHAR cmdline[1024];
ACE_OS::strcpy (cmdline, ACE_LIB_TEXT ("program "));
ACE_OS::strcat (cmdline, lpCmdLine);
ACE_ARGV ce_argv (cmdline);
ACE::init ();
ACE_MAIN_OBJECT_MANAGER
int i = mbase.run (ce_argv.argc (), ce_argv.argv ());
ACE::fini ();
return i;
}
class ACE_Main : public ACE_Main_Base
{
int run_i (int argc, ACE_TCHAR *argv[]);
};
inline int ACE_Main::run_i (int argc, ACE_TCHAR *argv[])
{
return ace_tmain_i (argc, argv);
}
int WINAPI WinMain (HINSTANCE hInstance, HINSTANCE hPrevInstance, LPWSTR lpCmdLine, int nCmdShow)
{
ACE_Main m;
return ace_os_wintmain_i (m, hInstance, hPrevInstance, lpCmdLine, nCmdShow);
}
int ace_tmain_i /*ACE_TMAIN end*/ ( int args, ACE_TCHAR* argv[])
{
int a = 0;
int b = 1;
a = a + b;
}
//end
WinMain -call-> ace_os_wintmain_i [进行ACE环境的初始] -call-> ACE_Main_Base::run() -call->ACE_Main::run_i() -call-> ace_tmain_i[运行我们自己的代码]
WinMain <-ret- ace_os_wintmain_i [释放ACE环境] <-ret- ACE_Main::run_i() <-ret- ace_tmain_i
还有,我上边列出来的ACE_TMAIN只是其中之一,ACE做了好几个程序入口函数的宏替换:
如:main,wmain
说明:
ACE对我们的程序入口,进行到替换. 在程序启动和退出时,做了一些初始化工作。
其中最主要的工作就是: ACE::init() 和 ACE::fini();
再说明我MFC吧,MFC将程序入口,包在了CWinApp类中。所以ACE没有办法对其进行修改。
也就没有办法在MFC中做一些“自动”的初始化和释放工作; 那么这个工作就只有我们自己完成了...
所以在MFC的工程中使用ACE,就得自己调用初始化: ACE::init(); 和释放:ACE::fini()
如果不调!!!呵呵。那就只好等着出错了。:)
(hardcorn 写于2005.10.27)
我们从一个ACE例子进行分析:
ACE程序中的ACE_TMAIN宏说明:
大家注意看我代码中的注释
先看原代码:
//--------------------------------------
//copy from: ACE_ROOT/ace/OS_main.h
//ACE_TMAIN define
# define ACE_TMAIN /
ace_tmain_i (int, ACE_TCHAR *[]); / //***我们自己的代码会添加到这个函数中,进行调用
ACE_Export int ace_os_wintmain_i (ACE_Main_Base&, HINSTANCE, HINSTANCE, LPWSTR, int); /* forward declaration */ /
class ACE_Main : public ACE_Main_Base {int run_i (int argc, ACE_TCHAR *argv[]);}; /
inline int ACE_Main::run_i (int argc, ACE_TCHAR *argv[]) /
{ /
return ace_tmain_i (argc, argv); / //***调用我们编写的代码
} /
int WINAPI WinMain (HINSTANCE hInstance, HINSTANCE hPrevInstance, LPWSTR lpCmdLine, int nCmdShow) / //***程序真实的入口
{ /
ACE_Main m; / //***定义一个ACE_Main对象,并传给ace_os_wintmain_i,在ace_os_wintmain_i中,会调用m.run_i()
return ace_os_wintmain_i (m, hInstance, hPrevInstance, lpCmdLine, nCmdShow); /
} /
int ace_tmain_i //***ACE为们提供一个函数头,函数体由我们自己来写。
//ACE_TMAIN end.
//-------------------------------------
//-------------------------------------
// copy form ACE_ROOT/ace/OS_main.cpp
//ace_os_wintmain_i define
int WINAPI ace_os_wintmain_i (ACE_Main_Base &mbase, HINSTANCE hInstance,
HINSTANCE hPrevInstance, LPWSTR lpCmdLine, int nCmdShow)
{
ACE_TCHAR cmdline[1024];
ACE_OS::strcpy (cmdline, ACE_LIB_TEXT ("program "));
ACE_OS::strcat (cmdline, lpCmdLine);
ACE_ARGV ce_argv (cmdline);
ACE::init (); //***注意,对ACE环境时行初始化
ACE_MAIN_OBJECT_MANAGER
//***注意下边这行代码。mbase.run()中,会去调用我们在外边定义的run_i(),这是一个虚函数
//***而run_i()中会调用ace_tmain_i(),这才是我们要自己要运行的代码
int i = mbase.run (ce_argv.argc (), ce_argv.argv ());
ACE::fini (); //***注意,释放ACE环境
return i;
}
//ace_os_wintmain_i end
//-------------------------------------
例子:
//我写一ACE的代码,并将宏进行还原:
//ACE代码:
int ACE_TMAIN(int args, ACE_TCHAR *argv[])
{
int a = 0;
int b = 1;
a = a + b;
}
//将宏还原后的真实代码:
int /*ACE_TMAIN strat*/ ace_tmain_i (int, ACE_TCHAR *[]);
//注:ace_os_wintmain_i是从ace库中导出的函数,直接用函数体来代替这个声明:
//ACE_Export int ace_os_wintmain_i (ACE_Main_Base&, HINSTANCE, HINSTANCE, LPWSTR, int);
int WINAPI ace_os_wintmain_i (ACE_Main_Base &mbase, HINSTANCE hInstance,
HINSTANCE hPrevInstance, LPWSTR lpCmdLine, int nCmdShow)
{
ACE_TCHAR cmdline[1024];
ACE_OS::strcpy (cmdline, ACE_LIB_TEXT ("program "));
ACE_OS::strcat (cmdline, lpCmdLine);
ACE_ARGV ce_argv (cmdline);
ACE::init ();
ACE_MAIN_OBJECT_MANAGER
int i = mbase.run (ce_argv.argc (), ce_argv.argv ());
ACE::fini ();
return i;
}
class ACE_Main : public ACE_Main_Base
{
int run_i (int argc, ACE_TCHAR *argv[]);
};
inline int ACE_Main::run_i (int argc, ACE_TCHAR *argv[])
{
return ace_tmain_i (argc, argv);
}
int WINAPI WinMain (HINSTANCE hInstance, HINSTANCE hPrevInstance, LPWSTR lpCmdLine, int nCmdShow)
{
ACE_Main m;
return ace_os_wintmain_i (m, hInstance, hPrevInstance, lpCmdLine, nCmdShow);
}
int ace_tmain_i /*ACE_TMAIN end*/ ( int args, ACE_TCHAR* argv[])
{
int a = 0;
int b = 1;
a = a + b;
}
//end
WinMain -call-> ace_os_wintmain_i [进行ACE环境的初始] -call-> ACE_Main_Base::run() -call->ACE_Main::run_i() -call-> ace_tmain_i[运行我们自己的代码]
WinMain <-ret- ace_os_wintmain_i [释放ACE环境] <-ret- ACE_Main::run_i() <-ret- ace_tmain_i
还有,我上边列出来的ACE_TMAIN只是其中之一,ACE做了好几个程序入口函数的宏替换:
如:main,wmain
说明:
ACE对我们的程序入口,进行到替换. 在程序启动和退出时,做了一些初始化工作。
其中最主要的工作就是: ACE::init() 和 ACE::fini();
再说明我MFC吧,MFC将程序入口,包在了CWinApp类中。所以ACE没有办法对其进行修改。
也就没有办法在MFC中做一些“自动”的初始化和释放工作; 那么这个工作就只有我们自己完成了...
所以在MFC的工程中使用ACE,就得自己调用初始化: ACE::init(); 和释放:ACE::fini()
如果不调!!!呵呵。那就只好等着出错了。:)
转贴地址:http://blog.sina.com.cn/s/blog_54c746f4010009cm.html