Exemplo n.º 1
0
        private ImmutableArray <TypeParameterSymbol> LoadTypeParameters(ref DiagnosticInfo diagnosticInfo)
        {
            try
            {
                var moduleSymbol = _containingType.ContainingPEModule;
                var gpHandles    = moduleSymbol.Module.GetGenericParametersForMethodOrThrow(_handle);

                if (gpHandles.Count == 0)
                {
                    return(ImmutableArray <TypeParameterSymbol> .Empty);
                }
                else
                {
                    var ownedParams = ImmutableArray.CreateBuilder <TypeParameterSymbol>(gpHandles.Count);
                    for (int i = 0; i < gpHandles.Count; i++)
                    {
                        ownedParams.Add(new PETypeParameterSymbol(moduleSymbol, this, (ushort)i, gpHandles[i]));
                    }

                    return(ownedParams.ToImmutable());
                }
            }
            catch (BadImageFormatException)
            {
                diagnosticInfo = new CSDiagnosticInfo(ErrorCode.ERR_BindToBogus, this);
                return(ImmutableArray <TypeParameterSymbol> .Empty);
            }
        }
 internal static CSDiagnosticInfo ReportDiagnostic(this ErrorCode code, ref DiagnosticBag diagnostics, Location location, params object[] args)
 {
     var info = new CSDiagnosticInfo(code, args);
     var diag = new Diagnostic(info, location);
     if (diagnostics == null)
         diagnostics = new DiagnosticBag();
     diagnostics.Add(diag);
     return info;
 }
Exemplo n.º 3
0
        private DiagnosticInfo InitializeUseSiteDiagnostic(DiagnosticInfo diagnostic)
        {
            Debug.Assert(!CSDiagnosticInfo.IsEmpty(diagnostic));
            if (diagnostic != null)
            {
                diagnostic = InterlockedOperations.Initialize(ref AccessUncommonFields()._lazyUseSiteDiagnostic, diagnostic, CSDiagnosticInfo.EmptyErrorInfo);
            }

            _packedFlags.SetIsUseSiteDiagnosticPopulated();
            return(diagnostic);
        }
Exemplo n.º 4
0
        internal static CSDiagnosticInfo ReportDiagnostic(this ErrorCode code, ref DiagnosticBag diagnostics, Location location, params object[] args)
        {
            var info = new CSDiagnosticInfo(code, args);
            var diag = new Diagnostic(info, location);

            if (diagnostics == null)
            {
                diagnostics = new DiagnosticBag();
            }
            diagnostics.Add(diag);
            return(info);
        }
Exemplo n.º 5
0
        private static ExtendedErrorTypeSymbol CyclicInheritanceError(
            RetargetingNamedTypeSymbol type,
            TypeSymbol declaredBase
            )
        {
            var info = new CSDiagnosticInfo(ErrorCode.ERR_ImportedCircularBase, declaredBase, type);

            return(new ExtendedErrorTypeSymbol(
                       declaredBase,
                       LookupResultKind.NotReferencable,
                       info,
                       true
                       ));
        }
Exemplo n.º 6
0
        internal ErrorTypeSymbol CreateCycleInTypeForwarderErrorTypeSymbol(
            ref MetadataTypeName emittedName
            )
        {
            DiagnosticInfo diagnosticInfo = new CSDiagnosticInfo(
                ErrorCode.ERR_CycleInTypeForwarder,
                emittedName.FullName,
                this.Name
                );

            return(new MissingMetadataTypeSymbol.TopLevel(
                       this.Modules[0],
                       ref emittedName,
                       diagnosticInfo
                       ));
        }
Exemplo n.º 7
0
        internal ErrorTypeSymbol CreateMultipleForwardingErrorTypeSymbol(
            ref MetadataTypeName emittedName,
            ModuleSymbol forwardingModule,
            AssemblySymbol destination1,
            AssemblySymbol destination2
            )
        {
            var diagnosticInfo = new CSDiagnosticInfo(
                ErrorCode.ERR_TypeForwardedToMultipleAssemblies,
                forwardingModule,
                this,
                emittedName.FullName,
                destination1,
                destination2
                );

            return(new MissingMetadataTypeSymbol.TopLevel(
                       forwardingModule,
                       ref emittedName,
                       diagnosticInfo
                       ));
        }
Exemplo n.º 8
0
        // Check if the given symbol can be accessed with the given arity. If OK, return false.
        // If not OK, return true and return a diagnosticinfo. Note that methods with type arguments
        // can be accesses with arity zero due to type inference (but non types).
        private bool WrongArity(Symbol symbol, int arity, out DiagnosticInfo diagInfo)
        {
            switch (symbol.Kind)
            {
            case SymbolKind.NamedType:
                NamedTypeSymbol namedType = (NamedTypeSymbol)symbol;
                if (namedType.Arity != arity)
                {
                    diagInfo = new CSDiagnosticInfo(ErrorCode.ERR_BadArity, namedType.GetFullName(), namedType.Arity);
                    return(true);
                }
                break;

            case SymbolKind.Method:
                if (arity != 0)
                {
                    MethodSymbol method = (MethodSymbol)symbol;
                    if (method.Arity != arity)
                    {
                        diagInfo = new CSDiagnosticInfo(ErrorCode.ERR_HasNoTypeVars, method.GetFullName());
                        return(true);
                    }
                }
                break;

            default:
                if (arity != 0)
                {
                    diagInfo = new CSDiagnosticInfo(ErrorCode.ERR_TypeArgsNotAllowed, symbol.GetFullName());
                    return(true);
                }
                break;
            }

            diagInfo = null;
            return(false);
        }
Exemplo n.º 9
0
        internal override DiagnosticInfo GetUseSiteDiagnostic()
        {
            if (!_packedFlags.IsUseSiteDiagnosticPopulated)
            {
                DiagnosticInfo result = null;
                CalculateUseSiteDiagnostic(ref result);
                EnsureTypeParametersAreLoaded(ref result);
                return(InitializeUseSiteDiagnostic(result));
            }

            var uncommonFields = _uncommonFields;

            if (uncommonFields == null)
            {
                return(null);
            }
            else
            {
                var result = uncommonFields._lazyUseSiteDiagnostic;
                return(CSDiagnosticInfo.IsEmpty(result)
                       ? InterlockedOperations.Initialize(ref uncommonFields._lazyUseSiteDiagnostic, null, CSDiagnosticInfo.EmptyErrorInfo)
                       : result);
            }
        }
Exemplo n.º 10
0
        internal override bool GetUnificationUseSiteDiagnostic(ref DiagnosticInfo result, TypeSymbol dependentType)
        {
            AssertReferencesInitialized();

            var ownerModule       = this;
            var ownerAssembly     = ownerModule.ContainingAssembly;
            var dependentAssembly = dependentType.ContainingAssembly;

            if (ownerAssembly == dependentAssembly)
            {
                return(false);
            }

            // TODO (tomat): we should report an error/warning for all unified references, not just the first one.

            foreach (var unifiedAssembly in GetUnifiedAssemblies())
            {
                if (!ReferenceEquals(unifiedAssembly.TargetAssembly, dependentAssembly))
                {
                    continue;
                }

                var referenceId        = unifiedAssembly.OriginalReference;
                var definitionId       = dependentAssembly.Identity;
                var involvedAssemblies = ImmutableArray.Create <Symbol>(ownerAssembly, dependentAssembly);

                DiagnosticInfo info;
                if (definitionId.Version > referenceId.Version)
                {
                    // unified with a definition whose version is higher than the reference
                    ErrorCode warning = (definitionId.Version.Major == referenceId.Version.Major && definitionId.Version.Minor == referenceId.Version.Minor) ?
                                        ErrorCode.WRN_UnifyReferenceBldRev : ErrorCode.WRN_UnifyReferenceMajMin;

                    // warning: Assuming assembly reference '{0}' used by '{1}' matches identity '{2}' of '{3}', you may need to supply runtime policy.
                    info = new CSDiagnosticInfo(
                        warning,
                        new object[]
                    {
                        referenceId.GetDisplayName(),
                        ownerAssembly.Name,     // TODO (tomat): should rather be MetadataReference.Display for the corresponding reference
                        definitionId.GetDisplayName(),
                        dependentAssembly.Name
                    },
                        involvedAssemblies,
                        ImmutableArray <Location> .Empty);
                }
                else
                {
                    // unified with a definition whose version is lower than the reference

                    // error: Assembly '{0}' with identity '{1}' uses '{2}' which has a higher version than referenced assembly '{3}' with identity '{4}'
                    info = new CSDiagnosticInfo(
                        ErrorCode.ERR_AssemblyMatchBadVersion,
                        new object[]
                    {
                        ownerAssembly.Name,     // TODO (tomat): should rather be MetadataReference.Display for the corresponding reference
                        ownerAssembly.Identity.GetDisplayName(),
                        referenceId.GetDisplayName(),
                        dependentAssembly.Name,     // TODO (tomat): should rather be MetadataReference.Display for the corresponding reference
                        definitionId.GetDisplayName()
                    },
                        involvedAssemblies,
                        ImmutableArray <Location> .Empty);
                }

                if (MergeUseSiteDiagnostics(ref result, info))
                {
                    return(true);
                }
            }

            return(false);
        }
Exemplo n.º 11
0
        private ImmutableArray<TypeParameterSymbol> LoadTypeParameters(ref DiagnosticInfo diagnosticInfo)
        {
            try
            {
                var moduleSymbol = _containingType.ContainingPEModule;
                var gpHandles = moduleSymbol.Module.GetGenericParametersForMethodOrThrow(_handle);

                if (gpHandles.Count == 0)
                {
                    return ImmutableArray<TypeParameterSymbol>.Empty;
                }
                else
                {
                    var ownedParams = ImmutableArray.CreateBuilder<TypeParameterSymbol>(gpHandles.Count);
                    for (int i = 0; i < gpHandles.Count; i++)
                    {
                        ownedParams.Add(new PETypeParameterSymbol(moduleSymbol, this, (ushort)i, gpHandles[i]));
                    }

                    return ownedParams.ToImmutable();
                }
            }
            catch (BadImageFormatException)
            {
                diagnosticInfo = new CSDiagnosticInfo(ErrorCode.ERR_BindToBogus, this);
                return ImmutableArray<TypeParameterSymbol>.Empty;
            }
        }
        private ImmutableArray<SynthesizedExplicitImplementationForwardingMethod> ComputeInterfaceImplementations(
            DiagnosticBag diagnostics,
            CancellationToken cancellationToken)
        {
            if (this.IsInterface)
            {
                return ImmutableArray<SynthesizedExplicitImplementationForwardingMethod>.Empty;
            }

            var synthesizedImplementations = ArrayBuilder<SynthesizedExplicitImplementationForwardingMethod>.GetInstance();

            // NOTE: We can't iterator over this collection directly, since it is not ordered.  Instead we 
            // iterate over AllInterfaces and filter out the interfaces that are not in this set.  This is 
            // preferable to doing the DFS ourselves because both AllInterfaces and 
            // InterfacesAndTheirBaseInterfaces are cached and used in multiple places.
            ImmutableHashSet<NamedTypeSymbol> interfacesAndTheirBases = this.InterfacesAndTheirBaseInterfacesNoUseSiteDiagnostics;

            foreach (var @interface in this.AllInterfacesNoUseSiteDiagnostics)
            {
                cancellationToken.ThrowIfCancellationRequested();

                if (!interfacesAndTheirBases.Contains(@interface))
                {
                    continue;
                }

                bool? hasImportedBaseTypeDeclaringInterface = null;

                foreach (var interfaceMember in @interface.GetMembersUnordered())
                {
                    cancellationToken.ThrowIfCancellationRequested();

                    // Only require implementations for members that can be implemented in C#.
                    SymbolKind interfaceMemberKind = interfaceMember.Kind;
                    switch (interfaceMemberKind)
                    {
                        case SymbolKind.Method:
                        case SymbolKind.Property:
                        case SymbolKind.Event:
                            if (interfaceMember.IsStatic)
                            {
                                continue;
                            }
                            break;
                        default:
                            continue;
                    }

                    var implementingMemberAndDiagnostics = this.FindImplementationForInterfaceMemberWithDiagnostics(interfaceMember);
                    var implementingMember = implementingMemberAndDiagnostics.Symbol;
                    var synthesizedImplementation = this.SynthesizeInterfaceMemberImplementation(implementingMemberAndDiagnostics, interfaceMember);

                    bool wasImplementingMemberFound = (object)implementingMember != null;

                    if ((object)synthesizedImplementation != null)
                    {
                        synthesizedImplementations.Add(synthesizedImplementation);
                    }

                    if (wasImplementingMemberFound && interfaceMemberKind == SymbolKind.Event)
                    {
                        // NOTE: unlike dev11, we're including a related location for the implementing type, because
                        // otherwise the only error location will be in the containing type of the implementing event
                        // (i.e. no indication of which type's interface list is actually problematic).

                        EventSymbol interfaceEvent = (EventSymbol)interfaceMember;
                        EventSymbol implementingEvent = (EventSymbol)implementingMember;
                        EventSymbol maybeWinRTEvent;
                        EventSymbol maybeRegularEvent;

                        if (interfaceEvent.IsWindowsRuntimeEvent)
                        {
                            maybeWinRTEvent = interfaceEvent; // Definitely WinRT.
                            maybeRegularEvent = implementingEvent; // Maybe regular.
                        }
                        else
                        {
                            maybeWinRTEvent = implementingEvent; // Maybe WinRT.
                            maybeRegularEvent = interfaceEvent; // Definitely regular.
                        }

                        if (interfaceEvent.IsWindowsRuntimeEvent != implementingEvent.IsWindowsRuntimeEvent)
                        {
                            // At this point (and not before), we know that maybeWinRTEvent is definitely a WinRT event and maybeRegularEvent is definitely a regular event.
                            var args = new object[] { implementingEvent, interfaceEvent, maybeWinRTEvent, maybeRegularEvent };
                            var info = new CSDiagnosticInfo(ErrorCode.ERR_MixingWinRTEventWithRegular, args, ImmutableArray<Symbol>.Empty, ImmutableArray.Create<Location>(this.Locations[0]));
                            diagnostics.Add(info, implementingEvent.Locations[0]);
                        }
                    }

                    // Dev10: If a whole property is missing, report the property.  If the property is present, but an accessor
                    // is missing, report just the accessor.

                    var associatedPropertyOrEvent = interfaceMemberKind == SymbolKind.Method ? ((MethodSymbol)interfaceMember).AssociatedSymbol : null;
                    if ((object)associatedPropertyOrEvent == null ||
                        ReportAccessorOfInterfacePropertyOrEvent(associatedPropertyOrEvent) ||
                        (wasImplementingMemberFound && !implementingMember.IsAccessor()))
                    {
                        //we're here because 
                        //(a) the interface member is not an accessor, or 
                        //(b) the interface member is an accessor of an interesting (see ReportAccessorOfInterfacePropertyOrEvent) property or event, or
                        //(c) the implementing member exists and is not an accessor.

                        if (implementingMemberAndDiagnostics.Diagnostics.Any())
                        {
                            diagnostics.AddRange(implementingMemberAndDiagnostics.Diagnostics);
                        }
                        else if (!wasImplementingMemberFound)
                        {
                            // NOTE: An alternative approach would be to keep track of this while searching for the implementing member.
                            // In some cases, we might even be able to stop looking and just accept that a base type has things covered
                            // (though we'd have to be careful about losing diagnostics and we might produce fewer bridge methods).
                            // However, this approach has the advantage that there is no cost unless we encounter a base type that
                            // claims to implement an interface, but we can't figure out how (i.e. free in nearly all cases).
                            hasImportedBaseTypeDeclaringInterface = hasImportedBaseTypeDeclaringInterface ?? HasImportedBaseTypeDeclaringInterface(@interface);

                            // If a base type from metadata declares that it implements the interface, we'll just trust it.
                            // (See fFoundImport in SymbolPreparer::CheckInterfaceMethodImplementation.)
                            if (!hasImportedBaseTypeDeclaringInterface.GetValueOrDefault())
                            {
                                // CONSIDER: Dev10 does not emit this diagnostic for interface properties if the
                                // derived type attempts to implement an accessor directly as a method.

                                // Suppress for bogus properties and events and for indexed properties.
                                if (!interfaceMember.MustCallMethodsDirectly() && !interfaceMember.IsIndexedProperty())
                                {
                                    DiagnosticInfo useSiteDiagnostic = interfaceMember.GetUseSiteDiagnostic();

                                    if (useSiteDiagnostic != null && useSiteDiagnostic.DefaultSeverity == DiagnosticSeverity.Error)
                                    {
                                        diagnostics.Add(useSiteDiagnostic, GetImplementsLocation(@interface));
                                    }
                                    else
                                    {
                                        diagnostics.Add(ErrorCode.ERR_UnimplementedInterfaceMember, GetImplementsLocation(@interface) ?? this.Locations[0], this, interfaceMember);
                                    }
                                }
                            }
                        }
                        else if (interfaceMemberKind == SymbolKind.Method)
                        {
                            // Don't report use site errors on properties - we'll report them on each of their accessors.

                            // Don't report use site errors for implementations in other types unless 
                            // a synthesized implementation is needed that invokes the base method.
                            // We can do so only if there are no use-site errors.

                            if ((object)synthesizedImplementation != null || implementingMember.ContainingType == this)
                            {
                                DiagnosticInfo useSiteDiagnostic = interfaceMember.GetUseSiteDiagnostic();
                                // CAVEAT: don't report ERR_ByRefReturnUnsupported since by-ref return types are 
                                // specifically allowed for the purposes of interface implementation (for C++ interop).
                                // However, if there's a reference to the interface member in source, then we do want
                                // to produce a use site error.
                                if (useSiteDiagnostic != null && (ErrorCode)useSiteDiagnostic.Code != ErrorCode.ERR_ByRefReturnUnsupported)
                                {
                                    // Don't report a use site error with a location in another compilation.  For example,
                                    // if the error is that a base type in another assembly implemented an interface member
                                    // on our behalf and the use site error is that the current assembly does not reference
                                    // some required assembly, then we want to report the error in the current assembly -
                                    // not in the implementing assembly.
                                    Location location = implementingMember.IsFromCompilation(this.DeclaringCompilation)
                                        ? implementingMember.Locations[0]
                                        : this.Locations[0];
                                    Symbol.ReportUseSiteDiagnostic(useSiteDiagnostic, diagnostics, location);
                                }
                            }
                        }
                    }
                }
            }

            return synthesizedImplementations.ToImmutableAndFree();
        }
Exemplo n.º 13
0
        internal override bool GetUnificationUseSiteDiagnostic(ref DiagnosticInfo result, TypeSymbol dependentType)
        {
            AssertReferencesInitialized();

            var ownerModule = this;
            var ownerAssembly = ownerModule.ContainingAssembly;
            var dependentAssembly = dependentType.ContainingAssembly;
            if (ownerAssembly == dependentAssembly)
            {
                return false;
            }

            // TODO (tomat): we should report an error/warning for all unified references, not just the first one.

            foreach (var unifiedAssembly in GetUnifiedAssemblies())
            {
                if (!ReferenceEquals(unifiedAssembly.TargetAssembly, dependentAssembly))
                {
                    continue;
                }

                var referenceId = unifiedAssembly.OriginalReference;
                var definitionId = dependentAssembly.Identity;
                var involvedAssemblies = ImmutableArray.Create<Symbol>(ownerAssembly, dependentAssembly);

                DiagnosticInfo info;
                if (definitionId.Version > referenceId.Version)
                {
                    // unified with a definition whose version is higher than the reference                    
                    ErrorCode warning = (definitionId.Version.Major == referenceId.Version.Major && definitionId.Version.Minor == referenceId.Version.Minor) ?
                                        ErrorCode.WRN_UnifyReferenceBldRev : ErrorCode.WRN_UnifyReferenceMajMin;

                    // warning: Assuming assembly reference '{0}' used by '{1}' matches identity '{2}' of '{3}', you may need to supply runtime policy.
                    info = new CSDiagnosticInfo(
                        warning,
                        new object[]
                        {
                            referenceId.GetDisplayName(),
                            ownerAssembly.Name, // TODO (tomat): should rather be MetadataReference.Display for the corresponding reference
                            definitionId.GetDisplayName(),
                            dependentAssembly.Name
                        },
                        involvedAssemblies,
                        ImmutableArray<Location>.Empty);
                }
                else
                {
                    // unified with a definition whose version is lower than the reference

                    // error: Assembly '{0}' with identity '{1}' uses '{2}' which has a higher version than referenced assembly '{3}' with identity '{4}'
                    info = new CSDiagnosticInfo(
                        ErrorCode.ERR_AssemblyMatchBadVersion,
                        new object[]
                        {
                            ownerAssembly.Name, // TODO (tomat): should rather be MetadataReference.Display for the corresponding reference
                            ownerAssembly.Identity.GetDisplayName(),
                            referenceId.GetDisplayName(),
                            dependentAssembly.Name, // TODO (tomat): should rather be MetadataReference.Display for the corresponding reference
                            definitionId.GetDisplayName()
                        },
                        involvedAssemblies,
                        ImmutableArray<Location>.Empty);
                }

                if (MergeUseSiteDiagnostics(ref result, info))
                {
                    return true;
                }
            }

            return false;
        }
 private static ExtendedErrorTypeSymbol CyclicInheritanceError(RetargetingNamedTypeSymbol type, TypeSymbol declaredBase)
 {
     var info = new CSDiagnosticInfo(ErrorCode.ERR_ImportedCircularBase, declaredBase, type);
     return new ExtendedErrorTypeSymbol(declaredBase, LookupResultKind.NotReferencable, info, true);
 }
Exemplo n.º 15
0
        public override BoundNode VisitAssignmentOperator(BoundAssignmentOperator node)
        {
            BoundExpression originalLeft = node.Left;

            if (originalLeft.Kind != BoundKind.Local)
            {
                return(base.VisitAssignmentOperator(node));
            }

            var leftLocal = (BoundLocal)originalLeft;

            BoundExpression originalRight = node.Right;

#if XSHARP
            if (leftLocal.LocalSymbol.RefKind != RefKind.None &&
                node.IsRef &&
                NeedsProxy(leftLocal.LocalSymbol))
            {
                var info = new CSDiagnosticInfo(ErrorCode.ERR_StaticLocalInCodeBlock, leftLocal.LocalSymbol.Name);
                this.Diagnostics.Add(info, node.Syntax.Location);
                return(node);
            }
#endif

            if (leftLocal.LocalSymbol.RefKind != RefKind.None &&
                node.IsRef &&
                NeedsProxy(leftLocal.LocalSymbol))
            {
                Debug.Assert(!proxies.ContainsKey(leftLocal.LocalSymbol));
                Debug.Assert(originalRight.Kind != BoundKind.ConvertedStackAllocExpression);
                //spilling ref local variables
                throw ExceptionUtilities.Unreachable;
            }

            if (NeedsProxy(leftLocal.LocalSymbol) && !proxies.ContainsKey(leftLocal.LocalSymbol))
            {
                Debug.Assert(leftLocal.LocalSymbol.DeclarationKind == LocalDeclarationKind.None);
                // spilling temp variables
                throw ExceptionUtilities.Unreachable;
            }

            BoundExpression rewrittenLeft  = (BoundExpression)this.Visit(leftLocal);
            BoundExpression rewrittenRight = (BoundExpression)this.Visit(originalRight);
            TypeSymbol      rewrittenType  = VisitType(node.Type);

            // Check if we're assigning the result of stackalloc to a hoisted local.
            // If we are, we need to store the result in a temp local and then assign
            // the value of the local to the field corresponding to the hoisted local.
            // If the receiver of the field is on the stack when the stackalloc happens,
            // popping it will free the memory (?) or otherwise cause verification issues.
            // DevDiv Bugs 59454
            if (rewrittenLeft.Kind != BoundKind.Local && originalRight.Kind == BoundKind.ConvertedStackAllocExpression)
            {
                // From ILGENREC::genAssign:
                // DevDiv Bugs 59454: Handle hoisted local initialized with a stackalloc
                // NOTE: Need to check for cast of stackalloc on RHS.
                // If LHS isLocal, then genAddr is a noop so regular case works fine.

                SyntheticBoundNodeFactory factory = new SyntheticBoundNodeFactory(this.CurrentMethod, rewrittenLeft.Syntax, this.CompilationState, this.Diagnostics);
                BoundAssignmentOperator   tempAssignment;
                BoundLocal tempLocal = factory.StoreToTemp(rewrittenRight, out tempAssignment);

                Debug.Assert(!node.IsRef);
                BoundAssignmentOperator rewrittenAssignment = node.Update(rewrittenLeft, tempLocal, node.IsRef, rewrittenType);

                return(new BoundSequence(
                           node.Syntax,
                           ImmutableArray.Create <LocalSymbol>(tempLocal.LocalSymbol),
                           ImmutableArray.Create <BoundExpression>(tempAssignment),
                           rewrittenAssignment,
                           rewrittenType));
            }

            return(node.Update(rewrittenLeft, rewrittenRight, node.IsRef, rewrittenType));
        }
        // Check if the given symbol can be accessed with the given arity. If OK, return false.
        // If not OK, return true and return a diagnosticinfo. Note that methods with type arguments
        // can be accesses with arity zero due to type inference (but non types).
        private bool WrongArity(Symbol symbol, int arity, out DiagnosticInfo diagInfo)
        {
            switch (symbol.Kind) {
                case SymbolKind.NamedType:
                    NamedTypeSymbol namedType = (NamedTypeSymbol)symbol;
                    if (namedType.Arity != arity) {
                        diagInfo = new CSDiagnosticInfo(ErrorCode.ERR_BadArity, namedType.GetFullName(), namedType.Arity);
                        return true;
                    }
                    break;

                case SymbolKind.Method:
                    if (arity != 0) {
                        MethodSymbol method = (MethodSymbol)symbol;
                        if (method.Arity != arity) {
                            diagInfo = new CSDiagnosticInfo(ErrorCode.ERR_HasNoTypeVars, method.GetFullName());
                            return true;
                        }
                    }
                    break;

                default:
                    if (arity != 0) {
                        diagInfo = new CSDiagnosticInfo(ErrorCode.ERR_TypeArgsNotAllowed, symbol.GetFullName());
                        return true;
                    }
                    break;
            }

            diagInfo = null;
            return false;
        }