9 /* time field stucture */
20 /* Rock27Boot.bin header structure */
24 uint8_t check_values
[16];
26 uint32_t ui_master_version
;
27 uint32_t ui_slave_version
;
36 uint32_t version_flag
;
49 CONTINOUS_ENC
, /* scramble whole block at once */
50 PAGE_ENC
/* nand bootloader is scrambled in 0x200 chunks */
53 /* scrambling/descrambling reverse engineered by AleMaxx */
54 static void encode_page(uint8_t *inpg
, uint8_t *outpg
, const int size
)
58 0x7C, 0x4E, 0x03, 0x04,
59 0x55, 0x05, 0x09, 0x07,
60 0x2D, 0x2C, 0x7B, 0x38,
61 0x17, 0x0D, 0x17, 0x11
63 int i
, i3
, x
, val
, idx
;
68 for (i
=0; i
<0x100; i
++) {
74 for (i
=0; i
<0x100; i
++) {
84 for (i
=0; i
<size
; i
++) {
85 x
= key1
[(i
+1) & 0xff];
87 idx
= (x
+ idx
) & 0xff;
88 key1
[(i
+1) & 0xff] = key1
[idx
];
89 key1
[idx
] = (x
& 0xff);
90 val
= (key1
[(i
+1)&0xff] + x
) & 0xff;
92 outpg
[i
] = val
^ inpg
[i
];
96 static void *binary_extract(FILE *fp
, uint32_t offset
, uint32_t len
, int descramble
, int encode_mode
)
98 void *buff
, *buff_ptr
;
101 if ((fp
== NULL
) || len
== 0)
105 if ((buff
= malloc(len
)) == NULL
)
108 /* seek to the begining of the data */
109 fseek(fp
, offset
, SEEK_SET
);
111 /* read into the buffer */
112 ret
= fread(buff
, 1, len
, fp
);
124 if (encode_mode
== PAGE_ENC
)
128 encode_page((uint8_t *)buff_ptr
,
136 encode_page((uint8_t *)buff_ptr
, (uint8_t *)buff_ptr
, len
);
142 static void usage(void)
144 printf("Usage: rkboottool [options] Rock27Boot.bin\n");
145 printf("-h|--help This help message\n");
146 printf("-e|--extract Extract binary images from Rock27Boot.bin file\n");
147 printf("-d|--descramble Descramble extracted binary images\n");
148 printf("-i|--info Print info about Rock27Boot.bin file\n");
150 printf("Usually you would like to use -d -e together to obtain raw binary\n");
151 printf("(out files rkboot_s1.bin, rkboot_s2.bin, rkboot_s3.bin, rkboot_s4.bin)\n");
154 int main (int argc
, char **argv
)
156 struct rkboot_info_t rkboot_info
;
157 FILE *fp_in
, *fp_out
;
158 int32_t i
= 0, action
= NONE
;
161 char *in_filename
= NULL
;
170 fprintf(stderr
,"rkboottool " VERSION
"\n");
171 fprintf(stderr
,"(C) Marcin Bukat 2011\n");
172 fprintf(stderr
,"This is free software; see the source for copying conditions. There is NO\n");
173 fprintf(stderr
,"warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.\n\n");
175 /* arguments handling */
178 if ((strcmp(argv
[i
],"-i")==0) || (strcmp(argv
[i
],"--info")==0))
182 else if ((strcmp(argv
[i
],"-e")==0) || (strcmp(argv
[i
],"--extract")==0))
186 else if ((strcmp(argv
[i
],"-d")==0) || (strcmp(argv
[i
],"--descramble")==0))
190 else if ((strcmp(argv
[i
],"-h")==0) || (strcmp(argv
[i
],"--help")==0))
195 else if ( argv
[i
][0] != '-' )
198 in_filename
= argv
[i
];
203 if ( (fp_in
= fopen(in_filename
, "rb")) == NULL
)
205 fprintf(stderr
, "error: can't open %s file for reading\n", in_filename
);
209 ret
= fread(&rkboot_info
, 1, sizeof(rkboot_info
), fp_in
);
211 if (ret
!= sizeof(rkboot_info
))
214 fprintf(stderr
, "error: can't read %s file header\n", in_filename
);
215 fprintf(stderr
, "read %d, expected %d\n", ret
, sizeof(rkboot_info
));
221 printf("file: %s\n", in_filename
);
222 printf("signature: %s\n", rkboot_info
.sign
);
223 printf("check bytes: ");
224 for (i
= 0; i
< 16; i
++)
225 printf("0x%0x ", rkboot_info
.check_values
[i
]);
228 printf("timestamp %d.%d.%d %d:%d:%d\n", rkboot_info
.time
.day
,
229 rkboot_info
.time
.month
,
230 rkboot_info
.time
.year
,
231 rkboot_info
.time
.hour
,
232 rkboot_info
.time
.minute
,
233 rkboot_info
.time
.second
);
234 printf("UI master version: 0x%0x\n", rkboot_info
.ui_master_version
);
235 printf("UI slave version: 0x%0x\n", rkboot_info
.ui_slave_version
);
236 printf("s1 data offset: 0x%0x\n", rkboot_info
.s1_offset
);
237 printf("s1 data len: 0x%0x\n", rkboot_info
.s1_len
);
238 printf("s2 offset: 0x%0x\n", rkboot_info
.s2_offset
);
239 printf("s2 len: 0x%0x\n", rkboot_info
.s2_len
);
240 printf("s3 offset: 0x%0x\n", rkboot_info
.s3_offset
);
241 printf("s3 len: 0x%0x\n", rkboot_info
.s3_len
);
242 printf("s4 offset: 0x%0x\n", rkboot_info
.s4_offset
);
243 printf("s4 len: 0x%0x\n", rkboot_info
.s4_len
);
244 printf("UI version flag: 0x%0x\n", rkboot_info
.version_flag
);
247 if (action
& EXTRACT
)
250 buff
= binary_extract(fp_in
, rkboot_info
.s1_offset
,
258 fprintf(stderr
, "error: can't extract image\n");
263 if ((fp_out
= fopen("rkboot_s1.bin", "wb")) == NULL
)
267 fprintf(stderr
, "[error]: can't open rkboot_s1.bin for writing\n");
271 fwrite(buff
, 1, rkboot_info
.s1_len
, fp_out
);
273 fprintf(stderr
, "[info]: extracted rkboot_s1.bin file\n");
278 buff
= binary_extract(fp_in
, rkboot_info
.s2_offset
,
286 fprintf(stderr
, "error: can't extract image\n");
290 if ((fp_out
= fopen("rkboot_s2.bin", "wb")) == NULL
)
294 fprintf(stderr
, "[error]: can't open rkboot_s2.bin for writing\n");
298 fwrite(buff
, 1, rkboot_info
.s2_len
, fp_out
);
300 fprintf(stderr
, "[info]: extracted rkboot_s2.bin file\n");
305 buff
= binary_extract(fp_in
, rkboot_info
.s3_offset
,
312 fprintf(stderr
, "[error]: can't extract image.\n");
316 if ((fp_out
= fopen("rkboot_s3.bin", "wb")) == NULL
)
320 fprintf(stderr
, "[error]: can't open rkboot_s3.bin for writing\n");
324 fwrite(buff
, 1, rkboot_info
.s3_len
, fp_out
);
326 fprintf(stderr
, "[info]: extracted rkboot_s3.bin file\n");
331 buff
= binary_extract(fp_in
, rkboot_info
.s4_offset
,
338 fprintf(stderr
, "[error]: can't extract image\n");
342 if ((fp_out
= fopen("rkboot_s4.bin", "wb")) == NULL
)
346 fprintf(stderr
, "[error]: can't open rkboot_s4.bin for writing\n");
350 fwrite(buff
, 1, rkboot_info
.s4_len
, fp_out
);
352 fprintf(stderr
, "[info]: extracted rkboot_s4.bin file\n");