////////////////////////////////////////////////////////////////////////// // Emit ////////////////////////////////////////////////////////////////////////// public static void emit(Emitter emitter, FPod pod) { //FPodEmit emit = new FPodEmit(pod); TypeAttr tattr = TypeAttr.Public | TypeAttr.Sealed; FieldAttr fattr = FieldAttr.Public | FieldAttr.Static; emitter.emitClass("System.Object", FanUtil.toDotnetTypeName(pod.m_podName, "$Pod", false), new string[0], tattr); pod.readLiterals(); // generate constant fields other types will reference, we don't // initialize them, rather we do that later via reflection for (int i=0; i<pod.m_literals.m_ints.size(); i++) emitter.emitField("I" + i, "System.Int64", fattr); for (int i=0; i<pod.m_literals.m_floats.size(); i++) emitter.emitField("F" + i, "System.Double", fattr); for (int i=0; i<pod.m_literals.m_decimals.size(); i++) emitter.emitField("D" + i, "Fan.Sys.BigDecimal", fattr); for (int i=0; i<pod.m_literals.m_strs.size(); i++) emitter.emitField("S" + i, "System.String", fattr); for (int i=0; i<pod.m_literals.m_durations.size(); i++) emitter.emitField("Dur" + i, "Fan.Sys.Duration", fattr); for (int i=0; i<pod.m_literals.m_uris.size(); i++) emitter.emitField("U" + i, "Fan.Sys.Uri", fattr); }
/// /// Dump to the specified print writer. /// public void dump(FPod pod, TextWriter writer) { for (int i=0; i<m_size; i++) { writer.Write(StrUtil.padr(" [" + i + "] ", 8)); writer.WriteLine(toString(i)); } writer.Flush(); }
public FTable m_uris; // Uri literals #endregion Fields #region Constructors ////////////////////////////////////////////////////////////////////////// // Constructor ////////////////////////////////////////////////////////////////////////// public FLiterals(FPod fpod) { this.m_fpod = fpod; this.m_ints = new FTable.Ints(fpod); this.m_floats = new FTable.Floats(fpod); this.m_decimals = new FTable.Decimals(fpod); this.m_strs = new FTable.Strs(fpod); this.m_durations = new FTable.Durations(fpod); this.m_uris = new FTable.Uris(fpod); }
////////////////////////////////////////////////////////////////////////// // Load ////////////////////////////////////////////////////////////////////////// public static System.Type load(System.Reflection.Assembly assembly, FPod pod) { System.Type type = null; string name = FanUtil.toDotnetTypeName(pod.m_podName, "$Pod", false); //if (Sys.usePrecompiledOnly) // type = System.Type.GetType(name); //else type = assembly.GetType(name); initFields(pod, type); return type; }
public FCodeEmit(FTypeEmit parent, FBuf fcode, CILInstructions code, Reg[] regs, FTypeRef ret) { this.pod = parent.pod; this.emitter = parent.emitter; this.parent = parent; this.buf = fcode.m_buf; this.len = fcode.m_len; this.code = code; this.podClass = FanUtil.toDotnetTypeName(pod.m_podName, "$Pod", false); this.jumps = new Jumps(code); this.regs = regs; this.ret = ret; }
private static void initFields(FPod pod, System.Type type) { FLiterals literals = pod.readLiterals(); for (int i=0; i<literals.m_ints.size(); i++) type.GetField("I"+i).SetValue(null, literals.m_ints.get(i)); for (int i=0; i<literals.m_floats.size(); i++) type.GetField("F"+i).SetValue(null, literals.m_floats.get(i)); for (int i=0; i<literals.m_decimals.size(); i++) type.GetField("D"+i).SetValue(null, literals.m_decimals.get(i)); for (int i=0; i<literals.m_strs.size(); i++) type.GetField("S"+i).SetValue(null, literals.m_strs.get(i)); for (int i=0; i<literals.m_durations.size(); i++) type.GetField("Dur"+i).SetValue(null, literals.m_durations.get(i)); for (int i=0; i<literals.m_uris.size(); i++) type.GetField("U"+i).SetValue(null, literals.m_uris.get(i)); }
internal FieldRefs(FPod pod) : base(pod) { }
internal Uris(FPod pod) : base(pod) { }
internal Strs(FPod pod) : base(pod) { }
public Input(FPod fpod, Stream baseStream) { this.bs = baseStream; this.fpod = fpod; }
public int m_self; // self typeRef index #endregion Fields #region Constructors ////////////////////////////////////////////////////////////////////////// // Constructor ////////////////////////////////////////////////////////////////////////// public FType(FPod pod) { this.m_pod = pod; }
internal MethodRefs(FPod pod) : base(pod) { }
////////////////////////////////////////////////////////////////////////// // Constructor ////////////////////////////////////////////////////////////////////////// public FCodePrinter(FPod pod) : this(pod, Console.OpenStandardOutput()) { }
internal Decimals(FPod pod) : base(pod) { }
internal Durations(FPod pod) : base(pod) { }
public FPrinter(FPod pod, Stream stream) : base(stream) { this.pod = pod; }
////////////////////////////////////////////////////////////////////////// // Constructor ////////////////////////////////////////////////////////////////////////// internal Pod(FPod fpod) { this.m_name = fpod.m_podName; load(fpod); }
////////////////////////////////////////////////////////////////////////// // Constructor ////////////////////////////////////////////////////////////////////////// protected FTable(FPod pod) { this.m_pod = pod; }
internal Floats(FPod pod) : base(pod) { }
public static Assembly emitPod(FPod pod, bool load, string path) { string podName = pod.m_podName; Assembly assembly = (Assembly)assemblies[podName]; if (assembly == null) { Emitter emitter = new Emitter(podName, path); // unzip the native.dll if one exists unzipToTemp(pod, podName + "Native_.dll"); unzipToTemp(pod, podName + "Native_.pdb"); // emit the pod class itself (which declares all constants) //FPodEmit.EmitAndLoad(emitter, pod); FPodEmit.emit(emitter, pod); // the Emitter needs base types to be defined before // descendant types, so make sure everything gets stubbed // out in the correct order ahead of time for (int i=0; i<pod.m_types.Length; i++) emitter.findType(pod.nname(pod.m_types[i].m_self)); // emit all the rest of the types in this pod for (int i=0; i<pod.m_types.Length; i++) { FType ftype = pod.m_types[i]; FTypeRef tref = ftype.m_pod.typeRef(ftype.m_self); Type parent = Type.find(tref.podName+"::"+tref.typeName, true); // make sure we have reflected to setup slots parent.reflect(); // route based on type if ((ftype.m_flags & FConst.Mixin) != 0) { // interface FMixinInterfaceEmit iemit = new FMixinInterfaceEmit(emitter, parent, ftype); iemit.emit(); // body class FMixinBodyEmit bemit = new FMixinBodyEmit(emitter, parent, ftype); bemit.emit(); ftypes[ftype] = new FTypeEmit[] { iemit, bemit }; } else if (parent.@is(Sys.ErrType)) { // error FErrEmit emitErr = new FErrEmit(emitter, parent, ftype); emitErr.emit(); FErrValEmit emitErrVal = new FErrValEmit(emitter, parent, ftype); emitErrVal.emit(); ftypes[ftype] = new FTypeEmit[] { emitErr, emitErrVal }; } else { // class FClassEmit emit = new FClassEmit(emitter, parent, ftype); emit.emit(); ftypes[ftype] = new FTypeEmit[] { emit }; } } // commit assembly byte[] buf = emitter.commit(); if (load) { //long start = System.Environment.TickCount; // load assembly assembly = (buf == null) ? Assembly.LoadFile(emitter.fileName) : Assembly.Load(buf); assemblies[podName] = assembly; //long end = System.Environment.TickCount; //System.Console.WriteLine("load " + podName + " in " + (end-start) + " ms"); // load $Pod type FPodEmit.load(assembly, pod); } } return assembly; }
public FCodePrinter(FPod pod, Stream stream) : base(stream) { this.m_pod = pod; }
/// <summary> /// Map fcode field to a sys::Field. /// </summary> private Field map(FPod fpod, FField f) { string name = String.Intern(f.m_name); Type fieldType = m_pod.findType(f.m_type); Facets facets = Facets.mapFacets(m_pod, f.m_attrs.m_facets); return new Field(this, name, f.m_flags, facets, f.m_attrs.m_lineNum, fieldType); }
internal Ints(FPod pod) : base(pod) { }
/// <summary> /// Map to .NET register info for the given Fantom local variables. /// </summary> internal static Reg[] initRegs(FPod pod, bool isStatic, FMethodVar[] vars) { Reg[] regs = new Reg[isStatic ? vars.Length : vars.Length+1]; int nindex = 0; for (int i=0; i<regs.Length; ++i) { Reg r = new Reg(); if (i == 0 && !isStatic) { // this pointer r.stackType = FTypeRef.OBJ; r.nindex = nindex; ++nindex; } else { FTypeRef typeRef = pod.typeRef(vars[isStatic ? i : i - 1].type); r.stackType = typeRef.stackType; r.nindex = nindex; nindex += 1; //nindex += typeRef.isWide() ? 2 : 1; } regs[i] = r; } return regs; }
private static Hashtable ftypes = new Hashtable(); // ftype[] lookup #endregion Fields #region Constructors ////////////////////////////////////////////////////////////////////////// // Constructor ////////////////////////////////////////////////////////////////////////// protected FTypeEmit(Emitter emitter, Type parent, FType type) { this.emitter = emitter; this.parent = parent; this.pod = type.m_pod; this.type = type; }
/// <summary> /// Unzip the file if it exists into the lib/tmp dir /// </summary> static void unzipToTemp(FPod pod, string filename) { if (pod.m_store == null) return; // compiled from script ZipEntry entry = pod.m_store.zipFile.GetEntry(filename); if (entry == null) return; BufferedStream fin = new BufferedStream(pod.m_store.zipFile.GetInputStream(entry)); FileStream fout = System.IO.File.Create( FileUtil.combine(Fan.Sys.Sys.m_homeDir, "lib", "tmp", filename)); byte[] b = new byte[4096]; while (true) { int r = fin.Read(b, 0, b.Length); if (r <= 0) break; fout.Write(b, 0, r); } fout.Flush(); fin.Close(); fout.Close(); }
/// <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); }
internal Names(FPod pod) : base(pod) { }
internal TypeRefs(FPod pod) : base(pod) { }
////////////////////////////////////////////////////////////////////////// // Stub ////////////////////////////////////////////////////////////////////////// public static void stub(string podName, DirectoryInfo outDir, bool verbose) { writeLine(" .NET Stub [" + podName + "]"); string fanHome = SysProps.getProperty("fan.home"); string podPath = fanHome + "\\lib\\fan\\" + podName + ".pod"; string target = new FileInfo(outDir + "\\" + podName + ".dll").FullName; if (verbose) { writeLine(" <- " + podPath); Pod pod = Pod.doFind(podName, true, null); List list = pod.types(); string pre = "Fan." + FanUtil.upper(podName) + "."; for (int i=0; i<list.sz(); i++) writeLine(" " + pre + (list.get(i) as Type).name()); writeLine(" -> " + target); } FStore store = new FStore(new ZipFile(podPath)); FPod fpod = new FPod(podName, store); fpod.read(); FTypeEmit.emitPod(fpod, false, target); }