Windows支持两种类型的应用程序:GUI和CUI程序。前者是Graphical
User Interface的简称,后者是Console User Interface的简称。
用VS创建一个项目的时候,IDE会设置各种链接器开关,使链接器将子系统(注1)的正确类型嵌入最终生成的可执行文件中。对于CUI程序,这个链接器开关是/SUBSYSTEM:CONSOLE,对于GUI程序,则是/SUBSYSTEM:WINDOWS。用户运行应用程序时,操作系统的加载程序会检查可执行文件映像的文件头,并获取这个子系统值。如果此值表明是一个CUI程序,加载程序会确保有一个可用的文本控制台窗口。如果是GUI程序,加载器就不会创建控制台窗口;相反,它只是加载这个程序,一定应用程序开始运行,操作系统就不再关心程序的界面是什么了。
Windows应用程序必须有一个入口函数,应用程序开始运行时,这个函数会被调用。C/C++开发人员可以使用以下两种入口点函数。
int WINAPI _tWinMain(
HINSTANCE
hInstanceExe,
HINSTANCE,
PTSTR
pszCmdLine,
int
nCmdShow);
int _tmain(
int
argc,
TCHAR
*argv[],
TCHAR
*envp[]);
注意,具体的符号取决于我们是否要使用Unicode字符串。操作系统实际并不调用我们所写的入口点函数,相反,它会调用由C/C++运行库实现并在连接时使用-entry:命令行选项来设置一个C/C++运行时启动函数。该函数将初始化C/C++运行库,使我们能调用malloc和free之类的函数。它还确保了在我们的代码开始执行之前,我们声明的任何全局和静态C++对象都被正确地构造。下表总结了源代码要实现什么入口点函数,以及每个入口点函数应该在什么时候使用。
应用程序类型
|
入口点函数
|
嵌入可执行文件的启动函数
|
处理ANSI字符和字符串的GUI应用程序
|
_tWinMain(WinMain)
|
WinMainCRTStartup
|
处理unicode字符和字符串的GUI程序
|
_tWinMain(wWinMain)
|
wWinMainCREStartup
|
处理ANSI字符和字符串的CUI程序
|
_tmain(Main)
|
mainCRTStartup
|
处理unicode字符和字符串的CUI程序
|
_tmain(Wmain)
|
wmainCRTStartup
|
在链接可执行文件时,链接器将选择正确的C/C++运行库启动函数,如果指定了/SUBSYSTEM:WINDOWS链接器开关,链接器就会寻找WinMain或wWinMain函数,如果这两个函数都没有找到,链接就会返回一个“unresolved external sumbol”错误,否则它将根据具体情况分别选择WinMainCRTStartup或者wWinMainCRTStartup。
类似的,如果指定了/SUBSYSTEM:CONSOLE链接器也遵循同样的规则。
一个鲜为人知的事实是,我们完全可以从自己的项目中移除/SUBSYSTEM链接器开关,一旦这样做,链接器就会自动判断应该为应用程序设置为哪个子系统。
所有C/C++运行库启动函数所做的事情基本都是一样的,区别在于他们要处理的是ANSI还是Unicode字符串;以及在初始化C运行库之后,他们调用的是哪一个入口函数。Visual C++自带了C运行库源码。可以在crtexe.c文件中找到4个启动函数的源码,这些启动函数的用途简单总结如下:
l 获取指向新进程的完整命令行的一个指针。
l 获取执行新进程的环境变量的一个指针。
l 初始化C/C++运行库的全局变量。如果包含了stdlib.h,我们的代码可以访问这些变量。下表总结了这些变量。
l 初始化C运行库的内存分配函数(malloc和calloc)和其他底层I/O例程使用的堆。
l 调用所有全局和静态C++类对象的构造函数。
变量名称
|
类型
|
描述和推荐使用的windows函数
|
_osver
|
unsigned
int
|
操作系统的构建版本号。例如:windows vista RTM为build 6000,所以_osver的值就是6000。请换用GetVersionEx
|
_winmajor
|
unsigned
int
|
以16进制表示的windows系统的主版本号,对于vista为6。请换用GetVersionEx
|
_winminor
|
unsigned
int
|
以16进制表示的windows系统的次版本号,对于vista为0。请换用GetVersionEx
|
_winver
|
unsigned
int
|
(_winmajor<<8)+_winminor。请换用GetVersionEx
|
_argc
|
unsigned
int
|
命令行上传递的参数个数。请换用GetCommandLine
|
_argv
_wargv
|
char
wchar_t
|
长度为_argc的一个数组,每一项指向一个命令行参数。请换用GetCommandLine
|
_environ
_wenviron
|
char
wchar_t
|
一个指针数组,数组中的每一项指向一个环境字符串。请换用GetEnvironmentStrings或GetEnvironmentVariable
|
_pgmptr
_wpgmptr
|
char
wchar_t
|
正在运行的程序的名称及其ANSI/Unicode完整路径。请换用GetModuleFileName,将NULL作为第一个参数传进去。
|
完成这些初始化工作以后,C/C++才会调用我们的入口函数。
入口函数返回后,启动函数将调用C运行库的exit函数,向其传递入口函数的返回值。Exit函数将执行以下操作:
l 调用_onexit函数调用所注册的任何一个函数。
l 调用所有全局和静态C++类对象的析构函数。
l 在DEBUG生成中,如果设置了_CRTDBG_LEAK_CHECK_DF标志,就通过调用_CrtDumpMemoryLeaks函数生成内存泄漏报告。
l 调用操作系统的ExitProcess函数,向其传递入口函数的返回值。这会导致操作系统杀死我们的进程,并设置它的退出代码。
注意,为了安全起见,Microsoft不赞成使用所有这些变量,因为使用了这些变量的代码可能会在C运行库初始化这些变量之前运行。
分享到:
相关推荐
### Windows Phone 7 应用程序生命周期:Tombstoning详解 #### 概述 Windows Phone 7 的应用程序生命周期管理是一套复杂而精细的机制,旨在优化用户体验和设备性能。在这一平台上,应用程序的生命周期受制于特定的...
熟悉Windows应用程序生命周期,包括窗口消息、事件处理和线程管理;还要了解如何使用Visual Studio进行项目管理和调试。 压缩包中的文件可能是模拟考试题库,包含了各种类型的题目,比如选择题、填空题和编程题,...
《MFC Windows应用程序设计》是任哲编著的关于Windows应用程序开发的专业教材,主要围绕Microsoft Foundation Classes (MFC) 库展开,该库是微软提供的一套C++类库,用于简化Windows API的使用,帮助开发者构建高效...
【Windows应用程序框架MFC】 MFC(Microsoft Foundation Classes)是微软提供的一套C++类库,主要用于简化Windows应用程序的开发。MFC将Windows API中的函数和数据封装为类,利用面向对象的特性如继承和多态,使得...
.NET 应用程序生命周期部署手册是一本详细的指南,旨在帮助开发者和系统管理员理解并执行.NET应用程序的完整生命周期,包括开发、测试、发布、部署以及维护等环节。这本手册覆盖了从项目创建到应用程序上线运行的每...
【第02章 WINDOWS应用程序.PPT】深入探讨了Windows应用程序的基础,包括应用程序的生命周期、窗口类、消息循环和消息处理。这一章的内容对于理解Windows程序如何响应用户交互至关重要。 【第03章 MFC应用程序框架....
它继承自CObject类,并且提供了与Windows应用程序生命周期相关的成员函数,如InitInstance和ExitInstance。 - **CWinThread类**:代表一个执行线程,MFC应用程序通常至少有一个主线程,即应用程序线程。CWinThread...
在Windows编程中,`WinMain`函数是应用程序的入口点,尤其在开发基于Windows操作系统的桌面应用程序时。这个函数替代了通常在...同时,`WinMain`函数也是理解Windows应用程序生命周期和事件驱动编程模式的一个起点。
- **CTestApp**: 应用程序类,负责管理应用程序生命周期,初始化资源等。 - **CMainFrame**: 主框架窗口类,用于管理主程序窗口,显示标题栏、工具栏、状态栏等,并处理窗口操作消息。 - **CTestDoc**: 文档类,...
### Windows应用程序编程指南知识点梳理 #### 一、系统概述 - **目标系统**: 本指南主要面向基于Hopen操作系统的应用程序开发。 - **系统特点**: Hopen操作系统是一种专门为嵌入式设备设计的操作系统,强调高性能...
5. **Windows应用程序生命周期**:从启动到关闭的过程,以及如何处理用户交互。 6. **.NET的资源管理**:如内存管理、异常处理和垃圾回收。 7. **文件和数据库访问**:使用.NET进行文件操作和连接SQL Server或其他...
MFC(Microsoft Foundation Classes)是微软提供的一个C++类库,它为开发者提供了构建Windows应用程序的框架。这套课程旨在帮助开发者掌握如何利用MFC高效地开发Windows桌面应用。 首先,第02章“WINDOWS应用程序”...
《MFC Windows程序设计(第二版)》是深入学习Microsoft Foundation Classes (MFC)库进行Windows应用程序开发的重要参考资料。MFC是微软为开发者提供的一套C++类库,它封装了Windows API,使得使用C++编写Windows应用...
### C++ & CLR (VS2015) 编写 Windows 窗体应用程序 #### 知识点一:理解CLR与C++ - **CLR(Common Language Runtime)**:是.NET框架的核心组件之一,提供了执行环境,使得开发人员能够用多种编程语言编写代码,...
### 安全开发生命周期(SDL)概览 #### 一、SDL概念 安全开发生命周期(SDL, Security Development Lifecycle)是一种旨在确保软件在各个开发阶段都融入了安全性考量的方法论。这种方法论着重于通过在软件开发早期阶段...
CWinApp类扩展了CObject类,并提供了与Windows应用程序生命周期相关的功能。 2. **CFrameWnd** 和 **CMDIFrameWnd**:它们是窗口框架类,用于创建顶级窗口,如MDI(多文档界面)或SDI(单文档界面)应用程序。...
4. Windows应用程序生命周期:了解从源代码到可执行文件的编译和链接过程,以及调试技巧。 对于初学者来说,通过研究这个项目,可以学习到基础的MFC应用开发流程,以及Visual Studio集成开发环境的使用,对提升C++...
1. MFC基础:介绍MFC的基本结构,如CWinApp、CWnd、CFrameWnd等核心类,以及它们在Windows应用程序生命周期中的角色。 2. 消息处理机制:详细解析MFC的消息映射和消息处理函数,如何通过消息队列和消息循环实现用户...