BFD 1.3.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/ChangeLog +2 -0
- data/LICENSE +674 -0
- data/LICENSE.README +8 -0
- data/README +48 -0
- data/examples/bfd_info.rb +30 -0
- data/examples/list_sections.rb +25 -0
- data/examples/list_symbols.rb +25 -0
- data/lib/BFD.rb +468 -0
- data/module/BFD.c +388 -0
- data/module/BFD.h +68 -0
- data/module/extconf.rb +14 -0
- data/module/rdoc_input/BFD.rb +266 -0
- data/module/ruby_compat.c +17 -0
- data/module/ruby_compat.h +28 -0
- data/tests/ut_bfd.rb +597 -0
- metadata +70 -0
data/module/BFD.c
ADDED
|
@@ -0,0 +1,388 @@
|
|
|
1
|
+
/* Bfd.c
|
|
2
|
+
* Copyright 2010 Thoughtgang <http://www.thoughtgang.org>
|
|
3
|
+
* Written by TG Community Developers <community@thoughtgang.org>
|
|
4
|
+
* Released under the GNU Public License, version 3.
|
|
5
|
+
* See http://www.gnu.org/licenses/gpl.txt for details.
|
|
6
|
+
*/
|
|
7
|
+
|
|
8
|
+
#include <bfd.h>
|
|
9
|
+
|
|
10
|
+
#include <ruby.h>
|
|
11
|
+
#include "ruby_compat.h"
|
|
12
|
+
|
|
13
|
+
#include "BFD.h"
|
|
14
|
+
|
|
15
|
+
#define IVAR(attr) "@" attr
|
|
16
|
+
|
|
17
|
+
static VALUE symFileno;
|
|
18
|
+
static VALUE symPath;
|
|
19
|
+
|
|
20
|
+
static VALUE modBfd;
|
|
21
|
+
static VALUE clsTarget;
|
|
22
|
+
static VALUE clsSection;
|
|
23
|
+
static VALUE clsSymbol;
|
|
24
|
+
|
|
25
|
+
|
|
26
|
+
static VALUE str_to_sym( const char * str ) {
|
|
27
|
+
VALUE var = rb_str_new_cstr(str);
|
|
28
|
+
return rb_funcall(var, rb_intern("to_sym"), 0);
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
/* ---------------------------------------------------------------------- */
|
|
32
|
+
/* Symbol Class */
|
|
33
|
+
|
|
34
|
+
static VALUE symbol_new(bfd * abfd, asymbol *s, char is_dynamic) {
|
|
35
|
+
symbol_info info;
|
|
36
|
+
VALUE class, instance;
|
|
37
|
+
VALUE argv[1] = { Qnil };
|
|
38
|
+
|
|
39
|
+
class = rb_class_new(clsSymbol);
|
|
40
|
+
instance = Data_Wrap_Struct(class, NULL, NULL, s);
|
|
41
|
+
rb_obj_call_init(instance, 0, argv);
|
|
42
|
+
|
|
43
|
+
bfd_symbol_info(s, &info);
|
|
44
|
+
|
|
45
|
+
/* set instance variables */
|
|
46
|
+
rb_iv_set(instance, IVAR(SYM_ATTR_NAME), rb_str_new_cstr(info.name) );
|
|
47
|
+
rb_iv_set(instance, IVAR(SYM_ATTR_TYPE), INT2NUM((int) info.type) );
|
|
48
|
+
rb_iv_set(instance, IVAR(SYM_ATTR_VALUE), SIZET2NUM(info.value) );
|
|
49
|
+
rb_iv_set(instance, IVAR(SYM_ATTR_FLAGS), INT2NUM(s->flags) );
|
|
50
|
+
rb_iv_set(instance, IVAR(SYM_ATTR_BIND),
|
|
51
|
+
rb_str_new_cstr( (is_dynamic ? SYM_BIND_DYNAMIC :
|
|
52
|
+
SYM_BIND_STATIC) ) );
|
|
53
|
+
if ( s->section ) {
|
|
54
|
+
rb_iv_set(instance, IVAR(SYM_ATTR_SECTION),
|
|
55
|
+
rb_str_new_cstr(s->section->name));
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
return instance;
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
static void add_symbol_to_hash( bfd * abfd, asymbol * s, PTR data,
|
|
62
|
+
char is_dynamic ) {
|
|
63
|
+
VALUE sym;
|
|
64
|
+
VALUE * hash = (VALUE *) data;
|
|
65
|
+
|
|
66
|
+
if (! abfd || ! s ) {
|
|
67
|
+
return;
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
sym = symbol_new(abfd, s, is_dynamic);
|
|
71
|
+
rb_hash_aset( *hash, rb_iv_get(sym, IVAR(SYM_ATTR_NAME)), sym);
|
|
72
|
+
}
|
|
73
|
+
|
|
74
|
+
static void init_symbol_class( VALUE modBfd ) {
|
|
75
|
+
/* NOTE: Symbol does not support instantiation via .new() */
|
|
76
|
+
clsSymbol = rb_define_class_under(modBfd, SYMBOL_CLASS_NAME,
|
|
77
|
+
rb_cObject);
|
|
78
|
+
|
|
79
|
+
/* attributes (read-only) */
|
|
80
|
+
rb_define_attr(clsSymbol, SYM_ATTR_NAME, 1, 0);
|
|
81
|
+
rb_define_attr(clsSymbol, SYM_ATTR_VALUE, 1, 0);
|
|
82
|
+
rb_define_attr(clsSymbol, SYM_ATTR_FLAGS, 1, 0);
|
|
83
|
+
rb_define_attr(clsSymbol, SYM_ATTR_SECTION, 1, 0);
|
|
84
|
+
rb_define_attr(clsSymbol, SYM_ATTR_BIND, 1, 0);
|
|
85
|
+
|
|
86
|
+
/* constants */
|
|
87
|
+
rb_define_const(clsSymbol, SYM_BIND_DYN_NAME,
|
|
88
|
+
rb_str_new_cstr(SYM_BIND_DYNAMIC));
|
|
89
|
+
rb_define_const(clsSymbol, SYM_BIND_STAT_NAME,
|
|
90
|
+
rb_str_new_cstr(SYM_BIND_STATIC));
|
|
91
|
+
}
|
|
92
|
+
|
|
93
|
+
/* ---------------------------------------------------------------------- */
|
|
94
|
+
/* Section Class */
|
|
95
|
+
|
|
96
|
+
// TODO: relocs/relfilepos, lines/linefilepos
|
|
97
|
+
|
|
98
|
+
static VALUE cls_section_contents(VALUE instance) {
|
|
99
|
+
/* lazy-loading of section list */
|
|
100
|
+
VALUE var = rb_iv_get(instance, IVAR(SEC_ATTR_CONTENTS));
|
|
101
|
+
if ( var == Qnil ) {
|
|
102
|
+
unsigned char * buf;
|
|
103
|
+
unsigned int size;
|
|
104
|
+
asection * sec;
|
|
105
|
+
|
|
106
|
+
var = Qnil;
|
|
107
|
+
Data_Get_Struct(instance, asection, sec);
|
|
108
|
+
size = bfd_section_size( sec->owner, sec );
|
|
109
|
+
buf = calloc( size, 1 );
|
|
110
|
+
if ( buf &&
|
|
111
|
+
bfd_get_section_contents(sec->owner, sec, buf, 0, size) ) {
|
|
112
|
+
var = rb_str_new( (const char *) buf, size );
|
|
113
|
+
rb_iv_set(instance, IVAR(SEC_ATTR_CONTENTS), var);
|
|
114
|
+
}
|
|
115
|
+
}
|
|
116
|
+
return var;
|
|
117
|
+
}
|
|
118
|
+
|
|
119
|
+
static VALUE section_new(bfd * abfd, asection *s) {
|
|
120
|
+
VALUE class, instance;
|
|
121
|
+
VALUE argv[1] = { Qnil };
|
|
122
|
+
|
|
123
|
+
class = rb_class_new(clsSection);
|
|
124
|
+
instance = Data_Wrap_Struct(class, NULL, NULL, s);
|
|
125
|
+
rb_obj_call_init(instance, 0, argv);
|
|
126
|
+
|
|
127
|
+
/* set instance variables */
|
|
128
|
+
rb_iv_set(instance, IVAR(SEC_ATTR_ID), INT2NUM(s->id) );
|
|
129
|
+
rb_iv_set(instance, IVAR(SEC_ATTR_NAME), rb_str_new_cstr(s->name) );
|
|
130
|
+
rb_iv_set(instance, IVAR(SEC_ATTR_INDEX), INT2NUM(s->index) );
|
|
131
|
+
rb_iv_set(instance, IVAR(SEC_ATTR_FLAGS), INT2NUM(s->flags) );
|
|
132
|
+
rb_iv_set(instance, IVAR(SEC_ATTR_VMA), SIZET2NUM(s->vma) );
|
|
133
|
+
rb_iv_set(instance, IVAR(SEC_ATTR_LMA), SIZET2NUM(s->lma) );
|
|
134
|
+
rb_iv_set(instance, IVAR(SEC_ATTR_SIZE),
|
|
135
|
+
SIZET2NUM(bfd_section_size(abfd, s)) );
|
|
136
|
+
rb_iv_set(instance, IVAR(SEC_ATTR_ALIGN), INT2NUM(s->alignment_power) );
|
|
137
|
+
rb_iv_set(instance, IVAR(SEC_ATTR_FPOS), SIZET2NUM(s->filepos) );
|
|
138
|
+
rb_iv_set(instance, IVAR(SEC_ATTR_CONTENTS), Qnil);
|
|
139
|
+
|
|
140
|
+
return instance;
|
|
141
|
+
}
|
|
142
|
+
|
|
143
|
+
static void add_section_to_hash( bfd * abfd, asection * s, PTR data ) {
|
|
144
|
+
VALUE sec;
|
|
145
|
+
VALUE * hash = (VALUE *) data;
|
|
146
|
+
if (! abfd || ! s ) {
|
|
147
|
+
return;
|
|
148
|
+
}
|
|
149
|
+
sec = section_new(abfd, s);
|
|
150
|
+
rb_hash_aset( *hash, rb_iv_get(sec, IVAR(SEC_ATTR_NAME)), sec);
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
static void init_section_class( VALUE modBfd ) {
|
|
154
|
+
/* NOTE: Section does not support instantiation via .new() */
|
|
155
|
+
clsSection = rb_define_class_under(modBfd, SECTION_CLASS_NAME,
|
|
156
|
+
rb_cObject);
|
|
157
|
+
|
|
158
|
+
/* attributes (read-only) */
|
|
159
|
+
rb_define_attr(clsSection, SEC_ATTR_ID, 1, 0);
|
|
160
|
+
rb_define_attr(clsSection, SEC_ATTR_NAME, 1, 0);
|
|
161
|
+
rb_define_attr(clsSection, SEC_ATTR_INDEX, 1, 0);
|
|
162
|
+
rb_define_attr(clsSection, SEC_ATTR_FLAGS, 1, 0);
|
|
163
|
+
rb_define_attr(clsSection, SEC_ATTR_VMA, 1, 0);
|
|
164
|
+
rb_define_attr(clsSection, SEC_ATTR_LMA, 1, 0);
|
|
165
|
+
rb_define_attr(clsSection, SEC_ATTR_SIZE, 1, 0);
|
|
166
|
+
rb_define_attr(clsSection, SEC_ATTR_ALIGN, 1, 0);
|
|
167
|
+
rb_define_attr(clsSection, SEC_ATTR_FPOS, 1, 0);
|
|
168
|
+
rb_define_attr(clsSection, SEC_ATTR_SYM, 1, 0);
|
|
169
|
+
|
|
170
|
+
rb_define_method(clsSection, SEC_ATTR_CONTENTS, cls_section_contents,
|
|
171
|
+
0);
|
|
172
|
+
}
|
|
173
|
+
|
|
174
|
+
/* ---------------------------------------------------------------------- */
|
|
175
|
+
/* Target Class */
|
|
176
|
+
|
|
177
|
+
static void fill_arch_info( const struct bfd_arch_info * info, VALUE * hash ) {
|
|
178
|
+
rb_hash_aset( *hash, str_to_sym(AINFO_MEMBER_BPW),
|
|
179
|
+
INT2NUM(info->bits_per_word) );
|
|
180
|
+
rb_hash_aset( *hash, str_to_sym(AINFO_MEMBER_BPA),
|
|
181
|
+
INT2NUM(info->bits_per_address) );
|
|
182
|
+
rb_hash_aset( *hash, str_to_sym(AINFO_MEMBER_BPB),
|
|
183
|
+
INT2NUM(info->bits_per_byte) );
|
|
184
|
+
rb_hash_aset( *hash, str_to_sym(AINFO_MEMBER_ALIGN),
|
|
185
|
+
INT2NUM(info->section_align_power) );
|
|
186
|
+
rb_hash_aset( *hash, str_to_sym(AINFO_MEMBER_ARCH),
|
|
187
|
+
rb_str_new_cstr(bfd_printable_arch_mach(info->arch,
|
|
188
|
+
info->mach)) );
|
|
189
|
+
}
|
|
190
|
+
|
|
191
|
+
static VALUE new_target_for_bfd(VALUE class, bfd * abfd, VALUE hash) {
|
|
192
|
+
VALUE instance, var;
|
|
193
|
+
VALUE argv[1] = { Qnil };
|
|
194
|
+
// TODO: process hash argument supporting flavour, arch, and mach info
|
|
195
|
+
|
|
196
|
+
if (! abfd || abfd == (bfd *) bfd_error_invalid_target ) {
|
|
197
|
+
bfd_error_type err = bfd_get_error();
|
|
198
|
+
rb_raise(rb_eRuntimeError, "BFD error (%d): %s", err,
|
|
199
|
+
bfd_errmsg(err) );
|
|
200
|
+
}
|
|
201
|
+
|
|
202
|
+
if (! bfd_check_format( abfd, bfd_object ) ) {
|
|
203
|
+
bfd_error_type err = bfd_get_error();
|
|
204
|
+
rb_raise(rb_eRuntimeError,
|
|
205
|
+
"Unable to identify target format (%d): %s", err,
|
|
206
|
+
bfd_errmsg(err) );
|
|
207
|
+
}
|
|
208
|
+
|
|
209
|
+
if ( bfd_get_flavour( abfd ) == bfd_target_unknown_flavour ) {
|
|
210
|
+
/* we do not want to raise an exception, as the BFD is
|
|
211
|
+
* still usable, just empty */
|
|
212
|
+
fprintf( stderr, "[BFD] Warning: unknown BFD flavour\n" );
|
|
213
|
+
}
|
|
214
|
+
|
|
215
|
+
instance = Data_Wrap_Struct(class, NULL, bfd_close, abfd);
|
|
216
|
+
rb_obj_call_init(instance, 0, argv);
|
|
217
|
+
|
|
218
|
+
/* set instance variables */
|
|
219
|
+
rb_iv_set(instance, IVAR(TGT_ATTR_ID), INT2NUM(abfd->id) );
|
|
220
|
+
rb_iv_set(instance, IVAR(TGT_ATTR_FILENAME),
|
|
221
|
+
rb_str_new_cstr(abfd->filename) );
|
|
222
|
+
rb_iv_set(instance, IVAR(TGT_ATTR_FORMAT),
|
|
223
|
+
rb_str_new_cstr(bfd_format_string(abfd->format)) );
|
|
224
|
+
rb_iv_set(instance, IVAR(TGT_ATTR_FMT_FLAGS), INT2NUM(abfd->flags) );
|
|
225
|
+
rb_iv_set(instance, IVAR(TGT_ATTR_FLAVOUR),
|
|
226
|
+
INT2NUM(abfd->xvec->flavour) );
|
|
227
|
+
rb_iv_set(instance, IVAR(TGT_ATTR_TYPE),
|
|
228
|
+
rb_str_new_cstr(abfd->xvec->name) );
|
|
229
|
+
rb_iv_set(instance, IVAR(TGT_ATTR_TYPEFLAGS),
|
|
230
|
+
INT2NUM(abfd->xvec->object_flags) );
|
|
231
|
+
rb_iv_set(instance, IVAR(TGT_ATTR_ENDIAN),
|
|
232
|
+
INT2NUM(abfd->xvec->byteorder) );
|
|
233
|
+
rb_iv_set(instance, IVAR(TGT_ATTR_START_ADDR),
|
|
234
|
+
SIZET2NUM(abfd->start_address) );
|
|
235
|
+
rb_iv_set(instance, IVAR(TGT_ATTR_SECTIONS), Qnil);
|
|
236
|
+
rb_iv_set(instance, IVAR(TGT_ATTR_SYMBOLS), Qnil);
|
|
237
|
+
|
|
238
|
+
var = rb_hash_new();
|
|
239
|
+
fill_arch_info( bfd_get_arch_info(abfd), &var );
|
|
240
|
+
rb_iv_set(instance, IVAR(TGT_ATTR_ARCH_INFO), var );
|
|
241
|
+
|
|
242
|
+
return instance;
|
|
243
|
+
}
|
|
244
|
+
|
|
245
|
+
static VALUE cls_target_new(VALUE class, VALUE tgt, VALUE hash) {
|
|
246
|
+
bfd * abfd = NULL;
|
|
247
|
+
|
|
248
|
+
if ( rb_respond_to( tgt, symFileno ) ) {
|
|
249
|
+
int fd;
|
|
250
|
+
VALUE fd_val = rb_funcall(tgt, symFileno, 0);
|
|
251
|
+
VALUE rb_path = rb_funcall(tgt, symPath, 0);
|
|
252
|
+
char * path = StringValuePtr(rb_path);
|
|
253
|
+
if ( Qnil == fd_val ) {
|
|
254
|
+
rb_raise(rb_eArgError, "Invalid fileno() in IO object");
|
|
255
|
+
}
|
|
256
|
+
fd = NUM2INT(fd_val);
|
|
257
|
+
abfd = bfd_fdopenr (path, NULL, fd);
|
|
258
|
+
if (! abfd ) {
|
|
259
|
+
bfd_error_type err = bfd_get_error();
|
|
260
|
+
rb_raise(rb_eRuntimeError, "BFD error (%d) in open: %s",
|
|
261
|
+
err, bfd_errmsg(err) );
|
|
262
|
+
}
|
|
263
|
+
|
|
264
|
+
} else if ( Qtrue == rb_obj_is_kind_of( tgt, rb_cString) ) {
|
|
265
|
+
char * path = StringValuePtr(tgt);
|
|
266
|
+
abfd = bfd_openr(path, NULL);
|
|
267
|
+
|
|
268
|
+
} else {
|
|
269
|
+
rb_raise(rb_eArgError, "Bfd requires a path or IO object");
|
|
270
|
+
}
|
|
271
|
+
|
|
272
|
+
return new_target_for_bfd( class, abfd, hash );
|
|
273
|
+
}
|
|
274
|
+
|
|
275
|
+
static VALUE cls_target_sections(VALUE instance) {
|
|
276
|
+
/* lazy-loading of section list */
|
|
277
|
+
VALUE var = rb_iv_get(instance, IVAR(TGT_ATTR_SECTIONS));
|
|
278
|
+
if ( var == Qnil ) {
|
|
279
|
+
bfd * abfd;
|
|
280
|
+
var = rb_hash_new();
|
|
281
|
+
|
|
282
|
+
Data_Get_Struct(instance, bfd, abfd);
|
|
283
|
+
bfd_map_over_sections( abfd, add_section_to_hash, &var );
|
|
284
|
+
rb_iv_set(instance, IVAR(TGT_ATTR_SECTIONS), var);
|
|
285
|
+
}
|
|
286
|
+
return var;
|
|
287
|
+
}
|
|
288
|
+
|
|
289
|
+
static void load_static_syms( bfd * abfd, VALUE * hash ) {
|
|
290
|
+
size_t size;
|
|
291
|
+
unsigned int i, num;
|
|
292
|
+
asymbol ** syms;
|
|
293
|
+
|
|
294
|
+
size = bfd_get_symtab_upper_bound(abfd);
|
|
295
|
+
if ( size <= 0 ) {
|
|
296
|
+
return;
|
|
297
|
+
}
|
|
298
|
+
|
|
299
|
+
syms = (struct bfd_symbol **) malloc(size);
|
|
300
|
+
if (! syms ) {
|
|
301
|
+
return;
|
|
302
|
+
}
|
|
303
|
+
|
|
304
|
+
num = bfd_canonicalize_symtab(abfd, syms);
|
|
305
|
+
for ( i=0; i < num; i++ ) {
|
|
306
|
+
add_symbol_to_hash( abfd, syms[i], hash, 0 );
|
|
307
|
+
}
|
|
308
|
+
|
|
309
|
+
free(syms);
|
|
310
|
+
}
|
|
311
|
+
|
|
312
|
+
static void load_dyn_syms( bfd * abfd, VALUE * hash ) {
|
|
313
|
+
size_t size;
|
|
314
|
+
unsigned int i, num;
|
|
315
|
+
asymbol ** syms;
|
|
316
|
+
|
|
317
|
+
size = bfd_get_dynamic_symtab_upper_bound(abfd);
|
|
318
|
+
if ( size <= 0 ) {
|
|
319
|
+
return;
|
|
320
|
+
}
|
|
321
|
+
|
|
322
|
+
syms = (asymbol **) malloc(size);
|
|
323
|
+
if (! syms ) {
|
|
324
|
+
return;
|
|
325
|
+
}
|
|
326
|
+
|
|
327
|
+
num = bfd_canonicalize_dynamic_symtab(abfd, syms);
|
|
328
|
+
for ( i=0; i < num; i++ ) {
|
|
329
|
+
add_symbol_to_hash( abfd, syms[i], hash, 1 );
|
|
330
|
+
}
|
|
331
|
+
|
|
332
|
+
free(syms);
|
|
333
|
+
}
|
|
334
|
+
|
|
335
|
+
static VALUE cls_target_symbols(VALUE instance) {
|
|
336
|
+
/* Lazy loading of symbols */
|
|
337
|
+
VALUE var = rb_iv_get(instance, IVAR(TGT_ATTR_SYMBOLS));
|
|
338
|
+
if ( var == Qnil ) {
|
|
339
|
+
var = rb_hash_new();
|
|
340
|
+
bfd * abfd;
|
|
341
|
+
Data_Get_Struct(instance, bfd, abfd);
|
|
342
|
+
if ( bfd_get_file_flags(abfd) & HAS_SYMS ) {
|
|
343
|
+
/* GNU uses macros, not functions, for these BFD
|
|
344
|
+
* routines so we cannot abstract to fn pointers */
|
|
345
|
+
load_static_syms( abfd, &var );
|
|
346
|
+
load_dyn_syms( abfd, &var );
|
|
347
|
+
}
|
|
348
|
+
rb_iv_set(instance, IVAR(TGT_ATTR_SYMBOLS), var);
|
|
349
|
+
}
|
|
350
|
+
return var;
|
|
351
|
+
}
|
|
352
|
+
|
|
353
|
+
static void init_target_class( VALUE modBfd ) {
|
|
354
|
+
clsTarget = rb_define_class_under(modBfd, TARGET_CLASS_NAME,
|
|
355
|
+
rb_cObject);
|
|
356
|
+
rb_define_singleton_method(clsTarget, "ext_new", cls_target_new, 2);
|
|
357
|
+
|
|
358
|
+
/* attributes (read-only) */
|
|
359
|
+
rb_define_attr(clsTarget, TGT_ATTR_ID, 1, 0);
|
|
360
|
+
rb_define_attr(clsTarget, TGT_ATTR_FILENAME, 1, 0);
|
|
361
|
+
rb_define_attr(clsTarget, TGT_ATTR_FORMAT, 1, 0);
|
|
362
|
+
rb_define_attr(clsTarget, TGT_ATTR_FMT_FLAGS, 1, 0);
|
|
363
|
+
rb_define_attr(clsTarget, TGT_ATTR_FLAVOUR, 1, 0);
|
|
364
|
+
rb_define_attr(clsTarget, TGT_ATTR_TYPE, 1, 0);
|
|
365
|
+
rb_define_attr(clsTarget, TGT_ATTR_TYPEFLAGS, 1, 0);
|
|
366
|
+
rb_define_attr(clsTarget, TGT_ATTR_ENDIAN, 1, 0);
|
|
367
|
+
rb_define_attr(clsTarget, TGT_ATTR_START_ADDR, 1, 0);
|
|
368
|
+
rb_define_attr(clsTarget, TGT_ATTR_ARCH_INFO, 1, 0);
|
|
369
|
+
|
|
370
|
+
rb_define_method(clsTarget, TGT_ATTR_SECTIONS, cls_target_sections, 0);
|
|
371
|
+
rb_define_method(clsTarget, TGT_ATTR_SYMBOLS, cls_target_symbols, 0);
|
|
372
|
+
|
|
373
|
+
bfd_init();
|
|
374
|
+
}
|
|
375
|
+
|
|
376
|
+
/* ---------------------------------------------------------------------- */
|
|
377
|
+
/* BFD Module */
|
|
378
|
+
|
|
379
|
+
void Init_BFDext() {
|
|
380
|
+
symFileno = rb_intern("fileno");
|
|
381
|
+
symPath = rb_intern("path");
|
|
382
|
+
|
|
383
|
+
modBfd = rb_define_module(BFD_MODULE_NAME);
|
|
384
|
+
|
|
385
|
+
init_target_class(modBfd);
|
|
386
|
+
init_section_class(modBfd);
|
|
387
|
+
init_symbol_class(modBfd);
|
|
388
|
+
}
|
data/module/BFD.h
ADDED
|
@@ -0,0 +1,68 @@
|
|
|
1
|
+
/* Bfd.h
|
|
2
|
+
* Copyright 2010 Thoughtgang <http://www.thoughtgang.org>
|
|
3
|
+
* Written by TG Community Developers <community@thoughtgang.org>
|
|
4
|
+
* Released under the GNU Public License, version 3.
|
|
5
|
+
* See http://www.gnu.org/licenses/gpl.txt for details.
|
|
6
|
+
*/
|
|
7
|
+
|
|
8
|
+
#ifndef BFD_RUBY_EXTENSION_H
|
|
9
|
+
#define BFD_RUBY_EXTENSION_H
|
|
10
|
+
|
|
11
|
+
/* Bfd::Symbol */
|
|
12
|
+
#define SYM_ATTR_NAME "name"
|
|
13
|
+
#define SYM_ATTR_TYPE "type"
|
|
14
|
+
#define SYM_ATTR_VALUE "value"
|
|
15
|
+
#define SYM_ATTR_FLAGS "raw_flags"
|
|
16
|
+
#define SYM_ATTR_SECTION "section"
|
|
17
|
+
#define SYM_ATTR_BIND "binding"
|
|
18
|
+
|
|
19
|
+
#define SYM_BIND_DYNAMIC "dynamic"
|
|
20
|
+
#define SYM_BIND_DYN_NAME "DYNAMIC"
|
|
21
|
+
#define SYM_BIND_STATIC "static"
|
|
22
|
+
#define SYM_BIND_STAT_NAME "STATIC"
|
|
23
|
+
|
|
24
|
+
/* Bfd::Section */
|
|
25
|
+
#define SEC_ATTR_ID "id"
|
|
26
|
+
#define SEC_ATTR_NAME "name"
|
|
27
|
+
#define SEC_ATTR_INDEX "index"
|
|
28
|
+
#define SEC_ATTR_FLAGS "raw_flags"
|
|
29
|
+
#define SEC_ATTR_VMA "vma"
|
|
30
|
+
#define SEC_ATTR_LMA "lma"
|
|
31
|
+
#define SEC_ATTR_SIZE "size"
|
|
32
|
+
#define SEC_ATTR_ALIGN "alignment_power"
|
|
33
|
+
#define SEC_ATTR_FPOS "file_pos"
|
|
34
|
+
#define SEC_ATTR_CONTENTS "contents"
|
|
35
|
+
#define SEC_ATTR_SYM "symbol"
|
|
36
|
+
|
|
37
|
+
/* Bfd::Target */
|
|
38
|
+
#define TGT_ATTR_ID "id"
|
|
39
|
+
#define TGT_ATTR_FILENAME "filename"
|
|
40
|
+
#define TGT_ATTR_FORMAT "format"
|
|
41
|
+
#define TGT_ATTR_FMT_FLAGS "raw_format_flags"
|
|
42
|
+
#define TGT_ATTR_START_ADDR "start_address"
|
|
43
|
+
#define TGT_ATTR_ARCH_INFO "arch_info"
|
|
44
|
+
#define TGT_ATTR_FLAVOUR "raw_flavour"
|
|
45
|
+
#define TGT_ATTR_TYPE "type"
|
|
46
|
+
#define TGT_ATTR_TYPEFLAGS "raw_type_flags"
|
|
47
|
+
#define TGT_ATTR_ENDIAN "raw_endian"
|
|
48
|
+
#define TGT_ATTR_SECTIONS "sections"
|
|
49
|
+
#define TGT_ATTR_SYMBOLS "symbols"
|
|
50
|
+
|
|
51
|
+
#define TGT_METHOD_SECVMA "section_for_vma"
|
|
52
|
+
|
|
53
|
+
/* arch_info members */
|
|
54
|
+
#define AINFO_MEMBER_BPW "bits_per_word"
|
|
55
|
+
#define AINFO_MEMBER_BPA "bits_per_address"
|
|
56
|
+
#define AINFO_MEMBER_BPB "bits_per_byte"
|
|
57
|
+
#define AINFO_MEMBER_ARCH "architecture"
|
|
58
|
+
#define AINFO_MEMBER_ALIGN "section_align_power"
|
|
59
|
+
|
|
60
|
+
/* module and class names */
|
|
61
|
+
#define BFD_MODULE_NAME "Bfd"
|
|
62
|
+
#define TARGET_CLASS_NAME "Target"
|
|
63
|
+
#define SECTION_CLASS_NAME "Section"
|
|
64
|
+
#define SYMBOL_CLASS_NAME "Symbol"
|
|
65
|
+
|
|
66
|
+
void Init_BFDext();
|
|
67
|
+
|
|
68
|
+
#endif
|