public void LoadFileDataComplete(CASCHandler casc) { if (!casc.FileExists("DBFilesClient\\FileDataComplete.db2")) return; Logger.WriteLine("WowRootHandler: loading file names from FileDataComplete.db2..."); using (var s = casc.OpenFile("DBFilesClient\\FileDataComplete.db2")) { DB5Reader fd = new DB5Reader(s); foreach (var row in fd) { string path = row.Value.GetField<string>(0); string name = row.Value.GetField<string>(1); string fullname = path + name; ulong fileHash = Hasher.ComputeHash(fullname); // skip invalid names if (!RootData.ContainsKey(fileHash)) { //Logger.WriteLine("Invalid file name: {0}", fullname); continue; } CASCFile.FileNames[fileHash] = fullname; } } }
public async Task AnalyzeUnknownFiles(Action<int> progressCallback) { if (_casc == null) return; IProgress<int> progress = new Progress<int>(progressCallback); await Task.Run(() => { FileScanner scanner = new FileScanner(_casc, _root); Dictionary<int, string> idToName = new Dictionary<int, string>(); if (_casc.Config.GameType == CASCGameType.WoW) { if (_casc.FileExists("DBFilesClient\\SoundEntries.db2")) { using (Stream stream = _casc.OpenFile("DBFilesClient\\SoundEntries.db2")) { DB2Reader se = new DB2Reader(stream); foreach (var row in se) { string name = row.Value.GetField<string>(2); int type = row.Value.GetField<int>(1); bool many = row.Value.GetField<int>(4) > 0; for (int i = 3; i < 23; i++) idToName[row.Value.GetField<int>(i)] = "unknown\\sound\\" + name + (many ? "_" + (i - 2).ToString("D2") : "") + (type == 28 ? ".mp3" : ".ogg"); } } } if (_casc.FileExists("DBFilesClient\\SoundKit.db2") && _casc.FileExists("DBFilesClient\\SoundKitEntry.db2")) { using (Stream skStream = _casc.OpenFile("DBFilesClient\\SoundKit.db2")) using (Stream skeStream = _casc.OpenFile("DBFilesClient\\SoundKitEntry.db2")) { DB5Reader sk = new DB5Reader(skStream); DB5Reader ske = new DB5Reader(skeStream); Dictionary<int, List<int>> lookup = new Dictionary<int, List<int>>(); foreach (var row in ske) { int soundKitId = row.Value.GetField<int>(3); if (!lookup.ContainsKey(soundKitId)) lookup[soundKitId] = new List<int>(); lookup[soundKitId].Add(row.Value.GetField<int>(0)); } foreach (var row in sk) { string name = row.Value.GetField<string>(0).Replace(':', '_'); int type = row.Value.GetField<byte>(12); List<int> ske_entries; if (!lookup.TryGetValue(row.Key, out ske_entries)) continue; bool many = ske_entries.Count > 1; int i = 0; foreach (var fid in ske_entries) { idToName[fid] = "unknown\\sound\\" + name + (many ? "_" + (i + 1).ToString("D2") : "") + (type == 28 ? ".mp3" : ".ogg"); i++; } } } } } CASCFolder unknownFolder = _root.GetEntry("unknown") as CASCFolder; if (unknownFolder == null) return; IEnumerable<CASCFile> files = CASCFolder.GetFiles(unknownFolder.Entries.Select(kv => kv.Value), null, true); int numTotal = files.Count(); int numDone = 0; WowRootHandler wowRoot = _casc.Root as WowRootHandler; foreach (var unknownEntry in files) { CASCFile unknownFile = unknownEntry as CASCFile; string name; if (idToName.TryGetValue(wowRoot.GetFileDataIdByHash(unknownFile.Hash), out name)) unknownFile.FullName = name; else { string ext = scanner.GetFileExtension(unknownFile); unknownFile.FullName += ext; if (ext == ".m2") { using (var m2file = _casc.OpenFile(unknownFile.Hash)) using (var br = new BinaryReader(m2file)) { m2file.Position = 0x138; string m2name = br.ReadCString(); unknownFile.FullName = "unknown\\" + m2name + ".m2"; } } } progress.Report((int)(++numDone / (float)numTotal * 100)); } _casc.Root.Dump(); }); }