private int GetArchType(sio.BinaryReader br, long len, out int fileCount) { sio.MemoryStream ms; long prevPos; long lastPos; byte b; byte[] bb; int size; int i; bool tru; bb = new byte[0xfc]; ms = (sio.MemoryStream)br.BaseStream; fileCount = 0; prevPos = ms.Position; lastPos = prevPos + len; if (lastPos < 0x4) return 0; if (br.ReadInt32() == 0x64) { fileCount = br.ReadInt32(); size = (fileCount + 1) << 3; if (fileCount > 0) if (br.ReadInt32() == size) { ms.Position += size - 0xc - 0x8; size = br.ReadInt32() + br.ReadInt32(); if (size <= lastPos) return 1; } } fileCount = 0; ms.Position = prevPos; if (lastPos > 0xff) { while (ms.Position < lastPos) { for (i = 0; i < bb.Length; i++) { b = br.ReadByte(); if (b == 0) break; else if ((b < 0x20) || (b > 0x7f)) { i = 0; break; } bb[i] = b; } if (i > 0) { if (!stre.Regex.IsMatch(ste.ASCII.GetString(bb, 0, i), "^(\\w*[/.]*){1,}.\\w+$")) break; } else if (fileCount == 0) break; ms.Position += bb.Length - i - 1; size = br.ReadInt32(); if (size < 0 || size > lastPos) break; ms.Position += size; ms.AlignPos(0x40); if (size == 0) if (fileCount == 0) break; else if (lastPos - ms.Position < 0x800) return 2; fileCount++; } if (fileCount > 0) if (ms.Position == lastPos) return 2; } fileCount = 0; ms.Position = prevPos; if (br.ReadInt32() == 1) if (br.ReadInt32() == 0) if (br.ReadInt32() == 0x30525053) if (br.ReadInt32() == 0x20) if (br.ReadInt32() - len - 0x4 < 0x40) { fileCount = br.ReadInt16(); return 3; } #if DEBUG else throw new ArgumentException("spr0 size mismatch!"); else throw new ArgumentException("spr0 header size mismatch!"); #endif fileCount = 0; ms.Position = prevPos; if (br.ReadInt32() == 0) if (br.ReadInt32() - len - 0x4 < 0x40) if (br.ReadInt32() == 0x31444D50) //pmd1 if (br.ReadInt32() == 0) { fileCount = br.ReadInt32(); if (br.ReadInt32() == 0x3) return 4; #if DEBUG else throw new ArgumentException("pmd1 flag mismatch!"); #endif } fileCount = 0; ms.Position = prevPos; if (br.ReadInt32() == 0x9) if (br.ReadInt32() - len - 0x4 < 0x40) if (br.ReadInt32() == 0x30505854) //txp0 if (br.ReadInt32() == 0) { fileCount = br.ReadInt32(); return 5; } fileCount = 0; ms.Position = prevPos; if (br.ReadInt32() == 1) { br.ReadInt32(); if (br.ReadInt32() == 0x30424950) //pib0 if (br.ReadInt32() == 0) return 6; } if (len > 0x80) { fileCount = 0; //epl ms.Position = prevPos + 0x44; tru = (br.ReadInt32() & 0x40a00000) == 0x40a00000; ms.Position += 0x4; tru &= br.ReadInt32() == 0x3f800000; ms.Position += 0xc; tru &= br.ReadInt32() == 0x3f800000; ms.Position += 0x28; tru &= br.ReadInt32() == 0x90; if (tru) return 7; } fileCount = 0; //rmd ms.Position = prevPos; if (br.ReadUInt32() == 0xf0f000f0) { if (br.ReadInt32() == 0x2) if (br.ReadInt32() == 0x40000000) return 7; } else { ms.Position = prevPos; tru = br.ReadInt32() == 0x16; ms.Position += 0x8; tru &= br.ReadInt32() == 1; i = br.ReadInt32(); if ((i > -1) && ((i + ms.Position + 0x4) < lastPos)) { ms.Position += 0x4 + i; if (ms.Position < lastPos) tru &= br.ReadInt32() == 0x15; else tru = false; if (tru) return 7; } } fileCount = 0; ms.Position = prevPos; if (br.ReadInt32() == 0x34444542) //bed4 if (br.ReadInt32() == 0x3030) { br.ReadInt32(); if (br.ReadInt32() == 0) return 7; } fileCount = 0; ms.Position = prevPos; if (br.ReadInt32() == 0x004E4943) if (br.ReadInt32() == 1) return 8; return 0; }
private void ExtractTxp0(string extrPath, sio.BinaryReader br, long len) { sio.MemoryStream ms; int size; long startPos; long pos; int count; string name; int i; ms = (sio.MemoryStream)br.BaseStream; startPos = ms.Position; pos = 0; ms.Position += 0x10; count = br.ReadInt32(); pos += 0x14; ms.Position += count << 0x2; pos += count << 0x2; pos = misc.Align(pos, 0x40); ms.Position = startPos + pos; for (i = 0; i < count; i++) { ms.Position += 0x4; size = br.ReadInt32(); if (br.ReadInt32() != 0x30584D54) //tmx0 throw new ArgumentException("txp0 contains wrong tmx0"); ms.Position -= 0xc; name = misc.InsertCounter("tmx", gFileCount++); GetArchs(extrPath, name, ms, size); pos += size; pos = misc.Align(pos, 0x40); ms.Position = startPos + pos; //sw.WriteLine(name); } }
private void ExtractUnNamedBinary(string extrPath, sio.BinaryReader br, long len) { sio.MemoryStream ms; long pos; int size; long prevPos; long startPos; int count; string name; bool found; int i; ms = (sio.MemoryStream)br.BaseStream; startPos = ms.Position; name = null; found = false; if (br.ReadInt32() == 0x64) { count = br.ReadInt32(); prevPos = ms.Position; for (i = 0; i < count; i++) { ms.Position = prevPos; pos = br.ReadInt32(); size = br.ReadInt32(); ms.Position = startPos + pos; if (br.ReadInt32() == 0x2) { br.ReadInt32(); if (br.ReadInt32() == 0x30584D54) if (br.ReadInt32() == 0) { name = misc.InsertCounter("tmx", gFileCount++); found = true; } } if (!found) { ms.Position = startPos + pos; if (br.ReadInt32() == 0x7) { br.ReadInt32(); if (br.ReadInt32() == 0x3147534D) if (br.ReadInt32() == 0) { name = misc.InsertCounter("msg", gFileCount++); found = true; } } } ms.Position = startPos + pos; if (found) { sw.WriteLine(name); ms.Extract(extrPath + name, size); found = false; } else { name = misc.InsertCounter("dat", gFileCount++); GetArchs(extrPath, name, ms, size); } //sw.WriteLine(name); prevPos += 0x8; } } }
private void ExtractTmx0Ps2(string extrPath, sio.BinaryReader br, long len) { sio.MemoryStream ms; long startPos; long lastPos; long curPos; byte b; int size; bool found; string name; ms = (sio.MemoryStream)br.BaseStream; startPos = ms.Position; lastPos = startPos + len; curPos = ms.Position; size = 0; name = null; found = false; while (curPos < lastPos) { ms.Position = curPos; b = br.ReadByte(); if (b == 0x2) { if (br.ReadByte() == 0) if (br.ReadInt16() == 0) { size = br.ReadInt32(); if (br.ReadInt32() == 0x30584D54) //tmx0 if (br.ReadInt32() == 0) { name = misc.InsertCounter("tmx", gFileCount++); found = true; } } } else if (b == 0x15) { if (br.ReadByte() == 0) if (br.ReadInt16() == 0) { size = br.ReadInt32() + 0xc; br.ReadInt32(); if (br.ReadInt32() == 1) if (br.ReadInt32() == 0x8) { ms.Position += 0x4; if (br.ReadInt32() == 0x325350) //ps2 { name = misc.InsertCounter("ps2", gFileCount++); found = true; } } } } if (found) { ms.Position = curPos; sw.WriteLine(string.Format("{0:x8},{1:x8}", curPos - startPos, size)); sw.WriteLine(name); ms.Extract(extrPath + name, size); curPos += size - 1; found = false; } curPos++; } }
private void ExtractSpr0(string extrPath, sio.BinaryReader br, long len) { sio.MemoryStream ms; long pos; int size; long prevPos; long startPos; int count; string name; int i; ms = (sio.MemoryStream)br.BaseStream; startPos = ms.Position; ms.Position += 0x14; count = br.ReadInt16(); ms.Position += 0xa; prevPos = ms.Position; if (count == 0) { ms.Position = prevPos - 0x10; size = br.ReadInt32() - (int)(prevPos - startPos); ms.Position = prevPos; } else { br.ReadInt32(); size = br.ReadInt32(); ms.Position += (count - 1) << 0x3; size -= (int)(ms.Position - startPos); } name = misc.InsertCounter("dat", gFileCount++); GetArchs(extrPath, name, ms, size); for (i = 0; i < count; i++) { ms.Position = prevPos; br.ReadInt32(); pos = br.ReadInt32(); ms.Position = startPos + pos + 0x4; size = br.ReadInt32(); ms.Position -= 0x8; name = misc.InsertCounter("tmx", gFileCount++); GetArchs(extrPath, name, ms, size); //sw.WriteLine(name); prevPos += 0x8; } }
private void ExtractPmd1(string extrPath, sio.BinaryReader br, long len) { sio.MemoryStream ms; long startPos; long prevPos, subPrevPos; int cnt; int cmd, blkSize, blkCnt, offset; int iNmIdx, iCode, iOffset, iSize, iEplSize; string[] names; string name; int nameIdx; int i, j; ms = (sio.MemoryStream)br.BaseStream; startPos = ms.Position; ms.Position += 0x10; cnt = br.ReadInt32(); ms.Position += 0xc; names = null; nameIdx = 0; prevPos = ms.Position; for (i = 0; i < cnt; i++) { ms.Position = prevPos; cmd = br.ReadInt32(); blkSize = br.ReadInt32(); blkCnt = br.ReadInt32(); offset = br.ReadInt32(); ms.Position = startPos + offset; sw.WriteLine(string.Format("{0:x2},{1:x8},{2:x8}", cmd, blkSize, blkCnt)); if ((blkSize > 0) && (blkCnt > 0)) switch (cmd) { case 0x01: names = new string[blkCnt]; for (j = 0; j < blkCnt; j++) { names[j] = ms.ReadNTString(blkSize); ms.Position += blkSize - names[j].Length - 1; sw.WriteLine(names[j]); } break; case 0x02: name = misc.InsertCounter(names[nameIdx++], gFileCount++); GetArchs(extrPath, name, ms, blkSize); break; case 0x03: subPrevPos = ms.Position; for (j = 0; j < blkCnt; j++) { ms.Position = subPrevPos; iNmIdx = br.ReadInt32(); ms.Position += 0xc; iOffset = br.ReadInt32(); iSize = br.ReadInt32(); iCode = br.ReadInt32(); sw.WriteLine(string.Format("{0:x8},{1:x8}", iNmIdx, iCode)); name = misc.InsertCounter(names[iNmIdx], gFileCount++); ms.Position = startPos + iOffset; GetArchs(extrPath, name, ms, iSize); subPrevPos += blkSize; nameIdx++; } break; case 0x06: name = misc.InsertCounter(names[nameIdx++], gFileCount++); GetArchs(extrPath, name, ms, blkSize); break; case 0x07: subPrevPos = ms.Position; ms.Position = prevPos + 0x2c; iEplSize = br.ReadInt32(); for (j = 0; j < blkCnt; j++) { ms.Position = subPrevPos; iNmIdx = br.ReadInt32(); iOffset = br.ReadInt32(); if (j == blkCnt - 1) { iSize = iEplSize - iOffset; } else { ms.Position += 0xc; iSize = br.ReadInt32() - iOffset; } ms.Position = startPos + iOffset; sw.WriteLine(string.Format("{0:x8}", iNmIdx)); name = misc.InsertCounter(names[iNmIdx], gFileCount++); GetArchs(extrPath, name, ms, iSize); subPrevPos += blkSize; nameIdx++; } break; case 0x08: //07 check break; case 0x09: //03 check break; case 0x0a: name = misc.InsertCounter("fl1", gFileCount++); GetArchs(extrPath, name, ms, blkSize); break; case 0x0b: name = misc.InsertCounter("fl2", gFileCount++); GetArchs(extrPath, name, ms, blkSize); break; case 0x0c: name = misc.InsertCounter("txp", gFileCount++); GetArchs(extrPath, name, ms, blkSize); break; case 0x16: subPrevPos = ms.Position; blkSize /= blkCnt; for (j = 0; j < blkCnt; j++) { ms.Position = subPrevPos; iNmIdx = br.ReadInt32(); iOffset = br.ReadInt32(); ms.Position = startPos + iOffset + 0x4; iSize = br.ReadInt32(); ms.Position -= 0x8; sw.WriteLine(string.Format("{0:x8}", iNmIdx)); name = misc.InsertCounter(names[iNmIdx], gFileCount++); GetArchs(extrPath, name, ms, iSize); subPrevPos += blkSize; nameIdx++; } break; case 0x17: //16 check break; case 0x1b: name = misc.InsertCounter(names[nameIdx++], gFileCount++); GetArchs(extrPath, name, ms, blkSize); break; default: throw new ArgumentException(string.Format("Unknown pmd1 cmd: {0}, path: '{1}'", cmd, extrPath)); } prevPos += 0x10; } }
private void ExtractPib0(string extrPath, sio.BinaryReader br, long len) { sio.MemoryStream ms; int cmd; int size; string name; long startPos; long datPos; long pos; ms = (sio.MemoryStream)br.BaseStream; startPos = ms.Position; br.ReadInt32(); size = br.ReadInt32() - 0x10; ms.Position += 0x8; GetArchs(extrPath, misc.InsertCounter("dat", gFileCount++), ms, size); pos = size + 0x10; pos = misc.Align(pos, 0x40); ms.Position = startPos + pos; name = null; while (true) { cmd = br.ReadInt32(); size = br.ReadInt32(); switch (cmd) { case 0x01: if (br.ReadInt32() != 0x00503344) //d3p throw new ArgumentException("pib0 command and type mismatch"); name = misc.InsertCounter("d3p", gFileCount++); break; case 0x06: if (br.ReadInt32() != 0x3030444D) //md00 throw new ArgumentException("pib0 command and type mismatch"); name = misc.InsertCounter("md0", gFileCount++); break; case 0x08: if (br.ReadInt32() != 0x3030544D) //mt00 throw new ArgumentException("pib0 command and type mismatch"); name = misc.InsertCounter("mt0", gFileCount++); break; case 0x09: if (br.ReadInt32() != 0x30505854) //txp0 throw new ArgumentException("pib0 command and type mismatch"); name = misc.InsertCounter("txp", gFileCount++); break; case 0xff: if (br.ReadInt32() != 0x30444E45) //end0 throw new ArgumentException("pib0 command and type mismatch"); break; default: throw new ArgumentException("pib0 unknown command"); } if (cmd == 0xff) break; ms.Position -= 0xc; datPos = ms.Position; GetArchs(extrPath, name, ms, size); pos += (int)(ms.Position - datPos); pos = misc.Align(pos, 0x40); ms.Position = startPos + pos; //sw.WriteLine(name); } }
private void ExtractNamedBinary(string extrPath, sio.BinaryReader br, long len) { sio.MemoryStream ms; long lastPos; string name; byte b; byte[] bb; int size; int i; bb = new byte[0xfc]; ms = (sio.MemoryStream)br.BaseStream; lastPos = ms.Position + len; while (ms.Position < lastPos) { for (i = 0; i < bb.Length; i++) { b = br.ReadByte(); if (b == 0) break; else if ((b < 0x20) || (b > 0x7f)) { i = 0; break; } bb[i] = b; } ms.Position += bb.Length - i - 1; size = br.ReadInt32(); if ((size == 0) || (i == 0)) if (lastPos - ms.Position < 0x800) break; name = misc.InsertCounter(ste.ASCII.GetString(bb, 0, i), gFileCount++); GetArchs(extrPath, name, ms, size); //sw.WriteLine(name); ms.AlignPos(0x40); } }