private void ReadScheme() { using (PartialStream stream = new PartialStream(m_stream, m_offset, m_size)) { using (EndianReader reader = new EndianReader(stream, EndianType.LittleEndian)) { Header.Read(reader); Metadata.Read(reader); } } }
private static async Task <ISerializable> DeserializePayloadAsync( Stream stream, IReadOnlyDictionary <string, object?> header, CancellationToken cancellationToken = default) { var payloadLength = header.GetValueOrDefault(LengthKey) switch { null => (long?)null, var value => Convert.ToInt64(value) }; var payloadType = header.GetValueOrDefault(TypeKey) as string; // Event if (string.Equals(payloadType, TypeValueEvent, StringComparison.OrdinalIgnoreCase)) { var bufferLength = (int)(payloadLength ?? stream.Length); var buffer = await stream.ReadByteChunkAsync(bufferLength, cancellationToken).ConfigureAwait(false); using var jsonDocument = JsonDocument.Parse(buffer); return(new JsonSerializable( SentryEvent.FromJson(jsonDocument.RootElement.Clone()) )); } // User report if (string.Equals(payloadType, TypeValueUserReport, StringComparison.OrdinalIgnoreCase)) { var bufferLength = (int)(payloadLength ?? stream.Length); var buffer = await stream.ReadByteChunkAsync(bufferLength, cancellationToken).ConfigureAwait(false); using var jsonDocument = JsonDocument.Parse(buffer); return(new JsonSerializable( UserFeedback.FromJson(jsonDocument.RootElement.Clone()) )); } // Arbitrary payload var payloadStream = new PartialStream(stream, stream.Position, payloadLength); if (payloadLength != null) { stream.Seek(payloadLength.Value, SeekOrigin.Current); } else { stream.Seek(0, SeekOrigin.End); } return(new StreamSerializable(payloadStream)); }
public SerializedFile ReadFile(IFileCollection collection, IAssemblyManager manager) { SerializedFile file = new SerializedFile(collection, manager, this); using (PartialStream stream = new PartialStream(m_stream, m_offset, m_size)) { EndianType endianess = Header.SwapEndianess ? EndianType.BigEndian : EndianType.LittleEndian; using (EndianReader reader = new EndianReader(stream, endianess, stream.Position)) { file.Read(reader); } } return(file); }
public async Task PartialStream_WithOffsetAndLength_SettingInvalidPosition_Throws() { // Arrange using var originalStream = new MemoryStream(); await originalStream.FillWithRandomBytesAsync(1024); const int offset = 10; const int length = 100; using var partialStream = new PartialStream(originalStream, offset, length); // Act & assert Assert.Throws <InvalidOperationException>(() => partialStream.Position = 200); }
protected virtual void Dispose(bool disposing) { if (disposing) { if (this.patchFile != null) { this.patchFile.Close(); } } this.patchFile = null; this.patchBlock = null; this.inflateStream = null; }
public async Task PartialStream_WithOffsetAndLength_Length_ReturnsPartialLength() { // Arrange using var originalStream = new MemoryStream(); await originalStream.FillWithRandomBytesAsync(1024); const int offset = 10; const int length = 100; using var partialStream = new PartialStream(originalStream, offset, length); // Act & assert partialStream.Length.Should().Be(length); }
public static DuplicatableStream ReadDuplicatableSubstream(this Stream stream, long bytecount) { DuplicatableStream?ds = stream as DuplicatableStream; if (ds != null) { long p = ds.Position; PartialStream ps = new PartialStream(ds, p, bytecount); ds.Position = p + bytecount; return(ps); } else { return(new DuplicatableByteArrayStream(ReadBytes(stream, bytecount))); } }
public byte[] GetContent(ISerializedFile file) { IResourceFile res = file.Collection.FindResourceFile(Path); if (res == null) { return(null); } byte[] data = new byte[Size]; using (PartialStream resStream = new PartialStream(res.Stream, res.Offset, res.Size)) { resStream.Position = Offset; resStream.ReadBuffer(data, 0, data.Length); } return(data); }
public async Task PartialStream_WithOffset_ReadToEnd_ReturnsOnlyDataInRange() { // Arrange using var originalStream = new MemoryStream(); await originalStream.FillWithRandomBytesAsync(1024); const int offset = 10; using var partialStream = new PartialStream(originalStream, offset, null); // Act using var outputStream = new MemoryStream(); await partialStream.CopyToAsync(outputStream); // Assert var originalPortion = originalStream.ToArray().Skip(offset).ToArray(); outputStream.Length.Should().Be(originalStream.Length - offset); outputStream.ToArray().Should().Equal(originalPortion); }
private void ExportTexture(IExportContainer container, FileStream fileStream, Texture2D texture) { byte[] buffer = null; if (Texture2D.IsReadStreamData(texture.File.Version)) { string path = texture.StreamData.Path; if (path == string.Empty) { buffer = (byte[])texture.ImageData; } else { if (texture.ImageData.Count != 0) { throw new Exception("Texture contains data and resource path"); } using (ResourcesFile res = texture.File.Collection.FindResourcesFile(texture.File, path)) { using (PartialStream resStream = new PartialStream(res.Stream, res.Offset, res.Size)) { resStream.Position = texture.StreamData.Offset; buffer = new byte[texture.StreamData.Size]; resStream.Read(buffer, 0, buffer.Length); } } } } else { buffer = (byte[])texture.ImageData; } using (Bitmap bitmap = ConvertToBitmap(container, texture, buffer)) { if (bitmap != null) { bitmap.Save(fileStream, ImageFormat.Png); } } }
public static void ExportBinary(Texture2D texture, Stream exportStream) { if (texture.CompleteImageSize == 0) { return; } if (Texture2D.IsReadStreamData(texture.File.Version)) { string path = texture.StreamData.Path; if (path != string.Empty) { if (texture.ImageData.Count != 0) { throw new Exception("Texture contains data and resource path"); } using (ResourcesFile res = texture.File.Collection.FindResourcesFile(texture.File, path)) { if (res == null) { Logger.Log(LogType.Warning, LogCategory.Export, $"Can't export '{texture.ValidName}' because resources file '{path}' wasn't found"); return; } using (PartialStream resStream = new PartialStream(res.Stream, res.Offset, res.Size)) { resStream.Position = texture.StreamData.Offset; Export(texture, exportStream, resStream, texture.StreamData.Size); } } return; } } using (MemoryStream memStream = new MemoryStream((byte[])texture.ImageData)) { Export(texture, exportStream, memStream, texture.ImageData.Count); } }
public override void ExportBinary(IExportContainer container, Stream stream) { if (CompleteImageSize == 0) { return; } if (IsReadStreamData(container.Version)) { string path = StreamData.Path; if (path != string.Empty) { if (m_imageData.Length != 0) { throw new Exception("Texture contains data and resource path"); } using (ResourcesFile res = File.Collection.FindResourcesFile(File, path)) { if (res == null) { Logger.Log(LogType.Warning, LogCategory.Export, $"Can't export '{ValidName}' because resources file '{path}' wasn't found"); return; } using (PartialStream resStream = new PartialStream(res.Stream, res.Offset, res.Size)) { resStream.Position = StreamData.Offset; Export(container, stream, resStream, StreamData.Size); } } return; } } using (MemoryStream memStream = new MemoryStream(m_imageData)) { Export(container, stream, memStream, m_imageData.Length); } }
public IReadOnlyList <byte> GetImageData() { byte[] data = m_imageData; if (IsReadStreamData(File.Version)) { if (StreamData.Path != string.Empty) { if (m_imageData.Length != 0) { throw new Exception($"Texture '{ValidName}' contains both data and resource path"); } using (ResourcesFile res = File.Collection.FindResourcesFile(File, StreamData.Path)) { if (res != null) { data = new byte[StreamData.Size]; using (PartialStream resStream = new PartialStream(res.Stream, res.Offset, res.Size)) { resStream.Position = StreamData.Offset; resStream.ReadBuffer(data, 0, data.Length); } } } } } if (IsSwapBytes(File.Platform, TextureFormat)) { for (int i = 0; i < data.Length; i += 2) { byte b = data[i]; data[i] = data[i + 1]; data[i + 1] = b; } } return(data); }
public async Task PartialStream_WithOffsetAndLength_InnerPositionChanged_StillReadsCorrectly() { // Arrange using var originalStream = new MemoryStream(); await originalStream.FillWithRandomBytesAsync(1024); const int offset = 10; const int length = 100; using var partialStream = new PartialStream(originalStream, offset, length); // Act originalStream.Position = 1000; // Assert using var outputStream = new MemoryStream(); await partialStream.CopyToAsync(outputStream); var originalPortion = originalStream.ToArray().Skip(offset).Take(length).ToArray(); outputStream.ToArray().Should().Equal(originalPortion); }
/// <summary> /// Imports a resource file. /// </summary> public void Import(Stream stream) { var resourceStream = new PartialStream( archiveWrapper.archive_.BaseStream, delegate() // offset { return(file.FileOffset * RageArchiveWrapper7.BLOCK_SIZE); }, delegate() // size { return(file.FileSize); }, delegate(long length) { archiveWrapper.RequestBytesRES(file, length); } ); resourceStream.SetLength(stream.Length); // read resource var reader = new DataReader(stream); reader.Position = 0; var ident = reader.ReadUInt32(); var version = reader.ReadUInt32(); var systemFlags = reader.ReadUInt32(); var graphicsFlags = reader.ReadUInt32(); reader.Position = 0; var buffer = reader.ReadBytes((int)stream.Length); file.SystemFlags = systemFlags; file.GraphicsFlags = graphicsFlags; resourceStream.Write(buffer, 0, buffer.Length); }
private void ReadScheme() { using (PartialStream stream = new PartialStream(m_stream, m_offset, m_size)) { using (EndianReader reader = new EndianReader(stream, EndianType.BigEndian)) { Header.Read(reader); switch (Header.Type) { case ArchiveType.GZip: m_dataStream = ReadGZip(reader); break; case ArchiveType.Brotli: m_dataStream = ReadBrotli(reader); break; default: throw new NotSupportedException(Header.Type.ToString()); } } } }
private PartialStream TrySplit(Stream metaStream) { metaStream.Seek(0, SeekOrigin.Begin); BinaryReader r = new BinaryReader(metaStream); PartialStream patchBlock; if (r.ReadUInt16() == 0x5a4d)//"MZ" { metaStream.Seek(-4, SeekOrigin.End); ulong check = r.ReadUInt32(); if (check == 0xf2f7fbf3) { metaStream.Seek(-12, SeekOrigin.End); int patchBlockLength = r.ReadInt32(); int noticeLength = r.ReadInt32(); metaStream.Seek(-12 - noticeLength - patchBlockLength, SeekOrigin.End); patchBlock = new PartialStream(metaStream, metaStream.Position, patchBlockLength); metaStream.Seek(patchBlockLength, SeekOrigin.Current); noticeText = Encoding.Default.GetString(r.ReadBytes(noticeLength)); } else //兼容TMS的patch.exe { metaStream.Seek(-8, SeekOrigin.End); check = r.ReadUInt64(); if (check == 0xf2f7fbf3) { metaStream.Seek(-24, SeekOrigin.End); long patchBlockLength = r.ReadInt64(); long noticeLength = r.ReadInt64(); metaStream.Seek(-24 - noticeLength - patchBlockLength, SeekOrigin.End); patchBlock = new PartialStream(metaStream, metaStream.Position, patchBlockLength); metaStream.Seek(patchBlockLength, SeekOrigin.Current); noticeText = Encoding.Default.GetString(r.ReadBytes((int)noticeLength)); } else { return(null); } } } else { patchBlock = new PartialStream(metaStream, 0, metaStream.Length); } if (patchBlock != null) { patchBlock.Seek(0, SeekOrigin.Begin); r = new BinaryReader(patchBlock); if (Encoding.ASCII.GetString(r.ReadBytes(8)) == "WzPatch\x1A") { patchBlock.Seek(0, SeekOrigin.Begin); } else { return(null); } } return(patchBlock); }
public override void Run() { long x; string id; IFile destTemp; ITempIdentityFileService destTempService; IFile dest; Stream srcStream = null, destStream = null; IFileHashingService hasher; string sourceHash, destTempHash; try { lock (this.SyncLock) { m_TaskThread = Thread.CurrentThread; if (m_TransferState != TransferState.NotStarted) { throw new InvalidOperationException(); } SetTransferState(TransferState.Preparing); ProcessTaskStateRequest(); } id = m_Source.Address.Uri + m_Source.Length.ToString() + (m_Source.Attributes.CreationTime ?? DateTime.MinValue).ToBinary().ToString(); destTempService = (ITempIdentityFileService)m_Destination.GetService(new TempIdentityFileServiceType(id)); destTemp = destTempService.GetTempFile(); for (;;) { try { x = destTemp.Length; } catch (FileNotFoundException) { x = 0; } dest = m_Destination.ParentDirectory.ResolveFile("$TMP_" + m_Destination.Address.Name + "_" + Guid.NewGuid().ToString("N")); try { if (x == m_Source.Length) { try { if (m_Source.IdenticalTo(destTemp, FileComparingFlags.CompareContents)) { SetTransferState(TransferState.Copying); ProcessTaskStateRequest(); m_Progress.RaiseValueChanged(m_Progress.CurrentValue, 0); destTemp.MoveTo(dest, true); if (!m_Source.IdenticalTo(dest, FileComparingFlags.CompareContents)) { continue; } dest.RenameTo(m_Destination.Address.NameAndQuery, true); m_BytesTransferred = m_Destination.Length; m_Progress.RaiseValueChanged(m_Progress.CurrentValue, m_BytesTransferred); SetTransferState(TransferState.Finished); ProcessTaskStateRequest(); return; } } catch (IOException) { } } srcStream = m_Source.GetContent().GetInputStream(FileShare.Read); if (!srcStream.CanSeek) { destStream = destTemp.GetContent().GetOutputStream(FileMode.Create, FileShare.Read); } else { destStream = destTemp.GetContent().GetOutputStream(FileMode.Append, FileShare.Read); SetTransferState(TransferState.Comparing); ProcessTaskStateRequest(); hasher = (IFileHashingService)m_Source.GetService(new FileHashingServiceType("md5")); sourceHash = hasher.ComputeHash(0, destStream.Length).TextValue; hasher = (IFileHashingService)destTemp.GetService(new FileHashingServiceType("md5")); destTempHash = hasher.ComputeHash().TextValue; if (sourceHash != destTempHash) { destStream.Close(); destStream = destTemp.GetContent().GetOutputStream(FileMode.Create, FileShare.Read); } else { m_Offset = destStream.Length; if (m_Offset > 0) { srcStream = new PartialStream(srcStream, m_Offset); } } } m_Progress.RaiseValueChanged(0, m_Offset); ProcessTaskStateRequest(); m_Pump = new StreamPump(srcStream, destStream, true, false, m_ServiceType.BufferSize); m_Pump.TaskStateChanged += new TaskEventHandler(Pump_TaskStateChanged); SetTransferState(TransferState.Transferring); ProcessTaskStateRequest(); m_Pump.Run(); if (m_Pump.TaskState == TaskState.Stopped) { throw new StopRequestedException(); } SetTransferState(TransferState.Copying); ProcessTaskStateRequest(); } finally { if (srcStream != null) { Routines.IgnoreExceptions(delegate { srcStream.Close(); }); } if (destStream != null) { Routines.IgnoreExceptions(delegate { destStream.Close(); }); } } break; } SetTransferState(TransferState.Tidying); destTemp.MoveTo(dest, true); /// /// Aquire an UpdateContext for the attributes /// so that all updates to the attributes are /// commited in a single operation /// using (dest.Attributes.AquireUpdateContext()) { foreach (string s in this.m_ServiceType.AttributesToTransfer) { dest.Attributes[s] = m_Source.Attributes[s]; } } dest.RenameTo(m_Destination.Address.Name, true); SetTransferState(TransferState.Finished); } finally { if (m_TransferState != TransferState.Stopped) { SetTransferState(TransferState.Finished); } } }
public override void DoRun() { IFile destinationTemp; Stream destinationTempStream; string sourceHash; try { lock (this) { SetTransferState(TransferState.Preparing); } Action <IFile> transferAttributes = delegate(IFile dest) { using (dest.Attributes.AquireUpdateContext()) { foreach (string s in this.serviceType.AttributesToTransfer) { dest.Attributes[s] = this.source.Attributes[s]; } } }; Stream sourceStream = null; for (var i = 0; i < 4; i++) { try { sourceStream = this.OperatingNode.GetContent().GetInputStream(FileMode.Open, FileShare.Read); break; } catch (NodeNotFoundException) { throw; } catch (Exception) { if (i == 3) { throw; } } ProcessTaskStateRequest(); } using (sourceStream) { var sourceHashingService = (IHashingService)this.OperatingNode.GetService(new StreamHashingServiceType(sourceStream, this.HashAlgorithmName)); // Compute the hash of the source file SetTransferState(TransferState.Comparing); ProcessTaskStateRequest(); sourceHash = sourceHashingService.ComputeHash().TextValue; // Try to open the destination file ProcessTaskStateRequest(); var destinationHashingService = (IHashingService)this.TargetNode.GetService(new FileHashingServiceType(this.HashAlgorithmName)); string destinationHash; try { destinationHash = destinationHashingService.ComputeHash().TextValue; } catch (DirectoryNodeNotFoundException) { this.TargetNode.ParentDirectory.Create(true); try { destinationHash = destinationHashingService.ComputeHash().TextValue; } catch (NodeNotFoundException) { destinationHash = null; } } catch (NodeNotFoundException) { destinationHash = null; } ProcessTaskStateRequest(); // Source and destination are identical if (sourceHash == destinationHash) { SetTransferState(TransferState.Transferring); this.progress.RaiseValueChanged(0, GetBytesToTransfer()); SetTransferState(TransferState.Tidying); // Transfer attributes try { transferAttributes((IFile)this.TargetNode); } catch (FileNotFoundException) { } // Done SetTransferState(TransferState.Finished); ProcessTaskStateRequest(); return; } // Get a temp file for the destination based on the source's hash destinationTemp = ((ITempIdentityFileService)this.destination.GetService(new TempIdentityFileServiceType(sourceHash))).GetTempFile(); // Get the stream for the destination temp file try { if (!destinationTemp.ParentDirectory.Exists) { destinationTemp.ParentDirectory.Create(true); } } catch (IOException) { } using (destinationTempStream = destinationTemp.GetContent().OpenStream(FileMode.OpenOrCreate, FileAccess.ReadWrite, FileShare.None)) { Action finishUp = delegate { SetTransferState(TransferState.Tidying); destinationTempStream.Close(); for (int i = 0; i < 4; i++) { try { // Save hash value StandardFileHashingService.SaveHashToCache((IFile)destinationTemp, this.HashAlgorithmName, sourceHash, (IFile)this.TargetNode); try { // Transfer attributes transferAttributes(destinationTemp); } catch (FileNotFoundException e) { Console.WriteLine(e); } // Move destination temp to destination destinationTemp.MoveTo(this.TargetNode, true); break; } catch (Exception) { if (i == 3) { throw; } } ProcessTaskStateRequest(); } // Done SetTransferState(TransferState.Finished); ProcessTaskStateRequest(); }; // Get the hash for the destination temp file var destinationTempHashingService = (IHashingService)destinationTemp.GetService(new StreamHashingServiceType(destinationTempStream)); // If the destination temp and the source aren't the same // then complete the destination temp string destinationTempHash; if (destinationTempStream.Length >= sourceStream.Length) { // Destination is longer than source but starts source (unlikely) destinationTempHash = destinationTempHashingService.ComputeHash(0, sourceStream.Length).TextValue; if (destinationTempHash == sourceHash) { if (destinationTempStream.Length != sourceStream.Length) { destinationTempStream.SetLength(sourceStream.Length); } finishUp(); return; } destinationTempStream.SetLength(0); } if (destinationTempStream.Length > 0) { destinationTempHash = destinationTempHashingService.ComputeHash().TextValue; // Destination shorter than the source but is a partial copy of source sourceHash = sourceHashingService.ComputeHash(0, destinationTempStream.Length).TextValue; if (sourceHash == destinationTempHash) { this.offset = destinationTempStream.Length; } else { this.offset = 0; destinationTempStream.SetLength(0); } } else { this.offset = 0; } this.progress.RaiseValueChanged(0, this.offset); // Transfer over the remaining part needed (or everything if offset is 0) this.offset = destinationTempStream.Length; Stream sourcePartialStream = new PartialStream(sourceStream, destinationTempStream.Length); Stream destinationTempPartialStream = new PartialStream(destinationTempStream, destinationTempStream.Length); this.copier = new StreamCopier(new BufferedStream(sourcePartialStream, this.serviceType.BufferSize), destinationTempPartialStream, false, false, this.serviceType.ChunkSize); this.copier.TaskStateChanged += delegate(object sender, TaskEventArgs eventArgs) { if (eventArgs.TaskState == TaskState.Running || eventArgs.TaskState == TaskState.Paused || eventArgs.TaskState == TaskState.Stopped) { SetTaskState(eventArgs.TaskState); } }; SetTransferState(TransferState.Transferring); ProcessTaskStateRequest(); this.copier.Run(); if (this.copier.TaskState == TaskState.Stopped) { throw new StopRequestedException(); } finishUp(); } } } catch (StopRequestedException) { } finally { if (this.TransferState != TransferState.Finished) { SetTransferState(TransferState.Stopped); } } }
public HyoutaArchiveChunk(DuplicatableStream duplicatableStream, out ulong chunkLength) { using (DuplicatableStream data = duplicatableStream.Duplicate()) { data.Position = 0; // header ulong extraMagic = data.ReadUInt64(EndianUtils.Endianness.LittleEndian); ulong magic = extraMagic & 0x00fffffffffffffful; if (magic != 0x6b6e7568636168) { throw new Exception("wrong magic"); } byte extra = (byte)((extraMagic >> 56) & 0xffu); byte packedAlignment = (byte)(extra & 0x1fu); long unpackedAlignment = 1L << packedAlignment; bool hasMetadata = (extra & 0x20) != 0; bool isCompressed = (extra & 0x40) != 0; bool isBigEndian = (extra & 0x80) != 0; EndianUtils.Endianness e = isBigEndian ? EndianUtils.Endianness.BigEndian : EndianUtils.Endianness.LittleEndian; ulong endOfFileOffset = data.ReadUInt64(e) << packedAlignment; ulong tableOfContentsOffset = data.ReadUInt64(e) << packedAlignment; ulong filecount = data.ReadUInt64(e); chunkLength = endOfFileOffset; if (hasMetadata) { // just skip past this for now ulong metadataLength = data.ReadUInt64(e); data.DiscardBytes(metadataLength); } DuplicatableStream dataBlockStream; if (isCompressed) { ushort compressionInfoLengthRaw = data.ReadUInt16(e); uint compressionInfoLength = compressionInfoLengthRaw & 0xfffcu; int compressionInfoAlignmentPacked = (compressionInfoLengthRaw & 0x3) + 1; data.ReadAlign(1u << compressionInfoAlignmentPacked); Compression.IHyoutaArchiveCompressionInfo?compressionInfo = HyoutaArchiveCompression.Deserialize(data, compressionInfoLength == 0 ? 0x10000u : compressionInfoLength, e); if (compressionInfo == null) { throw new Exception("File is indicated to be compressed, but no decompressor found."); } dataBlockStream = compressionInfo.Decompress(data); } else { data.ReadAlign(unpackedAlignment); dataBlockStream = new PartialStream(data, data.Position, (long)(endOfFileOffset - (ulong)data.Position)); } try { data.Dispose(); dataBlockStream.Position = (long)tableOfContentsOffset; uint offsetToFirstFileInfo = ReadContentLength(dataBlockStream, e); // decode content bitfield(s) long numberOfUnknownBits = 0; ushort contentBitfield1 = dataBlockStream.ReadUInt16(e); bool hasDummyContent = (contentBitfield1 & 0x0001u) != 0; bool hasFilename = (contentBitfield1 & 0x0002u) != 0; bool hasCompression = (contentBitfield1 & 0x0004u) != 0; bool hasBpsPatch = (contentBitfield1 & 0x0008u) != 0; bool hasCrc32 = (contentBitfield1 & 0x0010u) != 0; bool hasMd5 = (contentBitfield1 & 0x0020u) != 0; bool hasSha1 = (contentBitfield1 & 0x0040u) != 0; numberOfUnknownBits += (contentBitfield1 & 0x0080u) != 0 ? 1 : 0; numberOfUnknownBits += (contentBitfield1 & 0x0100u) != 0 ? 1 : 0; numberOfUnknownBits += (contentBitfield1 & 0x0200u) != 0 ? 1 : 0; numberOfUnknownBits += (contentBitfield1 & 0x0400u) != 0 ? 1 : 0; numberOfUnknownBits += (contentBitfield1 & 0x0800u) != 0 ? 1 : 0; numberOfUnknownBits += (contentBitfield1 & 0x1000u) != 0 ? 1 : 0; numberOfUnknownBits += (contentBitfield1 & 0x2000u) != 0 ? 1 : 0; numberOfUnknownBits += (contentBitfield1 & 0x4000u) != 0 ? 1 : 0; ushort currentBitfield = contentBitfield1; while ((currentBitfield & 0x8000u) != 0) { // more bitfields, though we don't understand them since only the first handful of bits are defined at the moment, so just count and skip them currentBitfield = dataBlockStream.ReadUInt16(e); numberOfUnknownBits += (currentBitfield & 0x0001u) != 0 ? 1 : 0; numberOfUnknownBits += (currentBitfield & 0x0002u) != 0 ? 1 : 0; numberOfUnknownBits += (currentBitfield & 0x0004u) != 0 ? 1 : 0; numberOfUnknownBits += (currentBitfield & 0x0008u) != 0 ? 1 : 0; numberOfUnknownBits += (currentBitfield & 0x0010u) != 0 ? 1 : 0; numberOfUnknownBits += (currentBitfield & 0x0020u) != 0 ? 1 : 0; numberOfUnknownBits += (currentBitfield & 0x0040u) != 0 ? 1 : 0; numberOfUnknownBits += (currentBitfield & 0x0080u) != 0 ? 1 : 0; numberOfUnknownBits += (currentBitfield & 0x0100u) != 0 ? 1 : 0; numberOfUnknownBits += (currentBitfield & 0x0200u) != 0 ? 1 : 0; numberOfUnknownBits += (currentBitfield & 0x0400u) != 0 ? 1 : 0; numberOfUnknownBits += (currentBitfield & 0x0800u) != 0 ? 1 : 0; numberOfUnknownBits += (currentBitfield & 0x1000u) != 0 ? 1 : 0; numberOfUnknownBits += (currentBitfield & 0x2000u) != 0 ? 1 : 0; numberOfUnknownBits += (currentBitfield & 0x4000u) != 0 ? 1 : 0; } uint dummyContentLength = hasDummyContent ? ReadContentLength(dataBlockStream, e) : 0; uint filenameLength = hasFilename ? ReadContentLength(dataBlockStream, e) : 0; uint compressionLength = hasCompression ? ReadContentLength(dataBlockStream, e) : 0; uint bpspatchLength = hasBpsPatch ? ReadContentLength(dataBlockStream, e) : 0; uint crc32Length = hasCrc32 ? ReadContentLength(dataBlockStream, e) : 0; uint md5Length = hasMd5 ? ReadContentLength(dataBlockStream, e) : 0; uint sha1Length = hasSha1 ? ReadContentLength(dataBlockStream, e) : 0; long unknownContentLength = 0; for (long i = 0; i < numberOfUnknownBits; ++i) { unknownContentLength += ReadContentLength(dataBlockStream, e); } dataBlockStream.Position = (long)(tableOfContentsOffset + offsetToFirstFileInfo); List <HyoutaArchiveFileInfo> files = new List <HyoutaArchiveFileInfo>((int)filecount); for (ulong i = 0; i < filecount; ++i) { ulong offset = dataBlockStream.ReadUInt64(e) << packedAlignment; ulong filesize = dataBlockStream.ReadUInt64(e); HyoutaArchiveFileInfo fi = new HyoutaArchiveFileInfo(); if (hasDummyContent) { fi.DummyContent = dataBlockStream.ReadBytes(dummyContentLength); } if (hasFilename) { fi.Filename = ReadString(dataBlockStream, filenameLength, e); } if (hasCompression) { fi.CompressionInfo = HyoutaArchiveCompression.Deserialize(dataBlockStream, compressionLength, e); fi.StreamIsCompressed = true; } if (hasBpsPatch) { fi.BpsPatchInfo = HyoutaArchiveBpsPatchInfo.Deserialize(dataBlockStream, bpspatchLength, e, i, this); fi.StreamIsBpsPatch = fi.BpsPatchInfo != null; } if (hasCrc32) { if (crc32Length >= 4) { fi.crc32 = new CRC32(dataBlockStream.ReadUInt32(EndianUtils.Endianness.BigEndian)); dataBlockStream.DiscardBytes(crc32Length - 4); } else { dataBlockStream.DiscardBytes(crc32Length); } } if (hasMd5) { if (md5Length >= 16) { ulong a = dataBlockStream.ReadUInt64(EndianUtils.Endianness.BigEndian); ulong b = dataBlockStream.ReadUInt64(EndianUtils.Endianness.BigEndian); fi.md5 = new MD5(a, b); dataBlockStream.DiscardBytes(md5Length - 16); } else { dataBlockStream.DiscardBytes(md5Length); } } if (hasSha1) { if (sha1Length >= 20) { ulong a = dataBlockStream.ReadUInt64(EndianUtils.Endianness.BigEndian); ulong b = dataBlockStream.ReadUInt64(EndianUtils.Endianness.BigEndian); uint c = dataBlockStream.ReadUInt32(EndianUtils.Endianness.BigEndian); fi.sha1 = new SHA1(a, b, c); dataBlockStream.DiscardBytes(sha1Length - 20); } else { dataBlockStream.DiscardBytes(sha1Length); } } dataBlockStream.DiscardBytes(unknownContentLength); fi.Data = new PartialStream(dataBlockStream, (long)offset, (long)filesize); files.Add(fi); } Files = files; } finally { dataBlockStream.Dispose(); } } }
public SaveData(HyoutaPluginBase.DuplicatableStream stream, EndianUtils.Endianness endian) { MenuBlock = new SaveMenuBlock(new PartialStream(stream, 0, 0x228)); // actual save file using (DuplicatableStream saveDataStream = new PartialStream(stream, 0x228, stream.Length - 0x228)) { string magic = saveDataStream.ReadAscii(8); if (magic != "TO8SAVE\0") { throw new Exception("Invalid magic byte sequence for ToV save: " + magic); } uint saveFileSize = saveDataStream.ReadUInt32().FromEndian(endian); saveDataStream.DiscardBytes(0x14); // seemingly unused uint sectionMetadataBlockStart = saveDataStream.ReadUInt32().FromEndian(endian); uint sectionCount = saveDataStream.ReadUInt32().FromEndian(endian); uint dataStart = saveDataStream.ReadUInt32().FromEndian(endian); uint refStringStart = saveDataStream.ReadUInt32().FromEndian(endian); for (uint i = 0; i < sectionCount; ++i) { uint headerPosition = sectionMetadataBlockStart + i * 0x20; saveDataStream.Position = headerPosition; uint refStringPos = saveDataStream.ReadUInt32().FromEndian(endian); uint offset = saveDataStream.ReadUInt32().FromEndian(endian); uint size = saveDataStream.ReadUInt32().FromEndian(endian); var blockStream = new PartialStream(saveDataStream, dataStart + offset, size); string blockName = saveDataStream.ReadAsciiNulltermFromLocationAndReset(refStringStart + refStringPos); if (blockName.StartsWith("PC_STATUS")) { int idx = int.Parse(blockName.Substring("PC_STATUS".Length)) - 1; CharacterData[idx] = new SaveDataBlockPCStatus(blockStream); } else { switch (blockName) { case "Scenario": Scenario = new SaveDataBlockScenario(blockStream); break; case "FieldCamera": FieldCamera = new SaveDataBlockFieldCamera(blockStream); break; case "FieldArea": FieldArea = new SaveDataBlockFieldArea(blockStream); break; case "FieldCar": FieldCar = new SaveDataBlockFieldCar(blockStream); break; case "Camp": Camp = new SaveDataBlockCamp(blockStream); break; case "FIELD_SAVE": FieldSave = new SaveDataBlockFieldSave(blockStream); break; case "STANDBYENEMY": StandbyEnemy = new SaveDataBlockStandbyEnemy(blockStream); break; case "TERASURE_SAVE": TerasureSave = new SaveDataBlockTerasureSave(blockStream); break; case "TreasureSaveData": TreasureSaveData = new SaveDataBlockTreasureSaveData(blockStream); break; case "CUSTOM_DATA": CustomData = new SaveDataBlockCustomData(blockStream); break; case "SoundTheater": SoundTheater = new SaveDataBlockSoundTheater(blockStream); break; case "SavePoint": SavePoint = new SaveDataBlockSavePoint(blockStream); break; case "MG2Poker": MG2Poker = new SaveDataBlockMG2Poker(blockStream); break; case "SnowBoard": SnowBoard = new SaveDataBlockSnowBoard(blockStream); break; case "PARTY_DATA": PartyData = new SaveDataBlockPartyData(blockStream); break; case "FieldGadget": FieldGadget = new SaveDataBlockFieldGadget(blockStream); break; default: Console.WriteLine("Unknown save data block '" + blockName + "'"); break; } } } } }
public async Task <HttpResponseMessage> Import() { using (var stream = await Request.Content.ReadAsStreamAsync().ConfigureAwait(false)) { var binaryReader = new BinaryReader(stream); long count = 0; while (true) { string name; try { name = binaryReader.ReadString(); } catch (EndOfStreamException) { break; // done } var metadata = RavenJObject.Parse(binaryReader.ReadString()); if (name.Length > SystemParameters.KeyMost) { if (Log.IsDebugEnabled) { Log.Debug("File '{0}' was not created due to illegal name length", name); } return(GetMessageWithString(string.Format("File '{0}' was not created due to illegal name length", name), HttpStatusCode.BadRequest)); } var contentSize = binaryReader.ReadInt64(); var options = new FileActions.PutOperationOptions { ContentSize = contentSize }; RavenJToken lastModifiedJToken; if (metadata.TryGetValue(Constants.RavenLastModified, out lastModifiedJToken)) { DateTimeOffset lastModified; if (DateTimeOffset.TryParse(lastModifiedJToken.Value <string>(), out lastModified)) { options.LastModified = lastModified; } } options.PreserveTimestamps = true; var fileStream = new PartialStream(stream, contentSize); var tcs = new TaskCompletionSource <Stream>(); tcs.SetResult(fileStream); await FileSystem.Files.PutAsync(name, null, metadata, () => tcs.Task, options).ConfigureAwait(false); if (count % 100 == 0) { SynchronizationTask.Context.NotifyAboutWork(); } } SynchronizationTask.Context.NotifyAboutWork(); } return(new HttpResponseMessage(HttpStatusCode.OK) { }); }
public override void ExportBinary(IExportContainer container, Stream stream) { if (IsReadLoadType(container.Version)) { using (ResourcesFile res = File.Collection.FindResourcesFile(File, FSBResource.Source)) { if (res == null) { Logger.Log(LogType.Warning, LogCategory.Export, $"Can't export '{ValidName}' because resources file '{FSBResource.Source}' hasn't been found"); return; } if (StreamedResource.IsReadSize(container.Version)) { using (PartialStream resStream = new PartialStream(res.Stream, res.Offset, res.Size)) { resStream.Position = FSBResource.Offset; resStream.CopyStream(stream, FSBResource.Size); } } else { // I think they read data by its type for this verison, so I can't even export raw data :/ Logger.Log(LogType.Warning, LogCategory.Export, $"Can't export '{ValidName}' because of unknown size"); } } } else { if (IsReadStreamingInfo(container.Version)) { if (LoadType == AudioClipLoadType.Streaming) { if (m_audioData == null) { using (ResourcesFile res = File.Collection.FindResourcesFile(File, StreamingInfo.Path)) { if (res == null) { Logger.Log(LogType.Warning, LogCategory.Export, $"Can't export '{ValidName}' because resources file '{StreamingInfo.Path}' hasn't been found"); return; } using (PartialStream resStream = new PartialStream(res.Stream, res.Offset, res.Size)) { resStream.Position = StreamingInfo.Offset; resStream.CopyStream(stream, StreamingInfo.Size); } } } else { stream.Write(m_audioData, 0, m_audioData.Length); } } else { stream.Write(m_audioData, 0, m_audioData.Length); } } else { stream.Write(m_audioData, 0, m_audioData.Length); } } }