private bool BuildConditions(XmlMapping mapping, int i, ref int mappingNameIndex, ref List <ConditionalExpression> result) { var type = Mappings[i].PropertyCache.Property.PropertyType; if (type.IsValueType && Nullable.GetUnderlyingType(type) == null) { var flagIndex = Expression.Constant(i); var flag = Expression.ArrayIndex(XmlExpressionConstants.SerializerFlags, flagIndex); //flagArray[0] var nameIndex = Expression.Constant(mappingNameIndex); var name = Expression.ArrayIndex(XmlExpressionConstants.SerializerNames, nameIndex); var assignName = XmlExpressionConstants.Serializer_Name(mapping.AttributeType).Assign(name); var throwNull = XmlExpressionConstants.Fail(null, type).Throw(); //throw Fail(null, null, typeof(int)); var block = Expression.Block( assignName, throwNull ); var condition = flag.Not().IfThen(block); result.Add(condition); } return(false); }
private LambdaExpression MakeSwitchLambda(ParameterExpression property, ParameterExpression rawValue) { var c = ReflectionCacheManager.GetEnumCache(propertyType).Cache; var fields = c.Fields; List <SwitchCase> cases = new List <SwitchCase>(); foreach (var f in fields) { if (f.Field.FieldType.IsEnum) { var val = f.Field.GetValue(null); Expression body = GetCaseBody((Enum)val, rawValue); if (body != null) { if (body.NodeType != ExpressionType.Block) { body = Expression.Convert(body, typeof(object)); } cases.Add(Expression.SwitchCase(body, Expression.Constant(val))); } } } var @default = Expression.Constant(null); var assignName = XmlExpressionConstants.Serializer_Name(XmlAttributeType.Element).Assign(property.Call("ToString").Call("ToLower")); var @switch = Expression.Switch(property, @default, cases.ToArray()); return(Expression.Lambda( Expression.Block( assignName, @switch ), "ReadObjectPropertyInner", new[] { XmlExpressionConstants.Serializer, property, rawValue })); }
public Expression GetLadder() { var castReaderName = Expression.Convert(XmlExpressionConstants.XmlReader_Name, typeof(object)); var assignReaderName = Expression.Assign(XmlExpressionConstants.Serializer_Name(attributeType), castReaderName); var conditions = generator.ForEachMappingValue <ConditionalExpression>(BuildConditions); var elseIf = new ElseIfExpression(conditions.ToArray(), XmlExpressionConstants.Serializer_SkipUnknownNode); if (Mappings.Where(m => m.AttributeType == attributeType).Count() > 0) { return(Expression.Block( assignReaderName, elseIf )); } else { return(elseIf); } }
/// <summary> /// Create an expression like !flagsArray[0] && (object)reader.Name == nameArray[0] /// </summary> /// <param name="mappingNameIndex">Index of the mapping name being analyzed.</param> /// <returns>The condition to check against and the flag of the flagArray that was used.</returns> private Tuple <BinaryExpression, IndexExpression> MakeElementCheckCondition(ref int mappingNameIndex) { Expression notFlag = null; IndexExpression flag = null; if (!MappingIsList(mapping)) { var flagIndex = Expression.Constant(mappingIndex); flag = Expression.ArrayAccess(XmlExpressionConstants.SerializerFlags, flagIndex); //flagsArray[0] notFlag = Expression.Not(flag); //!flagsArray[0] } Expression isNameEqual = null; foreach (var attributeName in mapping.AttributeValue) { var attributeValueIndex = Expression.Constant(mappingNameIndex); var name = Expression.ArrayIndex(XmlExpressionConstants.SerializerNames, attributeValueIndex); //nameArray[0] var expr = Expression.Equal(XmlExpressionConstants.Serializer_Name(mapping.AttributeType), name); //(object)reader.Name == nameArray[0] if (isNameEqual == null) { isNameEqual = expr; } else { isNameEqual = Expression.OrElse(isNameEqual, expr); //(object)reader.Name == nameArray[0] || (object)reader.Name == nameArray[1] } mappingNameIndex++; } var condition = isNameEqual; if (notFlag != null) { condition = Expression.AndAlso(notFlag, isNameEqual); //!flagsArray[0] && (object)reader.Name == nameArray[0] } return(Tuple.Create((BinaryExpression)condition, flag)); }