/// <summary> /// deconstructs objects that inhert ISerializable /// </summary> /// <returns></returns> private static BinaryBuilder SeriObjDeconstructor(ISerializable obj) { SerializationInfo info = new SerializationInfo(obj.GetType(), new FormatterConverter()); StreamingContext context = new StreamingContext(StreamingContextStates.All); obj.GetObjectData(info, context); var node = info.GetEnumerator(); BinaryBuilder byteBuilder = new BinaryBuilder(); byteBuilder.Append(serializerEntry); ///Object Type Change byteBuilder.Append(info.ObjectType.AssemblyQualifiedName); byteBuilder.Append(equals); ///Object Type Change while (node.MoveNext()) { //bytebuilder adds to itself the new byte arrays, no need to assign byteBuilder.Append(startClass + node.Name + typeEntry + node.ObjectType.ToString() + equals + Deconstruction(node.Value) + endClass); //stringBuilder.Append(startClass + node.Name + typeEntry + node.ObjectType + equals + Deconstruct(node.Value) + endClass); } byteBuilder.Append(serializerExit); return(byteBuilder); }
private static BinaryBuilder ListObjDeconstructor(IList list) { BinaryBuilder objGraph = new BinaryBuilder(); //TODO: ADD A WAY TO COUNT MEMEBERS AND AVOID NULL sends //THIS IS A BIG NONO (spent too much on to find these issue) //IF ANOTHER UNSOLVALBE ISSUE RAISES LISTS ARE YOUR FIRST WARNING if (list.GetType().IsArray) { //if (list is List<byte>) // return ((List<byte>)list).ToArray(); objGraph.Append(list.Count.ToString()); if (list is byte[]) { objGraph.Append(startEnum); objGraph.Append((byte[])list); objGraph.Append(endEnum); return(objGraph); } } objGraph.Append(startEnum); foreach (var member in list) { if (member == null) //Don't add to the list, { //objGraph.Append(nullObj + betweenEnum); //No sending nulls continue; } objGraph.Append(Deconstruction(member) + endClass); //between Enum is like endclass } objGraph.Append(endEnum); return(objGraph); }
private static object GetValue(Type objType, ref byte[] dataInfo, ref int location) { BinaryBuilder valueStr = GetSection(ref dataInfo, endClass, ref location); valueStr = valueStr == nullObj ? null : valueStr; //if the value is null, set it to null return(BinaryBuilder.ByteToPrimitive(objType, valueStr)); }
public static byte[] Deconstruct(object obj) { BinaryBuilder builder = new BinaryBuilder(); byte[] result = (startClass + obj.GetType().AssemblyQualifiedName + equals + Deconstruction(obj) + endClass); //Console.WriteLine("Binary Formatter Decompression: " + result.Length); return(result); //must delcare the type at first so the constructor later on knows with what type it deals //the properties and fields can be aligned later on by using the first type, like a puzzle //the name of the object doesn't matter (therefore doesn't need to be saved) as well since the it will be changed anyways }
public BinaryBuilder Append(BinaryBuilder obj) { list.AddRange(obj.list); return(this); BinaryBuilder hello = new BinaryBuilder("Hello "); byte[] world = BinaryBuilder.StrToBytes("World"); byte[] helloWorld = hello + world; BinaryBuilder result = helloWorld; Console.WriteLine(result); //Hello world }
/// <summary> /// This method will get the dataInfo and rescue the required section /// from the beginning of the dataInfo string until it encounters the given operation /// </summary> /// <param name="dataInfo">The operation</param> /// <param name="syntax">Object graph</param> /// <returns>The required section</returns> private static BinaryBuilder GetSection(ref byte[] dataInfo, byte[] syntax, ref int location) { BinaryBuilder sectionByte = new BinaryBuilder(); for (int i = location; i < dataInfo.Length; i++) { if (CheckHitOperator(dataInfo, syntax, ref location)) //when the program gets to "=" it continues { break; } sectionByte.Append(dataInfo[i]); location += 1; } location += syntax.Length; return(sectionByte); }
private static BinaryBuilder Deconstruction(object obj) { if (obj == null) { return(nullObj); } if (obj.GetType().IsPrimitive || obj is string) { return(BinaryBuilder.PrimitiveToByte(obj)); } if (!obj.GetType().IsSerializable) //PROTECTION { return(new byte[0]); //don't touch the field, CONSIDER: throwing an error } else if (obj is ISerializable) { return(SeriObjDeconstructor((ISerializable)obj)); } if (obj is IList) //string is also an enum but will never reach here thanks to the primitive check { return(ListObjDeconstructor((IList)obj)); } var fields = obj.GetType().GetFields(bindingFlags); BinaryBuilder objGraph = new BinaryBuilder(); #region SpecialCases /*Special cases so far: * 1. Object is null (Done) * 2. Object points to itself in an infnite loop (Done) * 3. backingField (Done) * 4. Object is an enum/list/array (Done) */ #endregion foreach (var field in fields) { //the field is a field class, the fieldValue is the value of this field (the actual object) //for examle field is "int num = 5" and the field value is the 5 if (field.IsNotSerialized) //PROTECTION { continue; //Don't touch the object, was meant to not be serialized } object fieldValue = field.GetValue(obj); if (fieldValue == null) //No sending nulls { continue; //Null object, ignore. spares the text in the writing } if (fieldValue == obj) { throw new StackOverflowException("An object points to itself"); //Will cause an infinite loop, so just throw it } //BACKING FIELDS ARE IGNORED BECAUSE THE PROPERTIES LINE SAVES THEM INSTEAD //one of the few compiler generated attributes is backing fields //backing field is a proprty with a get and set only, which has a hidden field behind it //instead we save this field in the properties if (Attribute.GetCustomAttribute(field, typeof(CompilerGeneratedAttribute)) == null) //this line checks for backing field { objGraph.Append(startClass + field.Name + equals + Deconstruction(fieldValue) + endClass); } else { objGraph.Append(startClass + GetNameOfBackingField(field.Name) + equals + Deconstruction(fieldValue) + endClass); } } return(objGraph); }
public BinaryBuilder(BinaryBuilder builder) { list = builder.list.ToList(); }