一键-apple safari

microsoft visual c runtime library
2023年4月2日发(作者:同步盘)

CC++中CRT表⽰什么意思?

参考⾄:/chio/archive/2007/11/26/

CRT原先是指Microsoft开发的CRuntimeLibrary,⽤于操作系统的开发及运⾏。后来在此基础上开发了C++Runtime

Library,所以现在CRT是指Microsoft开发的C/C++RuntimeLibrary。在VC的CRT/SRC⽬录下,可以看到CRT的源码,不仅

有C的,也有C++的。

CRT原先的⽬的就是⽀持操作系统的运⾏。因为Windows操作系统除汇编部分外,都是⽤C/C++编写的,所以内核及许多

关键服务都在CRT上运⾏(它们都采⽤dll技术动态链接)。此外,⽤VC编写的C/C++程序也⽤到它们(可以动态链接,也可

以静态链接,前者运⾏时需要系统中已安装CRT的dll,后者不需要)。可以说,CRT就是Microsoft编写Windows时使⽤的低

层类库。然后,它⼜被当作C++标准库的⼀个实现包含在了VC系列中;我们在VC中使⽤的C++标准库,其实就是CRT的⼀个

真⼦集(少了C++标准所不包含的代码,特别是⼤量的低层C代码)

⾄于CRT与WINDOWSAPI的关系,与许多⼈理解的相反,WINDOWSAPI作为Windows的⼀部份,是在CRT的基础上开

发的。你可以将Windows(及其API)看作⼀个项⽬,⽽这个项⽬使⽤的语⾔是汇编/C/C++,使⽤的类库就是CRT。所以,

离开CRT,WindowsAPI也⽆法使⽤的。

C++标准,是C++的通⽤语⾔规范,指导所有C++使⽤者。⽽CRT的其中⼀部分可以看作是Microsoft开发的⼀个C++标准

库实现(其实也确实如此,Microsoft在开发CRT时,参考了正在标准化过程中的C++语⾔规范)。它与C++标准有⼀定的差

距,部分原因是,在C++没有完成标准化之前,CRT已经开发并投⼊使⽤了。为了向下兼容以前的Windows代码,早期的

CRT与C++标准总有⼀定的差距。但是CRT确实在不断的改进中。VC6带的CRT与C++标准还有⽐较⼤的差距,⽽VC8的⼏

乎完全符合C++标准了。

综上,CRT(Microsoft'sC/C++RuntimeLibrary)的⼀个真⼦集(主要是C++RuntimeLibrary)是⼀个符合(或⾄少是

企图符合)C++标准的C++库。⽽WindowsAPI(以及Windows的其他许多部分)都是在CRT的基础上开发的。

除了以上介绍的,在使⽤CRT的过程中,还需要了解的是:

1、CRT的⼀些组成部分也调⽤了WindowsAPI。这可能就是有⼈认为CRT是建⽴的WindowsAPI基础上的原因。但是实

际上,这⼀部分剥离CRT没有任何的问题。只不过Microsoft将在Windows平台上可以使⽤的C/C++低层库都加⼊到CRT中。

因此,CRT中很⼤⼀部分是操作系统平台⽆关的(原始的CRT),是开发Windows本⾝及其上⼀切的基础。它们也可以作为

⼀个C/C++库在其他操作系统平台上使⽤。还有⼀部分,则是和Windows紧密绑定的,调⽤WindowsAPI来实现的,可以看

作扩展的CRT。之所以将这两部分放在⼀起,是因为它们都是开发Windows操作系统所需要的,也因为它们也都是Windows

平台上的C/C++程序员所需要的。这种复杂关系是Microsoft的⼈为因素造成的,不能因此认为CRT是建⽴在Windows或

WindowsAPI基础上的。

2、CRT的⼤部分内容是跨硬件平台的,但是也有⼀些部分,是直接⽤汇编写成、基于硬件平台、并根据特定硬件平台做

的优化(⽽不是将⽣成机器码的责任完全交给编译器)。如早期对Indel的x32做了优化,现在由加⼊对AMD64的优化,这部

分则是不跨硬件平台的。

关于ATL

ATL是建⽴在CRT上的,如果你看了ATL的源码就知道了。⾄于不⽤链接,是因为ATL库静态链接了CRT,所以它可以在

CRT之外运⾏。类似这样的误解在于混淆了作为低层基本库的CRT和作为产品⽽附带在VC中的CRT。虽然这两者是同样的代

码,但是概念是不⼀样的。

在编写操作系统时,你需要⼀个合适的低层库,以便完成⼀些基本的、多次重复的⼯作。于是,就有了CRT。在最低层的

时候,根本连dll这个概念都没有的,所以CRT的源代码只能做成lib,被静态链接。然后,随着Windows越做越复

杂,Microsoft提出了API的概念,它提供Windows开发者⼀组接⼝,可以直接操作Windows,这就是WindowsAPI了。当

然,WindowsAPI也是在CRT之上编写的。

接着,Microsoft想给予C/C++程序员以⾜够的⽀持,除了原始CRT之外,还要增加在Windows平台上编程所特有的东西,

如thread等等。这些东西都是和平台相关的,只能建⽴在WindowsAPI上。⽽这些新增内容,也被放进了CRT中。此

时,CRT不仅仅包含最低层平台⽆关的代码,还包括平台相关的部分。如你调⽤CRT的_beginthread,其实内部调⽤了

WindowsAPI的CreateThread。加⼊这些东西后,CRT仍然被⽤作编写操作系统;但是显然,那些调⽤了WindowsAPI的部

分已经失去移值性了。

然后,CRT被封装成产品,随编译器⼀起发布。此时CRT产品的LIB和DLL都是Windows格式的,你不能在Windows以外

的平台上使⽤EXE或DLL吧,这就是CRT和CRT产品的区别。WindowsAPI的产品,或是Windows的其他许多组成部分也是

⼀些LIB/DLL⽂件,这些都是表⾯的东西,是与Windows绑定在⼀起的。但是,如果你认为是先有Windows或WindowsAPI,

才有CRT的,那你就本末倒置了。除⾮你对CRT的定义就是那些LIB/DLL产品,⽽不包括⽤来产⽣它们的代码。

就象C++编译器⽤来编译⽤C++写的编译器⾃⾝⼀样,Windows(及其上的编译器)⽤来作为平台开发和编译CRT,并也

⽤CRT来写Windows⾃⾝(当然第⼀个CRT和第⼀个⽤来编译Windows的编译器不是在Windows上开发的)。就象“我”也可

以先写⼀个类库,然后在它基础上写⼀个操作系统,在这个操作系统上进⼀步扩充这个类库,然后将它配合编译器发布出去,

发展⼀些我的操作系统的⽀持者,顺便再赚点收⼊。或者以另⼀种模式发布另⼀个库(只是我在原来那个库上开发的⼀个产

品,由于我独⽴地发布这个新库,许多⼈会不知道这个新库与旧库的关系。这很好,因为编程本⾝就是尽量隐藏细节,尽量做

到对使⽤者透明的),吸引不同风格的开发者。这样我的付出得到了最⼤的回报——由于我没有发布操作系统的源代码,所以

许多⽤户认为我不仅做了系统,还做了编译器,还开发了⼀个类库。做了那么多事,回报是应该的。其实他们不知道,类库是

编写操作系统所必须的,编译器也是必须的,这些必须的东西却可以在操作系统之外获得更多的回报,真是太完美了!这是什

么?这就是商业精神!当然这些误解对我是有好处的,我就不必到处宣扬真相了。反正我把类库的源码都发布了,也没有骗过

⼈吧。我不过是在那个原始类库中加进了⼀些与我的操作系统相关的东西,以⽅便在我的系统上编写程序的⼈们,这是我的好

⼼吧;⾄于有⼈可能产⽣进⼀步的误解,就不是我需要考虑的了……

所以还是看看CRT的源码吧——看看那些针对硬件平台的汇编;看看VC的标准C++库和CRT关系;再看看其他操作系统

的源代码,想想CRT中的哪些部分可以⽀持⽤来写操作系统,⽽如果我⾃⼰写系统,⼜需要哪些东西;甚⾄你可以看看DOS

的源代码,想想和CRT的相似性,以及历史渊源。可惜不能看到Windows的源代码,否则⼀切就清楚了。

最后再说⼀句,C++当然不是Microsoft的专利。但是Microsoft选择了C++,并取得了成功,这是肯定的了:象CRT,象

VC,象Windows,象Office,象SQLServer......这⼀⽅⾯说明了C++的优势,⼀⽅⾯也是Microsoft⾃⾝的因素在起作⽤。然

后,它当然要紧抓C++的⼤旗,⼤⼒宣扬它⾃⼰的C++,并排斥其他的C++。这就是帝国的“风范”了。所以对Microsoft,总是

即恨且爱,总希望哪天它会良⼼发现——当然这只是幻想罢了。不过,肯定该肯定的,否定该否定的,总是应该的。但就产品

⽽⾔,Microsoft不是最好的,但⼤多都是最成功的,在看到它的不⾜的同时,也要看到它的优点。存在的即使不是合理的,也

⼀定有它的合理性。所以,不能简单⽤⼀两句话评价Microsoft及它的成功。惟有⼀点是可以肯定的,它决定选择C++,真是

太英明了!

转载⾄:/question/

CRT全称:Visual

C++CRunTimeLib就是C运⾏时库。

注:以下内容部分引⾃CSND中相关讨论的帖⼦,并结合⾃⼰的理解整理⽽成。仅供参考。

1)运⾏时库就是Crun-timelibrary,是C⽽⾮C++语⾔世界的概念:取这个名字就是因为你的C程序运⾏时需要这些库中的函

数.

2)C语⾔是所谓的“⼩内核”语⾔,就其语⾔本⾝来说很⼩(不多的关键字,程序流程控制,数据类型等);所以,C语⾔内核

开发出来之后,DennisRitchie和BrianKernighan就⽤C本⾝重写了90%以上的UNIX系统函数,并且把其中最常⽤的部

分独⽴出来,形成头⽂件和对应的LIBRARY,Crun-timelibrary就是这样形成的。

3)随后,随着C语⾔的流⾏,各个C编译器的⽣产商/个体/团体都遵循⽼的传统,在不同平台上都有相对应的Standard

Library,但⼤部分实现都是与各个平台有关的。由于各个C编译器对C的⽀持和理解有很多分歧和微妙的差别,所以就有了

ANSIC;ANSIC(主观意图上)详细的规定了C语⾔各个要素的具体含义和编译器实现要求,引进了新的函数声明⽅式,

同时订⽴了StandardLibrary的标准形式。所以C运⾏时库由编译器⽣产商提供。⾄于由其他⼚商/个⼈/团体提供的头⽂件和

库函数,应当称为第三⽅C运⾏库(ThirdpartyCrun-timelibraries)。

4)Crun-timelibrary⾥⾯含有初始化代码,还有错误处理代码(例如dividebyzero处理)。你写的程序可以没有math库,程序照

样运⾏,只是不能处理复杂的数学运算,不过如果没有了Crun-time库,main()就不会被调⽤,exit()也不能被响应。因为C

run-timelibrary包含了C程序运⾏的最基本和最常⽤的函数。

5)到了C++世界⾥,有另外⼀个概念:StandardC++Library,它包括了上⾯所说的Crun-timelibrary和STL。包含Crun-time

library的原因很明显,C++是C的超集,没有理由再重新来⼀个C++针对C++加⼊的StandardC++

Library主要包括:,和

6)Windows环境下,VC提供的Crun-timelibrary⼜分为动态运⾏时库和静态运⾏时库。

动态运⾏时库主要是DLL库⽂件(debugbuild),对应的Importlibrary⽂件是

(debugbuild)

静态运⾏时库(release版)对应的主要⽂件是:

(Singlethreadstaticlibrary,retailversion)

(Multithreadstaticlibrary,retailversion)

提供⼏千个C函数,即使是像printf这么低级的函数都在⾥。其实你的程序运⾏时,很⼤⼀部分时间时在这

些运⾏库⾥运⾏。在你的程序(release版)被编译时,VC会根据你的编译选项(单线程、多线程或DLL)⾃动将相应的运⾏时库⽂

件(,或)链接进来。

编译时到底哪个Crun-timelibrary联⼊你的程序取决于编译选项:

/MD,/ML,/MT,/LD(UseRun-TimeLibrary)

你可以VC中通过以下⽅法设置选择哪个Crun-timelibrary联⼊你的程序:

Tofindtheseoptionsinthedevelopmentenvironment,icktheC/C++tab,and

UseRun-TimeLibrarydrop-downbox.

从程序可移植性考虑,如果两函数都可完成⼀种功能,选运⾏时库函数好,因为各个C编译器的⽣产商对标准CRun-timelibrary

提供了统⼀的⽀持.

更多推荐

microsoft visual c runtime library