/* * Reads the header, directory, and filenames blocks from the file. Doesn't read actual sub-file data * Useful for quick initial analysis of a packfile for use with tools, so they can see what's inside * without loading the bulk of the data. */ public void ReadMetadata(string packfilePath) { PackfilePath = packfilePath; string packfileName = Path.GetFileName(packfilePath); var packfileInfo = new FileInfo(packfilePath); Filename = packfileName; Console.WriteLine("Extracting " + packfileName + "..."); if (packfileInfo.Length <= 2048) { Console.WriteLine($"Cancelled extraction of {packfileName}. Packfile is empty!"); return; } if (Verbose) { Console.WriteLine(packfileName + "> Reading header data..."); } using var stream = new FileStream(packfilePath, FileMode.Open); var packfile = new BinaryReader(stream); Header = new PackfileHeader(); Header.ReadFromBinary(packfile); for (int i = 0; i < Header.NumberOfFiles; i++) { var entry = new PackfileEntry(); entry.ReadFromBinary(packfile); DirectoryEntries.Add(entry); } packfile.ReadBytes(2048 - ((int)packfile.BaseStream.Position % 2048)); //Alignment Padding for (int i = 0; i < Header.NumberOfFiles; i++) { var name = new StringBuilder(); do { name.Append(packfile.ReadChar()); }while (packfile.PeekChar() != 0); packfile.ReadByte(); //Move past null byte if (Path.GetExtension(name.ToString()) == ".asm_pc") { ContainsAsmFiles = true; } DirectoryEntries[i].FileName = name.ToString(); DirectoryEntries[i].Extension = Path.GetExtension(name.ToString()); } packfile.ReadBytes(2048 - ((int)packfile.BaseStream.Position % 2048)); //Alignment Padding DataStartOffset = (uint)packfile.BaseStream.Position; MetadataWasRead = true; packfile.Dispose(); //Fix data offsets. Values in packfile not always valid. FixEntryDataOffsets(); }
public bool TryGetSubfileEntry(string subFileName, out PackfileEntry entry) { entry = null; int index = GetSubfileIndex(subFileName); if (index < 0) { return(false); } entry = DirectoryEntries[index]; return(true); }