Example #1
0
        /// <summary>
        /// Emit a method.
        /// </summary>
        protected virtual void emit(FMethod m)
        {
            string n        = m.m_name;
            bool   isNative = (m.m_flags & FConst.Native) != 0;
            bool   isCtor   = (m.m_flags & FConst.Ctor) != 0;

            // static$init -> .cctor
            // instance$init -> .ctor
            if (n == "static$init")
            {
                emitStaticInit(m); return;
            }
            if (n == "instance$init")
            {
                emitInstanceInit(m); return;
            }

            // handle native/constructor/normal method
            if (isNative)
            {
                new FMethodEmit(this, m).emitNative();
            }
            else if (isCtor)
            {
                new FMethodEmit(this, m).emitCtor();
            }
            else
            {
                new FMethodEmit(this, m).emitStandard();
            }
        }
Example #2
0
        /** 读一个工厂类 */
        public static FactoryClassInfo readFactory(string path)
        {
            string clsStr = FileUtils.readFileForUTF(path);

            FactoryClassInfo re = new FactoryClassInfo();

            re.clsStr     = clsStr;
            re.startIndex = clsStr.IndexOf('{') + 1;

            Regex reg1 = new Regex("public (virtual|override) (.*?) create(.*?)\\(\\)");
            Regex reg2 = new Regex("return new (.*?)\\(\\);");

            Match match1 = reg1.Match(clsStr);
            Match match2 = reg2.Match(clsStr);

            while (match1.Success)
            {
                FMethod method = new FMethod();
                method.isOverride = match1.Groups[1].Value.Equals("override");
                method.name       = match1.Groups[3].Value;
                method.returnType = match1.Groups[2].Value;
                method.useClsName = match2.Groups[1].Value;

                re.toAddMethod(method);

                match1 = match1.NextMatch();
                match2 = match2.NextMatch();
            }

            return(re);
        }
Example #3
0
        protected override void emit(FMethod m)
        {
            string name = m.m_name;

            if (name == "static$init")
            {
                emitStaticInit(m); cctorEmit = true; return;
            }

            new FMethodEmit(this, m).emitMixinBody();
        }
Example #4
0
            public void toAddMethod(FMethod method)
            {
                //有了
                if (methodDic.contains(method.name))
                {
                    return;
                }

                methodList.add(method);
                methodDic.put(method.name, method);
            }
Example #5
0
        protected virtual void emitInstanceInit(FMethod m)
        {
            hasInstanceInit = true;
            PERWAPI.CILInstructions code = ctor.CreateCodeBuffer();

            // initalize code to call super
            code.Inst(PERWAPI.Op.ldarg_0);

            // if closure, push FuncType static field
            if (funcType != null)
            {
                code.FieldInst(PERWAPI.FieldOp.ldsfld, typeField);
                PERWAPI.Method baseCtor = emitter.findMethod(baseClassName, ".ctor",
                                                             new string[] { "Fan.Sys.FuncType" }, "System.Void");
                baseCtor.AddCallConv(PERWAPI.CallConv.Instance); // if stub, make sure instance callconv
                code.MethInst(PERWAPI.MethodOp.call, baseCtor);
            }
            else
            {
                PERWAPI.Method baseCtor = emitter.findMethod(baseClassName, ".ctor",
                                                             new string[0], "System.Void");
                baseCtor.AddCallConv(PERWAPI.CallConv.Instance); // if stub, make sure instance callconv
                code.MethInst(PERWAPI.MethodOp.call, baseCtor);
            }

            // make peer
            if (isNative)
            {
                //code.op(ALOAD_0);  // for putfield
                //code.op(DUP);      // for arg to make
                //code.op2(INVOKESTATIC, method(selfName + "Peer.make(L" + className + ";)L" + className + "Peer;"));
                //code.op2(PUTFIELD, peerField.ref());

                code.Inst(PERWAPI.Op.ldarg_0);
                code.Inst(PERWAPI.Op.dup);
                PERWAPI.Method peerMake = emitter.findMethod(className + "Peer", "make",
                                                             new string[] { className }, className + "Peer");
                code.MethInst(PERWAPI.MethodOp.call, peerMake);
                code.FieldInst(PERWAPI.FieldOp.stfld, peerField);
            }

            if (m == null)
            {
                code.Inst(PERWAPI.Op.ret);
            }
            else
            {
                new FCodeEmit(this, m, code).emit();
            }
        }
Example #6
0
        //////////////////////////////////////////////////////////////////////////
        // Constructor
        //////////////////////////////////////////////////////////////////////////

        public FCodeEmit(FTypeEmit parent, FMethod fmethod, CILInstructions code)
            : this(parent, fmethod.m_code, code,
                   initRegs(parent.pod, fmethod.isStatic(), fmethod.m_vars),
                   parent.pod.typeRef(fmethod.m_ret))
        {
            this.fmethod    = fmethod;
            this.vars       = fmethod.m_vars;
            this.isStatic   = (fmethod.m_flags & FConst.Static) != 0;
            this.paramCount = fmethod.m_paramCount;
            if (!isStatic)
            {
                paramCount++;
            }
        }
Example #7
0
        //////////////////////////////////////////////////////////////////////////
        // Overrides
        //////////////////////////////////////////////////////////////////////////

        protected override void emitInstanceInit(FMethod m)
        {
            hasInstanceInit = true;

            // make peer
            if (isNative)
            {
                throw new System.Exception("No native support for Err subclasses");
            }

            // stub ctor2
            PERWAPI.MethodDef ctor2 = emitter.findMethod(selfName, ".ctor",
                                                         new string[] { "Fan.Sys.Err/Val" }, "System.Void") as PERWAPI.MethodDef;
            ctor2.SetMethAttributes(
                PERWAPI.MethAttr.Public |
                PERWAPI.MethAttr.HideBySig |
                PERWAPI.MethAttr.SpecialRTSpecialName);
            ctor2.AddCallConv(PERWAPI.CallConv.Instance);

            // no arg constructor -> calls this(Err/Val)
            PERWAPI.CILInstructions code = ctor.CreateCodeBuffer();
            code.Inst(PERWAPI.Op.ldarg_0);
            PERWAPI.Method valctor = emitter.findMethod(className + "/Val", ".ctor", new string[0], "System.Void");
            code.MethInst(PERWAPI.MethodOp.newobj, valctor);
            code.MethInst(PERWAPI.MethodOp.call, ctor2);
            code.Inst(PERWAPI.Op.ret);

            // arg constructor with Err$Val (and init implementation)
            code = ctor2.CreateCodeBuffer();
            code.Inst(PERWAPI.Op.ldarg_0);
            code.Inst(PERWAPI.Op.ldarg_1);
            PERWAPI.Method baseCtor = emitter.findMethod(baseClassName, ".ctor",
                                                         new string[] { "Fan.Sys.Err/Val" }, "System.Void");
            baseCtor.AddCallConv(PERWAPI.CallConv.Instance); // if stub, make sure instance callconv
            code.MethInst(PERWAPI.MethodOp.call, baseCtor);
            if (m == null)
            {
                //code.maxLocals = 2;
                //code.maxStack  = 2;
                code.Inst(PERWAPI.Op.ret);
            }
            else
            {
                // e.code.maxLocals++;  // alloc room for Val extra argument
                new FCodeEmit(this, m, code).emit();
            }
        }
Example #8
0
        /// <summary>
        /// Map fcode method to a sys::Method.
        /// </summary>
        private Method map(FPod fpod, FMethod m)
        {
            string name                = String.Intern(m.m_name);
            Type   returnType          = m_pod.findType(m.m_ret);
            Type   inheritedReturnType = m_pod.findType(m.m_inheritedRet);
            List   pars                = new List(Sys.ParamType, m.m_paramCount);

            for (int j = 0; j < m.m_paramCount; j++)
            {
                FMethodVar p      = m.m_vars[j];
                int        pflags = (p.def == null) ? 0 : Param.HAS_DEFAULT;
                pars.add(new Param(String.Intern(p.name), m_pod.findType(p.type), pflags));
            }
            Facets facets = Facets.mapFacets(m_pod, m.m_attrs.m_facets);

            return(new Method(this, name, m.m_flags, facets, m.m_attrs.m_lineNum, returnType, inheritedReturnType, pars));
        }
Example #9
0
        internal void emitStaticInit(FMethod m)
        {
            // make sure we add local defs
            if (m != null && m.m_localCount > 0)
            {
                PERWAPI.Local[] locals = new PERWAPI.Local[m.m_vars.Length];
                for (int i = 0; i < locals.Length; i++)
                {
                    string name = m.m_vars[i].name;
                    string type = nname(m.m_vars[i].type);
                    locals[i] = new PERWAPI.Local(name, emitter.findType(type));
                }
                cctor.AddLocals(locals, true);
            }

            hasStaticInit = true;
            PERWAPI.CILInstructions code = cctor.CreateCodeBuffer();

            // set $Type field with type (if we this is a closure,
            // then the FuncType will be the type exposed)
            if (!parent.isMixin())
            {
                Type t = parent;
                if (parent.@base() is FuncType)
                {
                    t = parent.@base();
                }

                code.ldstr(t.signature());
                PERWAPI.Method findType = emitter.findMethod("Fan.Sys.Type", "find",
                                                             new string[] { "System.String" }, "Fan.Sys.Type");
                code.MethInst(PERWAPI.MethodOp.call, findType);
                code.FieldInst(PERWAPI.FieldOp.stsfld, typeField);
            }

            if (m == null)
            {
                code.Inst(PERWAPI.Op.ret);
            }
            else
            {
                new FCodeEmit(this, m, code).emit();
            }
        }
Example #10
0
        //////////////////////////////////////////////////////////////////////////
        // Constructor
        //////////////////////////////////////////////////////////////////////////

        /// <summary>
        /// Constructor.
        /// </summary>
        public FMethodEmit(FTypeEmit emit, FMethod method)
        {
            this.emitter    = emit.emitter;
            this.emit       = emit;
            this.method     = method;
            this.code       = method.m_code;
            this.name       = FanUtil.toDotnetMethodName(method.m_name);
            this.paramLen   = method.m_paramCount;
            this.isStatic   = (method.m_flags & FConst.Static) != 0;
            this.isInternal = false; //(method.m_flags & FConst.Internal) != 0;
            this.isPrivate  = (method.m_flags & FConst.Private) != 0;
            this.isAbstract = (method.m_flags & FConst.Abstract) != 0;
            this.isVirtual  = (method.m_flags & FConst.Virtual) != 0;
            this.isOverride = (method.m_flags & FConst.Override) != 0;
            this.isCtor     = (method.m_flags & FConst.Ctor) != 0;
            this.isNative   = (method.m_flags & FConst.Native) != 0;
            this.isHide     = false; // only used for make/make_
            this.ret        = emit.pod.typeRef(method.m_inheritedRet);
            this.selfName   = emit.selfName;
        }
Example #11
0
            /** 添加方法 */
            public FMethod addMethod(string type, string mark)
            {
                bool   isOverride = false;
                string name       = type;
                string rType      = type;

                if (mark != "" && type.StartsWith(mark))
                {
                    string last  = type.Substring(1);
                    string first = last[0].ToString();

                    //首字母是大写的
                    if (first == first.ToUpper())
                    {
                        name = last;

                        FMethod pMethod = parentMethodDic.get(last);

                        if (pMethod != null)
                        {
                            rType      = pMethod.returnType;
                            isOverride = true;
                        }
                    }
                }

                FMethod method = new FMethod();

                method.name       = name;
                method.returnType = rType;
                method.isOverride = isOverride;
                method.useClsName = type;

                toAddMethod(method);

                return(method);
            }
Example #12
0
 protected override void emit(FMethod m)
 {
     new FMethodEmit(this, m).emitMixinInterface();
 }