summaryrefslogtreecommitdiff
path: root/tests/src/performance
diff options
context:
space:
mode:
Diffstat (limited to 'tests/src/performance')
-rw-r--r--tests/src/performance/linkbench/assets/MusicStore/MusicStoreReflection.xml27
-rw-r--r--tests/src/performance/linkbench/assets/Roslyn/RoslynRoots.txt3
-rw-r--r--tests/src/performance/linkbench/assets/Roslyn/RoslynRoots.xml5
-rw-r--r--tests/src/performance/linkbench/assets/Roslyn/illinkcsproj9
-rw-r--r--tests/src/performance/linkbench/linkbench.cs372
-rw-r--r--tests/src/performance/linkbench/linkbench.csproj41
-rw-r--r--tests/src/performance/linkbench/scripts/build.cmd116
-rw-r--r--tests/src/performance/linkbench/scripts/clone.cmd30
-rw-r--r--tests/src/performance/linkbench/scripts/empty.cmd1
-rw-r--r--tests/src/performance/linkbench/scripts/getcert.cmd2
-rw-r--r--tests/src/performance/project.json17
11 files changed, 615 insertions, 8 deletions
diff --git a/tests/src/performance/linkbench/assets/MusicStore/MusicStoreReflection.xml b/tests/src/performance/linkbench/assets/MusicStore/MusicStoreReflection.xml
new file mode 100644
index 0000000000..3673c65e60
--- /dev/null
+++ b/tests/src/performance/linkbench/assets/MusicStore/MusicStoreReflection.xml
@@ -0,0 +1,27 @@
+<linker>
+ <!--- Called by Microsoft.EntityFrameworkCore.EntityFrameworkQueryableExtensions:.cctor -->
+ <assembly fullname="System.Linq.Queryable">
+ <type fullname="System.Linq.Queryable" required="true" />
+ </assembly>
+
+ <assembly fullname="System.Linq.Expressions">
+ <!--- Called by System.Linq.Expressions.Expression:CreateLambda -->
+ <type fullname="System.Linq.Expressions.Expression`1" required="true" />
+ <!--- Called by [System.Linq.Expressions]System.Runtime.CompilerServices.CallSite<>.CreateCustomNoMatchDelegate and [System.Linq.Expressions]System.Runtime.CompilerServices.CallSite<>.CreateCustomUpdateDelegate-->
+ <type fullname="System.Runtime.CompilerServices.CallSiteOps" required="true" />
+ <!--- Called by [System.Linq.Expressions]System.Runtime.CompilerServices.CallSiteBinder.Stitch -->
+ <type fullname="System.Runtime.CompilerServices.CallSite" required="true" />
+ <!--- Called by [System.Linq.Expressions]System.Runtime.CompilerServices.CallSiteBinder.Stitch -->
+ <type fullname="System.Runtime.CompilerServices.CallSite`1" required="true" />
+ <!--- Called by [System.Linq.Expressions]System.Runtime.CompilerServices.CallSite`1.MakeUpdateDelegate -->
+ <type fullname="System.Dynamic.UpdateDelegates" required="true" />
+ <!--- Called by [System.Linq.Expressions]System.Dynamic.DynamicObject.MetaDynamic.BindBinaryOperation -->
+ <type fullname="System.Dynamic.DynamicObject" required="true" />
+ </assembly>
+
+ <assembly fullname="System.ComponentModel.TypeConverter">
+ <type fullname="System.ComponentModel.StringConverter" required="true" />
+ <type fullname="System.ComponentModel.BooleanConverter" required="true" />
+ <type fullname="System.ComponentModel.CollectionConverter" required="true" />
+ </assembly>
+</linker>
diff --git a/tests/src/performance/linkbench/assets/Roslyn/RoslynRoots.txt b/tests/src/performance/linkbench/assets/Roslyn/RoslynRoots.txt
new file mode 100644
index 0000000000..10f149e1c5
--- /dev/null
+++ b/tests/src/performance/linkbench/assets/Roslyn/RoslynRoots.txt
@@ -0,0 +1,3 @@
+Microsoft.CodeAnalysis
+Microsoft.CodeAnalysis.CSharp
+System.Private.CoreLib
diff --git a/tests/src/performance/linkbench/assets/Roslyn/RoslynRoots.xml b/tests/src/performance/linkbench/assets/Roslyn/RoslynRoots.xml
new file mode 100644
index 0000000000..afc1ce6922
--- /dev/null
+++ b/tests/src/performance/linkbench/assets/Roslyn/RoslynRoots.xml
@@ -0,0 +1,5 @@
+<linker>
+ <assembly fullname="csc">
+ <type fullname="*" required="true" />
+ </assembly>
+</linker>
diff --git a/tests/src/performance/linkbench/assets/Roslyn/illinkcsproj b/tests/src/performance/linkbench/assets/Roslyn/illinkcsproj
new file mode 100644
index 0000000000..1247c5e715
--- /dev/null
+++ b/tests/src/performance/linkbench/assets/Roslyn/illinkcsproj
@@ -0,0 +1,9 @@
+<Project Sdk="Microsoft.NET.Sdk">
+ <PropertyGroup>
+ <TargetFramework>netcoreapp2.0</TargetFramework>
+ <RuntimeIdentifiers>win7-x86;win7-x64</RuntimeIdentifiers>
+ </PropertyGroup>
+ <ItemGroup>
+ <PackageReference Include="ILLink.Tasks" Version="0.1.0-preview" />
+ </ItemGroup>
+</Project>
diff --git a/tests/src/performance/linkbench/linkbench.cs b/tests/src/performance/linkbench/linkbench.cs
new file mode 100644
index 0000000000..3d29957f90
--- /dev/null
+++ b/tests/src/performance/linkbench/linkbench.cs
@@ -0,0 +1,372 @@
+using System;
+using System.Diagnostics;
+using System.Collections.Generic;
+using System.IO;
+using System.Reflection;
+using System.Runtime.Loader;
+using System.Text;
+using System.Globalization;
+using System.Linq;
+using System.Xml.Linq;
+using Microsoft.Xunit.Performance;
+using Microsoft.Xunit.Performance.Api;
+using Xunit;
+using Xunit.Abstractions;
+
+namespace LinkBench
+{
+ public class Benchmark
+ {
+ public string Name;
+
+ public string UnlinkedDir;
+ public string LinkedDir;
+ public double UnlinkedMsilSize;
+ public double LinkedMsilSize;
+ public double UnlinkedDirSize;
+ public double LinkedDirSize;
+ public double MsilSizeReduction;
+ public double DirSizeReduction;
+
+ private DirectoryInfo unlinkedDirInfo;
+ private DirectoryInfo linkedDirInfo;
+ private double certDiff;
+ const double MB = 1024 * 1024;
+
+ public Benchmark(string _Name, string _UnlinkedDir, string _LinkedDir)
+ {
+ Name = _Name;
+ UnlinkedDir = _UnlinkedDir;
+ LinkedDir = _LinkedDir;
+ unlinkedDirInfo = new DirectoryInfo(UnlinkedDir);
+ linkedDirInfo = new DirectoryInfo(LinkedDir);
+ }
+
+ public void Compute()
+ {
+ ComputeCertDiff();
+ UnlinkedMsilSize = GetMSILSize(UnlinkedDir);
+ LinkedMsilSize = GetMSILSize(LinkedDir);
+ UnlinkedDirSize = GetDirSize(unlinkedDirInfo);
+ LinkedDirSize = GetDirSize(linkedDirInfo);
+
+ MsilSizeReduction = (UnlinkedMsilSize - LinkedMsilSize) / UnlinkedMsilSize * 100;
+ DirSizeReduction = (UnlinkedDirSize - LinkedDirSize) / UnlinkedDirSize * 100;
+ }
+
+ // Compute total size of a directory, in MegaBytes
+ // Includes all files and subdirectories recursively
+ private double GetDirSize(DirectoryInfo dir)
+ {
+ double size = 0;
+ FileInfo[] files = dir.GetFiles();
+ foreach (FileInfo fileInfo in files)
+ {
+ size += fileInfo.Length;
+ }
+ DirectoryInfo[] subDirs = dir.GetDirectories();
+ foreach (DirectoryInfo dirInfo in subDirs)
+ {
+ size += GetDirSize(dirInfo);
+ }
+
+ return size / MB;
+ }
+
+ // Compute the size of MSIL files in a directory, in MegaBytes
+ // Top level only, excludes crossgen files.
+ private double GetMSILSize(string dir)
+ {
+ string[] files = Directory.GetFiles(dir);
+ long msilSize = 0;
+
+ foreach (string file in files)
+ {
+ if (file.EndsWith(".ni.dll") || file.EndsWith(".ni.exe"))
+ {
+ continue;
+ }
+ try
+ {
+ AssemblyLoadContext.GetAssemblyName(file);
+ }
+ catch (BadImageFormatException)
+ {
+ continue;
+ }
+
+ msilSize += new FileInfo(file).Length;
+ }
+
+ return msilSize / MB;
+ }
+
+ // Gets the size of the Certificate header in a MSIL or ReadyToRun binary.
+ private long GetCertSize(string file)
+ {
+ Process p = new Process();
+ p.StartInfo.UseShellExecute = false;
+ p.StartInfo.RedirectStandardOutput = true;
+ p.StartInfo.FileName = LinkBench.ScriptDir + "GetCert.cmd";
+ p.StartInfo.Arguments = file;
+ p.Start();
+ string output = p.StandardOutput.ReadToEnd();
+ p.WaitForExit();
+ long size = Int32.Parse(output.Substring(18, 8),
+ NumberStyles.AllowLeadingWhite | NumberStyles.AllowTrailingWhite | NumberStyles.HexNumber);
+ return size;
+ }
+
+ // Get the total size difference for all certificates in all managed binaries
+ // in the unlinked and linked directories.
+ private double ComputeCertDiff()
+ {
+ string[] files = Directory.GetFiles(LinkedDir);
+ long totalDiff = 0;
+
+ foreach (string file in files)
+ {
+ try
+ {
+ AssemblyLoadContext.GetAssemblyName(file);
+ }
+ catch (BadImageFormatException)
+ {
+ continue;
+ }
+
+ FileInfo fileInfo = new FileInfo(file);
+ long linkedCert = GetCertSize(file);
+ long unlinkedCert = GetCertSize(UnlinkedDir + "\\" + fileInfo.Name);
+ totalDiff += (unlinkedCert - linkedCert);
+ }
+
+ return totalDiff / MB;
+ }
+ }
+
+ public class LinkBench
+ {
+ private static ScenarioConfiguration scenarioConfiguration = new ScenarioConfiguration(new TimeSpan(2000000));
+ private static MetricModel SizeMetric = new MetricModel { Name = "Size", DisplayName = "File Size", Unit = "MB" };
+ private static MetricModel PercMetric = new MetricModel { Name = "Perc", DisplayName = "% Reduction", Unit = "%" };
+ public static string Workspace;
+ public static string ScriptDir;
+ public static string AssetsDir;
+ private static Benchmark CurrentBenchmark;
+
+ public static int Main(String [] args)
+ {
+ // Workspace is the ROOT of the coreclr tree.
+ // If CORECLR_REPO is not set, the script assumes that the location of sandbox
+ // is <path>\coreclr\sandbox.
+ bool doClone = true;
+ bool doBuild = true;
+
+ for(int i=0; i < args.Length; i++)
+ {
+ if (String.Compare(args[i], "noclone", true) == 0)
+ {
+ doClone = false;
+ }
+ else if (String.Compare(args[i], "nobuild", true) == 0)
+ {
+ doClone = false;
+ doBuild = false;
+ }
+ else
+ {
+ Console.WriteLine("Unknown argument");
+ return -4;
+ }
+ }
+
+ Workspace = Environment.GetEnvironmentVariable("CORECLR_REPO");
+ if (Workspace == null)
+ {
+ Workspace = Directory.GetParent(Directory.GetCurrentDirectory()).FullName;
+ }
+ if (Workspace == null)
+ {
+ Console.WriteLine("CORECLR_REPO not found");
+ return -1;
+ }
+
+ string LinkBenchDir = Workspace + "\\tests\\src\\performance\\linkbench\\";
+ ScriptDir = LinkBenchDir + "scripts\\";
+ AssetsDir = LinkBenchDir + "assets\\";
+
+ Benchmark[] Benchmarks =
+ {
+ new Benchmark("HelloWorld",
+ "LinkBench\\HelloWorld\\bin\\release\\netcoreapp2.0\\win10-x64\\publish",
+ "LinkBench\\HelloWorld\\bin\\release\\netcoreapp2.0\\win10-x64\\linked"),
+ new Benchmark("WebAPI",
+ "LinkBench\\WebAPI\\bin\\release\\netcoreapp2.0\\win10-x64\\publish",
+ "LinkBench\\WebAPI\\bin\\release\\netcoreapp2.0\\win10-x64\\linked"),
+ new Benchmark("MusicStore",
+ "LinkBench\\JitBench\\src\\MusicStore\\bin\\release\\netcoreapp2.0\\win10-x64\\publish",
+ "LinkBench\\JitBench\\src\\MusicStore\\bin\\release\\netcoreapp2.0\\win10-x64\\linked"),
+ new Benchmark("MusicStore_R2R",
+ "LinkBench\\JitBench\\src\\MusicStore\\bin\\release\\netcoreapp2.0\\win10-x64\\publish_r2r",
+ "LinkBench\\JitBench\\src\\MusicStore\\bin\\release\\netcoreapp2.0\\win10-x64\\linked_r2r"),
+ new Benchmark("Corefx",
+ "LinkBench\\corefx\\bin\\ILLinkTrimAssembly\\netcoreapp-Windows_NT-Release-x64\\pretrimmed",
+ "LinkBench\\corefx\\bin\\ILLinkTrimAssembly\\netcoreapp-Windows_NT-Release-x64\\trimmed"),
+ new Benchmark("Roslyn",
+ "LinkBench\\roslyn\\Binaries\\Release\\Exes\\CscCore",
+ "LinkBench\\roslyn\\Binaries\\Release\\Exes\\Linked"),
+ };
+
+ // Update the build files to facilitate the link step
+ if(doClone)
+ {
+ if(!Setup())
+ {
+ return -2;
+ }
+ }
+
+ if (doBuild)
+ {
+ // Run the setup Script, which clones, builds and links the benchmarks.
+ using (var setup = new Process())
+ {
+ setup.StartInfo.FileName = ScriptDir + "build.cmd";
+ setup.StartInfo.Arguments = AssetsDir;
+ setup.Start();
+ setup.WaitForExit();
+ if (setup.ExitCode != 0)
+ {
+ Console.WriteLine("Setup failed");
+ return -3;
+ }
+ }
+ }
+
+ // Since this is a size measurement scenario, there are no iterations
+ // to perform. So, create a process that does nothing, to satisfy XUnit.
+ // All size measurements are performed PostRun()
+ var emptyCmd = new ProcessStartInfo()
+ {
+ FileName = ScriptDir + "empty.cmd"
+ };
+
+ for (int i = 0; i < Benchmarks.Length; i++)
+ {
+ CurrentBenchmark = Benchmarks[i];
+ string[] scriptArgs = { "--perf:runid", CurrentBenchmark.Name };
+
+ using (var h = new XunitPerformanceHarness(scriptArgs))
+ {
+ h.RunScenario(emptyCmd, null, null, PostRun, scenarioConfiguration);
+ }
+ }
+
+ return 0;
+ }
+
+ private static ScenarioBenchmark PostRun()
+ {
+ // The XUnit output doesn't print the benchmark name, so print it now.
+ Console.WriteLine("{0}", CurrentBenchmark.Name);
+
+ var scenario = new ScenarioBenchmark(CurrentBenchmark.Name)
+ {
+ Namespace = "LinkBench"
+ };
+
+ CurrentBenchmark.Compute();
+
+ addMeasurement(ref scenario, "MSIL Unlinked", SizeMetric, CurrentBenchmark.UnlinkedMsilSize);
+ addMeasurement(ref scenario, "MSIL Linked", SizeMetric, CurrentBenchmark.LinkedMsilSize);
+ addMeasurement(ref scenario, "MSIL %Reduction", PercMetric, CurrentBenchmark.MsilSizeReduction);
+ addMeasurement(ref scenario, "Total Uninked", SizeMetric, CurrentBenchmark.UnlinkedDirSize);
+ addMeasurement(ref scenario, "Total Linked", SizeMetric, CurrentBenchmark.LinkedDirSize);
+ addMeasurement(ref scenario, "Total %Reduction", PercMetric, CurrentBenchmark.DirSizeReduction);
+
+ return scenario;
+ }
+
+ private static bool Setup()
+ {
+ // Clone the benchmarks
+ using (var setup = new Process())
+ {
+ setup.StartInfo.FileName = ScriptDir + "clone.cmd";
+ Console.WriteLine("Run {0}", setup.StartInfo.FileName);
+ setup.Start();
+ setup.WaitForExit();
+ if (setup.ExitCode != 0)
+ {
+ Console.WriteLine("clone failed");
+ return false;
+ }
+ }
+
+ //Update the project files
+ AddLinkerReference("LinkBench\\HelloWorld\\HelloWorld.csproj");
+ AddLinkerReference("LinkBench\\WebAPI\\WebAPI.csproj");
+ AddLinkerReference("LinkBench\\JitBench\\src\\MusicStore\\MusicStore.csproj");
+ RemoveCrossgenTarget("LinkBench\\JitBench\\src\\MusicStore\\MusicStore.csproj");
+
+ return true;
+ }
+
+ private static void AddLinkerReference(string csproj)
+ {
+ var xdoc = XDocument.Load(csproj);
+ var ns = xdoc.Root.GetDefaultNamespace();
+ bool added = false;
+ foreach (var el in xdoc.Root.Elements(ns + "ItemGroup"))
+ {
+ if (el.Elements(ns + "PackageReference").Any())
+ {
+ el.Add(new XElement(ns + "PackageReference",
+ new XAttribute("Include", "ILLink.Tasks"),
+ new XAttribute("Version", "0.1.0-preview")));
+ added = true;
+ break;
+ }
+ }
+ if (!added)
+ {
+ xdoc.Root.Add(new XElement(ns + "ItemGroup",
+ new XElement(ns + "PackageReference",
+ new XAttribute("Include", "ILLink.Tasks"),
+ new XAttribute("Version", "0.1.0-preview"))));
+ added = true;
+ }
+ using (var fs = new FileStream(csproj, FileMode.Create))
+ {
+ xdoc.Save(fs);
+ }
+ }
+
+ private static void RemoveCrossgenTarget(string csproj)
+ {
+ var xdoc = XDocument.Load(csproj);
+ var ns = xdoc.Root.GetDefaultNamespace();
+ var target = xdoc.Root.Element(ns + "Target");
+ target.Remove();
+ using (var fs = new FileStream(csproj, FileMode.Create))
+ {
+ xdoc.Save(fs);
+ }
+ }
+
+ private static void addMeasurement(ref ScenarioBenchmark scenario, string name, MetricModel metric, double value)
+ {
+ var iteration = new IterationModel
+ {
+ Iteration = new Dictionary<string, double>()
+ };
+ iteration.Iteration.Add(metric.Name, value);
+
+ var size = new ScenarioTestModel(name);
+ size.Performance.Metrics.Add(metric);
+ size.Performance.IterationModels.Add(iteration);
+ scenario.Tests.Add(size);
+ }
+ }
+}
diff --git a/tests/src/performance/linkbench/linkbench.csproj b/tests/src/performance/linkbench/linkbench.csproj
new file mode 100644
index 0000000000..2a3048ab21
--- /dev/null
+++ b/tests/src/performance/linkbench/linkbench.csproj
@@ -0,0 +1,41 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project ToolsVersion="12.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+ <Import Project="$([MSBuild]::GetDirectoryNameOfFileAbove($(MSBuildThisFileDirectory), dir.props))\dir.props" />
+ <PropertyGroup>
+ <Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
+ <Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
+ <AssemblyName>LinkBench</AssemblyName>
+ <SchemaVersion>2.0</SchemaVersion>
+ <ProjectGuid>{507E3CC2-5D95-414D-9F01-2A106FC177DC}</ProjectGuid>
+ <OutputType>exe</OutputType>
+ <AppDesignerFolder>Properties</AppDesignerFolder>
+ <FileAlignment>512</FileAlignment>
+ <ProjectTypeGuids>{786C830F-07A1-408B-BD7F-6EE04809D6DB};{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}</ProjectTypeGuids>
+ <ReferencePath>$(ProgramFiles)\Common Files\microsoft shared\VSTT\11.0\UITestExtensionPackages</ReferencePath>
+ <SolutionDir Condition="$(SolutionDir) == '' Or $(SolutionDir) == '*Undefined*'">..\..\</SolutionDir>
+ <NuGetPackageImportStamp>7a9bfb7d</NuGetPackageImportStamp>
+ <DefineConstants>$(DefineConstants);STATIC</DefineConstants>
+ <NuGetTargetMoniker>.NETStandard,Version=v1.4</NuGetTargetMoniker>
+ </PropertyGroup>
+ <!-- Default configurations to help VS understand the configurations -->
+ <PropertyGroup Condition="'$(Configuration)|$(Platform)' == 'Debug|x64'">
+ </PropertyGroup>
+ <PropertyGroup Condition="'$(Configuration)|$(Platform)' == 'Release|x64'">
+ </PropertyGroup>
+ <PropertyGroup>
+ <ProjectJson>..\project.json</ProjectJson>
+ <ProjectLockJson>..\project.lock.json</ProjectLockJson>
+ </PropertyGroup>
+ <ItemGroup>
+ <CodeAnalysisDependentAssemblyPaths Condition=" '$(VS100COMNTOOLS)' != '' " Include="$(VS100COMNTOOLS)..\IDE\PrivateAssemblies">
+ <Visible>False</Visible>
+ </CodeAnalysisDependentAssemblyPaths>
+ </ItemGroup>
+ <ItemGroup>
+ <Compile Include="linkbench.cs" />
+ </ItemGroup>
+ <ItemGroup>
+ <Service Include="{82A7F48D-3B50-4B1E-B82E-3ADA8210C358}" />
+ </ItemGroup>
+ <Import Project="$([MSBuild]::GetDirectoryNameOfFileAbove($(MSBuildThisFileDirectory), performance.targets))\performance.targets" />
+</Project>
diff --git a/tests/src/performance/linkbench/scripts/build.cmd b/tests/src/performance/linkbench/scripts/build.cmd
new file mode 100644
index 0000000000..88b7eb139e
--- /dev/null
+++ b/tests/src/performance/linkbench/scripts/build.cmd
@@ -0,0 +1,116 @@
+@echo off
+
+REM Usage: Build.cmd <LinkBench assets directory>
+setlocal
+call "C:\Program Files (x86)\Microsoft Visual Studio 14.0\Common7\Tools\VsDevCmd.bat"
+
+set ROOT=%cd%\LinkBench
+set AssetDir=%1
+set ExitCode=0
+mkdir LinkBench 2> nul
+pushd %ROOT%
+
+echo Build ** HelloWorld **
+cd %ROOT%\HelloWorld
+dotnet restore -r win10-x64
+dotnet publish -c release -r win10-x64
+dotnet msbuild /t:Link /p:LinkerMode=sdk /p:RuntimeIdentifier=win10-x64 /v:n /p:Configuration=release
+if errorlevel 1 set ExitCode=1
+echo -- Done --
+
+echo Build ** WebAPI **
+cd %ROOT%\WebAPI
+dotnet restore -r win10-x64
+dotnet publish -c release -r win10-x64
+dotnet msbuild /t:Link /p:LinkerMode=sdk /p:RuntimeIdentifier=win10-x64 /v:n /p:Configuration=release
+if errorlevel 1 set ExitCode=1
+echo -- Done --
+
+echo Build ** MusicStore **
+cd %ROOT%\JitBench\src\MusicStore
+copy %AssetDir%\MusicStore\MusicStoreReflection.xml .
+dotnet restore -r win10-x64
+dotnet publish -c release -r win10-x64
+dotnet msbuild /t:Link /p:LinkerMode=sdk /p:RuntimeIdentifier=win10-x64 /v:n /p:LinkerRootFiles=MusicStoreReflection.xml /p:Configuration=release
+if errorlevel 1 set ExitCode=1
+echo -- Done --
+
+echo Build ** MusicStore Ready2Run **
+cd %ROOT%\JitBench\src\MusicStore
+powershell -noprofile -executionPolicy RemoteSigned -file Get-Crossgen.ps1
+pushd bin\release\netcoreapp2.0\win10-x64\
+call :SetupR2R publish
+if errorlevel 1 set ExitCode=1
+call :SetupR2R linked
+if errorlevel 1 set ExitCode=1
+echo -- Done --
+
+echo Build ** CoreFX **
+cd %ROOT%\corefx
+set BinPlaceILLinkTrimAssembly=true
+call build.cmd -release
+if errorlevel 1 set ExitCode=1
+echo -- Done --
+
+echo Build ** Roslyn **
+cd %ROOT%\roslyn
+copy %AssetDir%\Roslyn\RoslynRoots.txt .
+copy %AssetDir%\Roslyn\RoslynRoots.xml .
+set RoslynRoot=%cd%
+REM Build Roslyn
+call restore.cmd
+msbuild /m Roslyn.sln /p:Configuration=Release
+REM Fetch ILLink
+mkdir illink
+cd illink
+copy %AssetDir%\Roslyn\illinkcsproj illink.csproj
+dotnet restore illink.csproj -r win10-x64 --packages bin
+cd ..
+REM Create Linker Directory
+cd Binaries\Release\Exes
+mkdir Linked
+cd CscCore
+REM Copy Unmanaged Assets
+FOR /F "delims=" %%I IN ('DIR /b *') DO (
+ corflags %%I >nul 2> nul
+ if errorlevel 1 copy %%I ..\Linked >nul
+)
+copy *.ni.dll ..\Linked
+REM Run Linker
+dotnet %RoslynRoot%\illink\bin\illink.tasks\0.1.0-preview\tools\illink.dll -t -c link -a @%RoslynRoot%\RoslynRoots.txt -x %RoslynRoot%\RoslynRoots.xml -l none -out ..\Linked
+if errorlevel 1 set ExitCode=1
+echo -- Done --
+popd
+
+:Done
+exit /b %ExitCode%
+
+:SetupR2R
+REM Create R2R directory and copy all contents from MSIL to R2R directory
+mkdir %1_r2r
+xcopy /E /Y /Q %1 %1_r2r
+REM Generate Ready2Run images for all MSIL files by running crossgen
+cd %1_r2r
+copy ..\..\..\..\..\crossgen.exe
+FOR /F %%I IN ('dir /b *.dll ^| find /V /I ".ni.dll" ^| find /V /I "System.Private.CoreLib" ^| find /V /I "mscorlib.dll"') DO (
+ REM Don't crossgen Corlib, since the native image already exists.
+ REM For all other MSIL files (corflags returns 0), run crossgen
+ corflags %%I >nul 2>nul
+ if not errorlevel 1 (
+ crossgen /Platform_Assemblies_Paths . %%I >nul 2>nul
+ if errorlevel 1 (
+ exit /b 1
+ )
+ )
+)
+del crossgen.exe
+
+REM Remove the original MSIL files, rename the Ready2Run files .ni.dll --> .dll
+FOR /F "delims=" %%I IN ('dir /b *.dll') DO (
+ if exist %%~nI.ni.dll (
+ del %%I
+ ren %%~nI.ni.dll %%I
+ )
+)
+cd ..
+exit /b 0
diff --git a/tests/src/performance/linkbench/scripts/clone.cmd b/tests/src/performance/linkbench/scripts/clone.cmd
new file mode 100644
index 0000000000..ae28d41d08
--- /dev/null
+++ b/tests/src/performance/linkbench/scripts/clone.cmd
@@ -0,0 +1,30 @@
+@echo off
+
+rmdir /s /q LinkBench
+
+set ROOT=%cd%\LinkBench
+mkdir LinkBench 2> nul
+pushd %ROOT%
+
+mkdir HelloWorld
+cd HelloWorld
+dotnet new console
+if errorlevel 1 exit /b 1
+cd ..
+
+mkdir WebAPI
+cd WebAPI
+dotnet new webapi
+if errorlevel 1 exit /b 1
+cd ..
+
+git clone https://github.com/aspnet/JitBench -b dev
+if errorlevel 1 exit /b 1
+
+git clone http://github.com/dotnet/corefx
+if errorlevel 1 exit /b 1
+
+git clone https://github.com/dotnet/roslyn.git
+if errorlevel 1 exit /b 1
+
+popd \ No newline at end of file
diff --git a/tests/src/performance/linkbench/scripts/empty.cmd b/tests/src/performance/linkbench/scripts/empty.cmd
new file mode 100644
index 0000000000..83cb140ebd
--- /dev/null
+++ b/tests/src/performance/linkbench/scripts/empty.cmd
@@ -0,0 +1 @@
+@echo off
diff --git a/tests/src/performance/linkbench/scripts/getcert.cmd b/tests/src/performance/linkbench/scripts/getcert.cmd
new file mode 100644
index 0000000000..e02f72d714
--- /dev/null
+++ b/tests/src/performance/linkbench/scripts/getcert.cmd
@@ -0,0 +1,2 @@
+@echo off
+"%VS140COMNTOOLS%\..\..\VC\bin\amd64\dumpbin.exe" /headers %1 | findstr /C:"Certificates Directory
diff --git a/tests/src/performance/project.json b/tests/src/performance/project.json
index 1d0eb6d538..86a42f2df7 100644
--- a/tests/src/performance/project.json
+++ b/tests/src/performance/project.json
@@ -1,22 +1,23 @@
{
"dependencies": {
- "xunit.performance.api": "1.0.0-alpha-build0049",
- "xunit.performance.core": "1.0.0-alpha-build0049",
- "xunit.performance.execution": "1.0.0-alpha-build0049",
- "xunit.performance.metrics": "1.0.0-alpha-build0049",
+ "xunit.performance.api": "1.0.0-beta-build0003",
+ "xunit.performance.core": "1.0.0-beta-build0003",
+ "xunit.performance.execution": "1.0.0-beta-build0003",
+ "xunit.performance.metrics": "1.0.0-beta-build0003",
"Microsoft.Diagnostics.Tracing.TraceEvent": "1.0.3-alpha-experimental",
- "Microsoft.NETCore.Platforms": "2.0.0-preview1-25210-01",
+ "Microsoft.NETCore.Platforms": "2.0.0-preview1-25221-01",
"System.Collections.NonGeneric": "4.4.0-beta-24913-02",
"System.Console": "4.4.0-beta-24913-02",
"System.IO.FileSystem": "4.4.0-beta-24913-02",
"System.Linq": "4.4.0-beta-24913-02",
"System.Linq.Expressions": "4.4.0-beta-24913-02",
- "System.Numerics.Vectors": "4.4.0-preview1-25210-01",
+ "System.Numerics.Vectors": "4.4.0-preview1-25221-01",
"System.Reflection": "4.4.0-beta-24913-02",
"System.Reflection.Extensions": "4.4.0-beta-24913-02",
- "System.Reflection.TypeExtensions": "4.4.0-preview1-25210-01",
+ "System.Reflection.TypeExtensions": "4.4.0-preview1-25221-01",
"System.Runtime": "4.4.0-beta-24913-02",
"System.Runtime.Extensions": "4.4.0-beta-24913-02",
+ "System.Runtime.Loader": "4.0.0",
"System.Runtime.Numerics": "4.4.0-beta-24913-02",
"System.Text.RegularExpressions": "4.4.0-beta-24913-02",
"System.Threading": "4.4.0-beta-24913-02",
@@ -31,7 +32,7 @@
"xunit.runner.utility": "2.2.0-beta2-build3300"
},
"frameworks": {
- "netstandard1.4": {
+ "netstandard1.5": {
"imports": [
"dnxcore50",
"portable-net45+win8"