|
很久以前,在电驴上一不小心下载了一个HGAME(^^),当时在网上查了查,只知道这个游戏是用Krkr做的(小日本有很多这种制作工具,专门用来生产这种垃圾游戏,不过里面的图片资源我们就先收下了,呵呵),再看看XP3后缀的包文件也看不出什么头绪,所以就一直放在那里没去动过。前几天专门到网上搜了搜,找了些代码,下面就简单的描述一下XP3包文件的格式,同时对那位日本老兄致一下敬。 文件开头是文件标志,为"XP3" 偏移11处是文件信息表的位置,uint64(瞧,人家已经考虑64位了。。。) 从上面的值指示跳到文件信息表处,有以下一个结构: struct sXP3Info { byte_t zlib; // 文件信息表是否用zlib压缩过(难怪一开始看不出什么头绪) uint64 psize; // 文件信息表在包文件中的大小 #if zlib uint64 rsize; // 文件信息表解压后的大小 #endif byte_t fileInfo[psize]; // 文件信息表数据 }; 成功获取文件信息表数据后可以得到以下一组结构的数组,用于描述包中文件的信息: struct sXP3File { uint32 tag1; // 标志1,"File" 0x656c6946 uint64 fileSize; // 文件信息数据大小
uint32 tag2; // 标志2,"info" 0x6f666e69 uint64 infoSize; // 文件基本数据大小 uint32 protect; // 估计是表示此文件是否加过密 uint64 rsize; // 文件原始大小 uint64 psize; // 文件包中大小 uint16 nameLen; // 文件名长度(指的是UTF-16字符个数) wchar_t fileName[nameLen]; // 文件名(UTF-16LE编码,无0结尾)
uint32 tag3; // 标志3,"segm" 0x6d676573 uint64 segmSize; // 文件段数据大小 uint32 compress; // 文件是否用zlib压缩过 uint64 offset; // 文件开始的位置 uint64 rsize; uint64 psize; #if fileSize - infoSize - segmSize - 24 > 0 uint32 tag4; // 标志4,"adlr" 0x726c6461 uint64 adlrSize; // 文件附加数据大小,一般是4 uint32 key; // 附加数据,用于解密 #endif }; 下面写的是一些解密方法,似乎不同的游戏有不同的解密方法,只能通过exe或游戏目录来区别。而且包中并不是所有文件都加密的,我下的那个都没有加密。 // Braban InitKey = ((key ^ 0xff) & 0xff) - 1; for (uint32 i = 0; i < size; i++) data[ i ] ^= (byte_t)InitKey;
// Fate for (uint32 i = 0; i < size; i++) { data[ i ] ^= 0x36; if (offset + i == 0x13) data[ i ] ^= 0x01; if (offset + i == 0x2EA29) data[ i ] ^= 0x03; }
// Hachukano Key = 0; InitKey = key ^ 0x03020100; for (uint32 i = 0; i < size; i += 4) { if ((i & 255) == 0) Key = 0; else Key += 0x04040404; *(dword_t*)(&data[ i ]) ^= InitKey ^ Key; }
// Himesyo Key = 0; InitKey = key ^ 0x03020100 ^ 0xffffffff; for (uint32 i = 0; i < size; i += 4) { if ((i & 255) == 0) Key = 0; else Key += 0x04040404; *(dword_t*)(&data[ i ]) ^= InitKey ^ Key; }
// SisMiko InitKey = ~((key << 16) | (key >> 16)); for (uint32 i = 0; i < size; i += 4) *(dword_t*)(&data[ i ]) ^= InitKey;
// TokiPaku InitKey = ~(*(dword_t*)fileExt); // 文件扩展名 for (uint32 i = 0; i < size; i += 4) *(dword_t*)(&data[ i ]) ^= InitKey;
// Yotsunoha InitKey = (((key >> 8) & 0xff) ^ (key & 0xff)); for (uint32 i = 0; i < size; i++) data[ i ] ^= (byte_t)InitKey;
|
一共有 2 条评论
我刚提取了一个游戏的文本,但是苦于无法重新封包回去,
看见博主的文章,想来也有一定的技术,如果可以的话,希望能交个朋友
向你学习下技术,感谢
我的邮箱 healthlolicon@gmail.com