我应该使用 /MD 还是 /MT 进行编译?

发布于 2024-07-17 17:18:42 字数 334 浏览 7 评论 0原文

在 Visual Studio 中,有编译标志 /MD 和 /MT,可让您选择所需的 C 运行时库类型。

我了解实现上的差异,但我仍然不确定该使用哪一个。 有什么优点/缺点?

我听说 /MD 的一个优点是,这允许某人更新运行时(例如修补安全问题),并且我的应用程序将从这次更新中受益。 尽管对我来说,这几乎看起来像是一个非功能:我不希望人们在不允许我测试新版本的情况下更改我的运行时!

我很好奇的一些事情:

  • 这会如何影响构建时间? (大概 /MT 慢一点?)
  • 还有什么其他影响?
  • 大多数人使用哪一种?

In Visual Studio, there's the compile flags /MD and /MT which let you choose which kind of C runtime library you want.

I understand the difference in implementation, but I'm still not sure which one to use. What are the pros/cons?

One advantage to /MD that I've heard, is that this allows someone to update the runtime, (like maybe patch a security problem) and my app will benefit from this update. Although to me, this almost seems like a non-feature: I don't want people changing my runtime without allowing me to test against the new version!

Some things I am curious about:

  • How would this affect build times? (presumably /MT is a little slower?)
  • What are the other implications?
  • Which one do most people use?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(7

烟燃烟灭 2024-07-24 17:18:42

通过与 /MD 动态链接,

  • 您可以接触到系统更新(无论好坏),
  • 您的可执行文件可以更小(因为它没有嵌入其中的库),并且
  • 我相信至少DLL 在所有主动使用它的进程之间共享(减少消耗的 RAM 总量)。

我还发现,在实践中,当使用使用不同运行时选项构建的静态链接的第 3 方纯二进制库时,主应用程序中的 /MT 往往比 /MD 更容易引起冲突(因为您如果 C 运行时多次静态链接,就会遇到麻烦,特别是如果它们是不同的版本)。

By dynamically linking with /MD,

  • you are exposed to system updates (for good or ill),
  • your executable can be smaller (since it doesn't have the library embedded in it), and
  • I believe that at very least the code segment of a DLL is shared amongst all processes that are actively using it (reducing the total amount of RAM consumed).

I've also found that in practice, when working with statically-linked 3rd-party binary-only libraries that have been built with different runtime options, /MT in the main application tends to cause conflicts much more often than /MD (because you'll run into trouble if the C runtime is statically-linked multiple times, especially if they are different versions).

Bonjour°[大白 2024-07-24 17:18:42

如果您使用 DLL,那么您应该选择动态链接的 CRT (/MD)。

如果您对 .exe 和所有 .dll 使用动态 CRT,那么它们都将共享 CRT 的单个实现 - 这意味着它们都将共享单个 CRT 堆,并且可以在一个 .exe/.dll 中释放分配的内存其他。

如果您对 .exe 和所有 .dll 使用静态 CRT,那么它们都将获得 CRT 的单独副本 - 这意味着它们都将使用自己的 CRT 堆,因此必须在其所在的同一模块中释放内存被分配了。 您还将遭受代码膨胀(CRT 的多个副本)和过多的运行时开销(每个堆从操作系统分配内存以跟踪其状态,并且开销可能很明显)。

If you are using DLLs then you should go for the dynamically linked CRT (/MD).

If you use the dynamic CRT for your .exe and all .dlls then they will all share a single implementation of the CRT - which means they will all share a single CRT heap and memory allocated in one .exe/.dll can be freed in another.

If you use the static CRT for your .exe and all .dlls then they'll all get a seperate copy of the CRT - which means they'll all use their own CRT heap so memory must be freed in the same module in which it was allocated. You'll also suffer from code bloat (multiple copies of the CRT) and excess runtime overhead (each heap allocates memory from the OS to keep track of its state, and the overhead can be noticeable).

甚是思念 2024-07-24 17:18:42

我相信通过 Visual Studio 构建的项目的默认值是 /MD。

如果您使用 /MT,您的可执行文件将不依赖于目标系统上存在的 DLL。 如果您将其包装在安装程序中,则可能不会成为问题,并且您可以采用任何一种方式。

我自己使用 /MT,这样我就可以忽略整个 DLL 混乱。

PS 作为 先生。 Fooz 指出,保持一致至关重要。 如果您要链接其他库,则需要使用与它们相同的选项。 如果您使用第三方 DLL,则几乎可以肯定您需要使用运行时库的 DLL 版本。

I believe the default for projects built through Visual Studio is /MD.

If you use /MT, your executable won't depend on a DLL being present on the target system. If you're wrapping this in an installer, it probably won't be an issue and you can go either way.

I use /MT myself, so that I can ignore the whole DLL mess.

P.S. As Mr. Fooz points out, it's vital to be consistent. If you're linking with other libraries, you need to use the same option they do. If you're using a third party DLL, it's almost certain that you'll need to use the DLL version of the runtime library.

回首观望 2024-07-24 17:18:42

我更喜欢与 /MT 静态链接。

即使您确实使用 /MD 获得了较小的可执行文件,您仍然需要提供一堆 DLL 以确保用户获得运行程序的正确版本。 最后,您的安装程序将比与 /MT 链接时更大。

更糟糕的是,如果您选择将运行时库放在 Windows 目录中,那么用户迟早会安装具有不同库的新应用程序,如果运气不好,可能会破坏您的应用程序。

I prefer to link statically with /MT.

Even though you do get a smaller executable with /MD, you still have to ship a bunch of DLLs to make sure the user gets the right version for running your program. And in the end your installer is going to be BIGGER than when linking with /MT.

What's even worse, if you choose to put your runtime libraries in the windows directory, sooner or later the user is going to install a new application with different libraries and, with any bad luck, break your application.

梦在夏天 2024-07-24 17:18:42

使用 /MD 时您将遇到的问题是 CRT 的目标版本可能不在您的用户计算机上(特别是如果您使用的是最新版本的 Visual Studio 而用户使用的是较旧的操作系统)。

在这种情况下,您必须弄清楚如何将正确的版本安装到他们的机器上。

The problem you will run into with /MD is that the target version of the CRT may not be on your users machine (especially if you're using the latest version of Visual Studio and the user has an older operating system).

In that case you have to figure out how to get the right version onto their machine.

初吻给了烟 2024-07-24 17:18:42

来自 http://msdn.microsoft.com/en-us /library/2kzt1wy3(VS.71).aspx

/MT 定义 _MT,以便从标准头 (.h) 文件中选择运行时例程的多线程特定版本。 此选项还会导致编译器将库名称 LIBCMT.lib 放入 .obj 文件中,以便链接器将使用 LIBCMT.lib 来解析外部符号。 创建多线程程序需要 /MT 或 /MD(或其调试等效项 /MTd 或 /MDd)。

/MD 定义 _MT 和 _DLL,以便从标准 .h 文件中选择运行时例程的多线程和 DLL 特定版本。 此选项还会导致编译器将库名称 MSVCRT.lib 放入 .obj 文件中。

使用此选项编译的应用程序静态链接到 MSVCRT.lib。 该库提供了一层代码,允许链接器解析外部引用。 实际工作代码包含在 MSVCR71.DLL 中,与 MSVCRT.lib 链接的应用程序必须在运行时可用。

当 /MD 与定义的 _STATIC_CPPLIB (/D_STATIC_CPPLIB) 一起使用时,它将导致应用程序链接到静态多线程标准 C++ 库 (libcpmt.lib) 而不是动态版本 (msvcprt.lib),同时仍动态链接到通过 msvcrt.lib 主 CRT。

因此,如果我正确解释它,则 /MT 静态链接,/MD 动态链接。

from http://msdn.microsoft.com/en-us/library/2kzt1wy3(VS.71).aspx:

/MT Defines _MT so that multithread-specific versions of the run-time routines are selected from the standard header (.h) files. This option also causes the compiler to place the library name LIBCMT.lib into the .obj file so that the linker will use LIBCMT.lib to resolve external symbols. Either /MT or /MD (or their debug equivalents /MTd or /MDd) is required to create multithreaded programs.

/MD Defines _MT and _DLL so that both multithread- and DLL-specific versions of the run-time routines are selected from the standard .h files. This option also causes the compiler to place the library name MSVCRT.lib into the .obj file.

Applications compiled with this option are statically linked to MSVCRT.lib. This library provides a layer of code that allows the linker to resolve external references. The actual working code is contained in MSVCR71.DLL, which must be available at run time to applications linked with MSVCRT.lib.

When /MD is used with _STATIC_CPPLIB defined (/D_STATIC_CPPLIB) it will cause the application to link with the static multithread Standard C++ Library (libcpmt.lib) instead of the dynamic version (msvcprt.lib) while still dynamically linking to the main CRT via msvcrt.lib.

So if I am interpreting it correctly then /MT links statically and /MD links dynamically.

那伤。 2024-07-24 17:18:42

如果您正在构建使用其他 dll 或库的可执行文件,则首选 /MD 选项,因为这样所有组件将共享相同的库。 当然,此选项应该匹配所有涉及的模块,即 dll/lib/exe。

如果您的可执行文件不使用任何 lib 或 dll,那么任何人都可以调用。 现在差别已经不大了,因为共享方面还没有发挥作用。

因此,也许您可​​以使用 /MT 启动应用程序,因为没有其他令人信服的理由,但是当需要添加 lib 或 dll 时,您可以将其更改为 /MD ,这很容易。

If you are building executable that uses other dlls or libs than /MD option is preferred because that way all the components will be sharing same library. Of course this option should match for all the modules involved i.e dll/lib/exe.

If your executable doesn't uses any lib or dll than its anyone's call. The difference is not too much now because the sharing aspect is not into play.

So maybe you can start the application with /MT since there is no compelling reason otherwise but when its time to add a lib or dll, you can change it to /MD with that of the lib/dll which is easy.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文