/// <summary>
        /// Gets place of PHP <c>$this</c> variable.
        /// </summary>
        public virtual IPlace GetPhpThisVariablePlace(PEModuleBuilder module = null)
        {
            var thisPlace = GetThisPlace();

            if (thisPlace != null)
            {
                if (this.IsGeneratorMethod())
                {
                    // $this ~ arg1
                    thisPlace = new ArgPlace(thisPlace.Type, 1);
                }
                else if (this.ContainingType.IsTraitType())
                {
                    // $this ~ this.<>this
                    thisPlace = new FieldPlace(thisPlace, ((SourceTraitTypeSymbol)this.ContainingType).RealThisField, module);
                }

                //
                return(thisPlace);
            }
            else
            {
                return(null);
            }
        }
        void EmitPhpCallable(Emit.PEModuleBuilder module, DiagnosticBag diagnostics)
        {
            var __invoke = TryGetMagicInvoke();

            if (__invoke == null ||
                IsAlreadyImplemented(__invoke) ||
                IsAlreadyImplemented(DeclaringCompilation.CoreTypes.IPhpCallable))
            {
                // already implemented in a base class
                return;
            }

            //
            // IPhpCallable.Invoke(Context <ctx>, PhpVaue[] arguments)
            //
            var invoke = new SynthesizedMethodSymbol(this, "IPhpCallable.Invoke", false, true, DeclaringCompilation.CoreTypes.PhpValue, isfinal: false)
            {
                ExplicitOverride = (MethodSymbol)DeclaringCompilation.CoreTypes.IPhpCallable.Symbol.GetMembers("Invoke").Single(),
                ForwardedCall    = __invoke,
            };

            invoke.SetParameters(
                new SpecialParameterSymbol(invoke, DeclaringCompilation.CoreTypes.Context, SpecialParameterSymbol.ContextName, 0),
                new SynthesizedParameterSymbol(invoke, ArrayTypeSymbol.CreateSZArray(ContainingAssembly, DeclaringCompilation.CoreTypes.PhpValue.Symbol), 1, RefKind.None, name: "arguments", isParams: true));

            module.SetMethodBody(invoke, MethodGenerator.GenerateMethodBody(module, invoke, il =>
            {
                var cg = new CodeGenerator(il, module, diagnostics, module.Compilation.Options.OptimizationLevel, false, this, new ParamPlace(invoke.Parameters[0]), new ArgPlace(this, 0))
                {
                    CallerType = this,
                };

                cg.EmitRet(cg.EmitForwardCall(__invoke, invoke, callvirt: true));
            }, null, diagnostics, false));

            module.SynthesizedManager.AddMethod(this, invoke);

            //
            // IPhpCallable.ToPhpValue()
            //
            var tophpvalue = new SynthesizedMethodSymbol(this, "IPhpCallable.ToPhpValue", false, true, DeclaringCompilation.CoreTypes.PhpValue, isfinal: false)
            {
                ExplicitOverride = (MethodSymbol)DeclaringCompilation.CoreTypes.IPhpCallable.Symbol.GetMembers("ToPhpValue").Single(),
            };

            //
            module.SetMethodBody(tophpvalue, MethodGenerator.GenerateMethodBody(module, tophpvalue, il =>
            {
                var thisPlace = new ArgPlace(this, 0);
                var ctxPlace  = new FieldPlace(thisPlace, this.ContextStore, module);
                var cg        = new CodeGenerator(il, module, diagnostics, module.Compilation.Options.OptimizationLevel, false, this, ctxPlace, thisPlace);

                // return PhpValue.FromClass(this)
                cg.EmitThis();
                cg.EmitRet(cg.EmitCall(ILOpCode.Call, cg.CoreMethods.PhpValue.FromClass_Object));
            }, null, diagnostics, false));

            module.SynthesizedManager.AddMethod(this, tophpvalue);
        }
示例#3
0
        void EmitTraitImplementations(Emit.PEModuleBuilder module)
        {
            foreach (var t in TraitUses)
            {
                foreach (var m in t.GetMembers().OfType <SynthesizedMethodSymbol>())
                {
                    Debug.Assert(m.ForwardedCall != null);

                    module.SetMethodBody(m, MethodGenerator.GenerateMethodBody(module, m, il =>
                    {
                        IPlace thisPlace          = null;
                        IPlace traitInstancePlace = null;
                        IPlace ctxPlace;

                        if (m.IsStatic)
                        {
                            // Template: return TRAIT.method(...)
                            Debug.Assert(SpecialParameterSymbol.IsContextParameter(m.Parameters[0]));
                            ctxPlace = new ParamPlace(m.Parameters[0]);
                        }
                        else
                        {
                            // Template: return this.<>trait.method(...)
                            thisPlace          = new ArgPlace(this, 0);                                   // this
                            ctxPlace           = new FieldPlace(thisPlace, this.ContextStore, module);    // this.<ctx>
                            traitInstancePlace = new FieldPlace(thisPlace, t.TraitInstanceField, module); // this.<>trait
                        }

                        using (var cg = new CodeGenerator(il, module, DiagnosticBag.GetInstance(), module.Compilation.Options.OptimizationLevel, false, this, ctxPlace, thisPlace)
                        {
                            CallerType = this,
                        })
                        {
                            var forwarded_type = cg.EmitForwardCall(m.ForwardedCall, m, thisPlaceExplicit: traitInstancePlace);
                            var target_type    = m.ReturnType;

                            cg.EmitConvert(forwarded_type, 0, target_type); // always (forwarded_type === target_type)
                            cg.EmitRet(target_type);
                        }
                    }, null, DiagnosticBag.GetInstance(), false));
                    module.SynthesizedManager.AddMethod(this, m);

                    // NOTE: following is not needed anymore:
                    //// ghost stubs: // ... resolve this already in SourceTypeSymbol.GetMembers(), now it does not get overloaded properly
                    //var ps = m.Parameters;
                    //for (int i = 0; i < ps.Length; i++)
                    //{
                    //    if (ps[i].HasUnmappedDefaultValue())  // => ConstantValue couldn't be resolved for optional parameter
                    //    {
                    //        // create ghost stub foo(p0, .. pi-1) => foo(p0, .. , pN)
                    //        GhostMethodBuilder.CreateGhostOverload(m, module, DiagnosticBag.GetInstance(), i);
                    //    }
                    //}
                }
            }
        }
        void EmitToString(Emit.PEModuleBuilder module)
        {
            if (this.IsInterface || this.IsTrait)
            {
                return;
            }

            var __tostring = this.GetMembersByPhpName(SpecialMethodNames.Tostring.Value).OfType <MethodSymbol>().FirstOrDefault();

            if (__tostring != null)    // implement ToString if: there is __toString() function
            {
                // lookup base string ToString()
                var overriden = this.LookupMember <MethodSymbol>(
                    WellKnownMemberNames.ObjectToString,
                    m => OverrideHelper.SignaturesMatch(m, (MethodSymbol)DeclaringCompilation.GetSpecialTypeMember(SpecialMember.System_Object__ToString)));

                Debug.Assert(overriden != null);

                if (overriden == null || overriden.IsSealed || overriden.ContainingType == this)
                {
                    // cannot be overriden
                    return;
                }

                // public sealed override string ToString()
                var tostring = new SynthesizedMethodSymbol(this, WellKnownMemberNames.ObjectToString, false, true, DeclaringCompilation.CoreTypes.String, Accessibility.Public, isfinal: false, phphidden: true)
                {
                    ExplicitOverride = overriden,
                    ForwardedCall    = __tostring,
                };

                module.SetMethodBody(tostring, MethodGenerator.GenerateMethodBody(module, tostring, il =>
                {
                    var thisPlace = new ArgPlace(this, 0);
                    var cg        = new CodeGenerator(il, module, DiagnosticBag.GetInstance(), module.Compilation.Options.OptimizationLevel, false, this, new FieldPlace(thisPlace, this.ContextStore, module), thisPlace);

                    if (__tostring != null)
                    {
                        // __tostring().ToString()
                        cg.EmitConvert(cg.EmitForwardCall(__tostring, tostring, callvirt: true), 0, tostring.ReturnType);
                    }
                    else
                    {
                        // PhpException.ObjectToStringNotSupported(this)
                        cg.EmitThis();
                        cg.EmitPop(cg.EmitCall(ILOpCode.Call, cg.CoreTypes.PhpException.Method("ObjectToStringNotSupported", cg.CoreTypes.Object)));

                        // return ""
                        cg.Builder.EmitStringConstant(string.Empty);
                    }
                    cg.EmitRet(tostring.ReturnType);
                }, null, DiagnosticBag.GetInstance(), false));
                module.SynthesizedManager.AddMethod(this, tostring);
            }
        }
示例#5
0
        void EmitTraitImplementations(Emit.PEModuleBuilder module)
        {
            foreach (var t in TraitUses)
            {
                foreach (var m in t.GetMembers().OfType <SynthesizedMethodSymbol>())
                {
                    Debug.Assert(m.ForwardedCall != null);

                    module.SetMethodBody(m, MethodGenerator.GenerateMethodBody(module, m, il =>
                    {
                        IPlace thisPlace          = null;
                        IPlace traitInstancePlace = null;
                        IPlace ctxPlace;

                        if (m.IsStatic)
                        {
                            // Template: return TRAIT.method(...)
                            Debug.Assert(SpecialParameterSymbol.IsContextParameter(m.Parameters[0]));
                            ctxPlace = new ParamPlace(m.Parameters[0]);
                        }
                        else
                        {
                            // Template: return this.<>trait.method(...)
                            thisPlace          = new ArgPlace(this, 0);                                   // this
                            ctxPlace           = new FieldPlace(thisPlace, this.ContextStore, module);    // this.<ctx>
                            traitInstancePlace = new FieldPlace(thisPlace, t.TraitInstanceField, module); // this.<>trait
                        }

                        using (var cg = new CodeGenerator(il, module, DiagnosticBag.GetInstance(), module.Compilation.Options.OptimizationLevel, false, this, ctxPlace, thisPlace)
                        {
                            CallerType = this,
                        })
                        {
                            var forwarded_type = cg.EmitForwardCall(m.ForwardedCall, m, thisPlaceExplicit: traitInstancePlace);
                            var target_type    = m.ReturnType;

                            cg.EmitConvert(forwarded_type, 0, target_type); // always (forwarded_type === target_type)
                            cg.EmitRet(target_type);
                        }
                    }, null, DiagnosticBag.GetInstance(), false));
                    module.SynthesizedManager.AddMethod(this, m);
                }
            }
        }
示例#6
0
        void EmitToString(Emit.PEModuleBuilder module)
        {
            if (this.IsInterface || this.IsTrait)
            {
                return;
            }

            var __tostring = this.GetMembers(SpecialMethodNames.Tostring.Value, true).OfType <MethodSymbol>().FirstOrDefault();

            if (__tostring != null || this.Syntax.BaseClass == null)    // implement ToString if: there is __tostring() function or ToString is not overriden yet
            {
                // public override string ToString()
                // Note, there might be two ToString methods with same parameters only differing by their return type, CLR allows that
                var tostring = new SynthesizedMethodSymbol(this, "ToString", false, true, DeclaringCompilation.CoreTypes.String, Accessibility.Public, isfinal: false)
                {
                    ExplicitOverride = (MethodSymbol)DeclaringCompilation.GetSpecialTypeMember(SpecialMember.System_Object__ToString),
                    ForwardedCall    = __tostring,
                };

                module.SetMethodBody(tostring, MethodGenerator.GenerateMethodBody(module, tostring, il =>
                {
                    var thisPlace = new ArgPlace(this, 0);
                    var cg        = new CodeGenerator(il, module, DiagnosticBag.GetInstance(), module.Compilation.Options.OptimizationLevel, false, this, new FieldPlace(thisPlace, this.ContextStore, module), thisPlace);

                    if (__tostring != null)
                    {
                        // __tostring().ToString()
                        cg.EmitConvert(cg.EmitForwardCall(__tostring, tostring, callvirt: true), 0, tostring.ReturnType);
                    }
                    else
                    {
                        // PhpException.ObjectToStringNotSupported(this)
                        cg.EmitThis();
                        cg.EmitPop(cg.EmitCall(ILOpCode.Call, cg.CoreTypes.PhpException.Method("ObjectToStringNotSupported", cg.CoreTypes.Object)));

                        // return ""
                        cg.Builder.EmitStringConstant(string.Empty);
                    }
                    cg.EmitRet(tostring.ReturnType);
                }, null, DiagnosticBag.GetInstance(), false));
                module.SynthesizedManager.AddMethod(this, tostring);
            }
        }
示例#7
0
        void EmitPhpCallable(Emit.PEModuleBuilder module, DiagnosticBag diagnostics)
        {
            var __invoke = TryGetMagicInvoke();

            if (__invoke == null || __invoke.OverriddenMethod != null)
            {
                return;
            }

            //
            // IPhpCallable.Invoke(Context, PhpVaue[])
            //
            var invoke = new SynthesizedMethodSymbol(this, "IPhpCallable.Invoke", false, true, DeclaringCompilation.CoreTypes.PhpValue, isfinal: false)
            {
                ExplicitOverride = (MethodSymbol)DeclaringCompilation.CoreTypes.IPhpCallable.Symbol.GetMembers("Invoke").Single(),
            };

            invoke.SetParameters(
                new SpecialParameterSymbol(invoke, DeclaringCompilation.CoreTypes.Context, SpecialParameterSymbol.ContextName, 0),
                new SynthesizedParameterSymbol(invoke, ArrayTypeSymbol.CreateSZArray(ContainingAssembly, DeclaringCompilation.CoreTypes.PhpValue.Symbol), 1, RefKind.None, "arguments"));

            module.SetMethodBody(invoke, MethodGenerator.GenerateMethodBody(module, invoke, il =>
            {
                var cg = new CodeGenerator(il, module, diagnostics, OptimizationLevel.Release, false, this, new ParamPlace(invoke.Parameters[0]), new ArgPlace(this, 0));

                var argsplace    = new ParamPlace(invoke.Parameters[1]);
                var args_element = ((ArrayTypeSymbol)argsplace.TypeOpt).ElementType;
                var ps           = __invoke.Parameters;

                // Template: this.__invoke(args[0], args[1], ...)

                cg.EmitThis();

                for (int i = 0; i < ps.Length; i++)
                {
                    var p = ps[i];

                    // LOAD args[i]
                    // Template: (i < args.Length) ? (T)args[i] : default(T)

                    var lbldefault = new NamedLabel("args_default");
                    var lblend     = new NamedLabel("args_end");

                    cg.Builder.EmitIntConstant(i);  // <i>
                    argsplace.EmitLoad(cg.Builder); // <args>
                    cg.EmitArrayLength();           // .Length
                    cg.Builder.EmitBranch(ILOpCode.Bge, lbldefault);

                    // (T)args[i]
                    if (p.IsImplicitlyDeclared)
                    {
                        throw new NotImplementedException();
                    }
                    else if (p.Type == cg.CoreTypes.PhpAlias)
                    {
                        // args[i].EnsureAlias()
                        argsplace.EmitLoad(cg.Builder);          // <args>
                        cg.Builder.EmitIntConstant(i);           // <i>
                        cg.Builder.EmitOpCode(ILOpCode.Ldelema); // ref args[i]
                        cg.EmitSymbolToken(args_element, null);
                        cg.EmitCall(ILOpCode.Call, cg.CoreMethods.PhpValue.EnsureAlias);
                    }
                    else
                    {
                        // (T)args[i]
                        argsplace.EmitLoad(cg.Builder);         // <args>
                        cg.Builder.EmitIntConstant(i);          // <i>
                        cg.Builder.EmitOpCode(ILOpCode.Ldelem); // args[i]
                        cg.EmitSymbolToken(args_element, null);
                        cg.EmitConvert(args_element, 0, p.Type);
                    }

                    cg.Builder.EmitBranch(ILOpCode.Br, lblend);

                    // default(T)
                    cg.Builder.MarkLabel(lbldefault);
                    cg.EmitParameterDefaultValue(p);

                    //
                    cg.Builder.MarkLabel(lblend);
                }

                cg.EmitCall(ILOpCode.Callvirt, __invoke);
                cg.EmitRet(invoke.ReturnType);
            }, null, diagnostics, false));

            module.SynthesizedManager.AddMethod(this, invoke);

            //
            // IPhpCallable.ToPhpValue()
            //
            var tophpvalue = new SynthesizedMethodSymbol(this, "IPhpCallable.ToPhpValue", false, true, DeclaringCompilation.CoreTypes.PhpValue, isfinal: false)
            {
                ExplicitOverride = (MethodSymbol)DeclaringCompilation.CoreTypes.IPhpCallable.Symbol.GetMembers("ToPhpValue").Single(),
            };

            //
            module.SetMethodBody(tophpvalue, MethodGenerator.GenerateMethodBody(module, tophpvalue, il =>
            {
                var thisPlace = new ArgPlace(this, 0);
                var cg        = new CodeGenerator(il, module, diagnostics, OptimizationLevel.Release, false, this, new FieldPlace(thisPlace, this.ContextStore), thisPlace);

                // return PhpValue.FromClass(this)
                cg.EmitThis();
                cg.EmitRet(cg.EmitCall(ILOpCode.Call, cg.CoreMethods.PhpValue.FromClass_Object));
            }, null, diagnostics, false));

            module.SynthesizedManager.AddMethod(this, tophpvalue);
        }
        /// <summary>
        /// Emits initializers of all parameter's non-standard default values (such as PhpArray)
        /// within the type's static .cctor
        /// </summary>
        private void EmitParametersDefaultValue(PEModuleBuilder module, DiagnosticBag diagnostics)
        {
            foreach (var p in this.SourceParameters)
            {
                var field = p.DefaultValueField;
                if (field is SynthesizedFieldSymbol)
                {
                    Debug.Assert(p.Initializer != null);

                    module.SynthesizedManager.AddField(field.ContainingType, field);

                    // .cctor() {

                    var cctor = module.GetStaticCtorBuilder(field.ContainingType);
                    lock (cctor)
                    {
                        SynthesizedMethodSymbol func = null;

                        if (field.Type.Is_Func_Context_PhpValue())  // Func<Context, PhpValue>
                        {
                            // private static PhpValue func(Context) => INITIALIZER()
                            func = new SynthesizedMethodSymbol(field.ContainingType, field.Name + "Func", isstatic: true, isvirtual: false, DeclaringCompilation.CoreTypes.PhpValue, isfinal: true);
                            func.SetParameters(new SynthesizedParameterSymbol(func, DeclaringCompilation.CoreTypes.Context, 0, RefKind.None, name: SpecialParameterSymbol.ContextName));

                            //
                            module.SetMethodBody(func, MethodGenerator.GenerateMethodBody(module, func, il =>
                            {
                                var ctxPlace = new ArgPlace(DeclaringCompilation.CoreTypes.Context, 0);
                                var cg       = new CodeGenerator(il, module, diagnostics, module.Compilation.Options.OptimizationLevel, false, field.ContainingType, ctxPlace, null)
                                {
                                    CallerType                = ContainingType,
                                    ContainingFile            = ContainingFile,
                                    IsInCachedArrayExpression = true,   // do not cache array initializers twice
                                };

                                // return {Initializer}
                                cg.EmitConvert(p.Initializer, func.ReturnType);
                                cg.EmitRet(func.ReturnType);
                            }, null, diagnostics, false));

                            module.SynthesizedManager.AddMethod(func.ContainingType, func);
                        }

                        using (var cg = new CodeGenerator(cctor, module, diagnostics, module.Compilation.Options.OptimizationLevel, false, field.ContainingType,
                                                          contextPlace: null,
                                                          thisPlace: null)
                        {
                            CallerType = ContainingType,
                            ContainingFile = ContainingFile,
                            IsInCachedArrayExpression = true,   // do not cache array initializers twice
                        })
                        {
                            var fldplace = new FieldPlace(null, field, module);
                            fldplace.EmitStorePrepare(cg.Builder);
                            if (func == null)
                            {
                                // {field} = {Initializer};
                                cg.EmitConvert(p.Initializer, field.Type);
                            }
                            else
                            {
                                MethodSymbol funcsymbol = func;

                                // bind func in case it is generic
                                if (func.ContainingType is SourceTraitTypeSymbol st)
                                {
                                    funcsymbol = func.AsMember(st.Construct(st.TypeArguments));
                                }

                                // Func<,>(object @object, IntPtr method)
                                var func_ctor = ((NamedTypeSymbol)field.Type).InstanceConstructors.Single(m =>
                                                                                                          m.ParameterCount == 2 &&
                                                                                                          m.Parameters[0].Type.SpecialType == SpecialType.System_Object &&
                                                                                                          m.Parameters[1].Type.SpecialType == SpecialType.System_IntPtr
                                                                                                          );

                                // {field} = new Func<Context, PhpValue>( {func} )
                                cg.Builder.EmitNullConstant();                                                                         // null
                                cg.EmitOpCode(ILOpCode.Ldftn);                                                                         // method
                                cg.Builder.EmitToken(module.Translate(funcsymbol, null, cg.Diagnostics, false), null, cg.Diagnostics); // !! needDeclaration: false
                                cg.EmitCall(ILOpCode.Newobj, func_ctor);
                            }
                            fldplace.EmitStore(cg.Builder);
                        }
                    }
                }
            }
        }
        void EmitDisposable(Emit.PEModuleBuilder module, DiagnosticBag diagnostics)
        {
            var __destruct = TryGetDestruct();

            if (__destruct == null ||
                IsAlreadyImplemented(__destruct) ||
                IsAlreadyImplemented(DeclaringCompilation.GetSpecialType(SpecialType.System_IDisposable)))
            {
                // already implemented in a base class
                return;
            }

            //
            // IDisposable.Dispose()
            //
            var dispose = new SynthesizedMethodSymbol(this, "IDisposable.Dispose", false, true, DeclaringCompilation.GetSpecialType(SpecialType.System_Void), isfinal: true)
            {
                ExplicitOverride = (MethodSymbol)DeclaringCompilation.GetSpecialTypeMember(SpecialMember.System_IDisposable__Dispose),
                ForwardedCall    = __destruct,
            };

            module.SetMethodBody(dispose, MethodGenerator.GenerateMethodBody(module, dispose, il =>
            {
                var thisPlace = new ArgPlace(this, 0);
                var ctxPlace  = new FieldPlace(thisPlace, this.ContextStore, module);
                var cg        = new CodeGenerator(il, module, diagnostics, module.Compilation.Options.OptimizationLevel, false, this, ctxPlace, thisPlace)
                {
                    CallerType = this,
                };

                // private bool <>b_disposed;
                var disposedField = cg.Module.SynthesizedManager.GetOrCreateSynthesizedField(this, DeclaringCompilation.CoreTypes.Boolean, WellKnownPchpNames.SynthesizedDisposedFieldName, Accessibility.Private, false, false, false);
                var disposedPlace = new FieldPlace(thisPlace, disposedField, cg.Module);

                // if (<>b_disposed) return;
                var lblContinue = new object();
                disposedPlace.EmitLoad(cg.Builder);
                cg.Builder.EmitBranch(ILOpCode.Brfalse, lblContinue);
                cg.EmitRet(DeclaringCompilation.CoreTypes.Void);
                cg.Builder.MarkLabel(lblContinue);

                // <>b_disposed = true;
                disposedPlace.EmitStorePrepare(cg.Builder);
                cg.Builder.EmitBoolConstant(true);
                disposedPlace.EmitStore(cg.Builder);

                // __destruct()
                cg.EmitPop(cg.EmitForwardCall(__destruct, dispose, callvirt: true));

                // .ret
                cg.EmitRet(DeclaringCompilation.GetSpecialType(SpecialType.System_Void));
            }, null, diagnostics, false));

            module.SynthesizedManager.AddMethod(this, dispose);

            ////
            //// Finalize()
            ////
            //var finalize = new SynthesizedFinalizeSymbol(this)
            //{
            //    ForwardedCall = dispose,
            //};

            //Debug.Assert(finalize.OverriddenMethod != null);

            //module.SetMethodBody(finalize, MethodGenerator.GenerateMethodBody(module, finalize, il =>
            //{
            //    var thisPlace = new ArgPlace(this, 0);
            //    var ctxPlace = new FieldPlace(thisPlace, this.ContextStore, module);
            //    var cg = new CodeGenerator(il, module, diagnostics, module.Compilation.Options.OptimizationLevel, false, this, ctxPlace, thisPlace)
            //    {
            //        CallerType = this,
            //    };

            //    //
            //    cg.Builder.OpenLocalScope(ScopeType.TryCatchFinally);
            //    // try {
            //    cg.Builder.OpenLocalScope(ScopeType.Try);

            //    // Dispose()
            //    cg.EmitPop(cg.EmitForwardCall(dispose, finalize, callvirt: false));
            //    //if (cg.EmitPdbSequencePoints) cg.Builder.EmitOpCode(ILOpCode.Nop);

            //    // }
            //    cg.Builder.CloseLocalScope();
            //    // finally {
            //    cg.Builder.OpenLocalScope(ScopeType.Finally);

            //    // base.Finalize()
            //    thisPlace.EmitLoad(cg.Builder);
            //    cg.EmitCall(ILOpCode.Call, finalize.ExplicitOverride);
            //    //if (cg.EmitPdbSequencePoints) cg.Builder.EmitOpCode(ILOpCode.Nop);

            //    // }
            //    cg.Builder.CloseLocalScope();
            //    cg.Builder.CloseLocalScope();

            //    // .ret
            //    cg.EmitRet(DeclaringCompilation.GetSpecialType(SpecialType.System_Void));

            //}, null, diagnostics, false));

            //module.SynthesizedManager.AddMethod(this, finalize);
        }