public override void Initialize() { var structAttribute = this.ClrType.GetCustomAttribute <FlatBufferStructAttribute>(); if (structAttribute == null) { throw new InvalidFlatBufferDefinitionException($"Can't create struct type model from type {this.ClrType.Name} because it does not have a [FlatBufferStruct] attribute."); } TableTypeModel.EnsureClassCanBeInheritedByOutsideAssembly(this.ClrType, out this.preferredConstructor); var properties = this.ClrType .GetProperties(BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance) .Select(x => new { Property = x, Attribute = x.GetCustomAttribute <FlatBufferItemAttribute>() ! // suppress check here; we filter on the next line. })
public override void Initialize() { var structAttribute = this.ClrType.GetCustomAttribute <FlatBufferStructAttribute>(); if (structAttribute == null) { throw new InvalidFlatBufferDefinitionException($"Can't create struct type model from type {this.ClrType.Name} because it does not have a [FlatBufferStruct] attribute."); } TableTypeModel.EnsureClassCanBeInheritedByOutsideAssembly(this.ClrType, out var ctor); var properties = this.ClrType .GetProperties(BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Instance) .Select(x => new { Property = x, Attribute = x.GetCustomAttribute <FlatBufferItemAttribute>() }) .Where(x => x.Attribute != null) .OrderBy(x => x.Attribute.Index); ushort expectedIndex = 0; this.inlineSize = 0; foreach (var item in properties) { var propertyAttribute = item.Attribute; var property = item.Property; if (propertyAttribute.Deprecated) { throw new InvalidFlatBufferDefinitionException($"FlatBuffer struct {this.ClrType.Name} may not have deprecated properties"); } ushort index = propertyAttribute.Index; if (index != expectedIndex) { throw new InvalidFlatBufferDefinitionException($"FlatBuffer struct {this.ClrType.Name} does not declare an item with index {expectedIndex}. Structs must have sequenential indexes starting at 0."); } if (!object.ReferenceEquals(propertyAttribute.DefaultValue, null)) { throw new InvalidFlatBufferDefinitionException($"FlatBuffer struct {this.ClrType.Name} declares default value on index {expectedIndex}. Structs may not have default values."); } expectedIndex++; ITypeModel propertyModel = this.typeModelContainer.CreateTypeModel(property.PropertyType); if (!propertyModel.IsValidStructMember || propertyModel.PhysicalLayout.Length > 1) { throw new InvalidFlatBufferDefinitionException($"Struct property {property.Name} with type {property.PropertyType.Name} cannot be part of a flatbuffer struct."); } int propertySize = propertyModel.PhysicalLayout[0].InlineSize; int propertyAlignment = propertyModel.PhysicalLayout[0].Alignment; this.maxAlignment = Math.Max(propertyAlignment, this.maxAlignment); // Pad for alignment. this.inlineSize += SerializationHelpers.GetAlignmentError(this.inlineSize, propertyAlignment); StructMemberModel model = new StructMemberModel( propertyModel, property, index, this.inlineSize); this.memberTypes.Add(model); this.inlineSize += propertyModel.PhysicalLayout[0].InlineSize; } }
/// <summary> /// Tries to create a type model based on the given type. /// </summary> public bool TryCreateTypeModel(TypeModelContainer container, Type type, out ITypeModel typeModel) { if (type == typeof(string)) { typeModel = new StringTypeModel(); return(true); } if (type == typeof(SharedString)) { typeModel = new SharedStringTypeModel(); return(true); } if (type.IsArray) { typeModel = new ArrayVectorTypeModel(type, container); return(true); } if (type.IsGenericType) { var genericDef = type.GetGenericTypeDefinition(); if (genericDef == typeof(IList <>) || genericDef == typeof(IReadOnlyList <>)) { typeModel = new ListVectorTypeModel(type, container); return(true); } if (genericDef == typeof(Memory <>) || genericDef == typeof(ReadOnlyMemory <>)) { typeModel = new MemoryVectorTypeModel(type, container); return(true); } if (genericDef == typeof(IIndexedVector <,>)) { typeModel = new IndexedVectorTypeModel(type, container); return(true); } } if (typeof(IUnion).IsAssignableFrom(type)) { typeModel = new UnionTypeModel(type, container); return(true); } if (type.IsEnum) { typeModel = new EnumTypeModel(type, container); return(true); } if (Nullable.GetUnderlyingType(type) != null) { var underlyingType = Nullable.GetUnderlyingType(type); if (underlyingType.IsEnum) { typeModel = new NullableEnumTypeModel(type, container); return(true); } } var tableAttribute = type.GetCustomAttribute <FlatBufferTableAttribute>(); if (tableAttribute != null) { typeModel = new TableTypeModel(type, container); return(true); } var structAttribute = type.GetCustomAttribute <FlatBufferStructAttribute>(); if (structAttribute != null) { typeModel = new StructTypeModel(type, container); return(true); } typeModel = null; return(false); }