Esempio n. 1
0
        private static Func <object, ObjectClonerReferenceTracker, object> GenerateCloner(Type sourceType)
        {
            InternalSerializationStuff.ValidateSupportedTypes(sourceType);

            ParameterExpression sourceParameter = Expression.Parameter(typeof(object), "sourceParam");
            ParameterExpression refTrackerParam = Expression.Parameter(typeof(ObjectClonerReferenceTracker), "refTrackerParam");

            var clone  = Expression.Parameter(sourceType, "newInstance");
            var source = Expression.Parameter(sourceType, "source");

            var variables   = new List <ParameterExpression>();
            var expressions = new List <Expression>();

            variables.Add(source);
            variables.Add(clone);
            expressions.Add(Expression.Assign(source, Expression.Convert(sourceParameter, sourceType)));

            if (sourceType.IsPrimitive || sourceType.IsValueType || (sourceType == typeof(string)))
            {
                expressions.Add(Expression.Assign(clone, source));
            }
            else if (InternalSerializationStuff.ImplementsISerializableWithSerializationConstructor(sourceType))
            {
                expressions.Add(ISerializableCloner.GenerateISerializableExpression(variables, source, clone, sourceType, refTrackerParam));
            }
            else if (InternalSerializationStuff.ImplementsDictionaryGeneric(sourceType))
            {
                expressions.Add(DictionaryCloner.GenerateDictionaryGenericExpression(variables, source, clone, sourceType, refTrackerParam));
            }
            else if (sourceType == typeof(ExpandoObject))
            {
                expressions.Add(ExpandoCloner.GenerateExpandoObjectExpression(variables, source, clone, refTrackerParam));
            }
            else if (sourceType.IsArray)
            {
                expressions.Add(ArrayCloner.GenerateArrayExpression(variables, source, clone, sourceType, refTrackerParam));
            }
            else
            {
                expressions.Add(ClassCloner.GenerateClassExpressions(variables, sourceType, source, clone, refTrackerParam));
            }

            // Value types require manual boxing
            if (sourceType.IsValueType)
            {
                expressions.Add(Expression.Convert(clone, typeof(object)));
            }
            else
            {
                expressions.Add(clone);
            }

            return(Expression.Lambda <Func <object, ObjectClonerReferenceTracker, object> >(Expression.Block(variables, expressions), sourceParameter, refTrackerParam).Compile());
        }
Esempio n. 2
0
        private static System.Delegate CreateTypeSerializer(Type type)
        {
            InternalSerializationStuff.ValidateSupportedTypes(type);

            var variables      = new List <ParameterExpression>();
            var expressions    = new List <Expression>();
            var outputStream   = Expression.Parameter(typeof(Stream), "outputStream");
            var objToSerialize = Expression.Parameter(type, "objToSerialize");
            var objTracking    = Expression.Parameter(typeof(SerializerObjectTracker), "objTracking");

            var primitiveWriter = GetPrimitiveWriter(type);

            if (primitiveWriter != null)
            {
                Debug.Assert(type.IsPrimitive || type.IsValueType, "Value is not a primitive");
                expressions.Add(primitiveWriter(outputStream, objToSerialize, objTracking));
            }
            else if (type == typeof(string))
            {
                expressions.Add(GenerateStringExpression(outputStream, objToSerialize, objTracking));
            }
            else if (InternalSerializationStuff.ImplementsISerializableWithSerializationConstructor(type))
            {
                expressions.Add(ISerializableSerializer.GenerateISerializableExpression(type, variables, outputStream, objToSerialize, objTracking));
            }
            else if (InternalSerializationStuff.ImplementsDictionaryGeneric(type))
            {
                expressions.Add(DictionarySerializer.GenerateDictionaryGenericExpression(type, variables, outputStream, objToSerialize, objTracking));
            }
            else if (type == typeof(ExpandoObject))
            {
                expressions.Add(ExpandoSerializer.GenerateExpandoObjectExpression(type, variables, outputStream, objToSerialize, objTracking));
            }
            else if (type.IsArray)
            {
                expressions.Add(GenerateArrayExpression(type, outputStream, objToSerialize, objTracking));
            }
            else
            {
                expressions.Add(GenerateClassExpression(type, outputStream, objToSerialize, objTracking));
            }

            var block = Expression.Block(variables, expressions);

            var a = typeof(Action <, ,>).MakeGenericType(typeof(Stream), type, typeof(SerializerObjectTracker));

            return(Expression.Lambda(a, block, outputStream, objToSerialize, objTracking).Compile());
        }