diff --git a/docs/compilers/CSharp/Warnversion Warning Waves.md b/docs/compilers/CSharp/Warnversion Warning Waves.md
index 28ad714a979ee..f0ce4ec58cbd5 100644
--- a/docs/compilers/CSharp/Warnversion Warning Waves.md
+++ b/docs/compilers/CSharp/Warnversion Warning Waves.md
@@ -20,6 +20,7 @@ The compiler shipped with .NET 11 (the C# 15 compiler) contains the following wa
| Warning ID | Description |
|------------|-------------|
| CS9368 | [RequiresUnsafeAttribute is only valid under the updated memory safety rules](https://github.com/dotnet/csharplang/issues/9704) |
+| CS9377 | [The 'unsafe' modifier does not have any effect here under the current rules](https://github.com/dotnet/csharplang/issues/9704) |
## Warning level 10
diff --git a/src/Compilers/CSharp/Portable/CSharpResources.resx b/src/Compilers/CSharp/Portable/CSharpResources.resx
index 9146af5d34fb1..63e109852d062 100644
--- a/src/Compilers/CSharp/Portable/CSharpResources.resx
+++ b/src/Compilers/CSharp/Portable/CSharpResources.resx
@@ -8276,6 +8276,14 @@ To remove the warning, you can use /reference instead (set the Embed Interop Typ
An unsafe context is required for constructor '{0}' marked as 'RequiresUnsafe' or 'extern' to satisfy the 'new()' constraint of type parameter '{1}' in '{2}''RequiresUnsafe', 'extern', and 'new()' should not be localized. {2} is the generic method or type.
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+
'{0}' does not contain a definition for '{1}' and no accessible extension method '{1}' accepting a first argument of type '{0}' could be found (did you mean to iterate over the async collection with 'await foreach' instead?)'await foreach' is not localizable
diff --git a/src/Compilers/CSharp/Portable/Errors/ErrorCode.cs b/src/Compilers/CSharp/Portable/Errors/ErrorCode.cs
index f4a22e8e46ec6..e74090121257a 100644
--- a/src/Compilers/CSharp/Portable/Errors/ErrorCode.cs
+++ b/src/Compilers/CSharp/Portable/Errors/ErrorCode.cs
@@ -2482,6 +2482,7 @@ internal enum ErrorCode
ERR_UnionConstructorCallsDefaultConstructor = 9375,
ERR_UnsafeConstructorConstraint = 9376,
+ WRN_UnsafeMeaningless = 9377,
// Note: you will need to do the following after adding errors:
// 1) Update ErrorFacts.IsBuildOnlyDiagnostic (src/Compilers/CSharp/Portable/Errors/ErrorFacts.cs)
diff --git a/src/Compilers/CSharp/Portable/Errors/ErrorFacts.cs b/src/Compilers/CSharp/Portable/Errors/ErrorFacts.cs
index 275651d36925b..28b29c59ecaee 100644
--- a/src/Compilers/CSharp/Portable/Errors/ErrorFacts.cs
+++ b/src/Compilers/CSharp/Portable/Errors/ErrorFacts.cs
@@ -211,6 +211,7 @@ internal static int GetWarningLevel(ErrorCode code)
switch (code)
{
case ErrorCode.WRN_RequiresUnsafeAttributeLegacyRules:
+ case ErrorCode.WRN_UnsafeMeaningless:
// Warning level 11 is exclusively for warnings introduced in the compiler
// shipped with dotnet 11 (C# 15) and that can be reported for pre-existing code.
return 11;
@@ -2587,6 +2588,7 @@ or ErrorCode.ERR_InstanceFieldInUnion
or ErrorCode.ERR_InstanceCtorWithOneParameterInUnion
or ErrorCode.ERR_UnionConstructorCallsDefaultConstructor
or ErrorCode.ERR_UnsafeConstructorConstraint
+ or ErrorCode.WRN_UnsafeMeaningless
=> false,
};
#pragma warning restore CS8524 // The switch expression does not handle some values of its input type (it is not exhaustive) involving an unnamed enum value.
diff --git a/src/Compilers/CSharp/Portable/Generated/ErrorFacts.Generated.cs b/src/Compilers/CSharp/Portable/Generated/ErrorFacts.Generated.cs
index a5bdd3a4c251a..c0a24a1e72859 100644
--- a/src/Compilers/CSharp/Portable/Generated/ErrorFacts.Generated.cs
+++ b/src/Compilers/CSharp/Portable/Generated/ErrorFacts.Generated.cs
@@ -347,6 +347,7 @@ public static bool IsWarning(ErrorCode code)
case ErrorCode.WRN_InterceptsLocationAttributeUnsupportedSignature:
case ErrorCode.WRN_RedundantPattern:
case ErrorCode.WRN_RequiresUnsafeAttributeLegacyRules:
+ case ErrorCode.WRN_UnsafeMeaningless:
return true;
default:
return false;
diff --git a/src/Compilers/CSharp/Portable/Symbols/Source/SourceMemberContainerSymbol.cs b/src/Compilers/CSharp/Portable/Symbols/Source/SourceMemberContainerSymbol.cs
index e4b70ab7c88b4..1650d3e95b919 100644
--- a/src/Compilers/CSharp/Portable/Symbols/Source/SourceMemberContainerSymbol.cs
+++ b/src/Compilers/CSharp/Portable/Symbols/Source/SourceMemberContainerSymbol.cs
@@ -375,6 +375,14 @@ private DeclarationModifiers MakeModifiers(TypeKind typeKind, BindingDiagnosticB
diagnostics.Add(ErrorCode.ERR_SealedStaticClass, GetFirstLocation(), this);
}
+ if (!modifierErrors &&
+ typeKind == TypeKind.Delegate &&
+ (mods & DeclarationModifiers.Unsafe) == DeclarationModifiers.Unsafe &&
+ this.ContainingModule.UseUpdatedMemorySafetyRules)
+ {
+ diagnostics.Add(ErrorCode.WRN_UnsafeMeaningless, GetFirstLocation());
+ }
+
switch (typeKind)
{
case TypeKind.Interface:
diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.cs.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.cs.xlf
index 9e7bc6cfb0bd4..052baa36dc709 100644
--- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.cs.xlf
+++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.cs.xlf
@@ -5930,6 +5930,16 @@
Parametr se nepřečetl. Nezapomněli jste ho použít k inicializaci vlastnosti s daným názvem?
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+ UnscopedRefAttribute is only valid in C# 11 or later or when targeting net7.0 or later.UnscopedRefAttribute je platný jenom v C# 11 nebo novějším nebo při cílení na net7.0 nebo novější.
diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.de.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.de.xlf
index 1ab684b474b0f..f0a249a181628 100644
--- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.de.xlf
+++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.de.xlf
@@ -5930,6 +5930,16 @@
Der Parameter wird nicht gelesen. Möglicherweise haben Sie ihn nicht zum Initialisieren der gleichnamigen Eigenschaft verwendet?
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+ UnscopedRefAttribute is only valid in C# 11 or later or when targeting net7.0 or later.UnscopedRefAttribute ist nur in C# 11 oder höher oder bei net7.0 oder höher gültig.
diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.es.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.es.xlf
index 464dcdaf36e8f..448dfc246db9f 100644
--- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.es.xlf
+++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.es.xlf
@@ -5930,6 +5930,16 @@
El parámetro no se ha leído ¿Olvidó usarlo para inicializar la propiedad con ese nombre?
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+ UnscopedRefAttribute is only valid in C# 11 or later or when targeting net7.0 or later.UnscopedRefAttribute solo es válido en C# 11 o posterior o cuando el destino es net7.0 o posterior.
diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.fr.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.fr.xlf
index afe2d2f2f0e32..f86f64e2cd438 100644
--- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.fr.xlf
+++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.fr.xlf
@@ -5930,6 +5930,16 @@
Le paramètre est non lu. Avez-vous oublié de l'utiliser pour initialiser la propriété portant ce nom ?
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+ UnscopedRefAttribute is only valid in C# 11 or later or when targeting net7.0 or later.UnscopedRefAttribute n’est valide qu’en C# 11 ou version ultérieure, ou quand net7.0 ou version ultérieure est ciblé.
diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.it.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.it.xlf
index 547771bfe782e..d06e165aec2f1 100644
--- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.it.xlf
+++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.it.xlf
@@ -5930,6 +5930,16 @@ target:module Compila un modulo che può essere aggiunto ad altro
Il parametro non è stato letto. Si è dimenticato di usarlo per inizializzare la proprietà con tale nome?
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+ UnscopedRefAttribute is only valid in C# 11 or later or when targeting net7.0 or later.UnscopedRefAttribute è valido solo in C# 11 o versioni successive o se destinato a net7.0 o versione successiva.
diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.ja.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.ja.xlf
index 64241839c2145..314ec115ba5df 100644
--- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.ja.xlf
+++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.ja.xlf
@@ -5930,6 +5930,16 @@
パラメーターが未読のため、この名前のプロパティを初期化するために使用していることを確認する必要がある
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+ UnscopedRefAttribute is only valid in C# 11 or later or when targeting net7.0 or later.UnscopedRefAttribute は、C# 11 以降、または net7.0 以降をターゲットにする場合にのみ有効です。
diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.ko.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.ko.xlf
index eff00786a8a6f..48d40ab5c1af8 100644
--- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.ko.xlf
+++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.ko.xlf
@@ -5930,6 +5930,16 @@
매개 변수를 읽을 수 없습니다. 이 매개 변수를 사용하여 해당 이름으로 속성을 초기화했는지 확인하세요.
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+ UnscopedRefAttribute is only valid in C# 11 or later or when targeting net7.0 or later.UnscopedRefAttribute는 C# 11 이상 또는 net7.0 이상을 대상으로 하는 경우에만 유효합니다.
diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.pl.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.pl.xlf
index 91df953998ab0..31898263e6687 100644
--- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.pl.xlf
+++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.pl.xlf
@@ -5930,6 +5930,16 @@
Parametr nie został odczytany. Czy zapomniano użyć go do zainicjowania właściwości o tej nazwie?
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+ UnscopedRefAttribute is only valid in C# 11 or later or when targeting net7.0 or later.Atrybut UnscopedRefAttribute jest prawidłowy tylko w języku C# 11 lub nowszym albo w przypadku platformy docelowej net7.0 lub nowszej.
diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.pt-BR.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.pt-BR.xlf
index 7d7e754ac3fe4..586daa10c22ae 100644
--- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.pt-BR.xlf
+++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.pt-BR.xlf
@@ -5930,6 +5930,16 @@
O parâmetro não foi lido. Você esqueceu de usá-lo para inicializar a propriedade com esse nome?
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+ UnscopedRefAttribute is only valid in C# 11 or later or when targeting net7.0 or later.UnscopedRefAttribute só é válido em C# 11 ou posterior ou ao direcionar para net7.0 ou posterior.
diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.ru.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.ru.xlf
index 53af5a77dfb40..38be70365db6e 100644
--- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.ru.xlf
+++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.ru.xlf
@@ -5930,6 +5930,16 @@
Параметр не читается. Возможно, вы забыли использовать его для инициализации свойства с таким же именем?
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+ UnscopedRefAttribute is only valid in C# 11 or later or when targeting net7.0 or later.UnscopedRefAttribute допустим только в C# 11 или более поздней версии или при нацелии на net7.0 или более позднюю версию.
diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.tr.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.tr.xlf
index e330ba83a5747..5da00f33dc61e 100644
--- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.tr.xlf
+++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.tr.xlf
@@ -5930,6 +5930,16 @@
Parametre okunmadı. Bu ada sahip özelliği başlatmak için bu parametreyi kullanmayı unutmuş olabilirsiniz.
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+ UnscopedRefAttribute is only valid in C# 11 or later or when targeting net7.0 or later.UnscopedRefAttribute yalnızca C# 11 veya sonraki sürümde veya net7.0 veya üzeri hedeflendiğinde geçerlidir.
diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.zh-Hans.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.zh-Hans.xlf
index 12a29def04b22..812b37c4a0e7f 100644
--- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.zh-Hans.xlf
+++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.zh-Hans.xlf
@@ -5930,6 +5930,16 @@
参数未读。是否忘记通过它来使用该名称初始化属性?
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+ UnscopedRefAttribute is only valid in C# 11 or later or when targeting net7.0 or later.UnscopedRefAttribute 仅在 C# 11 或更高版本中或面向 net7.0 或更高版本时有效。
diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.zh-Hant.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.zh-Hant.xlf
index a85203e8cd5c4..f97a4215806a7 100644
--- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.zh-Hant.xlf
+++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.zh-Hant.xlf
@@ -5930,6 +5930,16 @@ strument:TestCoverage 產生檢測要收集
參數未讀取。是否忘記使用該參數來初始化該名稱的屬性?
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+
+
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ 'unsafe' is a keyword, should not be localized.
+ UnscopedRefAttribute is only valid in C# 11 or later or when targeting net7.0 or later.UnscopedRefAttribute 只在 C# 11 或更新版本中有效,或以 net7.0 或更新版本為目標時有效。
diff --git a/src/Compilers/CSharp/Test/CSharp15/UnsafeEvolutionTests.cs b/src/Compilers/CSharp/Test/CSharp15/UnsafeEvolutionTests.cs
index cffbb71778ef8..ece1317ae6dff 100644
--- a/src/Compilers/CSharp/Test/CSharp15/UnsafeEvolutionTests.cs
+++ b/src/Compilers/CSharp/Test/CSharp15/UnsafeEvolutionTests.cs
@@ -2710,6 +2710,76 @@ public class SkipLocalsInitAttribute : Attribute;
Diagnostic(ErrorCode.ERR_UnsafeUninitializedStackAlloc, "stackalloc int[5]").WithLocation(3, 26));
}
+ [Fact]
+ public void UnsafeDeclarations()
+ {
+ var source = """
+ #pragma warning disable CS0169 // unused field
+ #pragma warning disable CS8019 // unused using
+ #pragma warning disable CS8321 // unused local function
+ using static unsafe System.Collections.Generic.List;
+ using unsafe U = int*;
+ unsafe void F() { }
+ unsafe class C;
+ unsafe struct S;
+ unsafe interface I;
+ unsafe enum E { A }
+ unsafe record R;
+ unsafe delegate void D();
+ class X
+ {
+ unsafe X() { }
+ unsafe ~X() { }
+ unsafe int f;
+ unsafe void M() { }
+ unsafe int P { get; set; }
+ unsafe event System.Action E { add { } remove { } }
+ public static unsafe implicit operator int(X x) => 0;
+ }
+ """;
+
+ var expectedDiagnostics = new[]
+ {
+ // (10,13): error CS0106: The modifier 'unsafe' is not valid for this item
+ // unsafe enum E { A }
+ Diagnostic(ErrorCode.ERR_BadMemberFlag, "E").WithArguments("unsafe").WithLocation(10, 13),
+ };
+
+ CreateCompilation([source, IsExternalInitTypeDefinition], options: TestOptions.UnsafeReleaseExe).VerifyDiagnostics(expectedDiagnostics);
+
+ CreateCompilation([source, IsExternalInitTypeDefinition], options: TestOptions.UnsafeReleaseExe.WithUpdatedMemorySafetyRules().WithWarningLevel(10)).VerifyDiagnostics(expectedDiagnostics);
+
+ expectedDiagnostics =
+ [
+ // (10,13): error CS0106: The modifier 'unsafe' is not valid for this item
+ // unsafe enum E { A }
+ Diagnostic(ErrorCode.ERR_BadMemberFlag, "E").WithArguments("unsafe").WithLocation(10, 13),
+ // (12,22): warning CS9377: The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ // unsafe delegate void D();
+ Diagnostic(ErrorCode.WRN_UnsafeMeaningless, "D").WithLocation(12, 22),
+ ];
+
+ CreateCompilation([source, IsExternalInitTypeDefinition], options: TestOptions.UnsafeReleaseExe.WithUpdatedMemorySafetyRules()).VerifyDiagnostics(expectedDiagnostics);
+
+ CreateCompilation([source, IsExternalInitTypeDefinition], options: TestOptions.UnsafeReleaseExe.WithUpdatedMemorySafetyRules().WithWarningLevel(11)).VerifyDiagnostics(expectedDiagnostics);
+
+ CreateCompilation([source, IsExternalInitTypeDefinition],
+ parseOptions: TestOptions.RegularNext,
+ options: TestOptions.UnsafeReleaseExe.WithUpdatedMemorySafetyRules()).VerifyDiagnostics(expectedDiagnostics);
+
+ CreateCompilation([source, IsExternalInitTypeDefinition],
+ parseOptions: TestOptions.Regular14,
+ options: TestOptions.UnsafeReleaseExe.WithUpdatedMemorySafetyRules()).VerifyDiagnostics(
+ // error CS8630: Invalid 'MemorySafetyRules' value: '2' for C# 14.0. Please use language version 'preview' or greater.
+ Diagnostic(ErrorCode.ERR_CompilationOptionNotAvailable).WithArguments("MemorySafetyRules", "2", "14.0", "preview").WithLocation(1, 1),
+ // (10,13): error CS0106: The modifier 'unsafe' is not valid for this item
+ // unsafe enum E { A }
+ Diagnostic(ErrorCode.ERR_BadMemberFlag, "E").WithArguments("unsafe").WithLocation(10, 13),
+ // (12,22): warning CS9377: The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ // unsafe delegate void D();
+ Diagnostic(ErrorCode.WRN_UnsafeMeaningless, "D").WithLocation(12, 22));
+ }
+
[Fact]
public void Member_LangVersion()
{
@@ -3125,8 +3195,6 @@ public static void M() { }
[Fact]
public void Member_Method_ConvertToDelegate()
{
- // https://github.com/dotnet/roslyn/issues/82546: confirm with LDM that delegates cannot be marked caller-unsafe;
- // then unsafe modifier on a delegate should result in a warning
CompileAndVerifyUnsafe(
lib: """
public static class C
@@ -3155,6 +3223,15 @@ public static void M() { }
// (2,8): error CS9362: 'C.M()' must be used in an unsafe context because it is marked as 'RequiresUnsafe' or 'extern'
// D2 b = C.M;
Diagnostic(ErrorCode.ERR_UnsafeMemberOperation, "C.M").WithArguments("C.M()").WithLocation(2, 8),
+ // (7,22): warning CS9377: The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ // unsafe delegate void D2();
+ Diagnostic(ErrorCode.WRN_UnsafeMeaningless, "D2").WithLocation(7, 22),
+ ],
+ expectedDiagnosticsWhenReferencingLegacyLib:
+ [
+ // (7,22): warning CS9377: The 'unsafe' modifier does not have any effect here under the current memory safety rules.
+ // unsafe delegate void D2();
+ Diagnostic(ErrorCode.WRN_UnsafeMeaningless, "D2").WithLocation(7, 22),
]);
}
diff --git a/src/Compilers/CSharp/Test/Syntax/Diagnostics/DiagnosticTest.cs b/src/Compilers/CSharp/Test/Syntax/Diagnostics/DiagnosticTest.cs
index 7753a6118f1b7..b21e1edee14fa 100644
--- a/src/Compilers/CSharp/Test/Syntax/Diagnostics/DiagnosticTest.cs
+++ b/src/Compilers/CSharp/Test/Syntax/Diagnostics/DiagnosticTest.cs
@@ -482,6 +482,7 @@ public void WarningLevel_2()
Assert.Equal(10, ErrorFacts.GetWarningLevel(errorCode));
break;
case ErrorCode.WRN_RequiresUnsafeAttributeLegacyRules:
+ case ErrorCode.WRN_UnsafeMeaningless:
// These are the warnings introduced with the warning "wave" shipped with dotnet 11 and C# 15.
Assert.Equal(11, ErrorFacts.GetWarningLevel(errorCode));
break;