private void ApplyTableAttributeFlags(StructTypeDefinition structTypeDef, FlatBuffersTableAttribute attribute) { structTypeDef.UseOriginalOrdering = attribute.OriginalOrdering; if (attribute.HasIdentitifer) { structTypeDef.Identifier = attribute.Identifier; } }
private void SerializeFieldValue(object obj, StructTypeDefinition structDef, FieldTypeDefinition field) { if (structDef.IsFixed) { SerializeInlineValue(obj, field.TypeModel); } else { SerializePropertyValue(obj, field); } }
private void SerializeStructField(object obj, StructTypeDefinition structDef, FieldTypeDefinition field) { if (field.Deprecated) { return; } if (field.Padding > 0) { _builder.Pad(field.Padding); } var val = field.ValueProvider.GetValue(obj); SerializeFieldValue(val, structDef, field); }
private void ApplyStructAttributeFlags(StructTypeDefinition structTypeDef, FlatBuffersStructAttribute attribute) { // check force align makes sense if (attribute.IsForceAlignSet) { var align = attribute.ForceAlign; if (align < structTypeDef.MinAlign || align > 16 || (align & (align - 1)) != 0) { throw new FlatBuffersTypeReflectionException( "ForceAlign must be a power of two integer ranging from the struct's natural alignment to 16"); } structTypeDef.MinAlign = align; structTypeDef.ForceAlignSize = align; } }
private void DeserializeStructField(object obj, StructTypeDefinition structDef, FieldTypeDefinition field, int structBase) { if (field.Deprecated) { return; } object value = null; if (structDef.IsFixed) { value = DeserializeInlineValue(structBase, field); } else { value = DeserializePropertyValue(structBase, field); } field.ValueProvider.SetValue(obj, value); }
private void ReflectStructFieldDef(StructTypeDefinition structDef, MemberInfo member) { var valueProvider = CreateValueProvider(member); var defaultValueProvider = CreateDefaultValueProvider(member); var attr = member.Attribute <FlatBuffersFieldAttribute>(); var valueType = valueProvider.ValueType; TypeModel memberTypeModel = null; TypeModel nestedTypeModel = null; if (valueType == typeof(object)) { if (attr == null || (!attr.IsUnionField && !attr.HasNestedFlatBufferType)) { throw new FlatBuffersStructFieldReflectionException("Field with 'object' member must have a UnionType or NestedFlatBufferType declared"); } if (attr.HasNestedFlatBufferType) { memberTypeModel = nestedTypeModel = GetTypeModel(attr.NestedFlatBufferType); } if (attr.IsUnionField) { memberTypeModel = GetTypeModel(attr.UnionType); } } else { if (attr != null && attr.HasNestedFlatBufferType) { throw new FlatBuffersStructFieldReflectionException("HasNestedFlatBufferType can only be used on fields with 'object' member"); } memberTypeModel = GetTypeModel(valueType); } FieldTypeDefinition unionTypeField = null; if (memberTypeModel.IsUnion) { var unionTypeFieldValueProvider = new UnionTypeValueProvider(valueProvider, memberTypeModel); var unionTypeFieldDefaultValueProvider = TypeDefaultValueProvider.Instance; unionTypeField = new FieldTypeDefinition(unionTypeFieldValueProvider, unionTypeFieldDefaultValueProvider) { Name = string.Format("{0}_type", member.Name), TypeModel = GetTypeModel <UnionFieldType>() }; } var field = new FieldTypeDefinition(valueProvider, defaultValueProvider) { Name = member.Name, // TODO: allow attribute override TypeModel = memberTypeModel, }; if (nestedTypeModel != null) { field.NestedFlatBufferType = nestedTypeModel; } ReflectUserMetadata(member, field); if (attr != null) { if (!string.IsNullOrEmpty(attr.Name)) { field.Name = attr.Name; } if (attr.IsIdSetExplicitly) { field.UserIndex = attr.Id; if (unionTypeField != null) { unionTypeField.UserIndex = attr.Id - 1; } } field.Required = attr.Required; field.Deprecated = attr.Deprecated; if (attr.Key) { if (!ValidKeyType(valueType)) { throw new FlatBuffersStructFieldReflectionException("Cannot add '{0}' as a key field. Type must be string or scalar", member.Name); } field.Key = attr.Key; } if (attr.Hash != FlatBuffersHash.None) { if (!ValidHashType(valueType)) { throw new FlatBuffersStructFieldReflectionException("Cannot use Hash setting on '{0}'. Type must be int/uint/long/ulong", member.Name); } field.Hash = attr.Hash; } } if (unionTypeField != null) { structDef.AddField(unionTypeField); field.UnionTypeField = unionTypeField; } structDef.AddField(field); }
private StructTypeDefinition ReflectStructDef(Type type) { var members = type.GetMembers(BindingFlags.Public | BindingFlags.Instance) .Where(i => i.MemberType == MemberTypes.Field || i.MemberType == MemberTypes.Property) .Where(i => !i.Defined <FlatBuffersIgnoreAttribute>()) .ToArray(); var isFixed = !type.IsClass; if (type.IsClass && type.Defined <FlatBuffersStructAttribute>()) { isFixed = true; } if (!type.IsClass && type.Defined <FlatBuffersTableAttribute>()) { isFixed = false; } if (type.Defined <FlatBuffersTableAttribute>() && type.Defined <FlatBuffersStructAttribute>()) { throw new FlatBuffersTypeReflectionException("Cannot use FlatBuffersStructAttribute and FlatBuffersTableAttribute on same type"); } var structTypeDef = new StructTypeDefinition(isFixed); ReflectUserMetadata(type, structTypeDef); if (members.Any(i => { var attr = i.Attribute <FlatBuffersFieldAttribute>(); if (attr == null) { return(false); } return(attr.IsIdSetExplicitly); })) { structTypeDef.HasCustomOrdering = true; } if (structTypeDef.IsFixed) { var structAttr = type.Attribute <FlatBuffersStructAttribute>(); if (structAttr != null) { ApplyStructAttributeFlags(structTypeDef, structAttr); } } else { var tableAttr = type.Attribute <FlatBuffersTableAttribute>(); if (tableAttr != null) { ApplyTableAttributeFlags(structTypeDef, tableAttr); } } foreach (var member in members) { try { ReflectStructFieldDef(structTypeDef, member); } catch (FlatBuffersStructFieldReflectionException fieldEx) { fieldEx.ClrType = type; fieldEx.Member = member; throw; } } // Pad the last field in the struct so it aligns correctly structTypeDef.PadLastField(structTypeDef.MinAlign); structTypeDef.FinalizeFieldDefinition(); return(structTypeDef); }