steveju
Demon Girl
- Joined
- Jun 24, 2016
- Messages
- 81
- Reputation score
- 39
I was looking into DX archives because DXExtractor didn't work with some of the newer games that are being released, making it impossible to extract the game files for translation or modification. The archives are made with
Background
Implementation
Why is this needed?
How to use DxaDecodeDEC (example):
It's also easy to encode loose files back to archives with the tools provided, so translators can make archives that are compatible with the game after editing the source files without having to use the UI of eg. WOLF RPG Editor.
How to use DxaEncodeDEC (example):
It will create BasicData.dxa that you can rename to BasicData.wolf and it'll work with the game.
Requirements
tools.jar needs JRE from:
Included in this post are...
tool.zip - a simple tool that can take the encoded HEX (base 16) string, bruteforce it and decode it to DEC (base 10) and regular printable text/ASCII. It can also convert a string into encoded HEX (Windows/Linux/MacOS)
DxaDecodeDEC.zip - Altered version of DxaDecode that uses integers instead of characters as input for keystring (Windows only)
DxaEncodeDEC.zip - Altered version of DxaEncode that uses integers instead of characters as input for keystring (Windows only)
There's not much error checking in the files. They work with the correct input, will probably crash and burn with incorrect.
Remember to hit that "Add to reputation" button
.
You must be registered to see the links
and they are used by WOLF RPG Maker and other RPG games. I found that the encryption, while easy-ish to bypass, is hard because there are no tools available that worked.
You must be registered to see the links
was a pretty good tool for the job, but it hasn't been updated to support the newer archive formats and the tool that comes with DX Library, DxaDecode, can't handle non-ascii keys. DXExtract skips the key generation process and uses post-encryption keys in HEX to unpack the archives which was a cool idea.Background
DX archive keys are not really encrypted that well. The resulting key looks complicated eg. 1223344556677889900AABBC, but actually the long key is "encrypted" for each character individually... and since DX Library source code is available, we also know how every single character is calculated (see code). What this means for us is that we can easily decode the encryption string back to it's original form since we're not trying to decode the whole key, we're decoding it a single character at a time.
The number of different chars for each individual character in the keystring is 255 or 0xFF. The keys are always 12 characters long, if they're longer than that, the encryption function ignores extra characters and if it's shorter, it'll just append the encryption string to itself (before key[x] operations) to make it 12 characters long.
Eg. Viocide Vore Side Action RPG's password "boost" becomes "boostboostbo" and Uwasa no yado musume's "quingamepakcode" becomes "quingamepakc".
In the original DX Libs the string is basically split into chars, chars converted into binary, the binary for each char is placed into an array and then the operations listed above are done to each object in the array.
Eg. first character in Viocide is "b" which is 01100010 in binary, then we do "bitwise NOT" -operation to it, which results in 10011101, which is 9D in HEX (9DF6E5C88BCE90129B0BF0A3) and so on...
The encoding is ~"b" = 9D. To reverse this process, we just try a different x in ~x = 9D until we get one that results in 9D... Yes I know, in this case bitwise NOT is actually non-destructive and we can just do ~ on 10011101 and it'll come back as 01100010, which is the original character. This was just an example.
Code:
key[0] = ~key[0] ;
key[1] = ( key[1] >> 4 ) | ( key[1] << 4 ) ;
key[2] = key[2] ^ 0x8a ;
key[3] = ~( ( key[3] >> 4 ) | ( key[3] << 4 ) ) ;
key[4] = ~key[4] ;
key[5] = key[5] ^ 0xac ;
key[6] = ~key[6] ;
key[7] = ~( ( key[7] >> 3 ) | ( key[7] << 5 ) ) ;
key[8] = ( key[8] >> 5 ) | ( key[8] << 3 ) ;
key[9] = key[9] ^ 0x7f ;
key[10] = ( ( key[10] >> 4 ) | ( key[10] << 4 ) ) ^ 0xd6;
key[11] = key[11] ^ 0xcc;
Eg. Viocide Vore Side Action RPG's password "boost" becomes "boostboostbo" and Uwasa no yado musume's "quingamepakcode" becomes "quingamepakc".
In the original DX Libs the string is basically split into chars, chars converted into binary, the binary for each char is placed into an array and then the operations listed above are done to each object in the array.
Eg. first character in Viocide is "b" which is 01100010 in binary, then we do "bitwise NOT" -operation to it, which results in 10011101, which is 9D in HEX (9DF6E5C88BCE90129B0BF0A3) and so on...
The encoding is ~"b" = 9D. To reverse this process, we just try a different x in ~x = 9D until we get one that results in 9D... Yes I know, in this case bitwise NOT is actually non-destructive and we can just do ~ on 10011101 and it'll come back as 01100010, which is the original character. This was just an example.
Implementation
Now we can make an app that checks for every input variation possible until we get a match using the functions pulled from the source code. Do that for all characters and we have the original key.
Example code from tool.jar (slightly edited):
The resulting numbers are then converted to characters and put together to form a string, which only works with the original DxaDecode if the characters in the keystring are printable. Some DX archives use keys that have non-printable characters which makes them impossible to use with DxaDecode, which is probably why DXExtract was made back in the day, as it solved this issue. Eg. the example usage below contains a character that has a value of 7 which isn't writable in
Example code from tool.jar (slightly edited):
Code:
//try each possible character or value
for (int x = 1; x < 255; x++) {
//calculate the encoded character for each character until we get a match
if (key[1].equals(((x >> 4) | (x << 4))) {
// this is the original character or rather the integer that represents that character
return x;
}
// something goes terribly wrong
return -1;
}
and so on...
You must be registered to see the links
(it's BEL/Bell).Why is this needed?
Right now there is not much use for this yet (as in there's probably no archive out there that forces someone to use this... yet), as DXExtract supports the older archives and newer archive types are slowly just rolling out. Newer WOLF RPG titles updated their archives, but also changed the common encoding key to one that had an ASCII counterpart that the existing DxaDecode was able to use (key: 8P@(rO!p;s58). Tool.jar was used to decode the password from the encoded HEX used by Game.exe (you can analyze it with eg.
You can still use this modified tool. Say you want to use DxaDecode to extract contents from older Wolf RPG games but for some reason can't use DXExtract, the code for them in DXExtract is B39DA084D737531FF1081880. If we decode that back to the original key that was used, we get "76 217 42 183 40 155 172 7 62 119 236 76". Each number represents an ASCII character, small numbers don't have any ASCII counterpart and some of them like 62 are escape characters (>), so DxaDecode will fail to work as it can't read the key. With the edited version it's possible to input those impossible characters and decode the files. The included DEC versions are made and compiled from the latest source code at the time of posting (v1.06)... Or you could use these to troll someone and hand them a custom made archive.
You must be registered to see the links
).You can still use this modified tool. Say you want to use DxaDecode to extract contents from older Wolf RPG games but for some reason can't use DXExtract, the code for them in DXExtract is B39DA084D737531FF1081880. If we decode that back to the original key that was used, we get "76 217 42 183 40 155 172 7 62 119 236 76". Each number represents an ASCII character, small numbers don't have any ASCII counterpart and some of them like 62 are escape characters (>), so DxaDecode will fail to work as it can't read the key. With the edited version it's possible to input those impossible characters and decode the files. The included DEC versions are made and compiled from the latest source code at the time of posting (v1.06)... Or you could use these to troll someone and hand them a custom made archive.
How to use DxaDecodeDEC (example):
Code:
DxaDecodeDEC 76 217 42 183 40 155 172 7 62 119 236 76 EV-PIC.wolf
How to use DxaEncodeDEC (example):
Code:
DxaEncodeDEC 76 217 42 183 40 155 172 7 62 119 236 76 BasicData
Requirements
tools.jar needs JRE from:
You must be registered to see the links
Included in this post are...
tool.zip - a simple tool that can take the encoded HEX (base 16) string, bruteforce it and decode it to DEC (base 10) and regular printable text/ASCII. It can also convert a string into encoded HEX (Windows/Linux/MacOS)
DxaDecodeDEC.zip - Altered version of DxaDecode that uses integers instead of characters as input for keystring (Windows only)
DxaEncodeDEC.zip - Altered version of DxaEncode that uses integers instead of characters as input for keystring (Windows only)
There's not much error checking in the files. They work with the correct input, will probably crash and burn with incorrect.
Remember to hit that "Add to reputation" button
ToxicShock said:no trust in files shared by someone with red rep and <20 posts.
Attachments
-
159.3 KB Views: 1,865
-
159 KB Views: 742
-
5.3 KB Views: 878
Last edited: