rdwarf 0.0.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/.gitignore +16 -0
- data/.travis.yml +4 -0
- data/Gemfile +4 -0
- data/LICENSE.txt +28 -0
- data/README.md +39 -0
- data/Rakefile +8 -0
- data/bin/console +14 -0
- data/bin/setup +7 -0
- data/ext/rdwarf/depend +5 -0
- data/ext/rdwarf/extconf.rb +29 -0
- data/ext/rdwarf/libdwarf/CHANGES +102 -0
- data/ext/rdwarf/libdwarf/CODINGSTYLE +71 -0
- data/ext/rdwarf/libdwarf/COPYING +28 -0
- data/ext/rdwarf/libdwarf/ChangeLog +619 -0
- data/ext/rdwarf/libdwarf/ChangeLog2006 +835 -0
- data/ext/rdwarf/libdwarf/ChangeLog2007 +217 -0
- data/ext/rdwarf/libdwarf/ChangeLog2008 +263 -0
- data/ext/rdwarf/libdwarf/ChangeLog2009 +348 -0
- data/ext/rdwarf/libdwarf/ChangeLog2010 +175 -0
- data/ext/rdwarf/libdwarf/ChangeLog2011 +297 -0
- data/ext/rdwarf/libdwarf/ChangeLog2012 +131 -0
- data/ext/rdwarf/libdwarf/ChangeLog2013 +238 -0
- data/ext/rdwarf/libdwarf/ChangeLog2014 +399 -0
- data/ext/rdwarf/libdwarf/LGPL.txt +504 -0
- data/ext/rdwarf/libdwarf/LIBDWARFCOPYRIGHT +40 -0
- data/ext/rdwarf/libdwarf/Makefile.in +220 -0
- data/ext/rdwarf/libdwarf/NEWS +535 -0
- data/ext/rdwarf/libdwarf/README +235 -0
- data/ext/rdwarf/libdwarf/checkexamples.c +1179 -0
- data/ext/rdwarf/libdwarf/cmplrs/dwarf_addr_finder.h +55 -0
- data/ext/rdwarf/libdwarf/common.c +62 -0
- data/ext/rdwarf/libdwarf/common.h +38 -0
- data/ext/rdwarf/libdwarf/config.h.in +146 -0
- data/ext/rdwarf/libdwarf/configure +5581 -0
- data/ext/rdwarf/libdwarf/configure.in +167 -0
- data/ext/rdwarf/libdwarf/dw-linetableheader.txt +39 -0
- data/ext/rdwarf/libdwarf/dwarf.h +1342 -0
- data/ext/rdwarf/libdwarf/dwarf_abbrev.c +291 -0
- data/ext/rdwarf/libdwarf/dwarf_abbrev.h +45 -0
- data/ext/rdwarf/libdwarf/dwarf_addr_finder.c +676 -0
- data/ext/rdwarf/libdwarf/dwarf_alloc.c +685 -0
- data/ext/rdwarf/libdwarf/dwarf_alloc.h +38 -0
- data/ext/rdwarf/libdwarf/dwarf_arange.c +595 -0
- data/ext/rdwarf/libdwarf/dwarf_arange.h +62 -0
- data/ext/rdwarf/libdwarf/dwarf_base_types.h +157 -0
- data/ext/rdwarf/libdwarf/dwarf_die_deliv.c +1802 -0
- data/ext/rdwarf/libdwarf/dwarf_die_deliv.h +46 -0
- data/ext/rdwarf/libdwarf/dwarf_elf_access.c +1348 -0
- data/ext/rdwarf/libdwarf/dwarf_elf_access.h +46 -0
- data/ext/rdwarf/libdwarf/dwarf_error.c +492 -0
- data/ext/rdwarf/libdwarf/dwarf_error.h +53 -0
- data/ext/rdwarf/libdwarf/dwarf_form.c +1302 -0
- data/ext/rdwarf/libdwarf/dwarf_frame.c +2454 -0
- data/ext/rdwarf/libdwarf/dwarf_frame.h +418 -0
- data/ext/rdwarf/libdwarf/dwarf_frame2.c +1533 -0
- data/ext/rdwarf/libdwarf/dwarf_frame3.c +282 -0
- data/ext/rdwarf/libdwarf/dwarf_funcs.c +123 -0
- data/ext/rdwarf/libdwarf/dwarf_funcs.h +33 -0
- data/ext/rdwarf/libdwarf/dwarf_gdbindex.c +520 -0
- data/ext/rdwarf/libdwarf/dwarf_gdbindex.h +97 -0
- data/ext/rdwarf/libdwarf/dwarf_global.c +612 -0
- data/ext/rdwarf/libdwarf/dwarf_global.h +117 -0
- data/ext/rdwarf/libdwarf/dwarf_harmless.c +228 -0
- data/ext/rdwarf/libdwarf/dwarf_harmless.h +31 -0
- data/ext/rdwarf/libdwarf/dwarf_incl.h +61 -0
- data/ext/rdwarf/libdwarf/dwarf_init_finish.c +1263 -0
- data/ext/rdwarf/libdwarf/dwarf_leb.c +159 -0
- data/ext/rdwarf/libdwarf/dwarf_line.c +1822 -0
- data/ext/rdwarf/libdwarf/dwarf_line.h +446 -0
- data/ext/rdwarf/libdwarf/dwarf_line2.c +98 -0
- data/ext/rdwarf/libdwarf/dwarf_line_table_reader_common.c +1583 -0
- data/ext/rdwarf/libdwarf/dwarf_loc.c +1525 -0
- data/ext/rdwarf/libdwarf/dwarf_loc.h +149 -0
- data/ext/rdwarf/libdwarf/dwarf_loc2.c +833 -0
- data/ext/rdwarf/libdwarf/dwarf_macro.c +479 -0
- data/ext/rdwarf/libdwarf/dwarf_macro.h +35 -0
- data/ext/rdwarf/libdwarf/dwarf_opaque.h +778 -0
- data/ext/rdwarf/libdwarf/dwarf_original_elf_init.c +219 -0
- data/ext/rdwarf/libdwarf/dwarf_print_lines.c +631 -0
- data/ext/rdwarf/libdwarf/dwarf_pubtypes.c +132 -0
- data/ext/rdwarf/libdwarf/dwarf_query.c +1594 -0
- data/ext/rdwarf/libdwarf/dwarf_ranges.c +194 -0
- data/ext/rdwarf/libdwarf/dwarf_reloc_arm.h +308 -0
- data/ext/rdwarf/libdwarf/dwarf_reloc_mips.h +117 -0
- data/ext/rdwarf/libdwarf/dwarf_reloc_ppc.h +242 -0
- data/ext/rdwarf/libdwarf/dwarf_reloc_ppc64.h +272 -0
- data/ext/rdwarf/libdwarf/dwarf_reloc_x86_64.h +127 -0
- data/ext/rdwarf/libdwarf/dwarf_sort_line.c +665 -0
- data/ext/rdwarf/libdwarf/dwarf_string.c +82 -0
- data/ext/rdwarf/libdwarf/dwarf_stubs.c +38 -0
- data/ext/rdwarf/libdwarf/dwarf_tied.c +423 -0
- data/ext/rdwarf/libdwarf/dwarf_tsearch.h +125 -0
- data/ext/rdwarf/libdwarf/dwarf_tsearchhash.c +675 -0
- data/ext/rdwarf/libdwarf/dwarf_types.c +121 -0
- data/ext/rdwarf/libdwarf/dwarf_types.h +32 -0
- data/ext/rdwarf/libdwarf/dwarf_util.c +913 -0
- data/ext/rdwarf/libdwarf/dwarf_util.h +324 -0
- data/ext/rdwarf/libdwarf/dwarf_vars.c +125 -0
- data/ext/rdwarf/libdwarf/dwarf_vars.h +29 -0
- data/ext/rdwarf/libdwarf/dwarf_weaks.c +123 -0
- data/ext/rdwarf/libdwarf/dwarf_weaks.h +29 -0
- data/ext/rdwarf/libdwarf/dwarf_xu_index.c +579 -0
- data/ext/rdwarf/libdwarf/dwarf_xu_index.h +68 -0
- data/ext/rdwarf/libdwarf/dwgetopt.c +181 -0
- data/ext/rdwarf/libdwarf/dwgetopt.h +51 -0
- data/ext/rdwarf/libdwarf/gennames.c +531 -0
- data/ext/rdwarf/libdwarf/install.sh +119 -0
- data/ext/rdwarf/libdwarf/libdwarf.h.in +3746 -0
- data/ext/rdwarf/libdwarf/libdwarf2.1.mm +9805 -0
- data/ext/rdwarf/libdwarf/libdwarf2.1.pdf +0 -0
- data/ext/rdwarf/libdwarf/libdwarf2p.1.mm +2807 -0
- data/ext/rdwarf/libdwarf/libdwarf2p.1.pdf +0 -0
- data/ext/rdwarf/libdwarf/libdwarfdefs.h +81 -0
- data/ext/rdwarf/libdwarf/malloc_check.c +327 -0
- data/ext/rdwarf/libdwarf/malloc_check.h +52 -0
- data/ext/rdwarf/libdwarf/mips_extensions.mm +1266 -0
- data/ext/rdwarf/libdwarf/mips_extensions.pdf +0 -0
- data/ext/rdwarf/libdwarf/pro_alloc.c +179 -0
- data/ext/rdwarf/libdwarf/pro_alloc.h +33 -0
- data/ext/rdwarf/libdwarf/pro_arange.c +310 -0
- data/ext/rdwarf/libdwarf/pro_arange.h +51 -0
- data/ext/rdwarf/libdwarf/pro_die.c +431 -0
- data/ext/rdwarf/libdwarf/pro_die.h +59 -0
- data/ext/rdwarf/libdwarf/pro_encode_nm.c +108 -0
- data/ext/rdwarf/libdwarf/pro_encode_nm.h +39 -0
- data/ext/rdwarf/libdwarf/pro_error.c +96 -0
- data/ext/rdwarf/libdwarf/pro_error.h +43 -0
- data/ext/rdwarf/libdwarf/pro_expr.c +575 -0
- data/ext/rdwarf/libdwarf/pro_expr.h +36 -0
- data/ext/rdwarf/libdwarf/pro_finish.c +45 -0
- data/ext/rdwarf/libdwarf/pro_forms.c +1271 -0
- data/ext/rdwarf/libdwarf/pro_frame.c +572 -0
- data/ext/rdwarf/libdwarf/pro_frame.h +120 -0
- data/ext/rdwarf/libdwarf/pro_funcs.c +50 -0
- data/ext/rdwarf/libdwarf/pro_incl.h +91 -0
- data/ext/rdwarf/libdwarf/pro_init.c +327 -0
- data/ext/rdwarf/libdwarf/pro_line.c +373 -0
- data/ext/rdwarf/libdwarf/pro_line.h +112 -0
- data/ext/rdwarf/libdwarf/pro_macinfo.c +457 -0
- data/ext/rdwarf/libdwarf/pro_macinfo.h +31 -0
- data/ext/rdwarf/libdwarf/pro_opaque.h +513 -0
- data/ext/rdwarf/libdwarf/pro_pubnames.c +60 -0
- data/ext/rdwarf/libdwarf/pro_reloc.c +253 -0
- data/ext/rdwarf/libdwarf/pro_reloc.h +38 -0
- data/ext/rdwarf/libdwarf/pro_reloc_stream.c +256 -0
- data/ext/rdwarf/libdwarf/pro_reloc_stream.h +52 -0
- data/ext/rdwarf/libdwarf/pro_reloc_symbolic.c +245 -0
- data/ext/rdwarf/libdwarf/pro_reloc_symbolic.h +45 -0
- data/ext/rdwarf/libdwarf/pro_section.c +2233 -0
- data/ext/rdwarf/libdwarf/pro_section.h +100 -0
- data/ext/rdwarf/libdwarf/pro_types.c +274 -0
- data/ext/rdwarf/libdwarf/pro_types.h +34 -0
- data/ext/rdwarf/libdwarf/pro_util.h +38 -0
- data/ext/rdwarf/libdwarf/pro_vars.c +52 -0
- data/ext/rdwarf/libdwarf/pro_weaks.c +51 -0
- data/ext/rdwarf/rdwarf.c +765 -0
- data/ext/rdwarf/rdwarf.h +52 -0
- data/ext/rdwarf/rdwarf_names_gen.rb +109 -0
- data/lib/rdwarf.rb +181 -0
- data/lib/rdwarf/version.rb +3 -0
- data/rdwarf.gemspec +30 -0
- metadata +251 -0
@@ -0,0 +1,51 @@
|
|
1
|
+
/*
|
2
|
+
|
3
|
+
Copyright (C) 2000,2004 Silicon Graphics, Inc. All Rights Reserved.
|
4
|
+
Portions Copyright 2011 David Anderson. All Rights Reserved.
|
5
|
+
|
6
|
+
This program is free software; you can redistribute it and/or modify it
|
7
|
+
under the terms of version 2.1 of the GNU Lesser General Public License
|
8
|
+
as published by the Free Software Foundation.
|
9
|
+
|
10
|
+
This program is distributed in the hope that it would be useful, but
|
11
|
+
WITHOUT ANY WARRANTY; without even the implied warranty of
|
12
|
+
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
|
13
|
+
|
14
|
+
Further, this software is distributed without any warranty that it is
|
15
|
+
free of the rightful claim of any third person regarding infringement
|
16
|
+
or the like. Any license provided herein, whether implied or
|
17
|
+
otherwise, applies only to this software file. Patent licenses, if
|
18
|
+
any, provided herein do not apply to combinations of this program with
|
19
|
+
other software, or any other product whatsoever.
|
20
|
+
|
21
|
+
You should have received a copy of the GNU Lesser General Public
|
22
|
+
License along with this program; if not, write the Free Software
|
23
|
+
Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston MA 02110-1301,
|
24
|
+
USA.
|
25
|
+
|
26
|
+
*/
|
27
|
+
|
28
|
+
#include "config.h"
|
29
|
+
#include "libdwarfdefs.h"
|
30
|
+
#include <stdio.h>
|
31
|
+
#include <string.h>
|
32
|
+
#ifdef HAVE_ELFACCESS_H
|
33
|
+
#include <elfaccess.h>
|
34
|
+
#endif
|
35
|
+
#include "pro_incl.h"
|
36
|
+
#include "pro_section.h"
|
37
|
+
|
38
|
+
/*
|
39
|
+
This function adds another weak name to the
|
40
|
+
list of weak names for the given Dwarf_P_Debug.
|
41
|
+
It returns 0 on error, and 1 otherwise.
|
42
|
+
*/
|
43
|
+
Dwarf_Unsigned
|
44
|
+
dwarf_add_weakname(Dwarf_P_Debug dbg,
|
45
|
+
Dwarf_P_Die die,
|
46
|
+
char *weak_name, Dwarf_Error * error)
|
47
|
+
{
|
48
|
+
return
|
49
|
+
_dwarf_add_simple_name_entry(dbg, die, weak_name,
|
50
|
+
dwarf_snk_weakname, error);
|
51
|
+
}
|
data/ext/rdwarf/rdwarf.c
ADDED
@@ -0,0 +1,765 @@
|
|
1
|
+
/* -*- c-file-style: "ruby"; indent-tabs-mode: nil -*-
|
2
|
+
*
|
3
|
+
* rdwarf - a ruby module to read DWARF debugging information
|
4
|
+
* https://github.com/kubo/rdwarf
|
5
|
+
*
|
6
|
+
* Copyright (C) 2015 Kubo Takehiro <kubo@jiubao.org>
|
7
|
+
*
|
8
|
+
* Redistribution and use in source and binary forms, with or without
|
9
|
+
* modification, are permitted provided that the following conditions are met:
|
10
|
+
*
|
11
|
+
* 1. Redistributions of source code must retain the above copyright
|
12
|
+
* notice, this list of conditions and the following disclaimer.
|
13
|
+
*
|
14
|
+
* 2. Redistributions in binary form must reproduce the above
|
15
|
+
* copyright notice, this list of conditions and the following
|
16
|
+
* disclaimer in the documentation and/or other materials provided
|
17
|
+
* with the distribution.
|
18
|
+
*
|
19
|
+
* THIS SOFTWARE IS PROVIDED BY THE AUTHORS ''AS IS'' AND ANY EXPRESS OR
|
20
|
+
* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
21
|
+
* WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
22
|
+
* DISCLAIMED. IN NO EVENT SHALL <COPYRIGHT HOLDER> OR CONTRIBUTORS BE
|
23
|
+
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
24
|
+
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
25
|
+
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
|
26
|
+
* BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
|
27
|
+
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
|
28
|
+
* OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN
|
29
|
+
* IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
30
|
+
*
|
31
|
+
* The views and conclusions contained in the software and documentation
|
32
|
+
* are those of the authors and should not be interpreted as representing
|
33
|
+
* official policies, either expressed or implied, of the authors.
|
34
|
+
*/
|
35
|
+
#include "rdwarf.h"
|
36
|
+
#include <ruby/encoding.h>
|
37
|
+
#include <libelf.h>
|
38
|
+
#include <fcntl.h>
|
39
|
+
|
40
|
+
static VALUE cRDwarf; /* RDwarf */
|
41
|
+
static VALUE rd_eError; /* RDwarf:Error */
|
42
|
+
static VALUE rd_mDie; /* RDwarf::Die */
|
43
|
+
static VALUE rd_cDieBase; /* RDwarf::Die:Base */
|
44
|
+
static VALUE rd_mAttr; /* RDwarf::Attribute */
|
45
|
+
static VALUE rd_cAttrBase; /* RDwarf::Attribute::Base */
|
46
|
+
static VALUE rd_cLocList; /* RDwarf::LocationList */
|
47
|
+
static VALUE rd_cLocDesc; /* RDwarf::LocationDescriptor */
|
48
|
+
|
49
|
+
static VALUE sym_unsupported_type;
|
50
|
+
static ID id_at_top;
|
51
|
+
static ID id_at_cu;
|
52
|
+
|
53
|
+
typedef struct {
|
54
|
+
Elf *elf;
|
55
|
+
Dwarf_Debug dbg;
|
56
|
+
size_t refcnt;
|
57
|
+
VALUE off2die;
|
58
|
+
} rd_shared_data_t;
|
59
|
+
|
60
|
+
typedef struct {
|
61
|
+
rd_shared_data_t *shared_data;
|
62
|
+
VALUE compile_units;
|
63
|
+
} rdwarf_t;
|
64
|
+
|
65
|
+
typedef struct {
|
66
|
+
rd_shared_data_t *shared_data;
|
67
|
+
Dwarf_Die die;
|
68
|
+
VALUE children;
|
69
|
+
VALUE attributes;
|
70
|
+
VALUE srcfiles;
|
71
|
+
} rd_die_t;
|
72
|
+
|
73
|
+
typedef struct {
|
74
|
+
rd_shared_data_t *shared_data;
|
75
|
+
Dwarf_Attribute attr;
|
76
|
+
Dwarf_Half attr_type;
|
77
|
+
} rd_attr_t;
|
78
|
+
|
79
|
+
#define rd_shared_data_ref(sd) (++(sd)->refcnt, (sd))
|
80
|
+
#define rd_shared_data_unref(sd) ((--(sd)->refcnt) == 0 ? rd_shared_data_free(sd) : 0)
|
81
|
+
|
82
|
+
#define GetRDwarf(obj) (rdwarf_t*)rb_check_typeddata((obj), &rdwarf_data_type)
|
83
|
+
#define GetDie(obj) (rd_die_t*)rb_check_typeddata((obj), &rd_die_data_type)
|
84
|
+
#define GetAttr(obj) (rd_attr_t*)rb_check_typeddata((obj), &rd_attr_data_type)
|
85
|
+
|
86
|
+
static VALUE rd_die_new(rd_shared_data_t *sd, VALUE top, VALUE cu, Dwarf_Die die);
|
87
|
+
static VALUE rd_attr_new(rd_shared_data_t *sd, VALUE top, VALUE cu, Dwarf_Attribute attr);
|
88
|
+
static VALUE rd_attr_loc_list(VALUE self);
|
89
|
+
|
90
|
+
static rd_shared_data_t *rd_shared_data_alloc(Elf *elf, Dwarf_Debug dbg, VALUE obj)
|
91
|
+
{
|
92
|
+
rd_shared_data_t *sd = xmalloc(sizeof(rd_shared_data_t));
|
93
|
+
sd->elf = elf;
|
94
|
+
sd->dbg = dbg;
|
95
|
+
sd->refcnt = 1;
|
96
|
+
sd->off2die = rb_hash_new();
|
97
|
+
return sd;
|
98
|
+
}
|
99
|
+
|
100
|
+
static void rd_shared_data_mark(rd_shared_data_t *sd)
|
101
|
+
{
|
102
|
+
if (sd != NULL) {
|
103
|
+
rb_gc_mark(sd->off2die);
|
104
|
+
}
|
105
|
+
}
|
106
|
+
|
107
|
+
static void rd_shared_data_free(rd_shared_data_t *sd)
|
108
|
+
{
|
109
|
+
Dwarf_Error err;
|
110
|
+
|
111
|
+
dwarf_finish(sd->dbg, &err);
|
112
|
+
elf_end(sd->elf);
|
113
|
+
xfree(sd);
|
114
|
+
}
|
115
|
+
|
116
|
+
static void chkerr1(int ret, Dwarf_Error *err, VALUE obj)
|
117
|
+
{
|
118
|
+
VALUE exc = Qnil;
|
119
|
+
switch (ret) {
|
120
|
+
case DW_DLV_NO_ENTRY:
|
121
|
+
exc = rb_exc_new_cstr(rd_eError, "No Entry");
|
122
|
+
case DW_DLV_ERROR:
|
123
|
+
if (err != NULL) {
|
124
|
+
exc = rb_exc_new_cstr(rd_eError, dwarf_errmsg(*err));
|
125
|
+
} else {
|
126
|
+
exc = rb_exc_new_cstr(rd_eError, "Unknown Error");
|
127
|
+
}
|
128
|
+
}
|
129
|
+
if (!NIL_P(exc)) {
|
130
|
+
rb_iv_set(exc, "@obj", obj);
|
131
|
+
rb_exc_raise(exc);
|
132
|
+
}
|
133
|
+
}
|
134
|
+
|
135
|
+
static int chkerr2(int ret, Dwarf_Error *err)
|
136
|
+
{
|
137
|
+
if (ret == DW_DLV_ERROR) {
|
138
|
+
if (err != NULL) {
|
139
|
+
rb_raise(rd_eError, "%s", dwarf_errmsg(*err));
|
140
|
+
} else {
|
141
|
+
rb_raise(rd_eError, "Unknown Error");
|
142
|
+
}
|
143
|
+
}
|
144
|
+
return ret == DW_DLV_OK;
|
145
|
+
}
|
146
|
+
|
147
|
+
/*******************************************
|
148
|
+
* class definitins
|
149
|
+
*******************************************/
|
150
|
+
|
151
|
+
/* RDwarf */
|
152
|
+
|
153
|
+
static void rdwarf_dmark(void *ptr)
|
154
|
+
{
|
155
|
+
rdwarf_t *rd = (rdwarf_t *)ptr;
|
156
|
+
rd_shared_data_mark(rd->shared_data);
|
157
|
+
rb_gc_mark(rd->compile_units);
|
158
|
+
}
|
159
|
+
|
160
|
+
static void rdwarf_dfree(void *ptr)
|
161
|
+
{
|
162
|
+
rdwarf_t *rd = (rdwarf_t *)ptr;
|
163
|
+
|
164
|
+
if (rd->shared_data != NULL) {
|
165
|
+
rd_shared_data_unref(rd->shared_data);
|
166
|
+
}
|
167
|
+
xfree(rd);
|
168
|
+
}
|
169
|
+
|
170
|
+
static size_t rdwarf_dsize(const void *ptr)
|
171
|
+
{
|
172
|
+
return sizeof(rdwarf_t);
|
173
|
+
}
|
174
|
+
|
175
|
+
static const rb_data_type_t rdwarf_data_type = {
|
176
|
+
"RDwarf",
|
177
|
+
{rdwarf_dmark, rdwarf_dfree, rdwarf_dsize,},
|
178
|
+
#ifdef RUBY_TYPED_FREE_IMMEDIATELY
|
179
|
+
NULL, NULL, RUBY_TYPED_FREE_IMMEDIATELY
|
180
|
+
#endif
|
181
|
+
};
|
182
|
+
|
183
|
+
/* RDwarf::DIE:Base */
|
184
|
+
|
185
|
+
static void rd_die_dmark(void *ptr)
|
186
|
+
{
|
187
|
+
rd_die_t *die = (rd_die_t *)ptr;
|
188
|
+
rd_shared_data_mark(die->shared_data);
|
189
|
+
rb_gc_mark(die->children);
|
190
|
+
rb_gc_mark(die->attributes);
|
191
|
+
rb_gc_mark(die->srcfiles);
|
192
|
+
}
|
193
|
+
|
194
|
+
static void rd_die_dfree(void *ptr)
|
195
|
+
{
|
196
|
+
rd_die_t *die = (rd_die_t *)ptr;
|
197
|
+
if (die->shared_data != NULL) {
|
198
|
+
if (die->die != NULL) {
|
199
|
+
dwarf_dealloc(die->shared_data->dbg, die->die, DW_DLA_DIE);
|
200
|
+
}
|
201
|
+
rd_shared_data_unref(die->shared_data);
|
202
|
+
}
|
203
|
+
xfree(die);
|
204
|
+
}
|
205
|
+
|
206
|
+
static size_t rd_die_dsize(const void *ptr)
|
207
|
+
{
|
208
|
+
return sizeof(rd_die_t);
|
209
|
+
}
|
210
|
+
|
211
|
+
static const rb_data_type_t rd_die_data_type = {
|
212
|
+
"RDwarf::Die:Base",
|
213
|
+
{rd_die_dmark, rd_die_dfree, rd_die_dsize,},
|
214
|
+
#ifdef RUBY_TYPED_FREE_IMMEDIATELY
|
215
|
+
NULL, NULL, RUBY_TYPED_FREE_IMMEDIATELY
|
216
|
+
#endif
|
217
|
+
};
|
218
|
+
|
219
|
+
/* RDwarf::Attribute:Base */
|
220
|
+
|
221
|
+
static void rd_attr_dmark(void *ptr)
|
222
|
+
{
|
223
|
+
rd_attr_t *attr = (rd_attr_t *)ptr;
|
224
|
+
rd_shared_data_mark(attr->shared_data);
|
225
|
+
}
|
226
|
+
|
227
|
+
static void rd_attr_dfree(void *ptr)
|
228
|
+
{
|
229
|
+
rd_attr_t *attr = (rd_attr_t *)ptr;
|
230
|
+
if (attr->shared_data != NULL) {
|
231
|
+
if (attr->attr != NULL) {
|
232
|
+
dwarf_dealloc(attr->shared_data->dbg, attr->attr, DW_DLA_ATTR);
|
233
|
+
}
|
234
|
+
rd_shared_data_unref(attr->shared_data);
|
235
|
+
}
|
236
|
+
xfree(attr);
|
237
|
+
}
|
238
|
+
|
239
|
+
static size_t rd_attr_dsize(const void *ptr)
|
240
|
+
{
|
241
|
+
return sizeof(rd_attr_t);
|
242
|
+
}
|
243
|
+
|
244
|
+
static const rb_data_type_t rd_attr_data_type = {
|
245
|
+
"RDwarf::Attribute:Base",
|
246
|
+
{rd_attr_dmark, rd_attr_dfree, rd_attr_dsize,},
|
247
|
+
#ifdef RUBY_TYPED_FREE_IMMEDIATELY
|
248
|
+
NULL, NULL, RUBY_TYPED_FREE_IMMEDIATELY
|
249
|
+
#endif
|
250
|
+
};
|
251
|
+
|
252
|
+
/*******************************************
|
253
|
+
* method definitins
|
254
|
+
*******************************************/
|
255
|
+
|
256
|
+
/* RDwarf */
|
257
|
+
|
258
|
+
static VALUE rdwarf_s_alloc(VALUE klass)
|
259
|
+
{
|
260
|
+
VALUE obj;
|
261
|
+
rdwarf_t *rd;
|
262
|
+
|
263
|
+
obj = TypedData_Make_Struct(klass, rdwarf_t, &rdwarf_data_type, rd);
|
264
|
+
rd->compile_units = Qfalse;
|
265
|
+
return obj;
|
266
|
+
}
|
267
|
+
|
268
|
+
static VALUE rdwarf_initialize(VALUE self, VALUE filename)
|
269
|
+
{
|
270
|
+
rdwarf_t *rd = GetRDwarf(self);
|
271
|
+
Elf *elf;
|
272
|
+
Dwarf_Debug dbg;
|
273
|
+
Dwarf_Error err;
|
274
|
+
int fd;
|
275
|
+
int ret;
|
276
|
+
|
277
|
+
SafeStringValue(filename);
|
278
|
+
filename = rb_str_export_to_enc(filename, rb_filesystem_encoding());
|
279
|
+
|
280
|
+
fd = rb_cloexec_open(StringValueCStr(filename), O_RDONLY, 0);
|
281
|
+
if (fd < 0) {
|
282
|
+
rb_sys_fail("open");
|
283
|
+
}
|
284
|
+
elf = elf_begin(fd, ELF_C_READ, (Elf*)0);
|
285
|
+
ret = dwarf_elf_init(elf, DW_DLC_READ, NULL, NULL, &dbg, &err);
|
286
|
+
if (ret == DW_DLV_NO_ENTRY) {
|
287
|
+
elf_end(elf);
|
288
|
+
rb_raise(rd_eError, "%s", dwarf_errmsg(err));
|
289
|
+
}
|
290
|
+
rd->shared_data = rd_shared_data_alloc(elf, dbg, self);
|
291
|
+
return self;
|
292
|
+
}
|
293
|
+
|
294
|
+
static VALUE rdwarf_compile_units(VALUE self)
|
295
|
+
{
|
296
|
+
rdwarf_t *rd = GetRDwarf(self);
|
297
|
+
Dwarf_Unsigned cu_header_length = 0;
|
298
|
+
Dwarf_Unsigned abbrev_offset = 0;
|
299
|
+
Dwarf_Half version_stamp = 0;
|
300
|
+
Dwarf_Half address_size = 0;
|
301
|
+
Dwarf_Unsigned next_cu_offset = 0;
|
302
|
+
Dwarf_Error err;
|
303
|
+
Dwarf_Die die;
|
304
|
+
VALUE ary;
|
305
|
+
|
306
|
+
if (rd->compile_units != Qfalse) {
|
307
|
+
return rd->compile_units;
|
308
|
+
}
|
309
|
+
ary = rb_ary_new();
|
310
|
+
|
311
|
+
while (dwarf_next_cu_header(rd->shared_data->dbg, &cu_header_length, &version_stamp, &abbrev_offset,
|
312
|
+
&address_size, &next_cu_offset, &err) == DW_DLV_OK) {
|
313
|
+
if (!chkerr2(dwarf_siblingof(rd->shared_data->dbg, NULL, &die, &err), &err)) {
|
314
|
+
continue;
|
315
|
+
}
|
316
|
+
rb_ary_push(ary, rd_die_new(rd->shared_data, self, Qnil, die));
|
317
|
+
}
|
318
|
+
rd->compile_units = ary;
|
319
|
+
return ary;
|
320
|
+
}
|
321
|
+
|
322
|
+
static VALUE rdwarf_die_at(VALUE self, VALUE offset)
|
323
|
+
{
|
324
|
+
rdwarf_t *rd = GetRDwarf(self);
|
325
|
+
Dwarf_Die die;
|
326
|
+
Dwarf_Off cu_off;
|
327
|
+
Dwarf_Error err;
|
328
|
+
VALUE cu;
|
329
|
+
|
330
|
+
chkerr1(dwarf_offdie(rd->shared_data->dbg, NUM2LL(offset), &die, &err), &err, self);
|
331
|
+
chkerr1(dwarf_CU_dieoffset_given_die(die, &cu_off, &err), &err, self);
|
332
|
+
|
333
|
+
rdwarf_compile_units(self);
|
334
|
+
cu = rb_hash_aref(rd->shared_data->off2die, LL2NUM(cu_off));
|
335
|
+
if (NIL_P(cu)) {
|
336
|
+
rb_raise(rd_eError, "Cannot find CU");
|
337
|
+
}
|
338
|
+
return rd_die_new(rd->shared_data, self, cu, die);
|
339
|
+
}
|
340
|
+
|
341
|
+
/* RDwarf::DIE */
|
342
|
+
|
343
|
+
static VALUE rd_die_s_alloc(VALUE klass)
|
344
|
+
{
|
345
|
+
VALUE obj;
|
346
|
+
rd_die_t *die;
|
347
|
+
|
348
|
+
obj = TypedData_Make_Struct(klass, rd_die_t, &rd_die_data_type, die);
|
349
|
+
die->children = Qfalse;
|
350
|
+
die->attributes = Qfalse;
|
351
|
+
die->srcfiles = Qfalse;
|
352
|
+
return obj;
|
353
|
+
}
|
354
|
+
|
355
|
+
static VALUE rd_die_new(rd_shared_data_t *sd, VALUE top, VALUE cu, Dwarf_Die die)
|
356
|
+
{
|
357
|
+
rd_die_t *rd_die;
|
358
|
+
Dwarf_Off off;
|
359
|
+
Dwarf_Half tag;
|
360
|
+
Dwarf_Error err;
|
361
|
+
VALUE obj;
|
362
|
+
VALUE klass;
|
363
|
+
|
364
|
+
chkerr1(dwarf_dieoffset(die, &off, &err), &err, Qnil);
|
365
|
+
obj = rb_hash_aref(sd->off2die, LL2NUM(off));
|
366
|
+
if (!NIL_P(obj)) {
|
367
|
+
return obj;
|
368
|
+
}
|
369
|
+
|
370
|
+
chkerr1(dwarf_tag(die, &tag, &err), &err, Qnil);
|
371
|
+
klass = rb_hash_aref(rdwarf_tag2class, INT2FIX(tag));
|
372
|
+
if (NIL_P(klass)) {
|
373
|
+
rb_raise(rb_eRuntimeError, "unknown tag %d\n", tag);
|
374
|
+
}
|
375
|
+
obj = rd_die_s_alloc(klass);
|
376
|
+
rd_die = GetDie(obj);
|
377
|
+
rd_die->shared_data = rd_shared_data_ref(sd);
|
378
|
+
rd_die->die = die;
|
379
|
+
rb_ivar_set(obj, id_at_top, top);
|
380
|
+
rb_ivar_set(obj, id_at_cu, NIL_P(cu) ? obj : cu);
|
381
|
+
rb_hash_aset(sd->off2die, LL2NUM(off), obj);
|
382
|
+
return obj;
|
383
|
+
}
|
384
|
+
|
385
|
+
static VALUE rd_die_name(VALUE self)
|
386
|
+
{
|
387
|
+
rd_die_t *die = GetDie(self);
|
388
|
+
char *name;
|
389
|
+
Dwarf_Error err;
|
390
|
+
|
391
|
+
if (chkerr2(dwarf_diename(die->die, &name, &err), &err)) {
|
392
|
+
return rb_enc_str_new_cstr(name, rb_usascii_encoding());
|
393
|
+
} else {
|
394
|
+
return Qnil;
|
395
|
+
}
|
396
|
+
}
|
397
|
+
|
398
|
+
static VALUE rd_die_tag_name(VALUE self)
|
399
|
+
{
|
400
|
+
rd_die_t *die = GetDie(self);
|
401
|
+
Dwarf_Half tag = 0;
|
402
|
+
Dwarf_Error err;
|
403
|
+
|
404
|
+
chkerr1(dwarf_tag(die->die, &tag, &err), &err, self);
|
405
|
+
return rb_hash_aref(rdwarf_tag2name, INT2FIX(tag));
|
406
|
+
}
|
407
|
+
|
408
|
+
static VALUE rd_die_die_offset(VALUE self)
|
409
|
+
{
|
410
|
+
rd_die_t *die = GetDie(self);
|
411
|
+
Dwarf_Off off;
|
412
|
+
Dwarf_Error err;
|
413
|
+
|
414
|
+
chkerr1(dwarf_dieoffset(die->die, &off, &err), &err, self);
|
415
|
+
return LL2NUM(off);
|
416
|
+
}
|
417
|
+
|
418
|
+
static VALUE rd_die_die_cu_offset(VALUE self)
|
419
|
+
{
|
420
|
+
rd_die_t *die = GetDie(self);
|
421
|
+
Dwarf_Off off;
|
422
|
+
Dwarf_Error err;
|
423
|
+
|
424
|
+
chkerr1(dwarf_die_CU_offset(die->die, &off, &err), &err, self);
|
425
|
+
return LL2NUM(off);
|
426
|
+
}
|
427
|
+
|
428
|
+
static VALUE rd_die_children(VALUE self)
|
429
|
+
{
|
430
|
+
rd_die_t *die = GetDie(self);
|
431
|
+
VALUE top;
|
432
|
+
VALUE cu;
|
433
|
+
VALUE ary;
|
434
|
+
Dwarf_Die child;
|
435
|
+
Dwarf_Error err;
|
436
|
+
|
437
|
+
if (die->children != Qfalse) {
|
438
|
+
return die->children;
|
439
|
+
}
|
440
|
+
|
441
|
+
top = rb_ivar_get(self, id_at_top);
|
442
|
+
cu = rb_ivar_get(self, id_at_cu);
|
443
|
+
ary = rb_ary_new();
|
444
|
+
if (chkerr2(dwarf_child(die->die, &child, &err), &err)) {
|
445
|
+
do {
|
446
|
+
rb_ary_push(ary, rd_die_new(die->shared_data, top, cu, child));
|
447
|
+
} while (chkerr2(dwarf_siblingof(die->shared_data->dbg, child, &child, &err), &err));
|
448
|
+
}
|
449
|
+
die->children = ary;
|
450
|
+
return ary;
|
451
|
+
}
|
452
|
+
|
453
|
+
static VALUE rd_die_attributes(VALUE self)
|
454
|
+
{
|
455
|
+
rd_die_t *die = GetDie(self);
|
456
|
+
Dwarf_Attribute *list;
|
457
|
+
Dwarf_Signed count;
|
458
|
+
Dwarf_Error err;
|
459
|
+
Dwarf_Signed idx;
|
460
|
+
VALUE top;
|
461
|
+
VALUE cu;
|
462
|
+
VALUE ary;
|
463
|
+
|
464
|
+
if (die->attributes != Qfalse) {
|
465
|
+
return die->attributes;
|
466
|
+
}
|
467
|
+
|
468
|
+
top = rb_ivar_get(self, id_at_top);
|
469
|
+
cu = rb_ivar_get(self, id_at_cu);
|
470
|
+
if (chkerr2(dwarf_attrlist(die->die, &list, &count, &err), &err)) {
|
471
|
+
ary = rb_ary_new_capa(count);
|
472
|
+
for (idx = 0; idx < count; idx++) {
|
473
|
+
rb_ary_store(ary, idx, rd_attr_new(die->shared_data, top, cu, list[idx]));
|
474
|
+
}
|
475
|
+
} else {
|
476
|
+
ary = rb_ary_new();
|
477
|
+
}
|
478
|
+
die->attributes = ary;
|
479
|
+
return ary;
|
480
|
+
}
|
481
|
+
|
482
|
+
static VALUE rd_die_source_files(VALUE self)
|
483
|
+
{
|
484
|
+
rd_die_t *die = GetDie(self);
|
485
|
+
Dwarf_Signed cnt = 0;
|
486
|
+
char **srcfiles = 0;
|
487
|
+
Dwarf_Error err;
|
488
|
+
VALUE files = Qnil;
|
489
|
+
|
490
|
+
if (die->srcfiles != Qfalse) {
|
491
|
+
return die->srcfiles;
|
492
|
+
}
|
493
|
+
|
494
|
+
if (chkerr2(dwarf_srcfiles(die->die, &srcfiles, &cnt, &err), &err)) {
|
495
|
+
int i;
|
496
|
+
|
497
|
+
files = rb_ary_new_capa(cnt);
|
498
|
+
for (i = 0; i < cnt; i++) {
|
499
|
+
VALUE file = rb_str_new_cstr(srcfiles[i]);
|
500
|
+
OBJ_FREEZE(file);
|
501
|
+
rb_ary_store(files, i, file);
|
502
|
+
dwarf_dealloc(die->shared_data->dbg, srcfiles[i], DW_DLA_STRING);
|
503
|
+
}
|
504
|
+
dwarf_dealloc(die->shared_data->dbg, srcfiles, DW_DLA_LIST);
|
505
|
+
}
|
506
|
+
die->srcfiles = files;
|
507
|
+
return files;
|
508
|
+
}
|
509
|
+
|
510
|
+
static VALUE rd_die_inspect(VALUE self)
|
511
|
+
{
|
512
|
+
rd_die_t *die = GetDie(self);
|
513
|
+
char *name;
|
514
|
+
Dwarf_Off dieoff = 0;
|
515
|
+
Dwarf_Error err;
|
516
|
+
|
517
|
+
dwarf_dieoffset(die->die, &dieoff, &err);
|
518
|
+
|
519
|
+
switch (dwarf_diename(die->die, &name, &err)) {
|
520
|
+
case DW_DLV_OK:
|
521
|
+
return rb_sprintf("#<%s:(%llu) '%s'>", rb_obj_classname(self), dieoff, name);
|
522
|
+
default:
|
523
|
+
return rb_sprintf("#<%s:(%llu)>", rb_obj_classname(self), dieoff);
|
524
|
+
}
|
525
|
+
}
|
526
|
+
|
527
|
+
/* RDwarf::Attribute */
|
528
|
+
|
529
|
+
static VALUE rd_attr_s_alloc(VALUE klass)
|
530
|
+
{
|
531
|
+
VALUE obj;
|
532
|
+
rd_attr_t *attr;
|
533
|
+
|
534
|
+
obj = TypedData_Make_Struct(klass, rd_attr_t, &rd_attr_data_type, attr);
|
535
|
+
return obj;
|
536
|
+
}
|
537
|
+
|
538
|
+
static VALUE rd_attr_new(rd_shared_data_t *sd, VALUE top, VALUE cu, Dwarf_Attribute attr)
|
539
|
+
{
|
540
|
+
rd_attr_t *rd_attr;
|
541
|
+
Dwarf_Error err;
|
542
|
+
VALUE obj;
|
543
|
+
VALUE klass;
|
544
|
+
Dwarf_Half attr_type = 0;
|
545
|
+
|
546
|
+
chkerr1(dwarf_whatattr(attr, &attr_type, &err), &err, Qnil);
|
547
|
+
klass = rb_hash_aref(rdwarf_at2class, INT2FIX(attr_type));
|
548
|
+
if (NIL_P(klass)) {
|
549
|
+
rb_raise(rb_eRuntimeError, "unknown attribute %d\n", attr_type);
|
550
|
+
}
|
551
|
+
obj = rd_attr_s_alloc(klass);
|
552
|
+
rd_attr = GetAttr(obj);
|
553
|
+
rd_attr->shared_data = rd_shared_data_ref(sd);
|
554
|
+
rd_attr->attr = attr;
|
555
|
+
rd_attr->attr_type = attr_type;
|
556
|
+
rb_ivar_set(obj, id_at_top, top);
|
557
|
+
rb_ivar_set(obj, id_at_cu, cu);
|
558
|
+
return obj;
|
559
|
+
}
|
560
|
+
|
561
|
+
static VALUE rd_attr_type(VALUE self)
|
562
|
+
{
|
563
|
+
rd_attr_t *attr = GetAttr(self);
|
564
|
+
return rb_hash_aref(rdwarf_at2name, INT2FIX(attr->attr_type));
|
565
|
+
}
|
566
|
+
|
567
|
+
static VALUE rd_attr_form(VALUE self)
|
568
|
+
{
|
569
|
+
rd_attr_t *attr = GetAttr(self);
|
570
|
+
Dwarf_Half form_type;
|
571
|
+
Dwarf_Error err;
|
572
|
+
|
573
|
+
chkerr1(dwarf_whatform(attr->attr, &form_type, &err), &err, self);
|
574
|
+
return rb_hash_aref(rdwarf_form2name, INT2FIX(form_type));
|
575
|
+
}
|
576
|
+
|
577
|
+
static VALUE rd_attr_raw_value(VALUE self)
|
578
|
+
{
|
579
|
+
rd_attr_t *attr = GetAttr(self);
|
580
|
+
Dwarf_Half form;
|
581
|
+
Dwarf_Error err;
|
582
|
+
union {
|
583
|
+
Dwarf_Addr addr;
|
584
|
+
Dwarf_Off off;
|
585
|
+
Dwarf_Unsigned udata;
|
586
|
+
Dwarf_Signed sdata;
|
587
|
+
Dwarf_Bool bool;
|
588
|
+
char *str;
|
589
|
+
} val;
|
590
|
+
VALUE top;
|
591
|
+
|
592
|
+
chkerr1(dwarf_whatform(attr->attr, &form, &err), &err, self);
|
593
|
+
switch (form) {
|
594
|
+
case DW_FORM_addr:
|
595
|
+
chkerr1(dwarf_formaddr(attr->attr, &val.addr, &err), &err, self);
|
596
|
+
return ULL2NUM(val.addr);
|
597
|
+
case DW_FORM_ref1:
|
598
|
+
case DW_FORM_ref2:
|
599
|
+
case DW_FORM_ref4:
|
600
|
+
case DW_FORM_ref8:
|
601
|
+
case DW_FORM_ref_udata:
|
602
|
+
chkerr1(dwarf_global_formref(attr->attr, &val.off, &err), &err, self);
|
603
|
+
top = rb_ivar_get(self, id_at_top);
|
604
|
+
return rdwarf_die_at(top, LL2NUM(val.off));
|
605
|
+
case DW_FORM_data1:
|
606
|
+
case DW_FORM_data2:
|
607
|
+
case DW_FORM_data4:
|
608
|
+
case DW_FORM_data8:
|
609
|
+
case DW_FORM_udata:
|
610
|
+
chkerr1(dwarf_formudata(attr->attr, &val.udata, &err), &err, self);
|
611
|
+
return ULL2NUM(val.udata);
|
612
|
+
case DW_FORM_sdata:
|
613
|
+
chkerr1(dwarf_formsdata(attr->attr, &val.sdata, &err), &err, self);
|
614
|
+
return LL2NUM(val.sdata);
|
615
|
+
case DW_FORM_flag:
|
616
|
+
chkerr1(dwarf_formflag(attr->attr, &val.bool, &err), &err, self);
|
617
|
+
return val.bool ? Qtrue : Qfalse;
|
618
|
+
case DW_FORM_strp:
|
619
|
+
case DW_FORM_string:
|
620
|
+
chkerr1(dwarf_formstring(attr->attr, &val.str, &err), &err, self);
|
621
|
+
return rb_str_new_cstr(val.str);
|
622
|
+
}
|
623
|
+
return sym_unsupported_type;
|
624
|
+
}
|
625
|
+
|
626
|
+
static VALUE rd_attr_inspect(VALUE self)
|
627
|
+
{
|
628
|
+
rd_attr_t *attr = GetAttr(self);
|
629
|
+
Dwarf_Half form;
|
630
|
+
Dwarf_Error err;
|
631
|
+
const char *form_name = "?";
|
632
|
+
|
633
|
+
if (dwarf_whatform(attr->attr, &form, &err) == DW_DLV_OK) {
|
634
|
+
dwarf_get_FORM_name(form, &form_name);
|
635
|
+
}
|
636
|
+
return rb_sprintf("#<%s: %s>", rb_obj_classname(self), form_name);
|
637
|
+
}
|
638
|
+
|
639
|
+
static VALUE rd_attr_loc_list(VALUE self)
|
640
|
+
{
|
641
|
+
rd_attr_t *attr = GetAttr(self);
|
642
|
+
Dwarf_Error err;
|
643
|
+
Dwarf_Loc_Head_c loc_head;
|
644
|
+
Dwarf_Unsigned count;
|
645
|
+
VALUE lhead;
|
646
|
+
Dwarf_Unsigned idx;
|
647
|
+
|
648
|
+
chkerr1(dwarf_get_loclist_c(attr->attr, &loc_head, &count, &err), &err, self);
|
649
|
+
lhead = rb_ary_new_capa(count);
|
650
|
+
for (idx = 0; idx < count; idx++) {
|
651
|
+
Dwarf_Small lle;
|
652
|
+
Dwarf_Addr lowpc;
|
653
|
+
Dwarf_Addr hipc;
|
654
|
+
Dwarf_Unsigned loclist_count;
|
655
|
+
Dwarf_Locdesc_c locentry;
|
656
|
+
Dwarf_Small source;
|
657
|
+
Dwarf_Unsigned expression_offset;
|
658
|
+
Dwarf_Unsigned locdesc_offset;
|
659
|
+
ID id_lle;
|
660
|
+
ID id_lowpc;
|
661
|
+
ID id_hipc;
|
662
|
+
ID id_source;
|
663
|
+
ID id_expression_offset;
|
664
|
+
ID id_locdesc_offset;
|
665
|
+
VALUE llist;
|
666
|
+
int idx2;
|
667
|
+
|
668
|
+
CONST_ID(id_lle, "@lle");
|
669
|
+
CONST_ID(id_lowpc, "@lowpc");
|
670
|
+
CONST_ID(id_hipc, "@hipc");
|
671
|
+
CONST_ID(id_source, "@source");
|
672
|
+
CONST_ID(id_expression_offset, "@expression_offset");
|
673
|
+
CONST_ID(id_locdesc_offset, "@locdesc_offset");
|
674
|
+
|
675
|
+
chkerr1(dwarf_get_locdesc_entry_c(loc_head, idx, &lle, &lowpc, &hipc,
|
676
|
+
&loclist_count, &locentry, &source,
|
677
|
+
&expression_offset, &locdesc_offset, &err),
|
678
|
+
&err, self);
|
679
|
+
llist = rb_class_new_instance(0, NULL, rd_cLocList);
|
680
|
+
rb_ivar_set(llist, id_lle, rb_hash_aref(rdwarf_lle2name, INT2FIX(lle)));
|
681
|
+
rb_ivar_set(llist, id_lowpc, ULL2NUM(lowpc));
|
682
|
+
rb_ivar_set(llist, id_hipc, ULL2NUM(hipc));
|
683
|
+
rb_ivar_set(llist, id_source, INT2FIX(source));
|
684
|
+
rb_ivar_set(llist, id_expression_offset, ULL2NUM(expression_offset));
|
685
|
+
rb_ivar_set(llist, id_locdesc_offset, ULL2NUM(locdesc_offset));
|
686
|
+
for (idx2 = 0; idx2 < loclist_count; idx2++) {
|
687
|
+
Dwarf_Small atom;
|
688
|
+
Dwarf_Unsigned operand1;
|
689
|
+
Dwarf_Unsigned operand2;
|
690
|
+
Dwarf_Unsigned operand3;
|
691
|
+
Dwarf_Unsigned offset_for_branch;
|
692
|
+
ID id_atom;
|
693
|
+
ID id_operand1;
|
694
|
+
ID id_operand2;
|
695
|
+
ID id_operand3;
|
696
|
+
ID id_offset_for_branch;
|
697
|
+
VALUE ldesc;
|
698
|
+
|
699
|
+
CONST_ID(id_atom, "@atom");
|
700
|
+
CONST_ID(id_operand1, "@operand1");
|
701
|
+
CONST_ID(id_operand2, "@operand2");
|
702
|
+
CONST_ID(id_operand3, "@operand3");
|
703
|
+
CONST_ID(id_offset_for_branch, "@offset_for_branch");
|
704
|
+
|
705
|
+
chkerr1(dwarf_get_location_op_value_c(locentry, idx2, &atom, &operand1, &operand2, &operand3, &offset_for_branch, &err),
|
706
|
+
&err, self);
|
707
|
+
ldesc = rb_class_new_instance(0, NULL, rd_cLocDesc);
|
708
|
+
rb_ivar_set(ldesc, id_atom, rb_hash_aref(rdwarf_op2name, INT2FIX(atom)));
|
709
|
+
rb_ivar_set(ldesc, id_operand1, ULL2NUM(operand1));
|
710
|
+
rb_ivar_set(ldesc, id_operand2, ULL2NUM(operand2));
|
711
|
+
rb_ivar_set(ldesc, id_operand3, ULL2NUM(operand3));
|
712
|
+
rb_ivar_set(ldesc, id_offset_for_branch, ULL2NUM(offset_for_branch));
|
713
|
+
rb_ary_store(llist, idx2, ldesc);
|
714
|
+
}
|
715
|
+
rb_ary_store(lhead, idx, llist);
|
716
|
+
}
|
717
|
+
dwarf_loc_head_c_dealloc(loc_head);
|
718
|
+
return lhead;
|
719
|
+
}
|
720
|
+
|
721
|
+
void Init_rdwarf(void)
|
722
|
+
{
|
723
|
+
elf_version(EV_CURRENT);
|
724
|
+
|
725
|
+
sym_unsupported_type = ID2SYM(rb_intern("unsupported_type"));
|
726
|
+
id_at_top = rb_intern("@top");
|
727
|
+
id_at_cu = rb_intern("@cu");
|
728
|
+
|
729
|
+
cRDwarf = rb_define_class("RDwarf", rb_cObject);
|
730
|
+
rb_define_alloc_func(cRDwarf, rdwarf_s_alloc);
|
731
|
+
rb_define_method(cRDwarf, "initialize", rdwarf_initialize, 1);
|
732
|
+
rb_define_method(cRDwarf, "compile_units", rdwarf_compile_units, 0);
|
733
|
+
rb_define_method(cRDwarf, "die_at", rdwarf_die_at, 1);
|
734
|
+
|
735
|
+
rd_mDie = rb_define_module_under(cRDwarf, "DIE");
|
736
|
+
rd_cDieBase = rb_define_class_under(rd_mDie, "Base", rb_cObject);
|
737
|
+
rb_define_alloc_func(rd_cDieBase, rd_die_s_alloc);
|
738
|
+
rb_define_method(rd_cDieBase, "name", rd_die_name, 0);
|
739
|
+
rb_define_method(rd_cDieBase, "tag_name", rd_die_tag_name, 0);
|
740
|
+
rb_define_method(rd_cDieBase, "die_offset", rd_die_die_offset, 0);
|
741
|
+
rb_define_method(rd_cDieBase, "die_cu_offset", rd_die_die_cu_offset, 0);
|
742
|
+
rb_define_method(rd_cDieBase, "children", rd_die_children, 0);
|
743
|
+
rb_define_method(rd_cDieBase, "attributes", rd_die_attributes, 0);
|
744
|
+
rb_define_method(rd_cDieBase, "source_files", rd_die_source_files, 0);
|
745
|
+
rb_define_method(rd_cDieBase, "to_s", rd_die_inspect, 0);
|
746
|
+
rb_define_method(rd_cDieBase, "inspect", rd_die_inspect, 0);
|
747
|
+
|
748
|
+
rd_mAttr = rb_define_module_under(cRDwarf, "Attribute");
|
749
|
+
rd_cAttrBase = rb_define_class_under(rd_mAttr, "Base", rb_cObject);
|
750
|
+
rb_define_method(rd_cAttrBase, "type", rd_attr_type, 0);
|
751
|
+
rb_define_method(rd_cAttrBase, "form", rd_attr_form, 0);
|
752
|
+
rb_define_method(rd_cAttrBase, "raw_value", rd_attr_raw_value, 0);
|
753
|
+
rb_define_method(rd_cAttrBase, "value", rd_attr_raw_value, 0);
|
754
|
+
rb_define_method(rd_cAttrBase, "to_s", rd_attr_inspect, 0);
|
755
|
+
rb_define_method(rd_cAttrBase, "inspect", rd_attr_inspect, 0);
|
756
|
+
rb_define_private_method(rd_cAttrBase, "loc_list", rd_attr_loc_list, 0);
|
757
|
+
|
758
|
+
rd_cLocList = rb_define_class_under(cRDwarf, "LocationList", rb_cArray);
|
759
|
+
|
760
|
+
rd_cLocDesc = rb_define_class_under(cRDwarf, "LocationDescriptor", rb_cObject);
|
761
|
+
|
762
|
+
rd_eError = rb_define_class_under(cRDwarf, "Error", rb_eStandardError);
|
763
|
+
|
764
|
+
Init_rdwarf_names(cRDwarf, rd_mDie, rd_cDieBase, rd_mAttr, rd_cAttrBase);
|
765
|
+
}
|