public override void Deserialize_Array(teStructuredDataMgr manager, teStructuredData data, STUField_Info field, Array target, int index) { STUInstance instanceObj = (STUInstance)DeserializeArrayInternal(manager, data, field, target); instanceObj.Usage = TypeUsage.InlineArray; target.SetValue(instanceObj, index); }
public override void Deserialize(teStructuredDataMgr manager, teStructuredData data, STUField_Info field, object instance, FieldInfo target) { STUInstance instanceObj = (STUInstance)DeserializeInternal(manager, data, field, target); instanceObj.Usage = TypeUsage.Inline; target.SetValue(instance, instanceObj); }
/// <summary>Read a "Version2" STU asset</summary> private void DeserializeV2(BinaryReader reader) { reader.BaseStream.Position = StartPos; HeaderChecksum = CRC.CRC64(reader.ReadBytes(36), 36, 0xFFFFFFFFFFFFFFFF); reader.BaseStream.Position = StartPos; SerializableHelper.Deserialize(reader, out InstanceInfo); SerializableHelper.Deserialize(reader, out InlinedTypesInfo); SerializableHelper.Deserialize(reader, out FieldInfoBags); int dynDataSize = reader.ReadInt32(); int dynDataOff = reader.ReadInt32(); int dataBufferOffset = reader.ReadInt32(); if (dynDataSize > 0) { reader.BaseStream.Position = dynDataOff + StartPos; DynData = new BinaryReader(new MemoryStream(reader.ReadBytes(dynDataSize))); } if (dataBufferOffset < reader.BaseStream.Length) { long dataSize = reader.BaseStream.Length - dataBufferOffset; if (dataSize > int.MaxValue) { throw new Exception("oops"); } reader.BaseStream.Position = dataBufferOffset + StartPos; Data = new BinaryReader(new MemoryStream(reader.ReadBytes((int)dataSize))); } if (InstanceInfo.Count > 0) { Instances = new STUInstance[InstanceInfo.Count]; for (int i = 0; i < InstanceInfo.Count; i++) { Instances[i] = Manager.CreateInstance(InstanceInfo[i].Hash); } } for (int i = 0; i != InstanceInfo.Count; ++i) { STUInstance_Info info = InstanceInfo[i]; STUInstance instance = Instances[i]; long startPosition = Data.Position(); if (instance != null) { instance.Deserialize(this); long endPosition = Data.Position(); } Data.BaseStream.Position = startPosition + info.Size; //if (endPosition - startPosition != info.Size) // throw new Exceptions.InvalidTypeSize($"read len != type size. Type: '{instance.GetName()}', Data offset: {startPosition}"); } }
public override void Deserialize_Array(teStructuredDataMgr manager, teStructuredData data, STUField_Info field, Array target, int index) { // todo: ??? //if (data.Format == teStructuredDataFormat.V1 && index == 0) { // var n = data.Data.ReadInt64(); // if (n > 0) { // // } //} STUInstance instanceObj = (STUInstance)DeserializeArrayInternal(manager, data, field, target); instanceObj.Usage = TypeUsage.InlineArray; target.SetValue(instanceObj, index); }
public override void Deserialize(teStructuredDataMgr manager, teStructuredData data, STUField_Info field, object instance, FieldInfo target) { if (data.Format == teStructuredDataFormat.V1) { var n = data.Data.ReadInt64(); if (n > 0) { } } STUInstance instanceObj = (STUInstance)DeserializeInternal(manager, data, field, target); instanceObj.Usage = TypeUsage.Inline; target.SetValue(instance, instanceObj); }
public void Deserialize_Array(teStructuredDataMgr manager, teStructuredData data, STUField_Info field, Array target, int index) { if (data.Format == teStructuredDataFormat.V2) { int value = data.DynData.ReadInt32(); data.DynData.ReadInt32(); // Padding for in-place deserialization if (value == -1) { return; } if (value < data.Instances.Length) { STUInstance embeddedInstance = data.Instances[value]; if (embeddedInstance != null) { embeddedInstance.Usage = TypeUsage.EmbedArray; } target.SetValue(embeddedInstance, index); } else { throw new ArgumentOutOfRangeException( $"Instance index is out of range. Id: {value}, Type: EmbeddedInstanceFieldReader, DynData offset: {data.DynData.Position() - 8}"); } } else if (data.Format == teStructuredDataFormat.V1) { long offset = data.Data.ReadInt32(); data.Data.ReadInt32(); if (offset == -1) { return; } STUInstance embeddedInstance = data.GetInstanceAtOffset(offset); if (embeddedInstance != null) { embeddedInstance.Usage = TypeUsage.EmbedArray; } target.SetValue(embeddedInstance, index); } }
public void Deserialize(teStructuredDataMgr manager, teStructuredData data, STUField_Info field, object instance, FieldInfo target) { if (data.Format == teStructuredDataFormat.V2) { int value = data.Data.ReadInt32(); if (value == -1) { return; } if (value < data.Instances.Length) { STUInstance embeddedInstance = data.Instances[value]; if (embeddedInstance != null) { embeddedInstance.Usage = TypeUsage.Embed; } target.SetValue(instance, embeddedInstance); } } else if (data.Format == teStructuredDataFormat.V1) { int value = data.Data.ReadInt32(); data.Data.ReadInt32(); if (value <= 0) { return; } STUInstance embeddedInstance = data.GetInstanceAtOffset(value); if (embeddedInstance != null) { embeddedInstance.Usage = TypeUsage.Embed; } target.SetValue(instance, embeddedInstance); } }
/// <summary>Read a "Version1" STU asset</summary> private void DeserializeV1(BinaryReader reader) { _instanceOffsets = new Dictionary <long, STUInstance>(); reader.BaseStream.Position = StartPos; STUHeaderV1 header = reader.Read <STUHeaderV1>(); InstanceInfoV1 = new STUInstanceRecordV1[header.InstanceCount]; Instances = new STUInstance[header.InstanceCount]; for (int i = 0; i < header.InstanceCount; i++) { STUInstanceRecordV1 record = reader.Read <STUInstanceRecordV1>(); InstanceInfoV1[i] = record; long position = reader.BaseStream.Position; reader.BaseStream.Position = record.Offset + StartPos; uint instanceHash = reader.ReadUInt32(); uint nextOffset = reader.ReadUInt32(); STUInstance instance = Manager.CreateInstance(instanceHash); _instanceOffsets[record.Offset] = instance; Instances[i] = instance; reader.BaseStream.Position = position; } Data = reader; // hmm for (int i = 0; i < header.InstanceCount; i++) { STUInstanceRecordV1 record = InstanceInfoV1[i]; if (Instances[i] == null) { continue; } // dump instance /*reader.BaseStream.Position = record.Offset + StartPos; * Directory.CreateDirectory("STUV1Dump"); * using (Stream dumpFile = File.OpenWrite($"STUV1Dump\\{Instances[i].GetType().Name}_{i}")) { * dumpFile.SetLength(0); * int next; * { * IEnumerable<STUInstanceRecordV1> more = InstanceInfoV1.Where(x => x.Offset > record.Offset); * if (more.Any()) { * next = InstanceInfoV1.Where(x => x.Offset > record.Offset).Min(x => x.Offset); * } else { * next = (int)Data.BaseStream.Length; // err, not great * } * } * reader.BaseStream.Position = record.Offset + StartPos; * int size = next - (int) reader.BaseStream.Position; * byte[] buf = reader.ReadBytes(size); * dumpFile.Write(buf, 0, size); * }*/ const uint instPrefixSize = sizeof(uint) * 2; // nameCrc and "nextOffset" reader.BaseStream.Position = record.Offset + StartPos + instPrefixSize; //uint instanceHash = reader.ReadUInt32(); //uint nextOffset = reader.ReadUInt32(); //if (instanceHash == 0xEA30C5E9) continue; //if (instanceHash == 0x05C7059E) { // Debugger.Break(); //} #if RELEASE try { #endif var instance = Instances[i]; instance.m_posInDataAtDeserializeCall = instPrefixSize; instance.Deserialize(this); #if RELEASE } catch (Exception) { // ignored } #endif //if (instanceHash == 0x05C7059E) { // Debugger.Break(); //} } Instances[0].Usage = TypeUsage.Root; }
public void Deserialize(teStructuredData assetFile, STUField_Info field) { BinaryReader data = assetFile.Data; BinaryReader dynData = assetFile.DynData; int offset = data.ReadInt32(); if (offset == -1) { return; } dynData.Seek(offset); int unk2Size = dynData.ReadInt32(); if (unk2Size == 0) { return; } Unknown1 = dynData.ReadUInt32(); long unk2Offset = dynData.ReadInt64(); long dataOffset = dynData.ReadInt64(); dynData.Seek(unk2Offset); Unknown2 = new uint[unk2Size]; for (int i = 0; i != unk2Size; ++i) { Unknown2[i] = dynData.ReadUInt32(); } dynData.Seek(dataOffset); uint mapSize = Unknown2.Last(); for (int i = 0; i != mapSize; ++i) { ulong key = dynData.ReadUInt64(); // Last 4 bytes are padding for in-place deserialization. int value = (int)dynData.ReadUInt64(); if (value == -1) { Add(key, null); } else { if (value < assetFile.Instances.Length) { STUInstance stuType = assetFile.Instances[value]; if (stuType != null) { stuType.Usage = TypeUsage.HashMap; } if (stuType is T casted) { Add(key, casted); } else { throw new InvalidCastException( $"Attempted to cast '{stuType?.GetType().Name}' to '{typeof(T).Name}'"); } } else { throw new ArgumentOutOfRangeException( $"DataRoot index is out of range. Id: {value}, Type: STUHashMap<{typeof(T).Name}>, Data offset: {dynData.Position() - 8}"); } } } }