diff --git a/src/libraries/System.Text.RegularExpressions/gen/RegexGenerator.Emitter.cs b/src/libraries/System.Text.RegularExpressions/gen/RegexGenerator.Emitter.cs
index cbe77998186a2d..b95387ba4eceed 100644
--- a/src/libraries/System.Text.RegularExpressions/gen/RegexGenerator.Emitter.cs
+++ b/src/libraries/System.Text.RegularExpressions/gen/RegexGenerator.Emitter.cs
@@ -41,7 +41,7 @@ public partial class RegexGenerator
};
/// Generates the code for one regular expression class.
- private static (string, ImmutableArray) EmitRegexType(RegexType regexClass)
+ private static (string, ImmutableArray) EmitRegexType(RegexType regexClass, Compilation compilation)
{
var sb = new StringBuilder(1024);
var writer = new IndentedTextWriter(new StringWriter(sb));
@@ -82,7 +82,7 @@ private static (string, ImmutableArray) EmitRegexType(RegexType rege
generatedName += ComputeStringHash(generatedName).ToString("X");
// Generate the regex type
- ImmutableArray diagnostics = EmitRegexMethod(writer, regexClass.Method, generatedName);
+ ImmutableArray diagnostics = EmitRegexMethod(writer, regexClass.Method, generatedName, compilation);
while (writer.Indent != 0)
{
@@ -149,7 +149,7 @@ static bool ExceedsMaxDepthForSimpleCodeGeneration(RegexNode node, int allowedDe
}
/// Generates the code for a regular expression method.
- private static ImmutableArray EmitRegexMethod(IndentedTextWriter writer, RegexMethod rm, string id)
+ private static ImmutableArray EmitRegexMethod(IndentedTextWriter writer, RegexMethod rm, string id, Compilation compilation)
{
string patternExpression = Literal(rm.Pattern);
string optionsExpression = Literal(rm.Options);
@@ -174,6 +174,8 @@ private static ImmutableArray EmitRegexMethod(IndentedTextWriter wri
return ImmutableArray.Create(Diagnostic.Create(DiagnosticDescriptors.LimitedSourceGeneration, rm.MethodSyntax.GetLocation()));
}
+ bool allowUnsafe = compilation.Options is CSharpCompilationOptions { AllowUnsafe: true };
+
writer.WriteLine($"new {id}();");
writer.WriteLine();
writer.WriteLine($" private {id}()");
@@ -231,6 +233,10 @@ private static ImmutableArray EmitRegexMethod(IndentedTextWriter wri
writer.Indent -= 4;
writer.WriteLine($" }}");
writer.WriteLine();
+ if (allowUnsafe)
+ {
+ writer.WriteLine($" [global::System.Runtime.CompilerServices.SkipLocalsInit]");
+ }
writer.WriteLine($" protected override void Go()");
writer.WriteLine($" {{");
writer.Indent += 4;
diff --git a/src/libraries/System.Text.RegularExpressions/gen/RegexGenerator.cs b/src/libraries/System.Text.RegularExpressions/gen/RegexGenerator.cs
index a459c8312c2639..558c613eae3a8f 100644
--- a/src/libraries/System.Text.RegularExpressions/gen/RegexGenerator.cs
+++ b/src/libraries/System.Text.RegularExpressions/gen/RegexGenerator.cs
@@ -49,7 +49,7 @@ public void Initialize(IncrementalGeneratorInitializationContext context)
{
Debug.Assert(state.Item1 is not null);
object? result = GetRegexTypeToEmit(state.Item2, state.Item1, cancellationToken);
- return result is RegexType regexType ? EmitRegexType(regexType) : result;
+ return result is RegexType regexType ? EmitRegexType(regexType, state.Item2) : result;
})
.Collect();
diff --git a/src/libraries/System.Text.RegularExpressions/tests/System.Text.RegularExpressions.Generators.Tests/RegexGeneratorParserTests.cs b/src/libraries/System.Text.RegularExpressions/tests/System.Text.RegularExpressions.Generators.Tests/RegexGeneratorParserTests.cs
index 1e8523d2f73f4a..da7e19c820128e 100644
--- a/src/libraries/System.Text.RegularExpressions/tests/System.Text.RegularExpressions.Generators.Tests/RegexGeneratorParserTests.cs
+++ b/src/libraries/System.Text.RegularExpressions/tests/System.Text.RegularExpressions.Generators.Tests/RegexGeneratorParserTests.cs
@@ -297,8 +297,10 @@ partial class C
", compile: true));
}
- [Fact]
- public async Task Valid_ClassWithNamespace()
+ [Theory]
+ [InlineData(false)]
+ [InlineData(true)]
+ public async Task Valid_ClassWithNamespace(bool allowUnsafe)
{
Assert.Empty(await RunGenerator(@"
using System.Text.RegularExpressions;
@@ -310,7 +312,7 @@ partial class C
private static partial Regex Valid();
}
}
- ", compile: true));
+ ", compile: true, allowUnsafe: allowUnsafe));
}
[Fact]
@@ -557,13 +559,13 @@ partial class C
}
private async Task> RunGenerator(
- string code, bool compile = false, LanguageVersion langVersion = LanguageVersion.Preview, MetadataReference[]? additionalRefs = null, CancellationToken cancellationToken = default)
+ string code, bool compile = false, LanguageVersion langVersion = LanguageVersion.Preview, MetadataReference[]? additionalRefs = null, bool allowUnsafe = false, CancellationToken cancellationToken = default)
{
var proj = new AdhocWorkspace()
.AddSolution(SolutionInfo.Create(SolutionId.CreateNewId(), VersionStamp.Create()))
.AddProject("RegexGeneratorTest", "RegexGeneratorTest.dll", "C#")
.WithMetadataReferences(additionalRefs is not null ? s_refs.Concat(additionalRefs) : s_refs)
- .WithCompilationOptions(new CSharpCompilationOptions(OutputKind.DynamicallyLinkedLibrary)
+ .WithCompilationOptions(new CSharpCompilationOptions(OutputKind.DynamicallyLinkedLibrary, allowUnsafe: allowUnsafe)
.WithNullableContextOptions(NullableContextOptions.Enable))
.WithParseOptions(new CSharpParseOptions(langVersion))
.AddDocument("RegexGenerator.g.cs", SourceText.From(code, Encoding.UTF8)).Project;