public static BlockWriterStream ToStream(Stream baseStream, uint alignment, Endian endian, bool compress) { var instance = new BlockWriterStream(baseStream, alignment, endian, compress); baseStream.WriteValueU32(Signature, endian); baseStream.WriteValueU32(alignment, endian); baseStream.WriteValueU8(4); return(instance); }
public void Serialize(Stream output, Options options) { var compress = (options & Options.Compress) != 0; var basePosition = output.Position; var endian = _Endian; using (var data = new MemoryStream(12)) { data.WriteValueU32(Signature, Endian.Big); // Mafia II = 19 // Mafia III = 20 data.WriteValueU32(20, endian); data.WriteValueU32((uint)_Platform, Endian.Big); data.Flush(); output.WriteFromMemoryStreamSafe(data, endian); } var headerPosition = output.Position; Archive.FileHeader fileHeader; output.Seek(56, SeekOrigin.Current); fileHeader.ResourceTypeTableOffset = (uint)(output.Position - basePosition); output.WriteValueS32(_ResourceTypes.Count, endian); foreach (var resourceType in _ResourceTypes) { resourceType.Write(output, endian); } /*var blockAlignment = (options & ArchiveSerializeOptions.OneBlock) != 0 * ? (uint)this._ResourceEntries.Sum(re => 30 + (re.Data == null ? 0 : re.Data.Length)) * : 0x4000; */ var blockAlignment = (options & Options.OneBlock) != 0 ? (uint)_ResourceEntries.Sum(re => 38 + (re.Data == null ? 0 : re.Data.Length)) : 0x00010000; fileHeader.BlockTableOffset = (uint)(output.Position - basePosition); fileHeader.ResourceCount = 0; var blockStream = BlockWriterStream.ToStream(output, blockAlignment, endian, compress); foreach (var resourceEntry in _ResourceEntries) { Archive.ResourceHeader resourceHeader; resourceHeader.TypeId = resourceEntry.TypeId; // resourceHeader.Size = 30 + (uint)(resourceEntry.Data == null ? 0 : resourceEntry.Data.Length); resourceHeader.Size = 38 + (uint)(resourceEntry.Data == null ? 0 : resourceEntry.Data.Length); // M3 resourceHeader.Version = resourceEntry.Version; resourceHeader.SlotRamRequired = resourceEntry.SlotRamRequired; resourceHeader.SlotVramRequired = resourceEntry.SlotVramRequired; resourceHeader.OtherRamRequired = resourceEntry.OtherRamRequired; resourceHeader.OtherVramRequired = resourceEntry.OtherVramRequired; resourceHeader.Unknown1 = resourceEntry.Unknown1; // M3 resourceHeader.Unknown2 = resourceEntry.Unknown2; // M3 using (var data = new MemoryStream()) { resourceHeader.Write(data, endian); data.Flush(); blockStream.WriteFromMemoryStreamSafe(data, endian); } blockStream.WriteBytes(resourceEntry.Data); fileHeader.ResourceCount++; } blockStream.Flush(); blockStream.Finish(); fileHeader.XmlOffset = (uint)(output.Position - basePosition); if (string.IsNullOrEmpty(_ResourceInfoXml) == false) { output.WriteString(_ResourceInfoXml, Encoding.ASCII); } else { fileHeader.XmlOffset = 0; } fileHeader.SlotRamRequired = SlotRamRequired; fileHeader.SlotVramRequired = SlotVramRequired; fileHeader.OtherRamRequired = OtherRamRequired; fileHeader.OtherVramRequired = OtherVramRequired; fileHeader.Flags = 1; fileHeader.Unknown20 = _Unknown20 ?? new byte[16]; output.Position = headerPosition; using (var data = new MemoryStream()) { fileHeader.Write(data, endian); data.Flush(); output.WriteFromMemoryStreamSafe(data, endian); } }