private static void CheckCollision(Dictionary <ulong, Idstring> item, ulong hash, Idstring value) { if (item.ContainsKey(hash) && (item[hash] != value)) { Console.WriteLine("Hash collision: {0:x} : {1} == {2}", hash, item[hash], value); } }
/// <summary> /// The load. /// </summary> /// <param name="bundleId"> /// The bundle id. /// </param> /// <returns> /// The <see cref="bool"/>. /// </returns> public bool Load(string bundle_path) { if (!File.Exists(bundle_path)) { Console.WriteLine("Bundle header file does not exist."); return(false); } this._name = (Idstring)General.BundleNameToPackageID(Path.GetFileNameWithoutExtension(bundle_path).Replace("_h", "")).Clone(); this._name.SwapEdianness(); try { using (var fs = new FileStream(bundle_path, FileMode.Open)) { using (var br = new BinaryReader(fs)) { bool confSet = false; if (bundle_path.Contains("all_")) { Console.WriteLine(); } this.Header = new List <uint> { br.ReadUInt32(), //ref offset br.ReadUInt32(), //tag / count br.ReadUInt32(), //linux:tag / count br.ReadUInt32(), // offset / count }; if (this.Header[1] != this.Header[2]) { this.Header.Add(br.ReadUInt32()); } uint refOffset = this.Header[0]; uint itemCount = 0, offset = 0; for (int i = 1; i < (this.Header.Count - 1); i++) { if (this.Header[i] == this.Header[i + 1]) { itemCount = this.Header[i]; if (this.Header.Count <= i + 2) { this.Header.Add(br.ReadUInt32()); } offset = this.Header[i + 2]; if (i != 1) { /*if (this.Header[1] == 0) * { * offset += 4; * } * else*/ this.HasLengthField = true; } break; } } if (br.BaseStream.Position < offset) { uint amount = ((offset - (uint)br.BaseStream.Position) / 4); for (uint i = 0; i < amount; i++) { this.Header.Add(br.ReadUInt32()); } } if (offset == 0) { offset = refOffset - 4; } br.BaseStream.Position = offset; uint entryTag = br.ReadUInt32(); if (!confSet) { List <BundleHeaderConfig> configs = Defs.ConfigLookup.FindAll(conf => this.HasLengthField ? conf.EntryStartLengthTag.Equals(entryTag) : conf.EntryStartTag.Equals(entryTag)); if (configs.Count == 1) { this.Config = configs[0]; confSet = true; } } for (int i = 0; i < itemCount; ++i) { var be = new PackageFileEntry(br, this.HasLengthField) { Parent = this }; this._entries.Add(be); if (this.HasLengthField || i <= 0) { continue; } PackageFileEntry pbe = this._entries[i - 1]; pbe.Length = (int)(be.Address - pbe.Address); } if (itemCount > 0 && !this.HasLengthField) { string bundleFile; if (!File.Exists(bundleFile = bundle_path.Replace("_h", ""))) { this._entries[this._entries.Count - 1].Length = -1; } else { if (bundleFile == bundle_path) { this._entries[this._entries.Count - 1].Length = (int)(((uint)fs.Length) - this._entries[this._entries.Count - 1].Address); } else { long length = new System.IO.FileInfo(bundleFile).Length; this._entries[this._entries.Count - 1].Length = (int)(((uint)length) - this._entries[this._entries.Count - 1].Address); } } } //Footer breakdown /* * uint32 - tag * uint32 - section size * uint32 - count * uint32 - unknown * uint32 - unknown * uint32 - tag? * foreach (count): * uint64 - hash (extension) * uint64 - hash (path) * uint32 - end? * uint32 (0) - end */ uint sectag = br.ReadUInt32(); if (sectag.Equals(this.Config.ReferenceStartTag)) { this.ReadFooter(br); } //this.Footer = br.ReadBytes((int)(br.BaseStream.Length - br.BaseStream.Position)); //uint val = Convert.ToUInt32(this.Footer[0]); //if (confSet) //Console.WriteLine("Bundle Config detected!"); } } } catch (Exception exc) { Console.WriteLine(exc.Message); return(false); } return(true); }