Rizin
unix-like reverse engineering framework and cli tools
bin_dol.c
Go to the documentation of this file.
1 // SPDX-FileCopyrightText: 2015-2019 pancake <pancake@nopcode.org>
2 // SPDX-License-Identifier: LGPL-3.0-only
3 
4 #include <rz_types.h>
5 #include <rz_util.h>
6 #include <rz_lib.h>
7 #include <rz_bin.h>
8 #include <string.h>
9 
10 /*
11  Start End Length Description
12  0x0 0x3 4 File offset to start of Text0
13  0x04 0x1b 24 File offsets for Text1..6
14  0x1c 0x47 44 File offsets for Data0..10
15  0x48 0x4B 4 Loading address for Text0
16  0x4C 0x8F 68 Loading addresses for Text1..6, Data0..10
17  0x90 0xD7 72 Section sizes for Text0..6, Data0..10
18  0xD8 0xDB 4 BSS address
19  0xDC 0xDF 4 BSS size
20  0xE0 0xE3 4 Entry point
21  0xE4 0xFF padding
22  */
23 
24 #define N_TEXT 7
25 #define N_DATA 11
26 
28  typedef struct {
29  ut32 text_paddr[N_TEXT];
30  ut32 data_paddr[N_DATA];
31  ut32 text_vaddr[N_TEXT];
32  ut32 data_vaddr[N_DATA];
33  ut32 text_size[N_TEXT];
34  ut32 data_size[N_DATA];
35  ut32 bss_addr;
36  ut32 bss_size;
37  ut32 entrypoint;
38  ut32 padding[10];
39  // 0x100 -- start of data section
40  })
41 DolHeader;
42 
43 static bool check_buffer(RzBuffer *buf) {
44  ut8 tmp[6];
45  int r = rz_buf_read_at(buf, 0, tmp, sizeof(tmp));
46  bool one = r == sizeof(tmp) && !memcmp(tmp, "\x00\x00\x01\x00\x00\x00", sizeof(tmp));
47  if (one) {
48  int r = rz_buf_read_at(buf, 6, tmp, sizeof(tmp));
49  if (r != 6) {
50  return false;
51  }
52  return sizeof(tmp) && !memcmp(tmp, "\x00\x00\x00\x00\x00\x00", sizeof(tmp));
53  }
54  return false;
55 }
56 
57 static bool load_buffer(RzBinFile *bf, RzBinObject *obj, RzBuffer *buf, Sdb *sdb) {
58  if (rz_buf_size(buf) < sizeof(DolHeader)) {
59  return false;
60  }
61  DolHeader *dol = RZ_NEW0(DolHeader);
62  if (!dol) {
63  return false;
64  }
65  char *lowername = strdup(bf->file);
66  if (!lowername) {
67  goto dol_err;
68  }
69  rz_str_case(lowername, 0);
70  char *ext = strstr(lowername, ".dol");
71  if (!ext || ext[4] != 0) {
72  goto lowername_err;
73  }
74  free(lowername);
75  rz_buf_fread_at(bf->buf, 0, (void *)dol, "67I", 1);
76  obj->bin_obj = dol;
77  return true;
78 
79 lowername_err:
80  free(lowername);
81 dol_err:
82  free(dol);
83  return false;
84 }
85 
86 static RzList *sections(RzBinFile *bf) {
87  rz_return_val_if_fail(bf && bf->o && bf->o->bin_obj, NULL);
88  int i;
89  RzList *ret;
90  RzBinSection *s;
91  DolHeader *dol = bf->o->bin_obj;
92  if (!(ret = rz_list_new())) {
93  return NULL;
94  }
95 
96  /* text sections */
97  for (i = 0; i < N_TEXT; i++) {
98  if (!dol->text_paddr[i] || !dol->text_vaddr[i]) {
99  continue;
100  }
102  s->name = rz_str_newf("text_%d", i);
103  s->paddr = dol->text_paddr[i];
104  s->vaddr = dol->text_vaddr[i];
105  s->size = dol->text_size[i];
106  s->vsize = s->size;
107  s->perm = rz_str_rwx("r-x");
108  rz_list_append(ret, s);
109  }
110  /* data sections */
111  for (i = 0; i < N_DATA; i++) {
112  if (!dol->data_paddr[i] || !dol->data_vaddr[i]) {
113  continue;
114  }
116  s->name = rz_str_newf("data_%d", i);
117  s->paddr = dol->data_paddr[i];
118  s->vaddr = dol->data_vaddr[i];
119  s->size = dol->data_size[i];
120  s->vsize = s->size;
121  s->perm = rz_str_rwx("r--");
122  rz_list_append(ret, s);
123  }
124  /* bss section */
126  s->name = strdup("bss");
127  s->paddr = 0;
128  s->vaddr = dol->bss_addr;
129  s->size = dol->bss_size;
130  s->vsize = s->size;
131  s->perm = rz_str_rwx("rw-");
132  rz_list_append(ret, s);
133 
134  return ret;
135 }
136 
137 static RzList *entries(RzBinFile *bf) {
138  rz_return_val_if_fail(bf && bf->o && bf->o->bin_obj, NULL);
139  RzList *ret = rz_list_new();
141  DolHeader *dol = bf->o->bin_obj;
142  addr->vaddr = (ut64)dol->entrypoint;
143  addr->paddr = addr->vaddr & 0xFFFF;
144  rz_list_append(ret, addr);
145  return ret;
146 }
147 
148 static RzBinInfo *info(RzBinFile *bf) {
149  rz_return_val_if_fail(bf && bf->buf, NULL);
150  RzBinInfo *ret = RZ_NEW0(RzBinInfo);
151  if (!ret) {
152  return NULL;
153  }
154  ret->file = strdup(bf->file);
155  ret->big_endian = true;
156  ret->type = strdup("ROM");
157  ret->machine = strdup("Nintendo Wii");
158  ret->os = strdup("wii-ios");
159  ret->arch = strdup("ppc");
160  ret->has_va = true;
161  ret->bits = 32;
162 
163  return ret;
164 }
165 
166 static ut64 baddr(RzBinFile *bf) {
167  return 0x80b00000; // XXX
168 }
169 
171  .name = "dol",
172  .desc = "Nintendo Dolphin binary format",
173  .license = "BSD",
174  .load_buffer = &load_buffer,
175  .baddr = &baddr,
176  .check_buffer = &check_buffer,
177  .entries = &entries,
179  .sections = &sections,
180  .info = &info,
181 };
182 
183 #ifndef RZ_PLUGIN_INCORE
186  .data = &rz_bin_plugin_dol,
188 };
189 #endif
lzma_index ** i
Definition: index.h:629
static const char ext[]
Definition: apprentice.c:1981
RZ_API RZ_OWN RzList * rz_bin_maps_of_file_sections(RZ_NONNULL RzBinFile *binfile)
Create a list of RzBinMap from RzBinSections queried from the given file.
Definition: bin.c:1040
static bool check_buffer(RzBuffer *buf)
Definition: bin_art.c:129
static bool load_buffer(RzBinFile *bf, RzBinObject *obj, RzBuffer *buf, Sdb *sdb)
Definition: bin_dol.c:57
RZ_API RzLibStruct rizin_plugin
Definition: bin_dol.c:184
RZ_PACKED(typedef struct { ut32 text_paddr[N_TEXT];ut32 data_paddr[N_DATA];ut32 text_vaddr[N_TEXT];ut32 data_vaddr[N_DATA];ut32 text_size[N_TEXT];ut32 data_size[N_DATA];ut32 bss_addr;ut32 bss_size;ut32 entrypoint;ut32 padding[10];})
Definition: bin_dol.c:27
static RzBinInfo * info(RzBinFile *bf)
Definition: bin_dol.c:148
#define N_DATA
Definition: bin_dol.c:25
static ut64 baddr(RzBinFile *bf)
Definition: bin_dol.c:166
#define N_TEXT
Definition: bin_dol.c:24
static RzList * entries(RzBinFile *bf)
Definition: bin_dol.c:137
static RzList * sections(RzBinFile *bf)
Definition: bin_dol.c:86
RzBinPlugin rz_bin_plugin_dol
Definition: bin_dol.c:170
#define RZ_API
#define NULL
Definition: cris-opc.c:27
#define r
Definition: crypto_rc6.c:12
uint32_t ut32
RZ_API void Ht_() free(HtName_(Ht) *ht)
Definition: ht_inc.c:130
voidpf void * buf
Definition: ioapi.h:138
uint8_t ut8
Definition: lh5801.h:11
RZ_API RZ_OWN RzList * rz_list_new(void)
Returns a new initialized RzList pointer (free method is not initialized)
Definition: list.c:235
RZ_API RZ_BORROW RzListIter * rz_list_append(RZ_NONNULL RzList *list, void *data)
Appends at the end of the list a new element.
Definition: list.c:288
return strdup("=SP r13\n" "=LR r14\n" "=PC r15\n" "=A0 r0\n" "=A1 r1\n" "=A2 r2\n" "=A3 r3\n" "=ZF zf\n" "=SF nf\n" "=OF vf\n" "=CF cf\n" "=SN or0\n" "gpr lr .32 56 0\n" "gpr pc .32 60 0\n" "gpr cpsr .32 64 0 ____tfiae_________________qvczn\n" "gpr or0 .32 68 0\n" "gpr tf .1 64.5 0 thumb\n" "gpr ef .1 64.9 0 endian\n" "gpr jf .1 64.24 0 java\n" "gpr qf .1 64.27 0 sticky_overflow\n" "gpr vf .1 64.28 0 overflow\n" "gpr cf .1 64.29 0 carry\n" "gpr zf .1 64.30 0 zero\n" "gpr nf .1 64.31 0 negative\n" "gpr itc .4 64.10 0 if_then_count\n" "gpr gef .4 64.16 0 great_or_equal\n" "gpr r0 .32 0 0\n" "gpr r1 .32 4 0\n" "gpr r2 .32 8 0\n" "gpr r3 .32 12 0\n" "gpr r4 .32 16 0\n" "gpr r5 .32 20 0\n" "gpr r6 .32 24 0\n" "gpr r7 .32 28 0\n" "gpr r8 .32 32 0\n" "gpr r9 .32 36 0\n" "gpr r10 .32 40 0\n" "gpr r11 .32 44 0\n" "gpr r12 .32 48 0\n" "gpr r13 .32 52 0\n" "gpr r14 .32 56 0\n" "gpr r15 .32 60 0\n" "gpr r16 .32 64 0\n" "gpr r17 .32 68 0\n")
static RzSocket * s
Definition: rtr.c:28
#define rz_return_val_if_fail(expr, val)
Definition: rz_assert.h:108
RZ_API st64 rz_buf_read_at(RZ_NONNULL RzBuffer *b, ut64 addr, RZ_NONNULL RZ_OUT ut8 *buf, ut64 len)
Read len bytes of the buffer at the specified address.
Definition: buf.c:1136
RZ_API st64 rz_buf_fread_at(RZ_NONNULL RzBuffer *b, ut64 addr, RZ_NONNULL ut8 *buf, RZ_NONNULL const char *fmt, int n)
...
Definition: buf.c:1001
RZ_API ut64 rz_buf_size(RZ_NONNULL RzBuffer *b)
Return the size of the buffer.
Definition: buf.c:1225
@ RZ_LIB_TYPE_BIN
Definition: rz_lib.h:75
RZ_API char * rz_str_newf(const char *fmt,...) RZ_PRINTF_CHECK(1
RZ_API int rz_str_rwx(const char *str)
Definition: str.c:318
RZ_API void rz_str_case(char *str, bool up)
Definition: str.c:341
#define RZ_NEW0(x)
Definition: rz_types.h:284
#define RZ_VERSION
Definition: rz_version.h:8
XX curplugin == o->plugin.
Definition: rz_bin.h:298
RzBinObject * o
Definition: rz_bin.h:305
char * file
Definition: rz_bin.h:299
RzBuffer * buf
Definition: rz_bin.h:303
int has_va
Definition: rz_bin.h:228
char * type
Definition: rz_bin.h:211
char * os
Definition: rz_bin.h:219
char * machine
Definition: rz_bin.h:216
char * file
Definition: rz_bin.h:210
char * arch
Definition: rz_bin.h:214
int big_endian
Definition: rz_bin.h:235
void * bin_obj
Definition: rz_bin.h:293
char * name
Definition: rz_bin.h:509
char * version
Definition: rz_bin.h:512
Definition: sdb.h:63
ut64(WINAPI *w32_GetEnabledXStateFeatures)()
static int addr
Definition: z80asm.c:58