diff --git a/.github/CODEOWNERS b/.github/CODEOWNERS
index 7892c5dde5f8b..96aa66ea78416 100644
--- a/.github/CODEOWNERS
+++ b/.github/CODEOWNERS
@@ -51,4 +51,4 @@ src/Features/**/PublicAPI.Unshipped.txt @dotnet/roslyn-api-owners
src/EditorFeatures/**/PublicAPI.Unshipped.txt @dotnet/roslyn-api-owners
src/Tools/ExternalAccess/OmniSharp*/ @333fred @joerobich
-src/Tools/ExternalAccess/RazorCompiler @dotnet/roslyn-compiler
+src/Tools/ExternalAccess/RazorCompiler*/ @dotnet/roslyn-compiler
diff --git a/Compilers.slnf b/Compilers.slnf
index 1592c27fe452e..b543ac0c43dce 100644
--- a/Compilers.slnf
+++ b/Compilers.slnf
@@ -60,6 +60,7 @@
"src\\Scripting\\CoreTestUtilities\\Microsoft.CodeAnalysis.Scripting.TestUtilities.csproj",
"src\\Test\\PdbUtilities\\Roslyn.Test.PdbUtilities.csproj",
"src\\Tools\\ExternalAccess\\RazorCompiler\\Microsoft.CodeAnalysis.ExternalAccess.RazorCompiler.csproj",
+ "src\\Tools\\ExternalAccess\\RazorCompilerTest\\Microsoft.CodeAnalysis.ExternalAccess.RazorCompiler.UnitTests.csproj",
"src\\Tools\\PrepareTests\\PrepareTests.csproj",
"src\\Tools\\Source\\CompilerGeneratorTools\\Source\\CSharpSyntaxGenerator\\CSharpSyntaxGenerator.csproj",
"src\\Tools\\Source\\CompilerGeneratorTools\\Source\\BoundTreeGenerator\\CompilersBoundTreeGenerator.csproj",
diff --git a/Roslyn.sln b/Roslyn.sln
index 4070ee47d994e..93faf8198e9cc 100644
--- a/Roslyn.sln
+++ b/Roslyn.sln
@@ -523,6 +523,8 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "TestDiscoveryWorker", "src\
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.CodeAnalysis.ExternalAccess.RazorCompiler", "src\Tools\ExternalAccess\RazorCompiler\Microsoft.CodeAnalysis.ExternalAccess.RazorCompiler.csproj", "{E5E0BF73-95F7-4BC3-8443-2336C4FF4297}"
EndProject
+Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Microsoft.CodeAnalysis.ExternalAccess.RazorCompiler.UnitTests", "src\Tools\ExternalAccess\RazorCompilerTest\Microsoft.CodeAnalysis.ExternalAccess.RazorCompiler.UnitTests.csproj", "{828FD0DB-9927-42AC-B6C2-D1514965D6C3}"
+EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
@@ -1277,6 +1279,10 @@ Global
{E5E0BF73-95F7-4BC3-8443-2336C4FF4297}.Debug|Any CPU.Build.0 = Debug|Any CPU
{E5E0BF73-95F7-4BC3-8443-2336C4FF4297}.Release|Any CPU.ActiveCfg = Release|Any CPU
{E5E0BF73-95F7-4BC3-8443-2336C4FF4297}.Release|Any CPU.Build.0 = Release|Any CPU
+ {828FD0DB-9927-42AC-B6C2-D1514965D6C3}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+ {828FD0DB-9927-42AC-B6C2-D1514965D6C3}.Debug|Any CPU.Build.0 = Debug|Any CPU
+ {828FD0DB-9927-42AC-B6C2-D1514965D6C3}.Release|Any CPU.ActiveCfg = Release|Any CPU
+ {828FD0DB-9927-42AC-B6C2-D1514965D6C3}.Release|Any CPU.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
@@ -1515,6 +1521,7 @@ Global
{8A29449D-411E-49E4-B99E-E8428076BB21} = {55A62CFA-1155-46F1-ADF3-BEEE51B58AB5}
{8BC50AFF-1EBF-4E9A-AEBB-04F387AA800F} = {FD0FAF5F-1DED-485C-99FA-84B97F3A8EEC}
{E5E0BF73-95F7-4BC3-8443-2336C4FF4297} = {8977A560-45C2-4EC2-A849-97335B382C74}
+ {828FD0DB-9927-42AC-B6C2-D1514965D6C3} = {8977A560-45C2-4EC2-A849-97335B382C74}
EndGlobalSection
GlobalSection(ExtensibilityGlobals) = postSolution
SolutionGuid = {604E6B91-7BC0-4126-AE07-D4D2FEFC3D29}
diff --git a/src/Compilers/Core/Portable/SourceGeneration/GeneratorDriver.cs b/src/Compilers/Core/Portable/SourceGeneration/GeneratorDriver.cs
index 121d393fc3a7f..cc44c5649fc56 100644
--- a/src/Compilers/Core/Portable/SourceGeneration/GeneratorDriver.cs
+++ b/src/Compilers/Core/Portable/SourceGeneration/GeneratorDriver.cs
@@ -26,6 +26,8 @@ namespace Microsoft.CodeAnalysis
///
public abstract class GeneratorDriver
{
+ internal const IncrementalGeneratorOutputKind HostKind = (IncrementalGeneratorOutputKind)0b100000; // several steps higher than IncrementalGeneratorOutputKind.Implementation
+
internal readonly GeneratorDriverState _state;
internal GeneratorDriver(GeneratorDriverState state)
@@ -293,7 +295,7 @@ internal GeneratorDriverState RunGeneratorsCore(Compilation compilation, Diagnos
try
{
// We do not support incremental step tracking for v1 generators, as the pipeline is implicitly defined.
- var context = UpdateOutputs(generatorState.OutputNodes, IncrementalGeneratorOutputKind.Source | IncrementalGeneratorOutputKind.Implementation, new GeneratorRunStateTable.Builder(state.TrackIncrementalSteps), cancellationToken, driverStateBuilder);
+ var context = UpdateOutputs(generatorState.OutputNodes, IncrementalGeneratorOutputKind.Source | IncrementalGeneratorOutputKind.Implementation | HostKind, new GeneratorRunStateTable.Builder(state.TrackIncrementalSteps), cancellationToken, driverStateBuilder);
(var sources, var generatorDiagnostics, var generatorRunStateTable, var hostOutputs) = context.ToImmutableAndFree();
generatorDiagnostics = FilterDiagnostics(compilation, generatorDiagnostics, driverDiagnostics: diagnosticsBag, cancellationToken);
diff --git a/src/Compilers/Test/Core/Microsoft.CodeAnalysis.Test.Utilities.csproj b/src/Compilers/Test/Core/Microsoft.CodeAnalysis.Test.Utilities.csproj
index 93f58be9c4b0f..6cf90d717094f 100644
--- a/src/Compilers/Test/Core/Microsoft.CodeAnalysis.Test.Utilities.csproj
+++ b/src/Compilers/Test/Core/Microsoft.CodeAnalysis.Test.Utilities.csproj
@@ -57,6 +57,7 @@
+
diff --git a/src/Compilers/Test/Utilities/CSharp/Microsoft.CodeAnalysis.CSharp.Test.Utilities.csproj b/src/Compilers/Test/Utilities/CSharp/Microsoft.CodeAnalysis.CSharp.Test.Utilities.csproj
index ab6bbe3cea2fe..2bac019b860be 100644
--- a/src/Compilers/Test/Utilities/CSharp/Microsoft.CodeAnalysis.CSharp.Test.Utilities.csproj
+++ b/src/Compilers/Test/Utilities/CSharp/Microsoft.CodeAnalysis.CSharp.Test.Utilities.csproj
@@ -30,6 +30,7 @@
+
diff --git a/src/Tools/ExternalAccess/RazorCompiler/HostOutputNode.cs b/src/Tools/ExternalAccess/RazorCompiler/HostOutputNode.cs
index 73380e5550dba..3ae1b7dcd296e 100644
--- a/src/Tools/ExternalAccess/RazorCompiler/HostOutputNode.cs
+++ b/src/Tools/ExternalAccess/RazorCompiler/HostOutputNode.cs
@@ -26,7 +26,7 @@ public HostOutputNode(IIncrementalGeneratorNode source, Action (IncrementalGeneratorOutputKind)0b100000; // several steps higher than IncrementalGeneratorOutputKind.Implementation
+ public IncrementalGeneratorOutputKind Kind => GeneratorDriver.HostKind;
public NodeStateTable UpdateStateTable(DriverStateTable.Builder graphState, NodeStateTable? previousTable, CancellationToken cancellationToken)
{
diff --git a/src/Tools/ExternalAccess/RazorCompiler/Microsoft.CodeAnalysis.ExternalAccess.RazorCompiler.csproj b/src/Tools/ExternalAccess/RazorCompiler/Microsoft.CodeAnalysis.ExternalAccess.RazorCompiler.csproj
index 8868589e8e333..d22dd38f7a180 100644
--- a/src/Tools/ExternalAccess/RazorCompiler/Microsoft.CodeAnalysis.ExternalAccess.RazorCompiler.csproj
+++ b/src/Tools/ExternalAccess/RazorCompiler/Microsoft.CodeAnalysis.ExternalAccess.RazorCompiler.csproj
@@ -15,10 +15,13 @@
+
+
+
diff --git a/src/Tools/ExternalAccess/RazorCompilerTest/HostOutputsTests.cs b/src/Tools/ExternalAccess/RazorCompilerTest/HostOutputsTests.cs
new file mode 100644
index 0000000000000..ac6da1b1b9d6a
--- /dev/null
+++ b/src/Tools/ExternalAccess/RazorCompilerTest/HostOutputsTests.cs
@@ -0,0 +1,51 @@
+// Licensed to the .NET Foundation under one or more agreements.
+// The .NET Foundation licenses this file to you under the MIT license.
+// See the LICENSE file in the project root for more information.
+
+using System.Linq;
+using Microsoft.CodeAnalysis.CSharp;
+using Microsoft.CodeAnalysis.CSharp.Test.Utilities;
+using Microsoft.CodeAnalysis.CSharp.UnitTests;
+using Microsoft.CodeAnalysis.Test.Utilities;
+using Roslyn.Test.Utilities.TestGenerators;
+using Xunit;
+
+namespace Microsoft.CodeAnalysis.ExternalAccess.RazorCompiler.UnitTests
+{
+ public class HostOutputsTests : CSharpTestBase
+ {
+ [Fact]
+ public void Added()
+ {
+ var source = """
+ class C { }
+ """;
+ var parseOptions = TestOptions.Regular;
+ var compilation = CreateCompilation(source, options: TestOptions.DebugDllThrowing, parseOptions: parseOptions);
+ compilation.VerifyDiagnostics();
+
+ Assert.Single(compilation.SyntaxTrees);
+
+ var generator = new PipelineCallbackGenerator(ctx =>
+ {
+ var syntaxProvider = ctx.SyntaxProvider.CreateSyntaxProvider((n, _) => n.IsKind(SyntaxKind.ClassDeclaration), (c, _) => c.Node);
+
+ ctx.RegisterHostOutput(syntaxProvider, static (hpc, node, _) =>
+ {
+ hpc.AddOutput("test", node.ToFullString());
+ });
+ });
+
+ GeneratorDriver driver = CSharpGeneratorDriver.Create(new[] { generator.AsSourceGenerator() }, parseOptions: parseOptions);
+ driver = driver.RunGenerators(compilation);
+
+ var result = driver.GetRunResult().Results.Single();
+ Assert.Empty(result.Diagnostics);
+
+ var hostOutputs = result.GetHostOutputs();
+ Assert.Equal(1, hostOutputs.Length);
+ Assert.Equal("test", hostOutputs[0].Key);
+ Assert.Equal(source, hostOutputs[0].Value);
+ }
+ }
+}
diff --git a/src/Tools/ExternalAccess/RazorCompilerTest/Microsoft.CodeAnalysis.ExternalAccess.RazorCompiler.UnitTests.csproj b/src/Tools/ExternalAccess/RazorCompilerTest/Microsoft.CodeAnalysis.ExternalAccess.RazorCompiler.UnitTests.csproj
new file mode 100644
index 0000000000000..9f9413cfd9de3
--- /dev/null
+++ b/src/Tools/ExternalAccess/RazorCompilerTest/Microsoft.CodeAnalysis.ExternalAccess.RazorCompiler.UnitTests.csproj
@@ -0,0 +1,14 @@
+
+
+
+
+ Library
+ Microsoft.CodeAnalysis.ExternalAccess.RazorCompiler.UnitTests
+ net7.0;net472
+
+
+
+
+
+
+