private TypeWithAnnotations ComputeReturnType(DiagnosticBag diagnostics)
        {
            if (this.MethodKind == MethodKind.PropertyGet)
            {
                var type = _property.TypeWithAnnotations;
                if (!ContainingType.IsInterfaceType() && type.Type.IsStatic)
                {
                    // '{0}': static types cannot be used as return types
                    diagnostics.Add(ErrorCode.ERR_ReturnTypeIsStaticClass, this.locations[0], type.Type);
                }

                return(type);
            }
            else
            {
                var binder = GetBinder();
                var type   = TypeWithAnnotations.Create(binder.GetSpecialType(SpecialType.System_Void, diagnostics, this.GetSyntax()));

                if (IsInitOnly)
                {
                    var isInitOnlyType = Binder.GetWellKnownType(this.DeclaringCompilation,
                                                                 WellKnownType.System_Runtime_CompilerServices_IsExternalInit, diagnostics, this.locations[0]);

                    var modifiers = ImmutableArray.Create <CustomModifier>(
                        CSharpCustomModifier.CreateRequired(isInitOnlyType));
                    type = type.WithModifiers(modifiers);
                }

                return(type);
            }
        }
 private TypeSymbol ComputeReturnType(DiagnosticBag diagnostics)
 {
     if (this.MethodKind == MethodKind.PropertyGet)
     {
         var type = _property.Type;
         if (!ContainingType.IsInterfaceType() && type.IsStatic)
         {
             // '{0}': static types cannot be used as return types
             diagnostics.Add(ErrorCode.ERR_ReturnTypeIsStaticClass, this.locations[0], type);
         }
         return(type);
     }
     else
     {
         var binder = GetBinder();
         return(binder.GetSpecialType(SpecialType.System_Void, diagnostics, this.GetSyntax()));
     }
 }
示例#3
0
        private ImmutableArray <ParameterSymbol> ComputeParameters(DiagnosticBag diagnostics)
        {
            bool isGetMethod         = this.MethodKind == MethodKind.PropertyGet;
            var  propertyParameters  = _property.Parameters;
            int  nPropertyParameters = propertyParameters.Length;
            int  nParameters         = nPropertyParameters + (isGetMethod ? 0 : 1);

            if (nParameters == 0)
            {
                return(ImmutableArray <ParameterSymbol> .Empty);
            }

            var parameters = ArrayBuilder <ParameterSymbol> .GetInstance(nParameters);

            // Clone the property parameters for the accessor method. The
            // parameters are cloned (rather than referenced from the property)
            // since the ContainingSymbol needs to be set to the accessor.
            foreach (SourceParameterSymbol propertyParam in propertyParameters)
            {
                parameters.Add(new SourceClonedParameterSymbol(propertyParam, this, propertyParam.Ordinal, suppressOptional: false));
            }

            if (!isGetMethod)
            {
                var propertyType = _property.TypeWithAnnotations;
                if (!ContainingType.IsInterfaceType() && propertyType.IsStatic)
                {
                    // '{0}': static types cannot be used as parameters
                    diagnostics.Add(ErrorCode.ERR_ParameterIsStaticClass, this.locations[0], propertyType.Type);
                }

                parameters.Add(new SynthesizedAccessorValueParameterSymbol(this, propertyType, parameters.Count));
            }

            return(parameters.ToImmutableAndFree());
        }
示例#4
0
        private void CheckModifiers(Location location, DiagnosticBag diagnostics)
        {
            const DeclarationModifiers partialMethodInvalidModifierMask = (DeclarationModifiers.AccessibilityMask & ~DeclarationModifiers.Private) |
                                                                          DeclarationModifiers.Virtual |
                                                                          DeclarationModifiers.Abstract |
                                                                          DeclarationModifiers.Override |
                                                                          DeclarationModifiers.New |
                                                                          DeclarationModifiers.Sealed |
                                                                          DeclarationModifiers.Extern;

            if (IsPartial && !ReturnsVoid)
            {
                diagnostics.Add(ErrorCode.ERR_PartialMethodMustReturnVoid, location);
            }
            else if (IsPartial && !ContainingType.IsInterface && (DeclarationModifiers & partialMethodInvalidModifierMask) != 0)
            {
                diagnostics.Add(ErrorCode.ERR_PartialMethodInvalidModifier, location);
            }
            else if (this.DeclaredAccessibility == Accessibility.Private && (IsVirtual || IsAbstract || IsOverride))
            {
                diagnostics.Add(ErrorCode.ERR_VirtualPrivate, location, this);
            }
            else if (IsStatic && (IsOverride || IsVirtual || IsAbstract))
            {
                // A static member '{0}' cannot be marked as override, virtual, or abstract
                diagnostics.Add(ErrorCode.ERR_StaticNotVirtual, location, this);
            }
            else if (IsOverride && (IsNew || IsVirtual))
            {
                // A member '{0}' marked as override cannot be marked as new or virtual
                diagnostics.Add(ErrorCode.ERR_OverrideNotNew, location, this);
            }
            else if (IsSealed && !IsOverride)
            {
                // '{0}' cannot be sealed because it is not an override
                diagnostics.Add(ErrorCode.ERR_SealedNonOverride, location, this);
            }
            else if (IsSealed && ContainingType.TypeKind == TypeKind.Struct)
            {
                // The modifier '{0}' is not valid for this item
                diagnostics.Add(ErrorCode.ERR_BadMemberFlag, location, SyntaxFacts.GetText(SyntaxKind.SealedKeyword));
            }
            else if (!ContainingType.IsInterfaceType() && _lazyReturnType.IsStatic)
            {
                // '{0}': static types cannot be used as return types
                diagnostics.Add(ErrorCode.ERR_ReturnTypeIsStaticClass, location, _lazyReturnType);
            }
            else if (IsAbstract && IsExtern)
            {
                diagnostics.Add(ErrorCode.ERR_AbstractAndExtern, location, this);
            }
            else if (IsAbstract && IsSealed)
            {
                diagnostics.Add(ErrorCode.ERR_AbstractAndSealed, location, this);
            }
            else if (IsAbstract && IsVirtual)
            {
                diagnostics.Add(ErrorCode.ERR_AbstractNotVirtual, location, this);
            }
            else if (IsAbstract && ContainingType.TypeKind == TypeKind.Struct)
            {
                // The modifier '{0}' is not valid for this item
                diagnostics.Add(ErrorCode.ERR_BadMemberFlag, location, SyntaxFacts.GetText(SyntaxKind.AbstractKeyword));
            }
            else if (IsVirtual && ContainingType.TypeKind == TypeKind.Struct)
            {
                // The modifier '{0}' is not valid for this item
                diagnostics.Add(ErrorCode.ERR_BadMemberFlag, location, SyntaxFacts.GetText(SyntaxKind.VirtualKeyword));
            }
            else if (IsAbstract && !ContainingType.IsAbstract && (ContainingType.TypeKind == TypeKind.Class || ContainingType.TypeKind == TypeKind.Submission))
            {
                // '{0}' is abstract but it is contained in non-abstract class '{1}'
                diagnostics.Add(ErrorCode.ERR_AbstractInConcreteClass, location, this, ContainingType);
            }
            else if (IsVirtual && ContainingType.IsSealed)
            {
                // '{0}' is a new virtual member in sealed class '{1}'
                diagnostics.Add(ErrorCode.ERR_NewVirtualInSealed, location, this, ContainingType);
            }
            else if (bodySyntaxReferenceOpt == null && IsAsync)
            {
                diagnostics.Add(ErrorCode.ERR_BadAsyncLacksBody, location);
            }
            else if (bodySyntaxReferenceOpt == null && !IsExtern && !IsAbstract && !IsPartial && !IsExpressionBodied)
            {
                diagnostics.Add(ErrorCode.ERR_ConcreteMissingBody, location, this);
            }
            else if (ContainingType.IsSealed && this.DeclaredAccessibility.HasProtected() && !this.IsOverride)
            {
                diagnostics.Add(AccessCheck.GetProtectedMemberInSealedTypeError(ContainingType), location, this);
            }
            else if (ContainingType.IsStatic && !IsStatic)
            {
                diagnostics.Add(ErrorCode.ERR_InstanceMemberInStaticClass, location, Name);
            }
            else if (_lazyIsVararg && (IsGenericMethod || ContainingType.IsGenericType || _lazyParameters.Length > 0 && _lazyParameters[_lazyParameters.Length - 1].IsParams))
            {
                diagnostics.Add(ErrorCode.ERR_BadVarargs, location);
            }
            else if (_lazyIsVararg && IsAsync)
            {
                diagnostics.Add(ErrorCode.ERR_VarargsAsync, location);
            }
        }
示例#5
0
        private void CheckModifiers(bool isExplicitInterfaceImplementation, bool isVararg, bool hasBody, Location location, DiagnosticBag diagnostics)
        {
            bool isExplicitInterfaceImplementationInInterface = isExplicitInterfaceImplementation && ContainingType.IsInterface;

            if (IsPartial && HasExplicitAccessModifier)
            {
                Binder.CheckFeatureAvailability(SyntaxNode, MessageID.IDS_FeatureExtendedPartialMethods, diagnostics, location);
            }

            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);
            }
            else if (IsStatic && (IsOverride || IsVirtual || IsAbstract))
            {
                // A static member '{0}' cannot be marked as override, virtual, or abstract
                diagnostics.Add(ErrorCode.ERR_StaticNotVirtual, location, this);
            }
            else if (IsOverride && (IsNew || IsVirtual))
            {
                // A member '{0}' marked as override cannot be marked as new or virtual
                diagnostics.Add(ErrorCode.ERR_OverrideNotNew, location, this);
            }
            else if (IsSealed && !IsOverride && !(isExplicitInterfaceImplementationInInterface && IsAbstract))
            {
                // '{0}' cannot be sealed because it is not an override
                diagnostics.Add(ErrorCode.ERR_SealedNonOverride, location, this);
            }
            else if (IsSealed && ContainingType.TypeKind == TypeKind.Struct)
            {
                // The modifier '{0}' is not valid for this item
                diagnostics.Add(ErrorCode.ERR_BadMemberFlag, location, SyntaxFacts.GetText(SyntaxKind.SealedKeyword));
            }
            else if (!ContainingType.IsInterfaceType() && _lazyReturnType.IsStatic)
            {
                // '{0}': static types cannot be used as return types
                diagnostics.Add(ErrorCode.ERR_ReturnTypeIsStaticClass, location, _lazyReturnType.Type);
            }
            else if (IsAbstract && IsExtern)
            {
                diagnostics.Add(ErrorCode.ERR_AbstractAndExtern, location, this);
            }
            else if (IsAbstract && IsSealed && !isExplicitInterfaceImplementationInInterface)
            {
                diagnostics.Add(ErrorCode.ERR_AbstractAndSealed, location, this);
            }
            else if (IsAbstract && IsVirtual)
            {
                diagnostics.Add(ErrorCode.ERR_AbstractNotVirtual, location, this.Kind.Localize(), this);
            }
            else if (IsAbstract && ContainingType.TypeKind == TypeKind.Struct)
            {
                // The modifier '{0}' is not valid for this item
                diagnostics.Add(ErrorCode.ERR_BadMemberFlag, location, SyntaxFacts.GetText(SyntaxKind.AbstractKeyword));
            }
            else if (IsVirtual && ContainingType.TypeKind == TypeKind.Struct)
            {
                // The modifier '{0}' is not valid for this item
                diagnostics.Add(ErrorCode.ERR_BadMemberFlag, location, SyntaxFacts.GetText(SyntaxKind.VirtualKeyword));
            }
            else if (IsStatic && IsDeclaredReadOnly)
            {
                // Static member '{0}' cannot be marked 'readonly'.
                diagnostics.Add(ErrorCode.ERR_StaticMemberCantBeReadOnly, location, this);
            }
            else if (IsAbstract && !ContainingType.IsAbstract && (ContainingType.TypeKind == TypeKind.Class || ContainingType.TypeKind == TypeKind.Submission))
            {
                // '{0}' is abstract but it is contained in non-abstract class '{1}'
                diagnostics.Add(ErrorCode.ERR_AbstractInConcreteClass, location, this, ContainingType);
            }
            else if (IsVirtual && ContainingType.IsSealed)
            {
                // '{0}' is a new virtual member in sealed class '{1}'
                diagnostics.Add(ErrorCode.ERR_NewVirtualInSealed, location, this, ContainingType);
            }
            else if (!hasBody && IsAsync)
            {
                diagnostics.Add(ErrorCode.ERR_BadAsyncLacksBody, location);
            }
            else if (!hasBody && !IsExtern && !IsAbstract && !IsPartial && !IsExpressionBodied)
            {
                diagnostics.Add(ErrorCode.ERR_ConcreteMissingBody, location, this);
            }
            else if (ContainingType.IsSealed && this.DeclaredAccessibility.HasProtected() && !this.IsOverride)
            {
                diagnostics.Add(AccessCheck.GetProtectedMemberInSealedTypeError(ContainingType), location, this);
            }
            else if (ContainingType.IsStatic && !IsStatic)
            {
                diagnostics.Add(ErrorCode.ERR_InstanceMemberInStaticClass, location, Name);
            }
            else if (isVararg && (IsGenericMethod || ContainingType.IsGenericType || _lazyParameters.Length > 0 && _lazyParameters[_lazyParameters.Length - 1].IsParams))
            {
                diagnostics.Add(ErrorCode.ERR_BadVarargs, location);
            }
            else if (isVararg && IsAsync)
            {
                diagnostics.Add(ErrorCode.ERR_VarargsAsync, location);
            }
        }
示例#6
0
 private void CheckModifiers(Location location, DiagnosticBag diagnostics)
 {
     if (IsPartial && !ReturnsVoid)
     {
         diagnostics.Add(ErrorCode.ERR_PartialMethodMustReturnVoid, location);
     }
     else if (IsPartial && !ContainingType.IsInterface && 0 != (DeclarationModifiers &
                                                                (CSharp.DeclarationModifiers.AccessibilityMask & ~CSharp.DeclarationModifiers.Private |
                                                                 CSharp.DeclarationModifiers.Virtual |
                                                                 CSharp.DeclarationModifiers.Abstract |
                                                                 CSharp.DeclarationModifiers.Override |
                                                                 CSharp.DeclarationModifiers.New |
                                                                 CSharp.DeclarationModifiers.Sealed |
                                                                 CSharp.DeclarationModifiers.Extern)))
     {
         diagnostics.Add(ErrorCode.ERR_PartialMethodInvalidModifier, location);
     }
     else if (this.DeclaredAccessibility == Accessibility.Private && (IsVirtual || IsAbstract || IsOverride))
     {
         diagnostics.Add(ErrorCode.ERR_VirtualPrivate, location, this);
     }
     else if (IsStatic && (IsOverride || IsVirtual || IsAbstract))
     {
         // A static member '{0}' cannot be marked as override, virtual, or abstract
         diagnostics.Add(ErrorCode.ERR_StaticNotVirtual, location, this);
     }
     else if (IsOverride && (IsNew || IsVirtual))
     {
         // A member '{0}' marked as override cannot be marked as new or virtual
         diagnostics.Add(ErrorCode.ERR_OverrideNotNew, location, this);
     }
     else if (IsSealed && !IsOverride)
     {
         // '{0}' cannot be sealed because it is not an override
         diagnostics.Add(ErrorCode.ERR_SealedNonOverride, location, this);
     }
     else if (!ContainingType.IsInterfaceType() && this.lazyReturnType.IsStatic)
     {
         // '{0}': static types cannot be used as return types
         diagnostics.Add(ErrorCode.ERR_ReturnTypeIsStaticClass, location, this.lazyReturnType);
     }
     else if (IsAbstract && IsExtern)
     {
         diagnostics.Add(ErrorCode.ERR_AbstractAndExtern, location, this);
     }
     else if (IsAbstract && IsSealed)
     {
         diagnostics.Add(ErrorCode.ERR_AbstractAndSealed, location, this);
     }
     else if (IsAbstract && IsVirtual)
     {
         diagnostics.Add(ErrorCode.ERR_AbstractNotVirtual, location, this);
     }
     else if (IsAbstract && !ContainingType.IsAbstract && ContainingType.TypeKind == TypeKind.Class)
     {
         // '{0}' is abstract but it is contained in non-abstract class '{1}'
         diagnostics.Add(ErrorCode.ERR_AbstractInConcreteClass, location, this, ContainingType);
     }
     else if (IsVirtual && ContainingType.IsSealed)
     {
         // '{0}' is a new virtual member in sealed class '{1}'
         diagnostics.Add(ErrorCode.ERR_NewVirtualInSealed, location, this, ContainingType);
     }
     else if (blockSyntaxReference == null && IsAsync)
     {
         diagnostics.Add(ErrorCode.ERR_BadAsyncLacksBody, location);
     }
     else if (blockSyntaxReference == null && !IsExtern && !IsAbstract && !IsPartial)
     {
         diagnostics.Add(ErrorCode.ERR_ConcreteMissingBody, location, this);
     }
     else if (
         ContainingType.IsSealed &&
         (this.DeclaredAccessibility == Accessibility.Protected || this.DeclaredAccessibility == Accessibility.ProtectedOrInternal) &&
         !this.IsOverride)
     {
         diagnostics.Add(AccessCheck.GetProtectedMemberInSealedTypeError(ContainingType), location, this);
     }
     else if (ContainingType.IsStatic && !IsStatic)
     {
         diagnostics.Add(ErrorCode.ERR_InstanceMemberInStaticClass, location, Name);
     }
     else if (this.lazyIsVararg && (IsGenericMethod || ContainingType.IsGenericType || this.lazyParameters.Length > 0 && this.lazyParameters[this.lazyParameters.Length - 1].IsParams))
     {
         diagnostics.Add(ErrorCode.ERR_BadVarargs, location);
     }
     else if (this.lazyIsVararg && IsAsync)
     {
         diagnostics.Add(ErrorCode.ERR_VarargsAsync, location);
     }
 }