diff --git a/src/Compilers/CSharp/Portable/CSharpResources.resx b/src/Compilers/CSharp/Portable/CSharpResources.resx index 73669cf03a73b..f63705d10f4d1 100644 --- a/src/Compilers/CSharp/Portable/CSharpResources.resx +++ b/src/Compilers/CSharp/Portable/CSharpResources.resx @@ -2112,14 +2112,11 @@ If such a class is used as a base class and if the deriving class defines a dest Inconsistent lambda parameter usage; parameter types must be all explicit or all implicit - A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers + A partial method cannot have the 'abstract' modifier A partial method must be declared within a partial class, partial struct, or partial interface - - A partial method cannot have out parameters - A partial method may not explicitly implement an interface method @@ -2156,9 +2153,6 @@ If such a class is used as a base class and if the deriving class defines a dest Partial methods with only a defining declaration or removed conditional methods cannot be used in expression trees - - Partial methods must have a void return type - Obsolete member '{0}' overrides non-obsolete member '{1}' @@ -6070,4 +6064,25 @@ To remove the warning, you can use /reference instead (set the Embed Interop Typ Generator failed to initialize. + + extended partial methods + + + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + + + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + + + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + + + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + + + Both partial method declarations must have identical accessibility modifiers. + + + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + \ No newline at end of file diff --git a/src/Compilers/CSharp/Portable/Errors/ErrorCode.cs b/src/Compilers/CSharp/Portable/Errors/ErrorCode.cs index 548ce34a91b1f..d5f450887fa11 100644 --- a/src/Compilers/CSharp/Portable/Errors/ErrorCode.cs +++ b/src/Compilers/CSharp/Portable/Errors/ErrorCode.cs @@ -531,7 +531,7 @@ internal enum ErrorCode ERR_InconsistentLambdaParameterUsage = 748, ERR_PartialMethodInvalidModifier = 750, ERR_PartialMethodOnlyInPartialClass = 751, - ERR_PartialMethodCannotHaveOutParameters = 752, + // ERR_PartialMethodCannotHaveOutParameters = 752, Removed as part of 'extended partial methods' feature // ERR_PartialMethodOnlyMethods = 753, Removed as it is subsumed by ERR_PartialMisplaced ERR_PartialMethodNotExplicit = 754, ERR_PartialMethodExtensionDifference = 755, @@ -544,7 +544,7 @@ internal enum ErrorCode ERR_PartialMethodStaticDifference = 763, ERR_PartialMethodUnsafeDifference = 764, ERR_PartialMethodInExpressionTree = 765, - ERR_PartialMethodMustReturnVoid = 766, + // ERR_PartialMethodMustReturnVoid = 766, Removed as part of 'extended partial methods' feature ERR_ExplicitImplCollisionOnRefOut = 767, ERR_IndirectRecursiveConstructorCall = 768, @@ -1777,6 +1777,17 @@ internal enum ErrorCode ERR_ExpressionTreeContainsFromEndIndexExpression = 8791, ERR_ExpressionTreeContainsRangeExpression = 8792, + #region diagnostics introduced for C# 9 + + ERR_PartialMethodWithAccessibilityModsMustHaveImplementation = 8793, + ERR_PartialMethodWithNonVoidReturnMustHaveAccessMods = 8794, + ERR_PartialMethodWithOutParamMustHaveAccessMods = 8795, + ERR_PartialMethodWithExtendedModMustHaveAccessMods = 8796, + ERR_PartialMethodAccessibilityDifference = 8797, + ERR_PartialMethodExtendedModDifference = 8798, + + #endregion + // Note: you will need to re-generate compiler code after adding warnings (eng\generate-compiler-code.cmd) } } diff --git a/src/Compilers/CSharp/Portable/Errors/MessageID.cs b/src/Compilers/CSharp/Portable/Errors/MessageID.cs index ee1d0255674a3..6387bf79df4ee 100644 --- a/src/Compilers/CSharp/Portable/Errors/MessageID.cs +++ b/src/Compilers/CSharp/Portable/Errors/MessageID.cs @@ -192,6 +192,7 @@ internal enum MessageID IDS_FeatureMemberNotNull = MessageBase + 12768, IDS_FeatureNativeInt = MessageBase + 12769, IDS_FeatureTargetTypedObjectCreation = MessageBase + 12770, + IDS_FeatureExtendedPartialMethods = MessageBase + 12771 } // Message IDs may refer to strings that need to be localized. @@ -305,6 +306,7 @@ internal static LanguageVersion RequiredVersion(this MessageID feature) case MessageID.IDS_FeatureTargetTypedObjectCreation: // syntax check case MessageID.IDS_FeatureMemberNotNull: case MessageID.IDS_FeatureNativeInt: + case MessageID.IDS_FeatureExtendedPartialMethods: // semantic check return LanguageVersion.Preview; // C# 8.0 features. diff --git a/src/Compilers/CSharp/Portable/Symbols/Source/ModifierUtils.cs b/src/Compilers/CSharp/Portable/Symbols/Source/ModifierUtils.cs index 113edb51c177b..f46e0c21f789f 100644 --- a/src/Compilers/CSharp/Portable/Symbols/Source/ModifierUtils.cs +++ b/src/Compilers/CSharp/Portable/Symbols/Source/ModifierUtils.cs @@ -61,13 +61,6 @@ internal static DeclarationModifiers CheckModifiers( modifierErrors = true; } - bool isMethod = (allowedModifiers & (DeclarationModifiers.Partial | DeclarationModifiers.Virtual)) == (DeclarationModifiers.Partial | DeclarationModifiers.Virtual); - if (isMethod && ((result & (DeclarationModifiers.Partial | DeclarationModifiers.Private)) == (DeclarationModifiers.Partial | DeclarationModifiers.Private))) - { - diagnostics.Add(ErrorCode.ERR_PartialMethodInvalidModifier, errorLocation); - modifierErrors = true; - } - if ((result & DeclarationModifiers.PrivateProtected) != 0) { modifierErrors |= !Binder.CheckFeatureAvailability(errorLocation.SourceTree, MessageID.IDS_FeaturePrivateProtected, diagnostics, errorLocation); diff --git a/src/Compilers/CSharp/Portable/Symbols/Source/SourceMemberContainerSymbol.cs b/src/Compilers/CSharp/Portable/Symbols/Source/SourceMemberContainerSymbol.cs index 55e28950700af..ab6f419779b7d 100644 --- a/src/Compilers/CSharp/Portable/Symbols/Source/SourceMemberContainerSymbol.cs +++ b/src/Compilers/CSharp/Portable/Symbols/Source/SourceMemberContainerSymbol.cs @@ -1683,10 +1683,13 @@ private void CheckMemberNameConflicts(DiagnosticBag diagnostics) // UNDONE: Consider adding a secondary location pointing to the second method. private void ReportMethodSignatureCollision(DiagnosticBag diagnostics, SourceMemberMethodSymbol method1, SourceMemberMethodSymbol method2) { - // Partial methods are allowed to collide by signature. - if (method1.IsPartial && method2.IsPartial) + switch (method1, method2) { - return; + case (SourceOrdinaryMethodSymbol { IsPartialDefinition: true }, SourceOrdinaryMethodSymbol { IsPartialImplementation: true }): + case (SourceOrdinaryMethodSymbol { IsPartialImplementation: true }, SourceOrdinaryMethodSymbol { IsPartialDefinition: true }): + // these could be 2 parts of the same partial method. + // Partial methods are allowed to collide by signature. + return; } // If method1 is a constructor only because its return type is missing, then @@ -2567,6 +2570,10 @@ private static void MergePartialMembers( { diagnostics.Add(ErrorCode.ERR_PartialMethodInconsistentTupleNames, method.Locations[0], method, method.OtherPartOfPartial); } + else if (method is { IsPartialDefinition: true, OtherPartOfPartial: null, HasExplicitAccessModifier: true }) + { + diagnostics.Add(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, method.Locations[0], method); + } } } } diff --git a/src/Compilers/CSharp/Portable/Symbols/Source/SourceMemberContainerSymbol_ImplementationChecks.cs b/src/Compilers/CSharp/Portable/Symbols/Source/SourceMemberContainerSymbol_ImplementationChecks.cs index fea26594c042b..555e6caf002ba 100644 --- a/src/Compilers/CSharp/Portable/Symbols/Source/SourceMemberContainerSymbol_ImplementationChecks.cs +++ b/src/Compilers/CSharp/Portable/Symbols/Source/SourceMemberContainerSymbol_ImplementationChecks.cs @@ -827,7 +827,7 @@ private static void CheckOverrideMember(Symbol overridingMember, OverriddenOrHid diagnostics.Add(ErrorCode.ERR_CantOverrideSealed, overridingMemberLocation, overridingMember, overriddenMember); suppressAccessors = true; } - else if (!overridingMember.IsPartialMethod() && !OverrideHasCorrectAccessibility(overriddenMember, overridingMember)) + else if (!OverrideHasCorrectAccessibility(overriddenMember, overridingMember)) { var accessibility = SyntaxFacts.GetText(overriddenMember.DeclaredAccessibility); diagnostics.Add(ErrorCode.ERR_CantChangeAccessOnOverride, overridingMemberLocation, overridingMember, accessibility, overriddenMember); diff --git a/src/Compilers/CSharp/Portable/Symbols/Source/SourceMemberMethodSymbol.cs b/src/Compilers/CSharp/Portable/Symbols/Source/SourceMemberMethodSymbol.cs index 0c990945c7f25..da00327b943d4 100644 --- a/src/Compilers/CSharp/Portable/Symbols/Source/SourceMemberMethodSymbol.cs +++ b/src/Compilers/CSharp/Portable/Symbols/Source/SourceMemberMethodSymbol.cs @@ -441,7 +441,7 @@ public override Accessibility DeclaredAccessibility } } - public sealed override bool IsExtern + internal bool HasExternModifier { get { @@ -449,6 +449,14 @@ public sealed override bool IsExtern } } + public override bool IsExtern + { + get + { + return HasExternModifier; + } + } + public sealed override bool IsSealed { get diff --git a/src/Compilers/CSharp/Portable/Symbols/Source/SourceMethodSymbolWithAttributes.cs b/src/Compilers/CSharp/Portable/Symbols/Source/SourceMethodSymbolWithAttributes.cs index c697063b029ec..2e2ae5b7faad8 100644 --- a/src/Compilers/CSharp/Portable/Symbols/Source/SourceMethodSymbolWithAttributes.cs +++ b/src/Compilers/CSharp/Portable/Symbols/Source/SourceMethodSymbolWithAttributes.cs @@ -642,7 +642,8 @@ private void DecodeDllImportAttribute(ref DecodeWellKnownAttributeArguments MakeTypeParameters(MethodDeclaration return result.ToImmutableAndFree(); } + private const DeclarationModifiers PartialMethodExtendedModifierMask = + DeclarationModifiers.Virtual | + DeclarationModifiers.Override | + DeclarationModifiers.New | + DeclarationModifiers.Sealed | + DeclarationModifiers.Extern; + + internal bool HasExtendedPartialModifier => (DeclarationModifiers & PartialMethodExtendedModifierMask) != 0; + private void CheckModifiers(bool isExplicitInterfaceImplementation, bool hasBody, Location location, DiagnosticBag diagnostics) { - const DeclarationModifiers partialMethodInvalidModifierMask = (DeclarationModifiers.AccessibilityMask & ~DeclarationModifiers.Private) | - DeclarationModifiers.Virtual | - DeclarationModifiers.Abstract | - DeclarationModifiers.Override | - DeclarationModifiers.New | - DeclarationModifiers.Sealed | - DeclarationModifiers.Extern; - bool isExplicitInterfaceImplementationInInterface = isExplicitInterfaceImplementation && ContainingType.IsInterface; - if (IsPartial && !ReturnsVoid) + if (IsPartial && HasExplicitAccessModifier) { - diagnostics.Add(ErrorCode.ERR_PartialMethodMustReturnVoid, location); + Binder.CheckFeatureAvailability(SyntaxNode, MessageID.IDS_FeatureExtendedPartialMethods, diagnostics, location); } - else if (IsPartial && (DeclarationModifiers & partialMethodInvalidModifierMask) != 0) + + if (IsPartial && IsAbstract) { diagnostics.Add(ErrorCode.ERR_PartialMethodInvalidModifier, location); } + else if (IsPartial && !HasExplicitAccessModifier && !ReturnsVoid) + { + diagnostics.Add(ErrorCode.ERR_PartialMethodWithNonVoidReturnMustHaveAccessMods, location, this); + } + else if (IsPartial && !HasExplicitAccessModifier && HasExtendedPartialModifier) + { + diagnostics.Add(ErrorCode.ERR_PartialMethodWithExtendedModMustHaveAccessMods, location, this); + } + else if (IsPartial && !HasExplicitAccessModifier && Parameters.Any(p => p.RefKind == RefKind.Out)) + { + diagnostics.Add(ErrorCode.ERR_PartialMethodWithOutParamMustHaveAccessMods, location, this); + } else if (this.DeclaredAccessibility == Accessibility.Private && (IsVirtual || (IsAbstract && !isExplicitInterfaceImplementationInInterface) || IsOverride)) { diagnostics.Add(ErrorCode.ERR_VirtualPrivate, location, this); @@ -1144,6 +1173,20 @@ private static void PartialMethodChecks(SourceOrdinaryMethodSymbol definition, S diagnostics.Add(ErrorCode.ERR_PartialMethodParamsDifference, implementation.Locations[0]); } + if (definition.HasExplicitAccessModifier != implementation.HasExplicitAccessModifier + || definition.DeclaredAccessibility != implementation.DeclaredAccessibility) + { + diagnostics.Add(ErrorCode.ERR_PartialMethodAccessibilityDifference, implementation.Locations[0]); + } + + if (definition.IsVirtual != implementation.IsVirtual + || definition.IsOverride != implementation.IsOverride + || definition.IsSealed != implementation.IsSealed + || definition.IsNew != implementation.IsNew) + { + diagnostics.Add(ErrorCode.ERR_PartialMethodExtendedModDifference, implementation.Locations[0]); + } + PartialMethodConstraintsChecks(definition, implementation, diagnostics); SourceMemberContainerTypeSymbol.CheckValidNullableMethodOverride( diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.cs.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.cs.xlf index 3652cf943e922..da991558a1d9e 100644 --- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.cs.xlf +++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.cs.xlf @@ -397,11 +397,41 @@ Metoda {0} určuje omezení struct pro parametr typu {1}, ale odpovídající parametr typu {2} přepsané nebo explicitně implementované metody {3} není typ, který nemůže mít hodnotu null. + + Both partial method declarations must have identical accessibility modifiers. + Both partial method declarations must have identical accessibility modifiers. + + + + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + + Both partial method declarations must be readonly or neither may be readonly Obě deklarace částečné metody musí mít modifikátor readonly, nebo nesmí mít modifikátor readonly žádná z nich. + + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + + + + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + + + + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + + + + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + + Pattern-matching is not permitted for pointer types. Porovnávání vzorů není povolené pro typy ukazatelů. @@ -909,6 +939,11 @@ deklarace proměnných výrazu v inicializátorech členů a dotazech + + extended partial methods + extended partial methods + + extensible fixed statement rozšiřitelný příkaz fixed @@ -4924,8 +4959,8 @@ Pokud se taková třída používá jako základní třída a pokud odvozující - A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - Částečná metoda nemůže používat modifikátory přístupu ani modifikátory virtual, abstract, override, new, sealed či extern. + A partial method cannot have the 'abstract' modifier + Částečná metoda nemůže používat modifikátory přístupu ani modifikátory virtual, abstract, override, new, sealed či extern. @@ -4933,11 +4968,6 @@ Pokud se taková třída používá jako základní třída a pokud odvozující Částečná metoda musí být deklarovaná uvnitř částečné třídy, částečné struktury nebo částečného rozhraní. - - A partial method cannot have out parameters - Částečná metoda nemůže mít výstupní parametry. - - A partial method may not explicitly implement an interface method Částečná metoda nesmí explicitně implementovat metodu rozhraní. @@ -4998,11 +5028,6 @@ Pokud se taková třída používá jako základní třída a pokud odvozující Ve stromech výrazů nejde používat částečné metody, pro které existuje jenom definující deklarace, nebo odebrané podmíněné metody. - - Partial methods must have a void return type - Částečné metody musí mít návratový typ void. - - Obsolete member '{0}' overrides non-obsolete member '{1}' Zastaralý člen {0} potlačuje nezastaralý člen {1}. diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.de.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.de.xlf index 89f99f58ae35c..9ea50432e41b0 100644 --- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.de.xlf +++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.de.xlf @@ -397,11 +397,41 @@ Die Methode "{0}" gibt eine struct-Einschränkung für den Typparameter "{1}" an, aber der zugehörige Typparameter "{2}" der außer Kraft gesetzten oder explizit implementierten Methode "{3}" ist kein Non-Nullable-Werttyp. + + Both partial method declarations must have identical accessibility modifiers. + Both partial method declarations must have identical accessibility modifiers. + + + + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + + Both partial method declarations must be readonly or neither may be readonly Entweder beide oder keine der partiellen Methodendeklarationen müssen als "readonly" festgelegt werden. + + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + + + + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + + + + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + + + + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + + Pattern-matching is not permitted for pointer types. Der Musterabgleich ist für Zeigertypen unzulässig. @@ -909,6 +939,11 @@ Deklaration von Ausdrucksvariablen in Memberinitialisierern und Abfragen + + extended partial methods + extended partial methods + + extensible fixed statement Erweiterbare fixed-Anweisung @@ -4924,8 +4959,8 @@ Wenn solch eine Klasse als Basisklasse verwendet wird und die ableitende Klasse - A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - Eine partielle Methode darf keine Zugriffsmodifizierer oder die Modifizierer "virtual", "abstract", "override", "new", "sealed" oder "extern" enthalten. + A partial method cannot have the 'abstract' modifier + Eine partielle Methode darf keine Zugriffsmodifizierer oder die Modifizierer "virtual", "abstract", "override", "new", "sealed" oder "extern" enthalten. @@ -4933,11 +4968,6 @@ Wenn solch eine Klasse als Basisklasse verwendet wird und die ableitende Klasse Eine partielle Methode muss innerhalb einer partiellen Klasse, einer partiellen Struktur oder einer partiellen Schnittstelle deklariert sein. - - A partial method cannot have out parameters - Eine partielle Methode darf keine out-Parameter enthalten. - - A partial method may not explicitly implement an interface method Eine partielle Methode darf Schnittstellenmethoden nicht explizit implementieren. @@ -4998,11 +5028,6 @@ Wenn solch eine Klasse als Basisklasse verwendet wird und die ableitende Klasse In Ausdrucksbäumen dürfen weder partielle Methoden mit nur einer definierenden Deklaration noch entfernte bedingte Methoden verwendet werden. - - Partial methods must have a void return type - Partielle Methoden müssen einen void-Rückgabetyp haben. - - Obsolete member '{0}' overrides non-obsolete member '{1}' Der veraltete Member "{0}" überschreibt den nicht veralteten Member "{1}". diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.es.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.es.xlf index 4cd1fafa42e47..88fb58c426ea9 100644 --- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.es.xlf +++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.es.xlf @@ -397,11 +397,41 @@ El método "{0}" especifica una restricción "struct" para el parámetro de tipo "{1}", pero el parámetro de tipo correspondiente "{2}" de los métodos invalidados o implementados explícitamente "{3}" no es un tipo de valor que acepta valores NULL. + + Both partial method declarations must have identical accessibility modifiers. + Both partial method declarations must have identical accessibility modifiers. + + + + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + + Both partial method declarations must be readonly or neither may be readonly Ambas declaraciones de métodos parciales deben ser de solo lectura o ninguna de ellas puede ser de solo lectura + + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + + + + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + + + + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + + + + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + + Pattern-matching is not permitted for pointer types. No se permite la coincidencia de patrones para tipos de puntero. @@ -909,6 +939,11 @@ declaración de variables de expresión en inicializadores y consultas de miembros + + extended partial methods + extended partial methods + + extensible fixed statement instrucción "fixed" extensible @@ -4924,8 +4959,8 @@ Si se utiliza una clase de este tipo como clase base y si la clase derivada defi - A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - Un método parcial no puede tener modificadores de acceso ni los modificadores virtual, abstracto, invalidación, nuevo, sellado o externo + A partial method cannot have the 'abstract' modifier + Un método parcial no puede tener modificadores de acceso ni los modificadores virtual, abstracto, invalidación, nuevo, sellado o externo @@ -4933,11 +4968,6 @@ Si se utiliza una clase de este tipo como clase base y si la clase derivada defi Un método parcial debe declararse dentro de una clase parcial, una estructura parcial o una interfaz parcial - - A partial method cannot have out parameters - Un método parcial no puede tener parámetros out - - A partial method may not explicitly implement an interface method Un método parcial no puede implementar explícitamente un método de interfaz @@ -4998,11 +5028,6 @@ Si se utiliza una clase de este tipo como clase base y si la clase derivada defi En los árboles de expresión no se pueden usar métodos parciales con solo una declaración de definición ni métodos condicionales quitados - - Partial methods must have a void return type - Los métodos parciales deben tener un tipo de valor devuelto void - - Obsolete member '{0}' overrides non-obsolete member '{1}' El miembro obsoleto '{0}' invalida el miembro no obsoleto '{1}' diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.fr.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.fr.xlf index 62e8a589e10f8..149844e9da2d9 100644 --- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.fr.xlf +++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.fr.xlf @@ -397,11 +397,41 @@ La méthode '{0}' spécifie une contrainte 'struct' pour le paramètre de type '{1}', mais le paramètre de type '{2}' correspondant de la méthode substituée ou explicitement implémentée '{3}' n'est pas un type valeur non-nullable. + + Both partial method declarations must have identical accessibility modifiers. + Both partial method declarations must have identical accessibility modifiers. + + + + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + + Both partial method declarations must be readonly or neither may be readonly Soit les deux déclarations de méthodes partielles sont readonly, soit aucune ne l'est + + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + + + + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + + + + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + + + + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + + Pattern-matching is not permitted for pointer types. Les critères spéciaux ne sont pas autorisés pour les types de pointeur. @@ -909,6 +939,11 @@ déclaration de variables d'expression dans les initialiseurs de membres et les requêtes + + extended partial methods + extended partial methods + + extensible fixed statement instruction fixed extensible @@ -4924,8 +4959,8 @@ Si une telle classe est utilisée en tant que classe de base et si la classe dé - A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - Une méthode partielle ne peut pas avoir de modificateurs d'accès ou de modificateurs virtual, abstract, override, new, sealed ou extern + A partial method cannot have the 'abstract' modifier + Une méthode partielle ne peut pas avoir de modificateurs d'accès ou de modificateurs virtual, abstract, override, new, sealed ou extern @@ -4933,11 +4968,6 @@ Si une telle classe est utilisée en tant que classe de base et si la classe dé Une méthode partielle doit être déclarée dans une classe partielle, un struct partiel ou une interface partielle - - A partial method cannot have out parameters - Une méthode partielle ne peut pas avoir de paramètres out - - A partial method may not explicitly implement an interface method Une méthode partielle ne peut pas implémenter explicitement une méthode d'interface @@ -4998,11 +5028,6 @@ Si une telle classe est utilisée en tant que classe de base et si la classe dé Les méthodes partielles avec uniquement une déclaration de définition ou des méthodes conditionnelles supprimées ne peuvent pas être utilisées dans des arborescences d'expressions - - Partial methods must have a void return type - Les méthodes partielles doivent avoir un type de retour void - - Obsolete member '{0}' overrides non-obsolete member '{1}' Le membre obsolète '{0}' se substitue au membre non obsolète '{1}' diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.it.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.it.xlf index 3658daa426382..ade94016e89e5 100644 --- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.it.xlf +++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.it.xlf @@ -397,11 +397,41 @@ Il metodo '{0}' specifica un vincolo 'struct' per il parametro di tipo '{1}', ma il parametro di tipo corrispondente '{2}' del metodo '{3}' sottoposto a override o implementato in modo esplicito non è un tipo valore che non ammette valori Null. + + Both partial method declarations must have identical accessibility modifiers. + Both partial method declarations must have identical accessibility modifiers. + + + + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + + Both partial method declarations must be readonly or neither may be readonly Nessuna o entrambe le dichiarazioni di metodi parziali devono essere di tipo readonly + + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + + + + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + + + + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + + + + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + + Pattern-matching is not permitted for pointer types. I criteri di ricerca non sono consentiti per i tipi di puntatore. @@ -909,6 +939,11 @@ dichiarazione di variabili di espressione in query e inizializzatori di membri + + extended partial methods + extended partial methods + + extensible fixed statement istruzione fixed estendibile @@ -4924,8 +4959,8 @@ Se si usa tale classe come classe base e se la classe di derivazione definisce u - A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - Un metodo parziale non può avere modificatori di accesso o il modificatore virtual, abstract, override, new, sealed o extern + A partial method cannot have the 'abstract' modifier + Un metodo parziale non può avere modificatori di accesso o il modificatore virtual, abstract, override, new, sealed o extern @@ -4933,11 +4968,6 @@ Se si usa tale classe come classe base e se la classe di derivazione definisce u Un metodo parziale deve essere dichiarato in una classe, uno struct o un'interfaccia parziale - - A partial method cannot have out parameters - Un metodo parziale non può avere parametri out - - A partial method may not explicitly implement an interface method Un metodo parziale non può implementare in modo esplicito un metodo di interfaccia @@ -4998,11 +5028,6 @@ Se si usa tale classe come classe base e se la classe di derivazione definisce u Non è possibile usare negli alberi delle espressioni metodi parziali contenenti solo una dichiarazione di definizione o metodi condizionali rimossi - - Partial methods must have a void return type - I metodi parziali devono avere un tipo restituito void - - Obsolete member '{0}' overrides non-obsolete member '{1}' Il membro obsoleto '{0}' esegue l'override del membro non obsoleto '{1}' diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.ja.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.ja.xlf index 209c8a0cfc10d..23be828d7cd66 100644 --- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.ja.xlf +++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.ja.xlf @@ -397,11 +397,41 @@ メソッド '{0}' は、型パラメーター '{1}' に対して 'struct' 制約を指定していますが、オーバーライドされた、または明示的に実装されたメソッド '{3}' の対応する型パラメーター '{2}' は NULL 非許容の値型ではありません。 + + Both partial method declarations must have identical accessibility modifiers. + Both partial method declarations must have identical accessibility modifiers. + + + + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + + Both partial method declarations must be readonly or neither may be readonly 部分メソッド宣言は、両方とも readonly であるか、両方とも readonly でないかのいずれかである必要があります + + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + + + + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + + + + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + + + + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + + Pattern-matching is not permitted for pointer types. ポインター型でパターン マッチングを使用することはできません。 @@ -909,6 +939,11 @@ メンバー初期化子とクエリ内の式変数の宣言 + + extended partial methods + extended partial methods + + extensible fixed statement 拡張可能な fixed ステートメント @@ -4924,8 +4959,8 @@ If such a class is used as a base class and if the deriving class defines a dest - A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - 部分メソッドには、アクセス修飾子、あるいは virtual、abstract、override、new、sealed、または extern 修飾子を指定できません + A partial method cannot have the 'abstract' modifier + 部分メソッドには、アクセス修飾子、あるいは virtual、abstract、override、new、sealed、または extern 修飾子を指定できません @@ -4933,11 +4968,6 @@ If such a class is used as a base class and if the deriving class defines a dest 部分メソッドは、部分クラス、部分構造体、部分インターフェイス内で宣言される必要があります - - A partial method cannot have out parameters - 部分メソッドは、out パラメーターを含むことはできません - - A partial method may not explicitly implement an interface method 部分メソッドは、インターフェイス メソッドを明示的に実装できないことがあります @@ -4998,11 +5028,6 @@ If such a class is used as a base class and if the deriving class defines a dest 定義宣言だけを含む部分メソッドまたは削除された条件付きメソッドは、式ツリーで使用できません - - Partial methods must have a void return type - 部分メソッドには、void である戻り値の型が含まれている必要があります - - Obsolete member '{0}' overrides non-obsolete member '{1}' 旧形式のメンバー '{0}' は、旧形式でないメンバー '{1}' をオーバーライドします。 diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.ko.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.ko.xlf index 3f40cdc84e2b8..2a35af7f940a5 100644 --- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.ko.xlf +++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.ko.xlf @@ -397,11 +397,41 @@ '{0}' 메서드는 형식 매개 변수 '{1}'의 'struct' 제약 조건을 지정하지만 재정의되었거나 명시적으로 구현된 '{3}' 메서드의 해당 형식 매개 변수 '{2}'이(가) null을 허용하지 않는 값 형식이 아닙니다. + + Both partial method declarations must have identical accessibility modifiers. + Both partial method declarations must have identical accessibility modifiers. + + + + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + + Both partial method declarations must be readonly or neither may be readonly 두 부분 메서드(Partial method) 선언 모두 readonly이거나 readonly가 아니어야 합니다. + + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + + + + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + + + + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + + + + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + + Pattern-matching is not permitted for pointer types. 포인터 형식에 대해 패턴 일치가 허용되지 않습니다. @@ -909,6 +939,11 @@ 멤버 이니셜라이저 및 쿼리에서 식 변수 선언 + + extended partial methods + extended partial methods + + extensible fixed statement 확장 가능한 fixed 문 @@ -4924,8 +4959,8 @@ If such a class is used as a base class and if the deriving class defines a dest - A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - 부분 메서드(Partial Method)에는 액세스 한정자 또는 virtual, abstract, override, new, sealed나 extern 한정자를 사용할 수 없습니다. + A partial method cannot have the 'abstract' modifier + 부분 메서드(Partial Method)에는 액세스 한정자 또는 virtual, abstract, override, new, sealed나 extern 한정자를 사용할 수 없습니다. @@ -4933,11 +4968,6 @@ If such a class is used as a base class and if the deriving class defines a dest 부분 메서드(Partial method)는 partial 클래스, partial 구조체 또는 partial 인터페이스 내에 선언해야 합니다. - - A partial method cannot have out parameters - 부분 메서드(Partial Method)에는 out 매개 변수를 사용할 수 없습니다. - - A partial method may not explicitly implement an interface method 부분 메서드(Partial Method)는 인터페이스 메서드를 명시적으로 구현할 수 없습니다. @@ -4998,11 +5028,6 @@ If such a class is used as a base class and if the deriving class defines a dest 정의 선언만 있는 부분 메서드(Partial Method) 또는 제거된 조건부 메서드는 식 트리에 사용할 수 없습니다. - - Partial methods must have a void return type - 부분 메서드(Partial Method)의 반환 형식은 void여야 합니다. - - Obsolete member '{0}' overrides non-obsolete member '{1}' 사용되지 않는 '{0}' 멤버가 사용되는 '{1}' 멤버를 재정의합니다. diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.pl.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.pl.xlf index 9646a0784ee7c..f3197c24939db 100644 --- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.pl.xlf +++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.pl.xlf @@ -397,11 +397,41 @@ Metoda „{0}” określa ograniczenie „struct” dla parametru typu „{1}”, lecz odpowiadający parametr typu „{2}” przesłoniętej lub jawnie zaimplementowanej metody „{3}” nie jest nienullowalnym typem wartości. + + Both partial method declarations must have identical accessibility modifiers. + Both partial method declarations must have identical accessibility modifiers. + + + + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + + Both partial method declarations must be readonly or neither may be readonly Obie metody częściowe muszą być zadeklarowane jako readonly lub żadna nie może być zadeklarowana jako readonly + + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + + + + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + + + + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + + + + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + + Pattern-matching is not permitted for pointer types. Dopasowanie wzorca jest niedozwolone dla typów wskaźnika. @@ -909,6 +939,11 @@ deklaracje zmiennych wyrażeń w inicjatorach elementów członkowskich i zapytaniach + + extended partial methods + extended partial methods + + extensible fixed statement rozszerzalna instrukcja fixed @@ -4924,8 +4959,8 @@ Jeśli taka klasa zostanie użyta jako klasa bazowa i klasa pochodna definiuje d - A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - Metoda częściowa nie może mieć modyfikatorów dostępu ani modyfikatorów virtual, abstract, override, new, sealed lub extern. + A partial method cannot have the 'abstract' modifier + Metoda częściowa nie może mieć modyfikatorów dostępu ani modyfikatorów virtual, abstract, override, new, sealed lub extern. @@ -4933,11 +4968,6 @@ Jeśli taka klasa zostanie użyta jako klasa bazowa i klasa pochodna definiuje d Metoda częściowa musi być zadeklarowana w częściowej klasie, strukturze lub interfejsie - - A partial method cannot have out parameters - Metoda częściowa nie może mieć parametrów wyjściowych. - - A partial method may not explicitly implement an interface method Metoda częściowa nie może jawnie implementować metody interfejsu. @@ -4998,11 +5028,6 @@ Jeśli taka klasa zostanie użyta jako klasa bazowa i klasa pochodna definiuje d W drzewach wyrażeń nie można używać metod częściowych zawierających tylko deklarację definiującą ani usuniętych metod warunkowych. - - Partial methods must have a void return type - Metody częściowe muszą zwracać typ void. - - Obsolete member '{0}' overrides non-obsolete member '{1}' Przestarzała składowa „{0}” przesłania nieprzestarzałą składową „{1}”. diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.pt-BR.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.pt-BR.xlf index bc6654efe8ed8..cf20640f9c636 100644 --- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.pt-BR.xlf +++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.pt-BR.xlf @@ -397,11 +397,41 @@ O método '{0}' especifica uma restrição 'struct' para o parâmetro de tipo '{1}', mas o parâmetro de tipo correspondente '{2}' do método substituído ou implementado explicitamente '{3}' não é um tipo de valor não anulável. + + Both partial method declarations must have identical accessibility modifiers. + Both partial method declarations must have identical accessibility modifiers. + + + + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + + Both partial method declarations must be readonly or neither may be readonly As duas declarações de métodos parciais precisam ser readonly ou nenhuma deve ser readonly + + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + + + + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + + + + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + + + + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + + Pattern-matching is not permitted for pointer types. A correspondência de padrões não é permitida para tipos de ponteiro. @@ -907,6 +937,11 @@ declaração de variáveis de expressão em inicializadores e em consultas do membro + + extended partial methods + extended partial methods + + extensible fixed statement instrução fixed extensível @@ -4922,8 +4957,8 @@ Se tal classe for usada como uma classe base e se a classe derivada definir um d - A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - Um método parcial não pode ter modificadores de acesso ou modificadores do tipo virtual, abstract, override, new, sealed ou extern + A partial method cannot have the 'abstract' modifier + Um método parcial não pode ter modificadores de acesso ou modificadores do tipo virtual, abstract, override, new, sealed ou extern @@ -4931,11 +4966,6 @@ Se tal classe for usada como uma classe base e se a classe derivada definir um d Um método parcial precisa ser declarado em uma classe parcial, um struct parcial ou uma interface parcial - - A partial method cannot have out parameters - Um método parcial não pode ter parâmetros out - - A partial method may not explicitly implement an interface method Um método parcial não pode implementar explicitamente um método de interface @@ -4996,11 +5026,6 @@ Se tal classe for usada como uma classe base e se a classe derivada definir um d Os métodos parciais com apenas uma declaração de definição ou métodos condicionais removidos não podem ser usados em árvores de expressão - - Partial methods must have a void return type - Os métodos parciais devem ter um tipo de retorno void - - Obsolete member '{0}' overrides non-obsolete member '{1}' O membro obsoleto "{0}" substitui o membro não obsoleto "{1}" diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.ru.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.ru.xlf index bef3946e7ecba..d980ebadb770f 100644 --- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.ru.xlf +++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.ru.xlf @@ -397,11 +397,41 @@ Метод "{0}" задает ограничение struct для параметра типа "{1}", но соответствующий параметр типа "{2}" переопределенного или явно реализованного метода "{3}" не является типом значения, не допускающим значение NULL. + + Both partial method declarations must have identical accessibility modifiers. + Both partial method declarations must have identical accessibility modifiers. + + + + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + + Both partial method declarations must be readonly or neither may be readonly Либо оба объявления разделяемого метода должны иметь модификатор readonly, либо ни одно из них не должно иметь модификатор readonly. + + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + + + + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + + + + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + + + + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + + Pattern-matching is not permitted for pointer types. Сопоставление шаблонов запрещено для типов указателей. @@ -909,6 +939,11 @@ объявление переменных выражения в инициализаторах члена и запросах + + extended partial methods + extended partial methods + + extensible fixed statement расширяемый оператор fixed @@ -4924,8 +4959,8 @@ If such a class is used as a base class and if the deriving class defines a dest - A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - Разделяемый метод не может иметь модификаторы доступа или модификаторы virtual, abstract, override, new, sealed или extern. + A partial method cannot have the 'abstract' modifier + Разделяемый метод не может иметь модификаторы доступа или модификаторы virtual, abstract, override, new, sealed или extern. @@ -4933,11 +4968,6 @@ If such a class is used as a base class and if the deriving class defines a dest Разделяемый метод должен быть объявлен в разделяемом классе, разделяемой структуре или разделяемом интерфейсе - - A partial method cannot have out parameters - Разделяемый метод не может иметь параметры out. - - A partial method may not explicitly implement an interface method Разделяемый метод не может явно реализовывать метод интерфейса. @@ -4998,11 +5028,6 @@ If such a class is used as a base class and if the deriving class defines a dest В деревьях выражений не могут использоваться разделяемые методы, имеющие только определяющее объявление или только удаленные условные методы. - - Partial methods must have a void return type - Разделяемые методы должны иметь тип возвращаемого значения void. - - Obsolete member '{0}' overrides non-obsolete member '{1}' Член с атрибутом "obsolete" "{0}" переопределяет член без атрибута "obsolete" "{1}" diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.tr.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.tr.xlf index 3fbf2a504f69d..c660f60e16eb0 100644 --- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.tr.xlf +++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.tr.xlf @@ -397,11 +397,41 @@ '{0}' yöntemi, '{1}' tür parametresi için bir 'struct' kısıtlaması belirtiyor, ancak geçersiz kılınan veya açıkça uygulanan '{3}' yönteminin karşılık gelen '{2}' tür parametresi boş değer atanamaz bir tip değil. + + Both partial method declarations must have identical accessibility modifiers. + Both partial method declarations must have identical accessibility modifiers. + + + + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + + Both partial method declarations must be readonly or neither may be readonly İki kısmi yöntem bildiriminin de saltokunur olması ya da hiçbirinin saltokunur olmaması gerekir + + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + + + + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + + + + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + + + + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + + Pattern-matching is not permitted for pointer types. İşaretçi türleri için desen eşleştirmeye izin verilmez. @@ -909,6 +939,11 @@ üye başlatıcılarda ve sorgularda ifade değişkenlerinin bildirimi + + extended partial methods + extended partial methods + + extensible fixed statement genişletilebilir fixed deyimi @@ -4924,8 +4959,8 @@ Bu sınıf temel sınıf olarak kullanılırsa ve türetilen sınıf bir yıkıc - A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - Kısmi bir yöntemin erişim değiştiricileri ya da virtual, abstract, override, new, sealed veya extern değiştiricileri olamaz + A partial method cannot have the 'abstract' modifier + Kısmi bir yöntemin erişim değiştiricileri ya da virtual, abstract, override, new, sealed veya extern değiştiricileri olamaz @@ -4933,11 +4968,6 @@ Bu sınıf temel sınıf olarak kullanılırsa ve türetilen sınıf bir yıkıc Kısmi bir yöntemin kısmi bir sınıf, kısmi bir yapı veya kısmi bir arabirim içinde bildirilmesi gerekir - - A partial method cannot have out parameters - Kısmi bir yöntemin out parametreleri olamaz - - A partial method may not explicitly implement an interface method Kısmi bir yöntem bir arabirim yöntemini açık olarak uygulayamaz @@ -4998,11 +5028,6 @@ Bu sınıf temel sınıf olarak kullanılırsa ve türetilen sınıf bir yıkıc Yalnızca bir tanımlama bildirimi olan kısmi yöntemler veya kaldırılmış koşullu yöntemler ifade ağaçlarında kullanılamaz - - Partial methods must have a void return type - Kısmi yöntemlerin dönüş türü void olmalıdır - - Obsolete member '{0}' overrides non-obsolete member '{1}' Kullanılmayan '{0}' üyesi kullanılan '{1}' üyesini geçersiz kılar diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.zh-Hans.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.zh-Hans.xlf index 0a9d95c7c3bd3..4e72b1790144b 100644 --- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.zh-Hans.xlf +++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.zh-Hans.xlf @@ -397,11 +397,41 @@ 方法 "{0}" 为类型参数 "{1}" 指定了 "struct" 约束,但重写的或显式实现的方法 "{3}" 的相应类型参数 "{2}" 不是不可为 null 的值类型。 + + Both partial method declarations must have identical accessibility modifiers. + Both partial method declarations must have identical accessibility modifiers. + + + + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + + Both partial method declarations must be readonly or neither may be readonly 两个分部方法声明必须都是只读声明,或者两者都不能是只读声明 + + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + + + + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + + + + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + + + + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + + Pattern-matching is not permitted for pointer types. 指针类型不允许进行模式匹配。 @@ -909,6 +939,11 @@ 成员初始值设定项和查询中的表达式变量声明 + + extended partial methods + extended partial methods + + extensible fixed statement 可扩展 fixed 语句 @@ -4924,8 +4959,8 @@ If such a class is used as a base class and if the deriving class defines a dest - A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - 分部方法不能具有访问修饰符或 virtual、abstract、override、new、sealed 或 extern 修饰符 + A partial method cannot have the 'abstract' modifier + 分部方法不能具有访问修饰符或 virtual、abstract、override、new、sealed 或 extern 修饰符 @@ -4933,11 +4968,6 @@ If such a class is used as a base class and if the deriving class defines a dest 分部方法必须在分部类、分部结构或分布接口内声明 - - A partial method cannot have out parameters - 分部方法不能有 out 参数 - - A partial method may not explicitly implement an interface method 分部方法不能显式实现接口方法 @@ -4998,11 +5028,6 @@ If such a class is used as a base class and if the deriving class defines a dest 不能在表达式树中使用只有定义声明的分部方法或已移除的条件方法 - - Partial methods must have a void return type - 分部方法必须具有 void 返回类型 - - Obsolete member '{0}' overrides non-obsolete member '{1}' 过时成员“{0}”重写未过时成员“{1}” diff --git a/src/Compilers/CSharp/Portable/xlf/CSharpResources.zh-Hant.xlf b/src/Compilers/CSharp/Portable/xlf/CSharpResources.zh-Hant.xlf index d9b702bbc5e6a..314c7f3c5c090 100644 --- a/src/Compilers/CSharp/Portable/xlf/CSharpResources.zh-Hant.xlf +++ b/src/Compilers/CSharp/Portable/xlf/CSharpResources.zh-Hant.xlf @@ -397,11 +397,41 @@ 方法 '{0}' 會為型別參數 '{1}' 指定 'struct' 條件約束,但覆寫或明確實作的方法 '{3}' 對應型別參數 '{2}' 是不可為 Null 實值型別。 + + Both partial method declarations must have identical accessibility modifiers. + Both partial method declarations must have identical accessibility modifiers. + + + + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + + Both partial method declarations must be readonly or neither may be readonly 兩個部份方法宣告必須都為唯讀,或者都不為唯讀 + + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + Partial method '{0}' must have an implementation part because it has accessibility modifiers. + + + + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + Partial method '{0}' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + + + + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + Partial method '{0}' must have accessibility modifiers because it has a non-void return type. + + + + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + Partial method '{0}' must have accessibility modifiers because it has 'out' parameters. + + Pattern-matching is not permitted for pointer types. 指標類型不允許進行模式比對。 @@ -909,6 +939,11 @@ 成員初始設定式及查詢中之運算式變數的宣告 + + extended partial methods + extended partial methods + + extensible fixed statement 可延伸 fixed 陳述式 @@ -4924,8 +4959,8 @@ If such a class is used as a base class and if the deriving class defines a dest - A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - 部分方法不可有存取修飾詞或 virtual、abstract、override、new、sealed 或 extern 修飾元 + A partial method cannot have the 'abstract' modifier + 部分方法不可有存取修飾詞或 virtual、abstract、override、new、sealed 或 extern 修飾元 @@ -4933,11 +4968,6 @@ If such a class is used as a base class and if the deriving class defines a dest 在部分類別、部分結構或部分介面中必須宣告部分方法 - - A partial method cannot have out parameters - 部分方法不可有 out 參數 - - A partial method may not explicitly implement an interface method 部分方法不可明確地實作介面方法 @@ -4998,11 +5028,6 @@ If such a class is used as a base class and if the deriving class defines a dest 在運算式樹狀結構中,不可使用只具有定義宣告或已移除條件式方法的部分方法。 - - Partial methods must have a void return type - 部分方法必須有 void 傳回類型 - - Obsolete member '{0}' overrides non-obsolete member '{1}' 過時的成員 '{0}' 會覆寫非過時的成員 '{1}' diff --git a/src/Compilers/CSharp/Test/Emit/CodeGen/CodeGenAsyncIteratorTests.cs b/src/Compilers/CSharp/Test/Emit/CodeGen/CodeGenAsyncIteratorTests.cs index 23aa0898e705b..05567255d9951 100644 --- a/src/Compilers/CSharp/Test/Emit/CodeGen/CodeGenAsyncIteratorTests.cs +++ b/src/Compilers/CSharp/Test/Emit/CodeGen/CodeGenAsyncIteratorTests.cs @@ -7460,29 +7460,29 @@ public partial class C2 partial async System.Collections.Generic.IAsyncEnumerable M2([EnumeratorCancellation] CancellationToken token); // 6 } "; - var comp = CreateCompilationWithAsyncIterator(new[] { source, EnumeratorCancellationAttributeType }); + var comp = CreateCompilationWithAsyncIterator(new[] { source, EnumeratorCancellationAttributeType }, parseOptions: TestOptions.RegularWithExtendedPartialMethods); comp.VerifyDiagnostics( // (6,76): error CS1994: The 'async' modifier can only be used in methods that have a body. // public abstract async System.Collections.Generic.IAsyncEnumerable M([EnumeratorCancellation] CancellationToken token); // 1 Diagnostic(ErrorCode.ERR_BadAsyncLacksBody, "M").WithLocation(6, 76), - // (7,74): warning CS8424: The EnumeratorCancellationAttribute applied to parameter 'token' will have no effect. The attribute is only effective on a parameter of type CancellationToken in an async-iterator method returning IAsyncEnumerable + // (7,74): warning CS8424: The EnumeratorCancellationAttribute applied to parameter 'token' will have no effect. The attribute is only effective on a parameter of type CancellationToken in an async-iterator method returning IAsyncEnumerable // public abstract System.Collections.Generic.IAsyncEnumerable M2([EnumeratorCancellation] CancellationToken token); // 2 Diagnostic(ErrorCode.WRN_UnconsumedEnumeratorCancellationAttributeUsage, "EnumeratorCancellation").WithArguments("token").WithLocation(7, 74), - // (11,57): warning CS8424: The EnumeratorCancellationAttribute applied to parameter 'token' will have no effect. The attribute is only effective on a parameter of type CancellationToken in an async-iterator method returning IAsyncEnumerable + // (11,57): warning CS8424: The EnumeratorCancellationAttribute applied to parameter 'token' will have no effect. The attribute is only effective on a parameter of type CancellationToken in an async-iterator method returning IAsyncEnumerable // System.Collections.Generic.IAsyncEnumerable M([EnumeratorCancellation] CancellationToken token); // 3 Diagnostic(ErrorCode.WRN_UnconsumedEnumeratorCancellationAttributeUsage, "EnumeratorCancellation").WithArguments("token").WithLocation(11, 57), - // (15,80): warning CS8424: The EnumeratorCancellationAttribute applied to parameter 'token' will have no effect. The attribute is only effective on a parameter of type CancellationToken in an async-iterator method returning IAsyncEnumerable + // (15,80): warning CS8424: The EnumeratorCancellationAttribute applied to parameter 'token' will have no effect. The attribute is only effective on a parameter of type CancellationToken in an async-iterator method returning IAsyncEnumerable // public delegate System.Collections.Generic.IAsyncEnumerable Delegate([EnumeratorCancellation] CancellationToken token); // 4 Diagnostic(ErrorCode.WRN_UnconsumedEnumeratorCancellationAttributeUsage, "EnumeratorCancellation").WithArguments("token").WithLocation(15, 80), - // (16,62): error CS0766: Partial methods must have a void return type + // (16,62): error CS8794: Partial method 'C2.M(CancellationToken)' must have accessibility modifiers because it has a non-void return type. // partial System.Collections.Generic.IAsyncEnumerable M([EnumeratorCancellation] CancellationToken token); // 5 - Diagnostic(ErrorCode.ERR_PartialMethodMustReturnVoid, "M").WithLocation(16, 62), - // (16,65): warning CS8424: The EnumeratorCancellationAttribute applied to parameter 'token' will have no effect. The attribute is only effective on a parameter of type CancellationToken in an async-iterator method returning IAsyncEnumerable + Diagnostic(ErrorCode.ERR_PartialMethodWithNonVoidReturnMustHaveAccessMods, "M").WithArguments("C2.M(System.Threading.CancellationToken)").WithLocation(16, 62), + // (16,65): warning CS8424: The EnumeratorCancellationAttribute applied to parameter 'token' will have no effect. The attribute is only effective on a parameter of type CancellationToken in an async-iterator method returning IAsyncEnumerable // partial System.Collections.Generic.IAsyncEnumerable M([EnumeratorCancellation] CancellationToken token); // 5 Diagnostic(ErrorCode.WRN_UnconsumedEnumeratorCancellationAttributeUsage, "EnumeratorCancellation").WithArguments("token").WithLocation(16, 65), - // (17,68): error CS0766: Partial methods must have a void return type + // (17,68): error CS8794: Partial method 'C2.M2(CancellationToken)' must have accessibility modifiers because it has a non-void return type. // partial async System.Collections.Generic.IAsyncEnumerable M2([EnumeratorCancellation] CancellationToken token); // 6 - Diagnostic(ErrorCode.ERR_PartialMethodMustReturnVoid, "M2").WithLocation(17, 68) + Diagnostic(ErrorCode.ERR_PartialMethodWithNonVoidReturnMustHaveAccessMods, "M2").WithArguments("C2.M2(System.Threading.CancellationToken)").WithLocation(17, 68) ); } @@ -7559,23 +7559,23 @@ public partial class C3 partial async System.Collections.Generic.IAsyncEnumerable M2(CancellationToken token); // 5 } "; - var comp = CreateCompilationWithAsyncIterator(new[] { source, EnumeratorCancellationAttributeType }); + var comp = CreateCompilationWithAsyncIterator(new[] { source, EnumeratorCancellationAttributeType }, parseOptions: TestOptions.RegularWithExtendedPartialMethods); comp.VerifyDiagnostics( - // (7,67): error CS8425: Async-iterator 'C.M1(CancellationToken)' has one or more parameters of type 'CancellationToken' but none of them is decorated with the 'EnumeratorCancellation' attribute, so the cancellation token parameter from the generated 'IAsyncEnumerable<>.GetAsyncEnumerator' will be unconsumed + // (7,67): warning CS8425: Async-iterator 'C.M1(CancellationToken)' has one or more parameters of type 'CancellationToken' but none of them is decorated with the 'EnumeratorCancellation' attribute, so the cancellation token parameter from the generated 'IAsyncEnumerable<>.GetAsyncEnumerator' will be unconsumed // public async System.Collections.Generic.IAsyncEnumerable M1(CancellationToken token) // 1 Diagnostic(ErrorCode.WRN_UndecoratedCancellationTokenParameter, "M1").WithArguments("C.M1(System.Threading.CancellationToken)").WithLocation(7, 67), - // (12,67): error CS8425: Async-iterator 'C.M2(CancellationToken, CancellationToken)' has one or more parameters of type 'CancellationToken' but none of them is decorated with the 'EnumeratorCancellation' attribute, so the cancellation token parameter from the generated 'IAsyncEnumerable<>.GetAsyncEnumerator' will be unconsumed + // (12,67): warning CS8425: Async-iterator 'C.M2(CancellationToken, CancellationToken)' has one or more parameters of type 'CancellationToken' but none of them is decorated with the 'EnumeratorCancellation' attribute, so the cancellation token parameter from the generated 'IAsyncEnumerable<>.GetAsyncEnumerator' will be unconsumed // public async System.Collections.Generic.IAsyncEnumerable M2(CancellationToken token, CancellationToken token2) // 2 Diagnostic(ErrorCode.WRN_UndecoratedCancellationTokenParameter, "M2").WithArguments("C.M2(System.Threading.CancellationToken, System.Threading.CancellationToken)").WithLocation(12, 67), // (30,76): error CS1994: The 'async' modifier can only be used in methods that have a body. // public abstract async System.Collections.Generic.IAsyncEnumerable M(CancellationToken token); // 3 Diagnostic(ErrorCode.ERR_BadAsyncLacksBody, "M").WithLocation(30, 76), - // (40,62): error CS0766: Partial methods must have a void return type + // (40,62): error CS8794: Partial method 'C3.M(CancellationToken)' must have accessibility modifiers because it has a non-void return type. // partial System.Collections.Generic.IAsyncEnumerable M(CancellationToken token); // 4 - Diagnostic(ErrorCode.ERR_PartialMethodMustReturnVoid, "M").WithLocation(40, 62), - // (41,68): error CS0766: Partial methods must have a void return type + Diagnostic(ErrorCode.ERR_PartialMethodWithNonVoidReturnMustHaveAccessMods, "M").WithArguments("C3.M(System.Threading.CancellationToken)").WithLocation(40, 62), + // (41,68): error CS8794: Partial method 'C3.M2(CancellationToken)' must have accessibility modifiers because it has a non-void return type. // partial async System.Collections.Generic.IAsyncEnumerable M2(CancellationToken token); // 5 - Diagnostic(ErrorCode.ERR_PartialMethodMustReturnVoid, "M2").WithLocation(41, 68) + Diagnostic(ErrorCode.ERR_PartialMethodWithNonVoidReturnMustHaveAccessMods, "M2").WithArguments("C3.M2(System.Threading.CancellationToken)").WithLocation(41, 68) ); } } diff --git a/src/Compilers/CSharp/Test/Symbol/Symbols/DefaultInterfaceImplementationTests.cs b/src/Compilers/CSharp/Test/Symbol/Symbols/DefaultInterfaceImplementationTests.cs index 6d221ebfac973..fbbd2db849ec7 100644 --- a/src/Compilers/CSharp/Test/Symbol/Symbols/DefaultInterfaceImplementationTests.cs +++ b/src/Compilers/CSharp/Test/Symbol/Symbols/DefaultInterfaceImplementationTests.cs @@ -9199,27 +9199,27 @@ static partial void M8() {} } "; var compilation1 = CreateCompilation(source1, options: TestOptions.DebugDll, - parseOptions: TestOptions.Regular, + parseOptions: TestOptions.RegularWithExtendedPartialMethods, targetFramework: TargetFramework.NetStandardLatest); compilation1.VerifyDiagnostics( - // (4,24): error CS0766: Partial methods must have a void return type + // (4,24): error CS8794: Partial method 'I1.M1()' must have accessibility modifiers because it has a non-void return type. // static partial int M1(); - Diagnostic(ErrorCode.ERR_PartialMethodMustReturnVoid, "M1").WithLocation(4, 24), - // (5,32): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers + Diagnostic(ErrorCode.ERR_PartialMethodWithNonVoidReturnMustHaveAccessMods, "M1").WithArguments("I1.M1()").WithLocation(4, 24), + // (5,32): error CS8793: Partial method 'I1.M2()' must have an implementation part because it has accessibility modifiers. // public static partial void M2(); - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "M2").WithLocation(5, 32), - // (6,34): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers + Diagnostic(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, "M2").WithArguments("I1.M2()").WithLocation(5, 32), + // (6,34): error CS8793: Partial method 'I1.M3()' must have an implementation part because it has accessibility modifiers. // internal static partial void M3(); - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "M3").WithLocation(6, 34), - // (7,33): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers + Diagnostic(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, "M3").WithArguments("I1.M3()").WithLocation(6, 34), + // (7,33): error CS8793: Partial method 'I1.M4()' must have an implementation part because it has accessibility modifiers. // private static partial void M4(); - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "M4").WithLocation(7, 33), - // (8,25): error CS0752: A partial method cannot have out parameters + Diagnostic(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, "M4").WithArguments("I1.M4()").WithLocation(7, 33), + // (8,25): error CS8795: Partial method 'I1.M5(out int)' must have accessibility modifiers because it has 'out' parameters. // static partial void M5(out int x); - Diagnostic(ErrorCode.ERR_PartialMethodCannotHaveOutParameters, "M5").WithLocation(8, 25), + Diagnostic(ErrorCode.ERR_PartialMethodWithOutParamMustHaveAccessMods, "M5").WithArguments("I1.M5(out int)").WithLocation(8, 25), // (11,25): error CS0759: No defining declaration found for implementing declaration of partial method 'I1.M8()' - // static partial void M8() {} + // static partial void M8() {} Diagnostic(ErrorCode.ERR_PartialMethodMustHaveLatent, "M8").WithArguments("I1.M8()").WithLocation(11, 25), // (18,17): error CS0111: Type 'I1' already defines a member called 'M6' with the same parameter types // static void M6() {} @@ -9228,56 +9228,59 @@ static partial void M8() {} // static partial void M7(); Diagnostic(ErrorCode.ERR_MemberAlreadyExists, "M7").WithArguments("M7", "I1").WithLocation(19, 25), // (20,25): error CS0757: A partial method may not have multiple implementing declarations - // static partial void M8() {} + // static partial void M8() {} Diagnostic(ErrorCode.ERR_PartialMethodOnlyOneActual, "M8").WithLocation(20, 25), + // (20,25): error CS0111: Type 'I1' already defines a member called 'M8' with the same parameter types + // static partial void M8() {} + Diagnostic(ErrorCode.ERR_MemberAlreadyExists, "M8").WithArguments("M8", "I1").WithLocation(20, 25), // (21,25): error CS0756: A partial method may not have multiple defining declarations - // static partial void M9(); + // static partial void M9(); Diagnostic(ErrorCode.ERR_PartialMethodOnlyOneLatent, "M9").WithLocation(21, 25), - // (22,32): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - // static extern partial void M10(); - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "M10").WithLocation(22, 32), - // (22,32): error CS0756: A partial method may not have multiple defining declarations - // static extern partial void M10(); - Diagnostic(ErrorCode.ERR_PartialMethodOnlyOneLatent, "M10").WithLocation(22, 32), - // (23,35): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers + // (21,25): error CS0111: Type 'I1' already defines a member called 'M9' with the same parameter types + // static partial void M9(); + Diagnostic(ErrorCode.ERR_MemberAlreadyExists, "M9").WithArguments("M9", "I1").WithLocation(21, 25), + // (22,32): error CS8796: Partial method 'I1.M10()' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + // static extern partial void M10(); + Diagnostic(ErrorCode.ERR_PartialMethodWithExtendedModMustHaveAccessMods, "M10").WithArguments("I1.M10()").WithLocation(22, 32), + // (23,35): error CS8793: Partial method 'I1.M11()' must have an implementation part because it has accessibility modifiers. // protected static partial void M11(); - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "M11").WithLocation(23, 35), - // (24,44): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers + Diagnostic(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, "M11").WithArguments("I1.M11()").WithLocation(23, 35), + // (24,44): error CS8793: Partial method 'I1.M12()' must have an implementation part because it has accessibility modifiers. // protected internal static partial void M12(); - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "M12").WithLocation(24, 44), - // (25,43): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers + Diagnostic(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, "M12").WithArguments("I1.M12()").WithLocation(24, 44), + // (25,43): error CS8793: Partial method 'I1.M13()' must have an implementation part because it has accessibility modifiers. // private protected static partial void M13(); - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "M13").WithLocation(25, 43) + Diagnostic(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, "M13").WithArguments("I1.M13()").WithLocation(25, 43) ); var compilation2 = CreateCompilation(source1, options: TestOptions.DebugDll, - parseOptions: TestOptions.Regular, + parseOptions: TestOptions.RegularWithExtendedPartialMethods, targetFramework: TargetFramework.DesktopLatestExtended); compilation2.VerifyDiagnostics( - // (4,24): error CS0766: Partial methods must have a void return type + // (4,24): error CS8794: Partial method 'I1.M1()' must have accessibility modifiers because it has a non-void return type. // static partial int M1(); - Diagnostic(ErrorCode.ERR_PartialMethodMustReturnVoid, "M1").WithLocation(4, 24), - // (5,32): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers + Diagnostic(ErrorCode.ERR_PartialMethodWithNonVoidReturnMustHaveAccessMods, "M1").WithArguments("I1.M1()").WithLocation(4, 24), + // (5,32): error CS8793: Partial method 'I1.M2()' must have an implementation part because it has accessibility modifiers. // public static partial void M2(); - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "M2").WithLocation(5, 32), - // (6,34): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers + Diagnostic(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, "M2").WithArguments("I1.M2()").WithLocation(5, 32), + // (6,34): error CS8793: Partial method 'I1.M3()' must have an implementation part because it has accessibility modifiers. // internal static partial void M3(); - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "M3").WithLocation(6, 34), - // (7,33): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers + Diagnostic(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, "M3").WithArguments("I1.M3()").WithLocation(6, 34), + // (7,33): error CS8793: Partial method 'I1.M4()' must have an implementation part because it has accessibility modifiers. // private static partial void M4(); - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "M4").WithLocation(7, 33), - // (8,25): error CS0752: A partial method cannot have out parameters + Diagnostic(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, "M4").WithArguments("I1.M4()").WithLocation(7, 33), + // (8,25): error CS8795: Partial method 'I1.M5(out int)' must have accessibility modifiers because it has 'out' parameters. // static partial void M5(out int x); - Diagnostic(ErrorCode.ERR_PartialMethodCannotHaveOutParameters, "M5").WithLocation(8, 25), + Diagnostic(ErrorCode.ERR_PartialMethodWithOutParamMustHaveAccessMods, "M5").WithArguments("I1.M5(out int)").WithLocation(8, 25), // (10,17): error CS8701: Target runtime doesn't support default interface implementation. // static void M7() {} Diagnostic(ErrorCode.ERR_RuntimeDoesNotSupportDefaultInterfaceImplementation, "M7").WithLocation(10, 17), // (11,25): error CS8701: Target runtime doesn't support default interface implementation. - // static partial void M8() {} + // static partial void M8() {} Diagnostic(ErrorCode.ERR_RuntimeDoesNotSupportDefaultInterfaceImplementation, "M8").WithLocation(11, 25), // (11,25): error CS0759: No defining declaration found for implementing declaration of partial method 'I1.M8()' - // static partial void M8() {} + // static partial void M8() {} Diagnostic(ErrorCode.ERR_PartialMethodMustHaveLatent, "M8").WithArguments("I1.M8()").WithLocation(11, 25), // (18,17): error CS8701: Target runtime doesn't support default interface implementation. // static void M6() {} @@ -9289,32 +9292,35 @@ static partial void M8() {} // static partial void M7(); Diagnostic(ErrorCode.ERR_MemberAlreadyExists, "M7").WithArguments("M7", "I1").WithLocation(19, 25), // (20,25): error CS8701: Target runtime doesn't support default interface implementation. - // static partial void M8() {} + // static partial void M8() {} Diagnostic(ErrorCode.ERR_RuntimeDoesNotSupportDefaultInterfaceImplementation, "M8").WithLocation(20, 25), // (20,25): error CS0757: A partial method may not have multiple implementing declarations - // static partial void M8() {} + // static partial void M8() {} Diagnostic(ErrorCode.ERR_PartialMethodOnlyOneActual, "M8").WithLocation(20, 25), + // (20,25): error CS0111: Type 'I1' already defines a member called 'M8' with the same parameter types + // static partial void M8() {} + Diagnostic(ErrorCode.ERR_MemberAlreadyExists, "M8").WithArguments("M8", "I1").WithLocation(20, 25), // (21,25): error CS0756: A partial method may not have multiple defining declarations - // static partial void M9(); + // static partial void M9(); Diagnostic(ErrorCode.ERR_PartialMethodOnlyOneLatent, "M9").WithLocation(21, 25), + // (21,25): error CS0111: Type 'I1' already defines a member called 'M9' with the same parameter types + // static partial void M9(); + Diagnostic(ErrorCode.ERR_MemberAlreadyExists, "M9").WithArguments("M9", "I1").WithLocation(21, 25), // (22,32): error CS8701: Target runtime doesn't support default interface implementation. - // static extern partial void M10(); + // static extern partial void M10(); Diagnostic(ErrorCode.ERR_RuntimeDoesNotSupportDefaultInterfaceImplementation, "M10").WithLocation(22, 32), - // (22,32): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - // static extern partial void M10(); - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "M10").WithLocation(22, 32), - // (22,32): error CS0756: A partial method may not have multiple defining declarations - // static extern partial void M10(); - Diagnostic(ErrorCode.ERR_PartialMethodOnlyOneLatent, "M10").WithLocation(22, 32), - // (23,35): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers + // (22,32): error CS8796: Partial method 'I1.M10()' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + // static extern partial void M10(); + Diagnostic(ErrorCode.ERR_PartialMethodWithExtendedModMustHaveAccessMods, "M10").WithArguments("I1.M10()").WithLocation(22, 32), + // (23,35): error CS8793: Partial method 'I1.M11()' must have an implementation part because it has accessibility modifiers. // protected static partial void M11(); - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "M11").WithLocation(23, 35), - // (24,44): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers + Diagnostic(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, "M11").WithArguments("I1.M11()").WithLocation(23, 35), + // (24,44): error CS8793: Partial method 'I1.M12()' must have an implementation part because it has accessibility modifiers. // protected internal static partial void M12(); - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "M12").WithLocation(24, 44), - // (25,43): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers + Diagnostic(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, "M12").WithArguments("I1.M12()").WithLocation(24, 44), + // (25,43): error CS8793: Partial method 'I1.M13()' must have an implementation part because it has accessibility modifiers. // private protected static partial void M13(); - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "M13").WithLocation(25, 43) + Diagnostic(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, "M13").WithArguments("I1.M13()").WithLocation(25, 43) ); } @@ -9350,34 +9356,43 @@ interface I2 } "; var compilation1 = CreateCompilation(source1, options: TestOptions.DebugDll, - parseOptions: TestOptions.Regular, + parseOptions: TestOptions.RegularWithExtendedPartialMethods, targetFramework: TargetFramework.NetStandardLatest); compilation1.VerifyDiagnostics( - // (4,25): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers + // (4,25): error CS8796: Partial method 'I1.M1()' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. // sealed partial void M1(); - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "M1").WithLocation(4, 25), - // (5,27): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers + Diagnostic(ErrorCode.ERR_PartialMethodWithExtendedModMustHaveAccessMods, "M1").WithArguments("I1.M1()").WithLocation(4, 25), + // (5,27): error CS0750: A partial method cannot have the 'abstract' modifier // abstract partial void M2(); Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "M2").WithLocation(5, 27), - // (6,26): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers + // (6,26): error CS8796: Partial method 'I1.M3()' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. // virtual partial void M3(); - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "M3").WithLocation(6, 26), + Diagnostic(ErrorCode.ERR_PartialMethodWithExtendedModMustHaveAccessMods, "M3").WithArguments("I1.M3()").WithLocation(6, 26), // (10,21): error CS0754: A partial method may not explicitly implement an interface method // partial void I2.M7(); Diagnostic(ErrorCode.ERR_PartialMethodNotExplicit, "M7").WithLocation(10, 21), - // (15,25): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers + // (15,25): error CS8796: Partial method 'I1.M4()' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. // sealed partial void M4() {} - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "M4").WithLocation(15, 25), - // (16,27): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - // abstract partial void M5(); + Diagnostic(ErrorCode.ERR_PartialMethodWithExtendedModMustHaveAccessMods, "M4").WithArguments("I1.M4()").WithLocation(15, 25), + // (15,25): error CS8798: Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. + // sealed partial void M4() {} + Diagnostic(ErrorCode.ERR_PartialMethodExtendedModDifference, "M4").WithLocation(15, 25), + // (16,27): error CS0750: A partial method cannot have the 'abstract' modifier + // abstract partial void M5(); Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "M5").WithLocation(16, 27), // (16,27): error CS0756: A partial method may not have multiple defining declarations - // abstract partial void M5(); + // abstract partial void M5(); Diagnostic(ErrorCode.ERR_PartialMethodOnlyOneLatent, "M5").WithLocation(16, 27), - // (17,26): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers + // (16,27): error CS0111: Type 'I1' already defines a member called 'M5' with the same parameter types + // abstract partial void M5(); + Diagnostic(ErrorCode.ERR_MemberAlreadyExists, "M5").WithArguments("M5", "I1").WithLocation(16, 27), + // (17,26): error CS8796: Partial method 'I1.M6()' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + // virtual partial void M6() {} + Diagnostic(ErrorCode.ERR_PartialMethodWithExtendedModMustHaveAccessMods, "M6").WithArguments("I1.M6()").WithLocation(17, 26), + // (17,26): error CS8798: Both partial method declarations must have identical combinations of 'virtual', 'override', 'sealed', and 'new' modifiers. // virtual partial void M6() {} - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "M6").WithLocation(17, 26), + Diagnostic(ErrorCode.ERR_PartialMethodExtendedModDifference, "M6").WithLocation(17, 26), // (19,21): error CS0754: A partial method may not explicitly implement an interface method // partial void I2.M7() {} Diagnostic(ErrorCode.ERR_PartialMethodNotExplicit, "M7").WithLocation(19, 21), @@ -45774,7 +45789,7 @@ class Test1 : I2 "; var compilation1 = CreateCompilation(source1, options: TestOptions.DebugDll, - parseOptions: TestOptions.Regular, + parseOptions: TestOptions.RegularWithExtendedPartialMethods, targetFramework: TargetFramework.NetStandardLatest); validate(compilation1.SourceModule); @@ -45782,7 +45797,7 @@ class Test1 : I2 // (9,30): error CS0754: A partial method may not explicitly implement an interface method // abstract partial void I1.M1(); Diagnostic(ErrorCode.ERR_PartialMethodNotExplicit, "M1").WithLocation(9, 30), - // (9,30): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers + // (9,30): error CS0750: A partial method cannot have the 'abstract' modifier // abstract partial void I1.M1(); Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "M1").WithLocation(9, 30), // (12,15): error CS0535: 'Test1' does not implement interface member 'I1.M1()' diff --git a/src/Compilers/CSharp/Test/Symbol/Symbols/ExtendedPartialMethodsTests.cs b/src/Compilers/CSharp/Test/Symbol/Symbols/ExtendedPartialMethodsTests.cs new file mode 100644 index 0000000000000..ed6dadc1d769c --- /dev/null +++ b/src/Compilers/CSharp/Test/Symbol/Symbols/ExtendedPartialMethodsTests.cs @@ -0,0 +1,2018 @@ +// 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.Reflection; +using System.Runtime.InteropServices; +using Microsoft.CodeAnalysis.CSharp.Symbols; +using Microsoft.CodeAnalysis.CSharp.Test.Utilities; +using Microsoft.CodeAnalysis.Test.Utilities; +using Xunit; + +namespace Microsoft.CodeAnalysis.CSharp.UnitTests +{ + public class ExtendedPartialMethodsTests : CSharpTestBase + { + [Fact] + public void NonVoidReturnType_LangVersion() + { + const string text = @" +partial class C +{ + internal partial int M1(); + internal partial int M1() => 1; +}"; + var comp = CreateCompilation(text, parseOptions: TestOptions.Regular8); + comp.VerifyDiagnostics( + // (4,26): error CS8652: The feature 'extended partial methods' is currently in Preview and *unsupported*. To use Preview features, use the 'preview' language version. + // internal partial int M1(); + Diagnostic(ErrorCode.ERR_FeatureInPreview, "M1").WithArguments("extended partial methods").WithLocation(4, 26), + // (5,26): error CS8652: The feature 'extended partial methods' is currently in Preview and *unsupported*. To use Preview features, use the 'preview' language version. + // internal partial int M1() => 1; + Diagnostic(ErrorCode.ERR_FeatureInPreview, "M1").WithArguments("extended partial methods").WithLocation(5, 26) + ); + + comp = CreateCompilation(text, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics(); + } + + [Fact] + public void NonVoidReturnType_NoAccessibility() + { + const string text = @" +partial class C +{ + partial int M1(); + partial int M1() => 1; +}"; + var comp = CreateCompilation(text, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (4,17): error CS8794: Partial method 'C.M1()' must have accessibility modifiers because it has a non-void return type. + // partial int M1(); + Diagnostic(ErrorCode.ERR_PartialMethodWithNonVoidReturnMustHaveAccessMods, "M1").WithArguments("C.M1()").WithLocation(4, 17), + // (5,17): error CS8794: Partial method 'C.M1()' must have accessibility modifiers because it has a non-void return type. + // partial int M1() => 1; + Diagnostic(ErrorCode.ERR_PartialMethodWithNonVoidReturnMustHaveAccessMods, "M1").WithArguments("C.M1()").WithLocation(5, 17) + ); + } + + [Fact] + public void NonVoidReturnType_NoImpl() + { + const string text = @" +partial class C +{ + private partial int M1(); +}"; + var comp = CreateCompilation(text, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (4,25): error CS8793: Partial method 'C.M1()' must have an implementation part because it has accessibility modifiers. + // private partial int M1(); + Diagnostic(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, "M1").WithArguments("C.M1()").WithLocation(4, 25) + ); + } + + [Fact] + public void NonVoidReturnType_NoImpl_NoAccessibility() + { + const string text = @" +partial class C +{ + partial int M1(); +}"; + var comp = CreateCompilation(text, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (4,17): error CS8794: Partial method 'C.M1()' must have accessibility modifiers because it has a non-void return type. + // partial int M1(); + Diagnostic(ErrorCode.ERR_PartialMethodWithNonVoidReturnMustHaveAccessMods, "M1").WithArguments("C.M1()").WithLocation(4, 17) + ); + } + + [Fact] + public void NonVoidReturnType_Semantics() + { + const string text1 = @" +partial class C +{ + private partial int M1(); + + public static void Main() + { + System.Console.WriteLine(new C().M1()); + } +}"; + + const string text2 = @" +partial class C +{ + private partial int M1() { return 42; } +} +"; + var verifier = CompileAndVerify(new[] { text1, text2 }, parseOptions: TestOptions.RegularWithExtendedPartialMethods, expectedOutput: "42"); + verifier.VerifyDiagnostics(); + } + + [Fact] + public void OutParam_LangVersion() + { + const string text = @" +partial class C +{ + private partial void M1(out int i); + private partial void M1(out int i) { i = 0; } +}"; + var comp = CreateCompilation(text, parseOptions: TestOptions.Regular8); + comp.VerifyDiagnostics( + // (4,26): error CS8652: The feature 'extended partial methods' is currently in Preview and *unsupported*. To use Preview features, use the 'preview' language version. + // private partial void M1(out int i); + Diagnostic(ErrorCode.ERR_FeatureInPreview, "M1").WithArguments("extended partial methods").WithLocation(4, 26), + // (5,26): error CS8652: The feature 'extended partial methods' is currently in Preview and *unsupported*. To use Preview features, use the 'preview' language version. + // private partial void M1(out int i) { i = 0; } + Diagnostic(ErrorCode.ERR_FeatureInPreview, "M1").WithArguments("extended partial methods").WithLocation(5, 26) + ); + + comp = CreateCompilation(text, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics(); + } + + [Fact] + public void OutParam_NoAccessibility() + { + const string text = @" +partial class C +{ + partial void M1(out int i); + partial void M1(out int i) { i = 0; } +}"; + var comp = CreateCompilation(text, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (4,18): error CS8795: Partial method 'C.M1(out int)' must have accessibility modifiers because it has 'out' parameters. + // partial void M1(out int i); + Diagnostic(ErrorCode.ERR_PartialMethodWithOutParamMustHaveAccessMods, "M1").WithArguments("C.M1(out int)").WithLocation(4, 18), + // (5,18): error CS8795: Partial method 'C.M1(out int)' must have accessibility modifiers because it has 'out' parameters. + // partial void M1(out int i) { i = 0; } + Diagnostic(ErrorCode.ERR_PartialMethodWithOutParamMustHaveAccessMods, "M1").WithArguments("C.M1(out int)").WithLocation(5, 18) + ); + } + + [Fact] + public void OutParam_NoImpl() + { + const string text = @" +partial class C +{ + private partial void M1(out int i); +}"; + var comp = CreateCompilation(text, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (4,26): error CS8793: Partial method 'C.M1(out int)' must have an implementation part because it has accessibility modifiers. + // private partial void M1(out int i); + Diagnostic(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, "M1").WithArguments("C.M1(out int)").WithLocation(4, 26) + ); + } + + [Fact] + public void OutParam_NoImpl_NoAccessibility() + { + const string text = @" +partial class C +{ + partial void M1(out int i); +}"; + var comp = CreateCompilation(text, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (4,18): error CS8795: Partial method 'C.M1(out int)' must have accessibility modifiers because it has 'out' parameters. + // partial void M1(out int i); + Diagnostic(ErrorCode.ERR_PartialMethodWithOutParamMustHaveAccessMods, "M1").WithArguments("C.M1(out int)").WithLocation(4, 18) + ); + } + + [Fact] + public void OutParam_Semantics() + { + const string text1 = @" +partial class C +{ + private partial void M1(out int value); + + public static void Main() + { + new C().M1(out var value); + System.Console.WriteLine(value); + } +}"; + + const string text2 = @" +partial class C +{ + private partial void M1(out int value) { value = 42; } +} +"; + var verifier = CompileAndVerify(new[] { text1, text2 }, parseOptions: TestOptions.RegularWithExtendedPartialMethods, expectedOutput: "42"); + verifier.VerifyDiagnostics(); + } + + [Fact] + public void OutParam_DefiniteAssignment() + { + const string text1 = @" +partial class C +{ + private partial void M1(out int value); + + public static void Main() + { + int i; + new C().M1(out i); + System.Console.Write(i); + } +}"; + + const string text2 = @" +partial class C +{ + private partial void M1(out int value) { value = 42; } +} +"; + var verifier = CompileAndVerify(new[] { text1, text2 }, parseOptions: TestOptions.RegularWithExtendedPartialMethods, expectedOutput: "42"); + verifier.VerifyDiagnostics(); + } + + public static readonly object[][] s_accessMods = new[] + { + new[] { "public" }, + new[] { "internal" }, + new[] { "protected" }, + new[] { "private" }, + new[] { "protected internal" }, + new[] { "private protected" } + }; + + [Theory] + [MemberData(nameof(s_accessMods))] + public void AccessMod_LangVersion(string mod) + { + var text = $@" +partial class C +{{ + {mod} partial void M1(); + {mod} partial void M1() {{ }} +}}"; + var comp = CreateCompilation(text, parseOptions: TestOptions.Regular8); + comp.VerifyDiagnostics( + // (4,28): error CS8652: The feature 'extended partial methods' is currently in Preview and *unsupported*. To use Preview features, use the 'preview' language version. + // {mod} void M1(); + Diagnostic(ErrorCode.ERR_FeatureInPreview, "M1").WithArguments("extended partial methods"), + // (5,28): error CS8652: The feature 'extended partial methods' is currently in Preview and *unsupported*. To use Preview features, use the 'preview' language version. + // {mod} void M1() { } + Diagnostic(ErrorCode.ERR_FeatureInPreview, "M1").WithArguments("extended partial methods") + ); + + comp = CreateCompilation(text, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics(); + } + + [Fact] + public void AccessMod_Mismatch_01() + { + var text = @" +partial class C +{ + public partial void M1(); + internal partial void M1() { } +}"; + var comp = CreateCompilation(text, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (5,28): error CS8797: Both partial method declarations must have equivalent accessibility modifiers. + // internal partial void M1() { } + Diagnostic(ErrorCode.ERR_PartialMethodAccessibilityDifference, "M1").WithLocation(5, 28) + ); + } + + [Fact] + public void AccessMod_Mismatch_02() + { + var text = @" +partial class C +{ + private partial void M1(); + partial void M1() { } +}"; + var comp = CreateCompilation(text, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (5,19): error CS8797: Both partial method declarations must have identical accessibility modifiers. + // partial void M1() { } + Diagnostic(ErrorCode.ERR_PartialMethodAccessibilityDifference, "M1").WithLocation(5, 19) + ); + } + + [Fact] + public void AccessMod_Mismatch_03() + { + var text = @" +partial class C +{ + partial void M1(); + private partial void M1() { } +}"; + var comp = CreateCompilation(text, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (5,27): error CS8797: Both partial method declarations must have identical accessibility modifiers. + // private partial void M1() { } + Diagnostic(ErrorCode.ERR_PartialMethodAccessibilityDifference, "M1").WithLocation(5, 27) + ); + } + + [Theory] + [MemberData(nameof(s_accessMods))] + public void AccessMod_NoImpl(string mod) + { + var text = $@" +partial class C +{{ + {mod} partial void M1(); +}}"; + var comp = CreateCompilation(text, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (4,27): error CS8795: Partial method C.M1() must have an implementation part because it has accessibility modifiers. + // {mod} partial void M1(); + Diagnostic(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, "M1").WithArguments("C.M1()") + ); + } + + [Fact] + public void Static_NoImpl() + { + const string text1 = @" +partial class C +{ + static partial void M1(); +}"; + var comp = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics(); + } + + [Fact] + public void Simple_NoImpl() + { + const string text1 = @" +partial class C +{ + partial void M1(); +}"; + var comp = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics(); + } + + [Fact] + public void Virtual_LangVersion() + { + const string text1 = @" +partial class C +{ + internal virtual partial int M1(); + internal virtual partial int M1() => 1; +}"; + var comp = CreateCompilation(text1, parseOptions: TestOptions.Regular8); + comp.VerifyDiagnostics( + // (4,34): error CS8652: The feature 'extended partial methods' is currently in Preview and *unsupported*. To use Preview features, use the 'preview' language version. + // internal virtual partial int M1(); + Diagnostic(ErrorCode.ERR_FeatureInPreview, "M1").WithArguments("extended partial methods").WithLocation(4, 34), + // (5,34): error CS8652: The feature 'extended partial methods' is currently in Preview and *unsupported*. To use Preview features, use the 'preview' language version. + // internal virtual partial int M1() => 1; + Diagnostic(ErrorCode.ERR_FeatureInPreview, "M1").WithArguments("extended partial methods").WithLocation(5, 34) + ); + + comp = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics(); + } + + [Fact] + public void Virtual_NoAccessibility() + { + const string text1 = @" +partial class C +{ + virtual partial void M1(); + virtual partial void M1() { } +}"; + var comp = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (4,26): error CS8796: Partial method 'C.M1()' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + // virtual partial void M1(); + Diagnostic(ErrorCode.ERR_PartialMethodWithExtendedModMustHaveAccessMods, "M1").WithArguments("C.M1()").WithLocation(4, 26), + // (5,26): error CS8796: Partial method 'C.M1()' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + // virtual partial void M1() { } + Diagnostic(ErrorCode.ERR_PartialMethodWithExtendedModMustHaveAccessMods, "M1").WithArguments("C.M1()").WithLocation(5, 26) + ); + } + + [Fact] + public void Virtual_NoImpl() + { + const string text1 = @" +partial class C +{ + internal virtual partial void M1(); +}"; + var comp = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (4,35): error CS8793: Partial method 'C.M1()' must have an implementation part because it has accessibility modifiers. + // internal virtual partial void M1(); + Diagnostic(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, "M1").WithArguments("C.M1()").WithLocation(4, 35) + ); + } + + [Fact] + public void Virtual_Mismatch_01() + { + const string text1 = @" +partial class C +{ + internal virtual partial void M1(); + internal partial void M1() { } +}"; + var comp = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (5,27): error CS8798: Both partial method declarations must have equal combinations of 'virtual', 'override', 'sealed', or 'new' modifiers. + // internal partial void M1() { } + Diagnostic(ErrorCode.ERR_PartialMethodExtendedModDifference, "M1").WithLocation(5, 27) + ); + } + + [Fact] + public void Virtual_Mismatch_02() + { + const string text1 = @" +partial class C +{ + internal partial void M1(); + internal virtual partial void M1() { } +}"; + var comp = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (5,35): error CS8798: Both partial method declarations must have equal combinations of 'virtual', 'override', 'sealed', or 'new' modifiers. + // internal virtual partial void M1() { } + Diagnostic(ErrorCode.ERR_PartialMethodExtendedModDifference, "M1").WithLocation(5, 35) + ); + } + + [Fact] + public void Virtual_Semantics() + { + const string text1 = @" +using System; + +public partial class C +{ + internal virtual partial int M1(); + internal virtual partial int M1() => 1; +} + +public class D : C +{ + internal override int M1() => 2; + + static void UseC(C c) + { + Console.Write(c.M1()); + } + + public static void Main() + { + UseC(new C()); + UseC(new D()); + } +}"; + CompileAndVerify(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods, expectedOutput: "12").VerifyDiagnostics(); + } + + [Fact] + public void Virtual_AllowNull_01() + { + const string text1 = @" +#nullable enable +using System.Diagnostics.CodeAnalysis; + +partial class C +{ + internal virtual partial void M1([AllowNull] string s1); + internal virtual partial void M1(string s1) { } +} +class D : C +{ + internal override void M1(string s1) // 1 + { + } +}"; + var comp = CreateCompilation(new[] { text1, AllowNullAttributeDefinition }, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (12,28): warning CS8765: Nullability of type of parameter 's1' doesn't match overridden member (possibly because of nullability attributes). + // internal override void M1(string s1) // 1 + Diagnostic(ErrorCode.WRN_TopLevelNullabilityMismatchInParameterTypeOnOverride, "M1").WithArguments("s1").WithLocation(12, 28) + ); + } + + [Fact] + public void Virtual_AllowNull_02() + { + const string text1 = @" +#nullable enable +using System.Diagnostics.CodeAnalysis; + +partial class C +{ + internal virtual partial void M1(string s1); + internal virtual partial void M1([AllowNull] string s1) { } +} +class D : C +{ + internal override void M1(string s1) // 1 + { + } +}"; + var comp = CreateCompilation(new[] { text1, AllowNullAttributeDefinition }, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (12,28): warning CS8765: Nullability of type of parameter 's1' doesn't match overridden member (possibly because of nullability attributes). + // internal override void M1(string s1) // 1 + Diagnostic(ErrorCode.WRN_TopLevelNullabilityMismatchInParameterTypeOnOverride, "M1").WithArguments("s1").WithLocation(12, 28) + ); + } + + [Fact] + public void Virtual_AllowNull_03() + { + const string text1 = @" +#nullable enable +using System.Diagnostics.CodeAnalysis; + +partial class C +{ + internal virtual partial void M1(string s1); + internal virtual partial void M1([AllowNull] string s1) { } +} +class D : C +{ + internal override void M1([AllowNull] string s1) + { + } +}"; + var comp = CreateCompilation(new[] { text1, AllowNullAttributeDefinition }, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics(); + } + + [Fact] + public void Virtual_AllowNull_04() + { + const string text1 = @" +#nullable enable +using System.Diagnostics.CodeAnalysis; + +partial class C +{ + internal virtual partial void M1([AllowNull] string s1); + internal virtual partial void M1(string s1) { } +} +class D : C +{ + internal override void M1([AllowNull] string s1) + { + } +}"; + var comp = CreateCompilation(new[] { text1, AllowNullAttributeDefinition }, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics(); + } + + [Fact] + public void Override_LangVersion() + { + const string text1 = @" +partial class D +{ + public override partial string ToString(); + public override partial string ToString() => ""hello""; +}"; + var comp = CreateCompilation(text1); + comp.VerifyDiagnostics( + // (4,36): error CS8652: The feature 'extended partial methods' is currently in Preview and *unsupported*. To use Preview features, use the 'preview' language version. + // public override partial string ToString(); + Diagnostic(ErrorCode.ERR_FeatureInPreview, "ToString").WithArguments("extended partial methods").WithLocation(4, 36), + // (5,36): error CS8652: The feature 'extended partial methods' is currently in Preview and *unsupported*. To use Preview features, use the 'preview' language version. + // public override partial string ToString() => "hello"; + Diagnostic(ErrorCode.ERR_FeatureInPreview, "ToString").WithArguments("extended partial methods").WithLocation(5, 36) + ); + var method = comp.GetMember("D.ToString"); + Assert.Equal("System.String System.Object.ToString()", method.OverriddenMethod.ToTestDisplayString()); + + comp = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics(); + method = comp.GetMember("D.ToString"); + Assert.Equal("System.String System.Object.ToString()", method.OverriddenMethod.ToTestDisplayString()); + } + + [Fact] + public void Override_WrongAccessiblity() + { + const string text1 = @" +partial class D +{ + internal override partial string ToString(); + internal override partial string ToString() => ""hello""; +}"; + var comp = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (4,38): error CS0507: 'D.ToString()': cannot change access modifiers when overriding 'public' inherited member 'object.ToString()' + // internal override partial string ToString(); + Diagnostic(ErrorCode.ERR_CantChangeAccessOnOverride, "ToString").WithArguments("D.ToString()", "public", "object.ToString()").WithLocation(4, 38)); + var method = comp.GetMember("D.ToString"); + Assert.Equal("System.String System.Object.ToString()", method.OverriddenMethod.ToTestDisplayString()); + } + + [Fact] + public void Override_AbstractBase() + { + const string text1 = @" +abstract class C +{ + internal abstract void M1(); +} + +partial class D : C +{ + internal override partial void M1(); + internal override partial void M1() { } +}"; + var comp = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics(); + + var method = comp.GetMember("D.M1"); + Assert.Equal(comp.GetMember("C.M1"), method.OverriddenMethod); + } + + [Fact] + public void Override_NoAccessibility() + { + const string text1 = @" +class C +{ + internal virtual void M1() { } +} + +partial class D : C +{ + override partial void M1(); + override partial void M1() { } +}"; + var comp = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (9,27): error CS8796: Partial method 'D.M1()' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + // override partial void M1(); + Diagnostic(ErrorCode.ERR_PartialMethodWithExtendedModMustHaveAccessMods, "M1").WithArguments("D.M1()").WithLocation(9, 27), + // (9,27): error CS0507: 'D.M1()': cannot change access modifiers when overriding 'internal' inherited member 'C.M1()' + // override partial void M1(); + Diagnostic(ErrorCode.ERR_CantChangeAccessOnOverride, "M1").WithArguments("D.M1()", "internal", "C.M1()").WithLocation(9, 27), + // (10,27): error CS8796: Partial method 'D.M1()' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + // override partial void M1() { } + Diagnostic(ErrorCode.ERR_PartialMethodWithExtendedModMustHaveAccessMods, "M1").WithArguments("D.M1()").WithLocation(10, 27) + ); + var method = comp.GetMember("D.M1"); + Assert.Equal(comp.GetMember("C.M1"), method.OverriddenMethod); + } + + [Fact] + public void Override_Mismatch_01() + { + const string text1 = @" +class C +{ + internal virtual void M1() { } +} +partial class D : C +{ + internal override partial void M1(); + internal partial void M1() { } +}"; + var comp = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (9,27): error CS8798: Both partial method declarations must have equal combinations of 'virtual', 'override', 'sealed', or 'new' modifiers. + // internal partial void M1() { } + Diagnostic(ErrorCode.ERR_PartialMethodExtendedModDifference, "M1").WithLocation(9, 27) + ); + } + + [Fact] + public void Override_Mismatch_02() + { + const string text1 = @" +class C +{ + internal virtual void M1() { } +} +partial class D : C +{ + internal partial void M1(); + internal override partial void M1() { } +}"; + var comp = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (8,27): warning CS0114: 'D.M1()' hides inherited member 'C.M1()'. To make the current member override that implementation, add the override keyword. Otherwise add the new keyword. + // internal partial void M1(); + Diagnostic(ErrorCode.WRN_NewOrOverrideExpected, "M1").WithArguments("D.M1()", "C.M1()").WithLocation(8, 27), + // (9,36): error CS8798: Both partial method declarations must have equal combinations of 'virtual', 'override', 'sealed', or 'new' modifiers. + // internal override partial void M1() { } + Diagnostic(ErrorCode.ERR_PartialMethodExtendedModDifference, "M1").WithLocation(9, 36) + ); + } + + [Fact] + public void Override_AllowNull_01() + { + const string text1 = @" +#nullable enable +using System.Diagnostics.CodeAnalysis; + +class C +{ + internal virtual void M1([AllowNull] string s) { } +} +partial class D : C +{ + internal override partial void M1(string s1); // 1 + internal override partial void M1(string s1) { } +}"; + var comp = CreateCompilation(new[] { text1, AllowNullAttributeDefinition }, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (11,36): warning CS8765: Nullability of type of parameter 's1' doesn't match overridden member (possibly because of nullability attributes). + // internal override partial void M1(string s1); // 1 + Diagnostic(ErrorCode.WRN_TopLevelNullabilityMismatchInParameterTypeOnOverride, "M1").WithArguments("s1").WithLocation(11, 36) + ); + } + + [Fact] + public void Override_AllowNull_02() + { + const string text1 = @" +#nullable enable +using System.Diagnostics.CodeAnalysis; + +class C +{ + internal virtual void M1([AllowNull] string s1, [AllowNull] string s2) { } +} +partial class D : C +{ + internal override partial void M1([AllowNull] string s1, string s2); + internal override partial void M1(string s1, [AllowNull] string s2) + { + s1.ToString(); // 1 + s2.ToString(); // 2 + } +}"; + var comp = CreateCompilation(new[] { text1, AllowNullAttributeDefinition }, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (14,9): warning CS8602: Dereference of a possibly null reference. + // s1.ToString(); // 1 + Diagnostic(ErrorCode.WRN_NullReferenceReceiver, "s1").WithLocation(14, 9), + // (15,9): warning CS8602: Dereference of a possibly null reference. + // s2.ToString(); // 2 + Diagnostic(ErrorCode.WRN_NullReferenceReceiver, "s2").WithLocation(15, 9)); + } + + [Fact] + public void Sealed_LangVersion() + { + const string text1 = @" +class C +{ + internal virtual void M1() { } +} +partial class D : C +{ + internal sealed override partial void M1(); + internal sealed override partial void M1() { } +}"; + var comp = CreateCompilation(text1); + comp.VerifyDiagnostics( + // (8,43): error CS8652: The feature 'extended partial methods' is currently in Preview and *unsupported*. To use Preview features, use the 'preview' language version. + // internal sealed override partial void M1(); + Diagnostic(ErrorCode.ERR_FeatureInPreview, "M1").WithArguments("extended partial methods").WithLocation(8, 43), + // (9,43): error CS8652: The feature 'extended partial methods' is currently in Preview and *unsupported*. To use Preview features, use the 'preview' language version. + // internal sealed override partial void M1() { } + Diagnostic(ErrorCode.ERR_FeatureInPreview, "M1").WithArguments("extended partial methods").WithLocation(9, 43) + ); + comp = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics(); + } + + [Fact] + public void Sealed_NoAccessibility() + { + const string text1 = @" +class C +{ + internal virtual void M1() { } +} +partial class D : C +{ + sealed override partial void M1(); + sealed override partial void M1() { } +}"; + var comp = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (8,34): error CS8796: Partial method 'D.M1()' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + // sealed override partial void M1(); + Diagnostic(ErrorCode.ERR_PartialMethodWithExtendedModMustHaveAccessMods, "M1").WithArguments("D.M1()").WithLocation(8, 34), + // (8,34): error CS0507: 'D.M1()': cannot change access modifiers when overriding 'internal' inherited member 'C.M1()' + // sealed override partial void M1(); + Diagnostic(ErrorCode.ERR_CantChangeAccessOnOverride, "M1").WithArguments("D.M1()", "internal", "C.M1()").WithLocation(8, 34), + // (9,34): error CS8796: Partial method 'D.M1()' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + // sealed override partial void M1() { } + Diagnostic(ErrorCode.ERR_PartialMethodWithExtendedModMustHaveAccessMods, "M1").WithArguments("D.M1()").WithLocation(9, 34) + ); + } + + [Fact] + public void Sealed_Mismatch_01() + { + const string text1 = @" +class C +{ + internal virtual void M1() { } +} +partial class D : C +{ + internal sealed override partial void M1(); + internal override partial void M1() { } +}"; + var comp = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (9,36): error CS8798: Both partial method declarations must have equal combinations of 'virtual', 'override', 'sealed', or 'new' modifiers. + // internal override partial void M1() { } + Diagnostic(ErrorCode.ERR_PartialMethodExtendedModDifference, "M1").WithLocation(9, 36) + ); + } + + [Fact] + public void Sealed_Mismatch_02() + { + const string text1 = @" +class C +{ + internal virtual void M1() { } +} +partial class D : C +{ + internal override partial void M1(); + internal sealed override partial void M1() { } +}"; + var comp = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (9,43): error CS8798: Both partial method declarations must have equal combinations of 'virtual', 'override', 'sealed', or 'new' modifiers. + // internal sealed override partial void M1() { } + Diagnostic(ErrorCode.ERR_PartialMethodExtendedModDifference, "M1").WithLocation(9, 43) + ); + } + + [Fact] + public void SealedOverride_Reordered() + { + const string text1 = @" +class C +{ + internal virtual void M1() { } +} +partial class D : C +{ + internal override sealed partial void M1(); + internal sealed override partial void M1() { } +}"; + var comp = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics(); + } + + [Fact] + public void Extern_LangVersion() + { + const string text1 = @" +using System.Runtime.InteropServices; + +partial class C +{ + internal static partial void M1(); + + [DllImport(""something.dll"")] + internal static extern partial void M1(); +}"; + var comp = CreateCompilation(text1); + comp.VerifyDiagnostics( + // (6,34): error CS8652: The feature 'extended partial methods' is currently in Preview and *unsupported*. To use Preview features, use the 'preview' language version. + // internal static partial void M1(); + Diagnostic(ErrorCode.ERR_FeatureInPreview, "M1").WithArguments("extended partial methods").WithLocation(6, 34), + // (9,41): error CS8652: The feature 'extended partial methods' is currently in Preview and *unsupported*. To use Preview features, use the 'preview' language version. + // internal static extern partial void M1(); + Diagnostic(ErrorCode.ERR_FeatureInPreview, "M1").WithArguments("extended partial methods").WithLocation(9, 41)); + + comp = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics(); + } + + [Fact] + public void Extern_NoAccessibility() + { + const string text1 = @" +using System.Runtime.InteropServices; + +partial class C +{ + static partial void M1(); + + [DllImport(""something.dll"")] + static extern partial void M1(); +}"; + var comp = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (9,32): error CS8796: Partial method 'C.M1()' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + // static extern partial void M1(); + Diagnostic(ErrorCode.ERR_PartialMethodWithExtendedModMustHaveAccessMods, "M1").WithArguments("C.M1()").WithLocation(9, 32) + ); + } + + [Fact] + public void Extern_Symbols() + { + const string text1 = @" +using System.Runtime.InteropServices; + +public partial class C +{ + public static partial void M1(); + + [DllImport(""something.dll"")] + public static extern partial void M1(); + + public static void M2() { M1(); } +}"; + + const string text2 = @" +using System.Runtime.InteropServices; + +public partial class C +{ + [DllImport(""something.dll"")] + public static partial void M1(); + + public static extern partial void M1(); + + public static void M2() { M1(); } +}"; + const string expectedIL = @" +{ + // Code size 6 (0x6) + .maxstack 0 + IL_0000: call ""void C.M1()"" + IL_0005: ret +}"; + + var verifier = CompileAndVerify( + text1, + parseOptions: TestOptions.RegularWithExtendedPartialMethods, + sourceSymbolValidator: validator, + symbolValidator: validator); + verifier.VerifyDiagnostics(); + verifier.VerifyIL("C.M2", expectedIL); + + verifier = CompileAndVerify( + text2, + parseOptions: TestOptions.RegularWithExtendedPartialMethods, + sourceSymbolValidator: validator, + symbolValidator: validator); + verifier.VerifyDiagnostics(); + verifier.VerifyIL("C.M2", expectedIL); + + static void validator(ModuleSymbol module) + { + var type = module.ContainingAssembly.GetTypeByMetadataName("C"); + var method = type.GetMember("M1"); + + Assert.True(method.IsExtern); + + var importData = method.GetDllImportData(); + Assert.NotNull(importData); + Assert.Equal("something.dll", importData.ModuleName); + Assert.Equal("M1", importData.EntryPointName); + Assert.Equal(CharSet.None, importData.CharacterSet); + Assert.False(importData.SetLastError); + Assert.False(importData.ExactSpelling); + Assert.Equal(MethodImplAttributes.PreserveSig, method.ImplementationAttributes); + Assert.Equal(CallingConvention.Winapi, importData.CallingConvention); + Assert.Null(importData.BestFitMapping); + Assert.Null(importData.ThrowOnUnmappableCharacter); + } + } + + [Fact] + public void Async_01() + { + const string text = @" +partial class C +{ + partial void M1(); + async partial void M1() { } +} +"; + var comp = CreateCompilation(text); + comp.VerifyDiagnostics( + // (5,24): warning CS1998: This async method lacks 'await' operators and will run synchronously. Consider using the 'await' operator to await non-blocking API calls, or 'await Task.Run(...)' to do CPU-bound work on a background thread. + // async partial void M1() { } + Diagnostic(ErrorCode.WRN_AsyncLacksAwaits, "M1").WithLocation(5, 24)); + + var method = (MethodSymbol)comp.GetMembers("C.M1")[0]; + Assert.True(method.IsPartialDefinition()); + // PROTOTYPE: it feels like both IsAsync/IsExtern should be shared between + // definition+implementation, or neither should. + // Currently IsExtern is shared but IsAsync is not. + Assert.False(method.IsAsync); + Assert.True(method.PartialImplementationPart.IsAsync); + } + + [Fact] + public void Async_02() + { + const string text = @" +using System.Threading.Tasks; + +partial class C +{ + private partial Task M1(); + private async partial Task M1() { } +} +"; + var comp = CreateCompilation(text, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (7,32): warning CS1998: This async method lacks 'await' operators and will run synchronously. Consider using the 'await' operator to await non-blocking API calls, or 'await Task.Run(...)' to do CPU-bound work on a background thread. + // private async partial Task M1() { } + Diagnostic(ErrorCode.WRN_AsyncLacksAwaits, "M1").WithLocation(7, 32)); + + var method = (MethodSymbol)comp.GetMembers("C.M1")[0]; + Assert.True(method.IsPartialDefinition()); + // PROTOTYPE: it feels like both IsAsync/IsExtern should be shared between + // definition+implementation, or neither should. + // Currently IsExtern is shared but IsAsync is not. + Assert.False(method.IsAsync); + Assert.True(method.PartialImplementationPart.IsAsync); + } + + [Fact] + public void Async_03() + { + const string text = @" +using System.Threading.Tasks; +using System; + +partial class C +{ + private static async Task CompletedTask() { } + + private static partial Task M1(); + private static async partial Task M1() { await CompletedTask(); return 1; } + + public static async Task Main() + { + Console.Write(await M1()); + } +} +"; + var verifier = CompileAndVerify(text, parseOptions: TestOptions.RegularWithExtendedPartialMethods, expectedOutput: "1"); + verifier.VerifyDiagnostics( + // (7,31): warning CS1998: This async method lacks 'await' operators and will run synchronously. Consider using the 'await' operator to await non-blocking API calls, or 'await Task.Run(...)' to do CPU-bound work on a background thread. + // private static async Task CompletedTask() { } + Diagnostic(ErrorCode.WRN_AsyncLacksAwaits, "CompletedTask").WithLocation(7, 31)); + + var method = (MethodSymbol)verifier.Compilation.GetMembers("C.M1")[0]; + Assert.True(method.IsPartialDefinition()); + // PROTOTYPE: it feels like both IsAsync/IsExtern should be shared between + // definition+implementation, or neither should. + // Currently IsExtern is shared but IsAsync is not. + Assert.False(method.IsAsync); + Assert.True(method.PartialImplementationPart.IsAsync); + } + + [Fact] + public void Async_04() + { + const string text = @" +using System.Threading.Tasks; + +partial class C +{ + internal async partial Task M(); +} +"; + + var comp = CreateCompilation(text, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (6,33): error CS8793: Partial method 'C.M()' must have an implementation part because it has accessibility modifiers. + // internal async partial Task M(); + Diagnostic(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, "M").WithArguments("C.M()").WithLocation(6, 33), + // (6,33): error CS1994: The 'async' modifier can only be used in methods that have a body. + // internal async partial Task M(); + Diagnostic(ErrorCode.ERR_BadAsyncLacksBody, "M").WithLocation(6, 33)); + } + + [Fact] + public void Async_05() + { + const string text = @" +using System.Threading.Tasks; + +partial class C +{ + internal async partial Task M(); + internal async partial Task M() + { + await Task.Yield(); + } +} +"; + + var comp = CreateCompilation(text, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (6,33): error CS1994: The 'async' modifier can only be used in methods that have a body. + // internal async partial Task M(); + Diagnostic(ErrorCode.ERR_BadAsyncLacksBody, "M").WithLocation(6, 33)); + } + + [Fact] + public void Async_06() + { + const string text = @" +using System.Threading.Tasks; + +partial class C +{ + internal async partial Task M(); + internal partial Task M() + { + await Task.Yield(); + } +} +"; + + var comp = CreateCompilation(text, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (6,33): error CS1994: The 'async' modifier can only be used in methods that have a body. + // internal async partial Task M(); + Diagnostic(ErrorCode.ERR_BadAsyncLacksBody, "M").WithLocation(6, 33), + // (7,27): error CS0161: 'C.M()': not all code paths return a value + // internal partial Task M() + Diagnostic(ErrorCode.ERR_ReturnExpected, "M").WithArguments("C.M()").WithLocation(7, 27), + // (9,9): error CS4032: The 'await' operator can only be used within an async method. Consider marking this method with the 'async' modifier and changing its return type to 'Task'. + // await Task.Yield(); + Diagnostic(ErrorCode.ERR_BadAwaitWithoutAsyncMethod, "await Task.Yield()").WithArguments("System.Threading.Tasks.Task").WithLocation(9, 9)); + } + + [Fact] + public void New_LangVersion() + { + const string text1 = @" +class C +{ + internal void M1() { } +} + +partial class D : C +{ + internal new partial void M1(); + internal new partial void M1() { } +}"; + var comp = CreateCompilation(text1); + comp.VerifyDiagnostics( + // (9,31): error CS8652: The feature 'extended partial methods' is currently in Preview and *unsupported*. To use Preview features, use the 'preview' language version. + // internal new partial void M1(); + Diagnostic(ErrorCode.ERR_FeatureInPreview, "M1").WithArguments("extended partial methods").WithLocation(9, 31), + // (10,31): error CS8652: The feature 'extended partial methods' is currently in Preview and *unsupported*. To use Preview features, use the 'preview' language version. + // internal new partial void M1() { } + Diagnostic(ErrorCode.ERR_FeatureInPreview, "M1").WithArguments("extended partial methods").WithLocation(10, 31)); + + comp = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics(); + } + + [Fact] + public void New_NoImpl() + { + const string text1 = @" +class C +{ + internal void M1() { } +} + +partial class D : C +{ + internal new partial void M1(); +}"; + var comp = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (9,31): error CS8793: Partial method 'D.M1()' must have an implementation part because it has accessibility modifiers. + // internal new partial void M1(); + Diagnostic(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, "M1").WithArguments("D.M1()").WithLocation(9, 31) + ); + } + + [Fact] + public void New_NoAccessibility() + { + const string text1 = @" +class C +{ + internal void M1() { } +} + +partial class D : C +{ + new partial void M1(); + new partial void M1() { } +}"; + var comp = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (9,22): error CS8796: Partial method 'D.M1()' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + // new partial void M1(); + Diagnostic(ErrorCode.ERR_PartialMethodWithExtendedModMustHaveAccessMods, "M1").WithArguments("D.M1()").WithLocation(9, 22), + // (10,22): error CS8796: Partial method 'D.M1()' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + // new partial void M1() { } + Diagnostic(ErrorCode.ERR_PartialMethodWithExtendedModMustHaveAccessMods, "M1").WithArguments("D.M1()").WithLocation(10, 22) + ); + } + + [Fact] + public void New_Mismatch_01() + { + const string text1 = @" +class C +{ + internal void M1() { } +} + +partial class D : C +{ + internal new partial void M1(); + internal partial void M1() { } +}"; + var comp = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (10,27): error CS8798: Both partial method declarations must have equal combinations of 'virtual', 'override', 'sealed', or 'new' modifiers. + // internal partial void M1() { } + Diagnostic(ErrorCode.ERR_PartialMethodExtendedModDifference, "M1").WithLocation(10, 27) + ); + } + + [Fact] + public void New_Mismatch_02() + { + const string text1 = @" +class C +{ + internal void M1() { } +} + +partial class D : C +{ + internal partial void M1(); + internal new partial void M1() { } +}"; + var comp = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (9,27): warning CS0108: 'D.M1()' hides inherited member 'C.M1()'. Use the new keyword if hiding was intended. + // internal partial void M1(); + Diagnostic(ErrorCode.WRN_NewRequired, "M1").WithArguments("D.M1()", "C.M1()").WithLocation(9, 27), + // (10,31): error CS8798: Both partial method declarations must have equal combinations of 'virtual', 'override', 'sealed', or 'new' modifiers. + // internal new partial void M1() { } + Diagnostic(ErrorCode.ERR_PartialMethodExtendedModDifference, "M1").WithLocation(10, 31) + ); + } + + [Fact] + public void InterfaceImpl_01() + { + const string text = @" +interface I +{ + void M(); +} + +partial class C +{ + public partial void M(); +} + +partial class C : I +{ + public partial void M() + { + System.Console.Write(1); + } + + static void Main() + { + I i = new C(); + i.M(); + } +} +"; + var verifier = CompileAndVerify( + text, + parseOptions: TestOptions.RegularWithExtendedPartialMethods, + options: TestOptions.DebugExe, + expectedOutput: "1"); + verifier.VerifyDiagnostics(); + } + + [Fact] + public void InterfaceImpl_02() + { + const string text = @" +interface I +{ + void M(); +} + +partial class C : I +{ + public partial void M(); +} + +partial class C +{ + public partial void M() + { + System.Console.Write(1); + } + + static void Main() + { + I i = new C(); + i.M(); + } +} +"; + var verifier = CompileAndVerify( + text, + parseOptions: TestOptions.RegularWithExtendedPartialMethods, + options: TestOptions.DebugExe, + expectedOutput: "1"); + verifier.VerifyDiagnostics(); + } + + [Fact] + public void InterfaceImpl_03() + { + const string text = @" +#nullable enable + +using System.Diagnostics.CodeAnalysis; + +interface I +{ + void M([AllowNull] string s1); +} + +partial class C : I +{ + public partial void M(string s1); // 1 +} + +partial class C +{ + public partial void M(string s1) + { + s1.ToString(); + } +} +"; + var comp = CreateCompilation(new[] { text, AllowNullAttributeDefinition }, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (13,25): warning CS8767: Nullability of reference types in type of parameter 's1' of 'void C.M(string s1)' doesn't match implicitly implemented member 'void I.M(string s1)' (possibly because of nullability attributes). + // public partial void M(string s1); + Diagnostic(ErrorCode.WRN_TopLevelNullabilityMismatchInParameterTypeOnImplicitImplementation, "M").WithArguments("s1", "void C.M(string s1)", "void I.M(string s1)").WithLocation(13, 25)); + } + + [Fact] + public void InterfaceImpl_04() + { + const string text = @" +#nullable enable + +using System.Diagnostics.CodeAnalysis; + +interface I +{ + void M([AllowNull] string s1, [AllowNull] string s2); +} + +partial class C : I +{ + public partial void M([AllowNull] string s1, string s2); +} + +partial class C +{ + public partial void M(string s1, [AllowNull] string s2) + { + s1.ToString(); // 1 + s2.ToString(); // 2 + } +} +"; + var comp = CreateCompilation(new[] { text, AllowNullAttributeDefinition }, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (20,9): warning CS8602: Dereference of a possibly null reference. + // s1.ToString(); // 1 + Diagnostic(ErrorCode.WRN_NullReferenceReceiver, "s1").WithLocation(20, 9), + // (21,9): warning CS8602: Dereference of a possibly null reference. + // s2.ToString(); // 2 + Diagnostic(ErrorCode.WRN_NullReferenceReceiver, "s2").WithLocation(21, 9)); + } + + [Fact] + public void InterfaceImpl_05() + { + const string text = @" +#nullable enable + +using System.Diagnostics.CodeAnalysis; + +interface I +{ + void M([AllowNull] string s1); +} + +partial class C : I +{ + public partial void M([AllowNull] string s1); +} + +partial class C +{ + public partial void M([AllowNull] string s1) // 1 + { + s1.ToString(); // 2 + } +} +"; + var comp = CreateCompilation(new[] { text, AllowNullAttributeDefinition }, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (13,28): error CS0579: Duplicate 'AllowNull' attribute + // public partial void M([AllowNull] string s1); + Diagnostic(ErrorCode.ERR_DuplicateAttribute, "AllowNull").WithArguments("AllowNull").WithLocation(13, 28), + // (20,9): warning CS8602: Dereference of a possibly null reference. + // s1.ToString(); // 2 + Diagnostic(ErrorCode.WRN_NullReferenceReceiver, "s1").WithLocation(20, 9)); + } + + [Fact] + public void ExplicitInterfaceImpl_01() + { + const string text = @" +interface I +{ + void M(); +} + +partial class C : I +{ + partial void I.M(); // 1 + partial void I.M() { } // 2 +} +"; + var comp = CreateCompilation(text); + comp.VerifyDiagnostics( + // (9,20): error CS0754: A partial method may not explicitly implement an interface method + // partial void I.M(); // 1 + Diagnostic(ErrorCode.ERR_PartialMethodNotExplicit, "M").WithLocation(9, 20), + // (10,20): error CS0754: A partial method may not explicitly implement an interface method + // partial void I.M() { } // 2 + Diagnostic(ErrorCode.ERR_PartialMethodNotExplicit, "M").WithLocation(10, 20)); + } + + [Fact] + public void ReturnAttribute_01() + { + const string text = @" +class Attr1 : System.Attribute { } +class Attr2 : System.Attribute { } + +public partial class C +{ + [return: Attr1] + public partial string M(); + + [return: Attr2] + public partial string M() => ""hello""; +} +"; + var expectedAttributeNames = new[] { "Attr1", "Attr2" }; + + var comp = CreateCompilation(text, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics(); + + CompileAndVerify(comp, symbolValidator: validator); + + var definitionPart = comp.GetMember("C.M"); + Assert.True(definitionPart.IsPartialDefinition()); + Assert.Equal(expectedAttributeNames, GetAttributeNames(definitionPart.GetReturnTypeAttributes())); + + var implementationPart = definitionPart.PartialImplementationPart; + Assert.NotNull(implementationPart); + Assert.True(implementationPart.IsPartialImplementation()); + Assert.Equal(expectedAttributeNames, GetAttributeNames(implementationPart.GetReturnTypeAttributes())); + + void validator(ModuleSymbol module) + { + var method = module.ContainingAssembly + .GetTypeByMetadataName("C") + .GetMember("M"); + + Assert.Equal(expectedAttributeNames, GetAttributeNames(method.GetReturnTypeAttributes())); + } + } + + [Fact] + public void ConflictingOverloads_RefOut_01() + { + const string text = @" +partial class Program +{ + internal static partial void M(ref object o); + internal static partial void M(out object o); + internal static partial void M(out object o) { o = null; } +} +"; + var comp = CreateCompilation(text, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (4,34): error CS8793: Partial method 'Program.M(ref object)' must have an implementation part because it has accessibility modifiers. + // internal static partial void M(ref object o); + Diagnostic(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, "M").WithArguments("Program.M(ref object)").WithLocation(4, 34), + // (5,34): error CS0663: 'Program' cannot define an overloaded method that differs only on parameter modifiers 'out' and 'ref' + // internal static partial void M(out object o); + Diagnostic(ErrorCode.ERR_OverloadRefKind, "M").WithArguments("Program", "method", "out", "ref").WithLocation(5, 34)); + } + + [Fact] + public void ConflictingOverloads_RefOut_02() + { + const string text = @" +partial class Program +{ + internal static partial void M(ref object o); + internal static partial void M(ref object o) { } + internal static partial void M(out object o); + internal static partial void M(out object o) { o = null; } +} +"; + var comp = CreateCompilation(text, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (6,34): error CS0663: 'Program' cannot define an overloaded method that differs only on parameter modifiers 'out' and 'ref' + // internal static partial void M(out object o); + Diagnostic(ErrorCode.ERR_OverloadRefKind, "M").WithArguments("Program", "method", "out", "ref").WithLocation(6, 34)); + } + + [Fact] + public void RefReturn() + { + const string text = @" +using System; + +partial class Program +{ + static int i = 1; + private static partial ref int M(); + private static partial ref int M() => ref i; + + static void Main() + { + ref int local = ref M(); + Console.Write(local); + i++; + Console.Write(local); + } +} +"; + var verifier = CompileAndVerify( + text, + parseOptions: TestOptions.RegularWithExtendedPartialMethods, + expectedOutput: "12"); + verifier.VerifyDiagnostics(); + } + + [Fact] + public void PrivateProtectedAccessibility_01() + { + const string text1 = @" +using System; + +public partial class Base +{ + private protected static partial void M1(); + private protected static partial void M1() { Console.Write(1); } +}"; + + const string text2 = @" +class Derived : Base +{ + static void Main() + { + M1(); + } +}"; + var verifier = CompileAndVerify( + new[] { text1, text2 }, + parseOptions: TestOptions.RegularWithExtendedPartialMethods, + expectedOutput: "1"); + verifier.VerifyDiagnostics(); + + var comp1 = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + verify(comp1.ToMetadataReference()); + verify(comp1.EmitToImageReference()); + + void verify(MetadataReference reference) + { + var comp2 = CreateCompilation( + text2, + references: new[] { reference }, + parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp2.VerifyDiagnostics( + // (6,9): error CS0122: 'Base.M1()' is inaccessible due to its protection level + // M1(); + Diagnostic(ErrorCode.ERR_BadAccess, "M1").WithArguments("Base.M1()").WithLocation(6, 9)); + } + } + + [Fact] + public void PrivateProtectedAccessibility_02() + { + const string text1 = @" +using System; + +partial class C +{ + private protected static partial void M1(); + private protected static partial void M1() { Console.Write(1); } +}"; + + const string text2 = @" +class Program +{ + static void Main() + { + C.M1(); // 1 + } +}"; + var comp = CreateCompilation(new[] { text1, text2 }, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (6,11): error CS0122: 'C.M1()' is inaccessible due to its protection level + // C.M1(); // 1 + Diagnostic(ErrorCode.ERR_BadAccess, "M1").WithArguments("C.M1()").WithLocation(6, 11)); + } + + [Fact] + public void ProtectedAccessibility_01() + { + const string text1 = @" +using System; + +partial class Base +{ + protected static partial void M1(); + protected static partial void M1() { Console.Write(1); } +}"; + + const string text2 = @" +class Derived : Base +{ + static void Main() + { + M1(); + } +}"; + var verifier = CompileAndVerify( + new[] { text1, text2 }, + parseOptions: TestOptions.RegularWithExtendedPartialMethods, + expectedOutput: "1"); + verifier.VerifyDiagnostics(); + } + + [Fact] + public void ProtectedAccessibility_02() + { + const string text1 = @" +using System; + +partial class C +{ + protected static partial void M1(); + protected static partial void M1() { Console.Write(1); } +}"; + + const string text2 = @" +class Program +{ + static void Main() + { + C.M1(); // 1 + } +}"; + var comp = CreateCompilation(new[] { text1, text2 }, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp.VerifyDiagnostics( + // (6,11): error CS0122: 'C.M1()' is inaccessible due to its protection level + // C.M1(); // 1 + Diagnostic(ErrorCode.ERR_BadAccess, "M1").WithArguments("C.M1()").WithLocation(6, 11)); + } + + [Fact] + public void InternalAccessibility_01() + { + const string text1 = @" +using System; + +internal partial class C +{ + internal static partial void M1(); + internal static partial void M1() { Console.Write(1); } +}"; + + const string text2 = @" +class Program +{ + static void Main() + { + C.M1(); + } +}"; + var verifier = CompileAndVerify( + new[] { text1, text2 }, + parseOptions: TestOptions.RegularWithExtendedPartialMethods, + expectedOutput: "1"); + verifier.VerifyDiagnostics(); + } + + [Fact] + public void InternalAccessibility_02() + { + const string text1 = @" +using System; + +internal partial class C +{ + internal static partial void M1(); + internal static partial void M1() { Console.Write(1); } +}"; + + const string text2 = @" +class Program +{ + static void Main() + { + C.M1(); // 1 + } +}"; + var comp1 = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp1.VerifyDiagnostics(); + verify(comp1.ToMetadataReference()); + verify(comp1.EmitToImageReference()); + + void verify(MetadataReference reference) + { + var comp2 = CreateCompilation( + text2, + references: new[] { comp1.ToMetadataReference() }, + parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp2.VerifyDiagnostics( + // (6,9): error CS0122: 'C' is inaccessible due to its protection level + // C.M1(); // 1 + Diagnostic(ErrorCode.ERR_BadAccess, "C").WithArguments("C").WithLocation(6, 9)); + } + } + + [Fact] + public void ProtectedInternalAccessibility_01() + { + const string text1 = @" +using System; + +public partial class C +{ + protected internal static partial void M1(); + protected internal static partial void M1() { Console.Write(1); } +}"; + + const string text2 = @" +class Program +{ + static void Main() + { + C.M1(); + } +}"; + var verifier = CompileAndVerify( + new[] { text1, text2 }, + parseOptions: TestOptions.RegularWithExtendedPartialMethods, + expectedOutput: "1"); + verifier.VerifyDiagnostics(); + + var comp1 = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + verify(comp1.ToMetadataReference()); + verify(comp1.EmitToImageReference()); + + void verify(MetadataReference reference) + { + var comp2 = CreateCompilation( + text2, + references: new[] { reference }, + parseOptions: TestOptions.RegularWithExtendedPartialMethods); + comp2.VerifyDiagnostics( + // (6,11): error CS0122: 'C.M1()' is inaccessible due to its protection level + // C.M1(); + Diagnostic(ErrorCode.ERR_BadAccess, "M1").WithArguments("C.M1()").WithLocation(6, 11)); + } + } + + [Fact] + public void ProtectedInternalAccessibility_02() + { + const string text1 = @" +using System; + +public partial class Base +{ + protected internal static partial void M1(); + protected internal static partial void M1() { Console.Write(1); } +}"; + + const string text2 = @" +class Derived : Base +{ + static void Main() + { + M1(); + } +}"; + var verifier = CompileAndVerify( + new[] { text1, text2 }, + parseOptions: TestOptions.RegularWithExtendedPartialMethods, + expectedOutput: "1"); + verifier.VerifyDiagnostics(); + + var comp1 = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + verify(comp1.ToMetadataReference()); + verify(comp1.EmitToImageReference()); + + void verify(MetadataReference reference) + { + var verifier = CompileAndVerify( + text2, + references: new[] { reference }, + parseOptions: TestOptions.RegularWithExtendedPartialMethods, + expectedOutput: "1"); + verifier.VerifyDiagnostics(); + } + } + + [Fact] + public void PublicAccessibility() + { + const string text1 = @" +using System; + +public partial class C +{ + public static partial void M1(); + public static partial void M1() { Console.Write(1); } +}"; + + const string text2 = @" +class Program +{ + static void Main() + { + C.M1(); + } +}"; + var verifier = CompileAndVerify( + new[] { text1, text2 }, + parseOptions: TestOptions.RegularWithExtendedPartialMethods, + expectedOutput: "1"); + verifier.VerifyDiagnostics(); + + var comp1 = CreateCompilation(text1, parseOptions: TestOptions.RegularWithExtendedPartialMethods); + verify(comp1.ToMetadataReference()); + verify(comp1.EmitToImageReference()); + + void verify(MetadataReference reference) + { + var verifier = CompileAndVerify( + text2, + references: new[] { reference }, + parseOptions: TestOptions.RegularWithExtendedPartialMethods, + expectedOutput: "1"); + verifier.VerifyDiagnostics(); + } + } + + [Fact] + public void EntryPoint_01() + { + const string text1 = @" +using System.Threading.Tasks; + +public partial class C +{ + public static partial Task Main(); +}"; + var comp1 = CreateCompilation( + text1, + parseOptions: TestOptions.RegularWithExtendedPartialMethods, + options: TestOptions.DebugExe); + comp1.VerifyDiagnostics( + // error CS5001: Program does not contain a static 'Main' method suitable for an entry point + Diagnostic(ErrorCode.ERR_NoEntryPoint).WithLocation(1, 1), + // (6,32): error CS8793: Partial method 'C.Main()' must have an implementation part because it has accessibility modifiers. + // public static partial Task Main(); + Diagnostic(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, "Main").WithArguments("C.Main()").WithLocation(6, 32)); + } + + [Fact] + public void EntryPoint_02() + { + const string text1 = @" +using System.Threading.Tasks; +using System; + +public partial class C +{ + public static partial Task Main(); + public static partial async Task Main() + { + Console.Write(1); + } +}"; + var verifier = CompileAndVerify( + text1, + parseOptions: TestOptions.RegularWithExtendedPartialMethods, + options: TestOptions.DebugExe, + expectedOutput: "1"); + verifier.VerifyDiagnostics( + // (8,38): warning CS1998: This async method lacks 'await' operators and will run synchronously. Consider using the 'await' operator to await non-blocking API calls, or 'await Task.Run(...)' to do CPU-bound work on a background thread. + // public static partial async Task Main() + Diagnostic(ErrorCode.WRN_AsyncLacksAwaits, "Main").WithLocation(8, 38)); + } + + [Fact] + public void EntryPoint_03() + { + const string text1 = @" +using System.Threading.Tasks; + +public partial class C +{ + public static partial Task Main(); +}"; + var comp1 = CreateCompilation( + text1, + parseOptions: TestOptions.RegularWithExtendedPartialMethods, + options: TestOptions.DebugExe); + comp1.VerifyDiagnostics( + // error CS5001: Program does not contain a static 'Main' method suitable for an entry point + Diagnostic(ErrorCode.ERR_NoEntryPoint).WithLocation(1, 1), + // (6,37): error CS8793: Partial method 'C.Main()' must have an implementation part because it has accessibility modifiers. + // public static partial Task Main(); + Diagnostic(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, "Main").WithArguments("C.Main()").WithLocation(6, 37)); + } + + [Fact] + public void EntryPoint_04() + { + const string text1 = @" +using System.Threading.Tasks; +using System; + +public partial class C +{ + public static partial Task Main(); + public static partial async Task Main() + { + Console.Write(1); + return 1; + } +}"; + var verifier = CompileAndVerify( + text1, + parseOptions: TestOptions.RegularWithExtendedPartialMethods, + options: TestOptions.DebugExe, + expectedOutput: "1"); + verifier.VerifyDiagnostics( + // (8,43): warning CS1998: This async method lacks 'await' operators and will run synchronously. Consider using the 'await' operator to await non-blocking API calls, or 'await Task.Run(...)' to do CPU-bound work on a background thread. + // public static partial async Task Main() + Diagnostic(ErrorCode.WRN_AsyncLacksAwaits, "Main").WithLocation(8, 43)); + } + } +} diff --git a/src/Compilers/CSharp/Test/Symbol/Symbols/GenericConstraintTests.cs b/src/Compilers/CSharp/Test/Symbol/Symbols/GenericConstraintTests.cs index 4c0da2be8f1b9..b2d2f85c503d8 100644 --- a/src/Compilers/CSharp/Test/Symbol/Symbols/GenericConstraintTests.cs +++ b/src/Compilers/CSharp/Test/Symbol/Symbols/GenericConstraintTests.cs @@ -664,7 +664,7 @@ partial class B where T : struct static partial void M2(A a, A>.B b) where U : class; static partial void M3(A a); static partial void M4() where U : A; - static partial A M5(); + internal static partial A M5(); } partial class B where T : struct { @@ -672,13 +672,9 @@ static partial void M1(A a) where U : struct { } static partial void M2(A a, A>.B b) where U : class { } static partial void M3(A a) { } static partial void M4() where U : A { } - static partial A M5() { return null; } + internal static partial A M5() { return null; } }"; - CreateCompilation(source).VerifyDiagnostics( - // (11,25): error CS0766: Partial methods must have a void return type - Diagnostic(ErrorCode.ERR_PartialMethodMustReturnVoid, "M5").WithLocation(11, 25), - // (19,25): error CS0766: Partial methods must have a void return type - Diagnostic(ErrorCode.ERR_PartialMethodMustReturnVoid, "M5").WithLocation(19, 25), + CreateCompilation(source, parseOptions: TestOptions.RegularWithExtendedPartialMethods).VerifyDiagnostics( // (10,28): error CS0453: The type 'V' must be a non-nullable value type in order to use it as parameter 'T' in the generic type or method 'A' Diagnostic(ErrorCode.ERR_ValConstraintNotSatisfied, "U").WithArguments("A", "T", "V").WithLocation(10, 28), // (18,28): error CS0453: The type 'V' must be a non-nullable value type in order to use it as parameter 'T' in the generic type or method 'A' @@ -687,8 +683,8 @@ static partial void M4() where U : A { } Diagnostic(ErrorCode.ERR_ValConstraintNotSatisfied, "a").WithArguments("A", "T", "U").WithLocation(8, 36), // (8,51): error CS0453: The type 'A' must be a non-nullable value type in order to use it as parameter 'T' in the generic type or method 'A' Diagnostic(ErrorCode.ERR_ValConstraintNotSatisfied, "b").WithArguments("A", "T", "A").WithLocation(8, 51), - // (19,25): error CS0453: The type 'U' must be a non-nullable value type in order to use it as parameter 'T' in the generic type or method 'A' - Diagnostic(ErrorCode.ERR_ValConstraintNotSatisfied, "M5").WithArguments("A", "T", "U").WithLocation(11, 25)); + // (19,34): error CS0453: The type 'U' must be a non-nullable value type in order to use it as parameter 'T' in the generic type or method 'A' + Diagnostic(ErrorCode.ERR_ValConstraintNotSatisfied, "M5").WithArguments("A", "T", "U").WithLocation(11, 34)); } [ClrOnlyFact] @@ -3230,11 +3226,17 @@ partial void M(T1 t1, T2 t2) }"; CreateCompilation(source).VerifyDiagnostics( // (13,9): error CS0103: The name 't' does not exist in the current context + // t.ToString(); Diagnostic(ErrorCode.ERR_NameNotInContext, "t").WithArguments("t").WithLocation(13, 9), // (14,9): error CS0103: The name 'u' does not exist in the current context + // u.ToString(); Diagnostic(ErrorCode.ERR_NameNotInContext, "u").WithArguments("u").WithLocation(14, 9), // (16,18): error CS0756: A partial method may not have multiple defining declarations - Diagnostic(ErrorCode.ERR_PartialMethodOnlyOneLatent, "M").WithLocation(16, 18)); + // partial void M(T1 t1, T2 t2) + Diagnostic(ErrorCode.ERR_PartialMethodOnlyOneLatent, "M").WithLocation(16, 18), + // (16,18): error CS0111: Type 'C' already defines a member called 'M' with the same parameter types + // partial void M(T1 t1, T2 t2) + Diagnostic(ErrorCode.ERR_MemberAlreadyExists, "M").WithArguments("M", "C").WithLocation(16, 18)); } [WorkItem(542331, "http://vstfdevdiv:8080/DevDiv2/DevDiv/_workitems/edit/542331")] diff --git a/src/Compilers/CSharp/Test/Symbol/Symbols/SymbolErrorTests.cs b/src/Compilers/CSharp/Test/Symbol/Symbols/SymbolErrorTests.cs index 34d103086f652..ea1114e5dfb0d 100644 --- a/src/Compilers/CSharp/Test/Symbol/Symbols/SymbolErrorTests.cs +++ b/src/Compilers/CSharp/Test/Symbol/Symbols/SymbolErrorTests.cs @@ -12568,19 +12568,13 @@ public partial class C public partial void M() where T : IA; public partial void M() where T : IA { } }"; - CreateCompilation(source).VerifyDiagnostics( + CreateCompilation(source, parseOptions: TestOptions.RegularWithExtendedPartialMethods).VerifyDiagnostics( // (6,44): error CS07: Inconsistent accessibility: constraint type 'IB>' is less accessible than 'A.B' // public partial class B where U : IB> { } Diagnostic(ErrorCode.ERR_BadVisBound, "IB>").WithArguments("A.B", "IB>").WithLocation(6, 44), // (7,44): error CS07: Inconsistent accessibility: constraint type 'IB>' is less accessible than 'A.B' // public partial class B where U : IB> { } Diagnostic(ErrorCode.ERR_BadVisBound, "IB>").WithArguments("A.B", "IB>").WithLocation(7, 44), - // (11,25): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - // public partial void M() where T : IA; - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "M").WithLocation(11, 25), - // (12,25): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - // public partial void M() where T : IA { } - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "M").WithLocation(12, 25), // (11,42): error CS07: Inconsistent accessibility: constraint type 'IA' is less accessible than 'C.M()' // public partial void M() where T : IA; Diagnostic(ErrorCode.ERR_BadVisBound, "IA").WithArguments("C.M()", "IA").WithLocation(11, 42), @@ -13521,29 +13515,49 @@ public static int Main() } } "; - CreateCompilation(text).VerifyDiagnostics( - // (19,25): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "PartA"), - // (20,26): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "PartB"), - // (21,28): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "PartC"), - // (22,27): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "PartD"), - // (23,26): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "PartE"), - // (24,27): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "PartF"), - // (25,27): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "PartG"), - // (26,22): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "PartH"), - // (274): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "PartI"), - // (29,25): error CS0750: A partial method cannot have access modifiers or the virtual, abstract, override, new, sealed, or extern modifiers - Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "PartJ"), + CreateCompilation(text, parseOptions: TestOptions.RegularWithExtendedPartialMethods).VerifyDiagnostics( + // (19,25): error CS8793: Partial method 'C.PartA()' must have an implementation part because it has accessibility modifiers. + // public partial void PartA(); + Diagnostic(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, "PartA").WithArguments("C.PartA()").WithLocation(19, 25), + // (20,26): error CS8793: Partial method 'C.PartB()' must have an implementation part because it has accessibility modifiers. + // private partial void PartB(); + Diagnostic(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, "PartB").WithArguments("C.PartB()").WithLocation(20, 26), + // (21,28): error CS8793: Partial method 'C.PartC()' must have an implementation part because it has accessibility modifiers. + // protected partial void PartC(); + Diagnostic(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, "PartC").WithArguments("C.PartC()").WithLocation(21, 28), + // (22,27): error CS8793: Partial method 'C.PartD()' must have an implementation part because it has accessibility modifiers. + // internal partial void PartD(); + Diagnostic(ErrorCode.ERR_PartialMethodWithAccessibilityModsMustHaveImplementation, "PartD").WithArguments("C.PartD()").WithLocation(22, 27), + // (29,25): error CS0759: No defining declaration found for implementing declaration of partial method 'C.PartJ()' + // extern partial void PartJ(); + Diagnostic(ErrorCode.ERR_PartialMethodMustHaveLatent, "PartJ").WithArguments("C.PartJ()").WithLocation(29, 25), + // (23,26): error CS8796: Partial method 'C.PartE()' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + // virtual partial void PartE(); + Diagnostic(ErrorCode.ERR_PartialMethodWithExtendedModMustHaveAccessMods, "PartE").WithArguments("C.PartE()").WithLocation(23, 26), + // (24,27): error CS0750: A partial method cannot have the 'abstract' modifier + // abstract partial void PartF(); + Diagnostic(ErrorCode.ERR_PartialMethodInvalidModifier, "PartF").WithLocation(24, 27), + // (25,27): error CS8796: Partial method 'C.PartG()' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + // override partial void PartG(); + Diagnostic(ErrorCode.ERR_PartialMethodWithExtendedModMustHaveAccessMods, "PartG").WithArguments("C.PartG()").WithLocation(25, 27), + // (26,22): error CS8796: Partial method 'C.PartH()' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + // new partial void PartH(); + Diagnostic(ErrorCode.ERR_PartialMethodWithExtendedModMustHaveAccessMods, "PartH").WithArguments("C.PartH()").WithLocation(26, 22), + // (27,34): error CS8796: Partial method 'C.PartI()' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + // sealed override partial void PartI(); + Diagnostic(ErrorCode.ERR_PartialMethodWithExtendedModMustHaveAccessMods, "PartI").WithArguments("C.PartI()").WithLocation(27, 34), + // (29,25): error CS8796: Partial method 'C.PartJ()' must have accessibility modifiers because it has a 'virtual', 'override', 'sealed', 'new', or 'extern' modifier. + // extern partial void PartJ(); + Diagnostic(ErrorCode.ERR_PartialMethodWithExtendedModMustHaveAccessMods, "PartJ").WithArguments("C.PartJ()").WithLocation(29, 25), + // (25,27): error CS0507: 'C.PartG()': cannot change access modifiers when overriding 'protected' inherited member 'Base.PartG()' + // override partial void PartG(); + Diagnostic(ErrorCode.ERR_CantChangeAccessOnOverride, "PartG").WithArguments("C.PartG()", "protected", "Base.PartG()").WithLocation(25, 27), + // (27,34): error CS0507: 'C.PartI()': cannot change access modifiers when overriding 'protected' inherited member 'Base.PartI()' + // sealed override partial void PartI(); + Diagnostic(ErrorCode.ERR_CantChangeAccessOnOverride, "PartI").WithArguments("C.PartI()", "protected", "Base.PartI()").WithLocation(27, 34), // (28,6): error CS0601: The DllImport attribute must be specified on a method marked 'static' and 'extern' - Diagnostic(ErrorCode.ERR_DllImportOnInvalidMethod, "System.Runtime.InteropServices.DllImport")); + // [System.Runtime.InteropServices.DllImport("none")] + Diagnostic(ErrorCode.ERR_DllImportOnInvalidMethod, "System.Runtime.InteropServices.DllImport").WithLocation(28, 6)); } [Fact] @@ -13577,11 +13591,10 @@ public partial class C } } "; - var comp = DiagnosticsUtils.VerifyErrorsAndGetCompilationWithMscorlib(text, - new ErrorDescription { Code = (int)ErrorCode.ERR_PartialMethodCannotHaveOutParameters, Line = 7, Column = 22 }); - - var ns = comp.SourceModule.GlobalNamespace.GetMembers("NS").Single() as NamespaceSymbol; - // TODO... + CreateCompilation(text, parseOptions: TestOptions.RegularWithExtendedPartialMethods).VerifyDiagnostics( + // (7,22): error CS8795: Partial method 'C.F(out int)' must have accessibility modifiers because it has 'out' parameters. + // partial void F(out int x); + Diagnostic(ErrorCode.ERR_PartialMethodWithOutParamMustHaveAccessMods, "F").WithArguments("NS.C.F(out int)").WithLocation(7, 22)); } [Fact] @@ -13671,7 +13684,10 @@ public static int Main() CreateCompilation(text).VerifyDiagnostics( // (5,18): error CS0756: A partial method may not have multiple defining declarations // partial void Part(); // CS0756 - Diagnostic(ErrorCode.ERR_PartialMethodOnlyOneLatent, "Part").WithLocation(5, 18)); + Diagnostic(ErrorCode.ERR_PartialMethodOnlyOneLatent, "Part").WithLocation(5, 18), + // (5,18): error CS0111: Type 'C' already defines a member called 'Part' with the same parameter types + // partial void Part(); // CS0756 + Diagnostic(ErrorCode.ERR_MemberAlreadyExists, "Part").WithArguments("Part", "C").WithLocation(5, 18)); } [Fact] @@ -13957,8 +13973,8 @@ public void CS0766ERR_PartialMethodMustReturnVoid() public partial class C { - partial int Part(); // CS0766 - partial int Part() //CS0766 + partial int Part(); + partial int Part() { return 1; } @@ -13970,9 +13986,13 @@ public static int Main() } "; - var comp = DiagnosticsUtils.VerifyErrorsAndGetCompilationWithMscorlib(text, - new ErrorDescription { Code = (int)ErrorCode.ERR_PartialMethodMustReturnVoid, Line = 5, Column = 17 }, - new ErrorDescription { Code = (int)ErrorCode.ERR_PartialMethodMustReturnVoid, Line = 6, Column = 17 }); + CreateCompilation(text).VerifyDiagnostics( + // (5,17): error CS8794: Partial method 'C.Part()' must have accessibility modifiers because it has a non-void return type. + // partial int Part(); + Diagnostic(ErrorCode.ERR_PartialMethodWithNonVoidReturnMustHaveAccessMods, "Part").WithArguments("C.Part()").WithLocation(5, 17), + // (6,17): error CS8794: Partial method 'C.Part()' must have accessibility modifiers because it has a non-void return type. + // partial int Part() + Diagnostic(ErrorCode.ERR_PartialMethodWithNonVoidReturnMustHaveAccessMods, "Part").WithArguments("C.Part()").WithLocation(6, 17)); } [Fact] @@ -20498,11 +20518,11 @@ partial class C { partial void M(int i); partial void M(out int i) { i = 0; } }").VerifyDiagnostics( - // (4,18): error CS0752: A partial method cannot have out parameters - // partial void M(out int i) { i = 0; } - Diagnostic(ErrorCode.ERR_PartialMethodCannotHaveOutParameters, "M").WithLocation(4, 18), + // (4,18): error CS8795: Partial method 'C.M(out int)' must have accessibility modifiers because it has 'out' parameters. + // partial void M(out int i) { i = 0; } + Diagnostic(ErrorCode.ERR_PartialMethodWithOutParamMustHaveAccessMods, "M").WithArguments("C.M(out int)").WithLocation(4, 18), // (4,18): error CS0759: No defining declaration found for implementing declaration of partial method 'C.M(out int)' - // partial void M(out int i) { i = 0; } + // partial void M(out int i) { i = 0; } Diagnostic(ErrorCode.ERR_PartialMethodMustHaveLatent, "M").WithArguments("C.M(out int)").WithLocation(4, 18)); } @@ -20525,7 +20545,7 @@ public void PartialMethodsConsiderRefKindDifferences_RefWithIn() CreateCompilation(@" partial class C { partial void M(ref int i); - partial void M(in int i) {} + partial void M(in int i) {} }").VerifyDiagnostics( // (4,18): error CS0759: No defining declaration found for implementing declaration of partial method 'C.M(in int)' // partial void M(in int i) {} @@ -20538,13 +20558,13 @@ public void PartialMethodsConsiderRefKindDifferences_RefWithOut() CreateCompilation(@" partial class C { partial void M(ref int i); - partial void M(out int i) { i = 0; } + partial void M(out int i) { i = 0; } }").VerifyDiagnostics( - // (4,18): error CS0752: A partial method cannot have out parameters - // partial void M(out int i) { i = 0; } - Diagnostic(ErrorCode.ERR_PartialMethodCannotHaveOutParameters, "M").WithLocation(4, 18), + // (4,18): error CS8795: Partial method 'C.M(out int)' must have accessibility modifiers because it has 'out' parameters. + // partial void M(out int i) { i = 0; } + Diagnostic(ErrorCode.ERR_PartialMethodWithOutParamMustHaveAccessMods, "M").WithArguments("C.M(out int)").WithLocation(4, 18), // (4,18): error CS0759: No defining declaration found for implementing declaration of partial method 'C.M(out int)' - // partial void M(out int i) { i = 0; } + // partial void M(out int i) { i = 0; } Diagnostic(ErrorCode.ERR_PartialMethodMustHaveLatent, "M").WithArguments("C.M(out int)").WithLocation(4, 18)); } @@ -20582,11 +20602,11 @@ partial class C { partial void M(in int i); partial void M(out int i) { i = 0; } }").VerifyDiagnostics( - // (4,18): error CS0752: A partial method cannot have out parameters - // partial void M(out int i) { i = 0; } - Diagnostic(ErrorCode.ERR_PartialMethodCannotHaveOutParameters, "M").WithLocation(4, 18), + // (4,18): error CS8795: Partial method 'C.M(out int)' must have accessibility modifiers because it has 'out' parameters. + // partial void M(out int i) { i = 0; } + Diagnostic(ErrorCode.ERR_PartialMethodWithOutParamMustHaveAccessMods, "M").WithArguments("C.M(out int)").WithLocation(4, 18), // (4,18): error CS0759: No defining declaration found for implementing declaration of partial method 'C.M(out int)' - // partial void M(out int i) { i = 0; } + // partial void M(out int i) { i = 0; } Diagnostic(ErrorCode.ERR_PartialMethodMustHaveLatent, "M").WithArguments("C.M(out int)").WithLocation(4, 18)); } @@ -20598,9 +20618,9 @@ partial class C { partial void M(out int i); partial void M(int i) {} }").VerifyDiagnostics( - // (3,18): error CS0752: A partial method cannot have out parameters + // (3,18): error CS8794: Partial method C.M(out int) must have an implementation part because it has 'out' parameters. // partial void M(out int i); - Diagnostic(ErrorCode.ERR_PartialMethodCannotHaveOutParameters, "M").WithLocation(3, 18), + Diagnostic(ErrorCode.ERR_PartialMethodWithOutParamMustHaveAccessMods, "M").WithArguments("C.M(out int)").WithLocation(3, 18), // (4,18): error CS0759: No defining declaration found for implementing declaration of partial method 'C.M(int)' // partial void M(int i) {} Diagnostic(ErrorCode.ERR_PartialMethodMustHaveLatent, "M").WithArguments("C.M(int)").WithLocation(4, 18)); @@ -20612,13 +20632,13 @@ public void PartialMethodsConsiderRefKindDifferences_OutWithRef() CreateCompilation(@" partial class C { partial void M(out int i); - partial void M(ref int i) {} + partial void M(ref int i) {} }").VerifyDiagnostics( - // (3,18): error CS0752: A partial method cannot have out parameters + // (3,18): error CS8794: Partial method C.M(out int) must have an implementation part because it has 'out' parameters. // partial void M(out int i); - Diagnostic(ErrorCode.ERR_PartialMethodCannotHaveOutParameters, "M").WithLocation(3, 18), + Diagnostic(ErrorCode.ERR_PartialMethodWithOutParamMustHaveAccessMods, "M").WithArguments("C.M(out int)").WithLocation(3, 18), // (4,18): error CS0759: No defining declaration found for implementing declaration of partial method 'C.M(ref int)' - // partial void M(ref int i) {} + // partial void M(ref int i) {} Diagnostic(ErrorCode.ERR_PartialMethodMustHaveLatent, "M").WithArguments("C.M(ref int)").WithLocation(4, 18)); } @@ -20630,9 +20650,9 @@ partial class C { partial void M(out int i); partial void M(in int i) {} }").VerifyDiagnostics( - // (3,18): error CS0752: A partial method cannot have out parameters + // (3,18): error CS8794: Partial method C.M(out int) must have an implementation part because it has 'out' parameters. // partial void M(out int i); - Diagnostic(ErrorCode.ERR_PartialMethodCannotHaveOutParameters, "M").WithLocation(3, 18), + Diagnostic(ErrorCode.ERR_PartialMethodWithOutParamMustHaveAccessMods, "M").WithArguments("C.M(out int)").WithLocation(3, 18), // (4,18): error CS0759: No defining declaration found for implementing declaration of partial method 'C.M(in int)' // partial void M(in int i) {} Diagnostic(ErrorCode.ERR_PartialMethodMustHaveLatent, "M").WithArguments("C.M(in int)").WithLocation(4, 18)); diff --git a/src/Compilers/Test/Utilities/CSharp/TestOptions.cs b/src/Compilers/Test/Utilities/CSharp/TestOptions.cs index d171aef2dd8da..50513aa9f92bc 100644 --- a/src/Compilers/Test/Utilities/CSharp/TestOptions.cs +++ b/src/Compilers/Test/Utilities/CSharp/TestOptions.cs @@ -28,6 +28,8 @@ public static class TestOptions public static readonly CSharpParseOptions RegularWithLegacyStrongName = Regular.WithFeature("UseLegacyStrongNameProvider"); public static readonly CSharpParseOptions WithoutImprovedOverloadCandidates = Regular.WithLanguageVersion(MessageID.IDS_FeatureImprovedOverloadCandidates.RequiredVersion() - 1); + public static readonly CSharpParseOptions RegularWithExtendedPartialMethods = RegularPreview; + private static readonly SmallDictionary s_experimentalFeatures = new SmallDictionary { }; public static readonly CSharpParseOptions ExperimentalParseOptions = new CSharpParseOptions(kind: SourceCodeKind.Regular, documentationMode: DocumentationMode.None, languageVersion: LanguageVersion.Preview).WithFeatures(s_experimentalFeatures);