1 // C++ interface to dwfl
2 // Copyright (C) 2005-2009 Red Hat Inc.
3 // Copyright (C) 2005-2007 Intel Corporation.
4 // Copyright (C) 2008 James.Bottomley@HansenPartnership.com
6 // This file is part of systemtap, and is free software. You can
7 // redistribute it and/or modify it under the terms of the GNU General
8 // Public License (GPL); either version 2, or (at your option) any
15 #include "dwarf_wrappers.h"
16 #include "elaborate.h"
18 #include "unordered.h"
28 #include <elfutils/libdwfl.h>
32 #if !_ELFUTILS_PREREQ(0,142)
33 // Always use newer name, old name is deprecated in 0.142.
34 #define elf_getshdrstrndx elf_getshstrndx
39 struct inline_instance_info
;
44 enum line_t
{ ABSOLUTE
, RELATIVE
, RANGE
, WILDCARD
};
45 enum info_status
{ info_unknown
, info_present
, info_absent
};
48 typedef unordered_map
<Dwarf
*, std::vector
<Dwarf_Die
>*> module_cu_cache_t
;
51 typedef unordered_map
<std::string
, Dwarf_Die
> cu_function_cache_t
;
53 // cu die -> (function -> die)
54 typedef unordered_map
<void*, cu_function_cache_t
*> mod_cu_function_cache_t
;
56 // inline function die -> instance die[]
57 typedef unordered_map
<void*, std::vector
<Dwarf_Die
>*> cu_inl_function_cache_t
;
59 typedef std::vector
<func_info
> func_info_map_t
;
60 typedef std::vector
<inline_instance_info
> inline_instance_map_t
;
63 /* XXX FIXME functions that dwflpp needs from tapsets.cxx */
64 func_info_map_t
*get_filtered_functions(dwarf_query
*q
);
65 inline_instance_map_t
*get_filtered_inlines(dwarf_query
*q
);
76 symbol_table
*sym_table
;
77 info_status dwarf_status
; // module has dwarf info?
78 info_status symtab_status
; // symbol table cached?
80 void get_symtab(dwarf_query
*q
);
81 void update_symtab(cu_function_cache_t
*funcs
);
83 module_info(const char *name
) :
89 dwarf_status(info_unknown
),
90 symtab_status(info_unknown
)
100 std::map
<std::string
, module_info
*> cache
;
101 bool paths_collected
;
102 bool dwarf_collected
;
104 module_cache() : paths_collected(false), dwarf_collected(false) {}
111 : decl_file(NULL
), decl_line(-1), addr(0), prologue_end(0), weak(false)
113 std::memset(&die
, 0, sizeof(die
));
116 char const * decl_file
;
121 Dwarf_Addr prologue_end
;
126 struct inline_instance_info
128 inline_instance_info()
129 : decl_file(NULL
), decl_line(-1)
131 std::memset(&die
, 0, sizeof(die
));
134 char const * decl_file
;
143 systemtap_session
& sess
;
145 // These are "current" values we focus on.
146 Dwfl_Module
* module
;
147 Dwarf_Addr module_bias
;
148 module_info
* mod_info
;
150 // These describe the current module's PC address range
151 Dwarf_Addr module_start
;
152 Dwarf_Addr module_end
;
156 std::string module_name
;
157 std::string function_name
;
159 dwflpp(systemtap_session
& session
, const std::string
& user_module
, bool kernel_p
);
160 dwflpp(systemtap_session
& session
, const std::vector
<std::string
>& user_modules
);
163 void get_module_dwarf(bool required
= false, bool report
= true);
165 void focus_on_module(Dwfl_Module
* m
, module_info
* mi
);
166 void focus_on_cu(Dwarf_Die
* c
);
167 void focus_on_function(Dwarf_Die
* f
);
169 std::string
cu_name(void);
171 Dwarf_Die
*query_cu_containing_address(Dwarf_Addr a
);
173 bool module_name_matches(const std::string
& pattern
);
174 static bool name_has_wildcard(const std::string
& pattern
);
175 bool module_name_final_match(const std::string
& pattern
);
177 bool function_name_matches_pattern(const std::string
& name
, const std::string
& pattern
);
178 bool function_name_matches(const std::string
& pattern
);
179 bool function_name_final_match(const std::string
& pattern
);
181 void iterate_over_modules(int (* callback
)(Dwfl_Module
*, void **,
182 const char *, Dwarf_Addr
,
186 void iterate_over_cus (int (*callback
)(Dwarf_Die
* die
, void * arg
),
189 bool func_is_inline();
191 void iterate_over_inline_instances (int (* callback
)(Dwarf_Die
* die
, void * arg
),
194 Dwarf_Die
*declaration_resolve(const char *name
);
196 mod_cu_function_cache_t cu_function_cache
;
198 int iterate_over_functions (int (* callback
)(Dwarf_Die
* func
, base_query
* q
),
199 base_query
* q
, const std::string
& function
,
200 bool has_statement_num
=false);
202 void iterate_over_srcfile_lines (char const * srcfile
,
204 bool need_single_match
,
205 enum line_t line_type
,
206 void (* callback
) (const dwarf_line_t
& line
,
208 const std::string
& func_pattern
,
211 void iterate_over_labels (Dwarf_Die
*begin_die
,
212 const std::string
& sym
,
213 const std::string
& symfunction
,
215 void (* callback
)(const std::string
&,
222 const std::string
& current_function
);
224 void collect_srcfiles_matching (std::string
const & pattern
,
225 std::set
<std::string
> & filtered_srcfiles
);
227 void resolve_prologue_endings (func_info_map_t
& funcs
);
229 bool function_entrypc (Dwarf_Addr
* addr
);
230 bool die_entrypc (Dwarf_Die
* die
, Dwarf_Addr
* addr
);
232 void function_die (Dwarf_Die
*d
);
233 void function_file (char const ** c
);
234 void function_line (int *linep
);
236 bool die_has_pc (Dwarf_Die
& die
, Dwarf_Addr pc
);
238 std::string
literal_stmt_for_local (Dwarf_Die
*scope_die
,
240 std::string
const & local
,
241 const target_symbol
*e
,
246 std::string
literal_stmt_for_return (Dwarf_Die
*scope_die
,
248 const target_symbol
*e
,
252 std::string
literal_stmt_for_pointer (Dwarf_Die
*type_die
,
253 const target_symbol
*e
,
257 bool blacklisted_p(const std::string
& funcname
,
258 const std::string
& filename
,
260 const std::string
& module
,
261 const std::string
& section
,
265 Dwarf_Addr
relocate_address(Dwarf_Addr addr
,
266 std::string
& reloc_section
,
267 std::string
& blacklist_section
);
269 Dwarf_Addr
literal_addr_to_sym_addr(Dwarf_Addr lit_addr
);
275 // These are "current" values we focus on.
276 Dwarf
* module_dwarf
;
277 Dwarf_Die
* function
;
279 void setup_kernel(const std::string
& module_name
, bool debuginfo_needed
= true);
280 void setup_user(const std::vector
<std::string
>& modules
, bool debuginfo_needed
= true);
282 module_cu_cache_t module_cu_cache
;
284 std::set
<void*> cu_inl_function_cache_done
; // CUs that are already cached
285 cu_inl_function_cache_t cu_inl_function_cache
;
286 void cache_inline_instances (Dwarf_Die
* die
);
288 /* The global alias cache is used to resolve any DIE found in a
289 * module that is stubbed out with DW_AT_declaration with a defining
290 * DIE found in a different module. The current assumption is that
291 * this only applies to structures and unions, which have a global
292 * namespace (it deliberately only traverses program scope), so this
293 * cache is indexed by name. If other declaration lookups were
294 * added to it, it would have to be indexed by name and tag
296 mod_cu_function_cache_t global_alias_cache
;
297 static int global_alias_caching_callback(Dwarf_Die
*die
, void *arg
);
298 int iterate_over_globals (int (* callback
)(Dwarf_Die
*, void *),
301 static int cu_function_caching_callback (Dwarf_Die
* func
, void *arg
);
303 bool has_single_line_record (dwarf_query
* q
, char const * srcfile
, int lineno
);
305 static void loc2c_error (void *, const char *fmt
, ...);
307 // This function generates code used for addressing computations of
309 void emit_address (struct obstack
*pool
, Dwarf_Addr address
);
310 static void loc2c_emit_address (void *arg
, struct obstack
*pool
,
313 void print_locals(Dwarf_Die
*die
, std::ostream
&o
);
314 void print_members(Dwarf_Die
*vardie
, std::ostream
&o
);
316 Dwarf_Attribute
*find_variable_and_frame_base (Dwarf_Die
*scope_die
,
318 std::string
const & local
,
319 const target_symbol
*e
,
321 Dwarf_Attribute
*fb_attr_mem
);
323 struct location
*translate_location(struct obstack
*pool
,
324 Dwarf_Attribute
*attr
,
326 Dwarf_Attribute
*fb_attr
,
327 struct location
**tail
,
328 const target_symbol
*e
);
330 bool find_struct_member(const target_symbol::component
& c
,
331 Dwarf_Die
*parentdie
,
332 Dwarf_Die
*memberdie
,
333 std::vector
<Dwarf_Attribute
>& locs
);
335 Dwarf_Die
*translate_components(struct obstack
*pool
,
336 struct location
**tail
,
338 const target_symbol
*e
,
341 Dwarf_Attribute
*attr_mem
);
343 Dwarf_Die
*resolve_unqualified_inner_typedie (Dwarf_Die
*typedie_mem
,
344 Dwarf_Attribute
*attr_mem
,
345 const target_symbol
*e
);
347 void translate_final_fetch_or_store (struct obstack
*pool
,
348 struct location
**tail
,
349 Dwarf_Addr module_bias
,
351 Dwarf_Attribute
*attr_mem
,
353 const target_symbol
*e
,
358 std::string
express_as_string (std::string prelude
,
359 std::string postlude
,
360 struct location
*head
);
362 regex_t blacklist_func
; // function/statement probes
363 regex_t blacklist_func_ret
; // only for .return probes
364 regex_t blacklist_file
; // file name
365 bool blacklist_enabled
;
366 void build_blacklist();
367 std::string
get_blacklist_section(Dwarf_Addr addr
);
369 Dwarf_Addr pc_cached_scopes
;
370 int num_cached_scopes
;
371 Dwarf_Die
*cached_scopes
;
372 int dwarf_getscopes_cached (Dwarf_Addr pc
, Dwarf_Die
**scopes
);
374 // Returns the call frame address operations for the given program counter.
375 Dwarf_Op
*get_cfa_ops (Dwarf_Addr pc
);
381 /* vim: set sw=2 ts=8 cino=>4,n-2,{2,^-2,t0,(0,u0,w1,M1 : */