示例#1
0
        internal void EmitLetFnInits(CljILGen ilg, LocalBuilder localBuilder, ObjExpr objx, IPersistentSet letFnLocals)
        {
            if (TypeBuilder != null)
            {
                // Full compile
                ilg.Emit(OpCodes.Castclass, TypeBuilder);

                for (ISeq s = RT.keys(Closes); s != null; s = s.next())
                {
                    LocalBinding lb = (LocalBinding)s.first();
                    if (letFnLocals.contains(lb))
                    {
                        ClosedOverFieldsMap.TryGetValue(lb, out FieldBuilder fb);

                        Type primt = lb.PrimitiveType;
                        ilg.Emit(OpCodes.Dup);  // this
                        if (primt != null)
                        {
                            objx.EmitUnboxedLocal(ilg, lb);
                            ilg.MaybeEmitVolatileOp(IsVolatile(lb));
                            ilg.Emit(OpCodes.Stfld, fb);
                        }
                        else
                        {
                            objx.EmitLocal(ilg, lb);
                            ilg.MaybeEmitVolatileOp(IsVolatile(lb));
                            ilg.Emit(OpCodes.Stfld, fb);
                        }
                    }
                }
                ilg.Emit(OpCodes.Pop);
            }
        }
示例#2
0
        internal void EmitAssignLocal(CljILGen ilg, LocalBinding lb, Expr val)
        {
            if (!IsMutable(lb))
                throw new ArgumentException("Cannot assign to non-mutable: ", lb.Name);

            FieldBuilder fb = null;
            bool hasField = ClosedOverFieldsMap.TryGetValue(lb, out fb);

            ilg.Emit(OpCodes.Ldarg_0);  // this

            Type primt = lb.PrimitiveType;
            if (primt != null)
            {
                MaybePrimitiveExpr mbe = val as MaybePrimitiveExpr;
                if (!(mbe != null && mbe.CanEmitPrimitive))
                    throw new ArgumentException("Must assign primitive to primitive mutable", lb.Name);
                mbe.EmitUnboxed(RHC.Expression, this, ilg);

            }
            else
            {
                val.Emit(RHC.Expression, this, ilg);
            }

            if (hasField)
            {
                ilg.MaybeEmitVolatileOp(IsVolatile(lb));
                ilg.Emit(OpCodes.Stfld, fb);
            }
            else
                ilg.Emit(OpCodes.Stloc, lb.LocalVar);
        }