Ejemplo n.º 1
0
        public override BoundNode VisitEventAssignmentOperator(BoundEventAssignmentOperator node)
        {
            BoundExpression rewrittenReceiverOpt = VisitExpression(node.ReceiverOpt);
            BoundExpression rewrittenArgument    = VisitExpression(node.Argument);

            if (rewrittenReceiverOpt != null && node.Event.ContainingAssembly.IsLinked && node.Event.ContainingType.IsInterfaceType())
            {
                var @interface = node.Event.ContainingType;

                foreach (var attrData in @interface.GetAttributes())
                {
                    if (attrData.IsTargetAttribute(@interface, AttributeDescription.ComEventInterfaceAttribute) &&
                        attrData.CommonConstructorArguments.Length == 2)
                    {
                        return(RewriteNoPiaEventAssignmentOperator(node, rewrittenReceiverOpt, rewrittenArgument));
                    }
                }
            }

            if (node.Event.IsWindowsRuntimeEvent)
            {
                EventAssignmentKind kind = node.IsAddition ? EventAssignmentKind.Addition : EventAssignmentKind.Subtraction;
                return(RewriteWindowsRuntimeEventAssignmentOperator(node.Syntax, node.Event, kind, node.IsDynamic, rewrittenReceiverOpt, rewrittenArgument));
            }

            var rewrittenArguments = ImmutableArray.Create <BoundExpression>(rewrittenArgument);

            MethodSymbol method = node.IsAddition ? node.Event.AddMethod : node.Event.RemoveMethod;

            return(MakeCall(node.Syntax, rewrittenReceiverOpt, method, rewrittenArguments, node.Type));
        }
Ejemplo n.º 2
0
        public override BoundNode VisitEventAssignmentOperator(BoundEventAssignmentOperator node)
        {
            bool hasBaseReceiver = node.ReceiverOpt != null && node.ReceiverOpt.Kind == BoundKind.BaseReference;

            Binder.ReportDiagnosticsIfObsolete(_diagnostics, node.Event, ((AssignmentExpressionSyntax)node.Syntax).Left, hasBaseReceiver, _containingSymbol, _containingSymbol.ContainingType, BinderFlags.None);
            CheckReceiverIfField(node.ReceiverOpt);
            return(base.VisitEventAssignmentOperator(node));
        }
Ejemplo n.º 3
0
        public override BoundNode VisitEventAssignmentOperator(BoundEventAssignmentOperator node)
        {
            BoundExpression rewrittenReceiverOpt = VisitExpression(node.ReceiverOpt);
            BoundExpression rewrittenArgument    = VisitExpression(node.Argument);

            var rewrittenArguments = ImmutableArray.Create <BoundExpression>(rewrittenArgument);

            MethodSymbol method = node.IsAddition ? node.Event.AddMethod : node.Event.RemoveMethod;

            return(MakeCall(node.Syntax, rewrittenReceiverOpt, method, rewrittenArguments, node.Type));
        }
Ejemplo n.º 4
0
        private BoundExpression RewriteNoPiaEventAssignmentOperator(BoundEventAssignmentOperator node, BoundExpression rewrittenReceiver, BoundExpression rewrittenArgument)
        {
            // In the new NoPIA scenario, myPIA.event += someevent translates into
            //
            // new System.Runtime.InteropServices.ComAwareEventInfo(typeof(myPIA), "event").AddEventHandler(myPIA, someevent)

            BoundExpression result = null;

            SyntaxNode oldSyntax = _factory.Syntax;

            _factory.Syntax = node.Syntax;


            var ctor = _factory.WellKnownMethod(WellKnownMember.System_Runtime_InteropServices_ComAwareEventInfo__ctor);

            if ((object)ctor != null)
            {
                var addRemove = _factory.WellKnownMethod(node.IsAddition ? WellKnownMember.System_Runtime_InteropServices_ComAwareEventInfo__AddEventHandler :
                                                         WellKnownMember.System_Runtime_InteropServices_ComAwareEventInfo__RemoveEventHandler);

                if ((object)addRemove != null)
                {
                    BoundExpression eventInfo = _factory.New(ctor, _factory.Typeof(node.Event.ContainingType), _factory.Literal(node.Event.MetadataName));
                    result = _factory.Call(eventInfo, addRemove,
                                           _factory.Convert(addRemove.Parameters[0].Type.TypeSymbol, rewrittenReceiver),
                                           _factory.Convert(addRemove.Parameters[1].Type.TypeSymbol, rewrittenArgument));
                }
            }

            _factory.Syntax = oldSyntax;

            // The code we just generated doesn't contain any direct references to the event itself,
            // but the com event binder needs the event to exist on the local type. We'll poke the pia reference
            // cache directly so that the event is embedded.
            var module = this.EmitModule;

            if (module != null)
            {
                module.EmbeddedTypesManagerOpt.EmbedEventIfNeedTo(node.Event, node.Syntax, _diagnostics, isUsedForComAwareEventBinding: true);
            }

            if (result != null)
            {
                return(result);
            }

            return(new BoundBadExpression(node.Syntax, LookupResultKind.NotCreatable, ImmutableArray.Create <Symbol>(node.Event),
                                          ImmutableArray.Create(rewrittenReceiver, rewrittenArgument), ErrorTypeSymbol.UnknownResultType));
        }
Ejemplo n.º 5
0
        internal IEventReferenceOperation CreateBoundEventAccessOperation(BoundEventAssignmentOperator boundEventAssignmentOperator)
        {
            SyntaxNode syntax = boundEventAssignmentOperator.Syntax;
            // BoundEventAssignmentOperator doesn't hold on to BoundEventAccess provided during binding.
            // Based on the implementation of those two bound node types, the following data can be retrieved w/o changing BoundEventAssignmentOperator:
            //  1. the type of BoundEventAccess is the type of the event symbol.
            //  2. the constant value of BoundEventAccess is always null.
            //  3. the syntax of the boundEventAssignmentOperator is always AssignmentExpressionSyntax, so the syntax for the event reference would be the LHS of the assignment.
            IEventSymbol @event            = boundEventAssignmentOperator.Event.GetPublicSymbol();
            BoundNode    instance          = boundEventAssignmentOperator.ReceiverOpt;
            SyntaxNode   eventAccessSyntax = ((AssignmentExpressionSyntax)syntax).Left;
            bool         isImplicit        = boundEventAssignmentOperator.WasCompilerGenerated;

            return(new CSharpLazyEventReferenceOperation(this, instance, @event, _semanticModel, eventAccessSyntax, @event.Type, constantValue: null, isImplicit));
        }
Ejemplo n.º 6
0
 public override BoundNode VisitEventAssignmentOperator(BoundEventAssignmentOperator node)
 {
     return this.SetMayHaveSideEffects();
 }
 public override BoundNode VisitEventAssignmentOperator(BoundEventAssignmentOperator node)
 {
     return(this.SetMayHaveSideEffects());
 }