dotnet-installer/src/dotnet-compile-native/IntermediateCompilation/Windows/WindowsCppCompileStep.cs

132 lines
4.8 KiB
C#
Raw Normal View History

using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
using Microsoft.Dnx.Runtime.Common.CommandLine;
using Microsoft.DotNet.Cli.Utils;
using Microsoft.DotNet.Tools.Common;
namespace Microsoft.DotNet.Tools.Compiler.Native
{
2015-11-17 17:02:16 -08:00
public class WindowsCppCompileStep : IPlatformNativeStep
{
//TODO support x86
private readonly string CompilerName = "cl.exe";
2015-11-17 17:02:16 -08:00
private readonly string VSBin = "..\\..\\VC\\bin\\amd64";
private readonly string InputExtension = ".cpp";
private readonly string CompilerOutputExtension = ".obj";
private static readonly Dictionary<BuildConfiguration, string[]> ConfigurationCompilerOptionsMap = new Dictionary<BuildConfiguration, string[]>
2015-11-17 17:02:16 -08:00
{
{ BuildConfiguration.debug, new string[] {"/ZI", "/nologo", "/W3", "/WX-", "/sdl", "/Od", "/D", "CPPCODEGEN", "/D", "WIN32", "/D", "_CONSOLE", "/D", "_LIB", "/D", "_UNICODE", "/D", "UNICODE", "/Gm", "/EHsc", "/RTC1", "/MD", "/GS", "/fp:precise", "/Zc:wchar_t", "/Zc:forScope", "/Zc:inline", "/Gd", "/TP", "/wd4477", "/errorReport:prompt"} },
{ BuildConfiguration.release, new string[] {"/Zi", "/nologo", "/W3", "/WX-", "/sdl", "/O2", "/Oi", "/GL", "/D", "CPPCODEGEN", "/D", "WIN32", "/D", "NDEBUG", "/D", "_CONSOLE", "/D", "_LIB", "/D", "_UNICODE", "/D", "UNICODE", "/Gm-", "/EHsc", "/MD", "/GS", "/Gy", "/fp:precise", "/Zc:wchar_t", "/Zc:forScope", "/Zc:inline", "/Gd", "/TP", "/wd4477", "/errorReport:prompt"} }
2015-11-17 17:02:16 -08:00
};
private IEnumerable<string> CompilerArgs { get; set; }
2015-11-17 19:50:19 -08:00
private NativeCompileSettings config;
2015-11-17 17:02:16 -08:00
public WindowsCppCompileStep(NativeCompileSettings config)
{
2015-11-17 19:50:19 -08:00
this.config = config;
2015-11-17 17:02:16 -08:00
InitializeArgs(config);
}
2015-11-17 19:50:19 -08:00
public int Invoke()
2015-11-17 17:02:16 -08:00
{
var result = WindowsCommon.SetVCVars();
if (result != 0)
{
Reporter.Error.WriteLine("vcvarsall.bat invocation failed.");
return result;
}
2015-11-17 19:50:19 -08:00
result = InvokeCompiler();
2015-11-17 17:02:16 -08:00
if (result != 0)
{
Reporter.Error.WriteLine("Compilation of intermediate files failed.");
}
return result;
}
public bool CheckPreReqs()
{
var vcInstallDir = Environment.GetEnvironmentVariable("VS140COMNTOOLS");
return !string.IsNullOrEmpty(vcInstallDir);
2015-11-17 17:02:16 -08:00
}
private void InitializeArgs(NativeCompileSettings config)
{
var argsList = new List<string>();
// Use a Custom Link Step
argsList.Add("/c");
// Add Includes
var ilcSdkIncPath = Path.Combine(config.IlcSdkPath, "inc");
2015-11-17 17:02:16 -08:00
argsList.Add("/I");
argsList.Add($"{ilcSdkIncPath}");
2015-11-17 17:02:16 -08:00
// Configuration Based Compiler Options
argsList.AddRange(ConfigurationCompilerOptionsMap[config.BuildType]);
2015-11-17 17:02:16 -08:00
// Pass the optional native compiler flags if specified
if (!string.IsNullOrWhiteSpace(config.CppCompilerFlags))
{
argsList.Add(config.CppCompilerFlags);
}
2015-11-17 17:02:16 -08:00
// Output
var objOut = DetermineOutputFile(config);
argsList.Add($"/Fo{objOut}");
2015-11-17 17:02:16 -08:00
// Input File
var inCppFile = DetermineInFile(config);
argsList.Add($"{inCppFile}");
this.CompilerArgs = argsList;
2015-11-17 17:02:16 -08:00
}
2015-11-17 19:50:19 -08:00
private int InvokeCompiler()
2015-11-17 17:02:16 -08:00
{
var vcInstallDir = Environment.GetEnvironmentVariable("VS140COMNTOOLS");
var compilerPath = Path.Combine(vcInstallDir, VSBin, CompilerName);
var result = Command.Create(compilerPath, CompilerArgs.ToArray())
2015-11-17 17:02:16 -08:00
.ForwardStdErr()
.ForwardStdOut()
.Execute();
return result.ExitCode;
}
private string DetermineInFile(NativeCompileSettings config)
{
var intermediateDirectory = config.IntermediateDirectory;
var filename = Path.GetFileNameWithoutExtension(config.InputManagedAssemblyPath);
var infile = Path.Combine(intermediateDirectory, filename + InputExtension);
return infile;
}
public string DetermineOutputFile(NativeCompileSettings config)
{
var intermediateDirectory = config.IntermediateDirectory;
var filename = Path.GetFileNameWithoutExtension(config.InputManagedAssemblyPath);
var outfile = Path.Combine(intermediateDirectory, filename + CompilerOutputExtension);
return outfile;
2015-11-17 17:02:16 -08:00
}
}
}