逆向iReader解读ebk2电子书格式 -电脑资料

时间:2011-09-06 06:44:37
染雾
分享
WORD下载 PDF下载 投诉

发现从 iReader_1.3.2.0 版本起就采用了动态库把ebk相关解析函数封装了,

逆向iReader解读ebk2电子书格式

因此,这里我用的是iReader_1.3 ,apktool把它转成smali代码。

然后,通过研读smali 代码,初步获得的ebk2文档头结构如下:

代码:

+-------+---+-----------------------------+

|0 - 3|4|book_id|

+-------+---+-----------------------------+

|4 - 5|2|head_data_size|

+-------+---+-----------------------------+

|6 - 7|2|ebk_version|

+-------+---+-----------------------------+

|8 -11|4|ebk_size|

+-------+---+-----------------------------+

|12-75|64 |book_name|

+-------+---+-----------------------------+

|76-79|4|file_size|

+-------+---+-----------------------------+

|80-83|4|head_compress_size|

+-------+---+-----------------------------+

|84-87|4|first_compress_block_size|

+-------+---+-----------------------------+

|88-89|2|chapter_count|

+-------+---+-----------------------------+

|90-91|2|compress_block_count|

+-------+---+-----------------------------+

|92-95|4|media_count|

+-------+---+-----------------------------+

|96-99|4|media_data_length|

+-------+---+-----------------------------+

|100-103|4|txt_compress_size|

+-------+---+-----------------------------+

下面来验证一下逆向得出来的这个头结构对不对。

代码:

└─[$] <> xxd -l104 《白鹿原》.ebk2

0000000: 0000 0000 6800 0200 6636 0900 0a30 7d76....h...f6...0}v

0000010: 7f9e 9f53 0b30 0000 0000 0000 0000 0000...S.0..........

0000020: 0000 0000 0000 0000 0000 0000 0000 0000................

0000030: 0000 0000 0000 0000 0000 0000 0000 0000................

0000040: 0000 0000 0000 0000 0000 0000 f036 0e00.............6..

0000050: 9502 0000 0bab 0000 3000 0f00 0000 0000........0.......

0000060: 0000 0000 6933 0900....i3..

0-3 book_id

4 - 5head_data_size

0068 ,其十进制值为:104. 这与上图的结构是相符的。即整个ebk2文件头部信息数据总大小为 104个字节。

6-7 字节为 ebk文件版本,上面数据: 0200 ,其十六进制为:0002 ,即表示ebk2格式。

8 -11|4|ebk_size6636 0900

其十六进制为: 00093666

603750

我们查看下这个ebk2文件大小是不是这么大?

代码:

└─[$] <> ll 《白鹿原》.ebk2

-rwxrwxrwx 2 root root 603750 Oct 25 08:39 《白鹿原》.ebk2*

12-75|64 |book_name书名,共64个字节

代码:

0a30 7d76....h...f6...0}v

0000010: 7f9e 9f53 0b30 0000 0000 0000 0000 0000...S.0..........

0000020: 0000 0000 0000 0000 0000 0000 0000 0000................

0000030: 0000 0000 0000 0000 0000 0000 0000 0000................

0000040: 0000 0000 0000 0000 0000 0000

白鹿原 UTF-8 十六进制: 767D 9E7F 539F

《白鹿原》UTF-8 十六进制: 300A 767D 9E7F 539F 300B

后面的0000 是空格。

(可新建一文本文档,然后 在linux下用xxd或在windows下用EmEditor或WinHex以十六进制查看,即可查知其十六进制值)

由于一般机器普遍为小端字节序 (LE),因此,这个标题在ebk2文件中应该为:

7D76 7F9E 9F53

看上面的xxd dump出来的数据可知,是对的。

其标题是采用UTF-16LE编码存储的。

76-79|4|file_size 这个应该是解压后txt文件的大小

f036 0e00

000e 36f0 换算为十进制为 931568

代码:

└─[$] <> ll 《白鹿原》.ebk2.txt

-rwxrwxrwx 1 root root 931570 Nov3 16:57 《白鹿原》.ebk2.txt*

为什么是931570 ? 因为加上了两个字节的BOM (FFFE).

80-

83|4|head_compress_size

9502 0000

0000 0295 其十进制值为 661.

84-87|4|first_compress_block_size

0bab 0000

0000 ab0b 其十进制值为 43787.

88-89|2|chapter_count章节数量

3000

0030 其十进制值为 48.

用iReader打开这本书看了下,共34章,其中有14章是分为两个章节的。因此,48章是没错的。

90-91|2|compress_block_count

0f00

000f 为 15 .

64K * 15 = 65536 * 15 = 983040 >931568 (file_size解压后txt文件大小)

65536 * 14 = 917504 < 931568 ,因此,至少要分15个压缩段。

92-95|4|media_count

0000 0000

96-99|4|media_data_length

0000 0000

100-103|4|txt_compress_size

6933 0900

0009 3369 十进制为: 602985

===================================================

到这里,基本可以得出这样一个数量关系:

header.head_data_size + header.head_compress_size + header.txt_compress_size = ebk2文件的大小

三段数据的关系:

104(header.head_data_size) + 661(header.head_compress_size) + 602985(header.txt_compress_size) = 603750 (header.ebk_size)

章节信息索引表的开始位置,应该就是整个ebk2文件从0开始偏移104(header.head_data_size)个字节。

正文的offset 应该是整个ebk2文件从0开始偏移header.head_data_size + header.head_compress_size个字节。

这三段数据里,只有header没有压缩。

===================================================

现在再总结下104个字节的head的结构:

代码:

+-------+---+-----------------------------+----------------------------------------+

|0 - 3|4|book_id|一般为全0|

+-------+---+-----------------------------+----------------------------------------+

|4 - 5|2|head_data_size|ebk2文件的head大小,一般为104字节|

+-------+---+-----------------------------+----------------------------------------+

|6 - 7|2|ebk_version|ebk文件的版本|

+-------+---+-----------------------------+----------------------------------------+

|8 -11|4|ebk_size|ebk2文件大小|

+-------+---+-----------------------------+----------------------------------------+

|12-75|64 |book_name|书名|

+-------+---+-----------------------------+----------------------------------------+

|76-79|4|file_size|解压后txt文件的大小(包括章节名和内容) |

+-------+---+-----------------------------+----------------------------------------+

|80-83|4|head_compress_size|章节信息索引表的大小(压缩后的)|

+-------+---+-----------------------------+----------------------------------------+

|84-87|4|first_compress_block_size|第一个压缩块的大小|

+-------+---+-----------------------------+----------------------------------------+

|88-89|2|chapter_count|章节数|

+-------+---+-----------------------------+----------------------------------------+

|90-91|2|compress_block_count|小说内容压缩段的数量|

+-------+---+-----------------------------+----------------------------------------+

|92-95|4|media_count|媒体数量|

+-------+---+-----------------------------+----------------------------------------+

|96-99|4|media_data_length|媒体数据长度|

+-------+---+-----------------------------+----------------------------------------+

|100-103|4|txt_compress_size|压缩后的小说正文内容大小|

+-------+---+-----------------------------+----------------------------------------+

根据逆向的结果,可以这样定义其章节的结构:

代码:

struct ebk_chapter_info_tag

{

unsinged char chapter_name[大小未知];

unsigned int length;

unsigned int offset;

};

压缩块的结构:

代码:

struct ebk_compress_block_data_tag

{

unsigned int length;

unsigned int offset;

};

即一个压缩块占用8个字节。

媒体:

代码:

struct ebk_media_data_tag

{

unsigned int data_offset;

unsigned int length;

unsigned int media_type;

unsigned int offset;

};

因此,ebk2文件的结构应该是:

代码:

header

head_compress (章节和压缩块信息)

compressed_txt (正文,多个压缩块)

测试书名:

代码:

/*

* =====================================================================================

*

*Filename:test.c

*

*Description:

*

*Version:1.0

*Created:10/21/2012 07:01:50 PM

*Revision:none

*Compiler:gcc

*

*Author:荒野无灯

*Organization:

*

* =====================================================================================

*/

#include

#include

#include "util.h"

int main()

{

FILE * fp = fopen("foo.ebk2","rw");

fseek(fp,12,SEEK_SET);

char data[64];

char out[64];

int utlen = 64;

int inlen= 64;

fread(data,1,64,fp);

fclose(fp);

printf("%02x ",data);

char *in= data;

charset_convert("UTF-16LE","utf-8",in,inlen,out,outlen);

printf("%s\n",out);

return 0;

}

代码:

gcc -c util.c

gcc -c test.c

gcc -otest util.o test.o

└─[$] <> ./test

bf874cb0 《白鹿原》

===================================================================

接下来看看章节索引表

代码:

/*

* =====================================================================================

*

*Filename:z.c

*

*Description:

*

*Version:1.0

*Created:10/21/2012 11:56:55 PM

*Revision:none

*Compiler:gcc

*

*Author:荒野无灯 @ihacklog.com

*Organization:

*

* =====================================================================================

*/

#include

#include

#include

#include

int main()

{

unsigned char src[661];

FILE *fp0 = fopen("bailuyuan.ebk2","rb");

if(NULL == fp0 )

{

fprintf(stderr,"error open file!");

return -1;

}

fseek(fp0,104,SEEK_SET);

fread(src,1,661,fp0);

fclose(fp0);

uLongf srclen = 661;

uLongf destlen = 4096;

unsigned char *dest= (unsigned char *) malloc(destlen+1);

if( NULL == dest )

{

fprintf(stderr,"mallloc error");

return -1;

}

unsigned char *pdest = dest;

int err= 0;

err=uncompress(dest,&destlen,src,srclen);

if(Z_OK != err )

{

fprintf(stderr,"error no: %d\n",err);

return -1;

}

FILE *fp = fopen("chapter.dat","wb");

fwrite(dest,1,4096,fp);

fclose(fp);

printf("destlen: %d\n",destlen);

return 0;

}

代码:

gcc -c -g test_chapter_head.c

gcc -otest_chapter_head test_chapter_head.o -lz

./test_chapter_head

看看解压后的章节数据:

第 一 章

7B2C 4E00 7AE0

其UTF-16LE编码应该为: 2c7b 004e e07a

16×4= 68

接下来的0000 0000四个字节应该是相对偏移(这里由于是第一章,所以是0)

然后,0e50 0000 是长度。

0000 500e

接下来又是2c7b (第) ...

因此,到这里,我们终于知道了其ebk_chapter_info结构的大小为 64 + 4 + 4 = 72个字节。

再往下看,第3个2c7b前面8个字节: 0e50 0000 e644 0000

0e50 0000 正好是前面的长度.表示它要相对于第一章偏移0000 500e (20494)个字节。

因此,上面逆向出来的那个结构是有错误的,应该修正为:

代码:

struct ebk_chapter_info_tag

{

unsinged char chapter_name[64];

unsigned int offset;

unsigned int length;

};

代码:

└─[$] <> xxd chapter.dat

0000000: 2c7b 004e e07a 0000 0000 0000 0000 0000,{.N.z..........

0000010: 0000 0000 0000 0000 0000 0000 0000 0000................

0000020: 0000 0000 0000 0000 0000 0000 0000 0000................

0000030: 0000 0000 0000 0000 0000 0000 0000 0000................

0000040: 0000 0000 0e50 0000 2c7b 8c4e e07a 0000.....P..,{.N.z..

0000050: 0000 0000 0000 0000 0000 0000 0000 0000................

0000060: 0000 0000 0000 0000 0000 0000 0000 0000................

0000070: 0000 0000 0000 0000 0000 0000 0000 0000................

0000080: 0000 0000 0000 0000 0e50 0000 e644 0000.........P...D..

0000090: 2c7b 094e e07a 0000 0000 0000 0000 0000,{.N.z..........

00000a0: 0000 0000 0000 0000 0000 0000 0000 0000................

00000b0: 0000 0000 0000 0000 0000 0000 0000 0000................

00000c0: 0000 0000 0000 0000 0000 0000 0000 0000................

00000d0: f494 0000 e448 0000 2c7b db56 e07a 0000.....H..,{.V.z..

00000e0: 0000 0000 0000 0000 0000 0000 0000 0000................

00000f0: 0000 0000 0000 0000 0000 0000 0000 0000................

0000100: 0000 0000 0000 0000 0000 0000 0000 0000................

0000110: 0000 0000 0000 0000 d8dd 0000 6a4f 0000............jO..

0000120: 2c7b 944e e07a 0000 0000 0000 0000 0000,{.N.z..........

0000130: 0000 0000 0000 0000 0000 0000 0000 0000................

0000140: 0000 0000 0000 0000 0000 0000 0000 0000................

0000150: 0000 0000 0000 0000 0000 0000 0000 0000................

0000160: 422d 0100 8e4f 0000 2c7b 6d51 e07a 0000B-...O..,{mQ.z..

0000170: 0000 0000 0000 0000 0000 0000 0000 0000................

0000180: 0000 0000 0000 0000 0000 0000 0000 0000................

0000190: 0000 0000 0000 0000 0000 0000 0000 0000................

00001a0: 0000 0000 0000 0000 d07c 0100 da66 0000.........|...f..

00001b0: 2c7b 034e e07a 0000 0000 0000 0000 0000,{.N.z..........

00001c0: 0000 0000 0000 0000 0000 0000 0000 0000................

00001d0: 0000 0000 0000 0000 0000 0000 0000 0000................

00001e0: 0000 0000 0000 0000 0000 0000 0000 0000................

00001f0: aae3 0100 4c4a 0000 2c7b 6b51 e07a 0000....LJ..,{kQ.z..

0000200: 0000 0000 0000 0000 0000 0000 0000 0000................

0000210: 0000 0000 0000 0000 0000 0000 0000 0000................

0000220: 0000 0000 0000 0000 0000 0000 0000 0000................

0000230: 0000 0000 0000 0000 f62d 0200 785b 0000.........-..x[..

0000240: 2c7b 5d4e e07a 2000 08ff 004e 09ff 0000,{]N.z ....N....

0000250: 0000 0000 0000 0000 0000 0000 0000 0000................

0000260: 0000 0000 0000 0000 0000 0000 0000 0000................

0000270: 0000 0000 0000 0000 0000 0000 0000 0000................

0000280: 6e89 0200 665d 0000 2c7b 5d4e e07a 2000n...f]..,{]N.z .

0000290: 08ff 8c4e 09ff 0000 0000 0000 0000 0000...N............

00002a0: 0000 0000 0000 0000 0000 0000 0000 0000................

00002b0: 0000 0000 0000 0000 0000 0000 0000 0000................

00002c0: 0000 0000 0000 0000 d4e6 0200 0c15 0000................

00002d0: 2c7b 4153 e07a 0000 0000 0000 0000 0000,{AS.z..........

00002e0: 0000 0000 0000 0000 0000 0000 0000 0000................

00002f0: 0000 0000 0000 0000 0000 0000 0000 0000................

0000300: 0000 0000 0000 0000 0000 0000 0000 0000................

0000310: e0fb 0200 3e5f 0000 2c7b 4153 004e e07a....>_..,{AS.N.z

0000320: 0000 0000 0000 0000 0000 0000 0000 0000................

0000330: 0000 0000 0000 0000 0000 0000 0000 0000................

0000340: 0000 0000 0000 0000 0000 0000 0000 0000................

0000350: 0000 0000 0000 0000 1e5b 0300 ca51 0000.........[...Q..

0000360: 2c7b 4153 8c4e e07a 0000 0000 0000 0000,{AS.N.z........

0000370: 0000 0000 0000 0000 0000 0000 0000 0000................

0000380: 0000 0000 0000 0000 0000 0000 0000 0000................

0000390: 0000 0000 0000 0000 0000 0000 0000 0000................

00003a0: e8ac 0300 dc6e 0000 2c7b 4153 094e e07a.....n..,{AS.N.z

00003b0: 2000 08ff 004e 09ff 0000 0000 0000 0000....N..........

00003c0: 0000 0000 0000 0000 0000 0000 0000 0000................

00003d0: 0000 0000 0000 0000 0000 0000 0000 0000................

00003e0: 0000 0000 0000 0000 c41b 0400 7864 0000............xd..

00003f0: 2c7b 4153 094e e07a 2000 08ff 8c4e 09ff,{AS.N.z ....N..

0000400: 0000 0000 0000 0000 0000 0000 0000 0000................

0000410: 0000 0000 0000 0000 0000 0000 0000 0000................

0000420: 0000 0000 0000 0000 0000 0000 0000 0000................

0000430: 3c80 0400 f418 0000 2c7b 4153 db56 e07a<.......,{AS.V.z

0000440: 0000 0000 0000 0000 0000 0000 0000 0000................

0000450: 0000 0000 0000 0000 0000 0000 0000 0000................

0000460: 0000 0000 0000 0000 0000 0000 0000 0000................

0000470: 0000 0000 0000 0000 3099 0400 0a68 0000........0....h..

0000480: 2c7b 4153 944e e07a 0000 0000 0000 0000,{AS.N.z........

0000490: 0000 0000 0000 0000 0000 0000 0000 0000................

00004a0: 0000 0000 0000 0000 0000 0000 0000 0000................

00004b0: 0000 0000 0000 0000 0000 0000 0000 0000................

00004c0: 3a01 0500 fa6a 0000 2c7b 4153 6d51 e07a:....j..,{ASmQ.z

00004d0: 2000 08ff 004e 09ff 0000 0000 0000 0000....N..........

00004e0: 0000 0000 0000 0000 0000 0000 0000 0000................

00004f0: 0000 0000 0000 0000 0000 0000 0000 0000................

0000500: 0000 0000 0000 0000 346c 0500 5c37 0000........4l..\7..

0000510: 2c7b 4153 6d51 e07a 2000 08ff 8c4e 09ff,{ASmQ.z ....N..

0000520: 0000 0000 0000 0000 0000 0000 0000 0000................

0000530: 0000 0000 0000 0000 0000 0000 0000 0000................

0000540: 0000 0000 0000 0000 0000 0000 0000 0000................

0000550: 90a3 0500 803a 0000 2c7b 4153 034e e07a.....:..,{AS.N.z

0000560: 0000 0000 0000 0000 0000 0000 0000 0000................

0000570: 0000 0000 0000 0000 0000 0000 0000 0000................

0000580: 0000 0000 0000 0000 0000 0000 0000 0000................

0000590: 0000 0000 0000 0000 10de 0500 6264 0000............bd..

00005a0: 2c7b 4153 6b51 e07a 0000 0000 0000 0000,{ASkQ.z........

00005b0: 0000 0000 0000 0000 0000 0000 0000 0000................

00005c0: 0000 0000 0000 0000 0000 0000 0000 0000................

00005d0: 0000 0000 0000 0000 0000 0000 0000 0000................

00005e0: 7242 0600 3069 0000 2c7b 4153 5d4e e07arB..0i..,{AS]N.z

00005f0: 0000 0000 0000 0000 0000 0000 0000 0000................

0000600: 0000 0000 0000 0000 0000 0000 0000 0000................

0000610: 0000 0000 0000 0000 0000 0000 0000 0000................

0000620: 0000 0000 0000 0000 a2ab 0600 3a68 0000............:h..

0000630: 2c7b 8c4e 4153 e07a 0000 0000 0000 0000,{.NAS.z........

0000640: 0000 0000 0000 0000 0000 0000 0000 0000................

0000650: 0000 0000 0000 0000 0000 0000 0000 0000................

0000660: 0000 0000 0000 0000 0000 0000 0000 0000................

0000670: dc13 0700 8864 0000 2c7b 8c4e 4153 004e.....d..,{.NAS.N

0000680: e07a 0000 0000 0000 0000 0000 0000 0000.z..............

0000690: 0000 0000 0000 0000 0000 0000 0000 0000................

00006a0: 0000 0000 0000 0000 0000 0000 0000 0000................

00006b0: 0000 0000 0000 0000 6478 0700 5062 0000........dx..Pb..

00006c0: 2c7b 8c4e 4153 8c4e e07a 0000 0000 0000,{.NAS.N.z......

00006d0: 0000 0000 0000 0000 0000 0000 0000 0000................

00006e0: 0000 0000 0000 0000 0000 0000 0000 0000................

00006f0: 0000 0000 0000 0000 0000 0000 0000 0000................

0000700: b4da 0700 f86b 0000 2c7b 8c4e 4153 094e.....k..,{.NAS.N

0000710: e07a 2000 08ff 004e 09ff 0000 0000 0000.z ....N........

0000720: 0000 0000 0000 0000 0000 0000 0000 0000................

0000730: 0000 0000 0000 0000 0000 0000 0000 0000................

0000740: 0000 0000 0000 0000 ac46 0800 1457 0000.........F...W..

0000750: 2c7b 8c4e 4153 094e e07a 2000 08ff 8c4e,{.NAS.N.z ....N

0000760: 09ff 0000 0000 0000 0000 0000 0000 0000................

0000770: 0000 0000 0000 0000 0000 0000 0000 0000................

0000780: 0000 0000 0000 0000 0000 0000 0000 0000................

0000790: c09d 0800 e831 0000 2c7b 8c4e 4153 db56.....1..,{.NAS.V

00007a0: e07a 2000 08ff 004e 09ff 0000 0000 0000.z ....N........

00007b0: 0000 0000 0000 0000 0000 0000 0000 0000................

00007c0: 0000 0000 0000 0000 0000 0000 0000 0000................

00007d0: 0000 0000 0000 0000 a8cf 0800 da50 0000.............P..

00007e0: 2c7b 8c4e 4153 db56 e07a 2000 08ff 8c4e,{.NAS.V.z ....N

00007f0: 09ff 0000 0000 0000 0000 0000 0000 0000................

0000800: 0000 0000 0000 0000 0000 0000 0000 0000................

0000810: 0000 0000 0000 0000 0000 0000 0000 0000................

0000820: 8220 0900 bc36 0000 2c7b 8c4e 4153 944e. ...6..,{.NAS.N

0000830: e07a 2000 08ff 004e 09ff 0000 0000 0000.z ....N........

0000840: 0000 0000 0000 0000 0000 0000 0000 0000................

0000850: 0000 0000 0000 0000 0000 0000 0000 0000................

0000860: 0000 0000 0000 0000 3e57 0900 e852 0000........>W...R..

0000870: 2c7b 8c4e 4153 944e e07a 2000 08ff 8c4e,{.NAS.N.z ....N

0000880: 09ff 0000 0000 0000 0000 0000 0000 0000................

0000890: 0000 0000 0000 0000 0000 0000 0000 0000................

00008a0: 0000 0000 0000 0000 0000 0000 0000 0000................

00008b0: 26aa 0900 9c35 0000 2c7b 8c4e 4153 6d51&....5..,{.NASmQ

00008c0: e07a 2000 08ff 004e 09ff 0000 0000 0000.z ....N........

00008d0: 0000 0000 0000 0000 0000 0000 0000 0000................

00008e0: 0000 0000 0000 0000 0000 0000 0000 0000................

00008f0: 0000 0000 0000 0000 c2df 0900 103e 0000.............>..

0000900: 2c7b 8c4e 4153 6d51 e07a 2000 08ff 8c4e,{.NASmQ.z ....N

0000910: 09ff 0000 0000 0000 0000 0000 0000 0000................

0000920: 0000 0000 0000 0000 0000 0000 0000 0000................

0000930: 0000 0000 0000 0000 0000 0000 0000 0000................

0000940: d21d 0a00 3c42 0000 2c7b 8c4e 4153 034e....

0000950: e07a 2000 08ff 004e 09ff 0000 0000 0000.z ....N........

0000960: 0000 0000 0000 0000 0000 0000 0000 0000................

0000970: 0000 0000 0000 0000 0000 0000 0000 0000................

0000980: 0000 0000 0000 0000 0e60 0a00 d254 0000.........`...T..

0000990: 2c7b 8c4e 4153 034e e07a 2000 08ff 8c4e,{.NAS.N.z ....N

00009a0: 09ff 0000 0000 0000 0000 0000 0000 0000................

00009b0: 0000 0000 0000 0000 0000 0000 0000 0000................

00009c0: 0000 0000 0000 0000 0000 0000 0000 0000................

00009d0: e0b4 0a00 3030 0000 2c7b 8c4e 4153 6b51....00..,{.NASkQ

00009e0: e07a 2000 08ff 004e 09ff 0000 0000 0000.z ....N........

00009f0: 0000 0000 0000 0000 0000 0000 0000 0000................

0000a00: 0000 0000 0000 0000 0000 0000 0000 0000................

0000a10: 0000 0000 0000 0000 10e5 0a00 764f 0000............vO..

0000a20: 2c7b 8c4e 4153 6b51 e07a 2000 08ff 8c4e,{.NASkQ.z ....N

0000a30: 09ff 0000 0000 0000 0000 0000 0000 0000................

0000a40: 0000 0000 0000 0000 0000 0000 0000 0000................

0000a50: 0000 0000 0000 0000 0000 0000 0000 0000................

0000a60: 8634 0b00 4031 0000 2c7b 8c4e 4153 5d4e.4..@1..,{.NAS]N

0000a70: e07a 2000 08ff 004e 09ff 0000 0000 0000.z ....N........

0000a80: 0000 0000 0000 0000 0000 0000 0000 0000................

0000a90: 0000 0000 0000 0000 0000 0000 0000 0000................

0000aa0: 0000 0000 0000 0000 c665 0b00 7a59 0000.........e..zY..

0000ab0: 2c7b 8c4e 4153 5d4e e07a 2000 08ff 8c4e,{.NAS]N.z ....N

0000ac0: 09ff 0000 0000 0000 0000 0000 0000 0000................

0000ad0: 0000 0000 0000 0000 0000 0000 0000 0000................

0000ae0: 0000 0000 0000 0000 0000 0000 0000 0000................

0000af0: 40bf 0b00 681f 0000 2c7b 094e 4153 e07a@...h...,{.NAS.z

0000b00: 2000 08ff 004e 09ff 0000 0000 0000 0000....N..........

0000b10: 0000 0000 0000 0000 0000 0000 0000 0000................

0000b20: 0000 0000 0000 0000 0000 0000 0000 0000................

0000b30: 0000 0000 0000 0000 a8de 0b00 ee54 0000.............T..

0000b40: 2c7b 094e 4153 e07a 2000 08ff 8c4e 09ff,{.NAS.z ....N..

0000b50: 0000 0000 0000 0000 0000 0000 0000 0000................

0000b60: 0000 0000 0000 0000 0000 0000 0000 0000................

0000b70: 0000 0000 0000 0000 0000 0000 0000 0000................

0000b80: 9633 0c00 1425 0000 2c7b 094e 4153 004e.3...%..,{.NAS.N

0000b90: e07a 2000 08ff 004e 09ff 0000 0000 0000.z ....N........

0000ba0: 0000 0000 0000 0000 0000 0000 0000 0000................

0000bb0: 0000 0000 0000 0000 0000 0000 0000 0000................

0000bc0: 0000 0000 0000 0000 aa58 0c00 f463 0000.........X...c..

0000bd0: 2c7b 094e 4153 004e e07a 2000 08ff 8c4e,{.NAS.N.z ....N

0000be0: 09ff 0000 0000 0000 0000 0000 0000 0000................

0000bf0: 0000 0000 0000 0000 0000 0000 0000 0000................

0000c00: 0000 0000 0000 0000 0000 0000 0000 0000................

0000c10: 9ebc 0c00 761d 0000 2c7b 094e 4153 8c4e....v...,{.NAS.N

0000c20: e07a 2000 08ff 004e 09ff 0000 0000 0000.z ....N........

0000c30: 0000 0000 0000 0000 0000 0000 0000 0000................

0000c40: 0000 0000 0000 0000 0000 0000 0000 0000................

0000c50: 0000 0000 0000 0000 14da 0c00 c05a 0000.............Z..

0000c60: 2c7b 094e 4153 8c4e e07a 2000 08ff 8c4e,{.NAS.N.z ....N

0000c70: 09ff 0000 0000 0000 0000 0000 0000 0000................

0000c80: 0000 0000 0000 0000 0000 0000 0000 0000................

0000c90: 0000 0000 0000 0000 0000 0000 0000 0000................

0000ca0: d434 0d00 5a28 0000 2c7b 094e 4153 094e.4..Z(..,{.NAS.N

0000cb0: e07a 0000 0000 0000 0000 0000 0000 0000.z..............

0000cc0: 0000 0000 0000 0000 0000 0000 0000 0000................

0000cd0: 0000 0000 0000 0000 0000 0000 0000 0000................

0000ce0: 0000 0000 0000 0000 2e5d 0d00 fc6d 0000.........]...m..

0000cf0: 2c7b 094e 4153 db56 e07a 2000 08ff 004e,{.NAS.V.z ....N

0000d00: 09ff 0000 0000 0000 0000 0000 0000 0000................

0000d10: 0000 0000 0000 0000 0000 0000 0000 0000................

0000d20: 0000 0000 0000 0000 0000 0000 0000 0000................

0000d30: 2acb 0d00 5248 0000 2c7b 094e 4153 db56*...RH..,{.NAS.V

0000d40: e07a 2000 08ff 8c4e 09ff 0000 0000 0000.z ....N........

0000d50: 0000 0000 0000 0000 0000 0000 0000 0000................

0000d60: 0000 0000 0000 0000 0000 0000 0000 0000................

0000d70: 0000 0000 0000 0000 7c13 0e00 7423 0000........|...t#..

0000d80: 0000 0000 0bab 0000 0bab 0000 2ea7 0000................

0000d90: 3952 0100 a3a2 0000 dcf4 0100 dfa4 00009R..............

0000da0: bb99 0200 f8a1 0000 b33b 0300 45a7 0000.........;..E...

0000db0: f8e2 0300 c8a7 0000 c08a 0400 61a4 0000............a...

0000dc0: 212f 0500 66a3 0000 87d2 0500 84a4 0000!/..f...........

0000dd0: 0b77 0600 7da6 0000 881d 0700 51a4 0000.w..}.......Q...

0000de0: d9c1 0700 efa3 0000 c865 0800 a5a6 0000.........e......

0000df0: 6d0c 0900 fc26 0000 0000 0000 0000 0000m....&..........

0000e00: 0000 0000 0000 0000 0000 0000 0000 0000................

0000e10: 0000 0000 0000 0000 0000 0000 0000 0000................

0000e20: 0000 0000 0000 0000 0000 0000 0000 0000................

0000e30: 0000 0000 0000 0000 0000 0000 0000 0000................

0000e40: 0000 0000 0000 0000 0000 0000 0000 0000................

0000e50: 0000 0000 0000 0000 0000 0000 0000 0000................

0000e60: 0000 0000 0000 0000 0000 0000 0000 0000................

0000e70: 0000 0000 0000 0000 0000 0000 0000 0000................

0000e80: 0000 0000 0000 0000 0000 0000 0000 0000................

0000e90: 0000 0000 0000 0000 0000 0000 0000 0000................

0000ea0: 0000 0000 0000 0000 0000 0000 0000 0000................

0000eb0: 0000 0000 0000 0000 0000 0000 0000 0000................

0000ec0: 0000 0000 0000 0000 0000 0000 0000 0000................

0000ed0: 0000 0000 0000 0000 0000 0000 0000 0000................

0000ee0: 0000 0000 0000 0000 0000 0000 0000 0000................

0000ef0: 0000 0000 0000 0000 0000 0000 0000 0000................

0000f00: 0000 0000 0000 0000 0000 0000 0000 0000................

0000f10: 0000 0000 0000 0000 0000 0000 0000 0000................

0000f20: 0000 0000 0000 0000 0000 0000 0000 0000................

0000f30: 0000 0000 0000 0000 0000 0000 0000 0000................

0000f40: 0000 0000 0000 0000 0000 0000 0000 0000................

0000f50: 0000 0000 0000 0000 0000 0000 0000 0000................

0000f60: 0000 0000 0000 0000 0000 0000 0000 0000................

0000f70: 0000 0000 0000 0000 0000 0000 0000 0000................

0000f80: 0000 0000 0000 0000 0000 0000 0000 0000................

0000f90: 0000 0000 0000 0000 0000 0000 0000 0000................

0000fa0: 0000 0000 0000 0000 0000 0000 0000 0000................

0000fb0: 0000 0000 0000 0000 0000 0000 0000 0000................

0000fc0: 0000 0000 0000 0000 0000 0000 0000 0000................

0000fd0: 0000 0000 0000 0000 0000 0000 0000 0000................

0000fe0: 0000 0000 0000 0000 0000 0000 0000 0000................

0000ff0: 0000 0000 0000 0000 0000 0000 0000 0000................

由于未解压前的小说内容是分为多个段压缩存储的,

也就是说未解压前的数据是不具备搜索功能的,

电脑资料

《逆向iReader解读ebk2电子书格式》()。

因此,我们可以确定,偏移的这0000 500e (20494)个字节是解压后的。

仔细观察还可以看到,后面一部分数据中没有出现2c7b(第)。这部分就是

压缩数据块信息了。解压分成了很多数据块的正文需要这个信息。

====================================================================

实际上我后面试验了下,把导出的txt文件只保留第一章,然后统计其字节数:

└─[$] <> wc -c aaa.txt

20496 aaa.txt

可以看到是20496 (为什么?前面有两个字节的BOM)

这是后话了。

====================================================================

现在该是时候总结下104个字节的head的结构的作用了:

|0 - 3|4|book_id|一般为全0|

|4 - 5|2|head_data_size|ebk2文件的head大小,一般为104字节|

这个主要是让程序读取head时,知道它该读取多长的数据。

|6 - 7|2|ebk_version|ebk文件的版本|

标明当前文件的版本(版本不同,解析方法不同)。

|8 -11|4|ebk_size|ebk2文件大小|

这个应该是用于快速判断ebk2文件是否完整。

|12-75|64 |book_name|书名|

这个就不用说了。

|76-79|4|file_size|解压后txt文件的大小(包括章节名和内容) |

可以用于判断解压后的txt是否完整~~

|80-83|4|head_compress_size|章节信息索引表和压缩块信息的大小(压缩后的)|

这个主要用来确定章节信息索引表和压缩块信息的压缩数据的大小,在后面定位小说正文偏移也要用到。

在header之后就是这个数据,这个值是告诉程序header往后再读取这么多个字节来解压。

|84-87|4|first_compress_block_size|第一个压缩块的大小|

第一个小说正文压缩块的大小

|88-89|2|chapter_count|章节数|

|90-91|2|compress_block_count|小说内容压缩段的数量|

这个主要用于后面分段解压后再合并。

|92-95|4|media_count|媒体数量|

+-------+---+-----------------------------+----------------------------------------+

|96-99|4|media_data_length|媒体数据长度|

+-------+---+-----------------------------+----------------------------------------+

|100-103|4|txt_compress_size|压缩后的小说正文内容大小|

现在,再次深入到ebk2文件了。

ebk2文件的结构应该修正为:

header (一般是104字节)

head_compress (章节信息+压缩块信息)

compressed_txt (正文,多个压缩块)

下面想一下解压思路吧。

读取第4-5字节,获知 header->head_data_size (104) 。

然后,读取 header->head_data_size 个字节,获知整个ebk2文件的头信息。

从header->book_name可以获取UTF-16LE编码的书名。

然后,根据header->head_compress_size 读取压缩的header信息(包括章节信息和压缩块信息)

解压出压缩的header信息,

根据chapter_count 和 compress_block_count ,把相应的数据复制过来,即得到章节列表信息和压缩列表信息。

如果只需要解压为一个txt文件,那么只需要用到压缩块信息。如果需要提取单个章节,那就需要章节信息。

这里假设我们要解压ekb2文件为一个txt文件。

接下来根据压缩块信息和 header->compress_block_count

从header.head_data_size + header.head_compress_size 偏移处开始,对于每个压缩块,进行解压。

每解压一个数据块就写入到文件。如此进行header->compress_block_count次后,即得到解压后的txt文件。

再根据header->file_size可判断解压是否成功。

花了一些时间,写出转换程序。

在Archlinux 32位下测试成功。

然后就是在windows 下的编译了。。。windows下的编译比Linux下麻烦得多。最终我用Code::Blocks搞定。

EOF===========================================================

逆向iReader解读ebk2电子书格式 -电脑资料

手机扫码分享

Top