protected override bool OnInitialize() { RSARNode parent; //Find bank entry in rsar if ((_name == null) && ((parent = RSARNode) != null)) { RSARHeader *rsar = parent.Header; RuintList * list = rsar->INFOBlock->Banks; VoidPtr offset = &rsar->INFOBlock->_collection; SYMBHeader *symb = rsar->SYMBBlock; int count = list->_numEntries; for (int i = 0; i < count; i++) { INFOBankEntry *bank = (INFOBankEntry *)list->Get(offset, i); if (bank->_fileId == _fileIndex) { _name = symb->GetStringEntry(bank->_stringId); break; } } } base.OnInitialize(); ParseBlocks(); return(true); }
private void GetFiles() { RSARHeader *rsar = Header; //SYMBHeader* symb = rsar->SYMBBlock; //sbyte* offset = (sbyte*)symb + 8; //buint* stringOffsets = symb->StringOffsets; VoidPtr gOffset = (VoidPtr)rsar->INFOBlock + 8; ruint * groups = (ruint *)gOffset; ruint *list = (ruint *)((uint)groups + groups[3] + 4); int count = *((bint *)list - 1); //Get files INFOFileHeader * fileHeader; INFOFileEntry * fileEntry; RuintList * entryList; INFOGroupHeader *group; INFOGroupEntry * gEntry; RuintList * groupList = rsar->INFOBlock->Groups; RSARFileNode n; DataSource source; for (int x = 0; x < count; x++) { fileHeader = (INFOFileHeader *)(gOffset + list[x]); entryList = fileHeader->GetList(gOffset); if (entryList->_numEntries == 0) { //Must be external file. n = new RSARExtFileNode(); source = new DataSource(fileHeader, 0); } else { //use first entry fileEntry = (INFOFileEntry *)entryList->Get(gOffset, 0); //Find group with matching ID group = (INFOGroupHeader *)groupList->Get(gOffset, fileEntry->_groupId); //Find group entry with matching index gEntry = (INFOGroupEntry *)group->GetCollection(gOffset)->Get(gOffset, fileEntry->_index); //Create node and parse source = new DataSource((int)rsar + group->_headerOffset + gEntry->_headerOffset, gEntry->_headerLength); if ((n = NodeFactory.GetRaw(source) as RSARFileNode) == null) { n = new RSARFileNode(); } n._audioSource = new DataSource((int)rsar + group->_dataOffset + gEntry->_dataOffset, gEntry->_dataLength); } n._fileIndex = x; n._parent = this; //This is so that the node won't add itself to the child list. n.Initialize(this, source); _files.Add(n); } }
protected internal override void OnRebuild(VoidPtr address, int length, bool force) { int symbLen, infoLen, fileLen; RSARHeader *rsar = (RSARHeader *)address; SYMBHeader *symb = (SYMBHeader *)(address + 0x40); INFOHeader *info; FILEHeader *data; info = (INFOHeader *)((int)symb + (symbLen = RSARConverter.EncodeSYMBBlock(symb, _entryList))); data = (FILEHeader *)((int)info + (infoLen = RSARConverter.EncodeINFOBlock(info, _entryList))); fileLen = RSARConverter.EncodeFILEBlock(data, _entryList); rsar->Set(symbLen, infoLen, fileLen); _entryList.Clear(); }
public override void OnRebuild(VoidPtr address, int length, bool force) { int symbLen, infoLen, fileLen; RSARHeader *rsar = (RSARHeader *)address; SYMBHeader *symb = (SYMBHeader *)(address + 0x40); INFOHeader *info; FILEHeader *data; info = (INFOHeader *)(checked ((uint)symb + (symbLen = _converter.EncodeSYMBBlock(symb, _entryList, this)))); data = (FILEHeader *)(checked ((uint)info + (infoLen = _converter.EncodeINFOBlock(info, _entryList, this)))); fileLen = _converter.EncodeFILEBlock(data, address, _entryList, this); rsar->Set(symbLen, infoLen, fileLen, VersionMinor); _entryList.Clear(); }
public override void OnPopulate() { //Enumerate entries, attaching them to the files. RSARHeader *rsar = Header; SYMBHeader *symb = rsar->SYMBBlock; sbyte * offset = (sbyte *)symb + 8; buint * stringOffsets = symb->StringOffsets; VoidPtr baseAddr = (VoidPtr)rsar->INFOBlock + 8; ruint * typeList = (ruint *)baseAddr; //Iterate through group types for (int i = 0; i < 5; i++) { _infoCache[i] = new List <RSAREntryNode>(); Type t = null; RuintList *list = (RuintList *)((uint)baseAddr + typeList[i]); sbyte * str, end; switch (i) { case 0: t = typeof(RSARSoundNode); break; case 1: t = typeof(RSARBankNode); break; case 2: t = typeof(RSARPlayerInfoNode); break; case 3: continue; //Files case 4: t = typeof(RSARGroupNode); break; //Last group entry is null } for (int x = 0; x < list->_numEntries; x++) { VoidPtr addr = list->Get(baseAddr, x); ResourceNode parent = this; RSAREntryNode n = Activator.CreateInstance(t) as RSAREntryNode; n._origSource = n._uncompSource = new DataSource(addr, 0); n._infoIndex = x; if (i == 4 && x == list->_numEntries - 1) { n._name = "<null>"; n._parent = this; _nullGroup = n as RSARGroupNode; } else { str = offset + stringOffsets[n.StringId]; for (end = str; *end != 0; end++) { ; } while ((--end > str) && (*end != '_')) { ; } if (end > str) { parent = CreatePath(parent, str, (int)end - (int)str); n._name = new String(end + 1); } else { n._name = new String(str); } } n.Initialize(parent, addr, 0); _infoCache[i].Add(n); } } ftr = *(INFOFooter *)((uint)baseAddr + typeList[5]); foreach (RSARFileNode n in Files) { if (!(n is RSARExtFileNode)) { n.GetName(); } } _rootIds = new int[4]; _symbCache = new List <SYMBMaskEntry> [4]; bint *offsets = (bint *)((VoidPtr)symb + 12); for (int i = 0; i < 4; i++) { _symbCache[i] = new List <SYMBMaskEntry>(); SYMBMaskHeader *hdr = (SYMBMaskHeader *)((VoidPtr)symb + 8 + offsets[i]); //Console.WriteLine("Root Index = " + hdr->_rootId); _rootIds[i] = hdr->_rootId; for (int x = 0; x < hdr->_numEntries; x++) { SYMBMaskEntry *e = &hdr->Entries[x]; _symbCache[i].Add(*e); //Console.WriteLine(String.Format("[{5}] {0}, {1}, {2} - {4}", e->_bit != -1 ? e->_bit.ToString().PadLeft(3) : " ", e->_leftId != -1 ? e->_leftId.ToString().PadLeft(3) : " ", e->_rightId != -1 ? e->_rightId.ToString().PadLeft(3) : " ", e->_index != -1 ? e->_index.ToString().PadLeft(3) : " ", new string(offset + stringOffsets[e->_stringId]), x.ToString().PadLeft(3))); } } //Sort(true); }
private void GetFiles() { INFOFileHeader * fileHeader; INFOFileEntry * fileEntry; RuintList * entryList; INFOGroupHeader *group; INFOGroupEntry * gEntry; RSARFileNode n; DataSource source; RSARHeader * rsar = Header; //SYMBHeader* symb = rsar->SYMBBlock; //sbyte* offset = (sbyte*)symb + 8; //buint* stringOffsets = symb->StringOffsets; //Get ruint collection from info header VoidPtr infoCollection = rsar->INFOBlock->_collection.Address; //Info has 5 groups: //Sounds 0 //Banks 1 //Types 2 //Files 3 //Groups 4 //Convert to ruint buffer ruint *groups = (ruint *)infoCollection; //Get file ruint list at file offset (groups[3]) RuintList *fileList = (RuintList *)((uint)groups + groups[3]); //Get the info list RuintList *groupList = rsar->INFOBlock->Groups; //Loop through the ruint offsets to get all files for (int x = 0; x < fileList->_numEntries; x++) { //Get the file header for the file info fileHeader = (INFOFileHeader *)(infoCollection + fileList->Entries[x]); entryList = fileHeader->GetList(infoCollection); if (entryList->_numEntries == 0) { //Must be external file. n = new RSARExtFileNode(); source = new DataSource(fileHeader, 0); } else { //Use first entry fileEntry = (INFOFileEntry *)entryList->Get(infoCollection, 0); //Find group with matching ID group = (INFOGroupHeader *)groupList->Get(infoCollection, fileEntry->_groupId); //Find group entry with matching index gEntry = (INFOGroupEntry *)group->GetCollection(infoCollection)->Get(infoCollection, fileEntry->_index); //Create node and parse source = new DataSource((int)rsar + group->_headerOffset + gEntry->_headerOffset, gEntry->_headerLength); if ((n = NodeFactory.GetRaw(source) as RSARFileNode) == null) { n = new RSARFileNode(); } n._audioSource = new DataSource((int)rsar + group->_waveDataOffset + gEntry->_dataOffset, gEntry->_dataLength); n._infoHdr = fileHeader; } n._fileIndex = x; n._parent = this; //This is so that the node won't add itself to the child list. n.Initialize(this, source); _files.Add(n); } //foreach (ResourceNode r in _files) // r.Populate(); }
protected override void OnPopulate() { RSARFolderNode g = new RSARFolderNode(); g.Name = "Info"; g.Parent = this; g = new RSARFolderNode(); g.Name = "Files"; g.Parent = this; //Retrieve all files to attach to entries GetFiles(); //Enumerate entries, attaching them to the files. RSARHeader *rsar = Header; SYMBHeader *symb = rsar->SYMBBlock; sbyte * offset = (sbyte *)symb + 8; buint * stringOffsets = symb->StringOffsets; VoidPtr types = (VoidPtr)rsar->INFOBlock + 8; ruint * typeList = (ruint *)types; //Iterate through group types for (int i = 0; i < 5; i++) { Type t = null; ruint *entryList = (ruint *)((uint)types + typeList[i] + 4); int entryCount = *((bint *)entryList - 1); sbyte *str, end; switch (i) { case 0: t = typeof(RSARSoundNode); break; case 1: t = typeof(RSARBankNode); break; case 2: t = typeof(RSARTypeNode); break; case 3: continue; case 4: t = typeof(RSARGroupNode); break; } for (int x = 0; x < entryCount; x++) { ResourceNode parent = Children[0]; RSAREntryNode n = Activator.CreateInstance(t) as RSAREntryNode; n._origSource = n._uncompSource = new DataSource(types + entryList[x], 0); str = offset + stringOffsets[n.StringId]; for (end = str; *end != 0; end++) { ; } while ((--end > str) && (*end != '_')) { ; } if (end > str) { parent = CreatePath(parent, str, (int)end - (int)str); n._name = new String(end + 1); } else { n._name = new String(str); } n.Initialize(parent, types + entryList[x], 0); //n.Populate(); } } //Sort(true); }
//public RSARGroupNode _nullGroup; public override void OnPopulate() { //Enumerate entries, attaching them to the files. RSARHeader *rsar = Header; SYMBHeader *symb = rsar->SYMBBlock; sbyte * offset = (sbyte *)symb + 8; buint * stringOffsets = symb->StringOffsets; VoidPtr baseAddr = (VoidPtr)rsar->INFOBlock + 8; ruint * typeList = (ruint *)baseAddr; //Iterate through group types for (int i = 0; i < 5; i++) { Type t = null; switch (i) { case 0: t = typeof(RSARSoundNode); break; case 1: t = typeof(RSARBankNode); break; case 2: t = typeof(RSARPlayerInfoNode); break; case 3: continue; //Files case 4: t = typeof(RSARGroupNode); break; //Last group entry has no name } _infoCache[i] = new List <RSAREntryNode>(); RuintList *list = (RuintList *)((uint)baseAddr + typeList[i]); sbyte * str, end; for (int x = 0; x < list->_numEntries; x++) { VoidPtr addr = list->Get(baseAddr, x); ResourceNode parent = this; RSAREntryNode n = Activator.CreateInstance(t) as RSAREntryNode; n._origSource = n._uncompSource = new DataSource(addr, 0); if (n.StringId >= 0) { str = offset + stringOffsets[n.StringId]; for (end = str; *end != 0; end++) { ; } while ((--end > str) && (*end != '_')) { ; } if (end > str) { parent = CreatePath(parent, str, (int)end - (int)str); n._name = new String(end + 1); } else { n._name = new String(str); } } else { n._name = null; } n._infoIndex = x; n.Initialize(parent, addr, 0); _infoCache[i].Add(n); } _ftr = *(INFOFooter *)((uint)baseAddr + typeList[5]); foreach (RSARFileNode n in Files) { if (!(n is RSARExtFileNode)) { n.GetName(); } } } }
protected override void OnPopulate() { //Get files GetFiles(); //Enumerate entries, attaching them to the files. RSARHeader *rsar = Header; SYMBHeader *symb = rsar->SYMBBlock; sbyte * offset = (sbyte *)symb + 8; buint * stringOffsets = symb->StringOffsets; VoidPtr gOffset = (VoidPtr)rsar->INFOBlock + 8; ruint * groups = (ruint *)gOffset; for (int i = 0; i < 5; i++) { Type t = null; ruint *list = (ruint *)((uint)groups + groups[i] + 4); int count = *((bint *)list - 1); sbyte *str, end; switch (i) { case 0: t = typeof(RSARSoundNode); break; case 1: t = typeof(RSARBankNode); break; case 2: t = typeof(RSARTypeNode); break; case 3: { //Get files //INFOFileHeader* fileHeader; //INFOFileEntry* fileEntry; //RuintList* entryList; //INFOGroupHeader* group; //INFOGroupEntry* gEntry; //RuintList* groupList = rsar->INFOBlock->Groups; //RSARFileNode n; //DataSource source; //for (int x = 0; x < count; x++) //{ // fileHeader = (INFOFileHeader*)(gOffset + list[x]); // entryList = fileHeader->GetList(gOffset); // if (entryList->_numEntries == 0) // { // //Must be external file. // n = new RSARExtFileNode(); // source = new DataSource(fileHeader, 0); // } // else // { // //use first entry // fileEntry = (INFOFileEntry*)entryList->Get(gOffset, 0); // //Find group with matching ID // group = (INFOGroupHeader*)groupList->Get(gOffset, fileEntry->_groupId); // //Find group entry with matching index // gEntry = (INFOGroupEntry*)group->GetCollection(gOffset)->Get(gOffset, fileEntry->_index); // //Create node and parse // source = new DataSource((int)rsar + group->_headerOffset + gEntry->_headerOffset, gEntry->_headerLength); // if ((n = NodeFactory.GetRaw(source) as RSARFileNode) == null) // n = new RSARFileNode(); // n._audioSource = new DataSource((int)rsar + group->_dataOffset + gEntry->_dataOffset, gEntry->_dataLength); // } // n._fileIndex = x; // n._parent = this; //This is so that the node won't add itself to the child list. // n.Initialize(this, source); // _files.Add(n); //} continue; } case 4: t = typeof(RSARGroupNode); break; } for (int x = 0; x < count; x++) { ResourceNode parent = this; RSAREntryNode n = Activator.CreateInstance(t) as RSAREntryNode; n._origSource = n._uncompSource = new DataSource(gOffset + list[x], 0); str = offset + stringOffsets[n.StringId]; for (end = str; *end != 0; end++) { ; } while ((--end > str) && (*end != '_')) { ; } if (end > str) { parent = CreatePath(parent, str, (int)end - (int)str); n._name = new String(end + 1); } else { n._name = new String(str); } n.Initialize(parent, gOffset + list[x], 0); } } Sort(true); }
protected override void OnPopulate() { RSARHeader *rsar = Header; INFOHeader *info = Header->INFOBlock; VoidPtr offset = &info->_collection; RuintList * list = (RuintList *)info->_collection[_listIndex]; int count = list->_numEntries; Type t; switch (_listIndex) { case 2: t = typeof(RSARTypeNode); break; //Types case 3: //Files INFOFileHeader * fileHeader; INFOFileEntry * fileEntry; RuintList * entryList; INFOGroupHeader *group; INFOGroupEntry * gEntry; RuintList * groupList = info->Groups; RSARFileNode n; DataSource source; for (int i = 0; i < count; i++) { fileHeader = (INFOFileHeader *)list->Get(offset, i); entryList = fileHeader->GetList(offset); if (entryList->_numEntries == 0) { //Must be external file. n = new RSARExtFileNode(); n._fileIndex = i; n.Initialize(this, fileHeader, 0); } else { //use first entry fileEntry = (INFOFileEntry *)entryList->Get(offset, 0); //Find group with matching ID group = (INFOGroupHeader *)groupList->Get(offset, fileEntry->_groupId); //Find group entry with matching index gEntry = (INFOGroupEntry *)group->GetCollection(offset)->Get(offset, fileEntry->_index); //Create node and parse source = new DataSource((int)rsar + group->_headerOffset + gEntry->_headerOffset, gEntry->_headerLength); if ((n = NodeFactory.GetRaw(source) as RSARFileNode) == null) { n = new RSARFileNode(); } n._audioSource = new DataSource((int)rsar + group->_dataOffset + gEntry->_dataOffset, gEntry->_dataLength); n._fileIndex = i; n.Initialize(this, source); } } return; case 4: t = typeof(RSARGroupNode); break; //Groups default: return; } for (int i = 0; i < count; i++) { ResourceNode node = Activator.CreateInstance(t) as ResourceNode; node.Initialize(this, list->Get(offset, i), 0); } base.OnPopulate(); }