public DebugInfoCompileUnitEntry(
            DebugInfoGenerator debugInfoGenerator,
            ISourceFileEntry entry,
            CollectionMetadata file)
        {
            this.debugInfoGenerator = debugInfoGenerator;

            this.file = file;

            CollectionMetadata enumTypes;
            CollectionMetadata retainedTypes;
            CollectionMetadata subprograms;
            CollectionMetadata globalVariables;
            CollectionMetadata importedEntities;
            this.debugInfoGenerator.DefineCompilationUnit(
                this.file,
                out enumTypes,
                out retainedTypes,
                out subprograms,
                out globalVariables,
                out importedEntities);

            this.enumTypes = enumTypes;
            this.retainedTypes = retainedTypes;
            this.subprograms = subprograms;
            this.globalVariables = globalVariables;
            this.importedEntities = importedEntities;
        }
        public DebugInfoSourceFileEntry(DebugInfoGenerator debugInfoGenerator, string directory, string fileName)
        {
            this.debugInfoGenerator = debugInfoGenerator;

            this.Directory = directory;
            this.FileName = fileName;

            this.file = this.debugInfoGenerator.DefineFile(this);
        }
        public DebugInfoSourceMethodBuilder(DebugInfoGenerator debugInfoGenerator, ISourceMethod method, CollectionMetadata file, CollectionMetadata subprograms)
        {
            this.debugInfoGenerator = debugInfoGenerator;

            CollectionMetadata subroutineTypes;
            CollectionMetadata functionVariables;
            subprograms.Add(this.function = debugInfoGenerator.DefineMethod(method, file, out functionVariables));

            this.functionVariables = functionVariables;
        }
 /// <summary>
 /// Compiles the lambda into a method definition and custom debug information.
 /// </summary>
 /// <param name="method">A <see cref="MethodBuilder"/> which will be used to hold the lambda's IL.</param>
 /// <param name="debugInfoGenerator">Debugging information generator used by the compiler to mark sequence points and annotate local variables.</param>
 public void CompileToMethod(MethodBuilder method, DebugInfoGenerator debugInfoGenerator)
 {
     ContractUtils.RequiresNotNull(debugInfoGenerator, "debugInfoGenerator");
     CompileToMethodInternal(method, debugInfoGenerator);
 }
Example #5
0
 /// <summary></summary>
 public Func <T, bool> Compile(DebugInfoGenerator debugInfoGenerator)
 {
     return(Predicate.Compile(debugInfoGenerator));
 }
Example #6
0
        public IEnumerable <Func <HtmlElement, IEnumerable <HtmlElement> > > CreateHtmlFuncs(string htmlQueryString)
        {
            var elementParam  = Expression.Parameter(typeof(HtmlElement), "HtmlQueryDomElement");
            var keyValueParam = Expression.Parameter(typeof(KeyValuePair <string, IEnumerable <string> >), "HtmlQueryAttribute");
            var valueParam    = Expression.Parameter(typeof(string), "HtmlQueryAttributeValue");

            var expressions = ParseHtmlQuery(elementParam, keyValueParam, valueParam, htmlQueryString);

            foreach (var expression in expressions)
            {
                var expression2 = expression.ToString().Contains("HtmlQueryAttribute")
                                 ? elementParam.CreateKeyValueAnyExpression(
                    PredicateBuilder.EnumerableMethodName.Any,
                    "Attributes",
                    expression,
                    keyValueParam)
                                 : expression;

                var ee =
                    elementParam.CreateElementsWhereExpression <HtmlElement>(
                        PredicateBuilder.EnumerableMethodName.Where,
                        "Descendants",
                        expression2);

                yield return(Expression.Lambda <Func <HtmlElement, IEnumerable <HtmlElement> > >(ee, new[] { elementParam }).Compile(DebugInfoGenerator.CreatePdbGenerator()));
            }
        }
        public void TestMethod1()
        {
            //Expression<Func<IDictionary<string, IEnumerable<string>>, int>> test = attribute => attribute.Count;
            //Expression<Func<KeyValuePair<string, IEnumerable<string>>, int>> asdf = attribute => attribute.;
            //Expression<Func<IEnumerable<string>, int>> lfksjd = att => att.Count();
            //var eParmkeyValueParm2 = Expression.Parameter(typeof(KeyValuePair<string, IEnumerable<string>>));

            var eParm = Expression.Parameter(typeof(HtmlElement));
            var a     = eParm.CreateAnyExpression();

            var elem = new HtmlElement
            {
                Descendants = new List <HtmlElement>
                {
                    new HtmlElement
                    {
                        Attributes = new Dictionary <string, IEnumerable <string> >
                        {
                            { "id", new[] { "ID" } },
                            { "class", new[] { "CLASS" } }
                        }
                    }
                }
            };

            var elem2 = new HtmlElement
            {
                Descendants = new List <HtmlElement>
                {
                    new HtmlElement
                    {
                        Attributes = new Dictionary <string, IEnumerable <string> >()
                    }
                }
            };

            var elem3 = new HtmlElement
            {
                Descendants = new List <HtmlElement>
                {
                    new HtmlElement()
                }
            };

            var elem4 = new HtmlElement
            {
                Descendants = new List <HtmlElement>()
            };

            var elem5 = new HtmlElement
            {
                Descendants = new List <HtmlElement>
                {
                    new HtmlElement
                    {
                        Attributes = new Dictionary <string, IEnumerable <string> >
                        {
                            { "id", new[] { "class" } },
                            { "class", new[] { "id" } }
                        }
                    }
                }
            };

            var keyValueParm = Expression.Parameter(typeof(KeyValuePair <string, IEnumerable <string> >));

            var keyCompareExpression = keyValueParm.CreateStringPropertyCompareExpression(
                "class",
                "Key",
                PredicateBuilder.StringTransform.ToLowerInvariant,
                PredicateBuilder.StringComparison.Equals);

            var valueParm = Expression.Parameter(typeof(string));

            var valueCompareExpression = keyValueParm.CreateStringPropertyCompareExpression(
                "class",
                valueParm,
                PredicateBuilder.StringTransform.ToLowerInvariant,
                PredicateBuilder.StringComparison.Equals);

            var valuesCompareExpression = keyValueParm.CreateKeyValueBoolExpression <string>(
                valueParm,
                valueCompareExpression,
                PredicateBuilder.EnumerableMethodName.Any);

            var attributesCompareExpression = Expression.AndAlso(keyCompareExpression, valuesCompareExpression);

            var parm = Expression.Parameter(typeof(HtmlElement));

            var attributesAnyExpression = parm.CreateKeyValueAnyExpression(
                PredicateBuilder.EnumerableMethodName.Any,
                "Attributes",
                attributesCompareExpression,
                keyValueParm);

            var ee = parm.CreateElementsWhereExpression <HtmlElement>(
                PredicateBuilder.EnumerableMethodName.Where,
                "Descendants",
                attributesAnyExpression);

            var l = Expression.Lambda <Func <HtmlElement, IEnumerable <HtmlElement> > >(ee, new[] { parm }).Compile(DebugInfoGenerator.CreatePdbGenerator());

            Assert.IsTrue(l(elem).Any());
            Assert.IsFalse(l(elem2).Any());
            //Assert.IsFalse(l(elem3).Any());
            //Assert.IsFalse(l(elem4).Any());
            Assert.IsFalse(l(elem5).Any());
        }
Example #8
0
 public static T CompileToMethod <T>(Expression <T> lambda, DebugInfoGenerator debugInfoGenerator, bool emitDebugSymbols)
 {
     return((T)(object)CompileToMethod((LambdaExpression)lambda, debugInfoGenerator, emitDebugSymbols));
 }
Example #9
0
        private static void CompileToMethodInternal(LambdaExpression lambda, MethodBuilder method, DebugInfoGenerator debugInfoGenerator, CompilerOptions options)
        {
            var          compiledLambdas = new List <CompiledLambda>();
            ParsedLambda parsedLambda;
            var          module = method.Module as ModuleBuilder;

            if (module == null)
            {
                throw new ArgumentException("Unable to obtain module builder of the method", "method");
            }
            method.SetReturnType(lambda.ReturnType);
            method.SetParameters(lambda.Parameters.Select(parameter => parameter.Type).ToArray());
            var resolvedLambda = new ExpressionClosureResolver(lambda, module, false, options).Resolve(out parsedLambda);

            if (!string.IsNullOrEmpty(DebugOutputDirectory))
            {
                resolvedLambda = AdvancedDebugViewWriter.WriteToModifying(resolvedLambda, parsedLambda.ConstantsType,
                                                                          parsedLambda.ConstantsParameter, parsedLambda.Constants, GenerateFileName(resolvedLambda));
            }
            if (parsedLambda.ConstantsParameter != null)
            {
                throw new InvalidOperationException("Non-trivial constants are not allowed for compilation to method");
            }
            CompileToMethodInternal(resolvedLambda, debugInfoGenerator, parsedLambda, options, compiledLambdas, method);
        }
Example #10
0
        public static Delegate Compile(LambdaExpression lambda, CompilerOptions options)
        {
            CheckLambdaParameters(lambda);
            CompiledLambda[] subLambdas;
            var debugInfoGenerator = string.IsNullOrEmpty(DebugOutputDirectory) ? null : DebugInfoGenerator.CreatePdbGenerator();

            return(CompileInternal(lambda, debugInfoGenerator, out subLambdas, options));
        }
Example #11
0
 /// <summary>
 /// Compiles the LambdaExpression.
 ///
 /// If the lambda is compiled with emitDebugSymbols, it will be
 /// generated into a TypeBuilder. Otherwise, this method is the same as
 /// calling LambdaExpression.Compile()
 ///
 /// This is a workaround for a CLR limitiation: DynamicMethods cannot
 /// have debugging information.
 /// </summary>
 /// <param name="lambda">the lambda to compile</param>
 /// <param name="emitDebugSymbols">true to generate a debuggable method, false otherwise</param>
 /// <returns>the compiled delegate</returns>
 public static T Compile <T>(this Expression <T> lambda, bool emitDebugSymbols)
 {
     return(emitDebugSymbols ? CompileToMethod(lambda, DebugInfoGenerator.CreatePdbGenerator(), true) : lambda.Compile());
 }
Example #12
0
        public static Type Compile(Type inputElementType, params IFusionOperator[] chain)
        {
            chain = Optimize(chain).ToArray();

            var dbg = DebugInfoGenerator.CreatePdbGenerator();

            var outputElementType = chain.Last().OutputType;

            var asm = AppDomain.CurrentDomain.DefineDynamicAssembly(new AssemblyName("Test"), AssemblyBuilderAccess.RunAndSave);
            var mod = asm.DefineDynamicModule("Artifacts.dll", true);

            var stt = mod.DefineType("<>__Fused01_State", TypeAttributes.Class, typeof(Sink <>).MakeGenericType(outputElementType));

            /* TODO: hoist non-trivial constants to params object passed to ctor
             * var foo = stt.DefineMethod("Foo", MethodAttributes.Public | MethodAttributes.Static, typeof(int), Type.EmptyTypes);
             * var p = new { Age = 21 };
             * Expression<Func<int>> f = Expression.Lambda<Func<int>>(Expression.Property(Expression.Constant(p), "Age"));
             * f.CompileToMethod(foo);
             */

            var sttCtor    = stt.DefineConstructor(MethodAttributes.Public, CallingConventions.Standard, new[] { typeof(IObserver <>).MakeGenericType(outputElementType), typeof(IDisposable) });
            var sttCtorIlg = sttCtor.GetILGenerator();

            sttCtorIlg.Emit(OpCodes.Ldarg_0);
            sttCtorIlg.Emit(OpCodes.Ldarg_1);
            sttCtorIlg.Emit(OpCodes.Ldarg_2);
            sttCtorIlg.Emit(OpCodes.Call, typeof(Sink <>).MakeGenericType(outputElementType).GetConstructors()[0]);
            sttCtorIlg.Emit(OpCodes.Ret);

            var dirty = stt.DefineField("dirty", typeof(bool), FieldAttributes.Public);

            var fldIndex = 0;

            FieldBuilder declareField(Type t) => stt.DefineField("state" + fldIndex++, t, FieldAttributes.Public);

#if HOIST
            var mtdOnNextIndex = 0;
            MethodBuilder declareOnNext(Type t) => stt.DefineMethod("OnNext" + mtdOnNextIndex++, MethodAttributes.Public, typeof(void), new[] { t });

            var mtdOnErrorIndex = 0;
            MethodBuilder declareOnError() => stt.DefineMethod("OnError" + mtdOnErrorIndex++, MethodAttributes.Public, typeof(void), new[] { typeof(Exception) });

            var mtdOnCompletedIndex = 0;
            MethodBuilder declareOnCompleted() => stt.DefineMethod("OnCompleted" + mtdOnCompletedIndex++, MethodAttributes.Public, typeof(void), Type.EmptyTypes);
#endif

            var methods = new Dictionary <MethodBuilder, LambdaExpression>();

            var ctorBlock = new List <Expression>();
            Action <Expression> appendToCtor = ctorBlock.Add;

            var stateParameter = Expression.Parameter(stt);

            var markDirty = Expression.Assign(Expression.Field(stateParameter, dirty), Expression.Constant(true));

            var result     = Expression.Parameter(typeof(IObserver <>).MakeGenericType(outputElementType));
            var disposable = Expression.Parameter(typeof(IDisposable));

            var curOnNext      = default(Func <Expression, Expression>);
            var curOnError     = default(Func <Expression, Expression>);
            var curOnCompleted = default(Expression);

            foreach (var op in chain.Reverse())
            {
                op.Initialize(stateParameter, declareField, appendToCtor, result, disposable);

                var oldOnNext      = curOnNext;
                var oldOnError     = curOnError;
                var oldOnCompleted = curOnCompleted;

#if HOIST
                if ((op.Hoist & HoistOperations.OnNext) != 0)
                {
                    var onNext      = declareOnNext(op.OutputType);
                    var onNextValue = Expression.Parameter(op.OutputType);
                    var onNextMtd   = Expression.Lambda(oldOnNext(onNextValue), onNextValue);
                    methods[onNext] = onNextMtd;

                    // TODO: replace oldOnNext
                }

                if ((op.Hoist & HoistOperations.OnError) != 0)
                {
                    var onError      = declareOnError();
                    var onErrorValue = Expression.Parameter(typeof(Exception));
                    var onErrorMtd   = Expression.Lambda(oldOnError(onErrorValue), onErrorValue);
                    methods[onError] = onErrorMtd;

                    // TODO: replace oldOnError
                }

                if ((op.Hoist & HoistOperations.OnCompleted) != 0)
                {
                    var onCompleted    = declareOnCompleted();
                    var onCompletedMtd = Expression.Lambda(oldOnCompleted);
                    methods[onCompleted] = onCompletedMtd;

                    // TODO: replace oldOnCompleted
                }
#endif

                curOnNext      = op.CreateOnNext(oldOnNext, oldOnError, oldOnCompleted, stateParameter, markDirty);
                curOnError     = op.CreateOnError(oldOnNext, oldOnError, oldOnCompleted, stateParameter, markDirty);
                curOnCompleted = op.CreateOnCompleted(oldOnNext, oldOnError, oldOnCompleted, stateParameter, markDirty);
            }


            var ivOnNextValue = Expression.Parameter(inputElementType);
            var ivOnNextBody  = curOnNext(ivOnNextValue);

            var ivOnErrorValue = Expression.Parameter(typeof(Exception));
            var ivOnErrorBody  = curOnError(ivOnErrorValue);

            var ivOnCompletedBody = curOnCompleted;

            var ivCtorBody = (Expression)Expression.Empty();
            if (ctorBlock.Count > 0)
            {
                ivCtorBody = Expression.Block(ctorBlock.Concat(new[] { ivCtorBody }));
            }


            var stateType = stt.CreateType();


            var stateParameterNew = Expression.Parameter(stateType);

            var subst = new CloseStateParameter(stateParameter, stateParameterNew);

            ivOnNextBody      = subst.Visit(ivOnNextBody);
            ivOnErrorBody     = subst.Visit(ivOnErrorBody);
            ivOnCompletedBody = subst.Visit(ivOnCompletedBody);
            ivCtorBody        = subst.Visit(ivCtorBody);


            var ivOnNext      = Expression.Lambda(ivOnNextBody, stateParameterNew, ivOnNextValue);
            var ivOnError     = Expression.Lambda(ivOnErrorBody, stateParameterNew, ivOnErrorValue);
            var ivOnCompleted = Expression.Lambda(ivOnCompletedBody, stateParameterNew);
            var ivCtor        = Expression.Lambda(ivCtorBody, stateParameterNew, result, disposable);


            var typ = mod.DefineType("<>__Fused01", TypeAttributes.Public, stateType, new[] { typeof(IObserver <>).MakeGenericType(inputElementType) });


            var ivOnNextMtdImpl = typ.DefineMethod("OnNextImpl", MethodAttributes.Private | MethodAttributes.Static, typeof(void), new[] { stateType, inputElementType });
            ivOnNextMtdImpl.SetImplementationFlags(MethodImplAttributes.AggressiveInlining);
            ivOnNext.CompileToMethod(ivOnNextMtdImpl, dbg);

            var ivOnNextMtd = typ.DefineMethod("OnNext", MethodAttributes.Public | MethodAttributes.Virtual, typeof(void), new[] { inputElementType });
            var ivOnNextIlg = ivOnNextMtd.GetILGenerator();
            ivOnNextIlg.Emit(OpCodes.Ldarg_0);
            ivOnNextIlg.Emit(OpCodes.Ldarg_1);
            ivOnNextIlg.EmitCall(OpCodes.Call, ivOnNextMtdImpl, null);
            ivOnNextIlg.Emit(OpCodes.Ret);

            var ivOnErrorMtdImpl = typ.DefineMethod("OnErrorImpl", MethodAttributes.Private | MethodAttributes.Static, typeof(void), new[] { stateType, typeof(Exception) });
            ivOnErrorMtdImpl.SetImplementationFlags(MethodImplAttributes.AggressiveInlining);
            ivOnError.CompileToMethod(ivOnErrorMtdImpl, dbg);

            var ivOnErrorMtd = typ.DefineMethod("OnError", MethodAttributes.Public | MethodAttributes.Virtual, typeof(void), new[] { typeof(Exception) });
            var ivOnErrorIlg = ivOnErrorMtd.GetILGenerator();
            ivOnErrorIlg.Emit(OpCodes.Ldarg_0);
            ivOnErrorIlg.Emit(OpCodes.Ldarg_1);
            ivOnErrorIlg.EmitCall(OpCodes.Call, ivOnErrorMtdImpl, null);
            ivOnErrorIlg.Emit(OpCodes.Ret);

            var ivOnCompletedMtdImpl = typ.DefineMethod("OnCompletedImpl", MethodAttributes.Private | MethodAttributes.Static, typeof(void), new[] { stateType });
            ivOnCompleted.CompileToMethod(ivOnCompletedMtdImpl, dbg);

            var ivOnCompletedMtd = typ.DefineMethod("OnCompleted", MethodAttributes.Public | MethodAttributes.Virtual, typeof(void), Type.EmptyTypes);
            ivOnCompletedMtdImpl.SetImplementationFlags(MethodImplAttributes.AggressiveInlining);
            var ivOnCompletedIlg = ivOnCompletedMtd.GetILGenerator();
            ivOnCompletedIlg.Emit(OpCodes.Ldarg_0);
            ivOnCompletedIlg.EmitCall(OpCodes.Call, ivOnCompletedMtdImpl, null);
            ivOnCompletedIlg.Emit(OpCodes.Ret);

            var ivCtorMtdImpl = typ.DefineMethod(".ctorImpl", MethodAttributes.Private | MethodAttributes.Static, typeof(void), new[] { stateType, result.Type, typeof(IDisposable) });
            ivCtor.CompileToMethod(ivCtorMtdImpl, dbg);

            var ivCtorMtd = typ.DefineConstructor(MethodAttributes.Public, CallingConventions.Standard, new[] { result.Type, typeof(IDisposable) });
            ivCtorMtdImpl.SetImplementationFlags(MethodImplAttributes.AggressiveInlining);
            var ivCtorIlg = ivCtorMtd.GetILGenerator();
            ivCtorIlg.Emit(OpCodes.Ldarg_0);
            ivCtorIlg.Emit(OpCodes.Ldarg_1);
            ivCtorIlg.Emit(OpCodes.Ldarg_2);
            ivCtorIlg.Emit(OpCodes.Call, stateType.GetConstructors()[0]);
            ivCtorIlg.Emit(OpCodes.Ldarg_0);
            ivCtorIlg.Emit(OpCodes.Ldarg_1);
            ivCtorIlg.Emit(OpCodes.Ldarg_2);
            ivCtorIlg.EmitCall(OpCodes.Call, ivCtorMtdImpl, null);
            ivCtorIlg.Emit(OpCodes.Ret);


            var ivt = typ.CreateType();

            asm.Save("Artifacts.dll");

            return(ivt);
        }
 public void CompileToMethod(MethodBuilder method, DebugInfoGenerator debugInfoGenerator)
 {
     CompileToMethod(method);
 }
 /// <summary>
 /// Produces a delegate that represents the lambda expression.
 /// </summary>
 /// <param name="debugInfoGenerator">Debugging information generator used by the compiler to mark sequence points and annotate local variables.</param>
 /// <returns>A delegate containing the compiled version of the lambda.</returns>
 public Delegate Compile(DebugInfoGenerator debugInfoGenerator)
 {
     return(Compile());
 }
 public DebugInfoSymbolWriter(DebugInfoGenerator debugInfoGenerator)
 {
     this.debugInfoGenerator = debugInfoGenerator;
 }
 /// <summary>
 /// Produces a delegate that represents the lambda expression.
 /// </summary>
 /// <param name="debugInfoGenerator">Debugging information generator used by the compiler to mark sequence points and annotate local variables.</param>
 /// <returns>A delegate containing the compiled version of the lambda.</returns>
 public new TDelegate Compile(DebugInfoGenerator debugInfoGenerator)
 {
     ContractUtils.RequiresNotNull(debugInfoGenerator, "debugInfoGenerator");
     return((TDelegate)(object)LambdaCompiler.Compile(this, debugInfoGenerator));
 }
Example #17
0
 public DebugInfoSymbolWriter(DebugInfoGenerator debugInfoGenerator)
 {
     this.debugInfoGenerator = debugInfoGenerator;
 }
Example #18
0
 /// <summary></summary>
 public void CompileToMethod(MethodBuilder method, DebugInfoGenerator debugInfoGenerator)
 {
     Predicate.CompileToMethod(method, debugInfoGenerator);
 }
Example #19
0
        public static TDelegate Compile <TDelegate>(Expression <TDelegate> lambda, CompilerOptions options) where TDelegate : class
        {
            CheckLambdaParameters(lambda);
            CompiledLambda[] subLambdas;
            var debugInfoGenerator = string.IsNullOrEmpty(DebugOutputDirectory) ? null : DebugInfoGenerator.CreatePdbGenerator();

            return((TDelegate)(object)CompileInternal(lambda, debugInfoGenerator, out subLambdas, options));
        }
Example #20
0
 public Delegate Compile(DebugInfoGenerator debugInfoGenerator)
 {
     throw new NotImplementedException();
 }
Example #21
0
 public static void CompileToMethod(LambdaExpression lambda, MethodBuilder method, DebugInfoGenerator debugInfoGenerator, CompilerOptions options)
 {
     CheckLambdaParameters(lambda);
     CompileToMethodInternal(lambda, method, debugInfoGenerator, options);
 }
Example #22
0
 public void CompileToMethod(MethodBuilder method, DebugInfoGenerator debugInfoGenerator)
 {
     throw new NotImplementedException();
 }
Example #23
0
        /// <summary>
        /// Mutates the MethodBuilder parameter, filling in IL, parameters,
        /// and return type.
        ///
        /// (probably shouldn't be modifying parameters/return type...)
        /// </summary>
        internal static void Compile(LambdaExpression lambda, IMethodBuilderForLambdaCompiler method, DebugInfoGenerator debugInfoGenerator)
        {
            // 1. Bind lambda
            AnalyzedTree tree = AnalyzeLambda(ref lambda);

            tree.DebugInfoGenerator = debugInfoGenerator;

            // 2. Create lambda compiler
            LambdaCompiler c = new LambdaCompiler(tree, lambda, method);

            // 3. Emit
            c.EmitLambdaBody();
        }
Example #24
0
        /// <summary>
        /// Creates a lambda compiler that will compile into the provided MethodBuilder
        /// </summary>
        private LambdaCompiler(AnalyzedTree tree, LambdaExpression lambda, MethodBuilder method, DebugInfoGenerator debugInfoGenerator)
        {
            var scope = tree.Scopes[lambda];
            var hasClosureArgument = scope.NeedsClosure;

            Type[] paramTypes = GetParameterTypes(lambda, hasClosureArgument ? typeof(Closure) : null);

            method.SetReturnType(lambda.ReturnType);
            method.SetParameters(paramTypes);
            var parameters = lambda.Parameters;
            // parameters are index from 1, with closure argument we need to skip the first arg
            int startIndex = hasClosureArgument ? 2 : 1;

            for (int i = 0, n = parameters.Count; i < n; i++)
            {
                method.DefineParameter(i + startIndex, ParameterAttributes.None, parameters[i].Name);
            }

            _tree               = tree;
            _lambda             = lambda;
            _typeBuilder        = (TypeBuilder)method.DeclaringType;
            _method             = method;
            _hasClosureArgument = hasClosureArgument;

            _debugInfoGenerator = debugInfoGenerator;
            _ilg = method.GetILGenerator();

            // These are populated by AnalyzeTree/VariableBinder
            _scope          = scope;
            _boundConstants = tree.Constants[lambda];

            InitializeMethod();
        }