-
Notifications
You must be signed in to change notification settings - Fork 52
/
AndroidzImageTemplate.bt
155 lines (125 loc) · 4.25 KB
/
AndroidzImageTemplate.bt
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
//--------------------------------------
//--- 010 Editor v5.0beta2 Binary Template
//
// File: AndroidzImageTemplate.bt
// Author: Tim "diff" Strazzere <[email protected]> <[email protected]>
// Revision: 1.1
// Purpose: Quick template for parsing Android boot/recovery (zImage) images, just wip
//
// Most (if not all) research stolen from;
// - https://github.com/we3des/psychic-octo-robot/wiki/Android-boot.img-zImage-format
// Which is pulled mostly from;
// - https://github.com/android/platform_system_core/blob/master/mkbootimg/bootimg.h
//
// CertISW structure (added in 1.1) was taken from;
// - http://www.droid-developers.org/wiki/Cryptography
//--------------------------------------
#define PAGE_SIZE (0x800)
// utility type to show the SHA1 hash in the value column
typedef ubyte SHA1[20] <read=SHA1Read, format=hex>;
string SHA1Read(SHA1 sig) {
string ret;
string tmp;
int i;
for(i = 0; i<20; i++) {
SPrintf(tmp, "%.2X", sig[i]);
ret += tmp;
}
return ret;
}
typedef struct {
int image_offset;
int image_size;
int data_byte[5];
} Images;
typedef struct {
char signer_info[16];
long signature_info;
long key_id;
char digest[256];
} Digest;
typedef struct {
int reg_address;
int reg_value;
} Reg_table;
typedef struct {
char cert_mark[8] <comment="Magic bytes that the file command should use">;
if(Strcmp(cert_mark, "CertISW\00") != 0) {
return("Doesn't appear to be a correct CerISW struct - bailing!\n");
}
int cert_version;
int cert_type;
int minimum_version_src;
int minimum_version_pk;
int minimum_version_ppa;
int minimum_version_rd1;
int minimum_version_rd2;
int minimum_version_isw;
int watchdog_param;
int use_DMA;
int active_images;
Images images[4];
int magic[1];
int reg_bitfield;
Reg_table reg_table[32];
int reg_type_01;
int reg_type_02;
int enter_point_offset;
int zero_hole[32];
Digest digest;
} CertISW;
typedef struct {
char magic[8] <comment="Magic bytes that the file command should use">;
if(Strcmp(magic, "ANDROID!") != 0) {
return("Doesn't appear to be a zImage file - bailing!\n");
}
uint kernel_size;
uint kernel_address <format=hex, comment="Default is 0x10008000. Whatever number you type is added to 0x00008000">;
uint ramdisk_size;
uint ramdisk_address <format=hex, comment="Default is 0x11000000. base address + 0x01000000">;
uint second_size;
uint second_address <format=hex, comment="Default is 0x10F00000. base address + 0x00F00000">;
uint tag_address <format=hex, comment="Default is 0x10000100. base address + 0x00000100">;
uint page_size <comment="2048 is the default. 2048 and 4096 are the only values accepted by mkbootimg">;
ubyte unused[8] <comment="Reversed for future expansion">;
char name[16] <comment="Boot Image name">;
char cmd_line[512] <comment="Kernel command line">;
// Comments from bootimg.h claim this field is; "timestamp / checksum / sha1 / etc"
// However the actual usage in mkbootimg.c only appears to be the sha1 of
// the kernel data, ramdisk data and second data section
// - https://github.com/android/platform_system_core/blob/master/mkbootimg/mkbootimg.c#L237
SHA1 id <comment="Seems to be a SHA1">;
} Android_zImage_header;
// Does it look like it has a CertISW?
if(ReadByte(0) == 0x43) {
CertISW Cert_ISW;
}
local int start = FTell();
// This should always be one page
Android_zImage_header bootImage;
// Skip to the end of the page
FSkip(PAGE_SIZE - FTell() + start);
// Ensure we get the padded page at the end
local int pages = pages = bootImage.kernel_size / PAGE_SIZE;
if(bootImage.kernel_size % PAGE_SIZE) {
pages = pages + 1;
}
if(pages != 0) {
ubyte kernel[pages * PAGE_SIZE];
}
// Ensure we get the padded page at the end
pages = bootImage.ramdisk_size / PAGE_SIZE;
if(bootImage.ramdisk_size % PAGE_SIZE) {
pages = pages + 1;
}
if(pages != 0) {
ubyte ramdisk[pages * PAGE_SIZE];
}
// Ensure we get the padded page at the end
pages = bootImage.second_size / PAGE_SIZE;
if(bootImage.second_size % PAGE_SIZE) {
pages = pages + 1;
}
if(pages != 0) {
ubyte second[pages * PAGE_SIZE];
}