【问题标题】:MSBuild for projects with both native and managed project referencesMSBuild 适用于具有本机和托管项目引用的项目
【发布时间】:2011-10-07 23:54:51
【问题描述】:

我有一个包含几百个 C++ 和 C# 项目的解决方案。我不能使用 MSBuild 直接构建具有不同类型项目依赖项的任何单个项目,因为不同项目类型的有效配置 (Deubg/Release) 和平台 (Win32/AnyCPU/x64) 设置不同。

例如,如果我有一个依赖于 C# 项目“CsharpProj1”的 C++ 项目“CppProj1”,我无法通过在命令行中指定 Release/AnyCPU 来使用 MSBuild 编译 CppProj1,因为 CppProj1 会无法在未知平台类型上编译。同样,指定 Release/Win32 将导致 CsharpProj1 无法编译。 Visual Studio 通过在每个解决方案文件中存储配置/平台设置的映射来解决此问题,但使用 MSBuild 的一个巨大动机是将我的构建过程与 Visual Studio IDE 分离。有没有办法不使用VS解决方案来处理这个问题?

【问题讨论】:

    标签: visual-studio msbuild


    【解决方案1】:

    有很多方法可以做到这一点。 “MSBuild Trickery”一书(技巧 #19、#80、#104)的十几页内容对所有这些都进行了详尽的解释,但我将在这里总结基本机制。

    #80。定义您自己的解决方案机制

    #19。考虑使用标准扩展路径

    这些技巧讨论了 AdditionalProperties 元数据。为您的项目创建一个项目数组,并为 Platform 属性指定 AdditionalProperties 元数据,这些元数据将在使用 MSBuild 任务构建项目时使用。

    在构建的属性文件中...

    <ItemGroup>
       <Project Include="./Folder1/Project1.csproj" />
       <Project Include="./Folder2/Project2.vcxproj" />
       ...
    </ItemGroup>
    

    在构建目标中...

    <ItemGroup>
       <Project>
          <AdditionalProperties
             Condition="'%(Extension)' == '.csproj'">
             >Platform=AnyCPU</AdditionalProperties>
          <AdditionalProperties
             Condition="'%(Extension)' == '.vcxproj'">
             >Platform=Win32</AdditionalProperties>
       <Project>
    </ItemGroup>
    
    <MSBuild Projects=@(Project) ... />
    

    除此之外,您还可以添加 32 位和 64 位的检测。

    #104。如何为多种项目类型统一平台

    在一个通用的导入属性文件中,声明您自己的 $(__Platform) 属性,该属性派生自 $(Platform) 的值,类似于上述,它创建了一个“标准化”的“平台”概念以在项目的其余部分。这也适用于解决方案构建。

    <PropertyGroup>
       <__Platform
          Condition="'$(Platform)' == 'Win32'>Win32</__Platform>
       <__Platform
          Condition="'$(Platform)' == 'Win64'>Win64</__Platform>
       <__Platform
          Condition="'$(Platform)' == 'x32'>Win32</__Platform>
       <__Platform
          Condition="'$(Platform)' == 'x64'>Win64</__Platform>
    </PropertyGroup>
    <PropertyGroup
       Condition="'$(Platform)' == 'AnyCPU'">
       <__Platform
          Condition="'$(PROCESSOR_ARCHITECTURE)' == 'x86'>Win32</__Platform>
       ...etc...
    </PropertyGroup>
    

    ...然后稍后,对于不同的项目文件类型,使用此值进行自定义导入...

    <!-- for C# projects -->
    <PropertyGroup>
       <OutputPath>bin\$(__Platform).$(Configuration)\</OutputPath>
       <IntermediateOutputPath>obj\$(__Platform)...
    
    <!-- for C++ projects -->
    <PropertyGroup>
       <OutDir>bin\$(__Platform).$(Configuration)\</OutDir>
       <IntDir>obj\$(__Platform)...
    

    【讨论】:

      【解决方案2】:

      C++ 构建目标接受Win32x64$(Platform) 属性的值)。
      没关系,如果不需要AnyCPU

      我在两个项目中试过这个:C# 项目依赖于 C++ 项目,通过&lt;ProjectReference&gt;

      对于 C++,我使用以下包括:

      <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Targets" />
      

      对于 C#,我使用以下包括:

      <Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
      

      由于Microsoft.CSharp.targets 使用$(PlatformTarget) 为编译器指定平台,因此可以为C# 项目指定以下属性:

      <PropertyGroup>
          <PlatformTarget Condition="'$(Platform)' == 'Win32'">x86</PlatformTarget>
          <PlatformTarget Condition="'$(Platform)' == 'x64'">x64</PlatformTarget>
      </PropertyGroup>
      

      这是为了将正确的参数传递给命令行编译器。详情请参考/platform (C# Compiler Options)

      事实上,对于 C++ 和 C# 解决方案,$(Platform) 属性可以与值 Win32x64 一起使用

      【讨论】:

        猜你喜欢
        • 2018-09-07
        • 2021-12-04
        • 1970-01-01
        • 2012-06-26
        • 1970-01-01
        • 1970-01-01
        • 2011-11-21
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多