Skip to content
This repository was archived by the owner on Jan 12, 2024. It is now read-only.
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
29 commits
Select commit Hold shift + click to select a range
cebe4e3
prevent array of arrays in entry point arguments
Apr 10, 2020
6057fa5
verifying entry point argument names
Apr 10, 2020
cdf9628
... and the corresponding tests
Apr 10, 2020
c34b09b
forgot to remove something
Apr 10, 2020
e615d6a
one more test
Apr 10, 2020
736c0ab
adding DefaultSimulator property as assembly constant
Apr 10, 2020
69700f4
passing runtime capabilities as command line flag
Apr 10, 2020
2c82f3f
propagating the information whether or not the project to build is a …
Apr 10, 2020
f931edf
warning for missing entry point
Apr 10, 2020
5cfb4bd
Update src/QsCompiler/Compiler/CompilationLoader.cs
bettinaheim Apr 13, 2020
a024693
addressing review comments
Apr 13, 2020
c16a208
Merge branch 'beheim/standalone' of https://github.com/microsoft/qsha…
Apr 13, 2020
08adec5
some keywords etc
Apr 13, 2020
db9a5a2
warning for clashes with reserved arg names
Apr 13, 2020
bfcf9c8
removing a comment
Apr 14, 2020
9278c8b
comment
Apr 14, 2020
f579682
dragging project information into the comilation manager
Apr 14, 2020
b436401
first draft, not actually using the info yet
Apr 14, 2020
f6c8dc0
going with two additional arguments for the manager only
Apr 14, 2020
5e02919
error for entry point in library
Apr 14, 2020
7c19c79
warning for non-result types in return value
Apr 14, 2020
a23aa36
removing comment
Apr 14, 2020
8bde1f5
Merge branch 'master' into beheim/standalone
Apr 14, 2020
82dc9b5
forgot something
Apr 14, 2020
f4fe57f
correct return code
Apr 14, 2020
f9d547c
Merge branch 'master' into beheim/standalone
bettinaheim Apr 15, 2020
ca43168
Merge branch 'master' into beheim/standalone
bettinaheim Apr 17, 2020
1e78812
addressing review comments
Apr 17, 2020
ff83600
reserved command line abbreviations
Apr 17, 2020
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
18 changes: 14 additions & 4 deletions src/QsCompiler/CompilationManager/CompilationUnit.cs
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,7 @@
using System.Collections.Generic;
using System.Collections.Immutable;
using System.Collections.ObjectModel;
using System.IO;
using System.Linq;
using System.Text.RegularExpressions;
using System.Threading;
using Microsoft.Quantum.QsCompiler.DataTypes;
using Microsoft.Quantum.QsCompiler.Diagnostics;
Expand All @@ -18,6 +16,7 @@
using Microsoft.Quantum.QsCompiler.SyntaxTree;
using Microsoft.Quantum.QsCompiler.Transformations.SearchAndReplace;
using Microsoft.VisualStudio.LanguageServer.Protocol;
using static Microsoft.Quantum.QsCompiler.ReservedKeywords.AssemblyConstants;


namespace Microsoft.Quantum.QsCompiler.CompilationBuilder
Expand Down Expand Up @@ -221,11 +220,16 @@ public class CompilationUnit : IReaderWriterLock, IDisposable

internal References Externals { get; private set; }
internal NamespaceManager GlobalSymbols { get; private set; }

private readonly Dictionary<QsQualifiedName, QsCallable> CompiledCallables;
private readonly Dictionary<QsQualifiedName, QsCustomType> CompiledTypes;

private readonly ReaderWriterLockSlim SyncRoot;
private readonly HashSet<ReaderWriterLockSlim> DependentLocks;

internal readonly RuntimeCapabilities RuntimeCapabilities;
internal readonly bool IsExecutable;

public void Dispose()
{ this.SyncRoot.Dispose(); }

Expand All @@ -234,13 +238,18 @@ public void Dispose()
/// with the given sequence of locks registered as dependent locks if the sequence is not null.
/// Throws an ArgumentNullException if any of the given locks is.
/// </summary>
internal CompilationUnit(References externals = null, IEnumerable<ReaderWriterLockSlim> dependentLocks = null)
internal CompilationUnit(RuntimeCapabilities capabilities, bool isExecutable,
References externals = null, IEnumerable<ReaderWriterLockSlim> dependentLocks = null)
{
this.SyncRoot = new ReaderWriterLockSlim(LockRecursionPolicy.SupportsRecursion);
this.DependentLocks = dependentLocks == null
? new HashSet<ReaderWriterLockSlim>()
: new HashSet<ReaderWriterLockSlim>(dependentLocks);
if (dependentLocks?.Contains(null) ?? false) throw new ArgumentNullException(nameof(dependentLocks), "one or more of the given locks is null");

this.RuntimeCapabilities = capabilities;
this.IsExecutable = isExecutable;

this.CompiledCallables = new Dictionary<QsQualifiedName, QsCallable>();
this.CompiledTypes = new Dictionary<QsQualifiedName, QsCustomType>();
this.UpdateReferences(externals ?? References.Empty);
Expand All @@ -260,7 +269,8 @@ internal void UpdateReferences(References externals)
this.GlobalSymbols = new NamespaceManager(this,
this.Externals.Declarations.Values.SelectMany(h => h.Callables),
this.Externals.Declarations.Values.SelectMany(h => h.Specializations.Select(t => new Tuple<SpecializationDeclarationHeader, SpecializationImplementation>(t.Item1, t.Item2))),
this.Externals.Declarations.Values.SelectMany(h => h.Types));
this.Externals.Declarations.Values.SelectMany(h => h.Types),
this.RuntimeCapabilities, this.IsExecutable);
}
finally { this.ExitWriteLock(); }
}
Expand Down
13 changes: 8 additions & 5 deletions src/QsCompiler/CompilationManager/CompilationUnitManager.cs
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@
using System.Threading.Tasks;
using Microsoft.Quantum.QsCompiler.CompilationBuilder.DataStructures;
using Microsoft.Quantum.QsCompiler.DataTypes;
using Microsoft.Quantum.QsCompiler.ReservedKeywords;
using Microsoft.Quantum.QsCompiler.SyntaxProcessing;
using Microsoft.Quantum.QsCompiler.SyntaxTokens;
using Microsoft.Quantum.QsCompiler.SyntaxTree;
Expand Down Expand Up @@ -58,14 +59,16 @@ public class CompilationUnitManager : IDisposable
protected readonly ProcessingQueue Processing;

/// <summary>
/// Initializes a CompilationUnitManager instance.
/// If an <see cref="System.Action"/> for publishing diagnostics is given and is not null,
/// Initializes a CompilationUnitManager instance for a project with the given properties.
/// If an <see cref="Action"/> for publishing diagnostics is given and is not null,
/// that action is called whenever diagnostics within a file have changed and are ready for publishing.
/// </summary>
public CompilationUnitManager(Action<Exception> exceptionLogger = null, Action<PublishDiagnosticParams> publishDiagnostics = null, bool syntaxCheckOnly = false)
public CompilationUnitManager(
Action<Exception> exceptionLogger = null, Action<PublishDiagnosticParams> publishDiagnostics = null, bool syntaxCheckOnly = false,
AssemblyConstants.RuntimeCapabilities capabilities = AssemblyConstants.RuntimeCapabilities.Unknown, bool isExecutable = false)
{
this.EnableVerification = !syntaxCheckOnly;
this.CompilationUnit = new CompilationUnit();
this.CompilationUnit = new CompilationUnit(capabilities, isExecutable);
this.FileContentManagers = new ConcurrentDictionary<NonNullable<string>, FileContentManager>();
this.ChangedFiles = new ManagedHashSet<NonNullable<string>>(new ReaderWriterLockSlim(LockRecursionPolicy.SupportsRecursion));
this.PublishDiagnostics = publishDiagnostics ?? (_ => { });
Expand Down Expand Up @@ -437,7 +440,7 @@ private Task SpawnGlobalTypeCheckingAsync(bool runSynchronously = false)
// work with a separate compilation unit instance such that processing of all further edits can go on in parallel
var sourceFiles = this.FileContentManagers.Values.OrderBy(m => m.FileName);
this.ChangedFiles.RemoveAll(f => sourceFiles.Any(m => m.FileName.Value == f.Value));
var compilation = new CompilationUnit(this.CompilationUnit.Externals, sourceFiles.Select(file => file.SyncRoot));
var compilation = new CompilationUnit(this.CompilationUnit.RuntimeCapabilities, this.CompilationUnit.IsExecutable, this.CompilationUnit.Externals, sourceFiles.Select(file => file.SyncRoot));
var content = compilation.UpdateGlobalSymbolsFor(sourceFiles);
foreach (var file in sourceFiles) this.PublishDiagnostics(file.Diagnostics());

Expand Down
60 changes: 40 additions & 20 deletions src/QsCompiler/CompilationManager/ProjectManager.cs
Original file line number Diff line number Diff line change
Expand Up @@ -11,31 +11,49 @@
using System.Threading.Tasks;
using Microsoft.Quantum.QsCompiler.DataTypes;
using Microsoft.Quantum.QsCompiler.Diagnostics;
using Microsoft.Quantum.QsCompiler.ReservedKeywords;
using Microsoft.VisualStudio.LanguageServer.Protocol;


namespace Microsoft.Quantum.QsCompiler.CompilationBuilder
{
public class ProjectInformation
internal class ProjectProperties
{
public delegate bool Loader(Uri projectFile, out ProjectInformation projectInfo);

public readonly string Version;
public readonly string OutputPath;
public readonly AssemblyConstants.RuntimeCapabilities RuntimeCapabilities;
public readonly bool IsExecutable;
public readonly bool ExposeReferencesViaTestNames;

internal static ProjectProperties Default =>
new ProjectProperties("Latest", "", AssemblyConstants.RuntimeCapabilities.Unknown, false, false);

public ProjectProperties(string version, string outputPath, AssemblyConstants.RuntimeCapabilities runtimeCapabilities, bool isExecutable, bool loadTestNames)
{
this.Version = version ?? "";
this.OutputPath = outputPath ?? throw new ArgumentNullException(nameof(outputPath));
this.RuntimeCapabilities = runtimeCapabilities;
this.IsExecutable = isExecutable;
this.ExposeReferencesViaTestNames = loadTestNames;
}
}

public class ProjectInformation
{
public delegate bool Loader(Uri projectFile, out ProjectInformation projectInfo);

internal readonly ProjectProperties Properties;
public readonly ImmutableArray<string> SourceFiles;
public readonly ImmutableArray<string> ProjectReferences;
public readonly ImmutableArray<string> References;

internal static ProjectInformation Empty(string version, string outputPath) =>
new ProjectInformation(version, outputPath, false, Enumerable.Empty<string>(), Enumerable.Empty<string>(), Enumerable.Empty<string>());
internal static ProjectInformation Empty(string version, string outputPath, AssemblyConstants.RuntimeCapabilities runtimeCapabilities) =>
new ProjectInformation(version, outputPath, runtimeCapabilities, false, false, Enumerable.Empty<string>(), Enumerable.Empty<string>(), Enumerable.Empty<string>());

public ProjectInformation(string version, string outputPath, bool loadTestNames,
public ProjectInformation(string version, string outputPath, AssemblyConstants.RuntimeCapabilities runtimeCapabilities, bool isExecutable, bool loadTestNames,
IEnumerable<string> sourceFiles, IEnumerable<string> projectReferences, IEnumerable<string> references)
{
this.Version = version ?? "";
this.OutputPath = outputPath ?? throw new ArgumentNullException(nameof(outputPath));
this.ExposeReferencesViaTestNames = loadTestNames;
this.Properties = new ProjectProperties(version, outputPath, runtimeCapabilities, isExecutable, loadTestNames);
this.SourceFiles = sourceFiles?.ToImmutableArray() ?? throw new ArgumentNullException(nameof(sourceFiles));
this.ProjectReferences = projectReferences?.ToImmutableArray() ?? throw new ArgumentNullException(nameof(projectReferences));
this.References = references?.ToImmutableArray() ?? throw new ArgumentNullException(nameof(references));
Expand All @@ -48,7 +66,7 @@ private class Project : IDisposable
{
public readonly Uri ProjectFile;
public Uri OutputPath { get; private set; }
private bool ExposeReferencesViaTestNames;
public ProjectProperties Properties { get; private set; }
private bool IsLoaded;

/// <summary>
Expand Down Expand Up @@ -120,14 +138,16 @@ internal Project(Uri projectFile, ProjectInformation projectInfo,
this.ProjectFile = projectFile ?? throw new ArgumentNullException(nameof(projectFile));
this.SetProjectInformation(projectInfo ?? throw new ArgumentNullException(nameof(projectInfo)));

var version = Version.TryParse(projectInfo.Version, out Version v) ? v : null;
if (projectInfo.Version.Equals("Latest", StringComparison.InvariantCultureIgnoreCase)) version = new Version(0, 3);
var version = Version.TryParse(projectInfo.Properties.Version, out Version v) ? v : null;
if (projectInfo.Properties.Version.Equals("Latest", StringComparison.InvariantCultureIgnoreCase)) version = new Version(0, 3);
var ignore = version == null || version < new Version(0, 3) ? true : false;

// We track the file contents for unsupported projects in case the files are migrated to newer projects while editing,
// but we don't do any semantic verification, and we don't publish diagnostics for them.
this.Processing = new ProcessingQueue(onException);
this.Manager = new CompilationUnitManager(onException, ignore ? null : publishDiagnostics, syntaxCheckOnly: ignore);
this.Manager = new CompilationUnitManager(
onException, ignore ? null : publishDiagnostics, syntaxCheckOnly: ignore,
this.Properties.RuntimeCapabilities, this.Properties.IsExecutable);
this.Log = log ?? ((msg, severity) => Console.WriteLine($"{severity}: {msg}"));

this.LoadedSourceFiles = ImmutableHashSet<Uri>.Empty;
Expand All @@ -144,10 +164,10 @@ internal Project(Uri projectFile, ProjectInformation projectInfo,
private void SetProjectInformation(ProjectInformation projectInfo)
{
if (projectInfo == null) throw new ArgumentNullException(nameof(projectInfo));
this.ExposeReferencesViaTestNames = projectInfo.ExposeReferencesViaTestNames;
this.Properties = projectInfo.Properties;
this.IsLoaded = false;

var outputPath = projectInfo.OutputPath;
var outputPath = projectInfo.Properties.OutputPath;
try { outputPath = Path.GetFullPath(outputPath); }
catch { outputPath = null; }
var outputUri = Uri.TryCreate(outputPath, UriKind.Absolute, out Uri uri) ? uri : null;
Expand Down Expand Up @@ -261,7 +281,7 @@ private Task LoadProjectReferencesAsync(
projectReferences, GetProjectOutputPath(projectOutputPaths, diagnostics),
diagnostics.Add, this.Manager.LogException);

this.LoadedProjectReferences = new References(loadedHeaders);
this.LoadedProjectReferences = new References(loadedHeaders, this.Properties.ExposeReferencesViaTestNames);
var importedDeclarations = this.LoadedReferences.CombineWith(this.LoadedProjectReferences,
(code,args) => diagnostics.Add(Errors.LoadError(code, args, MessageSource(this.ProjectFile))));
this.ProjectReferenceDiagnostics = diagnostics.ToImmutableArray();
Expand All @@ -288,7 +308,7 @@ private void ReloadProjectReference(IDictionary<Uri, Uri> projectOutputPaths, Ur
var loadedHeaders = ProjectManager.LoadProjectReferences(
new string[] { projectReference.LocalPath }, GetProjectOutputPath(projectOutputPaths, diagnostics),
diagnostics.Add, this.Manager.LogException);
var loaded = new References(loadedHeaders);
var loaded = new References(loadedHeaders, this.Properties.ExposeReferencesViaTestNames);

QsCompilerError.Verify(!loaded.Declarations.Any() ||
(loaded.Declarations.Count == 1 && loaded.Declarations.First().Key.Value == projRefId.Value),
Expand Down Expand Up @@ -320,7 +340,7 @@ private Task LoadReferencedAssembliesAsync(IEnumerable<string> references, bool
var loadedHeaders = ProjectManager.LoadReferencedAssemblies(references,
diagnostics.Add, this.Manager.LogException);

this.LoadedReferences = new References(loadedHeaders);
this.LoadedReferences = new References(loadedHeaders, this.Properties.ExposeReferencesViaTestNames);
var importedDeclarations = this.LoadedReferences.CombineWith(this.LoadedProjectReferences,
(code, args) => diagnostics.Add(Errors.LoadError(code, args, MessageSource(this.ProjectFile))));
this.ReferenceDiagnostics = diagnostics.ToImmutableArray();
Expand All @@ -342,7 +362,7 @@ private void ReloadReferencedAssembly(Uri reference)
var diagnostics = new List<Diagnostic>();
var loadedHeaders = ProjectManager.LoadReferencedAssemblies(new string[] { reference.LocalPath },
diagnostics.Add, this.Manager.LogException);
var loaded = new References(loadedHeaders);
var loaded = new References(loadedHeaders, this.Properties.ExposeReferencesViaTestNames);

QsCompilerError.Verify(!loaded.Declarations.Any() ||
(loaded.Declarations.Count == 1 && loaded.Declarations.First().Key.Value == refId.Value),
Expand Down Expand Up @@ -687,7 +707,7 @@ public Task ProjectChangedOnDiskAsync(Uri projectFile, ProjectInformation.Loader
if (!loaded)
{
existing?.LoadProjectAsync(ImmutableDictionary<Uri,Uri>.Empty, null, MigrateToDefaultManager(openInEditor),
ProjectInformation.Empty("Latest", existing.OutputPath.LocalPath))?.Wait(); // does need to block, or the call to the DefaultManager in ManagerTaskAsync needs to be adapted
ProjectInformation.Empty("Latest", existing.OutputPath.LocalPath, AssemblyConstants.RuntimeCapabilities.Unknown))?.Wait(); // does need to block, or the call to the DefaultManager in ManagerTaskAsync needs to be adapted
if (existing != null) this.ProjectReferenceChangedOnDiskChangeAsync(projectFile);
return;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,3 +6,4 @@

// Allow the test assembly to use our internal methods
[assembly: InternalsVisibleTo("Tests.Microsoft.Quantum.QsCompiler" + SigningConstants.PUBLIC_KEY)]
[assembly: InternalsVisibleTo("Tests.Microsoft.Quantum.QsLanguageServer" + SigningConstants.PUBLIC_KEY)]
7 changes: 2 additions & 5 deletions src/QsCompiler/Compiler/CompilationLoader.cs
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@

using MetadataReference = Microsoft.CodeAnalysis.MetadataReference;
using OptimizationLevel = Microsoft.CodeAnalysis.OptimizationLevel;
using RuntimeCapabilities = Microsoft.Quantum.QsCompiler.ReservedKeywords.AssemblyConstants.RuntimeCapabilities;
using static Microsoft.Quantum.QsCompiler.ReservedKeywords.AssemblyConstants;


namespace Microsoft.Quantum.QsCompiler
Expand Down Expand Up @@ -435,7 +435,7 @@ public CompilationLoader(SourceLoader loadSources, ReferenceLoader loadReference
RaiseCompilationTaskStart("OverallCompilation", "Build");
this.CompilationStatus.Validation = Status.Succeeded;
var files = CompilationUnitManager.InitializeFileManagers(sourceFiles, null, this.OnCompilerException); // do *not* live track (i.e. use publishing) here!
var compilationManager = new CompilationUnitManager(this.OnCompilerException);
var compilationManager = new CompilationUnitManager(this.OnCompilerException, capabilities: this.Config.RuntimeCapabilities, isExecutable: this.Config.IsExecutable);
compilationManager.UpdateReferencesAsync(references);
compilationManager.AddOrUpdateSourceFilesAsync(files);
this.VerifiedCompilation = compilationManager.Build();
Expand All @@ -450,9 +450,6 @@ public CompilationLoader(SourceLoader loadSources, ReferenceLoader loadReference
this.Logger?.Log(WarningCode.MissingEntryPoint, Array.Empty<string>());

}
// TODO:
// give warnings and ignore entry points in libraries,
// and check additional restriction on the return type for execution on quantum processors.

// executing the specified rewrite steps

Expand Down
Loading