protected static void WriteAmf(Stream stm, object obj) { if (obj == null) { stm.WriteByte((byte)DataType.Null); } else if (obj is byte || obj is int || obj is uint || obj is float || obj is double) { stm.WriteByte((byte)DataType.Number); CDataHelper.BE_WriteDouble(stm, double.Parse(obj.ToString())); } else if (obj is bool) { stm.WriteByte((byte)DataType.Boolean); stm.WriteByte((byte)((bool)obj ? 1 : 0)); } else if (obj is string) { string str = obj as string; int len = Encoding.UTF8.GetByteCount(str); if (len > 0xffff) { stm.WriteByte((byte)DataType.LongString); CDataHelper.BE_WriteLongStr(stm, str); } else { stm.WriteByte((byte)DataType.String); CDataHelper.BE_WriteShortStr(stm, str); } } else if (obj is Array) { stm.WriteByte((byte)DataType.Array); Array ary = obj as Array; CDataHelper.BE_WriteUInt32(stm, (uint)ary.Length); foreach (object o in ary) { WriteAmf(stm, o); } } else if (obj is IDictionary) { stm.WriteByte((byte)DataType.Object); foreach (DictionaryEntry e in obj as IDictionary) { CDataHelper.BE_WriteShortStr(stm, e.Key.ToString()); WriteAmf(stm, e.Value); } CDataHelper.BE_WriteShortStr(stm, ""); // write only a short(0) stm.WriteByte((byte)DataType.EndOfObject); } else { stm.WriteByte((byte)DataType.Unsupported); } }
protected static CNameObjDict ReadHashObject(Stream stm) { CNameObjDict dic = new CNameObjDict(); dic.Position = stm.Position; bool oe = false; while (true) { string key = CDataHelper.BE_ReadShortStr(stm); object value = ReadAmf(stm, ref oe); if (oe) { Trace.Assert(key == ""); break; } dic[key] = value; } return(dic); }
protected static string ReadString(Stream stm, CRefTable rt) { uint head = ReadInt(stm); int len = (int)(head >> 1); if (len <= 0) { return(""); } if (IsRefrence(head)) { return(rt.str[len]); } string str = CDataHelper.ReadUtfStr(stm, len); rt.str.Add(str); return(str); }
protected static object ReadAmf(Stream stm, CRefTable rt) { int type = stm.ReadByte(); switch ((DataType)type) { case DataType.Undefined: return(null); case DataType.Null: return(null); case DataType.False: return(false); case DataType.True: return(true); case DataType.Integer: return(ReadInt(stm)); case DataType.Double: return(CDataHelper.BE_ReadDouble(stm)); case DataType.String: return(ReadString(stm, rt)); case DataType.XmlDoc: break; case DataType.Date: break; case DataType.Array: return(ReadArray(stm, rt)); case DataType.Object: return(ReadHashObject(stm, rt)); case DataType.Xml: break; case DataType.ByteArray: break; default: break; } return(null); }
protected static object ReadAmf(Stream stm, ref bool objEnd) { int type = stm.ReadByte(); bool oe = true; switch ((DataType)type) { case DataType.Number: return(CDataHelper.BE_ReadDouble(stm)); case DataType.Boolean: return(stm.ReadByte() != 0x0); case DataType.String: return(CDataHelper.BE_ReadShortStr(stm)); case DataType.Object: return(ReadHashObject(stm)); case DataType.MovieClip: break; case DataType.Null: return(null); case DataType.Undefined: return(null); case DataType.Reference: break; case DataType.MixedArray: CDataHelper.BE_ReadUInt32(stm); // highest numeric index return(ReadHashObject(stm)); case DataType.EndOfObject: objEnd = true; return(null); case DataType.Array: { uint len = CDataHelper.BE_ReadUInt32(stm); object[] ary = new object[len]; for (uint i = 0; i < len; i++) { ary[i] = ReadAmf(stm, ref oe); } return(ary); } case DataType.Date: break; case DataType.LongString: return(CDataHelper.BE_ReadLongStr(stm)); case DataType.Unsupported: return(null); case DataType.Recordset: break; case DataType.XML: break; case DataType.TypedObject: break; case DataType.AMF3data: return(CAmf3Helper.Read(stm)); default: break; } return(null); }
protected static void WriteAmf(Stream stm, object obj) { if (obj == null) { stm.WriteByte((byte)DataType.Null); } else if (obj is byte || (obj is int && (uint)(int)obj < MaxU29) || (obj is uint && (uint)obj < MaxU29)) { stm.WriteByte((byte)DataType.Integer); WriteInt(stm, uint.Parse(obj.ToString())); } else if (obj is int || obj is uint || obj is float || obj is double) { stm.WriteByte((byte)DataType.Double); CDataHelper.BE_WriteDouble(stm, double.Parse(obj.ToString())); } else if (obj is bool) { if ((bool)obj) { stm.WriteByte((byte)DataType.True); } else { stm.WriteByte((byte)DataType.False); } } else if (obj is string) { stm.WriteByte((byte)DataType.String); WriteString(stm, obj as string); } else if (obj is CMixArray) { stm.WriteByte((byte)DataType.Array); CMixArray ary = obj as CMixArray; uint head = ((uint)ary.FixedLength << 1) | 1; WriteInt(stm, head); foreach (KeyValuePair <string, object> pair in ary.Dynamic) { WriteString(stm, pair.Key); WriteAmf(stm, pair.Value); } WriteString(stm, ""); foreach (object o in ary.Fixed) { WriteAmf(stm, o); } } else if (obj is Array) { stm.WriteByte((byte)DataType.Array); Array ary = obj as Array; uint head = ((uint)ary.Length << 1) | 1; WriteInt(stm, head); WriteString(stm, ""); foreach (object o in ary) { WriteAmf(stm, o); } } else if (obj is IDictionary) { stm.WriteByte((byte)DataType.Object); IDictionary dic = obj as IDictionary; uint head = 0x0B; WriteInt(stm, head); if (obj is CNameObjDict) { WriteString(stm, (obj as CNameObjDict).className); } else { WriteString(stm, ""); } foreach (DictionaryEntry e in obj as IDictionary) { if (e.Key.ToString() == "" && e.Value is string) { continue; } WriteString(stm, e.Key.ToString()); WriteAmf(stm, e.Value); } WriteString(stm, ""); } else { stm.WriteByte((byte)DataType.Undefined); } }