Rizin
unix-like reverse engineering framework and cli tools
omap.c
Go to the documentation of this file.
1 // SPDX-FileCopyrightText: 2014-2016 iniside <inisider@gmail.com>
2 // SPDX-FileCopyrightText: 2014-2016 pancake <pancake@nopcode.org>
3 // SPDX-FileCopyrightText: 2021 Basstorm <basstorm@nyist.edu.cn>
4 // SPDX-License-Identifier: LGPL-3.0-only
5 
6 #include "pdb.h"
7 
9  rz_return_val_if_fail(pdb && stream, false);
10  if (!pdb->s_omap) {
12  }
13  RzBuffer *buf = stream->stream_data;
14  RzPdbOmapStream *s = pdb->s_omap;
15  if (!s) {
16  RZ_LOG_ERROR("Error allocating memory.\n");
17  return false;
18  }
19  if (!s->entries) {
20  s->entries = rz_list_new();
21  }
23  ut32 read_len = 0;
24  while (read_len < size) {
26  if (!entry) {
27  rz_list_free(s->entries);
28  return false;
29  }
30  if (!rz_buf_read_le32(buf, &entry->from) ||
31  !rz_buf_read_le32(buf, &entry->to)) {
32  free(entry);
33  rz_list_free(s->entries);
34  return false;
35  }
36  read_len += sizeof(ut32) * 2;
37  rz_list_append(s->entries, entry);
38  }
39  return true;
40 }
41 
43  if (!stream) {
44  return;
45  }
47  RzListIter *it;
48  rz_list_foreach (stream->entries, it, entry) { RZ_FREE(entry); }
49  rz_list_free(stream->entries);
50  free(stream);
51 }
52 
53 // inclusive indices
54 // 0 <= imin when using truncate toward zero divide
55 // imid = (imin+imax)/2;
56 // imin unrestricted when using truncate toward minus infinity divide
57 // imid = (imin+imax)>>1; or
58 // imid = (int)floor((imin+imax)/2.0);
59 static int binary_search(unsigned int *A, int key, int imin, int imax) {
60  int imid;
61 
62  // continually narrow search until just one element remains
63  while (imin < imax) {
64  imid = (imin + imax) / 2;
65  if (A[imid] < key) {
66  imin = imid + 1;
67  } else {
68  imax = imid;
69  }
70  }
71  // At exit of while:
72  // if A[] is empty, then imax < imin
73  // otherwise imax == imin
74 
75  // deferred test for equality
76  if ((imax == imin) && (A[imin] == key)) {
77  return imin;
78  }
79  return -1;
80 }
81 
89 RZ_API int rz_bin_pdb_omap_remap(RZ_NONNULL RzPdbOmapStream *omap_stream, int address) {
90  OmapEntry *omap_entry = 0;
91  RzListIter *it = 0;
92  int i = 0;
93  int pos = 0;
94  int len = 0;
95 
96  if (!omap_stream) {
97  return address;
98  }
99 
100  len = rz_list_length(omap_stream->entries);
101 
102  if (omap_stream->froms == 0) {
103  omap_stream->froms = (unsigned int *)malloc(4 * len);
104  if (!omap_stream->froms) {
105  return -1;
106  }
107  it = rz_list_iterator(omap_stream->entries);
108  while (rz_list_iter_next(it)) {
109  omap_entry = (OmapEntry *)rz_list_iter_get(it);
110  omap_stream->froms[i] = omap_entry->from;
111  i++;
112  }
113  }
114 
115  // mb (len -1) ???
116  pos = binary_search(omap_stream->froms, address, 0, (len));
117 
118  if (pos == -1) {
119  return -1;
120  }
121 
122  if (omap_stream->froms[pos] != address) {
123  pos -= 1;
124  }
125  omap_entry = (OmapEntry *)rz_list_get_n(omap_stream->entries, pos);
126  if (!omap_entry) {
127  return -1;
128  }
129  if (omap_entry->to == 0) {
130  return omap_entry->to;
131  }
132  return omap_entry->to + (address - omap_entry->from);
133 }
size_t len
Definition: 6502dis.c:15
#define RZ_IPI
Definition: analysis_wasm.c:11
lzma_index ** i
Definition: index.h:629
#define A(x)
Definition: arc.h:165
#define RZ_API
static static sync static getppid static getegid const char static filename char static len const char char static bufsiz static mask static vfork const void static prot static getpgrp const char static swapflags static arg static fd static protocol static who struct sockaddr static addrlen static backlog struct timeval struct timezone static tz const struct iovec static count static mode const void const struct sockaddr static tolen const char static pathname void static offset struct stat static buf void long static basep static whence static length const void static len key
Definition: sflib.h:118
uint32_t ut32
RZ_API void Ht_() free(HtName_(Ht) *ht)
Definition: ht_inc.c:130
voidpf void uLong size
Definition: ioapi.h:138
voidpf stream
Definition: ioapi.h:138
voidpf void * buf
Definition: ioapi.h:138
RZ_API RZ_BORROW RzListIter * rz_list_iterator(const RzList *list)
returns the first RzList iterator int the list
Definition: list.c:51
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 void * rz_list_get_n(RZ_NONNULL const RzList *list, ut32 n)
Returns the N-th element of the list.
Definition: list.c:574
RZ_API ut32 rz_list_length(RZ_NONNULL const RzList *list)
Returns the length of the list.
Definition: list.c:109
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
RZ_API void rz_list_free(RZ_NONNULL RzList *list)
Empties the list and frees the list pointer.
Definition: list.c:137
void * malloc(size_t size)
Definition: malloc.c:123
RZ_API int rz_bin_pdb_omap_remap(RZ_NONNULL RzPdbOmapStream *omap_stream, int address)
return remapped symbol address
Definition: omap.c:89
static int binary_search(unsigned int *A, int key, int imin, int imax)
Definition: omap.c:59
RZ_IPI bool parse_omap_stream(RzPdb *pdb, RzPdbMsfStream *stream)
Definition: omap.c:8
RZ_IPI void free_omap_stream(RzPdbOmapStream *stream)
Definition: omap.c:42
static RzSocket * s
Definition: rtr.c:28
#define rz_return_val_if_fail(expr, val)
Definition: rz_assert.h:108
#define rz_buf_read_le32(b, result)
Definition: rz_buf.h:267
RZ_API ut64 rz_buf_size(RZ_NONNULL RzBuffer *b)
Return the size of the buffer.
Definition: buf.c:1225
#define RZ_LOG_ERROR(fmtstr,...)
Definition: rz_log.h:58
#define RZ_NEW0(x)
Definition: rz_types.h:284
#define RZ_NONNULL
Definition: rz_types.h:64
#define RZ_FREE(x)
Definition: rz_types.h:369
Definition: omap.h:9
ut32 from
Definition: omap.h:10
ut32 to
Definition: omap.h:11
Definition: zipcmp.c:77
RzPdbOmapStream * s_omap
Definition: rz_pdb.h:249
int pos
Definition: main.c:11