提交 5be0bccc 编写于 作者: J Jason Malinowski

Merge remote-tracking branch 'dotnet/master' into master-vs-deps-to-master

......@@ -32,37 +32,26 @@ steps:
feed: '8f470c7e-ac49-4afe-a6ee-cf784e438b93'
- task: CmdLine@1
displayName: Create output directory
inputs:
filename: mkdir
arguments: 'Binaries\$(BuildConfiguration)'
- task: VSBuild@1
- script: build\scripts\cibuild.cmd
-configuration $(BuildConfiguration) -official -testDesktop -procdump
/p:OfficialBuildId=$(BUILD.BUILDNUMBER)
/p:DotNetSignType=$(PB_SignType)
/p:DotNetSymbolServerTokenMsdl=$(microsoft-symbol-server-pat)
/p:DotNetSymbolServerTokenSymWeb=$(symweb-symbol-server-pat)
displayName: Build
condition: succeeded()
- task: PowerShell@2
displayName: Publish Assets
inputs:
solution: 'src/Tools/MicroBuild/Build.proj'
vsVersion: 15.0
msbuildArgs: >-
/p:TreatWarningsAsErrors=true
/p:DeployExtension=false
/p:TrackFileAccess=false
/p:OfficialBuildId=$(BUILD.BUILDNUMBER)
/p:VisualStudioVersion=14.0
/flp1:Summary;Verbosity=diagnostic;Encoding=UTF-8;LogFile=$(Build.SourcesDirectory)\Binaries\$(BuildConfiguration)\Roslyn.log
/flp2:WarningsOnly;Verbosity=diagnostic;Encoding=UTF-8;LogFile=$(Build.SourcesDirectory)\Binaries\$(BuildConfiguration)\Roslyn.wrn
/flp3:ErrorsOnly;Verbosity=diagnostic;Encoding=UTF-8;LogFile=$(Build.SourcesDirectory)\Binaries\$(BuildConfiguration)\Roslyn.err
/p:RoslynMyGetApiKey=$(Roslyn.MyGetApiKey)
/p:RoslynNuGetApiKey=$(Roslyn.NuGetApiKey)
/p:RoslynGitHubEmail=$(Roslyn.GitHubEmail)
/p:RoslynGitHubToken=$(Roslyn.GitHubToken)
/p:RoslynGitHubUserName=$(Roslyn.GitHubUserName)
/p:PB_PublishBlobFeedKey=$(PB_PublishBlobFeedKey)
/p:PublishStableVersions=false
/p:VersionStampToPublish=prerelease
/p:DotNetSymbolServerTokenMsdl=$(microsoft-symbol-server-pat)
/p:DotNetSymbolServerTokenSymWeb=$(symweb-symbol-server-pat)
platform: '$(BuildPlatform)'
configuration: '$(BuildConfiguration)'
maximumCpuCount: true
logProjectEvents: false
arguments: '-config $(BuildConfiguration) -branchName "$(Build.SourceBranch)" -mygetApiKey $(Roslyn.MyGetApiKey) -nugetApiKey $(Roslyn.NuGetApiKey) -gitHubUserName $(Roslyn.GitHubUserName) -gitHubToken $(Roslyn.GitHubToken) -gitHubEmail $(Roslyn.GitHubEmail)'
filePath: 'build\scripts\publish-assets.ps1'
condition: succeeded()
- task: PublishBuildArtifacts@1
displayName: Publish Logs
......@@ -86,7 +75,7 @@ steps:
displayName: Upload VSTS Drop
inputs:
DropFolder: 'Binaries\VSSetup\$(BuildConfiguration)\Insertion'
condition: and(succeeded(), contains(variables['PB_PublishType'], 'vsts'))
condition: succeeded()
- task: NuGetCommand@2
displayName: NuGet CoreXT publish
......@@ -96,7 +85,7 @@ steps:
packagesToPush: '$(Build.SourcesDirectory)\Binaries\$(BuildConfiguration)\DevDivPackages\**\*.nupkg'
publishVstsFeed: '97a41293-2972-4f48-8c0e-05493ae82010'
allowPackageConflicts: true
condition: and(succeeded(), contains(variables['PB_PublishType'], 'vsts'))
condition: succeeded()
# Publish VSTS artifact that the RoslynInsertionTool is able to find by its name.
# The backing storage of the artifact is a file share.
......@@ -130,5 +119,5 @@ steps:
ArtifactName: '$(Build.BuildNumber)'
publishLocation: FilePath
TargetPath: '$(DropRoot)\Roslyn-Signed\$(Build.SourceBranchName)\$(BuildConfiguration)'
condition: and(succeededOrFailed(), contains(variables['PB_PublishType'], 'vsts'))
condition: succeededOrFailed()
phases:
- phase: Windows_Desktop_Unit_Tests
queue:
name: Helix
name: dotnet-external-temp
timeoutInMinutes: 90
parallel: 4
matrix:
......@@ -19,7 +19,8 @@ phases:
_testKind: Test64
steps:
- script: build/scripts/cibuild.cmd -$(_configuration) -testDesktop -$(_testKind)
- script: build/scripts/cibuild.cmd -configuration $(_configuration) -testDesktop -$(_testKind)
displayName: Build and Test
- task: PublishTestResults@1
inputs:
......@@ -39,7 +40,7 @@ phases:
- phase: Windows_CoreClr_Unit_Tests
queue:
name: Helix
name: dotnet-external-temp
timeoutInMinutes: 90
parallel: 2
matrix:
......@@ -49,7 +50,8 @@ phases:
_configuration: Release
steps:
- script: build/scripts/cibuild.cmd -$(_configuration) -testCoreClr -buildCoreClr
- script: build/scripts/cibuild.cmd -configuration $(_configuration) -testCoreClr -buildCoreClr
displayName: Build and Test
- task: PublishTestResults@1
inputs:
......@@ -69,10 +71,11 @@ phases:
- phase: Windows_Determinism_Test
queue:
name: Helix
name: dotnet-external-temp
timeoutInMinutes: 90
steps:
- script: build/scripts/cibuild.cmd -testDeterminism
displayName: Build - Validate determinism
- task: PublishBuildArtifacts@1
inputs:
......@@ -84,10 +87,11 @@ phases:
- phase: Windows_Correctness_Test
queue:
name: Helix
name: dotnet-external-temp
timeoutInMinutes: 90
steps:
- script: build/scripts/test-build-correctness.cmd -cibuild -release
- script: build/scripts/test-build-correctness.cmd -configuration Release -cibuild
displayName: Build - Validate correctness
- task: PublishBuildArtifacts@1
inputs:
......@@ -104,14 +108,16 @@ phases:
parallel: 2
matrix:
coreclr:
_args: --debug
_args: --configuration Debug
_name: CoreClr
mono:
_args: --debug --docker --mono
_args: --configuration Debug --docker --mono
_name: Mono
steps:
- script: ./build/scripts/cibuild.sh $(_args)
displayName: Build and Test
- script: ./build/scripts/dockerstop.sh
displayName: Stop Docker
condition: eq(variables['_name'], 'Mono')
- task: PublishTestResults@1
inputs:
......
......@@ -444,7 +444,6 @@ Global
{1EE8CAD3-55F9-4D91-96B2-084641DA9A6C} = {A41D1B99-F489-4C43-BBDF-96D61B19A6B9}
{9508F118-F62E-4C16-A6F4-7C3B56E166AD} = {E35DA3D1-16C0-4318-9187-6B664F12A870}
{F5CE416E-B906-41D2-80B9-0078E887A3F6} = {E35DA3D1-16C0-4318-9187-6B664F12A870}
{A41D1B99-F489-4C43-BBDF-96D61B19A6B9} = {32A48625-F0AD-419D-828B-A50BDABA38EA}
{4B45CA0C-03A0-400F-B454-3D4BCB16AF38} = {32A48625-F0AD-419D-828B-A50BDABA38EA}
{B501A547-C911-4A05-AC6E-274A50DFF30E} = {32A48625-F0AD-419D-828B-A50BDABA38EA}
{50D26304-0961-4A51-ABF6-6CAD1A56D203} = {32A48625-F0AD-419D-828B-A50BDABA38EA}
......@@ -453,7 +452,6 @@ Global
{B2C33A93-DB30-4099-903E-77D75C4C3F45} = {32A48625-F0AD-419D-828B-A50BDABA38EA}
{28026D16-EB0C-40B0-BDA7-11CAA2B97CCC} = {32A48625-F0AD-419D-828B-A50BDABA38EA}
{50D26304-0961-4A51-ABF6-6CAD1A56D202} = {32A48625-F0AD-419D-828B-A50BDABA38EA}
{C65C6143-BED3-46E6-869E-9F0BE6E84C37} = {32A48625-F0AD-419D-828B-A50BDABA38EA}
{7FE6B002-89D8-4298-9B1B-0B5C247DD1FD} = {A41D1B99-F489-4C43-BBDF-96D61B19A6B9}
{4371944A-D3BA-4B5B-8285-82E5FFC6D1F9} = {32A48625-F0AD-419D-828B-A50BDABA38EA}
{4371944A-D3BA-4B5B-8285-82E5FFC6D1F8} = {C65C6143-BED3-46E6-869E-9F0BE6E84C37}
......@@ -465,7 +463,6 @@ Global
{BDA5D613-596D-4B61-837C-63554151C8F5} = {C65C6143-BED3-46E6-869E-9F0BE6E84C37}
{91F6F646-4F6E-449A-9AB4-2986348F329D} = {C65C6143-BED3-46E6-869E-9F0BE6E84C37}
{AFDE6BEA-5038-4A4A-A88E-DBD2E4088EED} = {A41D1B99-F489-4C43-BBDF-96D61B19A6B9}
{FD0FAF5F-1DED-485C-99FA-84B97F3A8EEC} = {32A48625-F0AD-419D-828B-A50BDABA38EA}
{02459936-CD2C-4F61-B671-5C518F2A3DDC} = {FD0FAF5F-1DED-485C-99FA-84B97F3A8EEC}
{288089C5-8721-458E-BE3E-78990DAB5E2E} = {FD0FAF5F-1DED-485C-99FA-84B97F3A8EEC}
{288089C5-8721-458E-BE3E-78990DAB5E2D} = {FD0FAF5F-1DED-485C-99FA-84B97F3A8EEC}
......@@ -475,25 +472,20 @@ Global
{FCFA8808-A1B6-48CC-A1EA-0B8CA8AEDA8E} = {32A48625-F0AD-419D-828B-A50BDABA38EA}
{E58EE9D7-1239-4961-A0C1-F9EC3952C4C1} = {C65C6143-BED3-46E6-869E-9F0BE6E84C37}
{1DFEA9C5-973C-4179-9B1B-0F32288E1EF2} = {A41D1B99-F489-4C43-BBDF-96D61B19A6B9}
{E35DA3D1-16C0-4318-9187-6B664F12A870} = {32A48625-F0AD-419D-828B-A50BDABA38EA}
{AD6F474E-E6D4-4217-91F3-B7AF1BE31CCC} = {A41D1B99-F489-4C43-BBDF-96D61B19A6B9}
{6F016299-BA96-45BA-9BFF-6C0793979177} = {32A48625-F0AD-419D-828B-A50BDABA38EA}
{1A3941F1-1E1F-4EF7-8064-7729C4C2E2AA} = {6F016299-BA96-45BA-9BFF-6C0793979177}
{CCBD3438-3E84-40A9-83AD-533F23BCFCA5} = {6F016299-BA96-45BA-9BFF-6C0793979177}
{3CDEA9FB-CD44-4AB4-98A8-5537AAA2169B} = {32A48625-F0AD-419D-828B-A50BDABA38EA}
{C1930979-C824-496B-A630-70F5369A636F} = {3CDEA9FB-CD44-4AB4-98A8-5537AAA2169B}
{D73ADF7D-2C1C-42AE-B2AB-EDC9497E4B71} = {3CDEA9FB-CD44-4AB4-98A8-5537AAA2169B}
{7AD4FE65-9A30-41A6-8004-AA8F89BCB7F3} = {A41D1B99-F489-4C43-BBDF-96D61B19A6B9}
{2DAE4406-7A89-4B5F-95C3-BC5472CE47CE} = {3FF38FD4-DF16-44B0-924F-0D5AE155495B}
{2DAE4406-7A89-4B5F-95C3-BC5422CE47CE} = {3FF38FD4-DF16-44B0-924F-0D5AE155495B}
{ABC7262E-1053-49F3-B846-E3091BB92E8C} = {3FF38FD4-DF16-44B0-924F-0D5AE155495B}
{3FF38FD4-DF16-44B0-924F-0D5AE155495B} = {32A48625-F0AD-419D-828B-A50BDABA38EA}
{12A68549-4E8C-42D6-8703-A09335F97997} = {3FF38FD4-DF16-44B0-924F-0D5AE155495B}
{066F0DBD-C46C-4C20-AFEC-99829A172625} = {3FF38FD4-DF16-44B0-924F-0D5AE155495B}
{3E7DEA65-317B-4F43-A25D-62F18D96CFD7} = {3FF38FD4-DF16-44B0-924F-0D5AE155495B}
{21A01C2D-2501-4619-8144-48977DD22D9C} = {3FF38FD4-DF16-44B0-924F-0D5AE155495B}
{14118347-ED06-4608-9C45-18228273C712} = {3FF38FD4-DF16-44B0-924F-0D5AE155495B}
{D9591377-7868-4D64-9314-83E0C92A871B} = {32A48625-F0AD-419D-828B-A50BDABA38EA}
{5F8D2414-064A-4B3A-9B42-8E2A04246BE5} = {D9591377-7868-4D64-9314-83E0C92A871B}
{21B239D0-D144-430F-A394-C066D58EE267} = {D9591377-7868-4D64-9314-83E0C92A871B}
{57CA988D-F010-4BF2-9A2E-07D6DCD2FF2C} = {D9591377-7868-4D64-9314-83E0C92A871B}
......@@ -509,7 +501,6 @@ Global
{54E08BF5-F819-404F-A18D-0AB9EA81EA04} = {32A48625-F0AD-419D-828B-A50BDABA38EA}
{E8F0BAA5-7327-43D1-9A51-644E81AE55F1} = {C65C6143-BED3-46E6-869E-9F0BE6E84C37}
{46B3E63A-C462-4133-9F27-3B85DA5E7D37} = {FD0FAF5F-1DED-485C-99FA-84B97F3A8EEC}
{274B96B7-F815-47E3-9CA4-4024A57A478F} = {32A48625-F0AD-419D-828B-A50BDABA38EA}
{15FEBD1B-55CE-4EBD-85E3-04898260A25B} = {274B96B7-F815-47E3-9CA4-4024A57A478F}
{27B1EAE2-2E06-48EF-8A67-06D6FB3DC275} = {274B96B7-F815-47E3-9CA4-4024A57A478F}
{E0756C89-603F-4B48-8E64-1D53E62654C8} = {274B96B7-F815-47E3-9CA4-4024A57A478F}
......
#!/usr/bin/env bash
# Copyright (c) .NET Foundation and contributors. All rights reserved.
# Licensed under the MIT license. See LICENSE file in the project root for full license information.
set -e
set -u
source="${BASH_SOURCE[0]}"
usage()
{
echo "Main interface to running builds on Mac/Linux"
echo "Usage: build.sh [options]"
echo ""
echo "Options"
echo " --debug Build Debug (default)"
echo " --release Build Release"
echo " --restore Restore projects required to build"
echo " --build Build all projects"
echo " --pack Build nuget packages"
echo " --test Run unit tests"
echo " --mono Run unit tests with mono"
echo " --build-bootstrap Build the bootstrap compilers"
echo " --use-bootstrap Use the built bootstrap compilers when running main build"
echo " --bootstrap Implies --build-bootstrap and --use-bootstrap"
}
# resolve $SOURCE until the file is no longer a symlink
while [[ -h $source ]]; do
scriptroot="$( cd -P "$( dirname "$source" )" && pwd )"
source="$(readlink "$source")"
root_path="$(cd -P "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
binaries_path="${root_path}"/Binaries
bootstrap_path="${binaries_path}"/Bootstrap
args=
build_in_docker=false
build_configuration=Debug
restore=false
build=false
test_=false
pack=false
use_mono=false
build_bootstrap=false
use_bootstrap=false
stop_vbcscompiler=false
# LTTNG is the logging infrastructure used by coreclr. Need this variable set
# so it doesn't output warnings to the console.
export LTTNG_HOME="$HOME"
if [[ $# = 0 ]]
then
usage
echo ""
echo "To build and test this repo, try: ./build.sh --restore --build --test"
exit 1
fi
while [[ $# > 0 ]]
do
opt="$(echo "$1" | awk '{print tolower($0)}')"
case "$opt" in
-h|--help)
usage
exit 1
;;
--docker)
build_in_docker=true
shift
continue
;;
--debug)
build_configuration=Debug
;;
--release)
build_configuration=Release
;;
--restore|-r)
restore=true
;;
--build|-b)
build=true
;;
--test|-t)
test_=true
;;
--mono)
use_mono=true
;;
--build-bootstrap)
build_bootstrap=true
;;
--use-bootstrap)
use_bootstrap=true
;;
--bootstrap)
build_bootstrap=true
use_bootstrap=true
;;
--stop-vbcscompiler)
stop_vbcscompiler=true
;;
--pack)
pack=true
;;
*)
echo "$1"
usage
exit 1
;;
esac
args="$args $1"
shift
# if $source was a relative symlink, we need to resolve it relative to the path where the
# symlink file was located
[[ $source != /* ]] && source="$scriptroot/$source"
done
config_path=${binaries_path}/${build_configuration}
logs_path=${config_path}/Logs
mkdir -p ${binaries_path}
mkdir -p ${config_path}
mkdir -p ${logs_path}
function stop_processes {
echo "Killing running build processes..."
pkill -9 "dotnet" || true
pkill -9 "vbcscompiler" || true
}
if [[ "$build_in_docker" = true ]]
then
echo "Docker exec: $args"
BUILD_COMMAND=/opt/code/build.sh "$root_path"/build/scripts/dockerrun.sh $args
exit
fi
source "${root_path}"/build/scripts/obtain_dotnet.sh
if [[ "$restore" == true ]]
then
echo "Restoring RoslynToolset.csproj"
dotnet restore "${root_path}/build/ToolsetPackages/RoslynToolset.csproj" "/bl:${logs_path}/Restore-RoslynToolset.binlog"
echo "Restoring Compilers.sln"
dotnet restore "${root_path}/Compilers.sln" "/bl:${logs_path}/Restore-Compilers.binlog"
fi
build_args="--no-restore -c ${build_configuration} /nologo"
if [[ "$build_bootstrap" == true ]]
then
echo "Building bootstrap compiler"
rm -rf ${bootstrap_path}
mkdir -p ${bootstrap_path}
project_path=src/NuGet/Microsoft.NETCore.Compilers/Microsoft.NETCore.Compilers.Package.csproj
dotnet pack -nologo ${project_path} /p:DotNetUseShippingVersions=true /p:InitialDefineConstants=BOOTSTRAP /p:PackageOutputPath=${bootstrap_path}
unzip ${bootstrap_path}/Microsoft.NETCore.Compilers.*.nupkg -d ${bootstrap_path}
chmod -R 755 ${bootstrap_path}
echo "Cleaning Bootstrap compiler artifacts"
dotnet clean ${project_path}
stop_processes
fi
if [[ "${use_bootstrap}" == true ]]
then
build_args+=" /p:BootstrapBuildPath=${bootstrap_path}"
fi
# https://github.com/dotnet/roslyn/issues/23736
UNAME="$(uname)"
if [[ "$UNAME" == "Darwin" ]]
then
build_args+=" /p:UseRoslynAnalyzers=false"
fi
if [[ "${build}" == true ]]
then
echo "Building Compilers.sln"
if [[ "${pack}" == true ]]
then
build_args+=" /t:Pack"
fi
dotnet build "${root_path}/Compilers.sln" ${build_args} "/bl:${binaries_path}/Build.binlog"
fi
if [[ "${stop_vbcscompiler}" == true ]]
then
if [[ "${use_bootstrap}" == true ]]
then
dotnet build-server shutdown
else
echo "--stop-vbcscompiler requires --use-bootstrap. Aborting."
exit 1
fi
fi
if [[ "${test_}" == true ]]
then
if [[ "${use_mono}" == true ]]
then
test_runtime=mono
# Echo out the mono version to the comamnd line so it's visible in CI logs. It's not fixed
# as we're using a feed vs. a hard coded package.
mono --version
else
test_runtime=dotnet
fi
"${root_path}"/build/scripts/tests.sh "${build_configuration}" "${test_runtime}"
fi
scriptroot="$( cd -P "$( dirname "$source" )" && pwd )"
"$scriptroot/build/scripts/build.sh" $@
<!-- Copyright (c) Microsoft. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. -->
<Project DefaultTargets="Publish">
<!--
Optional variables:
Optional variables:
AzureFeedUrl Target Azure feed URL.
AzureAccountKey Azure account key.
DotNetOutputBlobFeedDir Source Build publishing directory
DotNetSymbolServerTokenMsdl Personal access token for MSDL symbol server. Available from variable group DotNet-Symbol-Publish.
DotNetSymbolServerTokenSymWeb Personal access token for SymWeb symbol server. Available from variable group DotNet-Symbol-Publish.
DotNetSymbolExpirationInDays Symbol expiration time in days (defaults to 10 years).
TODO: Roslyn specific
PublishStableVersions, VersionStampToPublish: Determine what packages to push for the .NET Core build.
- PublishStableVersions = false - Push PerBuildPreRelease
- PublishStableVersions = true - Push either PreRelease or Release, based on VersionStampToPublish value
- VersionStampToPublish = '' - Push Release
- VersionStampToPublish != '' - Push PreRelease
- PublishStableVersions = false and VersionStampToPublish == '' - Error, no per build versioning of release builds
TODO:
Unify this logic between Source and Orchestrated build (https://github.com/dotnet/arcade/issues/101)
......@@ -32,13 +24,7 @@
<PublishToSymbolServer>false</PublishToSymbolServer>
<PublishToSymbolServer Condition="'$(UsingToolSymbolUploader)' == 'true' and '$(AzureFeedUrl)' == '' and '$(ContinuousIntegrationBuild)' == 'true'">true</PublishToSymbolServer>
</PropertyGroup>
<!-- TODO: Roslyn specific -->
<PropertyGroup>
<PublishPackagesDir Condition="'$(PublishStableVersions)' == 'false'">$(ArtifactsPackagesDir)PerBuildPreRelease</PublishPackagesDir>
<PublishPackagesDir Condition="'$(PublishStableVersions)' == 'true' and '$(VersionStampToPublish)' == ''">$(ArtifactsPackagesDir)Release</PublishPackagesDir>
<PublishPackagesDir Condition="'$(PublishStableVersions)' == 'true' and '$(VersionStampToPublish)' != ''">$(ArtifactsPackagesDir)PreRelease</PublishPackagesDir>
<AssetManifestFilePath>$(ArtifactsLogDir)AssetManifest\$(OS)-$(PlatformName).xml</AssetManifestFilePath>
</PropertyGroup>
<Import Project="$(NuGetPackageRoot)microsoft.dotnet.build.tasks.feed\$(MicrosoftDotNetBuildTasksFeedVersion)\build\Microsoft.DotNet.Build.Tasks.Feed.targets" Condition="$(PublishToAzure)"/>
......@@ -50,16 +36,20 @@
</PropertyGroup>
<ItemGroup>
<ExistingSymbolPackages Include="$(PublishPackagesDir)*.symbols.nupkg" />
<ExistingSymbolPackages Include="$(ArtifactsShippingPackagesDir)*.symbols.nupkg" IsShipping="true" />
<ExistingSymbolPackages Include="$(ArtifactsNonShippingPackagesDir)*.symbols.nupkg" IsShipping="false" />
<PackagesToPublish Include="$(PublishPackagesDir)*.nupkg" />
<PackagesToPublish Include="$(ArtifactsShippingPackagesDir)*.nupkg" IsShipping="true" />
<PackagesToPublish Include="$(ArtifactsNonShippingPackagesDir)*.nupkg" IsShipping="false" />
<PackagesToPublish Remove="@(ExistingSymbolPackages)" />
<PackagesToPublish Update="@(PackagesToPublish)">
<SymbolPackageToGenerate Condition="!Exists('%(RootDir)%(Directory)%(Filename).symbols.nupkg')">$(SymbolPackagesDir)%(Filename).symbols.nupkg</SymbolPackageToGenerate>
</PackagesToPublish>
<SymbolPackagesToGenerate Include="@(PackagesToPublish->'%(SymbolPackageToGenerate)')" Condition="'%(PackagesToPublish.SymbolPackageToGenerate)' != ''">
<OriginalPackage>%(PackagesToPublish.Identity)</OriginalPackage>
<IsShipping>%(PackagesToPublish.IsShipping)</IsShipping>
</SymbolPackagesToGenerate>
</ItemGroup>
......@@ -72,13 +62,21 @@
<Copy SourceFiles="@(SymbolPackagesToGenerate->'%(OriginalPackage)')" DestinationFiles="@(SymbolPackagesToGenerate)" />
<!-- Orchestrated Build blob storage -->
<ItemGroup>
<ItemsToPushToBlobFeed Include="@(PackagesToPublish);@(ExistingSymbolPackages);@(SymbolPackagesToGenerate)">
<ManifestArtifactData Condition="!%(IsShipping)">NonShipping=true</ManifestArtifactData>
</ItemsToPushToBlobFeed>
</ItemGroup>
<PushToBlobFeed ExpectedFeedUrl="$(AzureFeedUrl)"
AccountKey="$(AzureAccountKey)"
ItemsToPush="@(PackagesToPublish);@(ExistingSymbolPackages);@(SymbolPackagesToGenerate)"
ManifestName="$(BUILD_REPOSITORY_NAME)"
ItemsToPush="@(ItemsToPushToBlobFeed)"
ManifestBuildData="Location=$(AzureFeedUrl)"
ManifestRepoUri="$(BUILD_REPOSITORY_URI)"
ManifestBranch="$(BUILD_SOURCEBRANCH)"
ManifestBuildId="$(BUILD_BUILDNUMBER)"
ManifestCommit="$(BUILD_SOURCEVERSION)"
AssetManifestPath="$(AssetManifestFilePath)"
Condition="$(PublishToAzure)"/>
<!-- Source Build local storage -->
......@@ -98,23 +96,28 @@
<DotNetSymbolServerTokenMsdl>DryRunPTA</DotNetSymbolServerTokenMsdl>
</PropertyGroup>
<!--
Publish Windows PDBs produced by SymStore.targets.
SymbolUploader doesn't support embedded PDBs yet, so let SymStore.targets do the conversion for now.
https://github.com/dotnet/core-eng/issues/3645
-->
<ItemGroup>
<FilesToPublish Include="$(ArtifactsSymStoreDirectory)**\*.pdb"/>
<!--
Publish Windows PDBs produced by SymStore.targets (by default, only shipping PDBs are placed there).
SymbolUploader doesn't support embedded PDBs yet, so let SymStore.targets do the conversion for now.
https://github.com/dotnet/core-eng/issues/3645
-->
<FilesToPublishToSymbolServer Include="$(ArtifactsSymStoreDirectory)**\*.pdb"/>
<!--
Publish Portable PDBs contained in symbol packages.
-->
<PackagesToPublishToSymbolServer Include="@(ExistingSymbolPackages);@(SymbolPackagesToGenerate)"/>
</ItemGroup>
<PropertyGroup>
<PublishToSymbolServer Condition="'@(FilesToPublish)' == '' and '@(ExistingSymbolPackages)' == '' and '@(SymbolPackagesToGenerate)' == ''">false</PublishToSymbolServer>
<PublishToSymbolServer Condition="'@(FilesToPublishToSymbolServer)' == '' and '@(PackagesToPublishToSymbolServer)' == ''">false</PublishToSymbolServer>
</PropertyGroup>
<!-- Symbol Uploader: MSDL -->
<Message Importance="High" Text="Publishing symbol packages to MSDL ..." />
<PublishSymbols PackagesToPublish="@(ExistingSymbolPackages);@(SymbolPackagesToGenerate)"
FilesToPublish="@(FilesToPublish)"
<PublishSymbols PackagesToPublish="@(PackagesToPublishToSymbolServer)"
FilesToPublish="@(FilesToPublishToSymbolServer)"
PersonalAccessToken="$(DotNetSymbolServerTokenMsdl)"
SymbolServerPath="https://microsoftpublicsymbols.artifacts.visualstudio.com/DefaultCollection"
ExpirationInDays="$(DotNetSymbolExpirationInDays)"
......@@ -130,8 +133,8 @@
Currently we need to call the task twice (https://github.com/dotnet/core-eng/issues/3489).
-->
<Message Importance="High" Text="Publishing symbol packages to SymWeb ..." />
<PublishSymbols PackagesToPublish="@(ExistingSymbolPackages);@(SymbolPackagesToGenerate)"
FilesToPublish="@(FilesToPublish)"
<PublishSymbols PackagesToPublish="@(PackagesToPublishToSymbolServer)"
FilesToPublish="@(FilesToPublishToSymbolServer)"
PersonalAccessToken="$(DotNetSymbolServerTokenSymWeb)"
SymbolServerPath="https://microsoft.artifacts.visualstudio.com/DefaultCollection"
ExpirationInDays="$(DotNetSymbolExpirationInDays)"
......
......@@ -16,9 +16,10 @@
[CmdletBinding(PositionalBinding=$false)]
param (
[string]$configuration = "Debug",
# Configuration
[switch]$restore = $false,
[switch]$release = $false,
[switch]$official = $false,
[switch]$cibuild = $false,
[switch]$build = $false,
......@@ -30,7 +31,6 @@ param (
[switch]$deployExtensions = $false,
[switch]$launch = $false,
[switch]$procdump = $false,
[string]$signType = "",
[switch]$skipAnalyzers = $false,
[switch]$checkLoc = $false,
......@@ -46,20 +46,19 @@ param (
# Special test options
[switch]$testDeterminism = $false,
[parameter(ValueFromRemainingArguments=$true)] $badArgs)
[parameter(ValueFromRemainingArguments=$true)][string[]]$properties)
Set-StrictMode -version 2.0
$ErrorActionPreference = "Stop"
function Print-Usage() {
Write-Host "Usage: build.ps1"
Write-Host " -release Perform release build (default is debug)"
Write-Host " -configuration Build configuration ('Debug' or 'Release')"
Write-Host " -restore Restore packages"
Write-Host " -build Build Roslyn.sln"
Write-Host " -official Perform an official build"
Write-Host " -bootstrap Build using a bootstrap Roslyn"
Write-Host " -sign Sign our binaries"
Write-Host " -signType Type of sign: real, test, verify"
Write-Host " -pack Build NuGet packages, VS insertion manifests and installer"
Write-Host " -deployExtensions Deploy built vsixes"
Write-Host " -binaryLog Create binary log for every MSBuild invocation"
......@@ -88,12 +87,6 @@ function Print-Usage() {
# $build based on say $testDesktop. It's possible the developer wanted only for testing
# to execute, not any build.
function Process-Arguments() {
if ($badArgs -ne $null) {
Write-Host "Unsupported argument $badArgs"
Print-Usage
exit 1
}
if ($test32 -and $test64) {
Write-Host "Cannot combine -test32 and -test64"
exit 1
......@@ -126,15 +119,18 @@ function Process-Arguments() {
}
$script:test32 = -not $test64
$script:debug = -not $release
}
function Run-MSBuild([string]$projectFilePath, [string]$buildArgs = "", [string]$logFileName = "", [switch]$parallel = $true, [switch]$useDotnetBuild = $false, [switch]$summary = $true) {
function Run-MSBuild([string]$projectFilePath, [string]$buildArgs = "", [string]$logFileName = "", [switch]$parallel = $true, [switch]$useDotnetBuild = $false, [switch]$summary = $true, [switch]$warnAsError = $true) {
# Because we override the C#/VB toolset to build against our LKG package, it is important
# that we do not reuse MSBuild nodes from other jobs/builds on the machine. Otherwise,
# we'll run into issues such as https://github.com/dotnet/roslyn/issues/6211.
# MSBuildAdditionalCommandLineArgs=
$args = "/p:TreatWarningsAsErrors=true /warnaserror /nologo /nodeReuse:false /p:Configuration=$buildConfiguration";
$args = "/p:TreatWarningsAsErrors=true /nologo /nodeReuse:false /p:Configuration=$configuration ";
if ($warnAsError) {
$args += " /warnaserror"
}
if ($summary) {
$args += " /consoleloggerparameters:Verbosity=minimal;summary"
......@@ -173,6 +169,7 @@ function Run-MSBuild([string]$projectFilePath, [string]$buildArgs = "", [string]
$args += " $buildArgs"
$args += " $projectFilePath"
$args += " $properties"
if ($useDotnetBuild) {
$args = " msbuild $args"
......@@ -242,7 +239,7 @@ function Build-Artifacts() {
}
if ($sign) {
Run-MSBuild "build\Targets\RepoToolset\Sign.proj" "/p:DotNetSignType=$signType"
Run-MSBuild "build\Targets\RepoToolset\Sign.proj"
}
if ($pack) {
......@@ -250,13 +247,18 @@ function Build-Artifacts() {
}
if ($pack -and $cibuild) {
Build-DeployToSymStore
Run-MSBuild "Roslyn.sln" "/t:DeployToSymStore" -logFileName "RoslynDeployToSymStore"
}
if ($build -and $pack -and (-not $buildCoreClr)) {
Build-InsertionItems
Build-Installer
}
if ($cibuild) {
# Symbol Uploader currently reports a warning for some files (https://github.com/dotnet/symstore/issues/76)
Run-MSBuild "build\Targets\RepoToolset\Publish.proj" "/t:Publish" -warnAsError:$false
}
}
function Build-InsertionItems() {
......@@ -321,10 +323,6 @@ function Build-Installer () {
Compress-Archive -Path $intermidateDirectory -DestinationPath $installerZip
}
function Build-DeployToSymStore() {
Run-MSBuild "Roslyn.sln" "/t:DeployToSymStore" -logFileName "RoslynDeployToSymStore"
}
function Build-CheckLocStatus() {
Run-MSBuild "Roslyn.sln" "/t:CheckLocStatus" -logFileName "RoslynCheckLocStatus"
}
......@@ -593,9 +591,8 @@ try {
$msbuild = Ensure-MSBuild
$dotnet = Ensure-DotnetSdk
$buildConfiguration = if ($release) { "Release" } else { "Debug" }
$configDir = Join-Path $binariesDir $buildConfiguration
$vsSetupDir = Join-Path $binariesDir (Join-Path "VSSetup" $buildConfiguration)
$configDir = Join-Path $binariesDir $configuration
$vsSetupDir = Join-Path $binariesDir (Join-Path "VSSetup" $configuration)
$logsDir = Join-Path $configDir "Logs"
$bootstrapDir = ""
......
#!/usr/bin/env bash
# Copyright (c) .NET Foundation and contributors. All rights reserved.
# Licensed under the MIT license. See LICENSE file in the project root for full license information.
set -e
set -u
usage()
{
echo "Main interface to running builds on Mac/Linux"
echo "Usage: build.sh [options]"
echo ""
echo "Options"
echo " --configuration Build configuration ('Debug' or 'Release')"
echo " --ci Building in CI"
echo " --restore Restore projects required to build"
echo " --build Build all projects"
echo " --pack Build nuget packages"
echo " --test Run unit tests"
echo " --mono Run unit tests with mono"
echo " --build-bootstrap Build the bootstrap compilers"
echo " --use-bootstrap Use the built bootstrap compilers when running main build"
echo " --bootstrap Implies --build-bootstrap and --use-bootstrap"
}
source="${BASH_SOURCE[0]}"
# resolve $source until the file is no longer a symlink
while [[ -h "$source" ]]; do
scriptroot="$( cd -P "$( dirname "$source" )" && pwd )"
source="$(readlink "$source")"
# if $source was a relative symlink, we need to resolve it relative to the path where the
# symlink file was located
[[ $source != /* ]] && source="$scriptroot/$source"
done
scriptroot="$( cd -P "$( dirname "$source" )" && pwd )"
root_path="$scriptroot/../.."
binaries_path="${root_path}"/Binaries
bootstrap_path="${binaries_path}"/Bootstrap
args=
build_in_docker=false
build_configuration=Debug
restore=false
build=false
test_=false
pack=false
use_mono=false
build_bootstrap=false
use_bootstrap=false
stop_vbcscompiler=false
ci=false
# LTTNG is the logging infrastructure used by coreclr. Need this variable set
# so it doesn't output warnings to the console.
export LTTNG_HOME="$HOME"
if [[ $# = 0 ]]
then
usage
echo ""
echo "To build and test this repo, try: ./build.sh --restore --build --test"
exit 1
fi
while [[ $# > 0 ]]
do
opt="$(echo "$1" | awk '{print tolower($0)}')"
case "$opt" in
-h|--help)
usage
exit 1
;;
--docker)
build_in_docker=true
shift
continue
;;
--configuration)
build_configuration=$2
args="$args $1"
shift
;;
--ci)
ci=true
;;
--restore|-r)
restore=true
;;
--build|-b)
build=true
;;
--test|-t)
test_=true
;;
--mono)
use_mono=true
;;
--build-bootstrap)
build_bootstrap=true
;;
--use-bootstrap)
use_bootstrap=true
;;
--bootstrap)
build_bootstrap=true
use_bootstrap=true
;;
--stop-vbcscompiler)
stop_vbcscompiler=true
;;
--pack)
pack=true
;;
*)
echo "$1"
usage
exit 1
;;
esac
args="$args $1"
shift
done
config_path=${binaries_path}/${build_configuration}
logs_path=${config_path}/Logs
mkdir -p ${binaries_path}
mkdir -p ${config_path}
mkdir -p ${logs_path}
function stop_processes {
echo "Killing running build processes..."
pkill -9 "dotnet" || true
pkill -9 "vbcscompiler" || true
}
if [[ "$build_in_docker" = true ]]
then
echo "Docker exec: $args"
BUILD_COMMAND=/opt/code/build.sh "$scriptroot"/dockerrun.sh $args
exit
fi
source "${scriptroot}"/obtain_dotnet.sh
if [[ "$restore" == true ]]
then
echo "Restoring RoslynToolset.csproj"
dotnet restore "${root_path}/build/ToolsetPackages/RoslynToolset.csproj" "/bl:${logs_path}/Restore-RoslynToolset.binlog"
echo "Restoring Compilers.sln"
dotnet restore "${root_path}/Compilers.sln" "/bl:${logs_path}/Restore-Compilers.binlog"
fi
build_args="--no-restore -c ${build_configuration} /nologo"
if [[ "$build_bootstrap" == true ]]
then
echo "Building bootstrap compiler"
rm -rf ${bootstrap_path}
mkdir -p ${bootstrap_path}
project_path=src/NuGet/Microsoft.NETCore.Compilers/Microsoft.NETCore.Compilers.Package.csproj
dotnet pack -nologo ${project_path} /p:DotNetUseShippingVersions=true /p:InitialDefineConstants=BOOTSTRAP /p:PackageOutputPath=${bootstrap_path}
unzip ${bootstrap_path}/Microsoft.NETCore.Compilers.*.nupkg -d ${bootstrap_path}
chmod -R 755 ${bootstrap_path}
echo "Cleaning Bootstrap compiler artifacts"
dotnet clean ${project_path}
stop_processes
fi
if [[ "${use_bootstrap}" == true ]]
then
build_args+=" /p:BootstrapBuildPath=${bootstrap_path}"
fi
if [[ "${ci}" == true ]]
then
build_args+=" /p:ContinuousIntegrationBuild=true"
fi
# https://github.com/dotnet/roslyn/issues/23736
UNAME="$(uname)"
if [[ "$UNAME" == "Darwin" ]]
then
build_args+=" /p:UseRoslynAnalyzers=false"
fi
if [[ "${build}" == true ]]
then
echo "Building Compilers.sln"
if [[ "${pack}" == true ]]
then
build_args+=" /t:Pack"
fi
dotnet build "${root_path}/Compilers.sln" ${build_args} "/bl:${binaries_path}/Build.binlog"
fi
if [[ "${stop_vbcscompiler}" == true ]]
then
if [[ "${use_bootstrap}" == true ]]
then
dotnet build-server shutdown
else
echo "--stop-vbcscompiler requires --use-bootstrap. Aborting."
exit 1
fi
fi
if [[ "${test_}" == true ]]
then
if [[ "${use_mono}" == true ]]
then
test_runtime=mono
# Echo out the mono version to the comamnd line so it's visible in CI logs. It's not fixed
# as we're using a feed vs. a hard coded package.
mono --version
else
test_runtime=dotnet
fi
"${scriptroot}"/tests.sh "${build_configuration}" "${test_runtime}"
fi
@echo off
powershell -noprofile -executionPolicy RemoteSigned -file "%~dp0\build.ps1" -cibuild -restore -checkLoc -release -binaryLog %*
powershell -noprofile -executionPolicy RemoteSigned -file "%~dp0\build.ps1" -configuration Release -cibuild -restore -checkLoc -binaryLog %*
@echo off
powershell -noprofile -executionPolicy RemoteSigned -file "%~dp0\build.ps1" -cibuild -build -restore -bootstrap -pack -binaryLog %*
powershell -noprofile -executionPolicy RemoteSigned -file "%~dp0\build.ps1" -cibuild -build -restore -bootstrap -pack -sign -binaryLog %*
#!/usr/bin/env bash
# Copyright (c) .NET Foundation and contributors. All rights reserved.
# Licensed under the MIT license. See LICENSE file in the project root for full license information.
set -e
set -u
source="${BASH_SOURCE[0]}"
root_path="$(cd -P "$(dirname "${BASH_SOURCE[0]}")/../.." && pwd)"
# resolve $SOURCE until the file is no longer a symlink
while [[ -h $source ]]; do
scriptroot="$( cd -P "$( dirname "$source" )" && pwd )"
source="$(readlink "$source")"
# if $source was a relative symlink, we need to resolve it relative to the path where
# the symlink file was located
[[ $source != /* ]] && source="$scriptroot/$source"
done
scriptroot="$( cd -P "$( dirname "$source" )" && pwd)"
# $HOME is unset when running the mac unit tests.
if [[ -z "${HOME+x}" ]]
......@@ -24,4 +30,5 @@ export DOTNET_SKIP_FIRST_TIME_EXPERIENCE=1
echo "Building this commit:"
git show --no-patch --pretty=raw HEAD
"${root_path}"/build.sh --restore --bootstrap --build --pack --stop-vbcscompiler --test "$@"
. "$scriptroot/build.sh" --restore --bootstrap --build --pack --stop-vbcscompiler --test --ci "$@"
\ No newline at end of file
......@@ -143,7 +143,7 @@ function Normalize-BranchName([string]$branchName) {
}
try {
. (Join-Path $PSScriptRoot "..\..\..\build\scripts\build-utils.ps1")
. (Join-Path $PSScriptRoot "build-utils.ps1")
$dotnet = Ensure-DotnetSdk
$configDir = Join-Path $binariesDir $config
$nugetDir = Join-Path $configDir "NuGet"
......
......@@ -16,7 +16,7 @@ Invoke-WebRequest -Uri http://dotnetci.blob.core.windows.net/roslyn-perf/cpc.zip
[Reflection.Assembly]::LoadWithPartialName('System.IO.Compression.FileSystem') | Out-Null
[IO.Compression.ZipFile]::ExtractToDirectory('cpc.zip', $CPCLocation)
./build/scripts/cibuild.cmd -release -testPerfRun
./build/scripts/cibuild.cmd -configuration Release -testPerfRun
if ( -not $? )
{
......
......@@ -11,7 +11,7 @@
[CmdletBinding(PositionalBinding=$false)]
param(
[switch]$release = $false,
[string]$configuration = "Debug",
[switch]$cibuild = $false)
Set-StrictMode -version 2.0
......@@ -20,12 +20,11 @@ $ErrorActionPreference="Stop"
try {
. (Join-Path $PSScriptRoot "build-utils.ps1")
Push-Location $repoDir
$buildConfiguration = if ($release) { "Release" } else { "Debug" }
$releaseArg = if ($release) { "-release" } else { "" }
$configDir = Join-Path $binariesDir $buildConfiguration
$releaseArg = if ($configuration -eq "Release") { "-release" } else { "" }
$configDir = Join-Path $binariesDir $configuration
Write-Host "Building Roslyn"
Exec-Block { & (Join-Path $PSScriptRoot "build.ps1") -restore -build -cibuild:$cibuild -release:$release -pack -binaryLog }
Exec-Block { & (Join-Path $PSScriptRoot "build.ps1") -restore -build -cibuild:$cibuild -configuration:$configuration -pack -binaryLog }
# Verify the state of our various build artifacts
......
#!/usr/bin/env bash
# Copyright (c) .NET Foundation and contributors. All rights reserved.
# Licensed under the MIT license. See LICENSE file in the project root for full license information.
# Temporary file until the netci.groovy change to use the new location propogates
exec ./build/scripts/cibuild.sh "$@"
......@@ -65,7 +65,7 @@ commitPullList.each { isPr ->
def myJob = job(jobName) {
description("Windows debug unit tests on unit32 using Spanish language")
steps {
batchFile(""".\\build\\scripts\\cibuild.cmd -debug -test32 -testDesktop""")
batchFile(""".\\build\\scripts\\cibuild.cmd -configuration Debug -test32 -testDesktop""")
}
}
def triggerPhraseOnly = false
......@@ -81,7 +81,7 @@ commitPullList.each { isPr ->
def myJob = job(jobName) {
description("Mac tests")
steps {
shell("./build/scripts/cibuild.sh --debug")
shell("./build/scripts/cibuild.sh --configuration Debug")
}
}
......@@ -92,22 +92,6 @@ commitPullList.each { isPr ->
addRoslynJob(myJob, jobName, branchName, isPr, triggerPhraseExtra, triggerPhraseOnly)
}
// Microbuild
commitPullList.each { isPr ->
def jobName = Utilities.getFullJobName(projectName, "microbuild", isPr)
def myJob = job(jobName) {
description('MicroBuild test')
steps {
batchFile(""".\\src\\Tools\\MicroBuild\\cibuild.cmd""")
}
}
def triggerPhraseOnly = false
def triggerPhraseExtra = "microbuild"
Utilities.setMachineAffinity(myJob, windowsUnitTestMachine)
addRoslynJob(myJob, jobName, branchName, isPr, triggerPhraseExtra, triggerPhraseOnly)
}
// VS Integration Tests
commitPullList.each { isPr ->
['debug', 'release'].each { configuration ->
......@@ -116,7 +100,7 @@ commitPullList.each { isPr ->
def myJob = job(jobName) {
description("Windows ${configuration} tests on ${buildTarget}")
steps {
batchFile(""".\\build\\scripts\\cibuild.cmd -${configuration} -testVsi""")
batchFile(""".\\build\\scripts\\cibuild.cmd -configuration ${configuration} -testVsi""")
}
}
......
......@@ -46,6 +46,8 @@ internal sealed override CommandLineArguments CommonParse(IEnumerable<string> ar
/// <returns>a commandlinearguments object representing the parsed command line.</returns>
public new CSharpCommandLineArguments Parse(IEnumerable<string> args, string baseDirectory, string sdkDirectory, string additionalReferenceDirectories = null)
{
Debug.Assert(baseDirectory == null || PathUtilities.IsAbsolute(baseDirectory));
List<Diagnostic> diagnostics = new List<Diagnostic>();
List<string> flattenedArgs = new List<string>();
List<string> scriptArgs = IsScriptCommandLineParser ? new List<string>() : null;
......@@ -1214,7 +1216,7 @@ public new CSharpCommandLineArguments Parse(IEnumerable<string> args, string bas
}
// add additional reference paths if specified
if (!string.IsNullOrWhiteSpace(additionalReferenceDirectories))
if (!string.IsNullOrEmpty(additionalReferenceDirectories))
{
ParseAndResolveReferencePaths(null, additionalReferenceDirectories, baseDirectory, libPaths, MessageID.IDS_LIB_ENV, diagnostics);
}
......@@ -1225,14 +1227,18 @@ public new CSharpCommandLineArguments Parse(IEnumerable<string> args, string bas
// Dev11 searches for the key file in the current directory and assembly output directory.
// We always look to base directory and then examine the search paths.
keyFileSearchPaths.Add(baseDirectory);
if (baseDirectory != outputDirectory)
if (!string.IsNullOrEmpty(baseDirectory))
{
keyFileSearchPaths.Add(baseDirectory);
}
if (!string.IsNullOrEmpty(outputDirectory) && baseDirectory != outputDirectory)
{
keyFileSearchPaths.Add(outputDirectory);
}
// Public sign doesn't use the legacy search path settings
if (publicSign && !string.IsNullOrWhiteSpace(keyFileSetting))
if (publicSign && !string.IsNullOrEmpty(keyFileSetting))
{
keyFileSetting = ParseGenericPathToFile(keyFileSetting, diagnostics, baseDirectory);
}
......
......@@ -243,6 +243,13 @@ public void ResponseFiles_RelativePaths()
Assert.Equal(basePath, args.BaseDirectory);
}
[Fact]
public void NullBaseDirectoryNotAddedToKeyFileSearchPaths()
{
var parser = CSharpCommandLineParser.Default.Parse(new string[0], null, SdkDirectory);
AssertEx.Equal(ImmutableArray.Create<string>(), parser.KeyFileSearchPaths);
}
[ConditionalFact(typeof(WindowsOnly))]
public void SourceFiles_Patterns()
{
......@@ -542,7 +549,7 @@ public void Win32IconContainsGarbage()
CleanupAllGeneratedFiles(tmpFileName);
}
[Fact]
[ConditionalFact(typeof(WindowsDesktopOnly), Reason = "https://github.com/dotnet/roslyn/issues/30289")]
public void Win32ResQuotes()
{
string[] responseFile = new string[] {
......
......@@ -753,24 +753,91 @@ void M(System.Action d1, System.Action<bool, bool> d2)
var graphM = ControlFlowGraph.Create((IMethodBodyOperation)semanticModel.GetOperation(tree.GetRoot().DescendantNodes().OfType<MethodDeclarationSyntax>().Single()));
Assert.NotNull(graphM);
Assert.Null(graphM.Parent);
IFlowAnonymousFunctionOperation lambdaD1 = getLambda(graphM);
Assert.Throws<ArgumentNullException>(() => graphM.GetLocalFunctionControlFlowGraph(null));
Assert.Throws<ArgumentOutOfRangeException>(() => graphM.GetLocalFunctionControlFlowGraph(lambdaD1.Symbol));
Assert.Throws<ArgumentNullException>(() => graphM.GetLocalFunctionControlFlowGraphInScope(null));
Assert.Throws<ArgumentOutOfRangeException>(() => graphM.GetLocalFunctionControlFlowGraphInScope(lambdaD1.Symbol));
var graphD1 = graphM.GetAnonymousFunctionControlFlowGraph(lambdaD1);
Assert.NotNull(graphD1);
Assert.Same(graphM, graphD1.Parent);
var graphD1_FromExtension = graphM.GetAnonymousFunctionControlFlowGraphInScope(lambdaD1);
Assert.Same(graphD1, graphD1_FromExtension);
IFlowAnonymousFunctionOperation lambdaD2 = getLambda(graphD1);
var graphD2 = graphD1.GetAnonymousFunctionControlFlowGraph(lambdaD2);
Assert.NotNull(graphD2);
Assert.Same(graphD1, graphD2.Parent);
Assert.Throws<ArgumentNullException>(() => graphM.GetAnonymousFunctionControlFlowGraph(null));
Assert.Throws<ArgumentOutOfRangeException>(() => graphM.GetAnonymousFunctionControlFlowGraph(lambdaD2));
Assert.Throws<ArgumentNullException>(() => graphM.GetAnonymousFunctionControlFlowGraphInScope(null));
Assert.Throws<ArgumentOutOfRangeException>(() => graphM.GetAnonymousFunctionControlFlowGraphInScope(lambdaD2));
IFlowAnonymousFunctionOperation getLambda(ControlFlowGraph graph)
{
return graph.Blocks.SelectMany(b => b.Operations.SelectMany(o => o.DescendantsAndSelf())).OfType<IFlowAnonymousFunctionOperation>().Single();
}
}
[CompilerTrait(CompilerFeature.IOperation, CompilerFeature.Dataflow)]
[Fact]
public void LambdaFlow_05()
{
string source = @"
struct C
{
void M(System.Action d1, System.Action d2)
/*<bind>*/{
d1 = () => { };
d2 = () =>
{
d1();
};
}/*</bind>*/
}
";
var compilation = CreateCompilation(source);
var tree = compilation.SyntaxTrees.Single();
var semanticModel = compilation.GetSemanticModel(tree);
var graphM = ControlFlowGraph.Create((IMethodBodyOperation)semanticModel.GetOperation(tree.GetRoot().DescendantNodes().OfType<MethodDeclarationSyntax>().Single()));
Assert.NotNull(graphM);
Assert.Null(graphM.Parent);
IFlowAnonymousFunctionOperation lambdaD1 = getLambda(graphM, index: 0);
Assert.NotNull(lambdaD1);
IFlowAnonymousFunctionOperation lambdaD2 = getLambda(graphM, index: 1);
Assert.NotNull(lambdaD2);
Assert.Throws<ArgumentNullException>(() => graphM.GetLocalFunctionControlFlowGraph(null));
Assert.Throws<ArgumentOutOfRangeException>(() => graphM.GetLocalFunctionControlFlowGraph(lambdaD1.Symbol));
Assert.Throws<ArgumentNullException>(() => graphM.GetLocalFunctionControlFlowGraphInScope(null));
Assert.Throws<ArgumentOutOfRangeException>(() => graphM.GetLocalFunctionControlFlowGraphInScope(lambdaD1.Symbol));
var graphD1 = graphM.GetAnonymousFunctionControlFlowGraph(lambdaD1);
Assert.NotNull(graphD1);
Assert.Same(graphM, graphD1.Parent);
var graphD2 = graphM.GetAnonymousFunctionControlFlowGraph(lambdaD2);
Assert.NotNull(graphD2);
Assert.Same(graphM, graphD2.Parent);
var graphD1_FromExtension = graphM.GetAnonymousFunctionControlFlowGraphInScope(lambdaD1);
Assert.Same(graphD1, graphD1_FromExtension);
Assert.Throws<ArgumentOutOfRangeException>(() => graphD2.GetAnonymousFunctionControlFlowGraph(lambdaD1));
graphD1_FromExtension = graphD2.GetAnonymousFunctionControlFlowGraphInScope(lambdaD1);
Assert.Same(graphD1, graphD1_FromExtension);
IFlowAnonymousFunctionOperation getLambda(ControlFlowGraph graph, int index)
{
return graph.Blocks.SelectMany(b => b.Operations.SelectMany(o => o.DescendantsAndSelf())).OfType<IFlowAnonymousFunctionOperation>().ElementAt(index);
}
}
}
}
// Copyright (c) Microsoft. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Linq;
using Microsoft.CodeAnalysis.CSharp.Syntax;
using Microsoft.CodeAnalysis.FlowAnalysis;
using Microsoft.CodeAnalysis.Operations;
using Microsoft.CodeAnalysis.Test.Utilities;
using Roslyn.Test.Utilities;
using Xunit;
......@@ -1629,5 +1633,113 @@ void local2(C result2, C input21, C input22)
VerifyFlowGraphAndDiagnosticsForTest<BlockSyntax>(source, expectedGraph, expectedDiagnostics);
}
[CompilerTrait(CompilerFeature.IOperation, CompilerFeature.Dataflow)]
[Fact]
public void LocalFunctionFlow_11()
{
string source = @"
struct C
{
void M()
/*<bind>*/{
void d1()
{
void d2(bool result1, bool input1)
{
result1 = input1;
}
};
}/*</bind>*/
}
";
var compilation = CreateCompilation(source);
var tree = compilation.SyntaxTrees.Single();
var semanticModel = compilation.GetSemanticModel(tree);
var graphM = ControlFlowGraph.Create((IMethodBodyOperation)semanticModel.GetOperation(tree.GetRoot().DescendantNodes().OfType<MethodDeclarationSyntax>().First()));
Assert.NotNull(graphM);
Assert.Null(graphM.Parent);
IMethodSymbol localFunctionD1 = getLocalFunction(graphM);
Assert.NotNull(localFunctionD1);
Assert.Equal("d1", localFunctionD1.Name);
var graphD1 = graphM.GetLocalFunctionControlFlowGraph(localFunctionD1);
Assert.NotNull(graphD1);
Assert.Same(graphM, graphD1.Parent);
var graphD1_FromExtension = graphM.GetLocalFunctionControlFlowGraphInScope(localFunctionD1);
Assert.Same(graphD1, graphD1_FromExtension);
IMethodSymbol localFunctionD2 = getLocalFunction(graphD1);
Assert.NotNull(localFunctionD2);
Assert.Equal("d2", localFunctionD2.Name);
var graphD2 = graphD1.GetLocalFunctionControlFlowGraph(localFunctionD2);
Assert.NotNull(graphD2);
Assert.Same(graphD1, graphD2.Parent);
Assert.Throws<ArgumentNullException>(() => graphM.GetLocalFunctionControlFlowGraph(null));
Assert.Throws<ArgumentOutOfRangeException>(() => graphM.GetLocalFunctionControlFlowGraph(localFunctionD2));
Assert.Throws<ArgumentNullException>(() => graphM.GetLocalFunctionControlFlowGraphInScope(null));
Assert.Throws<ArgumentOutOfRangeException>(() => graphM.GetLocalFunctionControlFlowGraphInScope(localFunctionD2));
IMethodSymbol getLocalFunction(ControlFlowGraph graph)
{
return graph.LocalFunctions.Single();
}
}
[CompilerTrait(CompilerFeature.IOperation, CompilerFeature.Dataflow)]
[Fact]
public void LocalFunctionFlow_12()
{
string source = @"
struct C
{
void M()
/*<bind>*/{
void d1() { }
void d2()
{
d1();
}
}/*</bind>*/
}
";
var compilation = CreateCompilation(source);
var tree = compilation.SyntaxTrees.Single();
var semanticModel = compilation.GetSemanticModel(tree);
var graphM = ControlFlowGraph.Create((IMethodBodyOperation)semanticModel.GetOperation(tree.GetRoot().DescendantNodes().OfType<MethodDeclarationSyntax>().First()));
Assert.NotNull(graphM);
Assert.Null(graphM.Parent);
IMethodSymbol localFunctionD1 = getLocalFunction(graphM, "d1");
Assert.NotNull(localFunctionD1);
IMethodSymbol localFunctionD2 = getLocalFunction(graphM, "d2");
Assert.NotNull(localFunctionD2);
var graphD1 = graphM.GetLocalFunctionControlFlowGraph(localFunctionD1);
Assert.NotNull(graphD1);
Assert.Same(graphM, graphD1.Parent);
var graphD2 = graphM.GetLocalFunctionControlFlowGraph(localFunctionD2);
Assert.NotNull(graphD2);
Assert.Same(graphM, graphD2.Parent);
var graphD1_FromExtension = graphM.GetLocalFunctionControlFlowGraphInScope(localFunctionD1);
Assert.Same(graphD1, graphD1_FromExtension);
Assert.Throws<ArgumentOutOfRangeException>(() => graphD2.GetLocalFunctionControlFlowGraph(localFunctionD1));
graphD1_FromExtension = graphD2.GetLocalFunctionControlFlowGraphInScope(localFunctionD1);
Assert.Same(graphD1, graphD1_FromExtension);
IMethodSymbol getLocalFunction(ControlFlowGraph graph, string name)
{
return graph.LocalFunctions.Single(l => l.Name == name);
}
}
}
}
......@@ -26,7 +26,7 @@ public sealed partial class ValidateBootstrap : Task
public string BootstrapPath
{
get { return _bootstrapPath; }
set { _bootstrapPath = NormalizePath(value); }
set { _bootstrapPath = NormalizePath(Path.GetFullPath(value)); }
}
public ValidateBootstrap()
......
......@@ -26,12 +26,14 @@ public sealed partial class ControlFlowGraph
private ControlFlowGraph[] _lazyAnonymousFunctionsGraphs;
internal ControlFlowGraph(IOperation originalOperation,
ControlFlowGraph parent,
ControlFlowGraphBuilder.CaptureIdDispenser captureIdDispenser,
ImmutableArray<BasicBlock> blocks, ControlFlowRegion root,
ImmutableArray<IMethodSymbol> localFunctions,
ImmutableDictionary<IMethodSymbol, (ControlFlowRegion region, ILocalFunctionOperation operation, int ordinal)> localFunctionsMap,
ImmutableDictionary<IFlowAnonymousFunctionOperation, (ControlFlowRegion region, int ordinal)> anonymousFunctionsMap)
{
Debug.Assert(parent != null == (originalOperation.Kind == OperationKind.LocalFunction || originalOperation.Kind == OperationKind.AnonymousFunction));
Debug.Assert(captureIdDispenser != null);
Debug.Assert(!blocks.IsDefault);
Debug.Assert(blocks.First().Kind == BasicBlockKind.Entry);
......@@ -54,6 +56,7 @@ public sealed partial class ControlFlowGraph
#endif
OriginalOperation = originalOperation;
Parent = parent;
Blocks = blocks;
Root = root;
LocalFunctions = localFunctions;
......@@ -193,6 +196,13 @@ internal static ControlFlowGraph CreateCore(IOperation operation, string argumen
/// </summary>
public IOperation OriginalOperation { get; }
/// <summary>
/// Optional parent control flow graph for this graph.
/// Non-null for a control flow graph generated for a local function or a lambda.
/// Null otherwise.
/// </summary>
public ControlFlowGraph Parent { get; }
/// <summary>
/// Basic blocks for the control flow graph.
/// </summary>
......@@ -220,11 +230,22 @@ public ControlFlowGraph GetLocalFunctionControlFlowGraph(IMethodSymbol localFunc
throw new ArgumentNullException(nameof(localFunction));
}
if (!_localFunctionsMap.TryGetValue(localFunction, out (ControlFlowRegion enclosing, ILocalFunctionOperation operation, int ordinal) info))
if (!TryGetLocalFunctionControlFlowGraph(localFunction, cancellationToken, out var controlFlowGraph))
{
throw new ArgumentOutOfRangeException(nameof(localFunction));
}
return controlFlowGraph;
}
internal bool TryGetLocalFunctionControlFlowGraph(IMethodSymbol localFunction, CancellationToken cancellationToken, out ControlFlowGraph controlFlowGraph)
{
if (!_localFunctionsMap.TryGetValue(localFunction, out (ControlFlowRegion enclosing, ILocalFunctionOperation operation, int ordinal) info))
{
controlFlowGraph = null;
return false;
}
Debug.Assert(localFunction == LocalFunctions[info.ordinal]);
if (_lazyLocalFunctionsGraphs == null)
......@@ -235,12 +256,14 @@ public ControlFlowGraph GetLocalFunctionControlFlowGraph(IMethodSymbol localFunc
if (_lazyLocalFunctionsGraphs[info.ordinal] == null)
{
Debug.Assert(localFunction == info.operation.Symbol);
ControlFlowGraph graph = ControlFlowGraphBuilder.Create(info.operation, info.enclosing, _captureIdDispenser);
ControlFlowGraph graph = ControlFlowGraphBuilder.Create(info.operation, this, info.enclosing, _captureIdDispenser);
Debug.Assert(graph.OriginalOperation == info.operation);
Interlocked.CompareExchange(ref _lazyLocalFunctionsGraphs[info.ordinal], graph, null);
}
return _lazyLocalFunctionsGraphs[info.ordinal];
controlFlowGraph = _lazyLocalFunctionsGraphs[info.ordinal];
Debug.Assert(controlFlowGraph.Parent == this);
return true;
}
/// <summary>
......@@ -255,11 +278,22 @@ public ControlFlowGraph GetAnonymousFunctionControlFlowGraph(IFlowAnonymousFunct
throw new ArgumentNullException(nameof(anonymousFunction));
}
if (!_anonymousFunctionsMap.TryGetValue(anonymousFunction, out (ControlFlowRegion enclosing, int ordinal) info))
if (!TryGetAnonymousFunctionControlFlowGraph(anonymousFunction, cancellationToken, out ControlFlowGraph controlFlowGraph))
{
throw new ArgumentOutOfRangeException(nameof(anonymousFunction));
}
return controlFlowGraph;
}
internal bool TryGetAnonymousFunctionControlFlowGraph(IFlowAnonymousFunctionOperation anonymousFunction, CancellationToken cancellationToken, out ControlFlowGraph controlFlowGraph)
{
if (!_anonymousFunctionsMap.TryGetValue(anonymousFunction, out (ControlFlowRegion enclosing, int ordinal) info))
{
controlFlowGraph = null;
return false;
}
if (_lazyAnonymousFunctionsGraphs == null)
{
Interlocked.CompareExchange(ref _lazyAnonymousFunctionsGraphs, new ControlFlowGraph[_anonymousFunctionsMap.Count], null);
......@@ -268,12 +302,14 @@ public ControlFlowGraph GetAnonymousFunctionControlFlowGraph(IFlowAnonymousFunct
if (_lazyAnonymousFunctionsGraphs[info.ordinal] == null)
{
var anonymous = (FlowAnonymousFunctionOperation)anonymousFunction;
ControlFlowGraph graph = ControlFlowGraphBuilder.Create(anonymous.Original, info.enclosing, _captureIdDispenser, in anonymous.Context);
ControlFlowGraph graph = ControlFlowGraphBuilder.Create(anonymous.Original, this, info.enclosing, _captureIdDispenser, in anonymous.Context);
Debug.Assert(graph.OriginalOperation == anonymous.Original);
Interlocked.CompareExchange(ref _lazyAnonymousFunctionsGraphs[info.ordinal], graph, null);
}
return _lazyAnonymousFunctionsGraphs[info.ordinal];
controlFlowGraph = _lazyAnonymousFunctionsGraphs[info.ordinal];
Debug.Assert(controlFlowGraph.Parent == this);
return true;
}
}
}
......@@ -55,7 +55,7 @@ private bool IsImplicit(IOperation operation)
return _forceImplicit || operation.IsImplicit;
}
public static ControlFlowGraph Create(IOperation body, ControlFlowRegion enclosing = null, CaptureIdDispenser captureIdDispenser = null, in Context context = default)
public static ControlFlowGraph Create(IOperation body, ControlFlowGraph parent = null, ControlFlowRegion enclosing = null, CaptureIdDispenser captureIdDispenser = null, in Context context = default)
{
Debug.Assert(body != null);
Debug.Assert(((Operation)body).OwningSemanticModel != null);
......@@ -71,10 +71,12 @@ public static ControlFlowGraph Create(IOperation body, ControlFlowRegion enclosi
body.Kind == OperationKind.PropertyInitializer ||
body.Kind == OperationKind.ParameterInitializer,
$"Unexpected root operation kind: {body.Kind}");
Debug.Assert(parent == null);
}
else
{
Debug.Assert(body.Kind == OperationKind.LocalFunction || body.Kind == OperationKind.AnonymousFunction);
Debug.Assert(parent != null);
}
#endif
......@@ -135,7 +137,7 @@ public static ControlFlowGraph Create(IOperation body, ControlFlowRegion enclosi
builder._regionMap.Free();
builder._labeledBlocks?.Free();
return new ControlFlowGraph(body, builder._captureIdDispenser, ToImmutableBlocks(blocks), region,
return new ControlFlowGraph(body, parent, builder._captureIdDispenser, ToImmutableBlocks(blocks), region,
localFunctions.ToImmutableAndFree(), localFunctionsMap.ToImmutable(),
anonymousFunctionsMapOpt?.ToImmutable() ?? ImmutableDictionary<IFlowAnonymousFunctionOperation, (ControlFlowRegion, int)>.Empty);
}
......
// Copyright (c) Microsoft. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
using System.Threading;
namespace Microsoft.CodeAnalysis.FlowAnalysis
{
public static partial class ControlFlowGraphExtensions
{
/// <summary>
/// Gets or creates a control flow graph for the given <paramref name="localFunction"/> defined in
/// the given <paramref name="controlFlowGraph"/> or any of it's parent control flow graphs.
/// </summary>
public static ControlFlowGraph GetLocalFunctionControlFlowGraphInScope(this ControlFlowGraph controlFlowGraph, IMethodSymbol localFunction, CancellationToken cancellationToken = default)
{
if (controlFlowGraph == null)
{
throw new ArgumentNullException(nameof(controlFlowGraph));
}
if (localFunction == null)
{
throw new ArgumentNullException(nameof(localFunction));
}
do
{
if (controlFlowGraph.TryGetLocalFunctionControlFlowGraph(localFunction, cancellationToken, out ControlFlowGraph localFunctionControlFlowGraph))
{
return localFunctionControlFlowGraph;
}
}
while ((controlFlowGraph = controlFlowGraph.Parent) != null);
throw new ArgumentOutOfRangeException(nameof(localFunction));
}
/// <summary>
/// Gets or creates a control flow graph for the given <paramref name="anonymousFunction"/> defined in
/// the given <paramref name="controlFlowGraph"/> or any of it's parent control flow graphs.
/// </summary>
public static ControlFlowGraph GetAnonymousFunctionControlFlowGraphInScope(this ControlFlowGraph controlFlowGraph, IFlowAnonymousFunctionOperation anonymousFunction, CancellationToken cancellationToken = default)
{
if (controlFlowGraph == null)
{
throw new ArgumentNullException(nameof(controlFlowGraph));
}
if (anonymousFunction == null)
{
throw new ArgumentNullException(nameof(anonymousFunction));
}
do
{
if (controlFlowGraph.TryGetAnonymousFunctionControlFlowGraph(anonymousFunction, cancellationToken, out ControlFlowGraph localFunctionControlFlowGraph))
{
return localFunctionControlFlowGraph;
}
}
while ((controlFlowGraph = controlFlowGraph.Parent) != null);
throw new ArgumentOutOfRangeException(nameof(anonymousFunction));
}
}
}
......@@ -20,6 +20,8 @@ Microsoft.CodeAnalysis.Diagnostics.Telemetry.AnalyzerTelemetryInfo.SymbolStartAc
Microsoft.CodeAnalysis.FlowAnalysis.ControlFlowGraph.GetAnonymousFunctionControlFlowGraph(Microsoft.CodeAnalysis.FlowAnalysis.IFlowAnonymousFunctionOperation anonymousFunction, System.Threading.CancellationToken cancellationToken = default(System.Threading.CancellationToken)) -> Microsoft.CodeAnalysis.FlowAnalysis.ControlFlowGraph
Microsoft.CodeAnalysis.FlowAnalysis.ControlFlowGraph.GetLocalFunctionControlFlowGraph(Microsoft.CodeAnalysis.IMethodSymbol localFunction, System.Threading.CancellationToken cancellationToken = default(System.Threading.CancellationToken)) -> Microsoft.CodeAnalysis.FlowAnalysis.ControlFlowGraph
Microsoft.CodeAnalysis.FlowAnalysis.ControlFlowGraph.LocalFunctions.get -> System.Collections.Immutable.ImmutableArray<Microsoft.CodeAnalysis.IMethodSymbol>
Microsoft.CodeAnalysis.FlowAnalysis.ControlFlowGraph.Parent.get -> Microsoft.CodeAnalysis.FlowAnalysis.ControlFlowGraph
Microsoft.CodeAnalysis.FlowAnalysis.ControlFlowGraphExtensions
Microsoft.CodeAnalysis.FlowAnalysis.ControlFlowRegion.CaptureIds.get -> System.Collections.Immutable.ImmutableArray<Microsoft.CodeAnalysis.FlowAnalysis.CaptureId>
Microsoft.CodeAnalysis.FlowAnalysis.ControlFlowRegion.LocalFunctions.get -> System.Collections.Immutable.ImmutableArray<Microsoft.CodeAnalysis.IMethodSymbol>
Microsoft.CodeAnalysis.FlowAnalysis.ICaughtExceptionOperation
......@@ -145,6 +147,8 @@ static Microsoft.CodeAnalysis.FlowAnalysis.ControlFlowGraph.Create(Microsoft.Cod
static Microsoft.CodeAnalysis.FlowAnalysis.ControlFlowGraph.Create(Microsoft.CodeAnalysis.Operations.IParameterInitializerOperation initializer, System.Threading.CancellationToken cancellationToken = default(System.Threading.CancellationToken)) -> Microsoft.CodeAnalysis.FlowAnalysis.ControlFlowGraph
static Microsoft.CodeAnalysis.FlowAnalysis.ControlFlowGraph.Create(Microsoft.CodeAnalysis.Operations.IPropertyInitializerOperation initializer, System.Threading.CancellationToken cancellationToken = default(System.Threading.CancellationToken)) -> Microsoft.CodeAnalysis.FlowAnalysis.ControlFlowGraph
static Microsoft.CodeAnalysis.FlowAnalysis.ControlFlowGraph.Create(Microsoft.CodeAnalysis.SyntaxNode node, Microsoft.CodeAnalysis.SemanticModel semanticModel, System.Threading.CancellationToken cancellationToken = default(System.Threading.CancellationToken)) -> Microsoft.CodeAnalysis.FlowAnalysis.ControlFlowGraph
static Microsoft.CodeAnalysis.FlowAnalysis.ControlFlowGraphExtensions.GetAnonymousFunctionControlFlowGraphInScope(this Microsoft.CodeAnalysis.FlowAnalysis.ControlFlowGraph controlFlowGraph, Microsoft.CodeAnalysis.FlowAnalysis.IFlowAnonymousFunctionOperation anonymousFunction, System.Threading.CancellationToken cancellationToken = default(System.Threading.CancellationToken)) -> Microsoft.CodeAnalysis.FlowAnalysis.ControlFlowGraph
static Microsoft.CodeAnalysis.FlowAnalysis.ControlFlowGraphExtensions.GetLocalFunctionControlFlowGraphInScope(this Microsoft.CodeAnalysis.FlowAnalysis.ControlFlowGraph controlFlowGraph, Microsoft.CodeAnalysis.IMethodSymbol localFunction, System.Threading.CancellationToken cancellationToken = default(System.Threading.CancellationToken)) -> Microsoft.CodeAnalysis.FlowAnalysis.ControlFlowGraph
static Microsoft.CodeAnalysis.Operations.OperationExtensions.GetCorrespondingOperation(this Microsoft.CodeAnalysis.Operations.IBranchOperation operation) -> Microsoft.CodeAnalysis.IOperation
virtual Microsoft.CodeAnalysis.Diagnostics.AnalysisContext.RegisterSymbolStartAction(System.Action<Microsoft.CodeAnalysis.Diagnostics.SymbolStartAnalysisContext> action, Microsoft.CodeAnalysis.SymbolKind symbolKind) -> void
virtual Microsoft.CodeAnalysis.Diagnostics.CompilationStartAnalysisContext.RegisterSymbolStartAction(System.Action<Microsoft.CodeAnalysis.Diagnostics.SymbolStartAnalysisContext> action, Microsoft.CodeAnalysis.SymbolKind symbolKind) -> void
......
......@@ -73,6 +73,8 @@ Namespace Microsoft.CodeAnalysis.VisualBasic
''' <param name="additionalReferenceDirectories">A string representing additional reference paths.</param>
''' <returns>A CommandLineArguments object representing the parsed command line.</returns>
Public Shadows Function Parse(args As IEnumerable(Of String), baseDirectory As String, sdkDirectory As String, Optional additionalReferenceDirectories As String = Nothing) As VisualBasicCommandLineArguments
Debug.Assert(baseDirectory Is Nothing OrElse PathUtilities.IsAbsolute(baseDirectory))
Const GenerateFileNameForDocComment As String = "USE-OUTPUT-NAME"
Dim diagnostics As List(Of Diagnostic) = New List(Of Diagnostic)()
......@@ -1252,7 +1254,7 @@ lVbRuntimePlus:
End If
' add additional reference paths if specified
If Not String.IsNullOrWhiteSpace(additionalReferenceDirectories) Then
If Not String.IsNullOrEmpty(additionalReferenceDirectories) Then
libPaths.AddRange(ParseSeparatedPaths(additionalReferenceDirectories))
End If
......@@ -1260,7 +1262,7 @@ lVbRuntimePlus:
Dim searchPaths As ImmutableArray(Of String) = BuildSearchPaths(baseDirectory, sdkPaths, responsePaths, libPaths)
' Public sign doesn't use legacy search path settings
If publicSign AndAlso Not String.IsNullOrWhiteSpace(keyFileSetting) Then
If publicSign AndAlso Not String.IsNullOrEmpty(keyFileSetting) Then
keyFileSetting = ParseGenericPathToFile(keyFileSetting, diagnostics, baseDirectory)
End If
......@@ -1291,8 +1293,11 @@ lVbRuntimePlus:
' Dev10 searches for the keyfile in the current directory and assembly output directory.
' We always look to base directory and then examine the search paths.
keyFileSearchPaths.Add(baseDirectory)
If baseDirectory <> outputDirectory Then
If Not String.IsNullOrEmpty(baseDirectory) Then
keyFileSearchPaths.Add(baseDirectory)
End If
If Not String.IsNullOrEmpty(outputDirectory) AndAlso baseDirectory <> outputDirectory Then
keyFileSearchPaths.Add(outputDirectory)
End If
......
......@@ -3188,6 +3188,12 @@ print Goodbye, World"
Assert.Equal(New KeyValuePair(Of String, String)("/temp/", "/bar/"), doublemap(1))
End Sub
<Fact>
Public Sub NothingBaseDirectoryNotAddedToKeyFileSearchPaths()
Dim args As VisualBasicCommandLineArguments = VisualBasicCommandLineParser.Default.Parse(New String() {}, Nothing, RuntimeEnvironment.GetRuntimeDirectory())
AssertEx.Equal(ImmutableArray.Create(Of String)(), args.KeyFileSearchPaths)
End Sub
<CompilerTrait(CompilerFeature.Determinism)>
<Fact>
Public Sub PathMapPdbDeterminism()
......
// Copyright (c) Microsoft. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Collections.Generic;
using System.Threading.Tasks;
using Microsoft.CodeAnalysis.CodeFixes;
using Microsoft.CodeAnalysis.CSharp;
......@@ -3989,6 +3990,80 @@ static void Main()
}");
}
[WorkItem(29264, "https://github.com/dotnet/roslyn/issues/29264")]
[Fact, Trait(Traits.Feature, Traits.Features.CodeActionsRemoveUnnecessaryCast)]
public async Task DontRemoveCastOnDictionaryIndexer()
{
await TestMissingInRegularAndScriptAsync(
@"
using System;
using System.Reflection;
using System.Collections.Generic;
static class Program
{
enum TestEnum
{
Test,
}
static void Main()
{
Dictionary<int, string> Icons = new Dictionary<int, string>
{
[[|(int)|] TestEnum.Test] = null,
};
}
}");
}
[WorkItem(29264, "https://github.com/dotnet/roslyn/issues/29264")]
[Fact, Trait(Traits.Feature, Traits.Features.CodeActionsRemoveUnnecessaryCast)]
public async Task RemoveCastOnDictionaryIndexer()
{
await TestInRegularAndScriptAsync(
@"
using System;
using System.Reflection;
using System.Collections.Generic;
static class Program
{
enum TestEnum
{
Test,
}
static void Main()
{
Dictionary<int, string> Icons = new Dictionary<int, string>
{
[[|(int)|] 0] = null,
};
}
}",
@"
using System;
using System.Reflection;
using System.Collections.Generic;
static class Program
{
enum TestEnum
{
Test,
}
static void Main()
{
Dictionary<int, string> Icons = new Dictionary<int, string>
{
[0] = null,
};
}
}");
}
[WorkItem(20630, "https://github.com/dotnet/roslyn/issues/20630")]
[Fact, Trait(Traits.Feature, Traits.Features.CodeActionsRemoveUnnecessaryCast)]
public async Task DontRemoveCastOnCallToAttributeWithParamsArgsAndProperty()
......
......@@ -2,6 +2,7 @@
using System.Linq;
using Microsoft.CodeAnalysis.CSharp;
using Microsoft.CodeAnalysis.CSharp.Syntax;
using Xunit;
using SyntaxUtilities = Microsoft.CodeAnalysis.CSharp.EditAndContinue.SyntaxUtilities;
......@@ -59,5 +60,96 @@ static void Main(string[] args)
";
VerifySyntaxMap(source1, source2);
}
[Fact]
public void FindLeafNodeAndPartner1()
{
var leftRoot = SyntaxFactory.ParseSyntaxTree(@"
using System;
class C
{
public void M()
{
if (0 == 1)
{
Console.WriteLine(0);
}
}
}
").GetRoot();
var leftPosition = leftRoot.DescendantNodes().OfType<LiteralExpressionSyntax>().ElementAt(2).SpanStart; // 0 within Console.WriteLine(0)
var rightRoot = SyntaxFactory.ParseSyntaxTree(@"
using System;
class C
{
public void M()
{
if (0 == 1)
{
if (2 == 3)
{
Console.WriteLine(0);
}
}
}
}
").GetRoot();
SyntaxUtilities.FindLeafNodeAndPartner(leftRoot, leftPosition, rightRoot, out SyntaxNode leftNode, out SyntaxNode rightNodeOpt);
Assert.Equal("0", leftNode.ToString());
Assert.Null(rightNodeOpt);
}
[Fact]
public void FindLeafNodeAndPartner2()
{
// Check that the method does not fail even if the index of the child (4)
// is greater than the count of children on the corresponding (from the upper side) node (3).
var leftRoot = SyntaxFactory.ParseSyntaxTree(@"
using System;
class C
{
public void M()
{
if (0 == 1)
{
Console.WriteLine(0);
Console.WriteLine(1);
Console.WriteLine(2);
Console.WriteLine(3);
}
}
}
").GetRoot();
var leftPosition = leftRoot.DescendantNodes().OfType<LiteralExpressionSyntax>().ElementAt(5).SpanStart; // 3 within Console.WriteLine(3)
var rightRoot = SyntaxFactory.ParseSyntaxTree(@"
using System;
class C
{
public void M()
{
if (0 == 1)
{
if (2 == 3)
{
Console.WriteLine(0);
Console.WriteLine(1);
Console.WriteLine(2);
Console.WriteLine(3);
}
}
}
}
").GetRoot();
SyntaxUtilities.FindLeafNodeAndPartner(leftRoot, leftPosition, rightRoot, out SyntaxNode leftNode, out SyntaxNode rightNodeOpt);
Assert.Equal("3", leftNode.ToString());
Assert.Null(rightNodeOpt);
}
}
}
// Copyright (c) Microsoft. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Threading.Tasks;
using Microsoft.CodeAnalysis.CodeFixes;
using Microsoft.CodeAnalysis.CSharp.OrderModifiers;
using Microsoft.CodeAnalysis.Diagnostics;
using Microsoft.CodeAnalysis.Editor.CSharp.UnitTests.Diagnostics;
using Microsoft.CodeAnalysis.Test.Utilities;
using Roslyn.Test.Utilities;
using Xunit;
namespace Microsoft.CodeAnalysis.Editor.CSharp.UnitTests.OrderModifiers
{
public sealed class OrderModifiersCompilerErrorTests : AbstractCSharpDiagnosticProviderBasedUserDiagnosticTest
{
internal override (DiagnosticAnalyzer, CodeFixProvider) CreateDiagnosticProviderAndFixer(Workspace workspace)
=> (null, new CSharpOrderModifiersCodeFixProvider());
[WorkItem(30352, "https://github.com/dotnet/roslyn/issues/30352")]
[Fact, Trait(Traits.Feature, Traits.Features.CodeActionsOrderModifiers)]
public async Task PartialAtTheEnd()
{
// Verify that the code fix claims it fixes the compiler error (CS0267) in addition to the analyzer diagnostic.
await TestInRegularAndScript1Async(
@"[|partial|] public class C { }",
@"public partial class C { }");
}
}
}
......@@ -274,5 +274,97 @@ internal static class C
#endif
");
}
[Fact, Trait(Traits.Feature, Traits.Features.CodeActionsOrderModifiers)]
public async Task PartialAtTheEndClass1()
{
await TestInRegularAndScript1Async(
@"[|partial|] public class C { }",
@"public partial class C { }");
}
[Fact, Trait(Traits.Feature, Traits.Features.CodeActionsOrderModifiers)]
public async Task PartialAtTheEndClass2()
{
await TestInRegularAndScript1Async(
@"[|partial|] abstract class C { }",
@"abstract partial class C { }");
}
[Fact, Trait(Traits.Feature, Traits.Features.CodeActionsOrderModifiers)]
public async Task PartialAtTheEndClass3()
{
await TestInRegularAndScript1Async(
@"[|partial|] sealed class C { }",
@"sealed partial class C { }");
}
[Fact, Trait(Traits.Feature, Traits.Features.CodeActionsOrderModifiers)]
public async Task PartialAtTheEndClass4()
{
await TestInRegularAndScript1Async(
@"[|partial|] static class C { }",
@"static partial class C { }");
}
[Fact, Trait(Traits.Feature, Traits.Features.CodeActionsOrderModifiers)]
public async Task PartialAtTheEndClass5()
{
await TestInRegularAndScript1Async(
@"[|partial|] unsafe class C { }",
@"unsafe partial class C { }");
}
[Fact, Trait(Traits.Feature, Traits.Features.CodeActionsOrderModifiers)]
public async Task PartialAtTheEndStruct1()
{
await TestInRegularAndScript1Async(
@"[|partial|] public struct S { }",
@"public partial struct S { }");
}
[Fact, Trait(Traits.Feature, Traits.Features.CodeActionsOrderModifiers)]
public async Task PartialAtTheEndStruct2()
{
await TestInRegularAndScript1Async(
@"[|partial|] unsafe struct S { }",
@"unsafe partial struct S { }");
}
[Fact, Trait(Traits.Feature, Traits.Features.CodeActionsOrderModifiers)]
public async Task PartialAtTheEndInterface()
{
await TestInRegularAndScript1Async(
@"[|partial|] public interface I { }",
@"public partial interface I { }");
}
[Fact, Trait(Traits.Feature, Traits.Features.CodeActionsOrderModifiers)]
public async Task PartialAtTheEndMethod1()
{
await TestInRegularAndScript1Async(
@"partial class C
{
[|partial|] static void M();
}",
@"partial class C
{
static partial void M();
}");
}
[Fact, Trait(Traits.Feature, Traits.Features.CodeActionsOrderModifiers)]
public async Task PartialAtTheEndMethod2()
{
await TestInRegularAndScript1Async(
@"partial class C
{
[|partial|] unsafe void M();
}",
@"partial class C
{
unsafe partial void M();
}");
}
}
}
......@@ -1243,6 +1243,22 @@ public async Task TestFalseKeyword()
MainDescription("struct System.Boolean"));
}
[WorkItem(26027, "https://github.com/dotnet/roslyn/issues/26027")]
[Fact, Trait(Traits.Feature, Traits.Features.QuickInfo)]
public async Task TestNullLiteral()
{
await TestInMethodAsync(@"string f = null$$",
MainDescription("class System.String"));
}
[WorkItem(26027, "https://github.com/dotnet/roslyn/issues/26027")]
[Fact, Trait(Traits.Feature, Traits.Features.QuickInfo)]
public async Task TestDefaultLiteral()
{
await TestInMethodAsync(@"string f = default$$",
MainDescription("class System.String"));
}
[WorkItem(756226, "http://vstfdevdiv:8080/DevDiv2/DevDiv/_workitems/edit/756226")]
[Fact, Trait(Traits.Feature, Traits.Features.QuickInfo)]
public async Task TestAwaitKeywordOnGenericTaskReturningAsync()
......
......@@ -108,6 +108,44 @@ Namespace Microsoft.CodeAnalysis.Editor.UnitTests.Workspaces
Await TestCSharpAsync(workspace, $"({FeaturesResources.local_constant}) int x = 2")
End Function
<Fact>
Public Async Function TestCSharpNullLiteralVar() As Task
Dim workspace =
<Workspace>
<Project Language="C#" CommonReferences="true">
<Document>
class Goo
{
void Method()
{
var x = nu$$ll
}
}
</Document>
</Project>
</Workspace>
Await TestCSharpAsync(workspace, "")
End Function
<Fact>
Public Async Function TestCSharpNullLiteralString() As Task
Dim workspace =
<Workspace>
<Project Language="C#" CommonReferences="true">
<Document>
class Goo
{
void Method()
{
string x = nu$$ll
}
}
</Document>
</Project>
</Workspace>
Await TestCSharpAsync(workspace, "class System.String")
End Function
#End Region
#Region "Basic SymbolDescription Tests"
......@@ -508,9 +546,8 @@ Namespace Microsoft.CodeAnalysis.Editor.UnitTests.Workspaces
Await TestBasicAsync(workspace, "Structure System.DateTime")
End Function
''' Design change from Dev10
<Fact>
Public Async Function TestNothingLiteral() As Task
Public Async Function TestNothingLiteralDim() As Task
Dim workspace =
<Workspace>
<Project Language="Visual Basic" CommonReferences="true">
......@@ -523,7 +560,40 @@ Namespace Microsoft.CodeAnalysis.Editor.UnitTests.Workspaces
</Document>
</Project>
</Workspace>
Await TestBasicAsync(workspace, "")
Await TestBasicAsync(workspace, "Class System.Object")
End Function
<Fact>
Public Async Function TestNothingLiteralDimAsString() As Task
Dim workspace =
<Workspace>
<Project Language="Visual Basic" CommonReferences="true">
<Document>
Class Goo
Sub Method()
Dim x As String = Nothin$$g
End Sub
End Class
</Document>
</Project>
</Workspace>
Await TestBasicAsync(workspace, "Class System.String")
End Function
<Fact>
Public Async Function TestNothingLiteralFieldDimOptionStrict() As Task
Dim workspace =
<Workspace>
<Project Language="Visual Basic" CommonReferences="true">
<Document>
Option Strict On
Class Goo
Dim x = Nothin$$g
End Class
</Document>
</Project>
</Workspace>
Await TestBasicAsync(workspace, "Class System.Object")
End Function
<Fact>
......
' Copyright (c) Microsoft. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
Imports Microsoft.CodeAnalysis.VisualBasic.Syntax
Imports SyntaxUtilities = Microsoft.CodeAnalysis.VisualBasic.EditAndContinue.SyntaxUtilities
Namespace Microsoft.CodeAnalysis.Editor.VisualBasic.UnitTests.EditAndContinue
......@@ -47,5 +48,84 @@ End Class
"
VerifySyntaxMap(source1, source2)
End Sub
<Fact>
Public Sub FindLeafNodeAndPartner1()
Dim leftRoot = SyntaxFactory.ParseSyntaxTree("
Imports System;
Class C
Public Sub M()
If 0 = 1 Then
Console.WriteLine(0)
End If
End Sub
End Class
").GetRoot()
Dim leftPosition = leftRoot.DescendantNodes().OfType(Of LiteralExpressionSyntax).ElementAt(2).SpanStart '0 within Console.WriteLine(0)
Dim rightRoot = SyntaxFactory.ParseSyntaxTree("
Imports System;
Class C
Public Sub M()
If 0 = 1 Then
If 2 = 3 Then
Console.WriteLine(0)
End If
End If
End Sub
End Class
").GetRoot()
Dim leftNode As SyntaxNode = Nothing
Dim rightNodeOpt As SyntaxNode = Nothing
SyntaxUtilities.FindLeafNodeAndPartner(leftRoot, leftPosition, rightRoot, leftNode, rightNodeOpt)
Assert.Equal("0", leftNode.ToString())
Assert.Null(rightNodeOpt)
End Sub
<Fact>
Public Sub FindLeafNodeAndPartner2()
' Check that the method does Not fail even if the index of the child (4)
' is greater than the count of children on the corresponding (from the upper side) node (3).
Dim leftRoot = SyntaxFactory.ParseSyntaxTree("
Imports System;
Class C
Public Sub M()
If 0 = 1 Then
Console.WriteLine(0)
Console.WriteLine(1)
Console.WriteLine(2)
Console.WriteLine(3)
End If
End Sub
End Class
").GetRoot()
Dim leftPosition = leftRoot.DescendantNodes().OfType(Of LiteralExpressionSyntax).ElementAt(5).SpanStart '3 within Console.WriteLine(3)
Dim rightRoot = SyntaxFactory.ParseSyntaxTree("
Imports System;
Class C
Public Sub M()
If 0 = 1 Then
If 2 = 3 Then
Console.WriteLine(0)
Console.WriteLine(1)
Console.WriteLine(2)
Console.WriteLine(3)
End If
End If
End Sub
End Class
").GetRoot()
Dim leftNode As SyntaxNode = Nothing
Dim rightNodeOpt As SyntaxNode = Nothing
SyntaxUtilities.FindLeafNodeAndPartner(leftRoot, leftPosition, rightRoot, leftNode, rightNodeOpt)
Assert.Equal("3", leftNode.ToString())
Assert.Null(rightNodeOpt)
End Sub
End Class
End Namespace
......@@ -1745,6 +1745,31 @@ End Class]]></text>.NormalizedValue(),
Text("cref."))))
End Function
<Fact, Trait(Traits.Feature, Traits.Features.QuickInfo)>
Public Async Function TestIntegerLiteral() As Task
Await TestInMethodAsync("Dim f = 37$$",
MainDescription("Structure System.Int32"))
End Function
<Fact, Trait(Traits.Feature, Traits.Features.QuickInfo)>
Public Async Function TestTrueKeyword() As Task
Await TestInMethodAsync("Dim f = True$$",
MainDescription("Structure System.Boolean"))
End Function
<Fact, Trait(Traits.Feature, Traits.Features.QuickInfo)>
Public Async Function TestFalseKeyword() As Task
Await TestInMethodAsync("Dim f = False$$",
MainDescription("Structure System.Boolean"))
End Function
<WorkItem(26027, "https://github.com/dotnet/roslyn/issues/26027")>
<Fact, Trait(Traits.Feature, Traits.Features.QuickInfo)>
Public Async Function TestNothingLiteral() As Task
Await TestInMethodAsync("Dim f As String = Nothing$$",
MainDescription("Class System.String"))
End Function
''' <Remarks>
''' As a part of fix for 756226, quick info for VB Await keyword now displays the type inferred from the AwaitExpression. This is C# behavior.
''' In Dev12, quick info for VB Await keyword was the syntactic help "Await &lt;expression&gt;".
......
......@@ -114,20 +114,36 @@ public static void AssertIsBody(SyntaxNode syntax, bool allowLambda)
Debug.Assert(false);
}
public static void FindLeafNodeAndPartner(SyntaxNode leftRoot, int leftPosition, SyntaxNode rightRoot, out SyntaxNode leftNode, out SyntaxNode rightNode)
public static void FindLeafNodeAndPartner(SyntaxNode leftRoot, int leftPosition, SyntaxNode rightRoot, out SyntaxNode leftNode, out SyntaxNode rightNodeOpt)
{
leftNode = leftRoot;
rightNode = rightRoot;
rightNodeOpt = rightRoot;
while (true)
{
Debug.Assert(leftNode.RawKind == rightNode.RawKind);
if (rightNodeOpt != null && leftNode.RawKind != rightNodeOpt.RawKind)
{
rightNodeOpt = null;
}
var leftChild = leftNode.ChildThatContainsPosition(leftPosition, out var childIndex);
if (leftChild.IsToken)
{
return;
}
rightNode = rightNode.ChildNodesAndTokens()[childIndex].AsNode();
if (rightNodeOpt != null)
{
var rightNodeChildNodesAndTokens = rightNodeOpt.ChildNodesAndTokens();
if (childIndex >= 0 && childIndex < rightNodeChildNodesAndTokens.Count)
{
rightNodeOpt = rightNodeChildNodesAndTokens[childIndex].AsNode();
}
else
{
rightNodeOpt = null;
}
}
leftNode = leftChild.AsNode();
}
}
......
// Copyright (c) Microsoft. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System.Collections.Generic;
using System.Collections.Immutable;
using System.Composition;
using Microsoft.CodeAnalysis.CodeFixes;
using Microsoft.CodeAnalysis.CSharp.CodeStyle;
......@@ -12,9 +13,13 @@ namespace Microsoft.CodeAnalysis.CSharp.OrderModifiers
[ExportCodeFixProvider(LanguageNames.CSharp), Shared]
internal class CSharpOrderModifiersCodeFixProvider : AbstractOrderModifiersCodeFixProvider
{
private const string CS0267 = nameof(CS0267); // The 'partial' modifier can only appear immediately before 'class', 'struct', 'interface', or 'void'
public CSharpOrderModifiersCodeFixProvider()
: base(CSharpSyntaxFactsService.Instance, CSharpCodeStyleOptions.PreferredModifierOrder, CSharpOrderModifiersHelper.Instance)
{
}
protected override ImmutableArray<string> FixableCompilerErrorIds { get; } = ImmutableArray.Create(CS0267);
}
}
......@@ -33,15 +33,22 @@ internal abstract class AbstractOrderModifiersCodeFixProvider : SyntaxEditorBase
_helpers = helpers;
}
public override ImmutableArray<string> FixableDiagnosticIds { get; } =
ImmutableArray.Create(IDEDiagnosticIds.OrderModifiersDiagnosticId);
protected abstract ImmutableArray<string> FixableCompilerErrorIds { get; }
public override Task RegisterCodeFixesAsync(CodeFixContext context)
public sealed override ImmutableArray<string> FixableDiagnosticIds
=> FixableCompilerErrorIds.Add(IDEDiagnosticIds.OrderModifiersDiagnosticId);
public override async Task RegisterCodeFixesAsync(CodeFixContext context)
{
context.RegisterCodeFix(
new MyCodeAction(c => FixAsync(context.Document, context.Diagnostics[0], c)),
context.Diagnostics);
return Task.CompletedTask;
var syntaxTree = await context.Document.GetSyntaxTreeAsync(context.CancellationToken).ConfigureAwait(false);
var syntaxNode = Location.Create(syntaxTree, context.Span).FindNode(context.CancellationToken);
if (_syntaxFacts.GetModifiers(syntaxNode) != default)
{
context.RegisterCodeFix(
new MyCodeAction(c => FixAsync(context.Document, context.Diagnostics[0], c)),
context.Diagnostics);
}
}
protected override async Task FixAllAsync(
......
......@@ -67,18 +67,29 @@ Namespace Microsoft.CodeAnalysis.VisualBasic.EditAndContinue
leftPosition As Integer,
rightRoot As SyntaxNode,
<Out> ByRef leftNode As SyntaxNode,
<Out> ByRef rightNode As SyntaxNode)
<Out> ByRef rightNodeOpt As SyntaxNode)
leftNode = leftRoot
rightNode = rightRoot
rightNodeOpt = rightRoot
While True
Debug.Assert(leftNode.RawKind = rightNode.RawKind)
If rightNodeOpt IsNot Nothing AndAlso leftNode.RawKind <> rightNodeOpt.RawKind Then
rightNodeOpt = Nothing
End If
Dim childIndex As Integer = 0
Dim leftChild = leftNode.ChildThatContainsPosition(leftPosition, childIndex)
If leftChild.IsToken Then
Return
End If
rightNode = rightNode.ChildNodesAndTokens()(childIndex).AsNode()
If rightNodeOpt IsNot Nothing Then
Dim rightNodeChildNodesAndTokens = rightNodeOpt.ChildNodesAndTokens()
If childIndex >= 0 AndAlso childIndex < rightNodeChildNodesAndTokens.Count Then
rightNodeOpt = rightNodeChildNodesAndTokens(childIndex).AsNode()
Else
rightNodeOpt = Nothing
End If
End If
leftNode = leftChild.AsNode()
End While
End Sub
......
' Copyright (c) Microsoft. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
Imports System.Collections.Immutable
Imports System.Composition
Imports Microsoft.CodeAnalysis.CodeFixes
Imports Microsoft.CodeAnalysis.OrderModifiers
......@@ -15,5 +16,8 @@ Namespace Microsoft.CodeAnalysis.VisualBasic.OrderModifiers
VisualBasicCodeStyleOptions.PreferredModifierOrder,
VisualBasicOrderModifiersHelper.Instance)
End Sub
Protected Overrides ReadOnly Property FixableCompilerErrorIds As ImmutableArray(Of String) =
ImmutableArray(Of String).Empty
End Class
End Namespace
......@@ -311,6 +311,8 @@ public static string GetFlowGraph(Compilation compilation, ControlFlowGraph grap
{
ControlFlowGraph g = localFunctionsMap[m];
Assert.Same(g, graph.GetLocalFunctionControlFlowGraph(m));
Assert.Same(g, graph.GetLocalFunctionControlFlowGraphInScope(m));
Assert.Same(graph, g.Parent);
}
Assert.Equal(graph.LocalFunctions.Length, localFunctionsMap.Count);
......@@ -318,6 +320,8 @@ public static string GetFlowGraph(Compilation compilation, ControlFlowGraph grap
foreach (KeyValuePair<IFlowAnonymousFunctionOperation, ControlFlowGraph> pair in anonymousFunctionsMap)
{
Assert.Same(pair.Value, graph.GetAnonymousFunctionControlFlowGraph(pair.Key));
Assert.Same(pair.Value, graph.GetAnonymousFunctionControlFlowGraphInScope(pair.Key));
Assert.Same(graph, pair.Value.Parent);
}
bool doCaptureVerification = true;
......
<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="14.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<!-- This is executed from our Microbuild runs to drive official builds only -->
<PropertyGroup>
<Configuration Condition="'$(Configuration)' == ''">Debug</Configuration>
<ScriptArgs></ScriptArgs>
<ScriptArgs Condition="'$(Configuration)' == 'Release'">-release</ScriptArgs>
<ScriptArgs Condition="'$(BUILD_SOURCEBRANCH)' != ''">$(ScriptArgs) -branch $(BUILD_SOURCEBRANCH)</ScriptArgs>
<ScriptArgs Condition="'$(RoslynNuGetApiKey)' != ''">$(ScriptArgs) -myGetApiKey $(RoslynNuGetApiKey)</ScriptArgs>
<ScriptArgs Condition="'$(RoslynGitHubToken)' != ''">$(ScriptArgs) -gitHubUserName $(RoslynGitHubUserName) -gitHubToken $(RoslynGitHubToken) -gitHubEmail $(RoslynGitHubEmail)</ScriptArgs>
<ScriptArgs Condition="'$(PB_SkipTests)' != 'true'">$(ScriptArgs) -testDesktop</ScriptArgs>
<ScriptArgs Condition="'$(PB_SignType)' == 'real'">$(ScriptArgs) -signType "real"</ScriptArgs>
<ScriptArgs Condition="'$(PB_SignType)' == 'test'">$(ScriptArgs) -signType "test"</ScriptArgs>
<ScriptArgs Condition="'$(PB_PublishType)' == 'vsts'">$(ScriptArgs) -publishType "vsts"</ScriptArgs>
<ScriptArgs Condition="'$(PB_PublishType)' == 'blob'">$(ScriptArgs) -publishType "blob"</ScriptArgs>
<ScriptArgs Condition="'$(PB_PublishBlobFeedUrl)' != ''">$(ScriptArgs) -blobFeedUrl $(PB_PublishBlobFeedUrl) -blobFeedKey $(PB_PublishBlobFeedKey)</ScriptArgs>
</PropertyGroup>
<Target Name="Build">
<Exec Command="powershell -noprofile -executionPolicy ByPass -file $(MSBuildThisFileDirectory)microbuild.ps1 -official $(ScriptArgs) " />
<ItemGroup>
<_PublishProps Include="Configuration=$(Configuration)"/>
<_PublishProps Include="ContinuousIntegrationBuild=true"/>
<_PublishProps Include="AzureFeedUrl=$(PB_PublishBlobFeedUrl)" Condition="'$(PB_PublishType)' == 'blob'" />
<_PublishProps Include="AzureAccountKey=$(PB_PublishBlobFeedKey)" Condition="'$(PB_PublishType)' == 'blob'" />
</ItemGroup>
<MSBuild Projects="..\..\..\build\Targets\RepoToolset\Publish.proj"
Properties="@(_PublishProps)"
Targets="Publish" />
</Target>
</Project>
powershell -noprofile -executionPolicy RemoteSigned -file "%~dp0\microbuild.ps1" -release
REM stub file (remove once netci.groovy is updated)
\ No newline at end of file
[CmdletBinding(PositionalBinding=$false)]
param (
[switch]$release = $false,
[switch]$official = $false,
[string]$branchName = "master",
[switch]$testDesktop = $false,
[string]$publishType = "",
[switch]$help = $false,
[string]$signType = "",
# Credentials
[string]$myGetApiKey = "",
[string]$nugetApiKey = "",
[string]$gitHubUserName = "",
[string]$gitHubToken = "",
[string]$gitHubEmail = "",
[string]$blobFeedUrl = "",
[string]$blobFeedKey = "",
[parameter(ValueFromRemainingArguments=$true)] $badArgs)
Set-StrictMode -version 2.0
$ErrorActionPreference = "Stop"
function Print-Usage() {
Write-Host "Usage: build.ps1"
Write-Host " -release Perform release build (default is debug)"
Write-Host " -official Perform an official build"
Write-Host " -testDesktop Run unit tests"
Write-Host " -publishType Publish to run: vsts, blob or none (default is none)"
Write-Host " -branchName Branch being built"
Write-Host " -nugetApiKey Key for NuGet publishing"
Write-Host " -signType Signing type: real, test or public (default is public)"
Write-Host " -help Print this message"
}
Push-Location $PSScriptRoot
try {
. (Join-Path $PSScriptRoot "..\..\..\build\scripts\build-utils.ps1")
if ($badArgs -ne $null) {
Write-Host "Unsupported argument $badArgs"
Print-Usage
exit 1
}
if ($help) {
Print-Usage
exit 1
}
# On Jenkins runs we deliberately run microbuild with a clean NuGet cache. This means at least
# one job runs with a clean cache and assures all packages we depend on are restored during
# the restore phase. As opposed to getting lucky based on a NuGet being available in the cache.
if (-not $official) {
Clear-PackageCache
}
$scriptDir = Join-Path $repoDir "build\scripts"
$config = if ($release) { "Release" } else { "Debug" }
$configDir = Join-Path $binariesDir $config
$setupDir = Join-Path $repoDir "src\Setup"
Exec-Block { & (Join-Path $scriptDir "build.ps1") -restore:$true -build -cibuild:$true -official:$official -release:$release -sign -signType $signType -pack -testDesktop:$testDesktop -binaryLog -procdump }
Get-Process vbcscompiler -ErrorAction SilentlyContinue | Stop-Process
switch ($publishType) {
"vsts" {
Exec-Block { & .\publish-assets.ps1 -config $config -branchName $branchName -mygetApiKey $mygetApiKey -nugetApiKey $nugetApiKey -gitHubUserName $githubUserName -gitHubToken $gitHubToken -gitHubEmail $gitHubEmail -test:$(-not $official) }
break;
}
"blob" {
# This is handled by the Build.proj file directly
break;
}
"" {
# Explicit don't publish
break;
}
default {
throw "Unexpected publish type: $publishType"
break;
}
}
exit 0
}
catch {
Write-Host $_
Write-Host $_.Exception
Write-Host $_.ScriptStackTrace
exit 1
}
finally {
Pop-Location
if (-not $official) {
Get-Process msbuild -ErrorAction SilentlyContinue | Stop-Process
Get-Process vbcscompiler -ErrorAction SilentlyContinue | Stop-Process
}
}
\ No newline at end of file
......@@ -26,7 +26,7 @@ Namespace Microsoft.VisualStudio.LanguageServices.VisualBasic.ProjectSystemShim
Private Shared s_conditionalCompilationSymbolsCache As Dictionary(Of KeyValuePair(Of String, OutputKind), ImmutableArray(Of KeyValuePair(Of String, Object))) =
New Dictionary(Of KeyValuePair(Of String, OutputKind), ImmutableArray(Of KeyValuePair(Of String, Object)))
Private Shared ReadOnly s_EmptyCommandLineArguments As VisualBasicCommandLineArguments = VisualBasicCommandLineParser.Default.Parse(SpecializedCollections.EmptyEnumerable(Of String)(), baseDirectory:="", sdkDirectory:=Nothing)
Private Shared ReadOnly s_EmptyCommandLineArguments As VisualBasicCommandLineArguments = VisualBasicCommandLineParser.Default.Parse(SpecializedCollections.EmptyEnumerable(Of String)(), baseDirectory:=Nothing, sdkDirectory:=Nothing)
Public Shared Function CreateCompilationOptions(baseCompilationOptionsOpt As VisualBasicCompilationOptions,
newParseOptions As VisualBasicParseOptions,
......
......@@ -512,7 +512,8 @@ protected override bool ExpressionMightReferenceMember(SyntaxNode node)
{
return node.IsKind(SyntaxKind.InvocationExpression) ||
node.IsKind(SyntaxKind.ElementAccessExpression) ||
node.IsKind(SyntaxKind.SimpleMemberAccessExpression);
node.IsKind(SyntaxKind.SimpleMemberAccessExpression) ||
node.IsKind(SyntaxKind.ImplicitElementAccess);
}
protected override ImmutableArray<ArgumentSyntax> GetArguments(ExpressionSyntax expression)
......
......@@ -16,12 +16,13 @@ namespace Microsoft.CodeAnalysis.Shared.Extensions
internal struct TokenSemanticInfo
{
public static readonly TokenSemanticInfo Empty = new TokenSemanticInfo(
null, null, ImmutableArray<ISymbol>.Empty, null, default(TextSpan));
null, null, ImmutableArray<ISymbol>.Empty, null, null, default(TextSpan));
public readonly ISymbol DeclaredSymbol;
public readonly IAliasSymbol AliasSymbol;
public readonly ImmutableArray<ISymbol> ReferencedSymbols;
public readonly ITypeSymbol Type;
public readonly ITypeSymbol ConvertedType;
public readonly TextSpan Span;
public TokenSemanticInfo(
......@@ -29,12 +30,14 @@ internal struct TokenSemanticInfo
IAliasSymbol aliasSymbol,
ImmutableArray<ISymbol> referencedSymbols,
ITypeSymbol type,
ITypeSymbol convertedType,
TextSpan span)
{
DeclaredSymbol = declaredSymbol;
AliasSymbol = aliasSymbol;
ReferencedSymbols = referencedSymbols;
Type = type;
ConvertedType = convertedType;
Span = span;
}
......@@ -47,7 +50,7 @@ public ImmutableArray<ISymbol> GetSymbols(bool includeType)
if (includeType)
{
result.AddIfNotNull(Type);
result.AddIfNotNull(Type ?? ConvertedType);
}
return result.ToImmutableAndFree();
......@@ -179,6 +182,7 @@ private static ISymbol MapSymbol(ISymbol symbol, ITypeSymbol type)
{
IAliasSymbol aliasSymbol;
ITypeSymbol type;
ITypeSymbol convertedType;
ISymbol declaredSymbol;
ImmutableArray<ISymbol> allSymbols;
......@@ -192,6 +196,7 @@ private static ISymbol MapSymbol(ISymbol symbol, ITypeSymbol type)
// on an "override" token, the overridden symbol is the only part of TokenSemanticInfo used by callers, so type doesn't matter
type = null;
convertedType = null;
declaredSymbol = null;
allSymbols = overriddenSymbol is null ? ImmutableArray<ISymbol>.Empty : ImmutableArray.Create(overriddenSymbol);
}
......@@ -199,7 +204,9 @@ private static ISymbol MapSymbol(ISymbol symbol, ITypeSymbol type)
{
aliasSymbol = semanticModel.GetAliasInfo(token.Parent, cancellationToken);
var bindableParent = syntaxFacts.GetBindableParent(token);
type = semanticModel.GetTypeInfo(bindableParent, cancellationToken).Type;
var typeInfo = semanticModel.GetTypeInfo(bindableParent, cancellationToken);
type = typeInfo.Type;
convertedType = typeInfo.ConvertedType;
declaredSymbol = MapSymbol(semanticFacts.GetDeclaredSymbol(semanticModel, token, cancellationToken), type);
var skipSymbolInfoLookup = declaredSymbol.IsKind(SymbolKind.RangeVariable);
......@@ -238,9 +245,10 @@ private static ISymbol MapSymbol(ISymbol symbol, ITypeSymbol type)
if (allSymbols.Length == 0 && syntaxFacts.IsQueryKeyword(token))
{
type = null;
convertedType = null;
}
return new TokenSemanticInfo(declaredSymbol, aliasSymbol, allSymbols, type, token.Span);
return new TokenSemanticInfo(declaredSymbol, aliasSymbol, allSymbols, type, convertedType, token.Span);
}
public static SemanticModel GetOriginalSemanticModel(this SemanticModel semanticModel)
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册