如何覆盖 Visual Studio 2017 社区的编译命令
我想用一个简单的 shell 脚本覆盖默认的 Visual Studio C++ 编译器.我想要的是捕获参数,例如文件名,并创建一些统计信息.但是我想完全覆盖编译过程 - 也就是说,我想从我的 shell 脚本中调用原始编译.
I would like to override the default Visual Studio C++ compiler with a simple shell script. What I want is to capture the arguments, such as file name, and create some statistics. However I want to override the compilation process completely - that is, I want to call the original compilation from my shell script.
我用谷歌搜索,但我发现的只是如何在项目中执行预构建和构建后脚本.那不是我想要的.
I googled but all I found was how to have pre-build and post-build scripts that execute within a project. That's not what I want.
我想在全球范围内改变这一点.我该怎么做?
I want to change this globally. How can I do it?
推荐答案
对于标准的 C++ 项目文件编译是通过调用 MsBuild 目标 名为 ClCompile
.请注意,还有一个名为 ClCompile 的 MsBuild Item 列出了实际的使用 C++ 源文件,通过在文本编辑器中打开 .vcxproj 可以很容易地看到这一点.因此,此 ClCompile 项用于 ClCompile 目标,并在其中传递给 CL
任务 依次调用 cl.exe
,实际编译器可执行文件.此代码可以在您使用的工具集的 Microsoft.CppCommon.targets 文件中找到,用于在 C:Program Files (x86)Microsoft Visual Studio2017Community 的 64 位机器上默认安装 VS2017 社区Common7IDEVCVCTargetsMicrosoft.CppCommon.targets.
For a standard C++ project file compilation is done by invoking the MsBuild Target named ClCompile
. Note there's also an MsBuild Item named ClCompile which lists the actual C++ source files used, this can be readily seen by opening your .vcxproj in a text editor. Consequently this ClCompile Item is used in the ClCompile Target, where it gets passed to the CL
Task which in turn will invoke cl.exe
, the actual compiler executable. This code for this can be found in the Microsoft.CppCommon.targets file for the toolset you use, for a default install of VS2017 community on a 64bit machine that is C:Program Files (x86)Microsoft Visual Studio2017CommunityCommon7IDEVCVCTargetsMicrosoft.CppCommon.targets.
这 3 个中的任何一个都可以用自定义版本覆盖,但是因为您认为仅替换磁盘上的 cl.exe 并不是最好的主意.
Any of those 3 could be overridden with a custom version however as you figured already just replacing cl.exe on disk isn't the best idea.
但是 CL 可以简单地通过覆盖 CLToolExe 和 CLToolPath 来使用任何可执行文件 属性.实际上:打开您的 .vcxproj 文件并添加
But CL can use any executable simply by overriding the CLToolExe and CLToolPath properties. Practically: open your .vcxproj file and add
<PropertyGroup>
<CLToolExe>mycl.exe</CLToolExe>
<CLToolPath>c:path omycompilerstub</CLToolPath>
</PropertyGroup>
一直到最后,在导入Microsoft.Cpp.targets的那一行之后;将调用 mycl.exe 而不是 cl.exe.如果您希望在您的机器上全局获得相同的效果,您可以将该 PropertyGroup 放在一个单独的 msbuild 文件中并将其保存在例如 C:Program Files (x86)Microsoft Visual Studio2017CommunityCommon7IDEVCVCTargetsPlatformsx64ImportAfterMyCustomImport.targets.该目录中的任何目标文件都将自动导入.
all the way at the end, after the line importing Microsoft.Cpp.targets; mycl.exe will be called instead of cl.exe. If you want the same effect globally on your machine, you'll put that PropertyGroup in a seperate msbuild file and save it in for example C:Program Files (x86)Microsoft Visual Studio2017CommunityCommon7IDEVCVCTargetsPlatformsx64ImportAfterMyCustomImport.targets. Any targets file in that directory will be imported automatically.
作为替代方案,您可以覆盖 ClCompile 目标或 CL 任务.不过,这更复杂,例如对于 ClCompile,您首先要复制 Microsoft.CppCommon.targets 中的整个实现,然后添加您需要的任何逻辑.优点是您可以直接访问例如源文件等,而无需解析命令行.例如,这将覆盖 ClCompile 并打印源文件并将它们传递给自定义可执行文件:
As an alternative you could override the ClCompile target or the CL task. That's more involved though, e.g. for ClCompile you'd start by copying the whole implementation found in Microsoft.CppCommon.targets and then add whatever logic you need. Advantage is you have direct access to e.g. source files etc without having to parse a command line. For example this would override ClCompile and print source files and pass them to a custom executable:
<Target Name="ClCompile"
Condition="'@(ClCompile)' != ''"
DependsOnTargets="SelectClCompile">
<Message Text="All the sources = @(ClCompile)"/>
<Exec Command="mycustom.exe @(ClCompile)" />
... <!--rest of implementation copied from Microsoft.CppCommon.targets goes here-->
</Target>
同样,这需要放在项目文件的末尾或 ImportAfter 目录中以进行全局覆盖.
Again, this needs to be put at the end of your project file or in the ImportAfter directory for global overriding.
相关文章