public CommonCompilation RoslynCompile(ICodeProgram codeProgram) { if (codeProgram == null) { throw new ArgumentNullException("codeProgram"); } var references = codeProgram.References.Select(x => MetadataReference.CreateAssemblyReference(x.AssemblyName)); var compilation = Compilation.Create(codeProgram.Name ?? "Untitled") .WithReferences(references) .WithOptions(DefaultCompilationOptions) .AddSyntaxTrees( SyntaxTree.ParseText(Console, options: DefaultParseOptions), SyntaxTree.ParseText(EntryPoint, options: DefaultParseOptions)); foreach (var document in codeProgram.Documents) { var text = document.IsEntryPoint ? BuildScript(document.Content) : document.Content; var tree = SyntaxTree.ParseText(text, document.Name, DefaultParseOptions); compilation = compilation.AddSyntaxTrees(tree); var rewriter = new ConsoleRewriter("__Console", compilation.GetSemanticModel(tree)); compilation = compilation.ReplaceSyntaxTree(tree, tree.RewriteWith(rewriter)); } return compilation; }
public IEnumerable<EditorError> GetCompilationErrors(ICodeProgram post) { var result = compiler.RoslynCompile(post).Emit(); return result.Diagnostics .Where(x => x.Info.Severity == DiagnosticSeverity.Error) .Select(x => new EditorError { Location = DocumentLineSpan.Create(x.Location.GetLineSpan(true)), Message = x.Info.GetMessage() }); }
public ICodeAssembly Compile(ICodeProgram program) { var compilation = RoslynCompile(program); var assembly = new ProgramAssembly { EntryPointClassName = "EntryPoint", EntryPointMethodName = "Main" }; using (var stream = new MemoryStream()) { var emitResult = compilation.Emit(stream); if (!emitResult.Success) { return null; } assembly.CompiledAssembly = stream.ToArray(); } return assembly; }
public Compilation RoslynCompile(ICodeProgram program) { if (program == null) { throw new ArgumentNullException("program"); } var asScript = ParseOptions.Default.WithKind(SourceCodeKind.Script); var console = SyntaxTree.ParseCompilationUnit( "public static readonly StringWriter __Console = new StringWriter();", options: asScript); var entry = SyntaxTree.ParseCompilationUnit(EntryPoint); var prompt = SyntaxTree.ParseCompilationUnit(BuildScript(program.Content), path: "Prompt", options: asScript); var editor = SyntaxTree.ParseCompilationUnit(program.Classes ?? string.Empty, path: "Editor", options: asScript); var compilation = RoslynCompile(program.Name ?? "Untitled", new[] { entry, prompt, editor, console }); var newPrompt = prompt.RewriteWith(new ConsoleRewriter("__Console", compilation.GetSemanticModel(prompt))); var newEditor = editor.RewriteWith(new ConsoleRewriter("__Console", compilation.GetSemanticModel(editor))); return compilation.ReplaceSyntaxTree(prompt, newPrompt).ReplaceSyntaxTree(editor, newEditor); }
public Task<ICodeRunResult> EvaluateAsync(ICodeProgram command, CancellationToken token) { if (command == null) { throw new ArgumentNullException("command"); } if (!(command is EvaluateCodeCommand)) { throw new ArgumentException("This evaluator can only deal with the type EvaluateCodeCommand"); } var cmd = (EvaluateCodeCommand)command; var tcs = new TaskCompletionSource<ICodeRunResult>(); var executionId = cmd.ExecutionId; // Create an anonymous event handler to be called if and when a worker finishes executing our code EventHandler<MessageReceivedEventArgs> handler = null; handler = (sender, e) => { token.ThrowIfCancellationRequested(); var result = serializer.Deserialize<WorkerResult>(e.Payload); if (result.ExecutionId == executionId) { messageBus.MessageReceived -= handler; tcs.TrySetResult(result); } }; messageBus.MessageReceived += handler; token.Register(() => { messageBus.MessageReceived -= handler; tcs.TrySetCanceled(); }); // Queue the command for processing var task = commandQueue.EnqueueAsync(cmd); task.ContinueWith( t => { token.ThrowIfCancellationRequested(); // If anything goes wrong, stop listening for the completion event and update the task if (t.IsFaulted) { messageBus.MessageReceived -= handler; tcs.TrySetException(t.Exception); } else if (t.IsCanceled) { tcs.TrySetCanceled(); } }, TaskContinuationOptions.NotOnRanToCompletion); return tcs.Task; }