/// <summary> /// static void w_object(VALUE obj, struct dump_arg *arg, int limit) /// </summary> /// <param name="obj"></param> public void WriteObject(object obj) { int num; if (this.m_objects.TryGetValue(obj, out num)) { WriteByte(RubyMarshal.Types.Link); WriteLong(num); return; } if (obj == null || obj == FuzzyNil.Instance) { WriteByte(RubyMarshal.Types.Nil); } else if (obj is bool && (bool)obj == true) { WriteByte(RubyMarshal.Types.True); } else if (obj is bool && (bool)obj == false) { WriteByte(RubyMarshal.Types.False); } else if (obj is FuzzyBool && (obj as FuzzyBool).Value) { WriteByte(RubyMarshal.Types.True); } else if (obj is FuzzyBool && !(obj as FuzzyBool).Value) { WriteByte(RubyMarshal.Types.False); } else if (obj is int || obj is long || obj is FuzzyFixnum) { long v; if (obj is int | obj is long) { v = (long)obj; } else { v = (obj as FuzzyFixnum).Value; } // (2**30).class => Bignum // (2**30-1).class => Fixnum // (-2**30-1).class=> Bignum // (-2**30).class => Fixnum if (v <= 1073741823 && v >= -1073741824) { WriteByte(RubyMarshal.Types.Fixnum); WriteLong((int)v); } else { WriteObject(FuzzyBignum.Create(v)); } } else if (obj is FuzzySymbol) { WriteSymbol(obj as FuzzySymbol); } else { FuzzyObject fobj = obj as FuzzyObject; bool hasiv = false; if (fobj != null) { hasiv = (obj as FuzzyObject).InstanceVariables.Count > 0 || fobj.Encoding != null; } var factor = Serialization.Factory <byte[]> .Factor(fobj.GetType()); if (factor != null) { WriteSymbol(fobj.ClassName); factor.dump(m_stream, fobj, null); } if (obj is IRubyUserdefinedMarshalDumpObject) { this.m_objects.Add(obj, this.m_objects.Count); object result = (obj as IRubyUserdefinedMarshalDumpObject).Dump(); if (hasiv) { WriteByte(RubyMarshal.Types.InstanceVariable); } WriteClass(RubyMarshal.Types.UserMarshal, obj, false); WriteObject(result); if (hasiv) { WriteObjectInstanceVariable(fobj); } return; } if (obj is IRubyUserdefinedDumpObject) { byte[] result = (obj as IRubyUserdefinedDumpObject).Dump(); if (hasiv) { WriteByte(RubyMarshal.Types.InstanceVariable); } WriteClass(RubyMarshal.Types.UserDefined, obj, false); WriteBytes(result, result.Length); if (hasiv) { WriteObjectInstanceVariable(fobj); } this.m_objects.Add(obj, this.m_objects.Count); return; } this.m_objects.Add(obj, this.m_objects.Count); if (hasiv) { WriteByte(RubyMarshal.Types.InstanceVariable); } if (obj is FuzzyClass) { WriteByte(RubyMarshal.Types.Class); WriteCString((obj as FuzzyClass).Name); } else if (obj is FuzzyModule) { WriteByte(RubyMarshal.Types.Module); WriteCString((obj as FuzzyModule).Name); } else if (obj is float) { WriteByte(RubyMarshal.Types.Float); WriteFloat((float)obj); } else if (obj is double) { WriteByte(RubyMarshal.Types.Float); WriteFloat((double)obj); } else if (obj is FuzzyFloat) { WriteByte(RubyMarshal.Types.Float); WriteFloat((FuzzyFloat)obj); } else if (obj is FuzzyBignum || obj is FuzzyBignumAdapter) { FuzzyBignum value; if (obj is FuzzyBignumAdapter) { value = (obj as FuzzyBignumAdapter).Value; } else { value = (FuzzyBignum)obj; } char ch; if (value.Sign > 0) { ch = '+'; } else if (value.Sign < 0) { ch = '-'; } else { ch = '0'; } this.m_writer.Write((byte)ch); uint[] words = value.GetWords(); int num2 = words.Length * 2; int index = words.Length - 1; bool flag = false; if ((words.Length > 0) && ((words[index] >> 0x10) == 0)) { num--; flag = true; } this.WriteLong(num2); for (int i = 0; i < words.Length; i++) { if (flag && (i == index)) { this.m_writer.Write((ushort)words[i]); } else { this.m_writer.Write(words[i]); } } } else if (obj is FuzzyString || obj is string) { FuzzyString v; if (obj is string) { v = new FuzzyString(obj as string); } else { v = (FuzzyString)obj; } WriteUserClass(v, FuzzyClass.GetClass("String")); WriteByte(RubyMarshal.Types.String); WriteBytes(v.Raw); } else if (obj is FuzzyRegexp) { FuzzyRegexp v = (FuzzyRegexp)obj; WriteUserClass(obj, FuzzyClass.GetClass("Regexp")); WriteByte(RubyMarshal.Types.Regexp); WriteBytes(v.Pattern.Raw); WriteByte((byte)v.Options); } else if (obj is FuzzyArray || obj is List <object> ) { FuzzyArray v; if (obj is List <object> ) { v = new FuzzyArray(obj as List <object>); } else { v = (FuzzyArray)obj; } WriteUserClass(v, FuzzyClass.GetClass("Array")); WriteByte(RubyMarshal.Types.Array); WriteLong(v.Length); for (int i = 0; i < v.Count; i++) { WriteObject(v[i]); } } else if (obj is FuzzyHash) { FuzzyHash v = (FuzzyHash)obj; WriteUserClass(obj, FuzzyClass.GetClass("Hash")); WriteByte(v.DefaultValue != null ? RubyMarshal.Types.HashWithDefault : RubyMarshal.Types.Hash); WriteLong(v.Length); foreach (KeyValuePair <object, object> item in v) { WriteObject(item.Key); WriteObject(item.Value); } if (v.DefaultValue != null) { WriteObject(v.DefaultValue); } } else if (obj is FuzzyStruct) { FuzzyStruct v = (FuzzyStruct)obj; WriteUserClass(obj, FuzzyClass.GetClass("Struct")); WriteLong(v.InstanceVariables.Count); foreach (KeyValuePair <FuzzySymbol, object> item in v.InstanceVariables) { WriteObject(item.Key); WriteObject(item.Value); } } else if (obj is FuzzyObject) { WriteClass(RubyMarshal.Types.Object, obj, true); WriteObjectInstanceVariable((FuzzyObject)obj); } else { throw new InvalidDataException(string.Format("can't dump {0}", obj.GetType().FullName)); } if (hasiv) { WriteInstanceVariable(fobj, fobj.InstanceVariables); } } }
public void WriteObject(object obj) { int num; if (this.x_objects.TryGetValue(obj, out num)) { WriteNode(XML.Types.Link, num.ToString()); return; } if (obj == null || obj == FuzzyNil.Instance) { WriteNode(XML.Types.Nil, ""); } else if (obj is bool && (bool)obj == true) { WriteNode(XML.Types.True, ""); } else if (obj is bool && (bool)obj == false) { WriteNode(XML.Types.False, ""); } else if (obj is int || obj is long || obj is FuzzyFixnum) { long v; if (obj is FuzzyFixnum) { v = (obj as FuzzyFixnum).Value; } else { v = (long)obj; } if (v <= 1073741823 && v >= -1073741824) { WriteNode(XML.Types.Fixnum, obj.ToString()); } else { WriteObject(FuzzyBignum.Create(v)); } } else if (obj is FuzzySymbol) { WriteSymbol(obj as FuzzySymbol); } else { FuzzyObject fobj = obj as FuzzyObject; bool hasiv = false; if (fobj != null) { hasiv = (obj as FuzzyObject).InstanceVariables.Count > 0 || fobj.Encoding != null; } if (obj is IXMLUserdefinedDumpObject) { this.x_objects.Add(obj, this.x_objects.Count); object result = (obj as IXMLUserdefinedMarshalDumpObject).Dump(); WritePopNode(XML.Types.UserMarshal, ""); WriteObject(result); x_parent_node.Pop(); return; } if (obj is IXMLUserdefinedDumpObject) { XmlNode result = (obj as IXMLUserdefinedDumpObject).Dump(); WritePopNode(XML.Types.UserDefined, "").AppendChild(result); this.x_objects.Add(obj, this.x_objects.Count); return; } this.x_objects.Add(obj, this.x_objects.Count); if (obj is FuzzyClass) { WriteNode(XML.Types.Class, (obj as FuzzyClass).Name); } else if (obj is FuzzyModule) { WriteNode(XML.Types.Module, (obj as FuzzyClass).Name); } else if (obj is float) { WriteFloat((float)obj); } else if (obj is double) { WriteFloat((double)obj); } else if (obj is FuzzyFloat) { WriteFloat((obj as FuzzyFloat).Value); } else if (obj is FuzzyBignum) { WriteNode(XML.Types.Bignum, obj.ToString()); } else if (obj is FuzzyBignumAdapter) { WriteNode(XML.Types.Bignum, (obj as FuzzyBignumAdapter).Value.ToString()); } else if (obj is FuzzyString || obj is string) { FuzzyString v; if (obj is string) { v = new FuzzyString(obj as string); } else { v = (FuzzyString)obj; } WritePopNode(XML.Types.String); WriteString(v.Text, v.Encoding); x_parent_node.Pop(); } else if (obj is FuzzyRegexp) { FuzzyRegexp v = (FuzzyRegexp)obj; WritePopNode(XML.Types.Regexp); WriteString(v.Pattern.Text, v.Pattern.Encoding); WriteNode("Options", ((int)v.Options).ToString()); } else if (obj is FuzzyArray || obj is List <object> ) { FuzzyArray v; if (obj is List <object> ) { v = new FuzzyArray(obj as List <object>); } else { v = (FuzzyArray)obj; } WritePopNode(XML.Types.Array); for (int i = 0; i < v.Count; i++) { WriteObject(v[i]); } x_parent_node.Pop(); } else if (obj is FuzzyHash) { FuzzyHash v = (FuzzyHash)obj; if (v.DefaultValue == null) { WritePopNode(XML.Types.Hash); } else { WritePopNode(XML.Types.HashWithDefault); WritePopNode("Default"); WriteObject(v.DefaultValue); x_parent_node.Pop(); } foreach (KeyValuePair <object, object> item in v) { WriteObject(item.Key); WriteObject(item.Value); } x_parent_node.Pop(); } else if (obj is FuzzyObject || obj is FuzzyStruct) { FuzzyObject v = fobj; if (obj is FuzzyObject) { WritePopNode(XML.Types.Object); } else { WritePopNode(XML.Types.Struct); } if (XML.Options.IgnoreSymbolEncoding) { WriteAttribute("Name", v.ClassName.Name); foreach (KeyValuePair <FuzzySymbol, object> item in v.InstanceVariables) { WritePopNode("Data"); WriteAttribute("Name", item.Key.Name); WriteObject(item.Value); x_parent_node.Pop(); } } else { var factor = Serialization.Factory <XmlNode> .Factor(fobj.GetType()); if (factor == null) { factor = Serialization.Factory <XmlNode> .Factor(fobj.ClassName.Name); } if (factor != null) { WritePopNode(XML.Types.UserDefined); XmlNode node = factor.dump(x_stream, fobj, null); node = x_document.ImportNode(node, true); x_parent_node.Pop().AppendChild(node); } else { WritePopNode("Name"); WriteObject(v.ClassName); x_parent_node.Pop(); foreach (KeyValuePair <FuzzySymbol, object> item in v.InstanceVariables) { WriteSymbol(item.Key); WriteObject(item.Value); } } } x_parent_node.Pop(); } else { throw new InvalidDataException(string.Format("can't dump {0}", obj.GetType().FullName)); } } }