Skip to content
View in the app

A better way to browse. Learn more.

ResHax

A full-screen app on your home screen with push notifications, badges and more.

To install this app on iOS and iPadOS
  1. Tap the Share icon in Safari
  2. Scroll the menu and tap Add to Home Screen.
  3. Tap Add in the top-right corner.
To install this app on Android
  1. Tap the 3-dot menu (⋮) in the top-right corner of the browser.
  2. Tap Add to Home screen or Install app.
  3. Confirm by tapping Install.
Help us keep the site running.

XianOL (.pak)

Featured Replies

  • Author
  • Localization

aluigi, posted Tue Sep 09, 2014 12:39 pm (443)


http://aluigi.org/papers/bms/others/xianol.bms

It uses a work-around to extract the files because the index table in the archive is encrypted/obfuscated.
For 8.pak I added a work-around to extract an mp3 file, because the script works only with compressed files (they are splitted in chunks).

So you will probably have problems with other archives.
  • Author
  • Localization

happyend, posted Tue Sep 09, 2014 1:37 pm (445)


very cool,but,unpack 7.pak get some error
  • Author
  • Localization

aluigi, posted Tue Sep 09, 2014 1:41 pm (447)


It looks like you have reached the end of the archive, so don't worry.
Check the extracted files, their total size should be bigger than the input archive.
  • Author
  • Localization

happyend, posted Tue Sep 09, 2014 2:30 pm (448)


Thanks :)
  • Author
  • Localization

Ekey, posted Tue Sep 09, 2014 4:55 pm (451)


Small info

Code:
struct PAKHeader
{
   DWORD dwID; // esl\x1A
   SHORT sNulls;
   DWORD dwHeaderSize;
   DWORD dwArchiveSize;
   DWORD dwHashTableOffset;
   SHORT sVersion; // 3
   DWORD dwEntryTableOffset;
   DWORD dwEntryTableSize; // shl 4
   DWORD dwHashTableSize; // shl 4
};


It's 100% modified MoPAQ. Algo and more info in attach :)
  • Author
  • Localization

aluigi, posted Tue Sep 09, 2014 5:42 pm (452)


Do you know that your pseudo code is slightly different than the assembly code?
Code:
   SHL EDI,0x15
   ADD EDI,0x7F98679
and
Code:
<< 19) - 0x55E0129A
Anyway doesn't give a correct result.
  • Author
  • Localization

Ekey, posted Tue Sep 09, 2014 5:46 pm (453)


Olly code is slightly different from the code IDA. from IDA

Code:
      shl   edi, 13h
      sub   edi, 55E0129Ah
      shr   esi, 0Bh


Here my works code. One problem with decrypting entry table

Edited: See below
  • Author
  • Localization

CriticalError, posted Wed Sep 10, 2014 3:08 am (459)


wow thanks for that Ekey and alugi, thats great

@happyend

so can you provide which format use this game for 3D Models?
  • Author
  • Localization

aluigi, posted Wed Sep 10, 2014 8:55 am (460)


The entry table is still invalid, do you think it's the password to be wrong?
I tried also using 21 and 0x7F98679 but still wrong.

I compiled it with both Gcc and VS and I noticed that the output changes and it's ever wrong.
Tried also to call pPAK_Init() and handling the entry before the hash but nothing, still wrong.
  • Author
  • Localization

Ekey, posted Wed Sep 10, 2014 10:08 am (462)


aluigi wrote:
The entry table is still invalid

Why?

aluigi wrote:
Tried also to call pPAK_Init() and handling the entry before the hash but nothing, still wrong.

pPAK_Init() used for initializing tables and they are always the same so that the function is not used.

aluigi wrote:
do you think it's the password to be wrong?

Password need only for generate dwSeed1 and i replaced this code to already generated dwSeed1 for each table.

aluigi wrote:
I compiled it with both Gcc and VS and I noticed that the output changes and it's ever wrong.
Tried also to call pPAK_Init() and handling the entry before the hash but nothing, still wrong.


For me works perfect. All tables dumped without any problems. See attach.

First you need to read the table of hashes to get the index that contains the records of the file offset, compressed size, real size, and ect.
Skip first 0x30 bytes.

Code:
struct HashTable
{
   DWORD dwHashA;
   DWORD dwHashB;
   DWORD dwNull;
   DWORD dwIndex; // dwIndex * 16 & 0xFFFFFFFF
};


Now reading entry

Code:
goto dwIndex;


Code:
struct EntryTable
{
   DWORD dwOffset;
   DWORD dwZSize;
   DWORD dwSize;
   DWORD dwFlag;
};


Flags

Code:
FILE_IMPLODE = 0x00000100 (File is compressed using PKWARE)
FILE_COMPRESS = 0x00000200 (File is compressed using combination of compression methods)
FILE_ENCRYPTED = 0x00010000 (The file is encrypted)
FILE_EXISTS = 0x80000000 (File exists)


Example flag from 0.pak

Code:
Flag: 0x80010100 -> FILE_IMPLODE   FILE_ENCRYPTED   FILE_EXISTS
  • Author
  • Localization

aluigi, posted Wed Sep 10, 2014 11:32 am (464)


Ok, great.
Apparently I got one of the first versions of your attachment (without exe) and so it didn't work.

I have updated the script, now everything seems to work perfectly:
http://aluigi.org/papers/bms/others/xianol.bms

The following is the dll as reference:
http://aluigi.org/papers/bms/others/xolpak.c

Well done Ekey
  • Author
  • Localization

Ekey, posted Wed Sep 10, 2014 11:51 am (465)


Good job! :)
  • Author
  • Localization

Ekey, posted Wed Sep 10, 2014 1:17 pm (466)


Continued..... In MoPAQ count tables 5.

1) (attributes) - attributes for files inside pak (not used in this game)
2) (blocktable) - for us it is entry table
3) (hashtable) - table with hashes
4) (listfile) - table with filenames (encrypted and compressed by Zlib) dwIndex for this file = 0, and of course in the entry table = first record
5) (version) - :)

(listfile) for 0.pak

Code:
Offset: 707801 (7370753.)
ZSize: 2E5 (741.)
Size: 7D9 (2009.)


Decryption algo (dwSeed = 0xC16D37E2)

Code:
int pPAK_Decrypt_FileData(unsigned int dwSize, int dwSeed, int pBuffer)
{
  unsigned int pSize1;
  bool pSize2; // zf@1
  int Buffer; // esi@1
  int result; // eax@1
  int dwTemp1; // eax@2
  int dwTemp2; // ecx@2

  pSize1 = dwSize >> 2;
  pSize2 = dwSize >> 2 == 0;
  Buffer = pBuffer;
  result = 0xEEEEEEEEu;
  if ( !dwSize >> 2 == 0 )
  {
    do
    {
      dwTemp1 = *(DWORD *)&pTable_e[4 * (unsigned __int8)dwSeed] result;
      dwTemp2 = *(DWORD *)Buffer ^ (dwTemp1 dwSeed);
      *(DWORD *)Buffer = dwTemp2;
      dwSeed = ((~dwSeed > 11);
      Buffer = 4;
      --pSize1;
      result = 33 * dwTemp1 dwTemp2 3;
    }
    while ( pSize1 );
  }
  return result;
}
  • Author
  • Localization

aluigi, posted Wed Sep 10, 2014 2:37 pm (467)


ok so the algorithm is just the same, what changes is the password and the 2 numbers used for "<< A B".
Do you have the password used to generate that dwSeed 0xC16D37E2?
  • Author
  • Localization

Ekey, posted Wed Sep 10, 2014 2:43 pm (468)


He has already has been generated.
  • Author
  • Localization

aluigi, posted Wed Sep 10, 2014 2:47 pm (469)


But don't you have the original password?
It would be useful for other games that use different passwords.
  • Author
  • Localization

aluigi, posted Wed Sep 10, 2014 3:08 pm (470)


Tested now, it looks like that dwSeed doesn't work for 8.pak. The first file decrypts incorrectly.

Anyway I have updated the script.
  • Author
  • Localization

Ekey, posted Wed Sep 10, 2014 3:22 pm (471)


Well i guess this dwSeed only for listfile. I have no idea how it generate :/
Guest
This topic is now closed to further replies.

Account

Navigation

Search

Search

Configure browser push notifications

Chrome (Android)
  1. Tap the lock icon next to the address bar.
  2. Tap Permissions → Notifications.
  3. Adjust your preference.
Chrome (Desktop)
  1. Click the padlock icon in the address bar.
  2. Select Site settings.
  3. Find Notifications and adjust your preference.