-
Notifications
You must be signed in to change notification settings - Fork 6.1k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[scripts] Remove a redundant manual /D_DEBUG from CMAKE_<LANG>_FLAGS_DEBUG #34123
base: master
Are you sure you want to change the base?
Conversation
…DEBUG We're already setting ${VCPKG_CRT_LINK_FLAG_PREFIX}d here, which expands to either /MDd or /MTd. When the compiler is given either of these options, it implicitly sets the _DEBUG define. Therefore, explicitly passing /D_DEBUG in these configs is redundant. Explicitly setting /D_DEBUG among these flags can be problematic; CMake projects that target CMake 3.15 or newer, with the policy CMP0091 set to NEW, may control the CRT to use via the variable CMAKE_MSVC_RUNTIME_LIBRARY. If this variable is overridden by the projects, setting it to a non-debug runtime library, we'd still have the explicitly set /D_DEBUG define left, which can cause conflicts. For such projects that do use the new policy behaviour of CMP0091, explicitly setting the CRT selection options in CMAKE_<LANG>_FLAGS_<CONFIG> isn't ideal - but as long as we don't know that all projects use the new policy behaviour, we might need to keep setting the CRT selection options (as long as we feel the need to set the CMAKE_<LANG>_FLAGS_<CONFIG> variables at all). For the cases where such projects override CMAKE_MSVC_RUNTIME_LIBRARY internally, it would only cause a mostly benign warning like "cl : Command line warning D9025 : overriding '/MDd' with '/MT'".
Some additional references; https://learn.microsoft.com/en-us/cpp/c-runtime-library/debug?view=msvc-170 explicitly says:
Therefore, This redundant define has passed through many layers of changes and can be traced back to being added initially in eba9f6a. |
But it is also totally unnecessary to remove it.
That would leave vcpkg in an invalid state either way. |
Currently, debug builds of llvm-project via vcpkg are allegedly broken, as reported by a user. This, because llvm-project switched to But as vcpkg has injected
Can you elaborate on what you mean here - what is in an invalid state? The regular executables that are built within llvm-project do honor the CRT that was chosen by the user of the build (vcpkg). The project internal CRT override only affects one of LLVM's runtime libraries that may be used by code compiled by LLVM. |
Just patch that line out. I assume compiler-rt only cares about Release builds. |
FWIW; #34117 probably doesn't work as such. Even if vcpkg itself might require CMake 3.15, the individual projects that are built might be targeting an older CMake version (or with a project targeting a newer version, it could still set the policy CMP0091 to OLD). So those projects would expect getting the CRT choice options ( However, whenever passing a debug CRT flag like |
This reverts one part of commit 9f4dfcb, with a modified comment added about the code. Ideally, this would only be reinstated temporarily - but given the situation in vcpkg, it looks likely that they would keep passing the duplicate options for quite some time. The conflicting CRT choice usually are benign but only would cause warnings about one option overriding the other, if passing e.g. "/MDd /MT". However when vcpkg currently sets these options in CMAKE_*_FLAGS_DEBUG, it passes the redundant option /D_DEBUG; thus the compiler finally ends up with e.g. "/D_DEBUG /MDd /MT", which has the effect of defining _DEBUG while using a release mode CRT, which allegedly breaks the build. There's a PR up for removing this redundant /D_DEBUG option in vcpkg in microsoft/vcpkg#34123. With that in place, this change wouldn't be strictly needed.
…S* (#67935) This reverts one part of commit 9f4dfcb, with a modified comment added about the code. Ideally, this would only be reinstated temporarily - but given the situation in vcpkg, it looks likely that they would keep passing the duplicate options for quite some time. The conflicting CRT choice usually are benign but only would cause warnings about one option overriding the other, if passing e.g. "/MDd /MT". However when vcpkg currently sets these options in CMAKE_*_FLAGS_DEBUG, it passes the redundant option /D_DEBUG; thus the compiler finally ends up with e.g. "/D_DEBUG /MDd /MT", which has the effect of defining _DEBUG while using a release mode CRT, which allegedly breaks the build. There's a PR up for removing this redundant /D_DEBUG option in vcpkg in microsoft/vcpkg#34123. With that in place, this change wouldn't be strictly needed.
…S* (#67935) This reverts one part of commit 9f4dfcb, with a modified comment added about the code. Ideally, this would only be reinstated temporarily - but given the situation in vcpkg, it looks likely that they would keep passing the duplicate options for quite some time. The conflicting CRT choice usually are benign but only would cause warnings about one option overriding the other, if passing e.g. "/MDd /MT". However when vcpkg currently sets these options in CMAKE_*_FLAGS_DEBUG, it passes the redundant option /D_DEBUG; thus the compiler finally ends up with e.g. "/D_DEBUG /MDd /MT", which has the effect of defining _DEBUG while using a release mode CRT, which allegedly breaks the build. There's a PR up for removing this redundant /D_DEBUG option in vcpkg in microsoft/vcpkg#34123. With that in place, this change wouldn't be strictly needed. (cherry picked from commit 7bc09a471fbc274d8632d1379d4134bec63fecc4)
…S* (#67935) This reverts one part of commit 9f4dfcb, with a modified comment added about the code. Ideally, this would only be reinstated temporarily - but given the situation in vcpkg, it looks likely that they would keep passing the duplicate options for quite some time. The conflicting CRT choice usually are benign but only would cause warnings about one option overriding the other, if passing e.g. "/MDd /MT". However when vcpkg currently sets these options in CMAKE_*_FLAGS_DEBUG, it passes the redundant option /D_DEBUG; thus the compiler finally ends up with e.g. "/D_DEBUG /MDd /MT", which has the effect of defining _DEBUG while using a release mode CRT, which allegedly breaks the build. There's a PR up for removing this redundant /D_DEBUG option in vcpkg in microsoft/vcpkg#34123. With that in place, this change wouldn't be strictly needed. (cherry picked from commit 7bc09a471fbc274d8632d1379d4134bec63fecc4)
Libraries distributed through vcpkg don't get to control this setting; this is controlled by the triplet via
We might also set @data-queue @vicroms @ras0219-msft @JavierMatosD and I discussed this today. I made the following pro/con list:
@JavierMatosD pointed out that we don't have a concrete problem this fixes (that is, my first bullet is theoretical) which argues to not take this. @ras0219-msft adds an additional con that this delays potential detection of the failure of mismatched runtimes. If a project is changing this setting in a way incompatible with We're going to close this for now. Please feel free to reopen the PR or submit a new PR if you have a real case this fixes. Thanks for your contribution to vcpkg and bringing this to our attention! |
Indeed, I understand that libraries in general don't get the freedom to do this. In this case, the libraries are upstream LLVM compiler-rt sanitizers; the sanitizers do more than enough low level CRT poking anyway, and their compatibility with other build configurations isn't up to whether vcpkg allows them to override this or not - the sanitizers, which are quite special libraries in all regards, override this anyway.
Actually, afaik vcpkg sets both
FWIW, that PR is an attempt to fix the same thing as this one does, but it assumes that every CMake project that vcpkg builds itself targets CMake 3.15 or newer, and there's certainly plenty of projects that still target a lower version of CMake, and thus
Thanks, I wasn't aware of the implication of that last point.
There is a real problem; @yurybura reported that LLVM 17.0.1 failed to build in vcpkg, when the vcpkg CRT choice had been switched to a debug CRT. (I'm not aware if there's a specific vcpkg issue filed for this detail, afaik this is part of a larger undertaking to update vcpkg to package LLVM 17.x.) I have temporarily worked around this on the LLVM side in llvm/llvm-project@7bc09a4 - by adding extra cleanup of
I feel this is a rather weak argument. There's plenty of other ways that one can set up a mismatch (e.g. switching between
There is a real issue: In LLVM, I would like to remove the temporary workaround from llvm/llvm-project@7bc09a4 which I have reinstated for the sake of vcpkg. But that's not possible as long as vcpkg forcibly injects |
Really for me it looks like these projects should be disabled for debug config? |
I think the specifics of what happened here need to be understood.
It sounds then like LLVM is trying to pick a CRT that does not match |
AFAIK the issue is what I've tried to summarize above; a debug build of LLVM 17.0.1 via vcpkg fails, as it forcibly injects If necessary, I think @yurybura can fill in with more details. Note that this issue no longer should be reproducible on 17.0.2, as I reinstated a workaround, in llvm/llvm-project@7bc09a4. But I wouldn't want that workaround to be permanent.
In general I would agree, but for this specific case - not really. And I guess this is the root issue to understand, in order to not dismiss the case as LLVM doing something wrong. I do understand that mixing/matching CRT choices among vcpkg libraries, in general, is doomed and not supported. However these are not regular libraries that are built as part of the vcpkg build, that other parts of vcpkg can link against and interact with directly. If you select a debug CRT via Let's explain the full scenario: Someone uses vcpkg to install Clang/LLVM. This Clang executable itself is built with the CRT choice set via vcpkg. Other vcpkg tools that use the LLVM libraries get those built with the same matching CRT choice. The user uses this Clang compiler to build their own private code, entirely outside of vcpkg's build system. They can use Clang to build their own code with any CRT choice, Now the sanitizer runtime libraries can come into play at this point. The other vcpkg packages/libraries won't interact with them as such. When the user uses Clang to build their own code, outside of vcpkg, and enables e.g. In order to produce these sanitizer libraries, that will work with all of the CRT choices that the end user might make, those libraries are built and linked carefully in a very specific way. And as part of that process, for building the set of sanitizer libraries that can work in all those conditions, they currently require that they can control exactly the CRT choice used for building them. |
@mstorsjo, thank you for detailed explanation. |
Unfortunately, it's not that simple. Even if you have CMake >= 3.15, if the project you're building has e.g. So in order to confidently pick between I agree that this probably isn't workable, so I agree that the only reasonable thing vcpkg can do at the moment is to pass the choice both ways. However the redundant |
Unfortunately, LLVM is doing something cursed but not doomed here. It's picking the linkage for the sanitizer runtime libraries, which are designed to work with any program CRT linkage configuration. The asan runtimes linked against the release DLL CRT do support asan instrumented programs that are linked with the debug dll or debug static CRTs. |
We're already setting
${VCPKG_CRT_LINK_FLAG_PREFIX}d
here, which expands to either/MDd
or/MTd
. When the compiler is given either of these options, it implicitly sets the_DEBUG
define. Therefore, explicitly passing/D_DEBUG
in these configs is redundant.Explicitly setting
/D_DEBUG
among these flags can be problematic; CMake projects that target CMake 3.15 or newer, with the policyCMP0091
set toNEW
, may control the CRT to use via the variableCMAKE_MSVC_RUNTIME_LIBRARY
. If this variable is overridden by the projects, setting it to a non-debug runtime library, we'd still have the explicitly set/D_DEBUG
define left, which can cause conflicts.For such projects that do use the new policy behaviour of
CMP0091
, explicitly setting the CRT selection options inCMAKE_<LANG>_FLAGS_<CONFIG>
isn't ideal - but as long as we don't know that all projects use the new policy behaviour, we might need to keep setting the CRT selection options (as long as we feel the need to set theCMAKE_<LANG>_FLAGS_<CONFIG>
variables at all).For the cases where such projects override
CMAKE_MSVC_RUNTIME_LIBRARY
internally, it would only cause a mostly benign warning likecl : Command line warning D9025 : overriding '/MDd' with '/MT'
.