forked from dotnet/runtime
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathresolveContract.targets
180 lines (153 loc) · 11.6 KB
/
resolveContract.targets
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
<Project>
<!--
##### Contract project settings #####
- Allows referencing contract projects for passing matching reference assemblies to tooling like ApiCompat.
- Allows building against contract assemblies when referencing source projects.
-->
<PropertyGroup>
<ContractProject Condition="'$(ContractProject)' == ''">$(LibrariesProjectRoot)$(MSBuildProjectName)\ref\$(MSBuildProjectName).csproj</ContractProject>
<HasMatchingContract Condition="'$(HasMatchingContract)' == '' and Exists('$(ContractProject)')">true</HasMatchingContract>
<!-- Don't build against reference assemblies when projects are packable and the tfm is not the latest .NETCoreApp as
such reference assemblies don't ship to customers and only exist for tooling scenarios. -->
<AnnotateTargetPathWithContract Condition="'$(AnnotateTargetPathWithContract)' == '' and
'$(HasMatchingContract)' == 'true' and
(
'$(IsPackable)' != 'true' or
(
'$(TargetFrameworkIdentifier)' == '.NETCoreApp' and
'$(TargetFrameworkVersion)' == 'v$(NetCoreAppCurrentVersion)'
)
)">true</AnnotateTargetPathWithContract>
</PropertyGroup>
<ItemGroup Condition="'$(HasMatchingContract)' == 'true' and '$(ContractProject)' != ''">
<ProjectReference Include="$(ContractProject)" ReferenceOutputAssembly="false" OutputItemType="ResolvedMatchingContract" />
</ItemGroup>
<!-- We aren't referencing the contract, but make sure it's considered as an input to Compile so that if it changes we rebuild and rerun API compat -->
<Target Name="AddResolvedMatchingContractToCompileInput"
BeforeTargets="CoreCompile"
AfterTargets="ResolveProjectReferences"
Condition="'@(ResolvedMatchingContract)' != ''">
<ItemGroup>
<CustomAdditionalCompileInputs Include="@(ResolvedMatchingContract)" />
</ItemGroup>
</Target>
<!-- Allow P2Ps that target a source project to build against the corresponding ref project. -->
<Target Name="AnnotateTargetPathWithTargetPlatformMonikerWithReferenceAssembly"
Condition="'$(AnnotateTargetPathWithContract)' == 'true'"
DependsOnTargets="ResolveProjectReferences;GetTargetPathWithTargetPlatformMoniker"
BeforeTargets="GetTargetPath">
<ItemGroup>
<TargetPathWithTargetPlatformMoniker ReferenceAssembly="@(ResolvedMatchingContract)" />
</ItemGroup>
</Target>
<!-- ##### APICompat settings ##### -->
<PropertyGroup>
<ApiCompatContractItemName>ResolvedMatchingContract</ApiCompatContractItemName>
<ApiCompatStrictMode Condition="'$(ApiCompatStrictMode)' == ''">true</ApiCompatStrictMode>
<ApiCompatUseRoslynToolsetPackagePath Condition="'$(DotNetBuildSourceOnly)' == 'true'">true</ApiCompatUseRoslynToolsetPackagePath>
<!-- Optional rules -->
<ApiCompatEnableRuleAttributesMustMatch>true</ApiCompatEnableRuleAttributesMustMatch>
<ApiCompatEnableRuleCannotChangeParameterName>true</ApiCompatEnableRuleCannotChangeParameterName>
<_ApiCompatCaptureGroupPattern>.+%5C$([System.IO.Path]::DirectorySeparatorChar)(.+)%5C$([System.IO.Path]::DirectorySeparatorChar)(.+)</_ApiCompatCaptureGroupPattern>
<_ApiCompatRuntimePrefixPattern>(.+)/(net%5Cd+%5C.%5Cd)-(.+)/(.+)</_ApiCompatRuntimePrefixPattern>
<_ApiCompatLibReplacementString>lib/$1/$2</_ApiCompatLibReplacementString>
<!-- CoreLib source projects have different output paths. -->
<_ApiCompatLibReplacementString Condition="'$(MSBuildProjectName)' == 'System.Private.CoreLib'">lib/$(NetCoreAppCurrent)/$2</_ApiCompatLibReplacementString>
</PropertyGroup>
<PropertyGroup>
<IsRuntimeAndReferenceAssembly Condition="'$(IsRuntimeAndReferenceAssembly)' == '' and
'$(HasMatchingContract)' != 'true' and
'$(IsPrivateAssembly)' != 'true'">true</IsRuntimeAndReferenceAssembly>
</PropertyGroup>
<!-- Disable suppression validation for packable projects that have a corresponding reference source project.
That is necessary as APICompat is invoked twice, once for the ref <-> src comparision and then again
for the package validation (which doesn't include reference assemblies). As both operations don't have
all the inputs available, some suppressions might only apply to one or the other and hence unnecessary
suppressions can't be determined.
Disable the validation under source build as that might use an out-of-date SDK and not the ApiCompat.Task package. -->
<PropertyGroup Condition="('$(IsPackable)' == 'true' and '$(IsRuntimeAndReferenceAssembly)' != 'true') or '$(DotNetBuildSourceOnly)' == 'true'">
<ApiCompatPreserveUnnecessarySuppressions>true</ApiCompatPreserveUnnecessarySuppressions>
<ApiCompatPermitUnnecessarySuppressions>true</ApiCompatPermitUnnecessarySuppressions>
</PropertyGroup>
<PropertyGroup Condition="'$(IsCrossTargetingBuild)' != 'true'">
<!-- Disable API compat if the project doesn't have a reference assembly. -->
<ApiCompatValidateAssemblies Condition="'$(HasMatchingContract)' != 'true'">false</ApiCompatValidateAssemblies>
<!-- TODO: Move into Microsoft.DotNet.GenFacadesNotSupported.targets. -->
<!-- Not supported sources are created from the ref assembly, we currently don't produce finalizers in dummy assemblies, so we disable ApiCompat to not fail. -->
<ApiCompatValidateAssemblies Condition="'$(GeneratePlatformNotSupportedAssemblyMessage)' != ''">false</ApiCompatValidateAssemblies>
</PropertyGroup>
<ItemGroup>
<ApiCompatExcludeAttributesFile Include="$(RepositoryEngineeringDir)DefaultGenApiDocIds.txt" />
<ApiCompatExcludeAttributesFile Include="$(RepositoryEngineeringDir)ApiCompatExcludeAttributes.txt" />
</ItemGroup>
<ItemGroup>
<!-- Transform the API Compat assemblies passed in to log-able strings. -->
<ApiCompatLeftAssembliesTransformationPattern Include="$(_ApiCompatCaptureGroupPattern)" ReplacementString="ref/$1/$2" />
<ApiCompatLeftAssembliesTransformationPattern Include="$(_ApiCompatRuntimePrefixPattern)" ReplacementString="runtimes/$3/$1/$2/$4" />
<ApiCompatLeftAssembliesTransformationPattern Include="runtimes/windows/" ReplacementString="runtimes/win/" />
<ApiCompatRightAssembliesTransformationPattern Include="$(_ApiCompatCaptureGroupPattern)" ReplacementString="$(_ApiCompatLibReplacementString)" />
<ApiCompatRightAssembliesTransformationPattern Include="$(_ApiCompatRuntimePrefixPattern)" ReplacementString="runtimes/$3/$1/$2/$4" />
<ApiCompatRightAssembliesTransformationPattern Include="runtimes/windows/" ReplacementString="runtimes/win/" />
<!-- Fall back to the targeting pack dir for NetCoreAppCurrent to avoid passing through dependencies from ref to src. -->
<ApiCompatContractAssemblyReferences Include="$(MicrosoftNetCoreAppRefPackRefDir)"
Condition="$([MSBuild]::IsTargetFrameworkCompatible('$(TargetFramework)', '$(NetCoreAppCurrent)'))" />
</ItemGroup>
<!-- Use the apicompat task package instead of the in-built SDK functionality to consume newer features. -->
<ItemGroup Condition="'$(EnablePackageValidation)' == 'true' or
'$(ApiCompatValidateAssemblies)' == 'true'">
<PackageReference Include="Microsoft.DotNet.ApiCompat.Task" Version="$(MicrosoftDotNetApiCompatTaskVersion)" PrivateAssets="all" IsImplicitlyDefined="true" />
</ItemGroup>
<!-- ##### GenFacades settings ##### -->
<PropertyGroup>
<!-- Let GenFacades use roslyn from the toolset package as it loads sources which might require newer language features. -->
<GenFacadesUseRoslynToolsetPackagePath>true</GenFacadesUseRoslynToolsetPackagePath>
</PropertyGroup>
<!-- ##### GenAPI settings ##### -->
<PropertyGroup>
<GenAPIExcludeAttributesList>$(RepositoryEngineeringDir)DefaultGenApiDocIds.txt</GenAPIExcludeAttributesList>
<GenAPIHeaderFile>$(RepositoryEngineeringDir)LicenseHeader.txt</GenAPIHeaderFile>
<GenAPITargetPath>$([MSBuild]::NormalizePath('$(MSBuildProjectDirectory)', '..', 'ref', '$(AssemblyName).cs'))</GenAPITargetPath>
<GenAPILangVersion Condition="'$(LangVersion)' != ''">$(LangVersion)</GenAPILangVersion>
<ProjectForGenAPIDocIdGeneration Condition="'$(ProjectForGenAPIDocIdGeneration)' == ''">$(CoreLibProject)</ProjectForGenAPIDocIdGeneration>
</PropertyGroup>
<ItemGroup>
<!-- GenAPI is currently only invoked on demand and not used as part of the build as it isn't source build compatible. -->
<PackageReference Include="Microsoft.DotNet.GenAPI"
Version="$(MicrosoftDotNetGenApiVersion)"
PrivateAssets="all"
IsImplicitlyDefined="true"
Condition="'$(DotNetBuildSourceOnly)' != 'true'" />
</ItemGroup>
<!-- Generate a .txt file with all public types of the project referenced by ProjectForGenAPIDocIdGeneration (e.g. System.Private.CoreLib or System.Private.Uri implementation assembly).
This file is then later on passed to GenAPI as the list of types which should be "split out" with the conditional compilation logic. -->
<Target Name="GenerateConditionalTypeLists"
Condition="'@(ProjectReference)' != '' and @(ProjectReference->AnyHaveMetadataValue('Identity', '$(ProjectForGenAPIDocIdGeneration)')) and ('$(ContractTypesPartiallyMoved)' == 'true' or '$(ContractTypesPartiallyMoved)' == 'true')">
<PropertyGroup>
<!-- We either wrap all contract types in a #if condition (when SymbolForGenAPIConditionalTypeLists is empty),
or just the types mentioned in GenAPIConditionalTypeLists with the symbol specified in SymbolForGenAPIConditionalTypeLists -->
<GenAPIDefaultCondition Condition="'$(SymbolForGenAPIConditionalTypeLists)' == ''">!BUILDING_CORELIB_REFERENCE</GenAPIDefaultCondition>
</PropertyGroup>
<ItemGroup>
<_genAPILibPathForGenAPIDocIdGeneration Include="@(ReferencePath->'%(RootDir)%(Directory)'->Distinct())" />
<_genAPIResolvedProjectForGenAPIDocIdGeneration Include="@(_ResolvedProjectReferencePaths->WithMetadataValue('MSBuildSourceProjectFile','$(ProjectForGenAPIDocIdGeneration)'))" />
<GenAPIConditionalTypeLists Include="$(IntermediateOutputPath)GenAPIConditionalTypeList.txt">
<Symbol Condition="'$(SymbolForGenAPIConditionalTypeLists)' != ''">$(SymbolForGenAPIConditionalTypeLists)</Symbol>
</GenAPIConditionalTypeLists>
</ItemGroup>
<!-- Generate conditional compilation symbols to hide types implemented in contracts so we can include the .cs in the System.Private.CoreLib ref -->
<Microsoft.DotNet.GenAPI.GenAPITask
Assembly="@(_genAPIResolvedProjectForGenAPIDocIdGeneration)"
LibPath="@(_genAPILibPathForGenAPIDocIdGeneration)"
WriterType="DocIds"
DocIdKinds="Namespace, Type"
OutputPath="@(GenAPIConditionalTypeLists)" />
</Target>
<Target Name="SetGenAPIProperties"
DependsOnTargets="GenerateConditionalTypeLists"
BeforeTargets="GenerateReferenceAssemblySource">
<PropertyGroup>
<GenAPIFollowTypeForwards Condition="'%(ProjectReference.Identity)' == '$(CoreLibProject)' or '%(ProjectReference.Identity)' == '$(UriProject)'">true</GenAPIFollowTypeForwards>
</PropertyGroup>
</Target>
<Import Project="$(RepositoryEngineeringDir)outerBuild.targets" Condition="'$(IsCrossTargetingBuild)' == 'true'" />
</Project>