]> sourceware.org Git - systemtap.git/blame - dwflpp.cxx
Zap dwarf_diename_integrate
[systemtap.git] / dwflpp.cxx
CommitLineData
440f755a
JS
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
5//
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
9// later version.
10
11#include "dwflpp.h"
12#include "config.h"
13#include "staptree.h"
14#include "elaborate.h"
15#include "tapsets.h"
16#include "task_finder.h"
17#include "translate.h"
18#include "session.h"
19#include "util.h"
20#include "buildrun.h"
21#include "dwarf_wrappers.h"
22#include "auto_free.h"
23#include "hash.h"
2ed04863 24#include "rpm_finder.h"
440f755a
JS
25
26#include <cstdlib>
27#include <algorithm>
28#include <deque>
29#include <iostream>
30#include <map>
440f755a
JS
31#include <set>
32#include <sstream>
33#include <stdexcept>
34#include <vector>
35#include <cstdarg>
36#include <cassert>
37#include <iomanip>
38#include <cerrno>
39
40extern "C" {
41#include <fcntl.h>
42#include <elfutils/libdwfl.h>
43#include <elfutils/libdw.h>
00b01a99
MW
44#ifdef HAVE_ELFUTILS_VERSION_H
45#include <elfutils/version.h>
46#endif
440f755a
JS
47#include <dwarf.h>
48#include <elf.h>
49#include <obstack.h>
50#include <regex.h>
51#include <glob.h>
52#include <fnmatch.h>
53#include <stdio.h>
54#include <sys/types.h>
55
56#include "loc2c.h"
57#define __STDC_FORMAT_MACROS
58#include <inttypes.h>
59}
60
61
62using namespace std;
63using namespace __gnu_cxx;
64
65
66static string TOK_KERNEL("kernel");
67
68
ae2552da 69dwflpp::dwflpp(systemtap_session & session, const string& name, bool kernel_p):
d0b4a5ff
JS
70 sess(session), module(NULL), module_bias(0), mod_info(NULL),
71 module_start(0), module_end(0), cu(NULL), dwfl(NULL),
c8ad0687
JS
72 module_dwarf(NULL), function(NULL), blacklist_enabled(false),
73 pc_cached_scopes(0), num_cached_scopes(0), cached_scopes(NULL)
440f755a 74{
ae2552da
FCE
75 if (kernel_p)
76 setup_kernel(name);
440f755a 77 else
0c16d512
JS
78 {
79 vector<string> modules;
80 modules.push_back(name);
81 setup_user(modules);
82 }
83}
84
85
86dwflpp::dwflpp(systemtap_session & session, const vector<string>& names):
87 sess(session), module(NULL), module_bias(0), mod_info(NULL),
88 module_start(0), module_end(0), cu(NULL), dwfl(NULL),
89 module_dwarf(NULL), function(NULL), blacklist_enabled(false),
90 pc_cached_scopes(0), num_cached_scopes(0), cached_scopes(NULL)
91{
92 setup_user(names);
440f755a
JS
93}
94
95
96dwflpp::~dwflpp()
97{
c8ad0687 98 free(cached_scopes);
440f755a
JS
99 if (dwfl)
100 dwfl_end(dwfl);
101}
102
103
440f755a
JS
104void
105dwflpp::get_module_dwarf(bool required, bool report)
106{
107 module_dwarf = dwfl_module_getdwarf(module, &module_bias);
108 mod_info->dwarf_status = (module_dwarf ? info_present : info_absent);
109 if (!module_dwarf && report)
110 {
111 string msg = "cannot find ";
112 if (module_name == "")
113 msg += "kernel";
114 else
115 msg += string("module ") + module_name;
116 msg += " debuginfo";
117
118 int i = dwfl_errno();
119 if (i)
120 msg += string(": ") + dwfl_errmsg (i);
121
2ed04863
WC
122 /* add module_name to list to find rpm */
123 find_debug_rpms(sess, module_name.c_str());
124
440f755a
JS
125 if (required)
126 throw semantic_error (msg);
83ca3872 127 else if (! sess.suppress_warnings)
440f755a
JS
128 cerr << "WARNING: " << msg << "\n";
129 }
130}
131
132
133void
134dwflpp::focus_on_module(Dwfl_Module * m, module_info * mi)
135{
136 module = m;
137 mod_info = mi;
138 if (m)
139 {
f517ee24
JS
140 module_name = dwfl_module_info(module, NULL, &module_start, &module_end,
141 NULL, NULL, NULL, NULL) ?: "module";
440f755a
JS
142 }
143 else
144 {
145 assert(mi && mi->name && mi->name == TOK_KERNEL);
146 module_name = mi->name;
147 module_start = 0;
148 module_end = 0;
149 module_bias = mi->bias;
150 }
151
152 // Reset existing pointers and names
153
154 module_dwarf = NULL;
155
156 cu_name.clear();
157 cu = NULL;
158
159 function_name.clear();
160 function = NULL;
161}
162
163
164void
165dwflpp::focus_on_cu(Dwarf_Die * c)
166{
167 assert(c);
168 assert(module);
169
170 cu = c;
f517ee24 171 cu_name = dwarf_diename(c) ?: "CU";
440f755a
JS
172
173 // Reset existing pointers and names
174 function_name.clear();
175 function = NULL;
c8ad0687
JS
176
177 free(cached_scopes);
178 cached_scopes = NULL;
440f755a
JS
179}
180
181
182void
183dwflpp::focus_on_function(Dwarf_Die * f)
184{
185 assert(f);
186 assert(module);
187 assert(cu);
188
189 function = f;
f517ee24 190 function_name = dwarf_diename(function) ?: "function";
440f755a
JS
191}
192
193
1f8592d1
MW
194/* Return the Dwarf_Die for the given address in the current module.
195 * The address should be in the module address address space (this
196 * function will take care of any dw bias).
197 */
1adf8ef1
JS
198Dwarf_Die *
199dwflpp::query_cu_containing_address(Dwarf_Addr a)
440f755a
JS
200{
201 Dwarf_Addr bias;
202 assert(dwfl);
b6fa229b 203 assert(module);
440f755a 204 get_module_dwarf();
b6fa229b 205
440f755a 206 Dwarf_Die* cudie = dwfl_module_addrdie(module, a, &bias);
440f755a 207 assert(bias == module_bias);
1adf8ef1 208 return cudie;
440f755a
JS
209}
210
211
440f755a 212bool
5f4c8c6e 213dwflpp::module_name_matches(const string& pattern)
440f755a
JS
214{
215 bool t = (fnmatch(pattern.c_str(), module_name.c_str(), 0) == 0);
216 if (t && sess.verbose>3)
217 clog << "pattern '" << pattern << "' "
218 << "matches "
219 << "module '" << module_name << "'" << "\n";
220 return t;
221}
222
223
224bool
665e1256 225dwflpp::name_has_wildcard (const string& pattern)
440f755a
JS
226{
227 return (pattern.find('*') != string::npos ||
228 pattern.find('?') != string::npos ||
229 pattern.find('[') != string::npos);
230}
231
232
233bool
5f4c8c6e 234dwflpp::module_name_final_match(const string& pattern)
440f755a
JS
235{
236 // Assume module_name_matches(). Can there be any more matches?
237 // Not unless the pattern is a wildcard, since module names are
238 // presumed unique.
239 return !name_has_wildcard(pattern);
240}
241
242
243bool
5f4c8c6e 244dwflpp::function_name_matches_pattern(const string& name, const string& pattern)
440f755a
JS
245{
246 bool t = (fnmatch(pattern.c_str(), name.c_str(), 0) == 0);
247 if (t && sess.verbose>3)
248 clog << "pattern '" << pattern << "' "
249 << "matches "
250 << "function '" << name << "'" << "\n";
251 return t;
252}
253
254
255bool
5f4c8c6e 256dwflpp::function_name_matches(const string& pattern)
440f755a
JS
257{
258 assert(function);
259 return function_name_matches_pattern(function_name, pattern);
260}
261
262
263bool
5f4c8c6e 264dwflpp::function_name_final_match(const string& pattern)
440f755a
JS
265{
266 return module_name_final_match (pattern);
267}
268
269
ae2552da
FCE
270static const char *offline_search_modname = NULL;
271static int offline_search_match_p = 0;
272
273static int dwfl_report_offline_predicate (const char* modname, const char* filename)
274{
275 if (pending_interrupts)
276 return -1;
277
ae2552da
FCE
278 assert (offline_search_modname);
279
fd6fef3d
FCE
280 // elfutils sends us NULL filenames sometimes if it can't find dwarf
281 if (filename == NULL)
282 return 0;
283
665e1256
FCE
284 if (dwflpp::name_has_wildcard (offline_search_modname)) {
285 int match_p = !fnmatch(offline_search_modname, modname, 0);
286 // In the wildcard case, we don't short-circuit (return -1) upon
287 // offline_search_match_p, analogously to dwflpp::module_name_final_match().
288
289 if (match_p)
ae2552da 290 offline_search_match_p ++;
665e1256
FCE
291
292 return match_p;
293 } else { /* non-wildcard mode */
294 if (offline_search_match_p)
295 return -1;
296
297 /* Reject mismatching module names */
298 if (strcmp(modname, offline_search_modname))
299 return 0;
300 else
301 {
302 offline_search_match_p ++;
303 return 1;
304 }
305 }
ae2552da
FCE
306}
307
308
440f755a 309void
ae2552da 310dwflpp::setup_kernel(const string& name, bool debuginfo_needed)
440f755a
JS
311{
312 // XXX: See also translate.cxx:emit_symbol_data
313
314 if (! sess.module_cache)
315 sess.module_cache = new module_cache ();
316
317 static const char *debuginfo_path_arr = "+:.debug:/usr/lib/debug:build";
318 static const char *debuginfo_env_arr = getenv("SYSTEMTAP_DEBUGINFO_PATH");
319 static const char *debuginfo_path = (debuginfo_env_arr ?: debuginfo_path_arr );
320
321 static const Dwfl_Callbacks kernel_callbacks =
322 {
323 dwfl_linux_kernel_find_elf,
324 dwfl_standard_find_debuginfo,
325 dwfl_offline_section_address,
326 (char **) & debuginfo_path
327 };
328
329 dwfl = dwfl_begin (&kernel_callbacks);
330 if (!dwfl)
331 throw semantic_error ("cannot open dwfl");
332 dwfl_report_begin (dwfl);
333
334 // We have a problem with -r REVISION vs -r BUILDDIR here. If
335 // we're running against a fedora/rhel style kernel-debuginfo
336 // tree, s.kernel_build_tree is not the place where the unstripped
337 // vmlinux will be installed. Rather, it's over yonder at
338 // /usr/lib/debug/lib/modules/$REVISION/. It seems that there is
339 // no way to set the dwfl_callback.debuginfo_path and always
340 // passs the plain kernel_release here. So instead we have to
341 // hard-code this magic here.
342 string elfutils_kernel_path;
343 if (sess.kernel_build_tree == string("/lib/modules/" + sess.kernel_release + "/build"))
344 elfutils_kernel_path = sess.kernel_release;
345 else
346 elfutils_kernel_path = sess.kernel_build_tree;
347
ae2552da
FCE
348 offline_search_modname = name.c_str();
349 offline_search_match_p = 0;
440f755a
JS
350 int rc = dwfl_linux_kernel_report_offline (dwfl,
351 elfutils_kernel_path.c_str(),
352 &dwfl_report_offline_predicate);
ae2552da
FCE
353 offline_search_modname = NULL;
354
355 (void) rc; /* Ignore since the predicate probably returned -1 at some point,
356 And libdwfl interprets that as "whole query failed" rather than
357 "found it already, stop looking". */
440f755a 358
ae2552da
FCE
359 /* But we still need to check whether the module was itself found. One could
360 do an iterate_modules() search over the resulting dwfl and count hits. Or
361 one could rely on the match_p flag being set just before. */
362 if (! offline_search_match_p)
363 {
364 if (debuginfo_needed) {
365 // Suggest a likely kernel dir to find debuginfo rpm for
366 string dir = string("/lib/modules/" + sess.kernel_release );
367 find_debug_rpms(sess, dir.c_str());
368 }
369 throw semantic_error (string("missing ") + sess.architecture +
370 string(" kernel/module debuginfo under '") +
371 sess.kernel_build_tree + string("'"));
209dd533 372 }
440f755a 373
440f755a
JS
374 // NB: the result of an _offline call is the assignment of
375 // virtualized addresses to relocatable objects such as
376 // modules. These have to be converted to real addresses at
377 // run time. See the dwarf_derived_probe ctor and its caller.
378
379 dwfl_assert ("dwfl_report_end", dwfl_report_end(dwfl, NULL, NULL));
27646582
JS
380
381 build_blacklist();
440f755a
JS
382}
383
384
385void
0c16d512 386dwflpp::setup_user(const vector<string>& modules, bool debuginfo_needed)
440f755a
JS
387{
388 if (! sess.module_cache)
389 sess.module_cache = new module_cache ();
390
391 static const char *debuginfo_path_arr = "+:.debug:/usr/lib/debug:build";
392 static const char *debuginfo_env_arr = getenv("SYSTEMTAP_DEBUGINFO_PATH");
393 // NB: kernel_build_tree doesn't enter into this, as it's for
394 // kernel-side modules only.
395 static const char *debuginfo_path = (debuginfo_env_arr ?: debuginfo_path_arr);
396
397 static const Dwfl_Callbacks user_callbacks =
398 {
399 NULL, /* dwfl_linux_kernel_find_elf, */
400 dwfl_standard_find_debuginfo,
401 dwfl_offline_section_address,
402 (char **) & debuginfo_path
403 };
404
405 dwfl = dwfl_begin (&user_callbacks);
406 if (!dwfl)
407 throw semantic_error ("cannot open dwfl");
408 dwfl_report_begin (dwfl);
409
0c16d512
JS
410 vector<string>::const_iterator it;
411 for (it = modules.begin(); it != modules.end(); ++it)
412 {
413 // XXX: should support buildid-based naming
414
415 const string& module_name = *it;
416 Dwfl_Module *mod = dwfl_report_offline (dwfl,
417 module_name.c_str(),
418 module_name.c_str(),
419 -1);
0c16d512
JS
420
421 if (debuginfo_needed)
422 dwfl_assert (string("missing process ") +
423 module_name +
424 string(" ") +
425 sess.architecture +
426 string(" debuginfo"),
427 mod);
428 }
440f755a
JS
429
430 // NB: the result of an _offline call is the assignment of
431 // virtualized addresses to relocatable objects such as
432 // modules. These have to be converted to real addresses at
433 // run time. See the dwarf_derived_probe ctor and its caller.
434
435 dwfl_assert ("dwfl_report_end", dwfl_report_end(dwfl, NULL, NULL));
436}
437
438
439void
440dwflpp::iterate_over_modules(int (* callback)(Dwfl_Module *, void **,
441 const char *, Dwarf_Addr,
442 void *),
443 base_query *data)
444{
0e14e079
JS
445 dwfl_getmodules (dwfl, callback, data, 0);
446
440f755a
JS
447 // Don't complain if we exited dwfl_getmodules early.
448 // This could be a $target variable error that will be
449 // reported soon anyway.
450 // dwfl_assert("dwfl_getmodules", off == 0);
451
452 // PR6864 XXX: For dwarfless case (if .../vmlinux is missing), then the
453 // "kernel" module is not reported in the loop above. However, we
454 // may be able to make do with symbol table data.
455}
456
457
440f755a
JS
458void
459dwflpp::iterate_over_cus (int (*callback)(Dwarf_Die * die, void * arg),
460 void * data)
461{
462 get_module_dwarf(false);
463 Dwarf *dw = module_dwarf;
464 if (!dw) return;
465
466 vector<Dwarf_Die>* v = module_cu_cache[dw];
467 if (v == 0)
468 {
469 v = new vector<Dwarf_Die>;
470 module_cu_cache[dw] = v;
471
472 Dwarf_Off off = 0;
473 size_t cuhl;
474 Dwarf_Off noff;
475 while (dwarf_nextcu (dw, off, &noff, &cuhl, NULL, NULL, NULL) == 0)
476 {
477 if (pending_interrupts) return;
478 Dwarf_Die die_mem;
479 Dwarf_Die *die;
480 die = dwarf_offdie (dw, off + cuhl, &die_mem);
481 v->push_back (*die); /* copy */
482 off = noff;
483 }
484 }
485
486 for (unsigned i = 0; i < v->size(); i++)
487 {
488 if (pending_interrupts) return;
489 Dwarf_Die die = v->at(i);
490 int rc = (*callback)(& die, data);
491 if (rc != DWARF_CB_OK) break;
492 }
493}
494
495
496bool
497dwflpp::func_is_inline()
498{
499 assert (function);
500 return dwarf_func_inline (function) != 0;
501}
502
503
504int
505dwflpp::cu_inl_function_caching_callback (Dwarf_Die* func, void *arg)
506{
507 vector<Dwarf_Die>* v = static_cast<vector<Dwarf_Die>*>(arg);
508 v->push_back (* func);
509 return DWARF_CB_OK;
510}
511
512
513void
514dwflpp::iterate_over_inline_instances (int (* callback)(Dwarf_Die * die, void * arg),
515 void * data)
516{
517 assert (function);
518 assert (func_is_inline ());
519
520 string key = module_name + ":" + cu_name + ":" + function_name;
521 vector<Dwarf_Die>* v = cu_inl_function_cache[key];
522 if (v == 0)
523 {
524 v = new vector<Dwarf_Die>;
525 cu_inl_function_cache[key] = v;
526 dwarf_func_inline_instances (function, cu_inl_function_caching_callback, v);
527 }
528
529 for (unsigned i=0; i<v->size(); i++)
530 {
531 if (pending_interrupts) return;
532 Dwarf_Die die = v->at(i);
533 int rc = (*callback)(& die, data);
534 if (rc != DWARF_CB_OK) break;
535 }
536}
537
538
539int
540dwflpp::global_alias_caching_callback(Dwarf_Die *die, void *arg)
541{
542 cu_function_cache_t *cache = static_cast<cu_function_cache_t*>(arg);
543 const char *name = dwarf_diename(die);
544
545 if (!name)
546 return DWARF_CB_OK;
547
548 string structure_name = name;
549
550 if (!dwarf_hasattr(die, DW_AT_declaration) &&
551 cache->find(structure_name) == cache->end())
552 (*cache)[structure_name] = *die;
553
554 return DWARF_CB_OK;
555}
556
557
558Dwarf_Die *
559dwflpp::declaration_resolve(const char *name)
560{
561 if (!name)
562 return NULL;
563
564 string key = module_name + ":" + cu_name;
565 cu_function_cache_t *v = global_alias_cache[key];
566 if (v == 0) // need to build the cache, just once per encountered module/cu
567 {
568 v = new cu_function_cache_t;
569 global_alias_cache[key] = v;
570 iterate_over_globals(global_alias_caching_callback, v);
571 if (sess.verbose > 4)
572 clog << "global alias cache " << key << " size " << v->size() << endl;
573 }
574
575 // XXX: it may be desirable to search other modules' declarations
576 // too, in case a module/shared-library processes a
577 // forward-declared pointer type only, where the actual definition
578 // may only be in vmlinux or the application.
579
580 // XXX: it is probably desirable to search other CU's declarations
581 // in the same module.
582
583 if (v->find(name) == v->end())
584 return NULL;
585
586 return & ((*v)[name]);
587}
588
589
590int
591dwflpp::cu_function_caching_callback (Dwarf_Die* func, void *arg)
592{
593 cu_function_cache_t* v = static_cast<cu_function_cache_t*>(arg);
594 const char *name = dwarf_diename(func);
595 if (!name)
596 return DWARF_CB_OK;
597
598 string function_name = name;
599 (*v)[function_name] = * func;
600 return DWARF_CB_OK;
601}
602
603
604int
605dwflpp::iterate_over_functions (int (* callback)(Dwarf_Die * func, base_query * q),
606 base_query * q, const string& function,
607 bool has_statement_num)
608{
609 int rc = DWARF_CB_OK;
610 assert (module);
611 assert (cu);
612
613 string key = module_name + ":" + cu_name;
614 cu_function_cache_t *v = cu_function_cache[key];
615 if (v == 0)
616 {
617 v = new cu_function_cache_t;
618 cu_function_cache[key] = v;
619 dwarf_getfuncs (cu, cu_function_caching_callback, v, 0);
620 if (sess.verbose > 4)
621 clog << "function cache " << key << " size " << v->size() << endl;
1c6b77e5 622 mod_info->update_symtab(v);
440f755a
JS
623 }
624
5f4c8c6e
JS
625 cu_function_cache_t::iterator it = v->find(function);
626 if (it != v->end())
440f755a 627 {
1c6b77e5 628 Dwarf_Die& die = it->second;
440f755a 629 if (sess.verbose > 4)
5f4c8c6e 630 clog << "function cache " << key << " hit " << function << endl;
440f755a
JS
631 return (*callback)(& die, q);
632 }
5f4c8c6e 633 else if (name_has_wildcard (function))
440f755a 634 {
1c6b77e5
JS
635 // track addresses we've already seen
636 set<Dwarf_Addr> alias_dupes;
637
5f4c8c6e 638 for (it = v->begin(); it != v->end(); it++)
440f755a 639 {
1c6b77e5
JS
640 if (pending_interrupts) return DWARF_CB_ABORT;
641 const string& func_name = it->first;
642 Dwarf_Die& die = it->second;
5f4c8c6e 643 if (function_name_matches_pattern (func_name, function))
440f755a
JS
644 {
645 if (sess.verbose > 4)
646 clog << "function cache " << key << " match " << func_name << " vs "
5f4c8c6e 647 << function << endl;
440f755a 648
1c6b77e5
JS
649 // make sure that this function address hasn't
650 // already been matched under an aliased name
651 Dwarf_Addr addr;
652 if (dwarf_entrypc(&die, &addr) == 0 &&
653 !alias_dupes.insert(addr).second)
654 continue;
655
440f755a
JS
656 rc = (*callback)(& die, q);
657 if (rc != DWARF_CB_OK) break;
658 }
659 }
660 }
661 else if (has_statement_num) // searching all for kernel.statement
662 {
663 for (cu_function_cache_t::iterator it = v->begin(); it != v->end(); it++)
664 {
665 Dwarf_Die die = it->second;
666 rc = (*callback)(& die, q);
667 if (rc != DWARF_CB_OK) break;
668 }
669 }
670 else // not a wildcard and no match in this CU
671 {
672 // do nothing
673 }
674 return rc;
675}
676
677
678/* This basically only goes one level down from the compile unit so it
679 * only picks up top level stuff (i.e. nothing in a lower scope) */
680int
681dwflpp::iterate_over_globals (int (* callback)(Dwarf_Die *, void *),
682 void * data)
683{
684 int rc = DWARF_CB_OK;
685 Dwarf_Die die;
686
687 assert (module);
688 assert (cu);
689 assert (dwarf_tag(cu) == DW_TAG_compile_unit);
690
691 if (dwarf_child(cu, &die) != 0)
692 return rc;
693
694 do
695 /* We're only currently looking for named types,
696 * although other types of declarations exist */
697 switch (dwarf_tag(&die))
698 {
699 case DW_TAG_base_type:
700 case DW_TAG_enumeration_type:
701 case DW_TAG_structure_type:
702 case DW_TAG_typedef:
703 case DW_TAG_union_type:
704 rc = (*callback)(&die, data);
705 break;
706 }
707 while (rc == DWARF_CB_OK && dwarf_siblingof(&die, &die) == 0);
708
709 return rc;
710}
711
712
713// This little test routine represents an unfortunate breakdown in
714// abstraction between dwflpp (putatively, a layer right on top of
715// elfutils), and dwarf_query (interpreting a systemtap probe point).
716// It arises because we sometimes try to fix up slightly-off
717// .statement() probes (something we find out in fairly low-level).
718//
719// An alternative would be to put some more intelligence into query_cu(),
720// and have it print additional suggestions after finding that
721// q->dw.iterate_over_srcfile_lines resulted in no new finished_results.
722
723bool
724dwflpp::has_single_line_record (dwarf_query * q, char const * srcfile, int lineno)
725{
726 if (lineno < 0)
727 return false;
728
729 Dwarf_Line **srcsp = NULL;
730 size_t nsrcs = 0;
731
732 dwarf_assert ("dwarf_getsrc_file",
733 dwarf_getsrc_file (module_dwarf,
734 srcfile, lineno, 0,
735 &srcsp, &nsrcs));
736
737 if (nsrcs != 1)
738 {
739 if (sess.verbose>4)
740 clog << "alternative line " << lineno << " rejected: nsrcs=" << nsrcs << endl;
741 return false;
742 }
743
744 // We also try to filter out lines that leave the selected
745 // functions (if any).
746
747 dwarf_line_t line(srcsp[0]);
748 Dwarf_Addr addr = line.addr();
749
750 func_info_map_t *filtered_functions = get_filtered_functions(q);
751 for (func_info_map_t::iterator i = filtered_functions->begin();
752 i != filtered_functions->end(); ++i)
753 {
754 if (die_has_pc (i->die, addr))
755 {
756 if (sess.verbose>4)
757 clog << "alternative line " << lineno << " accepted: fn=" << i->name << endl;
758 return true;
759 }
760 }
761
762 inline_instance_map_t *filtered_inlines = get_filtered_inlines(q);
763 for (inline_instance_map_t::iterator i = filtered_inlines->begin();
764 i != filtered_inlines->end(); ++i)
765 {
766 if (die_has_pc (i->die, addr))
767 {
768 if (sess.verbose>4)
769 clog << "alternative line " << lineno << " accepted: ifn=" << i->name << endl;
770 return true;
771 }
772 }
773
774 if (sess.verbose>4)
775 clog << "alternative line " << lineno << " rejected: leaves selected fns" << endl;
776 return false;
777}
778
779
780void
781dwflpp::iterate_over_srcfile_lines (char const * srcfile,
782 int lines[2],
783 bool need_single_match,
784 enum line_t line_type,
785 void (* callback) (const dwarf_line_t& line,
786 void * arg),
9b988eff 787 const std::string& func_pattern,
440f755a
JS
788 void *data)
789{
790 Dwarf_Line **srcsp = NULL;
791 size_t nsrcs = 0;
792 dwarf_query * q = static_cast<dwarf_query *>(data);
793 int lineno = lines[0];
794 auto_free_ref<Dwarf_Line**> free_srcsp(srcsp);
795
796 get_module_dwarf();
797
798 if (line_type == RELATIVE)
799 {
800 Dwarf_Addr addr;
801 Dwarf_Line *line;
802 int line_number;
803
804 dwarf_assert ("dwarf_entrypc", dwarf_entrypc (this->function, &addr));
805 line = dwarf_getsrc_die (this->cu, addr);
806 dwarf_assert ("dwarf_getsrc_die", line == NULL);
807 dwarf_assert ("dwarf_lineno", dwarf_lineno (line, &line_number));
808 lineno += line_number;
809 }
810 else if (line_type == WILDCARD)
811 function_line (&lineno);
1123a74a
WH
812 else if (line_type == RANGE) { /* correct lineno */
813 int start_lineno;
814
9b988eff
WH
815 if (name_has_wildcard(func_pattern)) /* PR10294: wider range like statement("*@foo.c") */
816 start_lineno = lineno;
817 else
818 function_line (&start_lineno);
1123a74a
WH
819 lineno = lineno < start_lineno ? start_lineno : lineno;
820 if (lineno > lines[1]) { /* invalid line range */
821 stringstream advice;
822 advice << "Invalid line range (" << lines[0] << "-" << lines[1] << ")";
823 if (start_lineno > lines[1])
824 advice << ", the end line number " << lines[1] << " < " << start_lineno;
825 throw semantic_error (advice.str());
826 }
827 }
828
440f755a
JS
829
830 for (int l = lineno; ; l = l + 1)
831 {
832 set<int> lines_probed;
833 pair<set<int>::iterator,bool> line_probed;
1123a74a
WH
834 int ret = 0;
835
836 ret = dwarf_getsrc_file (module_dwarf, srcfile, l, 0,
837 &srcsp, &nsrcs);
838 if (line_type != WILDCARD && line_type != RANGE)
839 dwarf_assert ("dwarf_getsrc_file", ret);
840
440f755a
JS
841 if (line_type == WILDCARD || line_type == RANGE)
842 {
843 Dwarf_Addr line_addr;
1123a74a
WH
844
845 if (ret != 0) /* tolerate invalid line number */
846 break;
847
440f755a 848 dwarf_lineno (srcsp [0], &lineno);
1123a74a
WH
849 /* Maybe lineno will exceed the input end */
850 if (line_type == RANGE && lineno > lines[1])
851 break;
440f755a
JS
852 line_probed = lines_probed.insert(lineno);
853 if (lineno != l || line_probed.second == false || nsrcs > 1)
854 continue;
855 dwarf_lineaddr (srcsp [0], &line_addr);
9b988eff 856 if (!function_name_matches(func_pattern) && dwarf_haspc (function, line_addr) != 1)
440f755a
JS
857 break;
858 }
859
860 // NB: Formerly, we used to filter, because:
861
862 // dwarf_getsrc_file gets one *near hits* for line numbers, not
863 // exact matches. For example, an existing file but a nonexistent
864 // line number will be rounded up to the next definition in that
865 // file. This may be similar to the GDB breakpoint algorithm, but
866 // we don't want to be so fuzzy in systemtap land. So we filter.
867
868 // But we now see the error of our ways, and skip this filtering.
869
870 // XXX: the code also fails to match e.g. inline function
871 // definitions when the srcfile is a header file rather than the
872 // CU name.
873
874 size_t remaining_nsrcs = nsrcs;
875
876 if (need_single_match && remaining_nsrcs > 1)
877 {
878 // We wanted a single line record (a unique address for the
879 // line) and we got a bunch of line records. We're going to
880 // skip this probe (throw an exception) but before we throw
881 // we're going to look around a bit to see if there's a low or
882 // high line number nearby which *doesn't* have this problem,
883 // so we can give the user some advice.
884
885 int lo_try = -1;
886 int hi_try = -1;
887 for (size_t i = 1; i < 6; ++i)
888 {
889 if (lo_try == -1 && has_single_line_record(q, srcfile, lineno - i))
890 lo_try = lineno - i;
891
892 if (hi_try == -1 && has_single_line_record(q, srcfile, lineno + i))
893 hi_try = lineno + i;
894 }
895
896 stringstream advice;
897 advice << "multiple addresses for " << srcfile << ":" << lineno;
898 if (lo_try > 0 || hi_try > 0)
899 {
900 advice << " (try ";
901 if (lo_try > 0)
902 advice << srcfile << ":" << lo_try;
903 if (lo_try > 0 && hi_try > 0)
904 advice << " or ";
905 if (hi_try > 0)
906 advice << srcfile << ":" << hi_try;
907 advice << ")";
908 }
909 throw semantic_error (advice.str());
910 }
911
912 for (size_t i = 0; i < nsrcs; ++i)
913 {
914 if (pending_interrupts) return;
915 if (srcsp [i]) // skip over mismatched lines
916 callback (dwarf_line_t(srcsp[i]), data);
917 }
918
919 if (line_type == ABSOLUTE || line_type == RELATIVE)
920 break;
921 else if (line_type == RANGE && l == lines[1])
922 break;
923 }
924}
925
926
927void
928dwflpp::iterate_over_labels (Dwarf_Die *begin_die,
929 const char *sym,
930 const char *symfunction,
931 void *data,
932 void (* callback)(const string &,
933 const char *,
934 int,
935 Dwarf_Die *,
936 Dwarf_Addr,
937 dwarf_query *))
938{
939 dwarf_query * q __attribute__ ((unused)) = static_cast<dwarf_query *>(data) ;
940
941 get_module_dwarf();
942
943 Dwarf_Die die;
944 int res = dwarf_child (begin_die, &die);
945 if (res != 0)
946 return; // die without children, bail out.
947
948 static string function_name = dwarf_diename (begin_die);
949 do
950 {
951 Dwarf_Attribute attr_mem;
952 Dwarf_Attribute *attr = dwarf_attr (&die, DW_AT_name, &attr_mem);
953 int tag = dwarf_tag(&die);
954 const char *name = dwarf_formstring (attr);
955 if (name == 0)
956 continue;
957 switch (tag)
958 {
959 case DW_TAG_label:
960 break;
961 case DW_TAG_subprogram:
962 if (!dwarf_hasattr(&die, DW_AT_declaration))
963 function_name = name;
964 else
965 continue;
966 default:
967 if (dwarf_haschildren (&die))
968 iterate_over_labels (&die, sym, symfunction, q, callback);
969 continue;
970 }
971
972 if (strcmp(function_name.c_str(), symfunction) == 0
973 || (name_has_wildcard(symfunction)
974 && function_name_matches (symfunction)))
975 {
976 }
977 else
978 continue;
979 if (strcmp(name, sym) == 0
980 || (name_has_wildcard(sym)
981 && function_name_matches_pattern (name, sym)))
982 {
983 const char *file = dwarf_decl_file (&die);
984 // Get the line number for this label
985 Dwarf_Attribute attr;
986 dwarf_attr (&die,DW_AT_decl_line, &attr);
987 Dwarf_Sword dline;
988 dwarf_formsdata (&attr, &dline);
989 Dwarf_Addr stmt_addr;
990 if (dwarf_lowpc (&die, &stmt_addr) != 0)
991 {
992 // There is no lowpc so figure out the address
993 // Get the real die for this cu
994 Dwarf_Die cudie;
995 dwarf_diecu (cu, &cudie, NULL, NULL);
996 size_t nlines = 0;
997 // Get the line for this label
998 Dwarf_Line **aline;
999 dwarf_getsrc_file (module_dwarf, file, (int)dline, 0, &aline, &nlines);
1000 // Get the address
1001 for (size_t i = 0; i < nlines; i++)
1002 {
1003 dwarf_lineaddr (*aline, &stmt_addr);
1004 if ((dwarf_haspc (&die, stmt_addr)))
1005 break;
1006 }
1007 }
1008
1009 Dwarf_Die *scopes;
1010 int nscopes = 0;
1011 nscopes = dwarf_getscopes_die (&die, &scopes);
1012 if (nscopes > 1)
1013 {
1014 callback(function_name.c_str(), file,
1015 (int)dline, &scopes[1], stmt_addr, q);
1016 add_label_name(q, name);
1017 }
1018 }
1019 }
1020 while (dwarf_siblingof (&die, &die) == 0);
1021}
1022
1023
1024void
1025dwflpp::collect_srcfiles_matching (string const & pattern,
1026 set<char const *> & filtered_srcfiles)
1027{
1028 assert (module);
1029 assert (cu);
1030
1031 size_t nfiles;
1032 Dwarf_Files *srcfiles;
1033
1034 // PR 5049: implicit * in front of given path pattern.
1035 // NB: fnmatch() is used without FNM_PATHNAME.
1036 string prefixed_pattern = string("*/") + pattern;
1037
1038 dwarf_assert ("dwarf_getsrcfiles",
1039 dwarf_getsrcfiles (cu, &srcfiles, &nfiles));
1040 {
1041 for (size_t i = 0; i < nfiles; ++i)
1042 {
1043 char const * fname = dwarf_filesrc (srcfiles, i, NULL, NULL);
1044 if (fnmatch (pattern.c_str(), fname, 0) == 0 ||
1045 fnmatch (prefixed_pattern.c_str(), fname, 0) == 0)
1046 {
1047 filtered_srcfiles.insert (fname);
1048 if (sess.verbose>2)
1049 clog << "selected source file '" << fname << "'\n";
1050 }
1051 }
1052 }
1053}
1054
1055
1056void
1057dwflpp::resolve_prologue_endings (func_info_map_t & funcs)
1058{
1059 // This heuristic attempts to pick the first address that has a
1060 // source line distinct from the function declaration's. In a
1061 // perfect world, this would be the first statement *past* the
1062 // prologue.
1063
1064 assert(module);
1065 assert(cu);
1066
1067 size_t nlines = 0;
1068 Dwarf_Lines *lines = NULL;
1069
1070 /* trouble cases:
1071 malloc do_symlink in init/initramfs.c tail-recursive/tiny then no-prologue
1072 sys_get?id in kernel/timer.c no-prologue
1073 sys_exit_group tail-recursive
1074 {do_,}sys_open extra-long-prologue (gcc 3.4)
1075 cpu_to_logical_apicid NULL-decl_file
1076 */
1077
1078 // Fetch all srcline records, sorted by address.
1079 dwarf_assert ("dwarf_getsrclines",
1080 dwarf_getsrclines(cu, &lines, &nlines));
1081 // XXX: free lines[] later, but how?
1082
1083 for(func_info_map_t::iterator it = funcs.begin(); it != funcs.end(); it++)
1084 {
1085#if 0 /* someday */
1086 Dwarf_Addr* bkpts = 0;
1087 int n = dwarf_entry_breakpoints (& it->die, & bkpts);
1088 // ...
1089 free (bkpts);
1090#endif
1091
1092 Dwarf_Addr entrypc = it->entrypc;
1093 Dwarf_Addr highpc; // NB: highpc is exclusive: [entrypc,highpc)
1094 dwfl_assert ("dwarf_highpc", dwarf_highpc (& it->die,
1095 & highpc));
1096
1097 if (it->decl_file == 0) it->decl_file = "";
1098
1099 unsigned entrypc_srcline_idx = 0;
1100 dwarf_line_t entrypc_srcline;
1101 // open-code binary search for exact match
1102 {
1103 unsigned l = 0, h = nlines;
1104 while (l < h)
1105 {
1106 entrypc_srcline_idx = (l + h) / 2;
1107 const dwarf_line_t lr(dwarf_onesrcline(lines,
1108 entrypc_srcline_idx));
1109 Dwarf_Addr addr = lr.addr();
1110 if (addr == entrypc) { entrypc_srcline = lr; break; }
1111 else if (l + 1 == h) { break; } // ran off bottom of tree
1112 else if (addr < entrypc) { l = entrypc_srcline_idx; }
1113 else { h = entrypc_srcline_idx; }
1114 }
1115 }
1116 if (!entrypc_srcline)
1117 {
1118 if (sess.verbose > 2)
1119 clog << "missing entrypc dwarf line record for function '"
1120 << it->name << "'\n";
1121 // This is probably an inlined function. We'll end up using
1122 // its lowpc as a probe address.
1123 continue;
1124 }
1125
1126 if (sess.verbose>2)
1127 clog << "prologue searching function '" << it->name << "'"
1128 << " 0x" << hex << entrypc << "-0x" << highpc << dec
1129 << "@" << it->decl_file << ":" << it->decl_line
1130 << "\n";
1131
1132 // Now we go searching for the first line record that has a
1133 // file/line different from the one in the declaration.
1134 // Normally, this will be the next one. BUT:
1135 //
1136 // We may have to skip a few because some old compilers plop
1137 // in dummy line records for longer prologues. If we go too
1138 // far (addr >= highpc), we take the previous one. Or, it may
1139 // be the first one, if the function had no prologue, and thus
1140 // the entrypc maps to a statement in the body rather than the
1141 // declaration.
1142
1143 unsigned postprologue_srcline_idx = entrypc_srcline_idx;
1144 bool ranoff_end = false;
1145 while (postprologue_srcline_idx < nlines)
1146 {
1147 dwarf_line_t lr(dwarf_onesrcline(lines, postprologue_srcline_idx));
1148 Dwarf_Addr postprologue_addr = lr.addr();
1149 const char* postprologue_file = lr.linesrc();
1150 int postprologue_lineno = lr.lineno();
1151
1152 if (sess.verbose>2)
1153 clog << "checking line record 0x" << hex << postprologue_addr << dec
1154 << "@" << postprologue_file << ":" << postprologue_lineno << "\n";
1155
1156 if (postprologue_addr >= highpc)
1157 {
1158 ranoff_end = true;
1159 postprologue_srcline_idx --;
1160 continue;
1161 }
1162 if (ranoff_end ||
1163 (strcmp (postprologue_file, it->decl_file) || // We have a winner!
1164 (postprologue_lineno != it->decl_line)))
1165 {
1166 it->prologue_end = postprologue_addr;
1167
1168 if (sess.verbose>2)
1169 {
1170 clog << "prologue found function '" << it->name << "'";
1171 // Add a little classification datum
1172 if (postprologue_srcline_idx == entrypc_srcline_idx) clog << " (naked)";
1173 if (ranoff_end) clog << " (tail-call?)";
1174 clog << " = 0x" << hex << postprologue_addr << dec << "\n";
1175 }
1176
1177 break;
1178 }
1179
1180 // Let's try the next srcline.
1181 postprologue_srcline_idx ++;
1182 } // loop over srclines
1183
1184 // if (strlen(it->decl_file) == 0) it->decl_file = NULL;
1185
1186 } // loop over functions
1187
1188 // XXX: how to free lines?
1189}
1190
1191
1192bool
1193dwflpp::function_entrypc (Dwarf_Addr * addr)
1194{
1195 assert (function);
1196 return (dwarf_entrypc (function, addr) == 0);
1197 // XXX: see also _lowpc ?
1198}
1199
1200
1201bool
1202dwflpp::die_entrypc (Dwarf_Die * die, Dwarf_Addr * addr)
1203{
1204 int rc = 0;
1205 string lookup_method;
1206
1207 * addr = 0;
1208
1209 lookup_method = "dwarf_entrypc";
1210 rc = dwarf_entrypc (die, addr);
1211
1212 if (rc)
1213 {
1214 lookup_method = "dwarf_lowpc";
1215 rc = dwarf_lowpc (die, addr);
1216 }
1217
1218 if (rc)
1219 {
1220 lookup_method = "dwarf_ranges";
1221
1222 Dwarf_Addr base;
1223 Dwarf_Addr begin;
1224 Dwarf_Addr end;
1225 ptrdiff_t offset = dwarf_ranges (die, 0, &base, &begin, &end);
1226 if (offset < 0) rc = -1;
1227 else if (offset > 0)
1228 {
1229 * addr = begin;
1230 rc = 0;
1231
1232 // Now we need to check that there are no more ranges
1233 // associated with this function, which could conceivably
1234 // happen if a function is inlined, then pieces of it are
1235 // split amongst different conditional branches. It's not
1236 // obvious which of them to favour. As a heuristic, we
1237 // pick the beginning of the first range, and ignore the
1238 // others (but with a warning).
1239
1240 unsigned extra = 0;
1241 while ((offset = dwarf_ranges (die, offset, &base, &begin, &end)) > 0)
1242 extra ++;
1243 if (extra)
1244 lookup_method += ", ignored " + lex_cast<string>(extra) + " more";
1245 }
1246 }
1247
1248 if (sess.verbose > 2)
1249 clog << "entry-pc lookup (" << lookup_method << ") = 0x" << hex << *addr << dec
1250 << " (rc " << rc << ")"
1251 << endl;
1252 return (rc == 0);
1253}
1254
1255
1256void
1257dwflpp::function_die (Dwarf_Die *d)
1258{
1259 assert (function);
1260 *d = *function;
1261}
1262
1263
1264void
1265dwflpp::function_file (char const ** c)
1266{
1267 assert (function);
1268 assert (c);
1269 *c = dwarf_decl_file (function);
1270}
1271
1272
1273void
1274dwflpp::function_line (int *linep)
1275{
1276 assert (function);
1277 dwarf_decl_line (function, linep);
1278}
1279
1280
1281bool
1282dwflpp::die_has_pc (Dwarf_Die & die, Dwarf_Addr pc)
1283{
1284 int res = dwarf_haspc (&die, pc);
1285 // dwarf_ranges will return -1 if a function die has no DW_AT_ranges
1286 // if (res == -1)
1287 // dwarf_assert ("dwarf_haspc", res);
1288 return res == 1;
1289}
1290
1291
1292void
1293dwflpp::loc2c_error (void *, const char *fmt, ...)
1294{
1295 const char *msg = "?";
1296 char *tmp = NULL;
1297 int rc;
1298 va_list ap;
1299 va_start (ap, fmt);
1300 rc = vasprintf (& tmp, fmt, ap);
1301 if (rc < 0)
1302 msg = "?";
1303 else
1304 msg = tmp;
1305 va_end (ap);
1306 throw semantic_error (msg);
1307}
1308
1309
1310// This function generates code used for addressing computations of
1311// target variables.
1312void
1313dwflpp::emit_address (struct obstack *pool, Dwarf_Addr address)
1314{
1315 #if 0
1316 // The easy but incorrect way is to just print a hard-wired
1317 // constant.
1318 obstack_printf (pool, "%#" PRIx64 "UL", address);
1319 #endif
1320
1321 // Turn this address into a section-relative offset if it should be one.
1322 // We emit a comment approximating the variable+offset expression that
1323 // relocatable module probing code will need to have.
1324 Dwfl_Module *mod = dwfl_addrmodule (dwfl, address);
1325 dwfl_assert ("dwfl_addrmodule", mod);
1326 const char *modname = dwfl_module_info (mod, NULL, NULL, NULL,
1327 NULL, NULL, NULL, NULL);
1328 int n = dwfl_module_relocations (mod);
1329 dwfl_assert ("dwfl_module_relocations", n >= 0);
1330 Dwarf_Addr reloc_address = address;
1331 int i = dwfl_module_relocate_address (mod, &reloc_address);
1332 dwfl_assert ("dwfl_module_relocate_address", i >= 0);
1333 dwfl_assert ("dwfl_module_info", modname);
1334 const char *secname = dwfl_module_relocation_info (mod, i, NULL);
1335
1336 if (sess.verbose > 2)
1337 {
1338 clog << "emit dwarf addr 0x" << hex << address << dec
1339 << " => module " << modname
1340 << " section " << (secname ?: "null")
1341 << " relocaddr 0x" << hex << reloc_address << dec
1342 << endl;
1343 }
1344
1345 if (n > 0 && !(n == 1 && secname == NULL))
1346 {
1347 dwfl_assert ("dwfl_module_relocation_info", secname);
1348 if (n > 1 || secname[0] != '\0')
1349 {
1350 // This gives us the module name, and section name within the
1351 // module, for a kernel module (or other ET_REL module object).
1352 obstack_printf (pool, "({ static unsigned long addr = 0; ");
1353 obstack_printf (pool, "if (addr==0) addr = _stp_module_relocate (\"%s\",\"%s\",%#" PRIx64 "); ",
1354 modname, secname, reloc_address);
1355 obstack_printf (pool, "addr; })");
1356 }
1357 else if (n == 1 && module_name == TOK_KERNEL && secname[0] == '\0')
1358 {
1359 // elfutils' way of telling us that this is a relocatable kernel address, which we
1360 // need to treat the same way here as dwarf_query::add_probe_point does: _stext.
1361 address -= sess.sym_stext;
1362 secname = "_stext";
1363 obstack_printf (pool, "({ static unsigned long addr = 0; ");
1364 obstack_printf (pool, "if (addr==0) addr = _stp_module_relocate (\"%s\",\"%s\",%#" PRIx64 "); ",
1365 modname, secname, address); // PR10000 NB: not reloc_address
1366 obstack_printf (pool, "addr; })");
1367 }
1368 else
1369 {
1370 throw semantic_error ("cannot relocate user-space dso (?) address");
1371#if 0
1372 // This would happen for a Dwfl_Module that's a user-level DSO.
1373 obstack_printf (pool, " /* %s+%#" PRIx64 " */",
1374 modname, address);
1375#endif
1376 }
1377 }
1378 else
1379 obstack_printf (pool, "%#" PRIx64 "UL", address); // assume as constant
1380}
1381
1382
1383void
1384dwflpp::loc2c_emit_address (void *arg, struct obstack *pool,
1385 Dwarf_Addr address)
1386{
c94efd63 1387 static_cast<dwflpp *>(arg)->emit_address (pool, address);
440f755a
JS
1388}
1389
1390
1391void
1392dwflpp::print_locals(Dwarf_Die *die, ostream &o)
1393{
1394 // Try to get the first child of die.
1395 Dwarf_Die child;
1396 if (dwarf_child (die, &child) == 0)
1397 {
1398 do
1399 {
1400 const char *name;
1401 // Output each sibling's name (that is a variable or
1402 // parameter) to 'o'.
1403 switch (dwarf_tag (&child))
1404 {
1405 case DW_TAG_variable:
1406 case DW_TAG_formal_parameter:
1407 name = dwarf_diename (&child);
1408 if (name)
1409 o << " " << name;
1410 break;
1411 default:
1412 break;
1413 }
1414 }
1415 while (dwarf_siblingof (&child, &child) == 0);
1416 }
1417}
1418
1419
1420Dwarf_Attribute *
1421dwflpp::find_variable_and_frame_base (Dwarf_Die *scope_die,
1422 Dwarf_Addr pc,
1423 string const & local,
1424 const target_symbol *e,
1425 Dwarf_Die *vardie,
1426 Dwarf_Attribute *fb_attr_mem)
1427{
1428 Dwarf_Die *scopes;
1429 int nscopes = 0;
1430 Dwarf_Attribute *fb_attr = NULL;
1431
1432 assert (cu);
1433
c8ad0687 1434 nscopes = dwarf_getscopes_cached (pc, &scopes);
440f755a
JS
1435 int sidx;
1436 // if pc and scope_die are disjoint then we need dwarf_getscopes_die
1437 for (sidx = 0; sidx < nscopes; sidx++)
1438 if (scopes[sidx].addr == scope_die->addr)
1439 break;
1440 if (sidx == nscopes)
1441 nscopes = dwarf_getscopes_die (scope_die, &scopes);
1442
1443 if (nscopes <= 0)
1444 {
1445 throw semantic_error ("unable to find any scopes containing "
1446 + lex_cast_hex<string>(pc)
1447 + ((scope_die == NULL) ? ""
1448 : (string (" in ")
1449 + (dwarf_diename(scope_die) ?: "<unknown>")
1450 + "(" + (dwarf_diename(cu) ?: "<unknown>")
1451 + ")"))
1452 + " while searching for local '" + local + "'",
1453 e->tok);
1454 }
1455
1456 int declaring_scope = dwarf_getscopevar (scopes, nscopes,
1457 local.c_str(),
1458 0, NULL, 0, 0,
1459 vardie);
1460 if (declaring_scope < 0)
1461 {
1462 stringstream alternatives;
1463 print_locals (scopes, alternatives);
1464 throw semantic_error ("unable to find local '" + local + "'"
1465 + " near pc " + lex_cast_hex<string>(pc)
1466 + ((scope_die == NULL) ? ""
1467 : (string (" in ")
1468 + (dwarf_diename(scope_die) ?: "<unknown>")
1469 + "(" + (dwarf_diename(cu) ?: "<unknown>")
1470 + ")"))
1471 + (alternatives.str() == "" ? "" : (" (alternatives:" + alternatives.str () + ")")),
1472 e->tok);
1473 }
1474
1475 for (int inner = 0; inner < nscopes; ++inner)
1476 {
1477 switch (dwarf_tag (&scopes[inner]))
1478 {
1479 default:
1480 continue;
1481 case DW_TAG_subprogram:
1482 case DW_TAG_entry_point:
1483 case DW_TAG_inlined_subroutine: /* XXX */
1484 if (inner >= declaring_scope)
1485 fb_attr = dwarf_attr_integrate (&scopes[inner],
1486 DW_AT_frame_base,
1487 fb_attr_mem);
1488 break;
1489 }
1490 }
1491 return fb_attr;
1492}
1493
1494
1495struct location *
1496dwflpp::translate_location(struct obstack *pool,
1497 Dwarf_Attribute *attr, Dwarf_Addr pc,
1498 Dwarf_Attribute *fb_attr,
1499 struct location **tail,
1500 const target_symbol *e)
1501{
619d9aaf
MW
1502
1503 /* DW_AT_data_member_location, can be either constant offsets
1504 (struct member fields), or full blown location expressions. */
1505 if (dwarf_whatattr (attr) == DW_AT_data_member_location)
1506 {
1507 unsigned int form = dwarf_whatform (attr);
1508 if (form == DW_FORM_data1 || form == DW_FORM_data2
1509 || form == DW_FORM_sdata || form == DW_FORM_udata)
1510 {
1511 Dwarf_Sword off;
1512 if (dwarf_formsdata (attr, &off) != 0)
1513 throw semantic_error (string ("dwarf_formsdata failed, ")
1514 + string (dwarf_errmsg (-1)), e->tok);
1515 c_translate_add_offset (pool, 1, NULL, off, tail);
1516 return *tail;
1517 }
1518 }
1519
440f755a
JS
1520 Dwarf_Op *expr;
1521 size_t len;
1522
1523 /* PR9768: formerly, we added pc+module_bias here. However, that bias value
1524 is not present in the pc value by the time we get it, so adding it would
1525 result in false negatives of variable reachibility. In other instances
1526 further below, the c_translate_FOO functions, the module_bias value used
1527 to be passed in, but instead should now be zero for the same reason. */
1528
1529 switch (dwarf_getlocation_addr (attr, pc /*+ module_bias*/, &expr, &len, 1))
1530 {
1531 case 1: /* Should always happen. */
1532 if (len > 0)
1533 break;
1534 /* Fall through. */
1535
1536 case 0: /* Shouldn't happen. */
1537 throw semantic_error ("not accessible at this address", e->tok);
1538
1539 default: /* Shouldn't happen. */
1540 case -1:
619d9aaf 1541 throw semantic_error (string ("dwarf_getlocation_addr failed, ") +
440f755a
JS
1542 string (dwarf_errmsg (-1)),
1543 e->tok);
1544 }
1545
88eaee9f
MW
1546 // get_cfa_ops works on the dw address space, pc is relative to current
1547 // module, so add do need to add module_bias.
1548 Dwarf_Op *cfa_ops = get_cfa_ops (pc + module_bias);
440f755a
JS
1549 return c_translate_location (pool, &loc2c_error, this,
1550 &loc2c_emit_address,
1551 1, 0 /* PR9768 */,
00b01a99 1552 pc, expr, len, tail, fb_attr, cfa_ops);
440f755a
JS
1553}
1554
1555
1556void
1557dwflpp::print_members(Dwarf_Die *vardie, ostream &o)
1558{
1559 const int typetag = dwarf_tag (vardie);
1560
1561 if (typetag != DW_TAG_structure_type && typetag != DW_TAG_union_type)
1562 {
1563 o << " Error: "
23d106b9 1564 << (dwarf_diename (vardie) ?: "<anonymous>")
440f755a
JS
1565 << " isn't a struct/union";
1566 return;
1567 }
1568
1569 // Try to get the first child of vardie.
1570 Dwarf_Die die_mem;
1571 Dwarf_Die *die = &die_mem;
1572 switch (dwarf_child (vardie, die))
1573 {
1574 case 1: // No children.
1575 o << ((typetag == DW_TAG_union_type) ? " union " : " struct ")
23d106b9 1576 << (dwarf_diename (die) ?: "<anonymous>")
440f755a
JS
1577 << " is empty";
1578 break;
1579
1580 case -1: // Error.
1581 default: // Shouldn't happen.
1582 o << ((typetag == DW_TAG_union_type) ? " union " : " struct ")
23d106b9 1583 << (dwarf_diename (die) ?: "<anonymous>")
440f755a
JS
1584 << ": " << dwarf_errmsg (-1);
1585 break;
1586
1587 case 0: // Success.
1588 break;
1589 }
1590
1591 // Output each sibling's name to 'o'.
1592 while (dwarf_tag (die) == DW_TAG_member)
1593 {
23d106b9 1594 const char *member = dwarf_diename (die) ;
440f755a
JS
1595
1596 if ( member != NULL )
1597 o << " " << member;
1598 else
1599 {
1600 Dwarf_Die temp_die = *die;
1601 Dwarf_Attribute temp_attr ;
1602
1603 if (!dwarf_attr_integrate (&temp_die, DW_AT_type, &temp_attr))
1604 {
1605 clog << "\n Error in obtaining type attribute for "
1606 << (dwarf_diename(&temp_die)?:"<anonymous>");
1607 return;
1608 }
1609
1610 if (!dwarf_formref_die (&temp_attr, &temp_die))
1611 {
1612 clog << "\n Error in decoding type attribute for "
1613 << (dwarf_diename(&temp_die)?:"<anonymous>");
1614 return;
1615 }
1616
1617 print_members(&temp_die,o);
1618 }
1619
1620 if (dwarf_siblingof (die, &die_mem) != 0)
1621 break;
1622 }
1623}
1624
1625
1626bool
c67847a0 1627dwflpp::find_struct_member(const target_symbol::component& c,
440f755a 1628 Dwarf_Die *parentdie,
440f755a
JS
1629 Dwarf_Die *memberdie,
1630 vector<Dwarf_Attribute>& locs)
1631{
1632 Dwarf_Attribute attr;
1633 Dwarf_Die die = *parentdie;
1634
1635 switch (dwarf_child (&die, &die))
1636 {
1637 case 0: /* First child found. */
1638 break;
1639 case 1: /* No children. */
1640 return false;
1641 case -1: /* Error. */
1642 default: /* Shouldn't happen */
1643 throw semantic_error (string (dwarf_tag(&die) == DW_TAG_union_type ? "union" : "struct")
23d106b9 1644 + string (dwarf_diename (&die) ?: "<anonymous>")
440f755a 1645 + string (dwarf_errmsg (-1)),
c67847a0 1646 c.tok);
440f755a
JS
1647 }
1648
1649 do
1650 {
1651 if (dwarf_tag(&die) != DW_TAG_member)
1652 continue;
1653
23d106b9 1654 const char *name = dwarf_diename(&die);
440f755a
JS
1655 if (name == NULL)
1656 {
1657 // need to recurse for anonymous structs/unions
1658 Dwarf_Die subdie;
1659
1660 if (!dwarf_attr_integrate (&die, DW_AT_type, &attr) ||
1661 !dwarf_formref_die (&attr, &subdie))
1662 continue;
1663
c67847a0 1664 if (find_struct_member(c, &subdie, memberdie, locs))
440f755a
JS
1665 goto success;
1666 }
c67847a0 1667 else if (name == c.member)
440f755a
JS
1668 {
1669 *memberdie = die;
1670 goto success;
1671 }
1672 }
1673 while (dwarf_siblingof (&die, &die) == 0);
1674
1675 return false;
1676
1677success:
1678 /* As we unwind the recursion, we need to build the chain of
1679 * locations that got to the final answer. */
1680 if (dwarf_attr_integrate (&die, DW_AT_data_member_location, &attr))
1681 locs.insert(locs.begin(), attr);
1682
1683 /* Union members don't usually have a location,
1684 * but just use the containing union's location. */
1685 else if (dwarf_tag(parentdie) != DW_TAG_union_type)
c67847a0 1686 throw semantic_error ("no location for field '" + c.member
440f755a 1687 + "': " + string(dwarf_errmsg (-1)),
c67847a0 1688 c.tok);
440f755a
JS
1689
1690 return true;
1691}
1692
1693
1694Dwarf_Die *
1695dwflpp::translate_components(struct obstack *pool,
1696 struct location **tail,
1697 Dwarf_Addr pc,
1698 const target_symbol *e,
1699 Dwarf_Die *vardie,
1700 Dwarf_Die *die_mem,
1701 Dwarf_Attribute *attr_mem)
1702{
1703 Dwarf_Die *die = NULL;
1704
1705 unsigned i = 0;
1706
1707 if (vardie)
1708 *die_mem = *vardie;
1709
1710 if (e->components.empty())
1711 return die_mem;
1712
1713 while (i < e->components.size())
1714 {
c67847a0
JS
1715 const target_symbol::component& c = e->components[i];
1716
440f755a
JS
1717 /* XXX: This would be desirable, but we don't get the target_symbol token,
1718 and printing that gives us the file:line number too early anyway. */
1719#if 0
1720 // Emit a marker to note which field is being access-attempted, to give
1721 // better error messages if deref() fails.
1722 string piece = string(...target_symbol token...) + string ("#") + stringify(components[i].second);
1723 obstack_printf (pool, "c->last_stmt = %s;", lex_cast_qstring(piece).c_str());
1724#endif
1725
1726 die = die ? dwarf_formref_die (attr_mem, die_mem) : die_mem;
1727 const int typetag = dwarf_tag (die);
1728 switch (typetag)
1729 {
1730 case DW_TAG_typedef:
1731 case DW_TAG_const_type:
1732 case DW_TAG_volatile_type:
1733 /* Just iterate on the referent type. */
1734 break;
1735
1736 case DW_TAG_pointer_type:
440f755a 1737 c_translate_pointer (pool, 1, 0 /* PR9768*/, die, tail);
6fda2dff
JS
1738 if (c.type != target_symbol::comp_literal_array_index &&
1739 c.type != target_symbol::comp_expression_array_index)
d52761f8
JS
1740 break;
1741 /* else fall through as an array access */
440f755a
JS
1742
1743 case DW_TAG_array_type:
c67847a0 1744 if (c.type == target_symbol::comp_literal_array_index)
440f755a
JS
1745 {
1746 c_translate_array (pool, 1, 0 /* PR9768 */, die, tail,
c67847a0 1747 NULL, c.num_index);
440f755a
JS
1748 ++i;
1749 }
6fda2dff
JS
1750 else if (c.type == target_symbol::comp_expression_array_index)
1751 {
1752 string index = "THIS->index" + lex_cast<string>(i);
1753 c_translate_array (pool, 1, 0 /* PR9768 */, die, tail,
1754 index.c_str(), 0);
1755 ++i;
1756 }
440f755a 1757 else
c67847a0
JS
1758 throw semantic_error ("invalid access '"
1759 + lex_cast<string>(c)
1760 + "' for array type",
1761 c.tok);
440f755a
JS
1762 break;
1763
1764 case DW_TAG_structure_type:
1765 case DW_TAG_union_type:
c67847a0
JS
1766 if (c.type != target_symbol::comp_struct_member)
1767 throw semantic_error ("invalid access '"
1768 + lex_cast<string>(c)
1769 + "' for struct/union type",
1770 c.tok);
1771
440f755a
JS
1772 if (dwarf_hasattr(die, DW_AT_declaration))
1773 {
1774 Dwarf_Die *tmpdie = dwflpp::declaration_resolve(dwarf_diename(die));
1775 if (tmpdie == NULL)
1776 throw semantic_error ("unresolved struct "
23d106b9 1777 + string (dwarf_diename (die) ?: "<anonymous>"),
c67847a0 1778 c.tok);
440f755a
JS
1779 *die_mem = *tmpdie;
1780 }
1781
1782 {
1783 vector<Dwarf_Attribute> locs;
c67847a0 1784 if (!find_struct_member(c, die, die, locs))
440f755a
JS
1785 {
1786 string alternatives;
1787 stringstream members;
1788 print_members(die, members);
1789 if (members.str().size() != 0)
1790 alternatives = " (alternatives:" + members.str();
1791 throw semantic_error("unable to find member '" +
c67847a0 1792 c.member + "' for struct "
23d106b9 1793 + string(dwarf_diename(die) ?: "<unknown>")
440f755a 1794 + alternatives,
c67847a0 1795 c.tok);
440f755a
JS
1796 }
1797
1798 for (unsigned j = 0; j < locs.size(); ++j)
1799 translate_location (pool, &locs[j], pc, NULL, tail, e);
1800 }
1801
1802 ++i;
1803 break;
1804
1805 case DW_TAG_enumeration_type:
c67847a0
JS
1806 throw semantic_error ("invalid access '"
1807 + lex_cast<string>(c)
440f755a 1808 + "' vs. enum type "
23d106b9 1809 + string(dwarf_diename (die) ?: "<anonymous type>"),
c67847a0 1810 c.tok);
440f755a
JS
1811 break;
1812 case DW_TAG_base_type:
c67847a0
JS
1813 throw semantic_error ("invalid access '"
1814 + lex_cast<string>(c)
440f755a 1815 + "' vs. base type "
23d106b9 1816 + string(dwarf_diename (die) ?: "<anonymous type>"),
c67847a0 1817 c.tok);
440f755a
JS
1818 break;
1819 case -1:
1820 throw semantic_error ("cannot find type: " + string(dwarf_errmsg (-1)),
c67847a0 1821 c.tok);
440f755a
JS
1822 break;
1823
1824 default:
23d106b9 1825 throw semantic_error (string(dwarf_diename (die) ?: "<anonymous type>")
440f755a
JS
1826 + ": unexpected type tag "
1827 + lex_cast<string>(dwarf_tag (die)),
c67847a0 1828 c.tok);
440f755a
JS
1829 break;
1830 }
1831
1832 /* Now iterate on the type in DIE's attribute. */
1833 if (dwarf_attr_integrate (die, DW_AT_type, attr_mem) == NULL)
c67847a0
JS
1834 throw semantic_error ("cannot get type of field: " + string(dwarf_errmsg (-1)),
1835 c.tok);
440f755a 1836 }
d52761f8
JS
1837
1838 /* For an array index, we need to dereference the final DIE */
6fda2dff
JS
1839 if (e->components.back().type == target_symbol::comp_literal_array_index ||
1840 e->components.back().type == target_symbol::comp_expression_array_index)
d52761f8
JS
1841 die = dwarf_formref_die (attr_mem, die_mem);
1842
440f755a
JS
1843 return die;
1844}
1845
1846
1847Dwarf_Die *
1848dwflpp::resolve_unqualified_inner_typedie (Dwarf_Die *typedie_mem,
1849 Dwarf_Attribute *attr_mem,
1850 const target_symbol *e)
1851{
1852 Dwarf_Die *typedie;
1853 int typetag = 0;
1854 while (1)
1855 {
1856 typedie = dwarf_formref_die (attr_mem, typedie_mem);
1857 if (typedie == NULL)
1858 throw semantic_error ("cannot get type: " + string(dwarf_errmsg (-1)), e->tok);
1859 typetag = dwarf_tag (typedie);
1860 if (typetag != DW_TAG_typedef &&
1861 typetag != DW_TAG_const_type &&
1862 typetag != DW_TAG_volatile_type)
1863 break;
1864 if (dwarf_attr_integrate (typedie, DW_AT_type, attr_mem) == NULL)
1865 throw semantic_error ("cannot get type of pointee: " + string(dwarf_errmsg (-1)), e->tok);
1866 }
1867 return typedie;
1868}
1869
1870
1871void
1872dwflpp::translate_final_fetch_or_store (struct obstack *pool,
1873 struct location **tail,
1874 Dwarf_Addr module_bias,
1875 Dwarf_Die *die,
1876 Dwarf_Attribute *attr_mem,
1877 bool lvalue,
1878 const target_symbol *e,
1879 string &,
1880 string &,
1881 exp_type & ty)
1882{
1883 /* First boil away any qualifiers associated with the type DIE of
1884 the final location to be accessed. */
1885
1886 Dwarf_Die typedie_mem;
1887 Dwarf_Die *typedie;
1888 int typetag;
1889 char const *dname;
1890 string diestr;
1891
1892 typedie = resolve_unqualified_inner_typedie (&typedie_mem, attr_mem, e);
1893 typetag = dwarf_tag (typedie);
1894
03c75a4a
JS
1895 /* If we're looking for an address, then we can just provide what
1896 we computed to this point, without using a fetch/store. */
1897 if (e->addressof)
1898 {
1899 if (lvalue)
1900 throw semantic_error ("cannot write to member address", e->tok);
1901
1902 if (dwarf_hasattr_integrate (die, DW_AT_bit_offset))
1903 throw semantic_error ("cannot take address of bit-field", e->tok);
1904
1905 c_translate_addressof (pool, 1, 0, 0, die, tail, "THIS->__retvalue");
1906 ty = pe_long;
1907 return;
1908 }
1909
440f755a
JS
1910 /* Then switch behavior depending on the type of fetch/store we
1911 want, and the type and pointer-ness of the final location. */
1912
1913 switch (typetag)
1914 {
1915 default:
1916 dname = dwarf_diename(die);
1917 diestr = (dname != NULL) ? dname : "<unknown>";
1918 throw semantic_error ("unsupported type tag "
1919 + lex_cast<string>(typetag)
1920 + " for " + diestr, e->tok);
1921 break;
1922
1923 case DW_TAG_structure_type:
1924 case DW_TAG_union_type:
1925 dname = dwarf_diename(die);
1926 diestr = (dname != NULL) ? dname : "<unknown>";
1927 throw semantic_error ("struct/union '" + diestr
1928 + "' is being accessed instead of a member of the struct/union", e->tok);
1929 break;
1930
1931 case DW_TAG_enumeration_type:
1932 case DW_TAG_base_type:
1933
1934 // Reject types we can't handle in systemtap
1935 {
1936 dname = dwarf_diename(die);
1937 diestr = (dname != NULL) ? dname : "<unknown>";
1938
1939 Dwarf_Attribute encoding_attr;
1940 Dwarf_Word encoding = (Dwarf_Word) -1;
1941 dwarf_formudata (dwarf_attr_integrate (typedie, DW_AT_encoding, &encoding_attr),
1942 & encoding);
1943 if (encoding < 0)
1944 {
1945 // clog << "bad type1 " << encoding << " diestr" << endl;
1946 throw semantic_error ("unsupported type (mystery encoding " + lex_cast<string>(encoding) + ")" +
1947 " for " + diestr, e->tok);
1948 }
1949
1950 if (encoding == DW_ATE_float
1951 || encoding == DW_ATE_complex_float
1952 /* XXX || many others? */)
1953 {
1954 // clog << "bad type " << encoding << " diestr" << endl;
1955 throw semantic_error ("unsupported type (encoding " + lex_cast<string>(encoding) + ")" +
1956 " for " + diestr, e->tok);
1957 }
1958 }
1959
1960 ty = pe_long;
1961 if (lvalue)
1962 c_translate_store (pool, 1, 0 /* PR9768 */, die, typedie, tail,
1963 "THIS->value");
1964 else
1965 c_translate_fetch (pool, 1, 0 /* PR9768 */, die, typedie, tail,
1966 "THIS->__retvalue");
1967 break;
1968
1969 case DW_TAG_array_type:
1970 case DW_TAG_pointer_type:
1971
1972 {
1973 Dwarf_Die pointee_typedie_mem;
1974 Dwarf_Die *pointee_typedie;
1975 Dwarf_Word pointee_encoding;
1976 Dwarf_Word pointee_byte_size = 0;
1977
1978 pointee_typedie = resolve_unqualified_inner_typedie (&pointee_typedie_mem, attr_mem, e);
1979
1980 if (dwarf_attr_integrate (pointee_typedie, DW_AT_byte_size, attr_mem))
1981 dwarf_formudata (attr_mem, &pointee_byte_size);
1982
1983 dwarf_formudata (dwarf_attr_integrate (pointee_typedie, DW_AT_encoding, attr_mem),
1984 &pointee_encoding);
1985
1986 if (lvalue)
1987 {
1988 ty = pe_long;
1989 if (typetag == DW_TAG_array_type)
1990 throw semantic_error ("cannot write to array address", e->tok);
1991 assert (typetag == DW_TAG_pointer_type);
1992 c_translate_pointer_store (pool, 1, 0 /* PR9768 */, typedie, tail,
1993 "THIS->value");
1994 }
1995 else
1996 {
1997 // We have the pointer: cast it to an integral type via &(*(...))
1998
1999 // NB: per bug #1187, at one point char*-like types were
2000 // automagically converted here to systemtap string values.
2001 // For several reasons, this was taken back out, leaving
2002 // pointer-to-string "conversion" (copying) to tapset functions.
2003
2004 ty = pe_long;
2005 if (typetag == DW_TAG_array_type)
2006 c_translate_array (pool, 1, 0 /* PR9768 */, typedie, tail, NULL, 0);
2007 else
2008 c_translate_pointer (pool, 1, 0 /* PR9768 */, typedie, tail);
2009 c_translate_addressof (pool, 1, 0 /* PR9768 */, NULL, pointee_typedie, tail,
2010 "THIS->__retvalue");
2011 }
2012 }
2013 break;
2014 }
2015}
2016
2017
2018string
2019dwflpp::express_as_string (string prelude,
2020 string postlude,
2021 struct location *head)
2022{
2023 size_t bufsz = 1024;
2024 char *buf = static_cast<char*>(malloc(bufsz));
2025 assert(buf);
2026
2027 FILE *memstream = open_memstream (&buf, &bufsz);
2028 assert(memstream);
2029
2030 fprintf(memstream, "{\n");
2031 fprintf(memstream, "%s", prelude.c_str());
2032 bool deref = c_emit_location (memstream, head, 1);
2033 fprintf(memstream, "%s", postlude.c_str());
2034 fprintf(memstream, " goto out;\n");
2035
2036 // dummy use of deref_fault label, to disable warning if deref() not used
2037 fprintf(memstream, "if (0) goto deref_fault;\n");
2038
2039 // XXX: deref flag not reliable; emit fault label unconditionally
2040 (void) deref;
2041 fprintf(memstream,
2042 "deref_fault:\n"
2043 " goto out;\n");
2044 fprintf(memstream, "}\n");
2045
2046 fclose (memstream);
2047 string result(buf);
2048 free (buf);
2049 return result;
2050}
2051
2052
2053string
2054dwflpp::literal_stmt_for_local (Dwarf_Die *scope_die,
2055 Dwarf_Addr pc,
2056 string const & local,
2057 const target_symbol *e,
2058 bool lvalue,
2059 exp_type & ty)
2060{
2061 Dwarf_Die vardie;
2062 Dwarf_Attribute fb_attr_mem, *fb_attr = NULL;
2063
2064 fb_attr = find_variable_and_frame_base (scope_die, pc, local, e,
2065 &vardie, &fb_attr_mem);
2066
2067 if (sess.verbose>2)
2068 clog << "finding location for local '" << local
2069 << "' near address 0x" << hex << pc
2070 << ", module bias 0x" << module_bias << dec
2071 << "\n";
2072
2073 Dwarf_Attribute attr_mem;
2074 if (dwarf_attr_integrate (&vardie, DW_AT_location, &attr_mem) == NULL)
2075 {
2076 throw semantic_error("failed to retrieve location "
2077 "attribute for local '" + local
2078 + "' (dieoffset: "
2079 + lex_cast_hex<string>(dwarf_dieoffset (&vardie))
2080 + ")",
2081 e->tok);
2082 }
2083
2084#define obstack_chunk_alloc malloc
2085#define obstack_chunk_free free
2086
2087 struct obstack pool;
2088 obstack_init (&pool);
2089 struct location *tail = NULL;
2090
2091 /* Given $foo->bar->baz[NN], translate the location of foo. */
2092
2093 struct location *head = translate_location (&pool,
2094 &attr_mem, pc, fb_attr, &tail,
2095 e);
2096
2097 if (dwarf_attr_integrate (&vardie, DW_AT_type, &attr_mem) == NULL)
2098 throw semantic_error("failed to retrieve type "
2099 "attribute for local '" + local + "'",
2100 e->tok);
2101
2102 /* Translate the ->bar->baz[NN] parts. */
2103
2104 Dwarf_Die die_mem, *die = dwarf_formref_die (&attr_mem, &die_mem);
2105 die = translate_components (&pool, &tail, pc, e,
2106 die, &die_mem, &attr_mem);
2107
2108 /* Translate the assignment part, either
2109 x = $foo->bar->baz[NN]
2110 or
2111 $foo->bar->baz[NN] = x
2112 */
2113
2114 string prelude, postlude;
2115 translate_final_fetch_or_store (&pool, &tail, module_bias,
2116 die, &attr_mem, lvalue, e,
2117 prelude, postlude, ty);
2118
2119 /* Write the translation to a string. */
2120 return express_as_string(prelude, postlude, head);
2121}
2122
2123
2124string
2125dwflpp::literal_stmt_for_return (Dwarf_Die *scope_die,
2126 Dwarf_Addr pc,
2127 const target_symbol *e,
2128 bool lvalue,
2129 exp_type & ty)
2130{
2131 if (sess.verbose>2)
2132 clog << "literal_stmt_for_return: finding return value for "
2133 << (dwarf_diename(scope_die) ?: "<unknown>")
2134 << "("
2135 << (dwarf_diename(cu) ?: "<unknown>")
2136 << ")\n";
2137
2138 struct obstack pool;
2139 obstack_init (&pool);
2140 struct location *tail = NULL;
2141
2142 /* Given $return->bar->baz[NN], translate the location of return. */
2143 const Dwarf_Op *locops;
2144 int nlocops = dwfl_module_return_value_location (module, scope_die,
2145 &locops);
2146 if (nlocops < 0)
2147 {
2148 throw semantic_error("failed to retrieve return value location"
2149 " for "
2150 + string(dwarf_diename(scope_die) ?: "<unknown>")
2151 + "(" + string(dwarf_diename(cu) ?: "<unknown>")
2152 + ")",
2153 e->tok);
2154 }
2155 // the function has no return value (e.g. "void" in C)
2156 else if (nlocops == 0)
2157 {
2158 throw semantic_error("function "
2159 + string(dwarf_diename(scope_die) ?: "<unknown>")
2160 + "(" + string(dwarf_diename(cu) ?: "<unknown>")
2161 + ") has no return value",
2162 e->tok);
2163 }
2164
2165 struct location *head = c_translate_location (&pool, &loc2c_error, this,
2166 &loc2c_emit_address,
2167 1, 0 /* PR9768 */,
2168 pc, locops, nlocops,
00b01a99 2169 &tail, NULL, NULL);
440f755a
JS
2170
2171 /* Translate the ->bar->baz[NN] parts. */
2172
2173 Dwarf_Attribute attr_mem;
2174 if (dwarf_attr_integrate (scope_die, DW_AT_type, &attr_mem) == NULL)
2175 throw semantic_error("failed to retrieve return value type attribute for "
2176 + string(dwarf_diename(scope_die) ?: "<unknown>")
2177 + "(" + string(dwarf_diename(cu) ?: "<unknown>")
2178 + ")",
2179 e->tok);
2180
2181 Dwarf_Die die_mem, *die = dwarf_formref_die (&attr_mem, &die_mem);
2182 die = translate_components (&pool, &tail, pc, e,
2183 die, &die_mem, &attr_mem);
2184
2185 /* Translate the assignment part, either
2186 x = $return->bar->baz[NN]
2187 or
2188 $return->bar->baz[NN] = x
2189 */
2190
2191 string prelude, postlude;
2192 translate_final_fetch_or_store (&pool, &tail, module_bias,
2193 die, &attr_mem, lvalue, e,
2194 prelude, postlude, ty);
2195
2196 /* Write the translation to a string. */
2197 return express_as_string(prelude, postlude, head);
2198}
2199
2200
2201string
2202dwflpp::literal_stmt_for_pointer (Dwarf_Die *type_die,
2203 const target_symbol *e,
2204 bool lvalue,
2205 exp_type & ty)
2206{
2207 if (sess.verbose>2)
2208 clog << "literal_stmt_for_pointer: finding value for "
2209 << (dwarf_diename(type_die) ?: "<unknown>")
2210 << "("
2211 << (dwarf_diename(cu) ?: "<unknown>")
2212 << ")\n";
2213
2214 struct obstack pool;
2215 obstack_init (&pool);
2216 struct location *head = c_translate_argument (&pool, &loc2c_error, this,
2217 &loc2c_emit_address,
2218 1, "THIS->pointer");
2219 struct location *tail = head;
2220
2221 /* Translate the ->bar->baz[NN] parts. */
2222
2223 Dwarf_Attribute attr_mem;
2224 Dwarf_Die die_mem, *die = NULL;
2225 die = translate_components (&pool, &tail, 0, e,
2226 type_die, &die_mem, &attr_mem);
2227
2228 /* Translate the assignment part, either
2229 x = (THIS->pointer)->bar->baz[NN]
2230 or
2231 (THIS->pointer)->bar->baz[NN] = x
2232 */
2233
2234 string prelude, postlude;
2235 translate_final_fetch_or_store (&pool, &tail, module_bias,
2236 die, &attr_mem, lvalue, e,
2237 prelude, postlude, ty);
2238
2239 /* Write the translation to a string. */
2240 return express_as_string(prelude, postlude, head);
2241}
2242
2243
27646582
JS
2244static bool
2245in_kprobes_function(systemtap_session& sess, Dwarf_Addr addr)
2246{
2247 if (sess.sym_kprobes_text_start != 0 && sess.sym_kprobes_text_end != 0)
2248 {
2249 // If the probe point address is anywhere in the __kprobes
2250 // address range, we can't use this probe point.
2251 if (addr >= sess.sym_kprobes_text_start && addr < sess.sym_kprobes_text_end)
2252 return true;
2253 }
2254 return false;
2255}
2256
2257
2258bool
2259dwflpp::blacklisted_p(const string& funcname,
2260 const string& filename,
2261 int,
2262 const string& module,
2263 const string& section,
2264 Dwarf_Addr addr,
2265 bool has_return)
2266{
2267 if (!blacklist_enabled)
2268 return false; // no blacklist for userspace
2269
2270 if (section.substr(0, 6) == string(".init.") ||
2271 section.substr(0, 6) == string(".exit.") ||
2272 section.substr(0, 9) == string(".devinit.") ||
2273 section.substr(0, 9) == string(".devexit.") ||
2274 section.substr(0, 9) == string(".cpuinit.") ||
2275 section.substr(0, 9) == string(".cpuexit.") ||
2276 section.substr(0, 9) == string(".meminit.") ||
2277 section.substr(0, 9) == string(".memexit."))
2278 {
2279 // NB: module .exit. routines could be probed in theory:
2280 // if the exit handler in "struct module" is diverted,
2281 // first inserting the kprobes
2282 // then allowing the exit code to run
2283 // then removing these kprobes
2284 if (sess.verbose>1)
2285 clog << " skipping - init/exit";
2286 return true;
2287 }
2288
2289 // Check for function marked '__kprobes'.
2290 if (module == TOK_KERNEL && in_kprobes_function(sess, addr))
2291 {
2292 if (sess.verbose>1)
2293 clog << " skipping - __kprobes";
2294 return true;
2295 }
2296
2297 // Check probe point against blacklist.
2298 int goodfn = regexec (&blacklist_func, funcname.c_str(), 0, NULL, 0);
2299 if (has_return)
2300 goodfn = goodfn && regexec (&blacklist_func_ret, funcname.c_str(), 0, NULL, 0);
2301 int goodfile = regexec (&blacklist_file, filename.c_str(), 0, NULL, 0);
2302
2303 if (! (goodfn && goodfile))
2304 {
2305 if (sess.guru_mode)
2306 {
2307 if (sess.verbose>1)
2308 clog << " guru mode enabled - ignoring blacklist";
2309 }
2310 else
2311 {
2312 if (sess.verbose>1)
2313 clog << " skipping - blacklisted";
2314 return true;
2315 }
2316 }
2317
2318 // This probe point is not blacklisted.
2319 return false;
2320}
2321
2322
2323void
2324dwflpp::build_blacklist()
2325{
2326 // We build up the regexps in these strings
2327
2328 // Add ^ anchors at the front; $ will be added just before regcomp.
2329
2330 string blfn = "^(";
2331 string blfn_ret = "^(";
2332 string blfile = "^(";
2333
2334 blfile += "kernel/kprobes.c"; // first alternative, no "|"
2335 blfile += "|arch/.*/kernel/kprobes.c";
2336 // Older kernels need ...
2337 blfile += "|include/asm/io.h";
2338 blfile += "|include/asm/bitops.h";
2339 // While newer ones need ...
2340 blfile += "|arch/.*/include/asm/io.h";
2341 blfile += "|arch/.*/include/asm/bitops.h";
2342 blfile += "|drivers/ide/ide-iops.c";
2343
2344 // XXX: it would be nice if these blacklisted functions were pulled
2345 // in dynamically, instead of being statically defined here.
2346 // Perhaps it could be populated from script files. A "noprobe
2347 // kernel.function("...")" construct might do the trick.
2348
2349 // Most of these are marked __kprobes in newer kernels. We list
2350 // them here (anyway) so the translator can block them on older
2351 // kernels that don't have the __kprobes function decorator. This
2352 // also allows detection of problems at translate- rather than
2353 // run-time.
2354
2355 blfn += "atomic_notifier_call_chain"; // first blfn; no "|"
2356 blfn += "|default_do_nmi";
2357 blfn += "|__die";
2358 blfn += "|die_nmi";
2359 blfn += "|do_debug";
2360 blfn += "|do_general_protection";
2361 blfn += "|do_int3";
2362 blfn += "|do_IRQ";
2363 blfn += "|do_page_fault";
2364 blfn += "|do_sparc64_fault";
2365 blfn += "|do_trap";
2366 blfn += "|dummy_nmi_callback";
2367 blfn += "|flush_icache_range";
2368 blfn += "|ia64_bad_break";
2369 blfn += "|ia64_do_page_fault";
2370 blfn += "|ia64_fault";
2371 blfn += "|io_check_error";
2372 blfn += "|mem_parity_error";
2373 blfn += "|nmi_watchdog_tick";
2374 blfn += "|notifier_call_chain";
2375 blfn += "|oops_begin";
2376 blfn += "|oops_end";
2377 blfn += "|program_check_exception";
2378 blfn += "|single_step_exception";
2379 blfn += "|sync_regs";
2380 blfn += "|unhandled_fault";
2381 blfn += "|unknown_nmi_error";
2382
2383 // Lots of locks
2384 blfn += "|.*raw_.*lock.*";
2385 blfn += "|.*read_.*lock.*";
2386 blfn += "|.*write_.*lock.*";
2387 blfn += "|.*spin_.*lock.*";
2388 blfn += "|.*rwlock_.*lock.*";
2389 blfn += "|.*rwsem_.*lock.*";
2390 blfn += "|.*mutex_.*lock.*";
2391 blfn += "|raw_.*";
2392 blfn += "|.*seq_.*lock.*";
2393
2394 // atomic functions
2395 blfn += "|atomic_.*";
2396 blfn += "|atomic64_.*";
2397
2398 // few other problematic cases
2399 blfn += "|get_bh";
2400 blfn += "|put_bh";
2401
2402 // Experimental
2403 blfn += "|.*apic.*|.*APIC.*";
2404 blfn += "|.*softirq.*";
2405 blfn += "|.*IRQ.*";
2406 blfn += "|.*_intr.*";
2407 blfn += "|__delay";
2408 blfn += "|.*kernel_text.*";
2409 blfn += "|get_current";
2410 blfn += "|current_.*";
2411 blfn += "|.*exception_tables.*";
2412 blfn += "|.*setup_rt_frame.*";
2413
2414 // PR 5759, CONFIG_PREEMPT kernels
2415 blfn += "|.*preempt_count.*";
2416 blfn += "|preempt_schedule";
2417
2418 // These functions don't return, so return probes would never be recovered
2419 blfn_ret += "do_exit"; // no "|"
2420 blfn_ret += "|sys_exit";
2421 blfn_ret += "|sys_exit_group";
2422
2423 // __switch_to changes "current" on x86_64 and i686, so return probes
2424 // would cause kernel panic, and it is marked as "__kprobes" on x86_64
2425 if (sess.architecture == "x86_64")
2426 blfn += "|__switch_to";
2427 if (sess.architecture == "i686")
2428 blfn_ret += "|__switch_to";
2429
2430 blfn += ")$";
2431 blfn_ret += ")$";
2432 blfile += ")$";
2433
2434 if (sess.verbose > 2)
2435 {
2436 clog << "blacklist regexps:" << endl;
2437 clog << "blfn: " << blfn << endl;
2438 clog << "blfn_ret: " << blfn_ret << endl;
2439 clog << "blfile: " << blfile << endl;
2440 }
2441
2442 int rc = regcomp (& blacklist_func, blfn.c_str(), REG_NOSUB|REG_EXTENDED);
2443 if (rc) throw semantic_error ("blacklist_func regcomp failed");
2444 rc = regcomp (& blacklist_func_ret, blfn_ret.c_str(), REG_NOSUB|REG_EXTENDED);
2445 if (rc) throw semantic_error ("blacklist_func_ret regcomp failed");
2446 rc = regcomp (& blacklist_file, blfile.c_str(), REG_NOSUB|REG_EXTENDED);
2447 if (rc) throw semantic_error ("blacklist_file regcomp failed");
2448
2449 blacklist_enabled = true;
2450}
2451
2452
2453string
2454dwflpp::get_blacklist_section(Dwarf_Addr addr)
2455{
2456 string blacklist_section;
2457 Dwarf_Addr bias;
2458 // We prefer dwfl_module_getdwarf to dwfl_module_getelf here,
2459 // because dwfl_module_getelf can force costly section relocations
2460 // we don't really need, while either will do for this purpose.
2461 Elf* elf = (dwarf_getelf (dwfl_module_getdwarf (module, &bias))
2462 ?: dwfl_module_getelf (module, &bias));
2463
2464 Dwarf_Addr offset = addr - bias;
2465 if (elf)
2466 {
2467 Elf_Scn* scn = 0;
2468 size_t shstrndx;
fcc30d6d 2469 dwfl_assert ("getshdrstrndx", elf_getshdrstrndx (elf, &shstrndx));
27646582
JS
2470 while ((scn = elf_nextscn (elf, scn)) != NULL)
2471 {
2472 GElf_Shdr shdr_mem;
2473 GElf_Shdr *shdr = gelf_getshdr (scn, &shdr_mem);
2474 if (! shdr)
2475 continue; // XXX error?
2476
2477 if (!(shdr->sh_flags & SHF_ALLOC))
2478 continue;
2479
2480 GElf_Addr start = shdr->sh_addr;
2481 GElf_Addr end = start + shdr->sh_size;
2482 if (! (offset >= start && offset < end))
2483 continue;
2484
2485 blacklist_section = elf_strptr (elf, shstrndx, shdr->sh_name);
2486 break;
2487 }
2488 }
2489 return blacklist_section;
2490}
2491
2492
2493Dwarf_Addr
d2309c6c 2494dwflpp::relocate_address(Dwarf_Addr dw_addr,
27646582
JS
2495 string& reloc_section,
2496 string& blacklist_section)
2497{
d2309c6c
MW
2498 // PR10273
2499 // libdw address, so adjust for bias gotten from dwfl_module_getdwarf
2500 Dwarf_Addr reloc_addr = dw_addr + module_bias;
27646582
JS
2501 if (!module)
2502 {
2503 assert(module_name == TOK_KERNEL);
2504 reloc_section = "";
2505 blacklist_section = "";
2506 }
2507 else if (dwfl_module_relocations (module) > 0)
2508 {
2509 // This is a relocatable module; libdwfl already knows its
2510 // sections, so we can relativize addr.
2511 int idx = dwfl_module_relocate_address (module, &reloc_addr);
2512 const char* r_s = dwfl_module_relocation_info (module, idx, NULL);
2513 if (r_s)
2514 reloc_section = r_s;
2515 blacklist_section = reloc_section;
2516
2517 if (reloc_section == "" && dwfl_module_relocations (module) == 1)
2518 {
d2309c6c 2519 blacklist_section = get_blacklist_section(dw_addr);
27646582 2520 reloc_section = ".dynamic";
27646582
JS
2521 }
2522 }
2523 else
2524 {
d2309c6c 2525 blacklist_section = get_blacklist_section(dw_addr);
27646582
JS
2526 reloc_section = ".absolute";
2527 }
2528 return reloc_addr;
2529}
2530
1f8592d1
MW
2531/* Converts a "global" literal address to the module symbol address
2532 * space. If necessary (not for kernel and executables using absolute
2533 * addresses), this adjust the address for the current module symbol
2534 * bias. Literal addresses are provided by the user (or contained on
2535 * the .probes section) based on the "on disk" layout of the module.
2536 */
2537Dwarf_Addr
2538dwflpp::literal_addr_to_sym_addr(Dwarf_Addr lit_addr)
2539{
88eaee9f
MW
2540 if (sess.verbose > 2)
2541 clog << "literal_addr_to_sym_addr 0x" << hex << lit_addr << dec << endl;
2542
1f8592d1
MW
2543 // Assume the address came from the symbol list.
2544 // If we cannot get the symbol bias fall back on the dw bias.
2545 // The kernel (and other absolute executable modules) is special though.
2546 if (module_name != TOK_KERNEL
2547 && dwfl_module_relocations (module) > 0)
2548 {
2549 Dwarf_Addr symbias = ~0;
2550 if (dwfl_module_getsymtab (module) != -1)
2551 dwfl_module_info (module, NULL, NULL, NULL, NULL,
2552 &symbias, NULL, NULL);
88eaee9f
MW
2553
2554 if (sess.verbose > 3)
2555 clog << "symbias 0x" << hex << symbias << dec
2556 << ", dwbias 0x" << hex << module_bias << dec << endl;
2557
1f8592d1
MW
2558 if (symbias == (Dwarf_Addr) ~0)
2559 symbias = module_bias;
2560
2561 lit_addr += symbias;
2562 }
2563
88eaee9f
MW
2564 if (sess.verbose > 2)
2565 clog << "literal_addr_to_sym_addr ret 0x" << hex << lit_addr << dec << endl;
2566
1f8592d1
MW
2567 return lit_addr;
2568}
27646582 2569
c8ad0687
JS
2570int
2571dwflpp::dwarf_getscopes_cached (Dwarf_Addr pc, Dwarf_Die **scopes)
2572{
2573 if (!cached_scopes || pc != pc_cached_scopes)
2574 {
2575 free(cached_scopes);
2576 cached_scopes = NULL;
2577 pc_cached_scopes = pc;
2578 num_cached_scopes = dwarf_getscopes(cu, pc, &cached_scopes);
2579 }
2580 *scopes = cached_scopes;
2581 return num_cached_scopes;
2582}
2583
88eaee9f
MW
2584/* Returns the call frame address operations for the given program counter
2585 * in the libdw address space.
2586 */
00b01a99
MW
2587Dwarf_Op *
2588dwflpp::get_cfa_ops (Dwarf_Addr pc)
2589{
2590 Dwarf_Op *cfa_ops = NULL;
2591
88eaee9f
MW
2592 if (sess.verbose > 2)
2593 clog << "get_cfa_ops @0x" << hex << pc << dec
2594 << ", module_start @0x" << hex << module_start << dec << endl;
2595
00b01a99
MW
2596#ifdef _ELFUTILS_PREREQ
2597#if _ELFUTILS_PREREQ(0,142)
2598 // Try debug_frame first, then fall back on eh_frame.
4a8636a3 2599 size_t cfa_nops;
00b01a99
MW
2600 Dwarf_Addr bias;
2601 Dwarf_CFI *cfi = dwfl_module_dwarf_cfi (module, &bias);
2602 if (cfi != NULL)
2603 {
88eaee9f
MW
2604 if (sess.verbose > 3)
2605 clog << "got dwarf cfi bias: 0x" << hex << bias << dec << endl;
00b01a99 2606 Dwarf_Frame *frame = NULL;
88eaee9f 2607 if (dwarf_cfi_addrframe (cfi, pc - bias, &frame) == 0)
97f529ab 2608 dwarf_frame_cfa (frame, &cfa_ops, &cfa_nops);
88eaee9f
MW
2609 else if (sess.verbose > 3)
2610 clog << "dwarf_cfi_addrframe failed: " << dwarf_errmsg(-1) << endl;
00b01a99 2611 }
88eaee9f
MW
2612 else if (sess.verbose > 3)
2613 clog << "dwfl_module_dwarf_cfi failed: " << dwfl_errmsg(-1) << endl;
2614
00b01a99
MW
2615 if (cfa_ops == NULL)
2616 {
2617 cfi = dwfl_module_eh_cfi (module, &bias);
2618 if (cfi != NULL)
2619 {
88eaee9f
MW
2620 if (sess.verbose > 3)
2621 clog << "got eh cfi bias: 0x" << hex << bias << dec << endl;
00b01a99 2622 Dwarf_Frame *frame = NULL;
88eaee9f 2623 if (dwarf_cfi_addrframe (cfi, pc - bias, &frame) == 0)
97f529ab 2624 dwarf_frame_cfa (frame, &cfa_ops, &cfa_nops);
88eaee9f
MW
2625 else if (sess.verbose > 3)
2626 clog << "dwarf_cfi_addrframe failed: " << dwarf_errmsg(-1) << endl;
00b01a99 2627 }
88eaee9f
MW
2628 else if (sess.verbose > 3)
2629 clog << "dwfl_module_eh_cfi failed: " << dwfl_errmsg(-1) << endl;
2630
00b01a99
MW
2631 }
2632#endif
2633#endif
2634
88eaee9f
MW
2635 if (sess.verbose > 2)
2636 clog << (cfa_ops == NULL ? "not " : " ") << "found cfa" << endl;
2637
00b01a99
MW
2638 return cfa_ops;
2639}
c8ad0687 2640
440f755a 2641/* vim: set sw=2 ts=8 cino=>4,n-2,{2,^-2,t0,(0,u0,w1,M1 : */
This page took 0.290098 seconds and 5 git commands to generate.