public static GARC Unpack(string path) { GARC garc = new GARC(); BinaryReader br = new BinaryReader(System.IO.File.OpenRead(path)); // GARC Header garc.id = br.ReadChars(4); garc.header_size = br.ReadUInt32(); garc.id_endian = br.ReadUInt16(); if (garc.id_endian == 0xFEFF) { Reverse(garc.id); } garc.constant = br.ReadUInt16(); garc.file_size = br.ReadUInt32(); garc.data_offset = br.ReadUInt32(); garc.file_length = br.ReadUInt32(); garc.lastsize = br.ReadUInt32(); // fix to header from goteniai br.ReadUInt32(); br.ReadUInt32(); // OTAF garc.otaf.id = br.ReadChars(4); garc.otaf.section_size = br.ReadUInt32(); garc.otaf.nFiles = br.ReadUInt16(); garc.otaf.padding = br.ReadUInt16(); garc.otaf.entries = new OTAF_Entry[garc.otaf.nFiles]; // not really needed; plus it's wrong for (int i = 0; i < garc.otaf.nFiles; i++) { uint val = br.ReadUInt32(); if (garc.otaf.padding == 0xffff) { val = Reverse(val); } garc.otaf.entries[i].name = val.ToString(); } // BTAF (File Allocation TaBle) garc.btaf.id = br.ReadChars(4); garc.btaf.section_size = br.ReadUInt32(); garc.btaf.nFiles = br.ReadUInt32(); garc.btaf.entries = new BTAF_Entry[garc.btaf.nFiles]; for (int i = 0; i < garc.btaf.nFiles; i++) { garc.btaf.entries[i].bits = br.ReadUInt32(); garc.btaf.entries[i].start_offset = br.ReadUInt32(); garc.btaf.entries[i].end_offset = br.ReadUInt32(); garc.btaf.entries[i].length = br.ReadUInt32(); } // BMIF garc.gmif.id = br.ReadChars(4); garc.gmif.section_size = br.ReadUInt32(); garc.gmif.data_size = br.ReadUInt32(); // Files data br.Close(); return(garc); }
private void B_Go_Click(object sender, EventArgs e) { // Continue only if a string path is loaded. if (textBox1.Text.Length < 1) { return; } // Fetch file extension (first 4 bytes) to check if it is a GARC BinaryReader brz = new BinaryReader(System.IO.File.OpenRead(textBox1.Text)); try { string s = new string(Reverse(brz.ReadChars(4))); if (s != "GARC") { RTB.Text += "Input file is not a .GARC"; return; } RTB.Text = s; } catch (EncoderFallbackException) { RTB.Text += "Invalid File."; return; } brz.Close(); // Unpack the GARC GARC garc = ARC.Unpack(textBox1.Text); RTB.Text += "\r\nCount: " + garc.otaf.nFiles; ProgressInit(garc.otaf.nFiles); if (garc.otaf.nFiles > 50) { CHK_NoPrint.Checked = true; } // Get file path infos for exporting FileInfo fileInfo = new FileInfo(textBox1.Text); string path = fileInfo.DirectoryName; string parentName = fileInfo.Name; string basepath = path + "\\" + parentName + "_"; BinaryReader br = new BinaryReader(System.IO.File.OpenRead(textBox1.Text)); // Create Extraction folder if it does not exist. if (!Directory.Exists(basepath)) { DirectoryInfo di = Directory.CreateDirectory(basepath); } // Pull out all the files for (int i = 0; i < garc.otaf.nFiles; i++) { string ext = "bin"; bool compressed = false; string newext; br.BaseStream.Position = garc.btaf.entries[i].start_offset + garc.data_offset; try { newext = TrimFromZero(new string(br.ReadChars(4))); if ((System.Text.RegularExpressions.Regex.IsMatch(newext, @"^[a-zA-Z0-9]+$")) && (!CHK_ForceBIN.Checked)) { ext = newext; } else { compressed = true; } } catch { newext = null; } // Set File Name string filename = i.ToString("D" + Math.Ceiling(Math.Log10(garc.otaf.nFiles))); string fileout = basepath + "\\" + filename + "." + ext; BinaryWriter bw = new BinaryWriter(File.OpenWrite(fileout)); // Write out the data for the file br.BaseStream.Position = garc.btaf.entries[i].start_offset + garc.data_offset; for (int x = 0; x < garc.btaf.entries[i].length; x++) { bw.Write(br.ReadByte()); } bw.Flush(); bw.Close(); printout("\r\nWrote to " + fileout); // See if decompression should be attempted. if (compressed && !CHK_SkipDecompress.Checked) { string decout = path + "\\" + parentName + "_\\" + "dec_" + filename; string result = LZSS.Decompress11LZS(fileout, decout); if (result != null) { printout("\r\n" + result); if (CHK_delAfterD.Checked) { try { File.Delete(fileout); } catch { } } } } pBar1.PerformStep(); } br.Close(); RTB.Text += "\r\nDone!"; RTB.Select(RTB.Text.Length - 1, 0); RTB.ScrollToCaret(); }
public static GARC Unpack(string path) { GARC garc = new GARC(); BinaryReader br = new BinaryReader(System.IO.File.OpenRead(path)); // GARC Header garc.id = br.ReadChars(4); garc.header_size = br.ReadUInt32(); garc.id_endian = br.ReadUInt16(); if (garc.id_endian == 0xFEFF) Reverse(garc.id); garc.constant = br.ReadUInt16(); garc.file_size = br.ReadUInt32(); garc.data_offset = br.ReadUInt32(); garc.file_length = br.ReadUInt32(); garc.lastsize = br.ReadUInt32(); // OTAF garc.otaf.id = br.ReadChars(4); garc.otaf.section_size = br.ReadUInt32(); garc.otaf.nFiles = br.ReadUInt16(); garc.otaf.padding = br.ReadUInt16(); garc.otaf.entries = new OTAF_Entry[garc.otaf.nFiles]; // not really needed; plus it's wrong for (int i = 0; i < garc.otaf.nFiles; i++) { uint val = br.ReadUInt32(); if (garc.otaf.padding == 0xffff) { val = Reverse(val); } garc.otaf.entries[i].name = val.ToString(); } // BTAF (File Allocation TaBle) garc.btaf.id = br.ReadChars(4); garc.btaf.section_size = br.ReadUInt32(); garc.btaf.nFiles = br.ReadUInt32(); garc.btaf.entries = new BTAF_Entry[garc.btaf.nFiles]; for (int i = 0; i < garc.btaf.nFiles; i++) { garc.btaf.entries[i].bits = br.ReadUInt32(); garc.btaf.entries[i].start_offset = br.ReadUInt32(); garc.btaf.entries[i].end_offset = br.ReadUInt32(); garc.btaf.entries[i].length = br.ReadUInt32(); } // BMIF garc.gmif.id = br.ReadChars(4); garc.gmif.section_size = br.ReadUInt32(); garc.gmif.data_size = br.ReadUInt32(); // Files data br.Close(); return garc; }