public void Parse() { _s_RFHeader rfheader = *(_s_RFHeader *)WorkingSource.Address; Header = new RfHeader { Tag = rfheader._rf, RegionEtc = rfheader._regionEtc, HeaderLen1 = rfheader._headerLen1, Pad = rfheader._pad0, EntriesChunkOffset = rfheader._headerLen2, EntriesChunkLen = rfheader._0x18EntriesLen, UnixTimestamp = rfheader._unixTimestamp, CompressedLen = rfheader._compressedLen, DecompressedLen = rfheader._decompressedLen, StrsChunkOffset = rfheader._strsPlus, StrsChunkLen = rfheader._strsLen, EntryCount = rfheader._resourceEntries }; VoidPtr addr = WorkingSource.Address + Header.StrsChunkOffset; addr += *(uint *)addr * 0x2000; addr += 4; Extensions = new string[*(uint *)addr]; addr += 4; for (int i = 0; i < Extensions.Length; i++) { Extensions[i] = GetStr(*(int *)(addr + i * 4)); } addr = WorkingSource.Address + Header.EntriesChunkOffset; uint size1 = *(uint *)addr * 8 + 4; addr += size1; uint size2 = *(uint *)addr + 4; addr += size2; var entries = new List <ResourceEntry>(); for (int i = 0; i < Header.EntryCount; i++, addr += 0x18) { _s_ResourceEntry entry = *(_s_ResourceEntry *)addr; ResourceEntry rsobj = new ResourceEntry() { OffInPack = entry.offInPack, NameOffsetEtc = entry.nameOffsetEtc, CmpSize = entry.cmpSize, DecSize = entry.decSize, Timestamp = DateTimeExtension.FromUnixBytes(entry.timestamp), Flags = entry.flags, }; if (rsobj.OffInPack == 0xBBBBBBBB) { ResourceEntries.Add(null); continue; } var name = ""; if ((entry.nameOffsetEtc & 0x00800000) > 0) { var strbytes = GetStrRef((int)rsobj.NameOffset); var reference = BitConverter.ToUInt16(strbytes, 0); var reflen = (reference & 0x1f) + 4; var refoff = (reference & 0xe0) >> 6 << 8 | (reference >> 8); name = GetStr((int)rsobj.NameOffset - refoff).Remove(reflen) + GetStr((int)rsobj.NameOffset + 2); } else { name = GetStr((int)rsobj.NameOffset); } rsobj.EntryString = name + Extensions[rsobj.extIndex]; ResourceEntries.Add(rsobj); } //ResourceEntries = LinkEntries(entries); }