Windows入口点函数

1.简介

Windows支持两种类型的应用程序:GUI程序和CUI程序,即图形用户界面和控制台用户界面。

Windows应有程序必须有一个入口点函数,应用程序开始运行时,这个函数会被调用。以下为应用程序类型和入口点啊函数:

应用程序类型 入口点函数(入口) 嵌入可执行文件的启动函数
处理ANSI字符和字符串的GUI应用程序 _tWinMain(WinMain) WinMainCRTStartup
处理Unicode字符和字符串的GUI应用程序 _tWinMain(wWinMain) wWinMainCRTStartup
处理ANSI字符和字符串的CUI应用程序 _tmain(Main) mainCRTStartup
处理Unicode字符和字符串的CUI应用程序 _tmain(wMain) wmainCRTStartup

操作系统实际并不调用我们所写的入口点函数。它会调用由C/C++运行库实现并在链接时使用-entry:命令行选项来设置的一个C/C++运行时启动函数。该函数将初始化C/C++运行库,使我们能调用malloc和free之类的函数。它还确保了在我们的代码开始执行之前,我们声明的任何全局和静态C++对象都被正确地构造。

所有的C/C++运行库启动函数所做的事情基本都是一样的,用途简单总结如下:

  • 获取指向新进程的完整命令行的一个指针
  • 获取指向新进程的环境变量的一个指针
  • 初始化C/C++运行库的全局变量。如果包含了StdLib.h,我们的代码就可以访问这些变量。
  • 初始化C运行库内存分配函数(malloc和calloc)和其他底层I/O例程使用的堆
  • 调用所有全局和静态C++类对象的构造函数

在完成了所有的这些初始化操作之后,C/C++启动函数就会调用应用程先生的入口点函数

当入口点函数返回之后,启动函数将调用C运行库函数exit,向其传递返回值(nMainRetVal)。exit函数执行以下任务:

  • 调用_onexit函数调用所注册的任何一个函数。
  • 调用所有全局和静态C++类对象的析构函数。
  • 在DEBUG生成中,如果设置了_CRTDBG_LEAK_CHECK_DF标志,就通过调用_CrtDumpMemoryLeaks函数来生成内存泄漏报告。
  • 调用操作系统的ExitProcess函数,向其传入nMainRetVal。这会导致操作系统杀死我们的进程,并设置它的退出代码。

2.参数简介

int APIENTRY wWinMain(_In_ HINSTANCE hInstance,
                     _In_opt_ HINSTANCE hPrevInstance,
                     _In_ LPWSTR    lpCmdLine,
                     _In_ int       nCmdShow)
{
    ....
}

上面是我生成一个GUI程序的main函数。

HINSTANCE hInstance:称为“实例句柄”或“模块句柄”。操作系统使用此值在内存中加载可执行文件时标识可执行文件 (EXE) 。 某些Windows函数需要实例句柄,例如加载图标或位图。

HINSTANCE hPrevInstance:C/C++运行库启动代码总是向此参数传递NULL,该参数用于16位操作系统,因而仍然保留,目的只是方便我们移植16位Windows应该程序。

LPWSTR lpCmdLine:C运行库启动代码开始执行一个GUI应用程序时,会调用Windows函数GetCommandLine来获取进程的完整命令行,忽略可执行文件的名称,然后将指向命令行剩余的部分的一个指针传给此参数。

 int nCmdShow:是一个标志,指示主应用程序窗口是最小化、最大化还是正常显示。

3.解析命令行

使用函数CommandLineToArgvW()解析,CommandLineToArgvW在内部分配内存,许多应用程序不会释放这块内存——它们依靠操作系统在进程终止时释放这块内存。如果想要自己释放内存,正确的做法就是调用HeapFree。

你可能感兴趣的:(Windows核心编程,c++,开发语言,windows,入口函数)