private void EmitDelegateCreation(BoundExpression node, BoundExpression receiver, bool isExtensionMethod, MethodSymbol method, TypeSymbol delegateType, bool used) { var isStatic = receiver == null || (!isExtensionMethod && method.IsStatic); if (!used) { if (!isStatic) { EmitExpression(receiver, false); } return; } // emit the receiver if (isStatic) { _builder.EmitNullConstant(); } else { EmitExpression(receiver, true); if (!receiver.Type.IsVerifierReference()) { EmitBox(receiver.Type, receiver.Syntax); } } // emit method pointer // Metadata Spec (II.14.6): // Delegates shall be declared sealed. // The Invoke method shall be virtual. if (method.IsMetadataVirtual() && !method.ContainingType.IsDelegateType() && !receiver.SuppressVirtualCalls) { // NOTE: method.IsMetadataVirtual -> receiver != null _builder.EmitOpCode(ILOpCode.Dup); _builder.EmitOpCode(ILOpCode.Ldvirtftn); // substitute the method with original virtual method method = method.GetConstructedLeastOverriddenMethod(_method.ContainingType, requireSameReturnType: true); } else { _builder.EmitOpCode(ILOpCode.Ldftn); } EmitSymbolToken(method, node.Syntax, null); // call delegate constructor _builder.EmitOpCode(ILOpCode.Newobj, -1); // pop 2 args and push delegate object var ctor = DelegateConstructor(node.Syntax, delegateType); if ((object)ctor != null) { EmitSymbolToken(ctor, node.Syntax, null); } }
public BoundExpression MethodInfo(MethodSymbol method) { var originalMethod = method.GetConstructedLeastOverriddenMethod(this.CompilationState.Type); return(new BoundMethodInfo( Syntax, originalMethod, GetMethodFromHandleMethod(originalMethod.ContainingType), WellKnownType(Microsoft.CodeAnalysis.WellKnownType.System_Reflection_MethodInfo)) { WasCompilerGenerated = true }); }