]> sourceware.org Git - systemtap.git/blame - tapsets.cxx
Add test to compile and run all tracepoints
[systemtap.git] / tapsets.cxx
CommitLineData
56e12059 1// tapset resolution
12b44fb3 2// Copyright (C) 2005-2009 Red Hat Inc.
aa30ccd3 3// Copyright (C) 2005-2007 Intel Corporation.
0b8f6579 4// Copyright (C) 2008 James.Bottomley@HansenPartnership.com
56e12059
FCE
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 "config.h"
12#include "staptree.h"
13#include "elaborate.h"
b55bc428 14#include "tapsets.h"
56e12059 15#include "translate.h"
dc38c0ae 16#include "session.h"
72dbc915 17#include "util.h"
0a6f5a3f 18#include "buildrun.h"
86bf665e 19#include "dwarf_wrappers.h"
2e67a43b 20#include "auto_free.h"
bd2b1e68 21
3b579393
FCE
22#include <cstdlib>
23#include <algorithm>
bd2b1e68 24#include <deque>
56e12059 25#include <iostream>
bd2b1e68 26#include <map>
3bf6ac45
TM
27#ifdef HAVE_TR1_UNORDERED_MAP
28#include <tr1/unordered_map>
29#else
2171f774 30#include <ext/hash_map>
3bf6ac45 31#endif
ec4373ff 32#include <set>
56e12059 33#include <sstream>
bd2b1e68 34#include <stdexcept>
b55bc428 35#include <vector>
e36387d7 36#include <cstdarg>
29e64872 37#include <cassert>
1969b5bc 38#include <iomanip>
f781f849 39#include <cerrno>
bd2b1e68
GH
40
41extern "C" {
df8fadee 42#include <fcntl.h>
bd2b1e68 43#include <elfutils/libdwfl.h>
7a053d3b 44#include <elfutils/libdw.h>
77de5e9e
GH
45#include <dwarf.h>
46#include <elf.h>
47#include <obstack.h>
30a279be 48#include <regex.h>
b20febf3 49#include <glob.h>
30a279be 50#include <fnmatch.h>
5f0a03a6 51#include <stdio.h>
349dc70e 52#include <sys/types.h>
4b1ad75e 53
30a279be 54#include "loc2c.h"
4b1ad75e
RM
55#define __STDC_FORMAT_MACROS
56#include <inttypes.h>
bd2b1e68 57}
77de5e9e 58
56e12059 59
47dd066d
WC
60#ifdef PERFMON
61#include <perfmon/pfmlib.h>
62#include <perfmon/perfmon.h>
63#endif
64
56e12059 65using namespace std;
2171f774 66using namespace __gnu_cxx;
56e12059 67
b20febf3
FCE
68// ------------------------------------------------------------------------
69// Generic derived_probe_group: contains an ordinary vector of the
70// given type. It provides only the enrollment function.
71
72template <class DP> struct generic_dpg: public derived_probe_group
73{
74protected:
75 vector <DP*> probes;
76public:
77 generic_dpg () {}
78 void enroll (DP* probe) { probes.push_back (probe); }
79};
46b84a80
DS
80
81
b20febf3
FCE
82
83// ------------------------------------------------------------------------
65aeaea0 84// begin/end/error probes are run right during registration / deregistration
9a604fac
FCE
85// ------------------------------------------------------------------------
86
12b21830
DS
87static string TOK_BEGIN("begin");
88static string TOK_END("end");
89static string TOK_ERROR("error");
90
65aeaea0
FCE
91enum be_t { BEGIN, END, ERROR };
92
b20febf3
FCE
93struct be_derived_probe: public derived_probe
94{
65aeaea0 95 be_t type;
16e8f21f
JS
96 int64_t priority;
97
65aeaea0
FCE
98 be_derived_probe (probe* p, probe_point* l, be_t t, int64_t pr):
99 derived_probe (p, l), type (t), priority (pr) {}
b20febf3
FCE
100
101 void join_group (systemtap_session& s);
16e8f21f
JS
102
103 static inline bool comp(be_derived_probe const *a,
104 be_derived_probe const *b)
65aeaea0
FCE
105 {
106 // This allows the BEGIN/END/ERROR probes to intermingle.
107 // But that's OK - they're always treversed with a nested
108 // "if (type==FOO)" conditional.
4baf0e53 109 return a->priority < b->priority;
65aeaea0 110 }
90f98cc3
DS
111
112 bool needs_global_locks () { return false; }
113 // begin/end probes don't need locks around global variables, since
114 // they aren't run concurrently with any other probes
b20febf3
FCE
115};
116
117
118struct be_derived_probe_group: public generic_dpg<be_derived_probe>
119{
120public:
121 void emit_module_decls (systemtap_session& s);
122 void emit_module_init (systemtap_session& s);
123 void emit_module_exit (systemtap_session& s);
124};
125
b20febf3
FCE
126struct be_builder: public derived_probe_builder
127{
65aeaea0
FCE
128 be_t type;
129
130 be_builder(be_t t) : type(t) {}
131
78f6bba6 132 virtual void build(systemtap_session &,
b20febf3
FCE
133 probe * base,
134 probe_point * location,
86bf665e 135 literal_map_t const & parameters,
b20febf3
FCE
136 vector<derived_probe *> & finished_results)
137 {
16e8f21f 138 int64_t priority;
12b21830
DS
139 if ((type == BEGIN && !get_param(parameters, TOK_BEGIN, priority)) ||
140 (type == END && !get_param(parameters, TOK_END, priority)) ||
141 (type == ERROR && !get_param(parameters, TOK_ERROR, priority)))
16e8f21f
JS
142 priority = 0;
143 finished_results.push_back(
65aeaea0 144 new be_derived_probe(base, location, type, priority));
b20febf3
FCE
145 }
146};
147
148
9a604fac 149void
b20febf3 150be_derived_probe::join_group (systemtap_session& s)
9a604fac 151{
b20febf3
FCE
152 if (! s.be_derived_probes)
153 s.be_derived_probes = new be_derived_probe_group ();
154 s.be_derived_probes->enroll (this);
155}
47dd066d 156
b20febf3
FCE
157
158// ------------------------------------------------------------------------
159void
a58d79d0 160common_probe_entryfn_prologue (translator_output* o, string statestr,
c12d974f 161 string new_pp,
e0a17418 162 bool overload_processing = true)
b20febf3 163{
72d18b98 164 o->newline() << "struct context* __restrict__ c;";
e0a17418
JS
165 o->newline() << "#if !INTERRUPTIBLE";
166 o->newline() << "unsigned long flags;";
167 o->newline() << "#endif";
b20febf3 168
a58d79d0
DS
169 if (overload_processing)
170 o->newline() << "#if defined(STP_TIMING) || defined(STP_OVERLOAD)";
171 else
172 o->newline() << "#ifdef STP_TIMING";
173 o->newline() << "cycles_t cycles_atstart = get_cycles ();";
b20febf3 174 o->newline() << "#endif";
b20febf3
FCE
175
176#if 0 /* XXX: PERFMON */
47dd066d
WC
177 o->newline() << "static struct pfarg_ctx _pfm_context;";
178 o->newline() << "static void *_pfm_desc;";
179 o->newline() << "static struct pfarg_pmc *_pfm_pmc_x;";
180 o->newline() << "static int _pfm_num_pmc_x;";
181 o->newline() << "static struct pfarg_pmd *_pfm_pmd_x;";
182 o->newline() << "static int _pfm_num_pmd_x;";
183#endif
184
e0a17418
JS
185 o->newline() << "#if INTERRUPTIBLE";
186 o->newline() << "preempt_disable ();";
187 o->newline() << "#else";
188 o->newline() << "local_irq_save (flags);";
189 o->newline() << "#endif";
b20febf3 190
c931ec8a 191 // Check for enough free enough stack space
d05a1d00 192 o->newline() << "if (unlikely ((((unsigned long) (& c)) & (THREAD_SIZE-1))"; // free space
a63401b1 193 o->newline(1) << "< (MINSTACKSPACE + sizeof (struct thread_info)))) {"; // needed space
d05a1d00
FCE
194 // XXX: may need porting to platforms where task_struct is not at bottom of kernel stack
195 // NB: see also CONFIG_DEBUG_STACKOVERFLOW
b3c3ca7c
FCE
196 o->newline() << "atomic_inc (& skipped_count);";
197 o->newline() << "#ifdef STP_TIMING";
198 o->newline() << "atomic_inc (& skipped_count_lowstack);";
199 o->newline() << "#endif";
c931ec8a
FCE
200 o->newline() << "goto probe_epilogue;";
201 o->newline(-1) << "}";
202
b20febf3
FCE
203 o->newline() << "if (atomic_read (&session_state) != " << statestr << ")";
204 o->newline(1) << "goto probe_epilogue;";
205 o->indent(-1);
9a604fac 206
a44a0785 207 o->newline() << "c = per_cpu_ptr (contexts, smp_processor_id());";
b3c3ca7c
FCE
208 o->newline() << "if (atomic_inc_return (& c->busy) != 1) {";
209 o->newline(1) << "atomic_inc (& skipped_count);";
210 o->newline() << "#ifdef STP_TIMING";
211 o->newline() << "atomic_inc (& skipped_count_reentrant);";
c12d974f
FCE
212 o->newline() << "#ifdef DEBUG_REENTRANCY";
213 o->newline() << "_stp_warn (\"Skipped %s due to %s residency on cpu %u\\n\", "
214 << new_pp << ", c->probe_point ?: \"?\", smp_processor_id());";
215 // NB: There is a conceivable race condition here with reading
216 // c->probe_point, knowing that this other probe is sort of running.
217 // However, in reality, it's interrupted. Plus even if it were able
218 // to somehow start again, and stop before we read c->probe_point,
219 // at least we have that ?: "?" bit in there to avoid a NULL deref.
220 o->newline() << "#endif";
b3c3ca7c 221 o->newline() << "#endif";
9a604fac 222 o->newline() << "atomic_dec (& c->busy);";
b20febf3 223 o->newline() << "goto probe_epilogue;";
9a604fac
FCE
224 o->newline(-1) << "}";
225 o->newline();
1e00cfb1 226 o->newline() << "c->last_stmt = 0;";
9a604fac 227 o->newline() << "c->last_error = 0;";
9a604fac 228 o->newline() << "c->nesting = 0;";
22f8b401 229 o->newline() << "c->regs = 0;";
b916df9c 230 o->newline() << "c->unwaddr = 0;";
c12d974f 231 o->newline() << "c->probe_point = " << new_pp << ";";
b916df9c 232 // reset unwound address cache
fcff848e 233 o->newline() << "c->pi = 0;";
9addf322 234 o->newline() << "c->regparm = 0;";
bc54e71c
MH
235 o->newline() << "c->marker_name = NULL;";
236 o->newline() << "c->marker_format = NULL;";
e0a17418
JS
237
238 o->newline() << "#if INTERRUPTIBLE";
239 o->newline() << "c->actionremaining = MAXACTION_INTERRUPTIBLE;";
240 o->newline() << "#else";
241 o->newline() << "c->actionremaining = MAXACTION;";
242 o->newline() << "#endif";
dbb68664
FCE
243 o->newline() << "#ifdef STP_TIMING";
244 o->newline() << "c->statp = 0;";
245 o->newline() << "#endif";
9915575b
FCE
246 // NB: The following would actually be incorrect.
247 // That's because cycles_sum/cycles_base values are supposed to survive
248 // between consecutive probes. Periodically (STP_OVERLOAD_INTERVAL
249 // cycles), the values will be reset.
250 /*
f0e6dc63
FCE
251 o->newline() << "#ifdef STP_OVERLOAD";
252 o->newline() << "c->cycles_sum = 0;";
253 o->newline() << "c->cycles_base = 0;";
41c262f3 254 o->newline() << "#endif";
9915575b 255 */
b20febf3 256}
9a604fac 257
a44a0785 258
b20febf3 259void
a58d79d0 260common_probe_entryfn_epilogue (translator_output* o,
e0a17418 261 bool overload_processing = true)
b20febf3 262{
a58d79d0
DS
263 if (overload_processing)
264 o->newline() << "#if defined(STP_TIMING) || defined(STP_OVERLOAD)";
265 else
266 o->newline() << "#ifdef STP_TIMING";
dbb68664 267 o->newline() << "{";
a58d79d0
DS
268 o->newline(1) << "cycles_t cycles_atend = get_cycles ();";
269 // NB: we truncate cycles counts to 32 bits. Perhaps it should be
270 // fewer, if the hardware counter rolls over really quickly. We
271 // handle 32-bit wraparound here.
272 o->newline() << "int32_t cycles_elapsed = ((int32_t)cycles_atend > (int32_t)cycles_atstart)";
273 o->newline(1) << "? ((int32_t)cycles_atend - (int32_t)cycles_atstart)";
274 o->newline() << ": (~(int32_t)0) - (int32_t)cycles_atstart + (int32_t)cycles_atend + 1;";
275 o->indent(-1);
dbb68664 276
a58d79d0 277 o->newline() << "#ifdef STP_TIMING";
dbb68664 278 o->newline() << "if (likely (c->statp)) _stp_stat_add(*c->statp, cycles_elapsed);";
a58d79d0
DS
279 o->newline() << "#endif";
280
281 if (overload_processing)
282 {
283 o->newline() << "#ifdef STP_OVERLOAD";
284 o->newline() << "{";
285 // If the cycle count has wrapped (cycles_atend > cycles_base),
286 // let's go ahead and pretend the interval has been reached.
287 // This should reset cycles_base and cycles_sum.
288 o->newline(1) << "cycles_t interval = (cycles_atend > c->cycles_base)";
289 o->newline(1) << "? (cycles_atend - c->cycles_base)";
290 o->newline() << ": (STP_OVERLOAD_INTERVAL + 1);";
291 o->newline(-1) << "c->cycles_sum += cycles_elapsed;";
292
293 // If we've spent more than STP_OVERLOAD_THRESHOLD cycles in a
294 // probe during the last STP_OVERLOAD_INTERVAL cycles, the probe
295 // has overloaded the system and we need to quit.
296 o->newline() << "if (interval > STP_OVERLOAD_INTERVAL) {";
297 o->newline(1) << "if (c->cycles_sum > STP_OVERLOAD_THRESHOLD) {";
298 o->newline(1) << "_stp_error (\"probe overhead exceeded threshold\");";
299 o->newline() << "atomic_set (&session_state, STAP_SESSION_ERROR);";
551e9f14 300 o->newline() << "atomic_inc (&error_count);";
a58d79d0
DS
301 o->newline(-1) << "}";
302
303 o->newline() << "c->cycles_base = cycles_atend;";
304 o->newline() << "c->cycles_sum = 0;";
305 o->newline(-1) << "}";
306 o->newline(-1) << "}";
307 o->newline() << "#endif";
308 }
309
dbb68664
FCE
310 o->newline(-1) << "}";
311 o->newline() << "#endif";
312
c3add01f 313 o->newline() << "c->probe_point = 0;"; // vacated
9a604fac
FCE
314 o->newline() << "if (unlikely (c->last_error && c->last_error[0])) {";
315 o->newline(1) << "if (c->last_stmt != NULL)";
316 o->newline(1) << "_stp_softerror (\"%s near %s\", c->last_error, c->last_stmt);";
317 o->newline(-1) << "else";
318 o->newline(1) << "_stp_softerror (\"%s\", c->last_error);";
319 o->indent(-1);
320 o->newline() << "atomic_inc (& error_count);";
9a604fac
FCE
321 o->newline() << "if (atomic_read (& error_count) > MAXERRORS) {";
322 o->newline(1) << "atomic_set (& session_state, STAP_SESSION_ERROR);";
323 o->newline() << "_stp_exit ();";
324 o->newline(-1) << "}";
9a604fac 325 o->newline(-1) << "}";
9a604fac 326 o->newline() << "atomic_dec (&c->busy);";
a44a0785 327
b20febf3
FCE
328 o->newline(-1) << "probe_epilogue:"; // context is free
329 o->indent(1);
a44a0785 330
b3c3ca7c
FCE
331 // Check for excessive skip counts.
332 o->newline() << "if (unlikely (atomic_read (& skipped_count) > MAXSKIPPED)) {";
333 o->newline(1) << "atomic_set (& session_state, STAP_SESSION_ERROR);";
334 o->newline() << "_stp_exit ();";
335 o->newline(-1) << "}";
336
e0a17418
JS
337 o->newline() << "#if INTERRUPTIBLE";
338 o->newline() << "preempt_enable_no_resched ();";
339 o->newline() << "#else";
340 o->newline() << "local_irq_restore (flags);";
341 o->newline() << "#endif";
9a604fac
FCE
342}
343
344
56e12059
FCE
345// ------------------------------------------------------------------------
346
56e12059 347void
b20febf3
FCE
348be_derived_probe_group::emit_module_decls (systemtap_session& s)
349{
350 if (probes.empty()) return;
351
352 s.op->newline() << "/* ---- begin/end probes ---- */";
4c2732a1 353 s.op->newline() << "static void enter_begin_probe (void (*fn)(struct context*), const char* pp) {";
b20febf3 354 s.op->indent(1);
e0a17418 355 common_probe_entryfn_prologue (s.op, "STAP_SESSION_STARTING", "pp", false);
b20febf3 356 s.op->newline() << "(*fn) (c);";
e0a17418 357 common_probe_entryfn_epilogue (s.op, false);
b20febf3 358 s.op->newline(-1) << "}";
65aeaea0 359
4c2732a1 360 s.op->newline() << "static void enter_end_probe (void (*fn)(struct context*), const char* pp) {";
b20febf3 361 s.op->indent(1);
e0a17418 362 common_probe_entryfn_prologue (s.op, "STAP_SESSION_STOPPING", "pp", false);
65aeaea0 363 s.op->newline() << "(*fn) (c);";
e0a17418 364 common_probe_entryfn_epilogue (s.op, false);
65aeaea0
FCE
365 s.op->newline(-1) << "}";
366
4c2732a1 367 s.op->newline() << "static void enter_error_probe (void (*fn)(struct context*), const char* pp) {";
65aeaea0 368 s.op->indent(1);
e0a17418 369 common_probe_entryfn_prologue (s.op, "STAP_SESSION_ERROR", "pp", false);
b20febf3 370 s.op->newline() << "(*fn) (c);";
e0a17418 371 common_probe_entryfn_epilogue (s.op, false);
b20febf3 372 s.op->newline(-1) << "}";
65aeaea0 373
4c2732a1 374 s.op->newline() << "static struct stap_be_probe {";
65aeaea0
FCE
375 s.op->newline(1) << "void (*ph)(struct context*);";
376 s.op->newline() << "const char* pp;";
377 s.op->newline() << "int type;";
378 s.op->newline(-1) << "} stap_be_probes[] = {";
379 s.op->indent(1);
380
381 // NB: We emit the table in sorted order here, so we don't have to
382 // store the priority numbers as integers and sort at run time.
383
384 sort(probes.begin(), probes.end(), be_derived_probe::comp);
385
386 for (unsigned i=0; i < probes.size(); i++)
387 {
4baf0e53
RM
388 s.op->newline () << "{";
389 s.op->line() << " .pp="
65aeaea0
FCE
390 << lex_cast_qstring (*probes[i]->sole_location()) << ",";
391 s.op->line() << " .ph=&" << probes[i]->name << ",";
392 s.op->line() << " .type=" << probes[i]->type;
393 s.op->line() << " },";
394 }
395 s.op->newline(-1) << "};";
56e12059
FCE
396}
397
dc38c0ae 398void
b20febf3 399be_derived_probe_group::emit_module_init (systemtap_session& s)
dc38c0ae 400{
b8da0ad1
FCE
401 if (probes.empty()) return;
402
65aeaea0
FCE
403 s.op->newline() << "for (i=0; i<" << probes.size() << "; i++) {";
404 s.op->newline(1) << "struct stap_be_probe* stp = & stap_be_probes [i];";
405 s.op->newline() << "if (stp->type != " << BEGIN << ") continue;";
406 s.op->newline() << "enter_begin_probe (stp->ph, stp->pp);";
407 s.op->newline() << "/* rc = 0; */";
408 // NB: begin probes that cause errors do not constitute registration
409 // failures. An error message will probably get printed and if
410 // MAXERRORS was left at 1, we'll get an stp_exit. The
411 // error-handling probes will be run during the ordinary
412 // unregistration phase.
413 s.op->newline(-1) << "}";
dc38c0ae
DS
414}
415
46b84a80 416void
b20febf3 417be_derived_probe_group::emit_module_exit (systemtap_session& s)
46b84a80 418{
b8da0ad1
FCE
419 if (probes.empty()) return;
420
65aeaea0
FCE
421 s.op->newline() << "for (i=0; i<" << probes.size() << "; i++) {";
422 s.op->newline(1) << "struct stap_be_probe* stp = & stap_be_probes [i];";
423 s.op->newline() << "if (stp->type != " << END << ") continue;";
424 s.op->newline() << "enter_end_probe (stp->ph, stp->pp);";
425 s.op->newline(-1) << "}";
426
427 s.op->newline() << "for (i=0; i<" << probes.size() << "; i++) {";
428 s.op->newline(1) << "struct stap_be_probe* stp = & stap_be_probes [i];";
429 s.op->newline() << "if (stp->type != " << ERROR << ") continue;";
430 s.op->newline() << "enter_error_probe (stp->ph, stp->pp);";
431 s.op->newline(-1) << "}";
46b84a80
DS
432}
433
dc38c0ae 434
b20febf3 435
6e3347a9
FCE
436// ------------------------------------------------------------------------
437// never probes are never run
438// ------------------------------------------------------------------------
439
12b21830
DS
440static string TOK_NEVER("never");
441
6e3347a9
FCE
442struct never_derived_probe: public derived_probe
443{
444 never_derived_probe (probe* p): derived_probe (p) {}
445 never_derived_probe (probe* p, probe_point* l): derived_probe (p, l) {}
78f6bba6 446 void join_group (systemtap_session&) { /* thus no probe_group */ }
dc38c0ae
DS
447};
448
449
6e3347a9
FCE
450struct never_builder: public derived_probe_builder
451{
452 never_builder() {}
78f6bba6 453 virtual void build(systemtap_session &,
6e3347a9
FCE
454 probe * base,
455 probe_point * location,
86bf665e 456 literal_map_t const &,
6e3347a9
FCE
457 vector<derived_probe *> & finished_results)
458 {
459 finished_results.push_back(new never_derived_probe(base, location));
460 }
461};
462
463
b20febf3 464
56e12059 465// ------------------------------------------------------------------------
b20febf3 466// Dwarf derived probes. "We apologize for the inconvience."
b55bc428 467// ------------------------------------------------------------------------
bd2b1e68 468
c239d28c
GH
469static string TOK_KERNEL("kernel");
470static string TOK_MODULE("module");
c239d28c 471static string TOK_FUNCTION("function");
54efe513 472static string TOK_INLINE("inline");
b8da0ad1 473static string TOK_CALL("call");
c239d28c 474static string TOK_RETURN("return");
c9bad430 475static string TOK_MAXACTIVE("maxactive");
c239d28c 476static string TOK_STATEMENT("statement");
37ebca01 477static string TOK_ABSOLUTE("absolute");
888af770 478static string TOK_PROCESS("process");
f28a8c28 479static string TOK_MARK("mark");
0a6f5a3f 480static string TOK_TRACE("trace");
0f336e95 481static string TOK_LABEL("label");
59ff2773 482
5f0a03a6
JK
483// Can we handle this query with just symbol-table info?
484enum dbinfo_reqt
485{
486 dbr_unknown,
487 dbr_none, // kernel.statement(NUM).absolute
488 dbr_need_symtab, // can get by with symbol table if there's no dwarf
489 dbr_need_dwarf
490};
491
492enum info_status
493{
494 info_unknown,
495 info_present,
496 info_absent
497};
b8da0ad1 498
20e4a32c 499struct
7e1279ea
FCE
500func_info
501{
20e4a32c 502 func_info()
ab91b232 503 : decl_file(NULL), decl_line(-1), addr(0), prologue_end(0), weak(false)
b6581717
GH
504 {
505 memset(&die, 0, sizeof(die));
506 }
7e1279ea 507 string name;
4cd232e4
GH
508 char const * decl_file;
509 int decl_line;
7e1279ea 510 Dwarf_Die die;
5f0a03a6 511 Dwarf_Addr addr;
3e961ba6 512 Dwarf_Addr entrypc;
7e1279ea 513 Dwarf_Addr prologue_end;
ab91b232 514 bool weak;
2e67a43b
TM
515 // Comparison functor for list of functions sorted by address. The
516 // two versions that take a Dwarf_Addr let us use the STL algorithms
517 // upper_bound, equal_range et al., but we don't know whether the
518 // searched-for value will be passed as the first or the second
519 // argument.
520 struct Compare
521 {
522 bool operator() (const func_info* f1, const func_info* f2) const
523 {
524 return f1->addr < f2->addr;
525 }
526 // For doing lookups by address.
527 bool operator() (Dwarf_Addr addr, const func_info* f2) const
528 {
529 return addr < f2->addr;
530 }
531 bool operator() (const func_info* f1, Dwarf_Addr addr) const
532 {
533 return f1->addr < addr;
534 }
535 };
7e1279ea
FCE
536};
537
538struct
539inline_instance_info
540{
20e4a32c 541 inline_instance_info()
b6581717
GH
542 : decl_file(NULL), decl_line(-1)
543 {
544 memset(&die, 0, sizeof(die));
545 }
7e1279ea 546 string name;
4cd232e4
GH
547 char const * decl_file;
548 int decl_line;
3e961ba6 549 Dwarf_Addr entrypc;
7e1279ea
FCE
550 Dwarf_Die die;
551};
552
c8959a29 553
c4ce66a1
JS
554struct base_query; // forward decls
555struct dwarf_query;
5f0a03a6
JK
556struct dwflpp;
557struct symbol_table;
558
405b71b8 559
5f0a03a6
JK
560struct
561module_info
562{
563 Dwfl_Module* mod;
564 const char* name;
565 string elf_path;
566 Dwarf_Addr addr;
567 Dwarf_Addr bias;
568 symbol_table *sym_table;
569 info_status dwarf_status; // module has dwarf info?
570 info_status symtab_status; // symbol table cached?
571
572 void get_symtab(dwarf_query *q);
573
574 module_info(const char *name) :
575 mod(NULL),
576 name(name),
577 addr(0),
578 bias(0),
579 sym_table(NULL),
580 dwarf_status(info_unknown),
581 symtab_status(info_unknown)
582 {}
583
584 ~module_info();
585};
586
587struct
588module_cache
589{
590 map<string, module_info*> cache;
591 bool paths_collected;
592 bool dwarf_collected;
593
594 module_cache() : paths_collected(false), dwarf_collected(false) {}
595};
596typedef struct module_cache module_cache_t;
597
3bf6ac45
TM
598#ifdef HAVE_TR1_UNORDERED_MAP
599typedef tr1::unordered_map<string,Dwarf_Die> cu_function_cache_t;
600typedef tr1::unordered_map<string,cu_function_cache_t*> mod_cu_function_cache_t; // module:cu -> function -> die
601#else
2171f774
FCE
602struct stringhash {
603 size_t operator() (const string& s) const { hash<const char*> h; return h(s.c_str()); }
604};
605
606typedef hash_map<string,Dwarf_Die,stringhash> cu_function_cache_t;
607typedef hash_map<string,cu_function_cache_t*,stringhash> mod_cu_function_cache_t; // module:cu -> function -> die
3bf6ac45 608#endif
5f0a03a6
JK
609
610struct
611symbol_table
612{
613 module_info *mod_info; // associated module
614 map<string, func_info*> map_by_name;
615 vector<func_info*> list_by_addr;
2e67a43b
TM
616 typedef vector<func_info*>::iterator iterator_t;
617 typedef pair<iterator_t, iterator_t> range_t;
46f7b6be
JK
618#ifdef __powerpc__
619 GElf_Word opd_section;
620#endif
2e67a43b
TM
621 // add_symbol doesn't leave symbol table in order; call
622 // symbol_table::sort() when done adding symbols.
ab91b232
JK
623 void add_symbol(const char *name, bool weak, Dwarf_Addr addr,
624 Dwarf_Addr *high_addr);
2e67a43b 625 void sort();
5f0a03a6
JK
626 enum info_status read_symbols(FILE *f, const string& path);
627 enum info_status read_from_elf_file(const string& path);
628 enum info_status read_from_text_file(const string& path);
629 enum info_status get_from_elf();
46f7b6be
JK
630 void prepare_section_rejection(Dwfl_Module *mod);
631 bool reject_section(GElf_Word section);
5f0a03a6 632 void mark_dwarf_redundancies(dwflpp *dw);
ab91b232 633 void purge_syscall_stubs();
5f0a03a6
JK
634 func_info *lookup_symbol(const string& name);
635 Dwarf_Addr lookup_symbol_address(const string& name);
636 func_info *get_func_containing_address(Dwarf_Addr addr);
5f0a03a6
JK
637
638 symbol_table(module_info *mi) : mod_info(mi) {}
639 ~symbol_table();
640};
641
642static bool null_die(Dwarf_Die *die)
643{
644 static Dwarf_Die null = { 0 };
645 return (!die || !memcmp(die, &null, sizeof(null)));
646}
647
7e1279ea
FCE
648static int
649query_cu (Dwarf_Die * cudie, void * arg);
59ff2773
FCE
650
651
bd2b1e68
GH
652// Helper for dealing with selected portions of libdwfl in a more readable
653// fashion, and with specific cleanup / checking / logging options.
654
91eefb1c
GH
655static const char *
656dwarf_diename_integrate (Dwarf_Die *die)
657{
658 Dwarf_Attribute attr_mem;
659 return dwarf_formstring (dwarf_attr_integrate (die, DW_AT_name, &attr_mem));
660}
661
879eb9e9
SC
662enum line_t { ABSOLUTE, RELATIVE, RANGE, WILDCARD };
663
3e961ba6
JB
664typedef vector<inline_instance_info> inline_instance_map_t;
665typedef vector<func_info> func_info_map_t;
666
b20febf3 667struct dwflpp
bd2b1e68 668{
5227f1ea 669 systemtap_session & sess;
bd2b1e68
GH
670 Dwfl * dwfl;
671
672 // These are "current" values we focus on.
673 Dwfl_Module * module;
674 Dwarf * module_dwarf;
675 Dwarf_Addr module_bias;
5f0a03a6 676 module_info * mod_info;
50e0d793
GH
677
678 // These describe the current module's PC address range
679 Dwarf_Addr module_start;
680 Dwarf_Addr module_end;
681
bd2b1e68 682 Dwarf_Die * cu;
20e4a32c 683 Dwarf_Die * function;
bd2b1e68
GH
684
685 string module_name;
686 string cu_name;
687 string function_name;
688
7a053d3b 689 string const default_name(char const * in,
78f6bba6 690 char const *)
bd2b1e68 691 {
7a053d3b 692 if (in)
bd2b1e68 693 return in;
a229fcd7 694 return string("");
bd2b1e68
GH
695 }
696
50e0d793 697
5f0a03a6 698 void get_module_dwarf(bool required = false, bool report = true)
5227f1ea 699 {
91af0778
FCE
700 module_dwarf = dwfl_module_getdwarf(module, &module_bias);
701 mod_info->dwarf_status = (module_dwarf ? info_present : info_absent);
5f0a03a6
JK
702 if (!module_dwarf && report)
703 {
704 string msg = "cannot find ";
705 if (module_name == "")
706 msg += "kernel";
707 else
708 msg += string("module ") + module_name;
709 msg += " debuginfo";
710
711 int i = dwfl_errno();
712 if (i)
713 msg += string(": ") + dwfl_errmsg (i);
714
715 if (required)
716 throw semantic_error (msg);
717 else
718 cerr << "WARNING: " << msg << "\n";
0ce64fb8 719 }
5227f1ea
GH
720 }
721
5f0a03a6 722 void focus_on_module(Dwfl_Module * m, module_info * mi)
bd2b1e68 723 {
bd2b1e68 724 module = m;
5f0a03a6
JK
725 mod_info = mi;
726 if (m)
727 {
728 module_name = default_name(dwfl_module_info(module, NULL,
50e0d793 729 &module_start, &module_end,
bd2b1e68
GH
730 NULL, NULL,
731 NULL, NULL),
732 "module");
5f0a03a6
JK
733 }
734 else
735 {
736 assert(mi && mi->name && mi->name == TOK_KERNEL);
737 module_name = mi->name;
738 module_start = 0;
739 module_end = 0;
740 module_bias = mi->bias;
741 }
50e0d793
GH
742
743 // Reset existing pointers and names
744
745 module_dwarf = NULL;
746
a229fcd7 747 cu_name.clear();
50e0d793
GH
748 cu = NULL;
749
a229fcd7 750 function_name.clear();
50e0d793 751 function = NULL;
bd2b1e68
GH
752 }
753
50e0d793 754
bd2b1e68
GH
755 void focus_on_cu(Dwarf_Die * c)
756 {
757 assert(c);
50e0d793
GH
758 assert(module);
759
bd2b1e68 760 cu = c;
50e0d793
GH
761 cu_name = default_name(dwarf_diename(c), "CU");
762
763 // Reset existing pointers and names
a229fcd7 764 function_name.clear();
50e0d793 765 function = NULL;
bd2b1e68
GH
766 }
767
50e0d793 768
20e4a32c 769 void focus_on_function(Dwarf_Die * f)
bd2b1e68
GH
770 {
771 assert(f);
50e0d793
GH
772 assert(module);
773 assert(cu);
774
bd2b1e68 775 function = f;
20e4a32c 776 function_name = default_name(dwarf_diename(function),
bd2b1e68 777 "function");
bd2b1e68
GH
778 }
779
50e0d793 780
bd2b1e68
GH
781 void focus_on_module_containing_global_address(Dwarf_Addr a)
782 {
783 assert(dwfl);
50e0d793 784 cu = NULL;
0ce64fb8
FCE
785 Dwfl_Module* mod = dwfl_addrmodule(dwfl, a);
786 if (mod) // address could be wildly out of range
5f0a03a6 787 focus_on_module(mod, NULL);
bd2b1e68
GH
788 }
789
50e0d793 790
7e1279ea 791 void query_cu_containing_global_address(Dwarf_Addr a, void *arg)
bd2b1e68 792 {
bd2b1e68 793 Dwarf_Addr bias;
50e0d793 794 assert(dwfl);
5227f1ea 795 get_module_dwarf();
ab55a5ae
FCE
796 Dwarf_Die* cudie = dwfl_module_addrdie(module, a, &bias);
797 if (cudie) // address could be wildly out of range
798 query_cu (cudie, arg);
bd2b1e68
GH
799 assert(bias == module_bias);
800 }
801
50e0d793 802
7e1279ea 803 void query_cu_containing_module_address(Dwarf_Addr a, void *arg)
bd2b1e68 804 {
7e1279ea 805 query_cu_containing_global_address(module_address_to_global(a), arg);
bd2b1e68
GH
806 }
807
50e0d793 808
bd2b1e68
GH
809 Dwarf_Addr module_address_to_global(Dwarf_Addr a)
810 {
50e0d793 811 assert(dwfl);
bd2b1e68 812 assert(module);
5227f1ea 813 get_module_dwarf();
76e954ca 814 if (module_name == TOK_KERNEL || dwfl_module_relocations (module) <= 0)
c239d28c 815 return a;
50e0d793 816 return a + module_start;
bd2b1e68
GH
817 }
818
50e0d793 819
bd2b1e68
GH
820 Dwarf_Addr global_address_to_module(Dwarf_Addr a)
821 {
822 assert(module);
5227f1ea 823 get_module_dwarf();
bd2b1e68
GH
824 return a - module_bias;
825 }
826
827
828 bool module_name_matches(string pattern)
829 {
bd2b1e68 830 bool t = (fnmatch(pattern.c_str(), module_name.c_str(), 0) == 0);
b8da0ad1 831 if (t && sess.verbose>3)
bd2b1e68 832 clog << "pattern '" << pattern << "' "
24cb178f 833 << "matches "
db22e55f 834 << "module '" << module_name << "'" << "\n";
bd2b1e68
GH
835 return t;
836 }
5f0a03a6
JK
837 bool name_has_wildcard(string pattern)
838 {
839 return (pattern.find('*') != string::npos ||
840 pattern.find('?') != string::npos ||
841 pattern.find('[') != string::npos);
842 }
b8da0ad1
FCE
843 bool module_name_final_match(string pattern)
844 {
845 // Assume module_name_matches(). Can there be any more matches?
846 // Not unless the pattern is a wildcard, since module names are
847 // presumed unique.
5f0a03a6 848 return !name_has_wildcard(pattern);
b8da0ad1 849 }
bd2b1e68 850
50e0d793 851
5f0a03a6 852 bool function_name_matches_pattern(string name, string pattern)
bd2b1e68 853 {
5f0a03a6 854 bool t = (fnmatch(pattern.c_str(), name.c_str(), 0) == 0);
b8da0ad1 855 if (t && sess.verbose>3)
bd2b1e68 856 clog << "pattern '" << pattern << "' "
24cb178f 857 << "matches "
5f0a03a6 858 << "function '" << name << "'" << "\n";
bd2b1e68
GH
859 return t;
860 }
5f0a03a6
JK
861 bool function_name_matches(string pattern)
862 {
863 assert(function);
864 return function_name_matches_pattern(function_name, pattern);
865 }
275f40a6
FCE
866 bool function_name_final_match(string pattern)
867 {
868 return module_name_final_match (pattern);
869 }
bd2b1e68 870
50e0d793 871
bd2b1e68
GH
872 bool cu_name_matches(string pattern)
873 {
874 assert(cu);
3213d089
FCE
875
876 // PR 5049: implicit * in front of given path pattern.
877 // NB: fnmatch() is used without FNM_PATHNAME.
79640c29 878 string prefixed_pattern = string("*/") + pattern;
3213d089 879
79640c29
FCE
880 bool t = (fnmatch(pattern.c_str(), cu_name.c_str(), 0) == 0 ||
881 fnmatch(prefixed_pattern.c_str(), cu_name.c_str(), 0) == 0);
b8da0ad1 882 if (t && sess.verbose>3)
3213d089 883 clog << "pattern '" << prefixed_pattern << "' "
24cb178f 884 << "matches "
db22e55f 885 << "CU '" << cu_name << "'" << "\n";
bd2b1e68
GH
886 return t;
887 }
888
5f0a03a6 889 dwflpp(systemtap_session & session)
bd2b1e68 890 :
5f0a03a6 891 sess(session),
bd2b1e68
GH
892 dwfl(NULL),
893 module(NULL),
894 module_dwarf(NULL),
895 module_bias(0),
5f0a03a6 896 mod_info(NULL),
50e0d793
GH
897 module_start(0),
898 module_end(0),
bd2b1e68
GH
899 cu(NULL),
900 function(NULL)
5f0a03a6 901 {
5f0a03a6 902 }
7a053d3b 903
50e0d793 904
b5e66ada
FCE
905 // XXX: See also translate.cxx:emit_symbol_data
906
7a24d422 907 void setup_kernel(bool debuginfo_needed = true)
bd2b1e68 908 {
405b71b8
FCE
909 if (! sess.module_cache)
910 sess.module_cache = new module_cache ();
911
0dc34322 912 static const char *debuginfo_path_arr = "+:.debug:/usr/lib/debug:build";
b5e66ada
FCE
913 static const char *debuginfo_env_arr = getenv("SYSTEMTAP_DEBUGINFO_PATH");
914 static const char *debuginfo_path = (debuginfo_env_arr ?: debuginfo_path_arr );
b5d77020 915
bd2b1e68
GH
916 static const Dwfl_Callbacks kernel_callbacks =
917 {
918 dwfl_linux_kernel_find_elf,
919 dwfl_standard_find_debuginfo,
b20febf3 920 dwfl_offline_section_address,
b5e66ada 921 (char **) & debuginfo_path
bd2b1e68
GH
922 };
923
7a24d422
FCE
924 dwfl = dwfl_begin (&kernel_callbacks);
925 if (!dwfl)
926 throw semantic_error ("cannot open dwfl");
927 dwfl_report_begin (dwfl);
06aca46a 928
b5e66ada
FCE
929 // We have a problem with -r REVISION vs -r BUILDDIR here. If
930 // we're running against a fedora/rhel style kernel-debuginfo
931 // tree, s.kernel_build_tree is not the place where the unstripped
932 // vmlinux will be installed. Rather, it's over yonder at
933 // /usr/lib/debug/lib/modules/$REVISION/. It seems that there is
934 // no way to set the dwfl_callback.debuginfo_path and always
935 // passs the plain kernel_release here. So instead we have to
936 // hard-code this magic here.
937 string elfutils_kernel_path;
938 if (sess.kernel_build_tree == string("/lib/modules/" + sess.kernel_release + "/build"))
939 elfutils_kernel_path = sess.kernel_release;
940 else
941 elfutils_kernel_path = sess.kernel_build_tree;
942
7a24d422 943 int rc = dwfl_linux_kernel_report_offline (dwfl,
b5e66ada 944 elfutils_kernel_path.c_str(),
91af0778 945 NULL);
06aca46a 946
7a24d422 947 if (debuginfo_needed)
b5e66ada
FCE
948 dwfl_assert (string("missing ") + sess.architecture +
949 string(" kernel/module debuginfo under '") +
950 sess.kernel_build_tree + string("'"),
7a24d422 951 rc);
06aca46a 952
7a24d422
FCE
953 // XXX: it would be nice if we could do a single
954 // ..._report_offline call for an entire systemtap script, so
955 // that a selection predicate would filter out modules outside
956 // the union of all the requested wildcards. But we build
957 // derived_probes one-by-one and we don't have lookahead.
958 // PR 3498.
06aca46a 959
7a24d422
FCE
960 // XXX: a special case: if we have only kernel.* probe points,
961 // we shouldn't waste time looking for module debug-info (and
962 // vice versa).
06aca46a 963
7a24d422
FCE
964 // NB: the result of an _offline call is the assignment of
965 // virtualized addresses to relocatable objects such as
966 // modules. These have to be converted to real addresses at
967 // run time. See the dwarf_derived_probe ctor and its caller.
968
969 dwfl_assert ("dwfl_report_end", dwfl_report_end(dwfl, NULL, NULL));
970 }
971
972 void setup_user(string module_name, bool debuginfo_needed = true)
973 {
dd22832a
JS
974 if (! sess.module_cache)
975 sess.module_cache = new module_cache ();
976
0dc34322 977 static const char *debuginfo_path_arr = "+:.debug:/usr/lib/debug:build";
b5e66ada
FCE
978 static const char *debuginfo_env_arr = getenv("SYSTEMTAP_DEBUGINFO_PATH");
979 // NB: kernel_build_tree doesn't enter into this, as it's for
980 // kernel-side modules only.
981 static const char *debuginfo_path = (debuginfo_env_arr ?: debuginfo_path_arr);
7a24d422
FCE
982
983 static const Dwfl_Callbacks user_callbacks =
bd2b1e68 984 {
7a24d422
FCE
985 NULL, /* dwfl_linux_kernel_find_elf, */
986 dwfl_standard_find_debuginfo,
987 dwfl_offline_section_address,
b5e66ada 988 (char **) & debuginfo_path
7a24d422 989 };
b20febf3 990
7a24d422
FCE
991 dwfl = dwfl_begin (&user_callbacks);
992 if (!dwfl)
993 throw semantic_error ("cannot open dwfl");
994 dwfl_report_begin (dwfl);
995
7a24d422 996 // XXX: should support buildid-based naming
405b71b8 997
7a24d422
FCE
998 Dwfl_Module *mod = dwfl_report_offline (dwfl,
999 module_name.c_str(),
1000 module_name.c_str(),
1001 -1);
1002 // XXX: save mod!
5f0a03a6 1003
7a24d422
FCE
1004 if (debuginfo_needed)
1005 dwfl_assert (string("missing process ") +
1006 module_name +
1007 string(" ") +
1008 sess.architecture +
1009 string(" debuginfo"),
1010 mod);
b20febf3 1011
f28a8c28
SC
1012 if (!module)
1013 module = mod;
1014
7a24d422
FCE
1015 // NB: the result of an _offline call is the assignment of
1016 // virtualized addresses to relocatable objects such as
1017 // modules. These have to be converted to real addresses at
1018 // run time. See the dwarf_derived_probe ctor and its caller.
bd2b1e68 1019
7e1279ea 1020 dwfl_assert ("dwfl_report_end", dwfl_report_end(dwfl, NULL, NULL));
bd2b1e68
GH
1021 }
1022
b8da0ad1
FCE
1023
1024
1025 // -----------------------------------------------------------------
1026
91af0778 1027 void iterate_over_modules(int (* callback)(Dwfl_Module *, void **,
5f0a03a6
JK
1028 const char *, Dwarf_Addr,
1029 void *),
c4ce66a1 1030 base_query *data)
5f0a03a6 1031 {
91af0778
FCE
1032 ptrdiff_t off = 0;
1033 do
b8da0ad1 1034 {
49abf162 1035 if (pending_interrupts) return;
91af0778 1036 off = dwfl_getmodules (dwfl, callback, data, off);
bd2b1e68 1037 }
91af0778
FCE
1038 while (off > 0);
1039 dwfl_assert("dwfl_getmodules", off == 0);
6f4c1275
FCE
1040
1041 // PR6864 XXX: For dwarfless case (if .../vmlinux is missing), then the
1042 // "kernel" module is not reported in the loop above. However, we
1043 // may be able to make do with symbol table data.
bd2b1e68
GH
1044 }
1045
91af0778 1046
5f0a03a6 1047 // Defined after dwarf_query
c4ce66a1 1048 void query_modules(base_query *q);
7e1279ea 1049
b8da0ad1
FCE
1050
1051 // -----------------------------------------------------------------
1052
1053 typedef map<Dwarf*, vector<Dwarf_Die>*> module_cu_cache_t;
1054 module_cu_cache_t module_cu_cache;
1055
7a053d3b 1056 void iterate_over_cus (int (*callback)(Dwarf_Die * die, void * arg),
bd2b1e68
GH
1057 void * data)
1058 {
0ce64fb8 1059 get_module_dwarf(false);
b8da0ad1
FCE
1060 Dwarf *dw = module_dwarf;
1061 if (!dw) return;
5227f1ea 1062
b8da0ad1
FCE
1063 vector<Dwarf_Die>* v = module_cu_cache[dw];
1064 if (v == 0)
1065 {
1066 v = new vector<Dwarf_Die>;
1067 module_cu_cache[dw] = v;
bd2b1e68 1068
b8da0ad1
FCE
1069 Dwarf_Off off = 0;
1070 size_t cuhl;
1071 Dwarf_Off noff;
1072 while (dwarf_nextcu (dw, off, &noff, &cuhl, NULL, NULL, NULL) == 0)
1073 {
49abf162 1074 if (pending_interrupts) return;
b8da0ad1
FCE
1075 Dwarf_Die die_mem;
1076 Dwarf_Die *die;
1077 die = dwarf_offdie (dw, off + cuhl, &die_mem);
1078 v->push_back (*die); /* copy */
1079 off = noff;
1080 }
1081 }
1082
1083 for (unsigned i = 0; i < v->size(); i++)
7a053d3b 1084 {
49abf162 1085 if (pending_interrupts) return;
b8da0ad1
FCE
1086 Dwarf_Die die = v->at(i);
1087 int rc = (*callback)(& die, data);
1088 if (rc != DWARF_CB_OK) break;
bd2b1e68
GH
1089 }
1090 }
1091
bd2b1e68 1092
b8da0ad1
FCE
1093 // -----------------------------------------------------------------
1094
7e1279ea 1095 bool func_is_inline()
bd2b1e68 1096 {
7e1279ea
FCE
1097 assert (function);
1098 return dwarf_func_inline (function) != 0;
bd2b1e68
GH
1099 }
1100
b8da0ad1
FCE
1101
1102 typedef map<string, vector<Dwarf_Die>*> cu_inl_function_cache_t;
1103 cu_inl_function_cache_t cu_inl_function_cache;
1104
1105 static int cu_inl_function_caching_callback (Dwarf_Die* func, void *arg)
1106 {
1107 vector<Dwarf_Die>* v = static_cast<vector<Dwarf_Die>*>(arg);
1108 v->push_back (* func);
1109 return DWARF_CB_OK;
1110 }
1111
7e1279ea
FCE
1112 void iterate_over_inline_instances (int (* callback)(Dwarf_Die * die, void * arg),
1113 void * data)
bd2b1e68 1114 {
7e1279ea
FCE
1115 assert (function);
1116 assert (func_is_inline ());
b8da0ad1
FCE
1117
1118 string key = module_name + ":" + cu_name + ":" + function_name;
1119 vector<Dwarf_Die>* v = cu_inl_function_cache[key];
1120 if (v == 0)
1121 {
1122 v = new vector<Dwarf_Die>;
1123 cu_inl_function_cache[key] = v;
1124 dwarf_func_inline_instances (function, cu_inl_function_caching_callback, v);
1125 }
1126
1127 for (unsigned i=0; i<v->size(); i++)
1128 {
f76427a2 1129 if (pending_interrupts) return;
b8da0ad1
FCE
1130 Dwarf_Die die = v->at(i);
1131 int rc = (*callback)(& die, data);
1132 if (rc != DWARF_CB_OK) break;
1133 }
4fa7b22b 1134 }
bd2b1e68 1135
50e0d793 1136
b8da0ad1
FCE
1137 // -----------------------------------------------------------------
1138
7bb73781 1139 /* The global alias cache is used to resolve any DIE found in a
0b8f6579
JB
1140 * module that is stubbed out with DW_AT_declaration with a defining
1141 * DIE found in a different module. The current assumption is that
1142 * this only applies to structures and unions, which have a global
1143 * namespace (it deliberately only traverses program scope), so this
1144 * cache is indexed by name. If other declaration lookups were
1145 * added to it, it would have to be indexed by name and tag
1146 */
7bb73781 1147 mod_cu_function_cache_t global_alias_cache;
0b8f6579
JB
1148 static int global_alias_caching_callback(Dwarf_Die *die, void *arg)
1149 {
7bb73781 1150 cu_function_cache_t *cache = static_cast<cu_function_cache_t*>(arg);
0b8f6579
JB
1151 const char *name = dwarf_diename(die);
1152
1153 if (!name)
1154 return DWARF_CB_OK;
1155
1156 string structure_name = name;
1157
1158 if (!dwarf_hasattr(die, DW_AT_declaration) &&
7bb73781
FCE
1159 cache->find(structure_name) == cache->end())
1160 (*cache)[structure_name] = *die;
0b8f6579
JB
1161
1162 return DWARF_CB_OK;
1163 }
1164
c4ce66a1 1165 Dwarf_Die *declaration_resolve(const char *name)
0b8f6579 1166 {
0b8f6579
JB
1167 if (!name)
1168 return NULL;
1169
7bb73781
FCE
1170 string key = module_name + ":" + cu_name;
1171 cu_function_cache_t *v = global_alias_cache[key];
1172 if (v == 0) // need to build the cache, just once per encountered module/cu
1173 {
1174 v = new cu_function_cache_t;
1175 global_alias_cache[key] = v;
1176 iterate_over_globals(global_alias_caching_callback, v);
1177 if (sess.verbose > 4)
1178 clog << "global alias cache " << key << " size " << v->size() << endl;
1179 }
1180
1181 // XXX: it may be desirable to search other modules' declarations
1182 // too, in case a module/shared-library processes a
1183 // forward-declared pointer type only, where the actual definition
1184 // may only be in vmlinux or the application.
1185
1186 // XXX: it is probably desirable to search other CU's declarations
1187 // in the same module.
41c262f3 1188
7bb73781 1189 if (v->find(name) == v->end())
0b8f6579
JB
1190 return NULL;
1191
7bb73781 1192 return & ((*v)[name]);
0b8f6579
JB
1193 }
1194
6561773f 1195 mod_cu_function_cache_t cu_function_cache;
b8da0ad1
FCE
1196
1197 static int cu_function_caching_callback (Dwarf_Die* func, void *arg)
1198 {
6561773f 1199 cu_function_cache_t* v = static_cast<cu_function_cache_t*>(arg);
0e68eaaa
DS
1200 const char *name = dwarf_diename(func);
1201 if (!name)
1202 return DWARF_CB_OK;
1203
1204 string function_name = name;
6561773f 1205 (*v)[function_name] = * func;
b8da0ad1
FCE
1206 return DWARF_CB_OK;
1207 }
1208
2da9cedb
JS
1209 int iterate_over_functions (int (* callback)(Dwarf_Die * func, base_query * q),
1210 base_query * q, const string& function,
1211 bool has_statement_num=false);
0b8f6579
JB
1212 int iterate_over_globals (int (* callback)(Dwarf_Die *, void *),
1213 void * data);
1214
fedd4090 1215 bool has_single_line_record (dwarf_query * q, char const * srcfile, int lineno);
897820ca 1216
7e1279ea 1217 void iterate_over_srcfile_lines (char const * srcfile,
879eb9e9 1218 int lines[2],
897820ca 1219 bool need_single_match,
879eb9e9 1220 enum line_t line_type,
86bf665e
TM
1221 void (* callback) (const dwarf_line_t& line,
1222 void * arg),
7e1279ea
FCE
1223 void *data)
1224 {
6315bd76
GH
1225 Dwarf_Line **srcsp = NULL;
1226 size_t nsrcs = 0;
fedd4090 1227 dwarf_query * q = static_cast<dwarf_query *>(data);
879eb9e9 1228 int lineno = lines[0];
558982c5 1229 auto_free_ref<Dwarf_Line**> free_srcsp(srcsp);
41c262f3 1230
7e1279ea 1231 get_module_dwarf();
bb788f9f 1232
41c262f3 1233 if (line_type == RELATIVE)
0c8b7d37
SC
1234 {
1235 Dwarf_Addr addr;
1236 Dwarf_Line *line;
1237 int line_number;
41c262f3 1238
0c8b7d37
SC
1239 dwarf_assert ("dwarf_entrypc", dwarf_entrypc (this->function, &addr));
1240 line = dwarf_getsrc_die (this->cu, addr);
1241 dwarf_assert ("dwarf_getsrc_die", line == NULL);
1242 dwarf_assert ("dwarf_lineno", dwarf_lineno (line, &line_number));
1243 lineno += line_number;
1244 }
879eb9e9
SC
1245 else if (line_type == WILDCARD)
1246 function_line (&lineno);
41c262f3 1247
879eb9e9
SC
1248 for (int l = lineno; ; l = l + 1)
1249 {
2ffc7958
SC
1250 set<int> lines_probed;
1251 pair<set<int>::iterator,bool> line_probed;
879eb9e9
SC
1252 dwarf_assert ("dwarf_getsrc_file",
1253 dwarf_getsrc_file (module_dwarf,
1254 srcfile, l, 0,
1255 &srcsp, &nsrcs));
879eb9e9
SC
1256 if (line_type == WILDCARD || line_type == RANGE)
1257 {
1258 Dwarf_Addr line_addr;
1259 dwarf_lineno (srcsp [0], &lineno);
2ffc7958 1260 line_probed = lines_probed.insert(lineno);
69087111 1261 if (lineno != l || line_probed.second == false || nsrcs > 1)
879eb9e9
SC
1262 continue;
1263 dwarf_lineaddr (srcsp [0], &line_addr);
1264 if (dwarf_haspc (function, line_addr) != 1)
1265 break;
1266 }
fedd4090 1267
879eb9e9 1268 // NB: Formerly, we used to filter, because:
20e4a32c 1269
879eb9e9
SC
1270 // dwarf_getsrc_file gets one *near hits* for line numbers, not
1271 // exact matches. For example, an existing file but a nonexistent
1272 // line number will be rounded up to the next definition in that
1273 // file. This may be similar to the GDB breakpoint algorithm, but
1274 // we don't want to be so fuzzy in systemtap land. So we filter.
847bf07f 1275
879eb9e9 1276 // But we now see the error of our ways, and skip this filtering.
fedd4090 1277
879eb9e9
SC
1278 // XXX: the code also fails to match e.g. inline function
1279 // definitions when the srcfile is a header file rather than the
1280 // CU name.
847bf07f 1281
879eb9e9 1282 size_t remaining_nsrcs = nsrcs;
847bf07f 1283
879eb9e9 1284 if (need_single_match && remaining_nsrcs > 1)
897820ca 1285 {
879eb9e9
SC
1286 // We wanted a single line record (a unique address for the
1287 // line) and we got a bunch of line records. We're going to
1288 // skip this probe (throw an exception) but before we throw
1289 // we're going to look around a bit to see if there's a low or
1290 // high line number nearby which *doesn't* have this problem,
1291 // so we can give the user some advice.
1292
1293 int lo_try = -1;
1294 int hi_try = -1;
1295 for (size_t i = 1; i < 6; ++i)
1296 {
1297 if (lo_try == -1 && has_single_line_record(q, srcfile, lineno - i))
1298 lo_try = lineno - i;
897820ca 1299
879eb9e9
SC
1300 if (hi_try == -1 && has_single_line_record(q, srcfile, lineno + i))
1301 hi_try = lineno + i;
1302 }
897820ca 1303
879eb9e9
SC
1304 stringstream advice;
1305 advice << "multiple addresses for " << srcfile << ":" << lineno;
1306 if (lo_try > 0 || hi_try > 0)
1307 {
1308 advice << " (try ";
1309 if (lo_try > 0)
1310 advice << srcfile << ":" << lo_try;
1311 if (lo_try > 0 && hi_try > 0)
1312 advice << " or ";
1313 if (hi_try > 0)
1314 advice << srcfile << ":" << hi_try;
1315 advice << ")";
1316 }
1317 throw semantic_error (advice.str());
1318 }
897820ca 1319
2e67a43b
TM
1320 for (size_t i = 0; i < nsrcs; ++i)
1321 {
1322 if (pending_interrupts) return;
1323 if (srcsp [i]) // skip over mismatched lines
1324 callback (dwarf_line_t(srcsp[i]), data);
1325 }
69087111
SC
1326
1327 if (line_type == ABSOLUTE || line_type == RELATIVE)
1328 break;
1329 else if (line_type == RANGE && l == lines[1])
1330 break;
20e4a32c 1331 }
50e0d793
GH
1332 }
1333
0f336e95
SC
1334 void
1335 iterate_over_cu_labels (string label_val, Dwarf_Die *cu, void *data,
1336 void (* callback)(const string &,
1337 const char *,
1338 int,
1339 Dwarf_Die *,
1340 Dwarf_Addr,
1341 dwarf_query *))
1342 {
1343 dwarf_query * q __attribute__ ((unused)) = static_cast<dwarf_query *>(data) ;
1344
1345 get_module_dwarf();
1346
1347 const char * sym = label_val.c_str();
1348 Dwarf_Die die;
3c1f71d5
MW
1349 int res = dwarf_child (cu, &die);
1350 if (res != 0)
1351 return; // die without children, bail out.
1352
0f336e95
SC
1353 static string function_name;
1354 do
1355 {
1356 Dwarf_Attribute attr_mem;
1357 Dwarf_Attribute *attr = dwarf_attr (&die, DW_AT_name, &attr_mem);
1358 int tag = dwarf_tag(&die);
1359 const char *name = dwarf_formstring (attr);
9e67aff9 1360 if (tag == DW_TAG_subprogram && name != 0)
0f336e95
SC
1361 {
1362 function_name = name;
1363 }
9e67aff9 1364 else if (tag == DW_TAG_label && name != 0
7b534f48 1365 && ((strncmp(name, sym, strlen(sym)) == 0)
0f336e95
SC
1366 || (name_has_wildcard (sym)
1367 && function_name_matches_pattern (name, sym))))
1368 {
1369 const char *file = dwarf_decl_file (&die);
7b534f48
SC
1370 // Get the line number for this label
1371 Dwarf_Attribute attr;
1372 dwarf_attr (&die,DW_AT_decl_line, &attr);
1373 Dwarf_Sword dline;
1374 dwarf_formsdata (&attr, &dline);
0f336e95
SC
1375 Dwarf_Addr stmt_addr;
1376 if (dwarf_lowpc (&die, &stmt_addr) != 0)
7b534f48
SC
1377 {
1378 // There is no lowpc so figure out the address
1379 // Get the real die for this cu
1380 Dwarf_Die cudie;
1381 dwarf_diecu (cu, &cudie, NULL, NULL);
1382 size_t nlines = 0;
1383 // Get the line for this label
1384 Dwarf_Line **aline;
1385 dwarf_getsrc_file (module_dwarf, file, (int)dline, 0, &aline, &nlines);
1386 // Get the address
1387 for (size_t i = 0; i < nlines; i++)
1388 {
1389 dwarf_lineaddr (*aline, &stmt_addr);
1390 if ((dwarf_haspc (&die, stmt_addr)))
1391 break;
1392 }
1393 }
1394
0f336e95
SC
1395 Dwarf_Die *scopes;
1396 int nscopes = 0;
1397 nscopes = dwarf_getscopes_die (&die, &scopes);
1398 if (nscopes > 1)
1399 callback(function_name.c_str(), file,
7b534f48 1400 (int)dline, &scopes[1], stmt_addr, q);
0f336e95
SC
1401 }
1402 if (dwarf_haschildren (&die) && tag != DW_TAG_structure_type
1403 && tag != DW_TAG_union_type)
1404 {
1405 iterate_over_cu_labels (label_val, &die, q, callback);
1406 }
1407 }
1408 while (dwarf_siblingof (&die, &die) == 0);
1409 }
1410
50e0d793 1411
7e1279ea
FCE
1412 void collect_srcfiles_matching (string const & pattern,
1413 set<char const *> & filtered_srcfiles)
50e0d793 1414 {
7e1279ea
FCE
1415 assert (module);
1416 assert (cu);
bb788f9f 1417
7e1279ea
FCE
1418 size_t nfiles;
1419 Dwarf_Files *srcfiles;
bb788f9f 1420
3213d089
FCE
1421 // PR 5049: implicit * in front of given path pattern.
1422 // NB: fnmatch() is used without FNM_PATHNAME.
79640c29 1423 string prefixed_pattern = string("*/") + pattern;
3213d089 1424
20e4a32c 1425 dwarf_assert ("dwarf_getsrcfiles",
7e1279ea
FCE
1426 dwarf_getsrcfiles (cu, &srcfiles, &nfiles));
1427 {
1428 for (size_t i = 0; i < nfiles; ++i)
50e0d793 1429 {
7e1279ea 1430 char const * fname = dwarf_filesrc (srcfiles, i, NULL, NULL);
79640c29
FCE
1431 if (fnmatch (pattern.c_str(), fname, 0) == 0 ||
1432 fnmatch (prefixed_pattern.c_str(), fname, 0) == 0)
50e0d793 1433 {
7e1279ea 1434 filtered_srcfiles.insert (fname);
b0ee93c4 1435 if (sess.verbose>2)
db22e55f 1436 clog << "selected source file '" << fname << "'\n";
50e0d793
GH
1437 }
1438 }
7e1279ea 1439 }
20e4a32c 1440 }
50e0d793 1441
3e961ba6 1442 void resolve_prologue_endings (func_info_map_t & funcs)
7d71e1d5
FCE
1443 {
1444 // This heuristic attempts to pick the first address that has a
34ca7d84
FCE
1445 // source line distinct from the function declaration's. In a
1446 // perfect world, this would be the first statement *past* the
1447 // prologue.
1448
7d71e1d5
FCE
1449 assert(module);
1450 assert(cu);
1451
456aa31c
FCE
1452 size_t nlines = 0;
1453 Dwarf_Lines *lines = NULL;
7d71e1d5 1454
dc223023
FCE
1455 /* trouble cases:
1456 malloc do_symlink in init/initramfs.c tail-recursive/tiny then no-prologue
1457 sys_get?id in kernel/timer.c no-prologue
1458 sys_exit_group tail-recursive
1459 {do_,}sys_open extra-long-prologue (gcc 3.4)
1460 cpu_to_logical_apicid NULL-decl_file
1461 */
1462
1463 // Fetch all srcline records, sorted by address.
20e4a32c
RM
1464 dwarf_assert ("dwarf_getsrclines",
1465 dwarf_getsrclines(cu, &lines, &nlines));
dc223023 1466 // XXX: free lines[] later, but how?
7d71e1d5 1467
3e961ba6 1468 for(func_info_map_t::iterator it = funcs.begin(); it != funcs.end(); it++)
7d71e1d5 1469 {
dc223023
FCE
1470#if 0 /* someday */
1471 Dwarf_Addr* bkpts = 0;
3e961ba6 1472 int n = dwarf_entry_breakpoints (& it->die, & bkpts);
dc223023
FCE
1473 // ...
1474 free (bkpts);
1475#endif
20e4a32c 1476
3e961ba6 1477 Dwarf_Addr entrypc = it->entrypc;
dc223023 1478 Dwarf_Addr highpc; // NB: highpc is exclusive: [entrypc,highpc)
3e961ba6 1479 dwfl_assert ("dwarf_highpc", dwarf_highpc (& it->die,
dc223023
FCE
1480 & highpc));
1481
3e961ba6 1482 if (it->decl_file == 0) it->decl_file = "";
e38d6504 1483
dc223023 1484 unsigned entrypc_srcline_idx = 0;
86bf665e 1485 dwarf_line_t entrypc_srcline;
dc223023
FCE
1486 // open-code binary search for exact match
1487 {
1488 unsigned l = 0, h = nlines;
1489 while (l < h)
1490 {
1491 entrypc_srcline_idx = (l + h) / 2;
86bf665e
TM
1492 const dwarf_line_t lr(dwarf_onesrcline(lines,
1493 entrypc_srcline_idx));
1494 Dwarf_Addr addr = lr.addr();
dc223023
FCE
1495 if (addr == entrypc) { entrypc_srcline = lr; break; }
1496 else if (l + 1 == h) { break; } // ran off bottom of tree
1497 else if (addr < entrypc) { l = entrypc_srcline_idx; }
1498 else { h = entrypc_srcline_idx; }
e38d6504 1499 }
dc223023 1500 }
86bf665e 1501 if (!entrypc_srcline)
dfa11ddb
FCE
1502 {
1503 if (sess.verbose > 2)
1504 clog << "missing entrypc dwarf line record for function '"
1505 << it->name << "'\n";
1506 // This is probably an inlined function. We'll end up using
1507 // its lowpc as a probe address.
1508 continue;
1509 }
dc223023
FCE
1510
1511 if (sess.verbose>2)
3e961ba6 1512 clog << "prologue searching function '" << it->name << "'"
5fe3e97f 1513 << " 0x" << hex << entrypc << "-0x" << highpc << dec
3e961ba6 1514 << "@" << it->decl_file << ":" << it->decl_line
dc223023
FCE
1515 << "\n";
1516
1517 // Now we go searching for the first line record that has a
1518 // file/line different from the one in the declaration.
1519 // Normally, this will be the next one. BUT:
1520 //
1521 // We may have to skip a few because some old compilers plop
1522 // in dummy line records for longer prologues. If we go too
1523 // far (addr >= highpc), we take the previous one. Or, it may
1524 // be the first one, if the function had no prologue, and thus
1525 // the entrypc maps to a statement in the body rather than the
1526 // declaration.
1527
1528 unsigned postprologue_srcline_idx = entrypc_srcline_idx;
1529 bool ranoff_end = false;
35f5f091 1530 while (postprologue_srcline_idx < nlines)
7d71e1d5 1531 {
86bf665e
TM
1532 dwarf_line_t lr(dwarf_onesrcline(lines, postprologue_srcline_idx));
1533 Dwarf_Addr postprologue_addr = lr.addr();
1534 const char* postprologue_file = lr.linesrc();
1535 int postprologue_lineno = lr.lineno();
456aa31c 1536
b0ee93c4 1537 if (sess.verbose>2)
dc223023
FCE
1538 clog << "checking line record 0x" << hex << postprologue_addr << dec
1539 << "@" << postprologue_file << ":" << postprologue_lineno << "\n";
1540
1541 if (postprologue_addr >= highpc)
e38d6504
RM
1542 {
1543 ranoff_end = true;
1544 postprologue_srcline_idx --;
dc223023
FCE
1545 continue;
1546 }
1547 if (ranoff_end ||
3e961ba6
JB
1548 (strcmp (postprologue_file, it->decl_file) || // We have a winner!
1549 (postprologue_lineno != it->decl_line)))
dc223023 1550 {
3e961ba6 1551 it->prologue_end = postprologue_addr;
dc223023
FCE
1552
1553 if (sess.verbose>2)
1554 {
3e961ba6 1555 clog << "prologue found function '" << it->name << "'";
dc223023
FCE
1556 // Add a little classification datum
1557 if (postprologue_srcline_idx == entrypc_srcline_idx) clog << " (naked)";
1558 if (ranoff_end) clog << " (tail-call?)";
1559 clog << " = 0x" << hex << postprologue_addr << dec << "\n";
1560 }
1561
1562 break;
1563 }
e38d6504 1564
dc223023
FCE
1565 // Let's try the next srcline.
1566 postprologue_srcline_idx ++;
1567 } // loop over srclines
7d71e1d5 1568
3e961ba6 1569 // if (strlen(it->decl_file) == 0) it->decl_file = NULL;
dc223023
FCE
1570
1571 } // loop over functions
b20febf3
FCE
1572
1573 // XXX: how to free lines?
bd2b1e68
GH
1574 }
1575
7e1279ea
FCE
1576
1577 bool function_entrypc (Dwarf_Addr * addr)
1578 {
1579 assert (function);
20e4a32c 1580 return (dwarf_entrypc (function, addr) == 0);
b8da0ad1 1581 // XXX: see also _lowpc ?
7e1279ea
FCE
1582 }
1583
1584
1585 bool die_entrypc (Dwarf_Die * die, Dwarf_Addr * addr)
1586 {
5bc4ac10
FCE
1587 int rc = 0;
1588 string lookup_method;
7e1279ea 1589
5bc4ac10
FCE
1590 * addr = 0;
1591
1592 lookup_method = "dwarf_entrypc";
1593 rc = dwarf_entrypc (die, addr);
1594
4baf0e53 1595 if (rc)
5bc4ac10
FCE
1596 {
1597 lookup_method = "dwarf_lowpc";
1598 rc = dwarf_lowpc (die, addr);
1599 }
1600
1601 if (rc)
1602 {
1603 lookup_method = "dwarf_ranges";
1604
1605 Dwarf_Addr base;
1606 Dwarf_Addr begin;
1607 Dwarf_Addr end;
1608 ptrdiff_t offset = dwarf_ranges (die, 0, &base, &begin, &end);
1609 if (offset < 0) rc = -1;
1610 else if (offset > 0)
1611 {
1612 * addr = begin;
1613 rc = 0;
1614
1615 // Now we need to check that there are no more ranges
1616 // associated with this function, which could conceivably
1617 // happen if a function is inlined, then pieces of it are
1618 // split amongst different conditional branches. It's not
1619 // obvious which of them to favour. As a heuristic, we
1620 // pick the beginning of the first range, and ignore the
1621 // others (but with a warning).
1622
1623 unsigned extra = 0;
1624 while ((offset = dwarf_ranges (die, offset, &base, &begin, &end)) > 0)
1625 extra ++;
1626 if (extra)
1627 lookup_method += ", ignored " + lex_cast<string>(extra) + " more";
1628 }
1629 }
4baf0e53 1630
5bc4ac10
FCE
1631 if (sess.verbose > 2)
1632 clog << "entry-pc lookup (" << lookup_method << ") = 0x" << hex << *addr << dec
4baf0e53 1633 << " (rc " << rc << ")"
5bc4ac10
FCE
1634 << endl;
1635 return (rc == 0);
7e1279ea
FCE
1636 }
1637
4cd232e4
GH
1638 void function_die (Dwarf_Die *d)
1639 {
1640 assert (function);
20e4a32c 1641 *d = *function;
4cd232e4 1642 }
7e1279ea 1643
4cd232e4 1644 void function_file (char const ** c)
7e1279ea
FCE
1645 {
1646 assert (function);
4cd232e4 1647 assert (c);
20e4a32c 1648 *c = dwarf_decl_file (function);
7e1279ea
FCE
1649 }
1650
4cd232e4 1651 void function_line (int *linep)
7e1279ea
FCE
1652 {
1653 assert (function);
20e4a32c 1654 dwarf_decl_line (function, linep);
7e1279ea
FCE
1655 }
1656
86bf665e 1657 bool die_has_pc (Dwarf_Die & die, Dwarf_Addr pc)
7e1279ea 1658 {
86bf665e 1659 int res = dwarf_haspc (&die, pc);
a688cff2
SC
1660 // dwarf_ranges will return -1 if a function die has no DW_AT_ranges
1661 // if (res == -1)
1662 // dwarf_assert ("dwarf_haspc", res);
7e1279ea
FCE
1663 return res == 1;
1664 }
1665
1666
78f6bba6 1667 static void loc2c_error (void *, const char *fmt, ...)
e36387d7 1668 {
78f6bba6
FCE
1669 const char *msg = "?";
1670 char *tmp = NULL;
5ce20b7a 1671 int rc;
e36387d7
RM
1672 va_list ap;
1673 va_start (ap, fmt);
78f6bba6
FCE
1674 rc = vasprintf (& tmp, fmt, ap);
1675 if (rc < 0)
1676 msg = "?";
1677 else
1678 msg = tmp;
e36387d7
RM
1679 va_end (ap);
1680 throw semantic_error (msg);
1681 }
bd2b1e68 1682
e664cf5b
FCE
1683 // This function generates code used for addressing computations of
1684 // target variables.
e38d6504
RM
1685 void emit_address (struct obstack *pool, Dwarf_Addr address)
1686 {
e664cf5b
FCE
1687 #if 0
1688 // The easy but incorrect way is to just print a hard-wired
1689 // constant.
e38d6504 1690 obstack_printf (pool, "%#" PRIx64 "UL", address);
e664cf5b 1691 #endif
e38d6504
RM
1692
1693 // Turn this address into a section-relative offset if it should be one.
1694 // We emit a comment approximating the variable+offset expression that
1695 // relocatable module probing code will need to have.
1696 Dwfl_Module *mod = dwfl_addrmodule (dwfl, address);
86bf665e 1697 dwfl_assert ("dwfl_addrmodule", mod);
e38d6504 1698 int n = dwfl_module_relocations (mod);
ba53ea9f 1699 dwfl_assert ("dwfl_module_relocations", n >= 0);
d64e82b1 1700 int i = dwfl_module_relocate_address (mod, &address);
ba53ea9f 1701 dwfl_assert ("dwfl_module_relocate_address", i >= 0);
d64e82b1
SD
1702 const char *modname = dwfl_module_info (mod, NULL, NULL, NULL,
1703 NULL, NULL, NULL, NULL);
86bf665e 1704 dwfl_assert ("dwfl_module_info", modname);
d64e82b1
SD
1705 const char *secname = dwfl_module_relocation_info (mod, i, NULL);
1706
1707 if (n > 0 && !(n == 1 && secname == NULL))
1708 {
ba53ea9f 1709 dwfl_assert ("dwfl_module_relocation_info", secname);
e38d6504 1710 if (n > 1 || secname[0] != '\0')
7e41d3dc
FCE
1711 {
1712 // This gives us the module name, and section name within the
1713 // module, for a kernel module (or other ET_REL module object).
1714 obstack_printf (pool, "({ static unsigned long addr = 0; ");
1715 obstack_printf (pool, "if (addr==0) addr = _stp_module_relocate (\"%s\",\"%s\",%#" PRIx64 "); ",
1716 modname, secname, address);
1717 obstack_printf (pool, "addr; })");
1718 }
4baf0e53 1719 else if (n == 1 && module_name == TOK_KERNEL && secname[0] == '\0')
21beacc9
FCE
1720 {
1721 // elfutils' way of telling us that this is a relocatable kernel address, which we
1722 // need to treat the same way here as dwarf_query::add_probe_point does: _stext.
1723 address -= sess.sym_stext;
1724 secname = "_stext";
1725 obstack_printf (pool, "({ static unsigned long addr = 0; ");
1726 obstack_printf (pool, "if (addr==0) addr = _stp_module_relocate (\"%s\",\"%s\",%#" PRIx64 "); ",
1727 modname, secname, address);
1728 obstack_printf (pool, "addr; })");
1729 }
e38d6504 1730 else
e664cf5b
FCE
1731 {
1732 throw semantic_error ("cannot relocate user-space dso (?) address");
1733#if 0
1734 // This would happen for a Dwfl_Module that's a user-level DSO.
1735 obstack_printf (pool, " /* %s+%#" PRIx64 " */",
1736 modname, address);
1737#endif
1738 }
e38d6504 1739 }
e664cf5b
FCE
1740 else
1741 obstack_printf (pool, "%#" PRIx64 "UL", address); // assume as constant
e38d6504 1742 }
7e1279ea 1743
4b1ad75e
RM
1744 static void loc2c_emit_address (void *arg, struct obstack *pool,
1745 Dwarf_Addr address)
1746 {
1747 dwflpp *dwfl = (dwflpp *) arg;
e38d6504 1748 dwfl->emit_address (pool, address);
4b1ad75e
RM
1749 }
1750
82e72903
DS
1751 void print_locals(Dwarf_Die *die, ostream &o)
1752 {
1753 // Try to get the first child of die.
82e72903
DS
1754 Dwarf_Die child;
1755 if (dwarf_child (die, &child) == 0)
1756 {
1757 do
1758 {
0e68eaaa 1759 const char *name;
82e72903
DS
1760 // Output each sibling's name (that is a variable or
1761 // parameter) to 'o'.
1762 switch (dwarf_tag (&child))
1763 {
1764 case DW_TAG_variable:
1765 case DW_TAG_formal_parameter:
0e68eaaa
DS
1766 name = dwarf_diename (&child);
1767 if (name)
1768 o << " " << name;
82e72903
DS
1769 break;
1770 default:
1771 break;
1772 }
1773 }
1774 while (dwarf_siblingof (&child, &child) == 0);
1775 }
82e72903
DS
1776 }
1777
e57b735a
GH
1778 Dwarf_Attribute *
1779 find_variable_and_frame_base (Dwarf_Die *scope_die,
20e4a32c 1780 Dwarf_Addr pc,
91eefb1c 1781 string const & local,
e57b735a
GH
1782 Dwarf_Die *vardie,
1783 Dwarf_Attribute *fb_attr_mem)
77de5e9e 1784 {
77de5e9e 1785 Dwarf_Die *scopes;
bcc12710 1786 int nscopes = 0;
e57b735a
GH
1787 Dwarf_Attribute *fb_attr = NULL;
1788
1789 assert (cu);
bcc12710 1790
f46d1b8a
SC
1791 nscopes = dwarf_getscopes (cu, pc, &scopes);
1792 int sidx;
1793 // if pc and scope_die are disjoint then we need dwarf_getscopes_die
1794 for (sidx = 0; sidx < nscopes; sidx++)
1795 if (scopes[sidx].addr == scope_die->addr)
1796 break;
1797 if (sidx == nscopes)
1798 nscopes = dwarf_getscopes_die (scope_die, &scopes);
77de5e9e 1799
955925b7 1800 if (nscopes <= 0)
77de5e9e 1801 {
7a053d3b 1802 throw semantic_error ("unable to find any scopes containing "
59ff2773 1803 + lex_cast_hex<string>(pc)
1c7643a9 1804 + ((scope_die == NULL) ? ""
0e68eaaa
DS
1805 : (string (" in ")
1806 + (dwarf_diename(scope_die) ?: "<unknown>")
1807 + "(" + (dwarf_diename(cu) ?: "<unknown>")
1808 + ")"))
77de5e9e
GH
1809 + " while searching for local '" + local + "'");
1810 }
7a053d3b 1811
77de5e9e 1812 int declaring_scope = dwarf_getscopevar (scopes, nscopes,
7a053d3b
RM
1813 local.c_str(),
1814 0, NULL, 0, 0,
e57b735a 1815 vardie);
77de5e9e
GH
1816 if (declaring_scope < 0)
1817 {
82e72903
DS
1818 stringstream alternatives;
1819 print_locals (scopes, alternatives);
77de5e9e 1820 throw semantic_error ("unable to find local '" + local + "'"
82e72903 1821 + " near pc " + lex_cast_hex<string>(pc)
1c7643a9 1822 + ((scope_die == NULL) ? ""
0e68eaaa
DS
1823 : (string (" in ")
1824 + (dwarf_diename(scope_die) ?: "<unknown>")
1825 + "(" + (dwarf_diename(cu) ?: "<unknown>")
1826 + ")"))
8215ea9a 1827 + (alternatives.str() == "" ? "" : (" (alternatives:" + alternatives.str () + ")")));
77de5e9e 1828 }
7a053d3b 1829
77de5e9e
GH
1830 for (int inner = 0; inner < nscopes; ++inner)
1831 {
1832 switch (dwarf_tag (&scopes[inner]))
1833 {
1834 default:
1835 continue;
1836 case DW_TAG_subprogram:
1837 case DW_TAG_entry_point:
1838 case DW_TAG_inlined_subroutine: /* XXX */
1839 if (inner >= declaring_scope)
1840 fb_attr = dwarf_attr_integrate (&scopes[inner],
1841 DW_AT_frame_base,
e57b735a 1842 fb_attr_mem);
77de5e9e
GH
1843 break;
1844 }
1845 }
e57b735a
GH
1846 return fb_attr;
1847 }
77de5e9e 1848
77de5e9e 1849
d1531387
RM
1850 struct location *
1851 translate_location(struct obstack *pool,
1852 Dwarf_Attribute *attr, Dwarf_Addr pc,
1853 Dwarf_Attribute *fb_attr,
1854 struct location **tail)
1855 {
1856 Dwarf_Op *expr;
1857 size_t len;
1858
67982217
FCE
1859 /* PR9768: formerly, we added pc+module_bias here. However, that bias value
1860 is not present in the pc value by the time we get it, so adding it would
1861 result in false negatives of variable reachibility. In other instances
1862 further below, the c_translate_FOO functions, the module_bias value used
1863 to be passed in, but instead should now be zero for the same reason. */
1864
1865 switch (dwarf_getlocation_addr (attr, pc /*+ module_bias*/, &expr, &len, 1))
d1531387
RM
1866 {
1867 case 1: /* Should always happen. */
1868 if (len > 0)
1869 break;
1870 /* Fall through. */
1871
1872 case 0: /* Shouldn't happen. */
1873 throw semantic_error ("not accessible at this address");
1874
1875 default: /* Shouldn't happen. */
1876 case -1:
1877 throw semantic_error (string ("dwarf_getlocation_addr failed") +
1878 string (dwarf_errmsg (-1)));
1879 }
1880
1881 return c_translate_location (pool, &loc2c_error, this,
1882 &loc2c_emit_address,
67982217 1883 1, 0 /* PR9768 */,
d1531387
RM
1884 pc, expr, len, tail, fb_attr);
1885 }
1886
82e72903
DS
1887 void
1888 print_members(Dwarf_Die *vardie, ostream &o)
1889 {
1890 const int typetag = dwarf_tag (vardie);
1891
1892 if (typetag != DW_TAG_structure_type && typetag != DW_TAG_union_type)
1893 {
1894 o << " Error: "
1895 << (dwarf_diename_integrate (vardie) ?: "<anonymous>")
1896 << " isn't a struct/union";
1897 return;
1898 }
1899
1900 // Try to get the first child of vardie.
1901 Dwarf_Die die_mem;
1902 Dwarf_Die *die = &die_mem;
1903 switch (dwarf_child (vardie, die))
1904 {
1905 case 1: // No children.
1906 o << ((typetag == DW_TAG_union_type) ? " union " : " struct ")
1907 << (dwarf_diename_integrate (die) ?: "<anonymous>")
1908 << " is empty";
1909 break;
1910
1911 case -1: // Error.
1912 default: // Shouldn't happen.
1913 o << ((typetag == DW_TAG_union_type) ? " union " : " struct ")
1914 << (dwarf_diename_integrate (die) ?: "<anonymous>")
1915 << ": " << dwarf_errmsg (-1);
1916 break;
1917
1918 case 0: // Success.
1919 break;
1920 }
1921
1922 // Output each sibling's name to 'o'.
1923 while (dwarf_tag (die) == DW_TAG_member)
1924 {
4b3b2cc7
PS
1925 const char *member = dwarf_diename_integrate (die) ;
1926
1927 if ( member != NULL )
4baf0e53 1928
4b3b2cc7
PS
1929 o << " " << member;
1930
1931 else
1932 {
1933 Dwarf_Die temp_die = *die;
1934 Dwarf_Attribute temp_attr ;
1935
1936 if (!dwarf_attr_integrate (&temp_die, DW_AT_type, &temp_attr))
1937 {
1938 clog<<"\n Error in obtaining type attribute for "
1939 <<(dwarf_diename(&temp_die)?:"<anonymous>");
1940 return ;
1941 }
1942
1943 if ( ! dwarf_formref_die (&temp_attr,&temp_die))
1944 {
1945 clog<<"\n Error in decoding type attribute for "
1946 <<(dwarf_diename(&temp_die)?:"<anonymous>");
1947 return ;
1948 }
1949 print_members(&temp_die,o);
1950
1951 }
82e72903
DS
1952
1953 if (dwarf_siblingof (die, &die_mem) != 0)
1954 break;
1955 }
1956 }
1957
e57b735a
GH
1958 Dwarf_Die *
1959 translate_components(struct obstack *pool,
20e4a32c
RM
1960 struct location **tail,
1961 Dwarf_Addr pc,
e57b735a
GH
1962 vector<pair<target_symbol::component_type,
1963 std::string> > const & components,
1964 Dwarf_Die *vardie,
1965 Dwarf_Die *die_mem,
1966 Dwarf_Attribute *attr_mem)
1967 {
c4ce66a1 1968 Dwarf_Die *die = die_mem;
82e72903 1969 Dwarf_Die struct_die;
4b3b2cc7
PS
1970 Dwarf_Attribute temp_attr;
1971
d9b516ca 1972 unsigned i = 0;
4b3b2cc7 1973
c4ce66a1
JS
1974 if (vardie)
1975 *die_mem = *vardie;
1976
4b3b2cc7
PS
1977 static unsigned int func_call_level ;
1978 static unsigned int dwarf_error_flag ; // indicates current error is dwarf error
1979 static unsigned int dwarf_error_count ; // keeps track of no of dwarf errors
1980 static semantic_error saved_dwarf_error("");
1981
d9b516ca
RM
1982 while (i < components.size())
1983 {
0301cfe7
FCE
1984 /* XXX: This would be desirable, but we don't get the target_symbol token,
1985 and printing that gives us the file:line number too early anyway. */
1986#if 0
1987 // Emit a marker to note which field is being access-attempted, to give
1988 // better error messages if deref() fails.
1989 string piece = string(...target_symbol token...) + string ("#") + stringify(components[i].second);
1990 obstack_printf (pool, "c->last_stmt = %s;", lex_cast_qstring(piece).c_str());
1991#endif
1992
d9b516ca
RM
1993 const int typetag = dwarf_tag (die);
1994 switch (typetag)
1995 {
1996 case DW_TAG_typedef:
fdfbe4f7
GH
1997 case DW_TAG_const_type:
1998 case DW_TAG_volatile_type:
d9b516ca
RM
1999 /* Just iterate on the referent type. */
2000 break;
91eefb1c 2001
d9b516ca
RM
2002 case DW_TAG_pointer_type:
2003 if (components[i].first == target_symbol::comp_literal_array_index)
2302c47e
FCE
2004 throw semantic_error ("cannot index pointer");
2005 // XXX: of course, we should support this the same way C does,
b0be9bdb 2006 // by explicit pointer arithmetic etc. PR4166.
91eefb1c 2007
67982217 2008 c_translate_pointer (pool, 1, 0 /* PR9768*/, die, tail);
d9b516ca 2009 break;
91eefb1c 2010
d9b516ca
RM
2011 case DW_TAG_array_type:
2012 if (components[i].first == target_symbol::comp_literal_array_index)
2013 {
67982217 2014 c_translate_array (pool, 1, 0 /* PR9768 */, die, tail,
d9b516ca
RM
2015 NULL, lex_cast<Dwarf_Word>(components[i].second));
2016 ++i;
2017 }
2018 else
2019 throw semantic_error("bad field '"
2020 + components[i].second
2021 + "' for array type");
2022 break;
91eefb1c 2023
d9b516ca
RM
2024 case DW_TAG_structure_type:
2025 case DW_TAG_union_type:
82e72903 2026 struct_die = *die;
0b8f6579
JB
2027 if (dwarf_hasattr(die, DW_AT_declaration))
2028 {
c4ce66a1 2029 Dwarf_Die *tmpdie = dwflpp::declaration_resolve(dwarf_diename(die));
0b8f6579
JB
2030 if (tmpdie == NULL)
2031 throw semantic_error ("unresolved struct "
2032 + string (dwarf_diename_integrate (die) ?: "<anonymous>"));
2033 *die_mem = *tmpdie;
2034 }
e57b735a 2035 switch (dwarf_child (die, die_mem))
d9b516ca
RM
2036 {
2037 case 1: /* No children. */
4b3b2cc7 2038 return NULL;
d9b516ca
RM
2039 case -1: /* Error. */
2040 default: /* Shouldn't happen */
2041 throw semantic_error (string (typetag == DW_TAG_union_type ? "union" : "struct")
2042 + string (dwarf_diename_integrate (die) ?: "<anonymous>")
2043 + string (dwarf_errmsg (-1)));
2044 break;
2045
2046 case 0:
2047 break;
2048 }
2049
2050 while (dwarf_tag (die) != DW_TAG_member
2051 || ({ const char *member = dwarf_diename_integrate (die);
2052 member == NULL || string(member) != components[i].second; }))
4b3b2cc7
PS
2053 {
2054 if ( dwarf_diename (die) == NULL ) // handling Anonymous structs/unions
2055 {
2056 Dwarf_Die temp_die = *die;
2057 Dwarf_Die temp_die_2;
2058
2059 try
2060 {
2061 if (!dwarf_attr_integrate (&temp_die, DW_AT_type, &temp_attr))
2062 {
2063 dwarf_error_flag ++ ;
2064 dwarf_error_count ++;
2065 throw semantic_error(" Error in obtaining type attribute for "+ string(dwarf_diename(&temp_die)?:"<anonymous>"));
2066 }
2067
2068 if ( !dwarf_formref_die (&temp_attr, &temp_die))
2069 {
2070 dwarf_error_flag ++ ;
2071 dwarf_error_count ++;
2072 throw semantic_error(" Error in decoding DW_AT_type attribute for " + string(dwarf_diename(&temp_die)?:"<anonymous>"));
2073 }
2074
2075 func_call_level ++ ;
2076
2077 Dwarf_Die *result_die = translate_components(pool, tail, pc, components, &temp_die, &temp_die_2, &temp_attr );
2078
2079 func_call_level -- ;
2080
2081 if (result_die != NULL)
2082 {
2083 memcpy(die_mem, &temp_die_2, sizeof(Dwarf_Die));
2084 memcpy(attr_mem, &temp_attr, sizeof(Dwarf_Attribute));
2085 return die_mem;
2086 }
2087 }
2088 catch (const semantic_error& e)
2089 {
2090 if ( !dwarf_error_flag ) //not a dwarf error
2091 throw;
2092 else
2093 {
2094 dwarf_error_flag = 0 ;
2095 saved_dwarf_error = e ;
2096 }
2097 }
2098 }
e57b735a 2099 if (dwarf_siblingof (die, die_mem) != 0)
4b3b2cc7
PS
2100 {
2101 if ( func_call_level == 0 && dwarf_error_count ) // this is parent call & a dwarf error has been reported in a branch somewhere
2102 throw semantic_error( saved_dwarf_error );
2103 else
2104 return NULL;
2105 }
2106 }
d9b516ca
RM
2107
2108 if (dwarf_attr_integrate (die, DW_AT_data_member_location,
e57b735a 2109 attr_mem) == NULL)
d9b516ca
RM
2110 {
2111 /* Union members don't usually have a location,
2112 but just use the containing union's location. */
2113 if (typetag != DW_TAG_union_type)
9f36b77f 2114 throw semantic_error ("no location for field '"
d9b516ca 2115 + components[i].second
9f36b77f 2116 + "' :" + string(dwarf_errmsg (-1)));
d9b516ca
RM
2117 }
2118 else
d1531387 2119 translate_location (pool, attr_mem, pc, NULL, tail);
d9b516ca
RM
2120 ++i;
2121 break;
2122
2123 case DW_TAG_base_type:
9f36b77f 2124 throw semantic_error ("field '"
d9b516ca 2125 + components[i].second
9f36b77f 2126 + "' vs. base type "
d9b516ca
RM
2127 + string(dwarf_diename_integrate (die) ?: "<anonymous type>"));
2128 break;
2129 case -1:
2130 throw semantic_error ("cannot find type: " + string(dwarf_errmsg (-1)));
2131 break;
2132
2133 default:
2134 throw semantic_error (string(dwarf_diename_integrate (die) ?: "<anonymous type>")
2135 + ": unexpected type tag "
2136 + lex_cast<string>(dwarf_tag (die)));
2137 break;
2138 }
2139
2140 /* Now iterate on the type in DIE's attribute. */
e57b735a 2141 if (dwarf_attr_integrate (die, DW_AT_type, attr_mem) == NULL)
d9b516ca 2142 throw semantic_error ("cannot get type of field: " + string(dwarf_errmsg (-1)));
c4ce66a1 2143 die = dwarf_formref_die (attr_mem, die_mem);
d9b516ca 2144 }
e57b735a
GH
2145 return die;
2146 }
91eefb1c 2147
d9b516ca 2148
e57b735a
GH
2149 Dwarf_Die *
2150 resolve_unqualified_inner_typedie (Dwarf_Die *typedie_mem,
2151 Dwarf_Attribute *attr_mem)
2152 {
2153 ;
d9b516ca 2154 Dwarf_Die *typedie;
e57b735a 2155 int typetag = 0;
d9b516ca 2156 while (1)
20e4a32c 2157 {
e57b735a 2158 typedie = dwarf_formref_die (attr_mem, typedie_mem);
d9b516ca 2159 if (typedie == NULL)
e57b735a 2160 throw semantic_error ("cannot get type: " + string(dwarf_errmsg (-1)));
d9b516ca 2161 typetag = dwarf_tag (typedie);
20e4a32c 2162 if (typetag != DW_TAG_typedef &&
fdfbe4f7
GH
2163 typetag != DW_TAG_const_type &&
2164 typetag != DW_TAG_volatile_type)
91eefb1c 2165 break;
e57b735a
GH
2166 if (dwarf_attr_integrate (typedie, DW_AT_type, attr_mem) == NULL)
2167 throw semantic_error ("cannot get type of pointee: " + string(dwarf_errmsg (-1)));
d9b516ca 2168 }
e57b735a
GH
2169 return typedie;
2170 }
91eefb1c 2171
91eefb1c 2172
20e4a32c 2173 void
e57b735a
GH
2174 translate_final_fetch_or_store (struct obstack *pool,
2175 struct location **tail,
2176 Dwarf_Addr module_bias,
2177 Dwarf_Die *die,
2178 Dwarf_Attribute *attr_mem,
2179 bool lvalue,
b8da0ad1
FCE
2180 string &,
2181 string &,
e57b735a
GH
2182 exp_type & ty)
2183 {
2184 /* First boil away any qualifiers associated with the type DIE of
2185 the final location to be accessed. */
fdfbe4f7 2186
e57b735a
GH
2187 Dwarf_Die typedie_mem;
2188 Dwarf_Die *typedie;
2189 int typetag;
022b623f
DS
2190 char const *dname;
2191 string diestr;
e57b735a
GH
2192
2193 typedie = resolve_unqualified_inner_typedie (&typedie_mem, attr_mem);
2194 typetag = dwarf_tag (typedie);
2195
2196 /* Then switch behavior depending on the type of fetch/store we
2197 want, and the type and pointer-ness of the final location. */
20e4a32c 2198
fdfbe4f7
GH
2199 switch (typetag)
2200 {
fdfbe4f7 2201 default:
022b623f
DS
2202 dname = dwarf_diename(die);
2203 diestr = (dname != NULL) ? dname : "<unknown>";
66d284f4 2204 throw semantic_error ("unsupported type tag "
022b623f
DS
2205 + lex_cast<string>(typetag)
2206 + " for " + diestr);
2207 break;
2208
2209 case DW_TAG_structure_type:
2210 case DW_TAG_union_type:
2211 dname = dwarf_diename(die);
2212 diestr = (dname != NULL) ? dname : "<unknown>";
2213 throw semantic_error ("struct/union '" + diestr
2214 + "' is being accessed instead of a member of the struct/union");
fdfbe4f7 2215 break;
66d284f4 2216
e7a012f0 2217 case DW_TAG_enumeration_type:
fdfbe4f7 2218 case DW_TAG_base_type:
00cf3709
FCE
2219
2220 // Reject types we can't handle in systemtap
2221 {
2222 dname = dwarf_diename(die);
2223 diestr = (dname != NULL) ? dname : "<unknown>";
2224
2225 Dwarf_Attribute encoding_attr;
6503a1cc 2226 Dwarf_Word encoding = (Dwarf_Word) -1;
00cf3709
FCE
2227 dwarf_formudata (dwarf_attr_integrate (typedie, DW_AT_encoding, &encoding_attr),
2228 & encoding);
2229 if (encoding < 0)
2230 {
2231 // clog << "bad type1 " << encoding << " diestr" << endl;
2232 throw semantic_error ("unsupported type (mystery encoding " + lex_cast<string>(encoding) + ")" +
2233 " for " + diestr);
2234 }
2235
2236 if (encoding == DW_ATE_float
2237 || encoding == DW_ATE_complex_float
2238 /* XXX || many others? */)
2239 {
2240 // clog << "bad type " << encoding << " diestr" << endl;
2241 throw semantic_error ("unsupported type (encoding " + lex_cast<string>(encoding) + ")" +
2242 " for " + diestr);
2243 }
2244 }
2245
fdfbe4f7 2246 ty = pe_long;
e57b735a 2247 if (lvalue)
67982217 2248 c_translate_store (pool, 1, 0 /* PR9768 */, die, typedie, tail,
e57b735a 2249 "THIS->value");
20e4a32c 2250 else
67982217 2251 c_translate_fetch (pool, 1, 0 /* PR9768 */, die, typedie, tail,
e57b735a 2252 "THIS->__retvalue");
fdfbe4f7
GH
2253 break;
2254
2255 case DW_TAG_array_type:
2256 case DW_TAG_pointer_type:
e57b735a 2257
b0be9bdb 2258 {
fdfbe4f7
GH
2259 Dwarf_Die pointee_typedie_mem;
2260 Dwarf_Die *pointee_typedie;
2261 Dwarf_Word pointee_encoding;
246b383e 2262 Dwarf_Word pointee_byte_size = 0;
fdfbe4f7 2263
e57b735a
GH
2264 pointee_typedie = resolve_unqualified_inner_typedie (&pointee_typedie_mem, attr_mem);
2265
2266 if (dwarf_attr_integrate (pointee_typedie, DW_AT_byte_size, attr_mem))
2267 dwarf_formudata (attr_mem, &pointee_byte_size);
20e4a32c
RM
2268
2269 dwarf_formudata (dwarf_attr_integrate (pointee_typedie, DW_AT_encoding, attr_mem),
fdfbe4f7
GH
2270 &pointee_encoding);
2271
b0be9bdb
FCE
2272 if (lvalue)
2273 {
2274 ty = pe_long;
2275 if (typetag == DW_TAG_array_type)
2276 throw semantic_error ("cannot write to array address");
2277 assert (typetag == DW_TAG_pointer_type);
67982217 2278 c_translate_pointer_store (pool, 1, 0 /* PR9768 */, typedie, tail,
b0be9bdb
FCE
2279 "THIS->value");
2280 }
2281 else
2282 {
2283 // We have the pointer: cast it to an integral type via &(*(...))
41c262f3 2284
b0be9bdb
FCE
2285 // NB: per bug #1187, at one point char*-like types were
2286 // automagically converted here to systemtap string values.
2287 // For several reasons, this was taken back out, leaving
2288 // pointer-to-string "conversion" (copying) to tapset functions.
41c262f3 2289
b0be9bdb
FCE
2290 ty = pe_long;
2291 if (typetag == DW_TAG_array_type)
67982217 2292 c_translate_array (pool, 1, 0 /* PR9768 */, typedie, tail, NULL, 0);
b0be9bdb 2293 else
67982217
FCE
2294 c_translate_pointer (pool, 1, 0 /* PR9768 */, typedie, tail);
2295 c_translate_addressof (pool, 1, 0 /* PR9768 */, NULL, pointee_typedie, tail,
b0be9bdb
FCE
2296 "THIS->__retvalue");
2297 }
2298 }
20e4a32c 2299 break;
fdfbe4f7 2300 }
20e4a32c 2301 }
e57b735a 2302
e19fda4e
DS
2303 string
2304 express_as_string (string prelude,
2305 string postlude,
2306 struct location *head)
2307 {
2308 size_t bufsz = 1024;
2309 char *buf = static_cast<char*>(malloc(bufsz));
2310 assert(buf);
2311
2312 FILE *memstream = open_memstream (&buf, &bufsz);
2313 assert(memstream);
2314
2315 fprintf(memstream, "{\n");
bec508de 2316 fprintf(memstream, "%s", prelude.c_str());
e19fda4e 2317 bool deref = c_emit_location (memstream, head, 1);
bec508de 2318 fprintf(memstream, "%s", postlude.c_str());
e19fda4e
DS
2319 fprintf(memstream, " goto out;\n");
2320
2321 // dummy use of deref_fault label, to disable warning if deref() not used
2322 fprintf(memstream, "if (0) goto deref_fault;\n");
2323
2324 // XXX: deref flag not reliable; emit fault label unconditionally
78f6bba6 2325 (void) deref;
e19fda4e
DS
2326 fprintf(memstream,
2327 "deref_fault:\n"
e19fda4e
DS
2328 " goto out;\n");
2329 fprintf(memstream, "}\n");
2330
2331 fclose (memstream);
2332 string result(buf);
2333 free (buf);
2334 return result;
2335 }
e57b735a 2336
20e4a32c 2337 string
e57b735a 2338 literal_stmt_for_local (Dwarf_Die *scope_die,
20e4a32c 2339 Dwarf_Addr pc,
e57b735a
GH
2340 string const & local,
2341 vector<pair<target_symbol::component_type,
2342 std::string> > const & components,
2343 bool lvalue,
2344 exp_type & ty)
2345 {
2346 Dwarf_Die vardie;
2347 Dwarf_Attribute fb_attr_mem, *fb_attr = NULL;
2348
20e4a32c 2349 fb_attr = find_variable_and_frame_base (scope_die, pc, local,
e57b735a
GH
2350 &vardie, &fb_attr_mem);
2351
b0ee93c4 2352 if (sess.verbose>2)
e57b735a 2353 clog << "finding location for local '" << local
12b44fb3
FCE
2354 << "' near address 0x" << hex << pc
2355 << ", module bias 0x" << module_bias << dec
db22e55f 2356 << "\n";
e57b735a
GH
2357
2358 Dwarf_Attribute attr_mem;
2359 if (dwarf_attr_integrate (&vardie, DW_AT_location, &attr_mem) == NULL)
2360 {
2361 throw semantic_error("failed to retrieve location "
20e4a32c
RM
2362 "attribute for local '" + local
2363 + "' (dieoffset: "
2364 + lex_cast_hex<string>(dwarf_dieoffset (&vardie))
e57b735a
GH
2365 + ")");
2366 }
2367
2368#define obstack_chunk_alloc malloc
2369#define obstack_chunk_free free
2370
2371 struct obstack pool;
2372 obstack_init (&pool);
2373 struct location *tail = NULL;
2374
2375 /* Given $foo->bar->baz[NN], translate the location of foo. */
2376
d1531387
RM
2377 struct location *head = translate_location (&pool,
2378 &attr_mem, pc, fb_attr, &tail);
e57b735a
GH
2379
2380 if (dwarf_attr_integrate (&vardie, DW_AT_type, &attr_mem) == NULL)
2381 throw semantic_error("failed to retrieve type "
2382 "attribute for local '" + local + "'");
2383
e57b735a
GH
2384 /* Translate the ->bar->baz[NN] parts. */
2385
2386 Dwarf_Die die_mem, *die = NULL;
c4ce66a1 2387 die = dwarf_formref_die (&attr_mem, &die_mem);
20e4a32c 2388 die = translate_components (&pool, &tail, pc, components,
c4ce66a1 2389 die, &die_mem, &attr_mem);
4b3b2cc7
PS
2390 if(!die)
2391 {
2392 die = dwarf_formref_die (&attr_mem, &vardie);
2393 stringstream alternatives;
a3de5d6e
MW
2394 if (die != NULL)
2395 print_members(die,alternatives);
b487a14d
FCE
2396 throw semantic_error("unable to find local '" + local + "'"
2397 + " near pc " + lex_cast_hex<string>(pc)
2398 + (alternatives.str() == "" ? "" : (" (alternatives:" + alternatives.str () + ")")));
4b3b2cc7 2399 }
e57b735a 2400
20e4a32c
RM
2401 /* Translate the assignment part, either
2402 x = $foo->bar->baz[NN]
2403 or
e57b735a
GH
2404 $foo->bar->baz[NN] = x
2405 */
2406
2407 string prelude, postlude;
20e4a32c 2408 translate_final_fetch_or_store (&pool, &tail, module_bias,
e57b735a
GH
2409 die, &attr_mem, lvalue,
2410 prelude, postlude, ty);
2411
2412 /* Write the translation to a string. */
e19fda4e
DS
2413 return express_as_string(prelude, postlude, head);
2414 }
20e4a32c 2415
20e4a32c 2416
e19fda4e
DS
2417 string
2418 literal_stmt_for_return (Dwarf_Die *scope_die,
2419 Dwarf_Addr pc,
2420 vector<pair<target_symbol::component_type,
2421 std::string> > const & components,
2422 bool lvalue,
2423 exp_type & ty)
2424 {
2425 if (sess.verbose>2)
2426 clog << "literal_stmt_for_return: finding return value for "
0e68eaaa 2427 << (dwarf_diename(scope_die) ?: "<unknown>")
e19fda4e 2428 << "("
0e68eaaa 2429 << (dwarf_diename(cu) ?: "<unknown>")
e19fda4e 2430 << ")\n";
7a053d3b 2431
e19fda4e
DS
2432 struct obstack pool;
2433 obstack_init (&pool);
2434 struct location *tail = NULL;
7a053d3b 2435
e19fda4e
DS
2436 /* Given $return->bar->baz[NN], translate the location of return. */
2437 const Dwarf_Op *locops;
2438 int nlocops = dwfl_module_return_value_location (module, scope_die,
2439 &locops);
2440 if (nlocops < 0)
2441 {
194c6687 2442 throw semantic_error("failed to retrieve return value location"
0e68eaaa
DS
2443 " for "
2444 + string(dwarf_diename(scope_die) ?: "<unknown>")
2445 + "(" + string(dwarf_diename(cu) ?: "<unknown>")
2446 + ")");
e19fda4e
DS
2447 }
2448 // the function has no return value (e.g. "void" in C)
2449 else if (nlocops == 0)
2450 {
0e68eaaa
DS
2451 throw semantic_error("function "
2452 + string(dwarf_diename(scope_die) ?: "<unknown>")
2453 + "(" + string(dwarf_diename(cu) ?: "<unknown>")
194c6687 2454 + ") has no return value");
e19fda4e 2455 }
a781f401 2456
e19fda4e
DS
2457 struct location *head = c_translate_location (&pool, &loc2c_error, this,
2458 &loc2c_emit_address,
67982217 2459 1, 0 /* PR9768 */,
e19fda4e
DS
2460 pc, locops, nlocops,
2461 &tail, NULL);
7a053d3b 2462
e19fda4e 2463 /* Translate the ->bar->baz[NN] parts. */
7a053d3b 2464
e19fda4e
DS
2465 Dwarf_Attribute attr_mem;
2466 Dwarf_Attribute *attr = dwarf_attr (scope_die, DW_AT_type, &attr_mem);
2467
2468 Dwarf_Die vardie_mem;
2469 Dwarf_Die *vardie = dwarf_formref_die (attr, &vardie_mem);
2470
2471 Dwarf_Die die_mem, *die = NULL;
2472 die = translate_components (&pool, &tail, pc, components,
2473 vardie, &die_mem, &attr_mem);
4b3b2cc7
PS
2474 if(!die)
2475 {
2476 die = dwarf_formref_die (&attr_mem, vardie);
2477 stringstream alternatives;
a3de5d6e
MW
2478 if (die != NULL)
2479 print_members(die,alternatives);
b487a14d
FCE
2480 throw semantic_error("unable to find return value"
2481 " near pc " + lex_cast_hex<string>(pc)
0e68eaaa
DS
2482 + " for "
2483 + string(dwarf_diename(scope_die) ?: "<unknown>")
2484 + "(" + string(dwarf_diename(cu) ?: "<unknown>")
2485 + ")"
b487a14d 2486 + (alternatives.str() == "" ? "" : (" (alternatives:" + alternatives.str () + ")")));
4b3b2cc7
PS
2487 }
2488
e19fda4e
DS
2489
2490 /* Translate the assignment part, either
2491 x = $return->bar->baz[NN]
2492 or
2493 $return->bar->baz[NN] = x
2494 */
2495
2496 string prelude, postlude;
2497 translate_final_fetch_or_store (&pool, &tail, module_bias,
2498 die, &attr_mem, lvalue,
2499 prelude, postlude, ty);
2500
2501 /* Write the translation to a string. */
2502 return express_as_string(prelude, postlude, head);
2503 }
7a053d3b 2504
77de5e9e 2505
c4ce66a1
JS
2506 string
2507 literal_stmt_for_pointer (Dwarf_Die *type_die,
2508 vector<pair<target_symbol::component_type,
2509 std::string> > const & components,
2510 bool lvalue,
2511 exp_type & ty)
2512 {
2513 if (sess.verbose>2)
2514 clog << "literal_stmt_for_pointer: finding value for "
2515 << (dwarf_diename(type_die) ?: "<unknown>")
2516 << "("
2517 << (dwarf_diename(cu) ?: "<unknown>")
2518 << ")\n";
2519
2520 struct obstack pool;
2521 obstack_init (&pool);
2522 struct location *head = c_translate_argument (&pool, &loc2c_error, this,
2523 &loc2c_emit_address,
2524 1, "THIS->pointer");
2525 struct location *tail = head;
2526
2527 /* Translate the ->bar->baz[NN] parts. */
2528
2529 Dwarf_Attribute attr_mem;
2530 Dwarf_Die die_mem, *die = NULL;
2531 die = translate_components (&pool, &tail, 0, components,
2532 type_die, &die_mem, &attr_mem);
2533 if(!die)
2534 {
2535 die = dwarf_formref_die (&attr_mem, &die_mem);
2536 stringstream alternatives;
2537 print_members(die ?: type_die, alternatives);
2538 throw semantic_error("unable to find member for struct "
2539 + string(dwarf_diename(die ?: type_die) ?: "<unknown>")
2540 + (alternatives.str() == "" ? "" : (" (alternatives:" + alternatives.str () + ")")));
2541 }
2542
2543
2544 /* Translate the assignment part, either
2545 x = (THIS->pointer)->bar->baz[NN]
2546 or
2547 (THIS->pointer)->bar->baz[NN] = x
2548 */
2549
2550 string prelude, postlude;
2551 translate_final_fetch_or_store (&pool, &tail, module_bias,
2552 die, &attr_mem, lvalue,
2553 prelude, postlude, ty);
2554
2555 /* Write the translation to a string. */
2556 return express_as_string(prelude, postlude, head);
2557 }
2558
2559
bd2b1e68
GH
2560 ~dwflpp()
2561 {
2562 if (dwfl)
2563 dwfl_end(dwfl);
2564 }
2565};
2566
405b71b8 2567
20c6c071 2568
7a053d3b 2569enum
bd2b1e68 2570function_spec_type
7a053d3b 2571 {
bd2b1e68
GH
2572 function_alone,
2573 function_and_file,
7a053d3b 2574 function_file_and_line
bd2b1e68
GH
2575 };
2576
ec4373ff 2577
bd2b1e68 2578struct dwarf_builder;
77de5e9e 2579
2930abc7 2580
b20febf3
FCE
2581// XXX: This class is a candidate for subclassing to separate
2582// the relocation vs non-relocation variants. Likewise for
2583// kprobe vs kretprobe variants.
2584
2585struct dwarf_derived_probe: public derived_probe
b55bc428 2586{
b20febf3
FCE
2587 dwarf_derived_probe (const string& function,
2588 const string& filename,
2589 int line,
2590 const string& module,
2591 const string& section,
2592 Dwarf_Addr dwfl_addr,
2930abc7 2593 Dwarf_Addr addr,
b20febf3
FCE
2594 dwarf_query & q,
2595 Dwarf_Die* scope_die);
20e4a32c 2596
b20febf3
FCE
2597 string module;
2598 string section;
2599 Dwarf_Addr addr;
2930abc7 2600 bool has_return;
c9bad430
DS
2601 bool has_maxactive;
2602 long maxactive_val;
b95e2b79 2603 bool access_vars;
2930abc7 2604
b8da0ad1 2605 void printsig (std::ostream &o) const;
b20febf3 2606 void join_group (systemtap_session& s);
9020300d
FCE
2607 void emit_probe_local_init(translator_output * o);
2608
bd2b1e68 2609 // Pattern registration helpers.
7a053d3b 2610 static void register_statement_variants(match_node * root,
bd2b1e68 2611 dwarf_builder * dw);
fd6602a0
FCE
2612 static void register_function_variants(match_node * root,
2613 dwarf_builder * dw);
7a053d3b 2614 static void register_function_and_statement_variants(match_node * root,
bd2b1e68 2615 dwarf_builder * dw);
c4ce66a1 2616 static void register_patterns(systemtap_session& s);
20c6c071
GH
2617};
2618
dc38c0ae 2619
6d0f3f0c
FCE
2620struct uprobe_derived_probe: public derived_probe
2621{
2622 bool return_p;
2623 string module; // * => unrestricted
2624 int pid; // 0 => unrestricted
2625 string section; // empty => absolute address
2626 Dwarf_Addr address;
2627 // bool has_maxactive;
2628 // long maxactive_val;
0973d815 2629
6d0f3f0c
FCE
2630 uprobe_derived_probe (const string& function,
2631 const string& filename,
2632 int line,
2633 const string& module,
2634 int pid,
2635 const string& section,
2636 Dwarf_Addr dwfl_addr,
2637 Dwarf_Addr addr,
2638 dwarf_query & q,
2639 Dwarf_Die* scope_die);
2640
0973d815
FCE
2641 // alternate constructor for process(PID).statement(ADDR).absolute
2642 uprobe_derived_probe (probe *base,
2643 probe_point *location,
2644 int pid,
2645 Dwarf_Addr addr,
2646 bool return_p);
2647
6d0f3f0c
FCE
2648 void printsig (std::ostream &o) const;
2649 void join_group (systemtap_session& s);
2650};
2651
2652
2653
dc38c0ae
DS
2654struct dwarf_derived_probe_group: public derived_probe_group
2655{
2656private:
b20febf3
FCE
2657 multimap<string,dwarf_derived_probe*> probes_by_module;
2658 typedef multimap<string,dwarf_derived_probe*>::iterator p_b_m_iterator;
dc38c0ae
DS
2659
2660public:
b20febf3
FCE
2661 void enroll (dwarf_derived_probe* probe);
2662 void emit_module_decls (systemtap_session& s);
2663 void emit_module_init (systemtap_session& s);
2664 void emit_module_exit (systemtap_session& s);
dc38c0ae
DS
2665};
2666
2667
20c6c071 2668// Helper struct to thread through the dwfl callbacks.
2c384610 2669struct base_query
20c6c071 2670{
c4ce66a1
JS
2671 base_query(dwflpp & dw, literal_map_t const & params);
2672 base_query(dwflpp & dw, const string & module_val);
2c384610 2673 virtual ~base_query() {}
bd2b1e68 2674
5227f1ea 2675 systemtap_session & sess;
2c384610 2676 dwflpp & dw;
5227f1ea 2677
bd2b1e68 2678 // Parameter extractors.
86bf665e 2679 static bool has_null_param(literal_map_t const & params,
888af770 2680 string const & k);
86bf665e 2681 static bool get_string_param(literal_map_t const & params,
bd2b1e68 2682 string const & k, string & v);
86bf665e 2683 static bool get_number_param(literal_map_t const & params,
bd2b1e68 2684 string const & k, long & v);
86bf665e 2685 static bool get_number_param(literal_map_t const & params,
c239d28c 2686 string const & k, Dwarf_Addr & v);
b55bc428 2687
2c384610
DS
2688 // Extracted parameters.
2689 bool has_kernel;
91af0778
FCE
2690 bool has_module;
2691 bool has_process;
2c384610
DS
2692 string module_val; // has_kernel => module_val = "kernel"
2693
2694 virtual void handle_query_module() = 0;
2695};
2696
2697
c4ce66a1
JS
2698base_query::base_query(dwflpp & dw, literal_map_t const & params):
2699 sess(dw.sess), dw(dw)
2c384610 2700{
91af0778 2701 has_kernel = has_null_param (params, TOK_KERNEL);
2c384610
DS
2702 if (has_kernel)
2703 module_val = "kernel";
91af0778
FCE
2704
2705 has_module = get_string_param (params, TOK_MODULE, module_val);
2706 if (has_module)
2707 has_process = false;
4baf0e53 2708 else
d0a7f5a9
FCE
2709 {
2710 has_process = get_string_param(params, TOK_PROCESS, module_val);
06aca46a 2711 if (has_process)
d0a7f5a9
FCE
2712 module_val = find_executable (module_val);
2713 }
91af0778
FCE
2714
2715 assert (has_kernel || has_process || has_module);
2c384610
DS
2716}
2717
c4ce66a1
JS
2718base_query::base_query(dwflpp & dw, const string & module_val)
2719 : sess(dw.sess), dw(dw), module_val(module_val)
2720{
2721 // NB: This uses '/' to distinguish between kernel modules and userspace,
2722 // which means that userspace modules won't get any PATH searching.
2723 if (module_val.find('/') == string::npos)
2724 {
2725 has_kernel = (module_val == TOK_KERNEL);
2726 has_module = !has_kernel;
2727 has_process = false;
2728 }
2729 else
2730 {
2731 has_kernel = has_module = false;
2732 has_process = true;
2733 }
2734}
2735
2c384610 2736bool
86bf665e 2737base_query::has_null_param(literal_map_t const & params,
2c384610
DS
2738 string const & k)
2739{
888af770 2740 return derived_probe_builder::has_null_param(params, k);
2c384610
DS
2741}
2742
2743
2744bool
86bf665e 2745base_query::get_string_param(literal_map_t const & params,
2c384610
DS
2746 string const & k, string & v)
2747{
2748 return derived_probe_builder::get_param (params, k, v);
2749}
2750
2751
2752bool
86bf665e 2753base_query::get_number_param(literal_map_t const & params,
2c384610
DS
2754 string const & k, long & v)
2755{
2756 int64_t value;
2757 bool present = derived_probe_builder::get_param (params, k, value);
2758 v = (long) value;
2759 return present;
2760}
2761
2762
2763bool
86bf665e 2764base_query::get_number_param(literal_map_t const & params,
2c384610
DS
2765 string const & k, Dwarf_Addr & v)
2766{
2767 int64_t value;
2768 bool present = derived_probe_builder::get_param (params, k, value);
2769 v = (Dwarf_Addr) value;
2770 return present;
2771}
2772
2c384610
DS
2773struct dwarf_query : public base_query
2774{
2775 dwarf_query(systemtap_session & sess,
2776 probe * base_probe,
2777 probe_point * base_loc,
2778 dwflpp & dw,
86bf665e 2779 literal_map_t const & params,
2c384610
DS
2780 vector<derived_probe *> & results);
2781
c4ce66a1
JS
2782 vector<derived_probe *> & results;
2783 probe * base_probe;
2784 probe_point * base_loc;
2785
2c384610 2786 virtual void handle_query_module();
5f0a03a6
JK
2787 void query_module_dwarf();
2788 void query_module_symtab();
2c384610 2789
2930abc7
FCE
2790 void add_probe_point(string const & funcname,
2791 char const * filename,
2792 int line,
2793 Dwarf_Die *scope_die,
2794 Dwarf_Addr addr);
d64e82b1 2795 string get_blacklist_section(Dwarf_Addr addr);
20c6c071 2796
a7301475
FCE
2797 regex_t blacklist_func; // function/statement probes
2798 regex_t blacklist_func_ret; // only for .return probes
2799 regex_t blacklist_file; // file name
0daad364
JS
2800 void build_blacklist();
2801
b20febf3
FCE
2802 bool blacklisted_p(const string& funcname,
2803 const string& filename,
36f9dd1d 2804 int line,
b20febf3
FCE
2805 const string& module,
2806 const string& section,
36f9dd1d
FCE
2807 Dwarf_Addr addr);
2808
2930abc7 2809 // Extracted parameters.
7a053d3b 2810 string function_val;
20c6c071
GH
2811
2812 bool has_function_str;
2813 bool has_statement_str;
2814 bool has_function_num;
2815 bool has_statement_num;
7a053d3b
RM
2816 string statement_str_val;
2817 string function_str_val;
c239d28c
GH
2818 Dwarf_Addr statement_num_val;
2819 Dwarf_Addr function_num_val;
20c6c071 2820
b8da0ad1
FCE
2821 bool has_call;
2822 bool has_inline;
20c6c071
GH
2823 bool has_return;
2824
c9bad430
DS
2825 bool has_maxactive;
2826 long maxactive_val;
2827
20c6c071
GH
2828 bool has_label;
2829 string label_val;
2830
2831 bool has_relative;
2832 long relative_val;
2833
37ebca01
FCE
2834 bool has_absolute;
2835
5f0a03a6
JK
2836 enum dbinfo_reqt dbinfo_reqt;
2837 enum dbinfo_reqt assess_dbinfo_reqt();
2838
20c6c071
GH
2839 function_spec_type parse_function_spec(string & spec);
2840 function_spec_type spec_type;
2841 string function;
2842 string file;
0c8b7d37 2843 line_t line_type;
879eb9e9 2844 int line[2];
5f0a03a6 2845 bool query_done; // Found exact match
20c6c071 2846
7e1279ea
FCE
2847 set<char const *> filtered_srcfiles;
2848
2849 // Map official entrypc -> func_info object
86bf665e
TM
2850 inline_instance_map_t filtered_inlines;
2851 func_info_map_t filtered_functions;
7e1279ea
FCE
2852 bool choose_next_line;
2853 Dwarf_Addr entrypc_for_next_line;
b55bc428
FCE
2854};
2855
98afd80e 2856
fedd4090
FCE
2857// This little test routine represents an unfortunate breakdown in
2858// abstraction between dwflpp (putatively, a layer right on top of
2859// elfutils), and dwarf_query (interpreting a systemtap probe point).
2860// It arises because we sometimes try to fix up slightly-off
2861// .statement() probes (something we find out in fairly low-level).
2862//
2cb3fe26 2863// An alternative would be to put some more intelligence into query_cu(),
4baf0e53 2864// and have it print additional suggestions after finding that
fedd4090
FCE
2865// q->dw.iterate_over_srcfile_lines resulted in no new finished_results.
2866
2867bool
2868dwflpp::has_single_line_record (dwarf_query * q, char const * srcfile, int lineno)
2869{
2870 if (lineno < 0)
2871 return false;
2872
2873 Dwarf_Line **srcsp = NULL;
2874 size_t nsrcs = 0;
2875
2876 dwarf_assert ("dwarf_getsrc_file",
2877 dwarf_getsrc_file (module_dwarf,
2878 srcfile, lineno, 0,
2879 &srcsp, &nsrcs));
2880
4baf0e53 2881 if (nsrcs != 1)
fedd4090
FCE
2882 {
2883 if (sess.verbose>4)
2884 clog << "alternative line " << lineno << " rejected: nsrcs=" << nsrcs << endl;
2885 return false;
2886 }
2887
2888 // We also try to filter out lines that leave the selected
2889 // functions (if any).
2890
86bf665e
TM
2891 dwarf_line_t line(srcsp[0]);
2892 Dwarf_Addr addr = line.addr();
fedd4090 2893
86bf665e 2894 for (func_info_map_t::iterator i = q->filtered_functions.begin();
fedd4090
FCE
2895 i != q->filtered_functions.end(); ++i)
2896 {
3e961ba6 2897 if (q->dw.die_has_pc (i->die, addr))
fedd4090
FCE
2898 {
2899 if (q->sess.verbose>4)
3e961ba6 2900 clog << "alternative line " << lineno << " accepted: fn=" << i->name << endl;
fedd4090
FCE
2901 return true;
2902 }
2903 }
2904
86bf665e 2905 for (inline_instance_map_t::iterator i = q->filtered_inlines.begin();
fedd4090
FCE
2906 i != q->filtered_inlines.end(); ++i)
2907 {
3e961ba6 2908 if (q->dw.die_has_pc (i->die, addr))
fedd4090
FCE
2909 {
2910 if (sess.verbose>4)
3e961ba6 2911 clog << "alternative line " << lineno << " accepted: ifn=" << i->name << endl;
fedd4090
FCE
2912 return true;
2913 }
2914 }
2915
2916 if (sess.verbose>4)
2917 clog << "alternative line " << lineno << " rejected: leaves selected fns" << endl;
2918 return false;
2919 }
2920
0b8f6579
JB
2921/* This basically only goes one level down from the compile unit so it
2922 * only picks up top level stuff (i.e. nothing in a lower scope) */
2923int
2924dwflpp::iterate_over_globals (int (* callback)(Dwarf_Die *, void *),
2925 void * data)
2926{
2927 int rc = DWARF_CB_OK;
2928 Dwarf_Die die;
2929
2930 assert (module);
2931 assert (cu);
2932 assert (dwarf_tag(cu) == DW_TAG_compile_unit);
2933
2934 if (dwarf_child(cu, &die) != 0)
2935 return rc;
2936
2937 do {
2938 /* We're only currently looking for structures and unions,
2939 * although other types of declarations exist */
2940 if (dwarf_tag(&die) != DW_TAG_structure_type &&
2941 dwarf_tag(&die) != DW_TAG_union_type)
2942 continue;
2943
2944 rc = (*callback)(&die, data);
2945 if (rc != DWARF_CB_OK)
2946 break;
2947
2948 } while (dwarf_siblingof(&die, &die) == 0);
2949
2950 return rc;
2951}
fedd4090 2952
6561773f 2953int
2da9cedb
JS
2954dwflpp::iterate_over_functions (int (* callback)(Dwarf_Die * func, base_query * q),
2955 base_query * q, const string& function,
2956 bool has_statement_num)
6561773f
FCE
2957{
2958 int rc = DWARF_CB_OK;
2959 assert (module);
2960 assert (cu);
41c262f3 2961
6561773f
FCE
2962 string key = module_name + ":" + cu_name;
2963 cu_function_cache_t *v = cu_function_cache[key];
2964 if (v == 0)
2965 {
2966 v = new cu_function_cache_t;
2967 cu_function_cache[key] = v;
2968 dwarf_getfuncs (cu, cu_function_caching_callback, v, 0);
2969 if (q->sess.verbose > 4)
2970 clog << "function cache " << key << " size " << v->size() << endl;
2971 }
41c262f3 2972
2da9cedb 2973 string subkey = function;
6561773f
FCE
2974 if (v->find(subkey) != v->end())
2975 {
2171f774 2976 Dwarf_Die die = v->find(subkey)->second;
6561773f
FCE
2977 if (q->sess.verbose > 4)
2978 clog << "function cache " << key << " hit " << subkey << endl;
2da9cedb 2979 return (*callback)(& die, q);
6561773f
FCE
2980 }
2981 else if (name_has_wildcard (subkey))
2982 {
2983 for (cu_function_cache_t::iterator it = v->begin(); it != v->end(); it++)
2984 {
f76427a2 2985 if (pending_interrupts) return DWARF_CB_ABORT;
6561773f
FCE
2986 string func_name = it->first;
2987 Dwarf_Die die = it->second;
2988 if (function_name_matches_pattern (func_name, subkey))
2989 {
2990 if (q->sess.verbose > 4)
2991 clog << "function cache " << key << " match " << func_name << " vs " << subkey << endl;
41c262f3 2992
2da9cedb 2993 rc = (*callback)(& die, q);
6561773f
FCE
2994 if (rc != DWARF_CB_OK) break;
2995 }
2996 }
2997 }
2da9cedb 2998 else if (has_statement_num) // searching all for kernel.statement
cf314c0f
WH
2999 {
3000 for (cu_function_cache_t::iterator it = v->begin(); it != v->end(); it++)
3001 {
3002 Dwarf_Die die = it->second;
2da9cedb 3003 rc = (*callback)(& die, q);
cf314c0f
WH
3004 if (rc != DWARF_CB_OK) break;
3005 }
3006 }
6561773f
FCE
3007 else // not a wildcard and no match in this CU
3008 {
3009 // do nothing
3010 }
3011 return rc;
3012}
3013
3014
fedd4090 3015
98afd80e 3016struct dwarf_builder: public derived_probe_builder
b55bc428 3017{
e38d6504 3018 dwflpp *kern_dw;
7a24d422 3019 map <string,dwflpp*> user_dw;
b8da0ad1 3020 dwarf_builder(): kern_dw(0) {}
aa30ccd3 3021
7a24d422
FCE
3022
3023 /* NB: not virtual, so can be called from dtor too: */
06aca46a 3024 void dwarf_build_no_more (bool verbose)
aa30ccd3
FCE
3025 {
3026 if (kern_dw)
3027 {
7a24d422
FCE
3028 if (verbose)
3029 clog << "dwarf_builder releasing kernel dwflpp" << endl;
aa30ccd3
FCE
3030 delete kern_dw;
3031 kern_dw = 0;
3032 }
7a24d422
FCE
3033
3034 for (map<string,dwflpp*>::iterator udi = user_dw.begin();
3035 udi != user_dw.end();
3036 udi ++)
3037 {
3038 if (verbose)
3039 clog << "dwarf_builder releasing user dwflpp " << udi->first << endl;
3040 delete udi->second;
3041 }
3042 user_dw.erase (user_dw.begin(), user_dw.end());
3043 }
3044
3045 void build_no_more (systemtap_session &s)
3046 {
3047 dwarf_build_no_more (s.verbose > 3);
aa30ccd3
FCE
3048 }
3049
e38d6504
RM
3050 ~dwarf_builder()
3051 {
7a24d422 3052 dwarf_build_no_more (false);
c8959a29 3053 }
aa30ccd3 3054
5227f1ea 3055 virtual void build(systemtap_session & sess,
7a053d3b 3056 probe * base,
20c6c071 3057 probe_point * location,
86bf665e 3058 literal_map_t const & parameters,
20c6c071 3059 vector<derived_probe *> & finished_results);
b55bc428
FCE
3060};
3061
888af770 3062
5227f1ea
GH
3063dwarf_query::dwarf_query(systemtap_session & sess,
3064 probe * base_probe,
20c6c071
GH
3065 probe_point * base_loc,
3066 dwflpp & dw,
86bf665e 3067 literal_map_t const & params,
20c6c071 3068 vector<derived_probe *> & results)
c4ce66a1
JS
3069 : base_query(dw, params), results(results),
3070 base_probe(base_probe), base_loc(base_loc)
bd2b1e68
GH
3071{
3072 // Reduce the query to more reasonable semantic values (booleans,
3073 // extracted strings, numbers, etc).
bd2b1e68
GH
3074 has_function_str = get_string_param(params, TOK_FUNCTION, function_str_val);
3075 has_function_num = get_number_param(params, TOK_FUNCTION, function_num_val);
3076
3077 has_statement_str = get_string_param(params, TOK_STATEMENT, statement_str_val);
3078 has_statement_num = get_number_param(params, TOK_STATEMENT, statement_num_val);
3079
0f336e95
SC
3080 has_label = get_string_param(params, TOK_LABEL, label_val);
3081
b8da0ad1
FCE
3082 has_call = has_null_param(params, TOK_CALL);
3083 has_inline = has_null_param(params, TOK_INLINE);
bd2b1e68 3084 has_return = has_null_param(params, TOK_RETURN);
c9bad430 3085 has_maxactive = get_number_param(params, TOK_MAXACTIVE, maxactive_val);
37ebca01
FCE
3086 has_absolute = has_null_param(params, TOK_ABSOLUTE);
3087
bd2b1e68
GH
3088 if (has_function_str)
3089 spec_type = parse_function_spec(function_str_val);
3090 else if (has_statement_str)
3091 spec_type = parse_function_spec(statement_str_val);
0daad364 3092
b8da0ad1 3093 build_blacklist(); // XXX: why not reuse amongst dwarf_query instances?
5f0a03a6
JK
3094 dbinfo_reqt = assess_dbinfo_reqt();
3095 query_done = false;
0daad364
JS
3096}
3097
3098
2c384610 3099void
5f0a03a6 3100dwarf_query::query_module_dwarf()
2c384610
DS
3101{
3102 if (has_function_num || has_statement_num)
3103 {
3104 // If we have module("foo").function(0xbeef) or
3105 // module("foo").statement(0xbeef), the address is relative
3106 // to the start of the module, so we seek the function
3107 // number plus the module's bias.
3108
3109 Dwarf_Addr addr;
3110 if (has_function_num)
3111 addr = function_num_val;
3112 else
3113 addr = statement_num_val;
4baf0e53 3114
2c384610
DS
3115 // NB: we don't need to add the module base address or bias
3116 // value here (for reasons that may be coincidental).
3117 dw.query_cu_containing_module_address(addr, this);
3118 }
3119 else
3120 {
3121 // Otherwise if we have a function("foo") or statement("foo")
3122 // specifier, we have to scan over all the CUs looking for
3123 // the function(s) in question
3124 assert(has_function_str || has_statement_str);
3125 dw.iterate_over_cus(&query_cu, this);
3126 }
3127}
3128
5f0a03a6
JK
3129static void query_func_info (Dwarf_Addr entrypc, func_info & fi,
3130 dwarf_query * q);
3131
3132void
3133dwarf_query::query_module_symtab()
3134{
3135 // Get the symbol table if it's necessary, sufficient, and not already got.
3136 if (dbinfo_reqt == dbr_need_dwarf)
3137 return;
3138
3139 module_info *mi = dw.mod_info;
3140 if (dbinfo_reqt == dbr_need_symtab)
3141 {
3142 if (mi->symtab_status == info_unknown)
3143 mi->get_symtab(this);
3144 if (mi->symtab_status == info_absent)
3145 return;
3146 }
3147
3148 func_info *fi = NULL;
3149 symbol_table *sym_table = mi->sym_table;
3150
3151 if (has_function_str)
3152 {
3153 // Per dwarf_query::assess_dbinfo_reqt()...
3154 assert(spec_type == function_alone);
3155 if (dw.name_has_wildcard(function_str_val))
3156 {
3157 // Until we augment the blacklist sufficently...
3158 if (function_str_val.find_first_not_of("*?") == string::npos)
3159 {
3160 // e.g., kernel.function("*")
3161 cerr << "Error: Pattern '"
3162 << function_str_val
3163 << "' matches every instruction address in the symbol table,"
3164 << endl
3165 << "some of which aren't even functions."
3166 << " Please be more precise."
3167 << endl;
3168 return;
3169 }
2e67a43b
TM
3170 symbol_table::iterator_t iter;
3171 for (iter = sym_table->list_by_addr.begin();
3172 iter != sym_table->list_by_addr.end();
3173 ++iter)
5f0a03a6 3174 {
2e67a43b 3175 fi = *iter;
5f0a03a6
JK
3176 if (!null_die(&fi->die))
3177 continue; // already handled in query_module_dwarf()
3178 if (dw.function_name_matches_pattern(fi->name, function_str_val))
3179 query_func_info(fi->addr, *fi, this);
3180 }
3181 }
3182 else
3183 {
3184 fi = sym_table->lookup_symbol(function_str_val);
3185 if (fi && null_die(&fi->die))
3186 query_func_info(fi->addr, *fi, this);
3187 }
3188 }
3189 else
3190 {
3191 assert(has_function_num || has_statement_num);
3192 // Find the "function" in which the indicated address resides.
3193 Dwarf_Addr addr =
3194 (has_function_num ? function_num_val : statement_num_val);
3195 fi = sym_table->get_func_containing_address(addr);
3196 if (!fi)
3197 {
3198 cerr << "Warning: address "
3199 << hex << addr << dec
3200 << " out of range for module "
3201 << dw.module_name;
3202 return;
3203 }
3204 if (!null_die(&fi->die))
3205 {
3206 // addr looks like it's in the compilation unit containing
3207 // the indicated function, but query_module_dwarf() didn't
3208 // match addr to any compilation unit, so addr must be
3209 // above that cu's address range.
3210 cerr << "Warning: address "
3211 << hex << addr << dec
3212 << " maps to no known compilation unit in module "
3213 << dw.module_name;
3214 return;
3215 }
3216 query_func_info(fi->addr, *fi, this);
3217 }
3218}
3219
3220void
3221dwarf_query::handle_query_module()
3222{
3223 dw.get_module_dwarf(false,
3224 (dbinfo_reqt == dbr_need_dwarf || !sess.consult_symtab));
3225 if (dw.mod_info->dwarf_status == info_present)
3226 query_module_dwarf();
3227 // Consult the symbol table if we haven't found all we're looking for.
3228 // asm functions can show up in the symbol table but not in dwarf.
3229 if (sess.consult_symtab && !query_done)
3230 query_module_symtab();
3231}
3232
2c384610 3233
0daad364
JS
3234void
3235dwarf_query::build_blacklist()
3236{
91af0778
FCE
3237 // No blacklist for userspace.
3238 if (has_process)
3239 return;
3240
a7301475
FCE
3241 // We build up the regexps in these strings
3242
3243 // Add ^ anchors at the front; $ will be added just before regcomp.
3244
a7301475
FCE
3245 string blfn = "^(";
3246 string blfn_ret = "^(";
3247 string blfile = "^(";
3248
e4c58386 3249 blfile += "kernel/kprobes.c"; // first alternative, no "|"
a7301475 3250 blfile += "|arch/.*/kernel/kprobes.c";
275a898f 3251 // Older kernels need ...
02a929d1 3252 blfile += "|include/asm/io.h";
275a898f
AM
3253 blfile += "|include/asm/bitops.h";
3254 // While newer ones need ...
3255 blfile += "|arch/.*/include/asm/io.h";
3256 blfile += "|arch/.*/include/asm/bitops.h";
02a929d1 3257 blfile += "|drivers/ide/ide-iops.c";
a7301475
FCE
3258
3259 // XXX: it would be nice if these blacklisted functions were pulled
3260 // in dynamically, instead of being statically defined here.
49f426d9
FCE
3261 // Perhaps it could be populated from script files. A "noprobe
3262 // kernel.function("...")" construct might do the trick.
0daad364 3263
b20febf3 3264 // Most of these are marked __kprobes in newer kernels. We list
a7301475
FCE
3265 // them here (anyway) so the translator can block them on older
3266 // kernels that don't have the __kprobes function decorator. This
3267 // also allows detection of problems at translate- rather than
3268 // run-time.
3269
e4c58386 3270 blfn += "atomic_notifier_call_chain"; // first blfn; no "|"
a7301475
FCE
3271 blfn += "|default_do_nmi";
3272 blfn += "|__die";
3273 blfn += "|die_nmi";
3274 blfn += "|do_debug";
3275 blfn += "|do_general_protection";
3276 blfn += "|do_int3";
3277 blfn += "|do_IRQ";
3278 blfn += "|do_page_fault";
3279 blfn += "|do_sparc64_fault";
3280 blfn += "|do_trap";
3281 blfn += "|dummy_nmi_callback";
3282 blfn += "|flush_icache_range";
3283 blfn += "|ia64_bad_break";
3284 blfn += "|ia64_do_page_fault";
3285 blfn += "|ia64_fault";
3286 blfn += "|io_check_error";
3287 blfn += "|mem_parity_error";
3288 blfn += "|nmi_watchdog_tick";
3289 blfn += "|notifier_call_chain";
3290 blfn += "|oops_begin";
3291 blfn += "|oops_end";
3292 blfn += "|program_check_exception";
3293 blfn += "|single_step_exception";
3294 blfn += "|sync_regs";
3295 blfn += "|unhandled_fault";
3296 blfn += "|unknown_nmi_error";
3297
3298 // Lots of locks
3299 blfn += "|.*raw_.*lock.*";
3300 blfn += "|.*read_.*lock.*";
3301 blfn += "|.*write_.*lock.*";
3302 blfn += "|.*spin_.*lock.*";
3303 blfn += "|.*rwlock_.*lock.*";
3304 blfn += "|.*rwsem_.*lock.*";
3305 blfn += "|.*mutex_.*lock.*";
3306 blfn += "|raw_.*";
3307 blfn += "|.*seq_.*lock.*";
3308
a11f4bae 3309 // atomic functions
2ca12712
JS
3310 blfn += "|atomic_.*";
3311 blfn += "|atomic64_.*";
a11f4bae
SD
3312
3313 // few other problematic cases
3314 blfn += "|get_bh";
3315 blfn += "|put_bh";
3316
a7301475
FCE
3317 // Experimental
3318 blfn += "|.*apic.*|.*APIC.*";
3319 blfn += "|.*softirq.*";
3320 blfn += "|.*IRQ.*";
3321 blfn += "|.*_intr.*";
3322 blfn += "|__delay";
3323 blfn += "|.*kernel_text.*";
3324 blfn += "|get_current";
3325 blfn += "|current_.*";
3326 blfn += "|.*exception_tables.*";
3327 blfn += "|.*setup_rt_frame.*";
c931ec8a 3328
a8c9be6f 3329 // PR 5759, CONFIG_PREEMPT kernels
a7301475
FCE
3330 blfn += "|.*preempt_count.*";
3331 blfn += "|preempt_schedule";
a8c9be6f 3332
e4c58386
FCE
3333 // These functions don't return, so return probes would never be recovered
3334 blfn_ret += "do_exit"; // no "|"
3335 blfn_ret += "|sys_exit";
3336 blfn_ret += "|sys_exit_group";
3337
a721fbcf
MH
3338 // __switch_to changes "current" on x86_64 and i686, so return probes
3339 // would cause kernel panic, and it is marked as "__kprobes" on x86_64
0daad364 3340 if (sess.architecture == "x86_64")
a7301475 3341 blfn += "|__switch_to";
a721fbcf 3342 if (sess.architecture == "i686")
a7301475 3343 blfn_ret += "|__switch_to";
0daad364 3344
a7301475
FCE
3345 blfn += ")$";
3346 blfn_ret += ")$";
3347 blfile += ")$";
3348
41c262f3 3349 if (sess.verbose > 2)
e4c58386
FCE
3350 {
3351 clog << "blacklist regexps:" << endl;
3352 clog << "blfn: " << blfn << endl;
3353 clog << "blfn_ret: " << blfn_ret << endl;
3354 clog << "blfile: " << blfile << endl;
3355 }
3356
a7301475
FCE
3357 int rc = regcomp (& blacklist_func, blfn.c_str(), REG_NOSUB|REG_EXTENDED);
3358 if (rc) throw semantic_error ("blacklist_func regcomp failed");
3359 rc = regcomp (& blacklist_func_ret, blfn_ret.c_str(), REG_NOSUB|REG_EXTENDED);
3360 if (rc) throw semantic_error ("blacklist_func_ret regcomp failed");
3361 rc = regcomp (& blacklist_file, blfile.c_str(), REG_NOSUB|REG_EXTENDED);
3362 if (rc) throw semantic_error ("blacklist_file regcomp failed");
7a053d3b 3363}
bd2b1e68
GH
3364
3365
bd2b1e68 3366function_spec_type
20c6c071 3367dwarf_query::parse_function_spec(string & spec)
bd2b1e68
GH
3368{
3369 string::const_iterator i = spec.begin(), e = spec.end();
7a053d3b 3370
bd2b1e68
GH
3371 function.clear();
3372 file.clear();
879eb9e9
SC
3373 line[0] = 0;
3374 line[1] = 0;
bd2b1e68
GH
3375
3376 while (i != e && *i != '@')
3377 {
0c8b7d37 3378 if (*i == ':' || *i == '+')
bd2b1e68
GH
3379 goto bad;
3380 function += *i++;
3381 }
3382
3383 if (i == e)
3384 {
b0ee93c4 3385 if (sess.verbose>2)
7a053d3b
RM
3386 clog << "parsed '" << spec
3387 << "' -> func '" << function
db22e55f 3388 << "'\n";
bd2b1e68
GH
3389 return function_alone;
3390 }
3391
3392 if (i++ == e)
3393 goto bad;
3394
0c8b7d37 3395 while (i != e && *i != ':' && *i != '+')
bd2b1e68 3396 file += *i++;
41c262f3 3397 if (*i == ':')
879eb9e9
SC
3398 {
3399 if (*(i + 1) == '*')
3400 line_type = WILDCARD;
3401 else
3402 line_type = ABSOLUTE;
3403 }
0c8b7d37
SC
3404 else if (*i == '+')
3405 line_type = RELATIVE;
7a053d3b 3406
bd2b1e68
GH
3407 if (i == e)
3408 {
b0ee93c4 3409 if (sess.verbose>2)
7a053d3b
RM
3410 clog << "parsed '" << spec
3411 << "' -> func '"<< function
3412 << "', file '" << file
db22e55f 3413 << "'\n";
bd2b1e68
GH
3414 return function_and_file;
3415 }
3416
3417 if (i++ == e)
3418 goto bad;
3419
3420 try
3421 {
879eb9e9
SC
3422 if (line_type != WILDCARD)
3423 {
3424 string::const_iterator dash = i;
41c262f3 3425
879eb9e9
SC
3426 while (dash != e && *dash != '-')
3427 dash++;
3428 if (dash == e)
3429 line[0] = line[1] = lex_cast<int>(string(i, e));
3430 else
3431 {
3432 line_type = RANGE;
3433 line[0] = lex_cast<int>(string(i, dash));
3434 line[1] = lex_cast<int>(string(dash + 1, e));
3435 }
3436 }
41c262f3 3437
b0ee93c4 3438 if (sess.verbose>2)
7a053d3b
RM
3439 clog << "parsed '" << spec
3440 << "' -> func '"<< function
3441 << "', file '" << file
db22e55f 3442 << "', line " << line << "\n";
bd2b1e68
GH
3443 return function_file_and_line;
3444 }
3445 catch (runtime_error & exn)
3446 {
3447 goto bad;
3448 }
3449
3450 bad:
7a053d3b 3451 throw semantic_error("malformed specification '" + spec + "'",
20c6c071 3452 base_probe->tok);
bd2b1e68
GH
3453}
3454
3455
91af0778 3456#if 0
b20febf3 3457// Forward declaration.
91af0778 3458static int query_kernel_module (Dwfl_Module *, void **, const char *,
b20febf3 3459 Dwarf_Addr, void *);
91af0778 3460#endif
7e1279ea 3461
2930abc7 3462
b8da0ad1 3463// XXX: pull this into dwflpp
b20febf3
FCE
3464static bool
3465in_kprobes_function(systemtap_session& sess, Dwarf_Addr addr)
2930abc7 3466{
84048984 3467 if (sess.sym_kprobes_text_start != 0 && sess.sym_kprobes_text_end != 0)
1d3a40b6
DS
3468 {
3469 // If the probe point address is anywhere in the __kprobes
3470 // address range, we can't use this probe point.
84048984 3471 if (addr >= sess.sym_kprobes_text_start && addr < sess.sym_kprobes_text_end)
1d3a40b6
DS
3472 return true;
3473 }
3474 return false;
3475}
3476
20e4a32c 3477
36f9dd1d 3478bool
b20febf3
FCE
3479dwarf_query::blacklisted_p(const string& funcname,
3480 const string& filename,
78f6bba6 3481 int,
b20febf3
FCE
3482 const string& module,
3483 const string& section,
36f9dd1d
FCE
3484 Dwarf_Addr addr)
3485{
91af0778
FCE
3486 if (has_process)
3487 return false; // no blacklist for userspace
3488
b20febf3 3489 if (section.substr(0, 6) == string(".init.") ||
f90f9261
SD
3490 section.substr(0, 6) == string(".exit.") ||
3491 section.substr(0, 9) == string(".devinit.") ||
3492 section.substr(0, 9) == string(".devexit.") ||
3493 section.substr(0, 9) == string(".cpuinit.") ||
3494 section.substr(0, 9) == string(".cpuexit.") ||
3495 section.substr(0, 9) == string(".meminit.") ||
3496 section.substr(0, 9) == string(".memexit."))
703621ae 3497 {
b8da0ad1
FCE
3498 // NB: module .exit. routines could be probed in theory:
3499 // if the exit handler in "struct module" is diverted,
3500 // first inserting the kprobes
3501 // then allowing the exit code to run
3502 // then removing these kprobes
b20febf3
FCE
3503 if (sess.verbose>1)
3504 clog << " skipping - init/exit";
3505 return true;
703621ae
FCE
3506 }
3507
1d3a40b6 3508 // Check for function marked '__kprobes'.
b20febf3 3509 if (module == TOK_KERNEL && in_kprobes_function(sess, addr))
1d3a40b6
DS
3510 {
3511 if (sess.verbose>1)
b20febf3 3512 clog << " skipping - __kprobes";
1d3a40b6
DS
3513 return true;
3514 }
4baf0e53 3515
a7301475
FCE
3516 // Check probe point against blacklist.
3517 int goodfn = regexec (&blacklist_func, funcname.c_str(), 0, NULL, 0);
3518 if (has_return)
3519 goodfn = goodfn && regexec (&blacklist_func_ret, funcname.c_str(), 0, NULL, 0);
3520 int goodfile = regexec (&blacklist_file, filename.c_str(), 0, NULL, 0);
3521
3522 if (! (goodfn && goodfile))
36f9dd1d 3523 {
b0ee93c4 3524 if (sess.verbose>1)
b20febf3 3525 clog << " skipping - blacklisted";
36f9dd1d
FCE
3526 return true;
3527 }
3528
3529 // This probe point is not blacklisted.
3530 return false;
3531}
3532
d64e82b1
SD
3533string dwarf_query::get_blacklist_section(Dwarf_Addr addr)
3534{
d64e82b1 3535 string blacklist_section;
f9331b29
RM
3536 Dwarf_Addr bias;
3537 // We prefer dwfl_module_getdwarf to dwfl_module_getelf here,
3538 // because dwfl_module_getelf can force costly section relocations
3539 // we don't really need, while either will do for this purpose.
3540 Elf* elf = (dwarf_getelf (dwfl_module_getdwarf (dw.module, &bias))
3541 ?: dwfl_module_getelf (dw.module, &bias));
3542
3543 Dwarf_Addr offset = addr - bias;
d64e82b1
SD
3544 if (elf)
3545 {
3546 Elf_Scn* scn = 0;
3547 size_t shstrndx;
86bf665e 3548 dwfl_assert ("getshstrndx", elf_getshstrndx (elf, &shstrndx));
d64e82b1
SD
3549 while ((scn = elf_nextscn (elf, scn)) != NULL)
3550 {
3551 GElf_Shdr shdr_mem;
3552 GElf_Shdr *shdr = gelf_getshdr (scn, &shdr_mem);
3553 if (! shdr) continue; // XXX error?
3554
f9331b29
RM
3555 if (!(shdr->sh_flags & SHF_ALLOC))
3556 continue;
3557
d64e82b1
SD
3558 GElf_Addr start = shdr->sh_addr;
3559 GElf_Addr end = start + shdr->sh_size;
3560 if (! (offset >= start && offset < end))
3561 continue;
3562
3563 blacklist_section = elf_strptr (elf, shstrndx, shdr->sh_name);
3564 break;
3565 }
3566 }
3567 return blacklist_section;
3568}
36f9dd1d 3569
b20febf3 3570
36f9dd1d 3571void
b20febf3
FCE
3572dwarf_query::add_probe_point(const string& funcname,
3573 const char* filename,
36f9dd1d 3574 int line,
b20febf3 3575 Dwarf_Die* scope_die,
36f9dd1d
FCE
3576 Dwarf_Addr addr)
3577{
b20febf3
FCE
3578 string reloc_section; // base section for relocation purposes
3579 Dwarf_Addr reloc_addr = addr; // relocated
3580 string blacklist_section; // linking section for blacklist purposes
3581 const string& module = dw.module_name; // "kernel" or other
36f9dd1d 3582
37ebca01
FCE
3583 assert (! has_absolute); // already handled in dwarf_builder::build()
3584
5f0a03a6
JK
3585 if (!dw.module)
3586 {
3587 assert(module == TOK_KERNEL);
3588 reloc_section = "";
3589 blacklist_section = "";
3590 }
3591 else if (dwfl_module_relocations (dw.module) > 0)
2930abc7 3592 {
17c128f2 3593 // This is a relocatable module; libdwfl already knows its
b20febf3
FCE
3594 // sections, so we can relativize addr.
3595 int idx = dwfl_module_relocate_address (dw.module, &reloc_addr);
3596 const char* r_s = dwfl_module_relocation_info (dw.module, idx, NULL);
3597 if (r_s)
3598 reloc_section = r_s;
3599 blacklist_section = reloc_section;
d64e82b1
SD
3600
3601 if(reloc_section == "" && dwfl_module_relocations (dw.module) == 1)
17c128f2
FCE
3602 {
3603 blacklist_section = this->get_blacklist_section(addr);
3604 reloc_section = ".dynamic";
4b0eb118 3605 reloc_addr = addr;
17c128f2 3606 }
2930abc7
FCE
3607 }
3608 else
3609 {
d64e82b1 3610 blacklist_section = this->get_blacklist_section(addr);
17c128f2 3611 reloc_section = ".absolute";
2930abc7
FCE
3612 }
3613
7f9f3386
FCE
3614 if (sess.verbose > 1)
3615 {
b20febf3
FCE
3616 clog << "probe " << funcname << "@" << filename << ":" << line;
3617 if (string(module) == TOK_KERNEL)
3618 clog << " kernel";
91af0778 3619 else if (has_module)
b20febf3 3620 clog << " module=" << module;
91af0778
FCE
3621 else if (has_process)
3622 clog << " process=" << module;
b20febf3
FCE
3623 if (reloc_section != "") clog << " reloc=" << reloc_section;
3624 if (blacklist_section != "") clog << " section=" << blacklist_section;
3625 clog << " pc=0x" << hex << addr << dec;
7f9f3386 3626 }
4baf0e53 3627
b20febf3
FCE
3628 bool bad = blacklisted_p (funcname, filename, line, module, blacklist_section, addr);
3629 if (sess.verbose > 1)
3630 clog << endl;
7f9f3386 3631
84048984
FCE
3632 if (module == TOK_KERNEL)
3633 {
3634 // PR 4224: adapt to relocatable kernel by subtracting the _stext address here.
3635 reloc_addr = addr - sess.sym_stext;
37ebca01 3636 reloc_section = "_stext"; // a message to runtime's _stp_module_relocate
84048984
FCE
3637 }
3638
b20febf3
FCE
3639 if (! bad)
3640 {
1a0dbc5a 3641 sess.unwindsym_modules.insert (module);
6d0f3f0c
FCE
3642
3643 if (has_process)
3644 {
3645 results.push_back (new uprobe_derived_probe(funcname, filename, line,
3646 module, 0, reloc_section, addr, reloc_addr,
3647 *this, scope_die));
3648 }
3649 else
3650 {
3651 assert (has_kernel || has_module);
3652 results.push_back (new dwarf_derived_probe(funcname, filename, line,
06aca46a 3653 module, reloc_section, addr, reloc_addr,
6d0f3f0c
FCE
3654 *this, scope_die));
3655 }
b20febf3 3656 }
2930abc7
FCE
3657}
3658
5f0a03a6
JK
3659enum dbinfo_reqt
3660dwarf_query::assess_dbinfo_reqt()
3661{
3662 if (has_absolute)
3663 {
3664 // kernel.statement(NUM).absolute
3665 return dbr_none;
3666 }
3667 if (has_inline)
3668 {
3669 // kernel.function("f").inline or module("m").function("f").inline
3670 return dbr_need_dwarf;
3671 }
3672 if (has_function_str && spec_type == function_alone)
3673 {
3674 // kernel.function("f") or module("m").function("f")
3675 return dbr_need_symtab;
3676 }
3677 if (has_statement_num)
3678 {
3679 // kernel.statement(NUM) or module("m").statement(NUM)
3680 // Technically, all we need is the module offset (or _stext, for
3681 // the kernel). But for that we need either the ELF file or (for
3682 // _stext) the symbol table. In either case, the symbol table
3683 // is available, and that allows us to map the NUM (address)
3684 // to a function, which is goodness.
3685 return dbr_need_symtab;
3686 }
3687 if (has_function_num)
3688 {
3689 // kernel.function(NUM) or module("m").function(NUM)
3690 // Need the symbol table so we can back up from NUM to the
3691 // start of the function.
3692 return dbr_need_symtab;
3693 }
3694 // Symbol table tells us nothing about source files or line numbers.
3695 return dbr_need_dwarf;
3696}
2930abc7
FCE
3697
3698
b8da0ad1
FCE
3699// The critical determining factor when interpreting a pattern
3700// string is, perhaps surprisingly: "presence of a lineno". The
3701// presence of a lineno changes the search strategy completely.
3702//
3703// Compare the two cases:
3704//
3705// 1. {statement,function}(foo@file.c:lineno)
3706// - find the files matching file.c
3707// - in each file, find the functions matching foo
3708// - query the file for line records matching lineno
3709// - iterate over the line records,
3710// - and iterate over the functions,
3711// - if(haspc(function.DIE, line.addr))
3712// - if looking for statements: probe(lineno.addr)
3713// - if looking for functions: probe(function.{entrypc,return,etc.})
3714//
3715// 2. {statement,function}(foo@file.c)
3716// - find the files matching file.c
3717// - in each file, find the functions matching foo
3718// - probe(function.{entrypc,return,etc.})
3719//
3720// Thus the first decision we make is based on the presence of a
3721// lineno, and we enter entirely different sets of callbacks
3722// depending on that decision.
3723//
3724// Note that the first case is a generalization fo the second, in that
3725// we could theoretically search through line records for matching
3726// file names (a "table scan" in rdbms lingo). Luckily, file names
3727// are already cached elsewhere, so we can do an "index scan" as an
3728// optimization.
7e1279ea 3729
bd2b1e68 3730static void
4cd232e4 3731query_statement (string const & func,
20e4a32c 3732 char const * file,
4cd232e4 3733 int line,
bcc12710 3734 Dwarf_Die *scope_die,
20e4a32c 3735 Dwarf_Addr stmt_addr,
4cd232e4 3736 dwarf_query * q)
bd2b1e68 3737{
39bcd429
FCE
3738 try
3739 {
cee35f73 3740 q->add_probe_point(func, file ? file : "",
a9b2f3a5 3741 line, scope_die, stmt_addr);
39bcd429
FCE
3742 }
3743 catch (const semantic_error& e)
3744 {
3745 q->sess.print_error (e);
3746 }
bd2b1e68
GH
3747}
3748
7e1279ea 3749static void
3e961ba6 3750query_inline_instance_info (inline_instance_info & ii,
7e1279ea
FCE
3751 dwarf_query * q)
3752{
b6581717 3753 try
7e1279ea 3754 {
b6581717
GH
3755 if (q->has_return)
3756 {
3757 throw semantic_error ("cannot probe .return of inline function '" + ii.name + "'");
3758 }
3759 else
3760 {
b0ee93c4 3761 if (q->sess.verbose>2)
20e4a32c 3762 clog << "querying entrypc "
3e961ba6 3763 << hex << ii.entrypc << dec
db22e55f 3764 << " of instance of inline '" << ii.name << "'\n";
20e4a32c 3765 query_statement (ii.name, ii.decl_file, ii.decl_line,
3e961ba6 3766 &ii.die, ii.entrypc, q);
b6581717 3767 }
7e1279ea 3768 }
b6581717 3769 catch (semantic_error &e)
7e1279ea 3770 {
b6581717 3771 q->sess.print_error (e);
7e1279ea
FCE
3772 }
3773}
3774
3775static void
3776query_func_info (Dwarf_Addr entrypc,
bcc12710 3777 func_info & fi,
7e1279ea
FCE
3778 dwarf_query * q)
3779{
b6581717 3780 try
7e1279ea 3781 {
b6581717
GH
3782 if (q->has_return)
3783 {
3784 // NB. dwarf_derived_probe::emit_registrations will emit a
3785 // kretprobe based on the entrypc in this case.
20e4a32c 3786 query_statement (fi.name, fi.decl_file, fi.decl_line,
b6581717
GH
3787 &fi.die, entrypc, q);
3788 }
3789 else
3790 {
35dc8b04 3791 if (fi.prologue_end != 0)
44f75386 3792 {
44f75386
FCE
3793 query_statement (fi.name, fi.decl_file, fi.decl_line,
3794 &fi.die, fi.prologue_end, q);
3795 }
3796 else
3797 {
3798 query_statement (fi.name, fi.decl_file, fi.decl_line,
3799 &fi.die, entrypc, q);
3800 }
b6581717 3801 }
7e1279ea 3802 }
b6581717 3803 catch (semantic_error &e)
7e1279ea 3804 {
b6581717 3805 q->sess.print_error (e);
7e1279ea
FCE
3806 }
3807}
3808
3809
3810static void
86bf665e 3811query_srcfile_line (const dwarf_line_t& line, void * arg)
7e1279ea
FCE
3812{
3813 dwarf_query * q = static_cast<dwarf_query *>(arg);
3814
86bf665e 3815 Dwarf_Addr addr = line.addr();
4cd232e4 3816
86bf665e 3817 int lineno = line.lineno();
847bf07f 3818
86bf665e 3819 for (func_info_map_t::iterator i = q->filtered_functions.begin();
7e1279ea
FCE
3820 i != q->filtered_functions.end(); ++i)
3821 {
3e961ba6 3822 if (q->dw.die_has_pc (i->die, addr))
7e1279ea 3823 {
b0ee93c4 3824 if (q->sess.verbose>3)
db22e55f 3825 clog << "function DIE lands on srcfile\n";
4cd232e4 3826 if (q->has_statement_str)
3e961ba6 3827 query_statement (i->name, i->decl_file,
847bf07f 3828 lineno, // NB: not q->line !
3e961ba6 3829 &(i->die), addr, q);
4cd232e4 3830 else
3e961ba6 3831 query_func_info (i->entrypc, *i, q);
7e1279ea 3832 }
20e4a32c
RM
3833 }
3834
86bf665e 3835 for (inline_instance_map_t::iterator i
897820ca
GH
3836 = q->filtered_inlines.begin();
3837 i != q->filtered_inlines.end(); ++i)
3838 {
3e961ba6 3839 if (q->dw.die_has_pc (i->die, addr))
7e1279ea 3840 {
b0ee93c4 3841 if (q->sess.verbose>3)
db22e55f 3842 clog << "inline instance DIE lands on srcfile\n";
897820ca 3843 if (q->has_statement_str)
3e961ba6
JB
3844 query_statement (i->name, i->decl_file,
3845 q->line[0], &(i->die), addr, q);
897820ca 3846 else
3e961ba6 3847 query_inline_instance_info (*i, q);
897820ca 3848 }
20e4a32c 3849 }
7e1279ea
FCE
3850}
3851
3852
4fa7b22b 3853static int
7e1279ea 3854query_dwarf_inline_instance (Dwarf_Die * die, void * arg)
4fa7b22b
GH
3855{
3856 dwarf_query * q = static_cast<dwarf_query *>(arg);
7e1279ea 3857 assert (!q->has_statement_num);
bd2b1e68 3858
39bcd429 3859 try
7a053d3b 3860 {
b0ee93c4 3861 if (q->sess.verbose>2)
db22e55f 3862 clog << "examining inline instance of " << q->dw.function_name << "\n";
7e1279ea 3863
4baf0e53 3864 if ((q->has_function_str && ! q->has_call)
b8da0ad1 3865 || q->has_statement_str)
7e1279ea 3866 {
b0ee93c4 3867 if (q->sess.verbose>2)
db22e55f
FCE
3868 clog << "selected inline instance of " << q->dw.function_name
3869 << "\n";
7e1279ea
FCE
3870
3871 Dwarf_Addr entrypc;
3872 if (q->dw.die_entrypc (die, &entrypc))
3873 {
3874 inline_instance_info inl;
3875 inl.die = *die;
3876 inl.name = q->dw.function_name;
3e961ba6 3877 inl.entrypc = entrypc;
4cd232e4
GH
3878 q->dw.function_file (&inl.decl_file);
3879 q->dw.function_line (&inl.decl_line);
3e961ba6 3880 q->filtered_inlines.push_back(inl);
7e1279ea
FCE
3881 }
3882 }
3883 return DWARF_CB_OK;
3884 }
3885 catch (const semantic_error& e)
3886 {
3887 q->sess.print_error (e);
3888 return DWARF_CB_ABORT;
3889 }
3890}
bb788f9f 3891
7e1279ea 3892static int
2da9cedb 3893query_dwarf_func (Dwarf_Die * func, base_query * bq)
7e1279ea 3894{
2da9cedb 3895 dwarf_query * q = static_cast<dwarf_query *>(bq);
bb788f9f 3896
7e1279ea
FCE
3897 try
3898 {
7e1279ea
FCE
3899 q->dw.focus_on_function (func);
3900
20e4a32c 3901 if (q->dw.func_is_inline ()
b8da0ad1
FCE
3902 && (! q->has_call) && (! q->has_return)
3903 && (((q->has_statement_str || q->has_function_str)
3904 && q->dw.function_name_matches(q->function))))
7e1279ea 3905 {
b0ee93c4 3906 if (q->sess.verbose>3)
db22e55f
FCE
3907 clog << "checking instances of inline " << q->dw.function_name
3908 << "\n";
2da9cedb 3909 q->dw.iterate_over_inline_instances (query_dwarf_inline_instance, q);
275f40a6
FCE
3910
3911 if (q->dw.function_name_final_match (q->function))
3912 return DWARF_CB_ABORT;
7e1279ea 3913 }
396afcee 3914 else if (!q->dw.func_is_inline () && (! q->has_inline))
20e4a32c 3915 {
7e1279ea
FCE
3916 bool record_this_function = false;
3917
3918 if ((q->has_statement_str || q->has_function_str)
3919 && q->dw.function_name_matches(q->function))
3920 {
3921 record_this_function = true;
3922 }
e4c58386 3923 else if (q->has_function_num || q->has_statement_num)
7e1279ea 3924 {
e4c58386 3925 Dwarf_Addr query_addr =
9b692b91
SC
3926 (q->has_function_num ? q->function_num_val :
3927 q->has_statement_num ? q->statement_num_val :
3928 (assert(0) , 0));
7e1279ea
FCE
3929 Dwarf_Die d;
3930 q->dw.function_die (&d);
20e4a32c 3931
86bf665e 3932 if (q->dw.die_has_pc (d, query_addr))
7e1279ea
FCE
3933 record_this_function = true;
3934 }
3935
3936 if (record_this_function)
3937 {
b0ee93c4 3938 if (q->sess.verbose>2)
db22e55f 3939 clog << "selected function " << q->dw.function_name << "\n";
7e1279ea 3940
e4c58386
FCE
3941 func_info func;
3942 q->dw.function_die (&func.die);
3943 func.name = q->dw.function_name;
3944 q->dw.function_file (&func.decl_file);
3945 q->dw.function_line (&func.decl_line);
3946
3947 if (q->has_function_num || q->has_function_str || q->has_statement_str)
3948 {
3949 Dwarf_Addr entrypc;
3950 if (q->dw.function_entrypc (&entrypc))
3e961ba6
JB
3951 {
3952 func.entrypc = entrypc;
3953 q->filtered_functions.push_back (func);
3954 }
e4c58386 3955 else
552fdd9f
JB
3956 /* this function just be fully inlined, just ignore it */
3957 return DWARF_CB_OK;
e4c58386
FCE
3958 }
3959 else if (q->has_statement_num)
3960 {
3e961ba6
JB
3961 func.entrypc = q->statement_num_val;
3962 q->filtered_functions.push_back (func);
275f40a6
FCE
3963 if (q->dw.function_name_final_match (q->function))
3964 return DWARF_CB_ABORT;
e4c58386
FCE
3965 }
3966 else
3967 assert(0);
3968
3969 if (q->dw.function_name_final_match (q->function))
3970 return DWARF_CB_ABORT;
7e1279ea
FCE
3971 }
3972 }
39bcd429 3973 return DWARF_CB_OK;
bd2b1e68 3974 }
39bcd429 3975 catch (const semantic_error& e)
bd2b1e68 3976 {
39bcd429
FCE
3977 q->sess.print_error (e);
3978 return DWARF_CB_ABORT;
bd2b1e68 3979 }
bd2b1e68
GH
3980}
3981
3982static int
3983query_cu (Dwarf_Die * cudie, void * arg)
3984{
20c6c071 3985 dwarf_query * q = static_cast<dwarf_query *>(arg);
49abf162 3986 if (pending_interrupts) return DWARF_CB_ABORT;
7a053d3b 3987
39bcd429 3988 try
bd2b1e68 3989 {
7e1279ea 3990 q->dw.focus_on_cu (cudie);
b5d77020 3991
b0ee93c4 3992 if (false && q->sess.verbose>2)
b5d77020 3993 clog << "focused on CU '" << q->dw.cu_name
db22e55f 3994 << "', in module '" << q->dw.module_name << "'\n";
d9b516ca 3995
e4c58386 3996 if (q->has_statement_str || q->has_statement_num
54efe513 3997 || q->has_function_str || q->has_function_num)
7e1279ea
FCE
3998 {
3999 q->filtered_srcfiles.clear();
4000 q->filtered_functions.clear();
4001 q->filtered_inlines.clear();
4002
4003 // In this path, we find "abstract functions", record
4004 // information about them, and then (depending on lineno
4005 // matching) possibly emit one or more of the function's
4006 // associated addresses. Unfortunately the control of this
4007 // cannot easily be turned inside out.
4008
b8da0ad1 4009 if ((q->has_statement_str || q->has_function_str)
7e1279ea
FCE
4010 && (q->spec_type != function_alone))
4011 {
4012 // If we have a pattern string with a filename, we need
4013 // to elaborate the srcfile mask in question first.
4014 q->dw.collect_srcfiles_matching (q->file, q->filtered_srcfiles);
4015
4016 // If we have a file pattern and *no* srcfile matches, there's
4017 // no need to look further into this CU, so skip.
4018 if (q->filtered_srcfiles.empty())
4019 return DWARF_CB_OK;
4020 }
86bf665e
TM
4021 // Verify that a raw address matches the beginning of a
4022 // statement. This is a somewhat lame check that the address
4023 // is at the start of an assembly instruction.
1f0cfd98
SC
4024 // Avoid for now since this thwarts a probe on a statement in a macro
4025 if (0 && q->has_statement_num)
86bf665e
TM
4026 {
4027 Dwarf_Addr queryaddr = q->statement_num_val;
4028 dwarf_line_t address_line(dwarf_getsrc_die(cudie, queryaddr));
4029 Dwarf_Addr lineaddr = 0;
4030 if (address_line)
4031 lineaddr = address_line.addr();
4032 if (!address_line || lineaddr != queryaddr)
4033 {
4034 stringstream msg;
4035 msg << "address 0x" << hex << queryaddr
1b1b4ceb 4036 << " does not match the beginning of a statement";
86bf665e
TM
4037 throw semantic_error(msg.str());
4038 }
4039 }
7e1279ea
FCE
4040 // Pick up [entrypc, name, DIE] tuples for all the functions
4041 // matching the query, and fill in the prologue endings of them
4042 // all in a single pass.
2da9cedb
JS
4043 int rc = q->dw.iterate_over_functions (query_dwarf_func, q,
4044 q->function,
4045 q->has_statement_num);
5f0a03a6
JK
4046 if (rc != DWARF_CB_OK)
4047 q->query_done = true;
44f75386 4048
35dc8b04 4049 if ((q->sess.prologue_searching || q->has_process) // PR 6871
e4c58386 4050 && !q->has_statement_str && !q->has_statement_num) // PR 2608
44f75386
FCE
4051 if (! q->filtered_functions.empty())
4052 q->dw.resolve_prologue_endings (q->filtered_functions);
7e1279ea 4053
b8da0ad1 4054 if ((q->has_statement_str || q->has_function_str)
7e1279ea
FCE
4055 && (q->spec_type == function_file_and_line))
4056 {
4057 // If we have a pattern string with target *line*, we
20e4a32c 4058 // have to look at lines in all the matched srcfiles.
7e1279ea
FCE
4059 for (set<char const *>::const_iterator i = q->filtered_srcfiles.begin();
4060 i != q->filtered_srcfiles.end(); ++i)
897820ca 4061 q->dw.iterate_over_srcfile_lines (*i, q->line, q->has_statement_str,
0c8b7d37 4062 q->line_type, query_srcfile_line, q);
7e1279ea 4063 }
0f336e95
SC
4064 else if (q->has_label)
4065 {
4066 // If we have a pattern string with target *label*, we
4067 // have to look at labels in all the matched srcfiles.
4068 q->dw.iterate_over_cu_labels (q->label_val, q->dw.cu, q, query_statement);
4069 }
7e1279ea
FCE
4070 else
4071 {
e4c58386 4072 // Otherwise, simply probe all resolved functions.
86bf665e 4073 for (func_info_map_t::iterator i = q->filtered_functions.begin();
e4c58386 4074 i != q->filtered_functions.end(); ++i)
3e961ba6 4075 query_func_info (i->entrypc, *i, q);
e4c58386
FCE
4076
4077 // And all inline instances (if we're not excluding inlines with ".call")
4078 if (! q->has_call)
86bf665e 4079 for (inline_instance_map_t::iterator i
54efe513 4080 = q->filtered_inlines.begin(); i != q->filtered_inlines.end(); ++i)
3e961ba6 4081 query_inline_instance_info (*i, q);
7e1279ea
FCE
4082 }
4083 }
39bcd429
FCE
4084 else
4085 {
e4c58386
FCE
4086 // Before PR 5787, we used to have this:
4087#if 0
7e1279ea
FCE
4088 // Otherwise we have a statement number, and we can just
4089 // query it directly within this module.
7e1279ea
FCE
4090 assert (q->has_statement_num);
4091 Dwarf_Addr query_addr = q->statement_num_val;
b8da0ad1 4092 query_addr = q->dw.module_address_to_global(query_addr);
7e1279ea 4093
bcc12710 4094 query_statement ("", "", -1, NULL, query_addr, q);
e4c58386
FCE
4095#endif
4096 // But now, we traverse CUs/functions even for
4097 // statement_num's, for blacklist sensitivity and $var
4098 // resolution purposes.
4099
4100 assert (0); // NOTREACHED
39bcd429
FCE
4101 }
4102 return DWARF_CB_OK;
bd2b1e68 4103 }
39bcd429 4104 catch (const semantic_error& e)
bd2b1e68 4105 {
39bcd429
FCE
4106 q->sess.print_error (e);
4107 return DWARF_CB_ABORT;
bd2b1e68 4108 }
bd2b1e68
GH
4109}
4110
0ce64fb8 4111
91af0778 4112#if 0
1d3a40b6
DS
4113static int
4114query_kernel_module (Dwfl_Module *mod,
91af0778 4115 void **,
1d3a40b6 4116 const char *name,
b8da0ad1 4117 Dwarf_Addr,
1d3a40b6
DS
4118 void *arg)
4119{
4120 if (TOK_KERNEL == name)
4121 {
4122 Dwfl_Module **m = (Dwfl_Module **)arg;
4123
4124 *m = mod;
4125 return DWARF_CB_ABORT;
4126 }
4127 return DWARF_CB_OK;
4128}
91af0778
FCE
4129#endif
4130
1d3a40b6 4131
5f0a03a6
JK
4132static void
4133validate_module_elf (Dwfl_Module *mod, const char *name, base_query *q)
4134{
4135 // Validate the machine code in this elf file against the
4136 // session machine. This is important, in case the wrong kind
4137 // of debuginfo is being automagically processed by elfutils.
4138 // While we can tell i686 apart from x86-64, unfortunately
4139 // we can't help confusing i586 vs i686 (both EM_386).
4140
4141 Dwarf_Addr bias;
4142 // We prefer dwfl_module_getdwarf to dwfl_module_getelf here,
4143 // because dwfl_module_getelf can force costly section relocations
4144 // we don't really need, while either will do for this purpose.
4145 Elf* elf = (dwarf_getelf (dwfl_module_getdwarf (mod, &bias))
4146 ?: dwfl_module_getelf (mod, &bias));
4147
4148 GElf_Ehdr ehdr_mem;
4149 GElf_Ehdr* em = gelf_getehdr (elf, &ehdr_mem);
86bf665e 4150 if (em == 0) { dwfl_assert ("dwfl_getehdr", dwfl_errno()); }
5f0a03a6
JK
4151 int elf_machine = em->e_machine;
4152 const char* debug_filename = "";
4153 const char* main_filename = "";
4154 (void) dwfl_module_info (mod, NULL, NULL,
4155 NULL, NULL, NULL,
4156 & main_filename,
4157 & debug_filename);
4158 const string& sess_machine = q->sess.architecture;
4159 string expect_machine;
4160
4161 switch (elf_machine)
4162 {
4163 case EM_386: expect_machine = "i?86"; break; // accept e.g. i586
4164 case EM_X86_64: expect_machine = "x86_64"; break;
7635926c
JK
4165 // We don't support 32-bit ppc kernels, but we support 32-bit apps
4166 // running on ppc64 kernels.
4167 case EM_PPC: expect_machine = "ppc64"; break;
5f0a03a6
JK
4168 case EM_PPC64: expect_machine = "ppc64"; break;
4169 case EM_S390: expect_machine = "s390x"; break;
4170 case EM_IA_64: expect_machine = "ia64"; break;
4171 case EM_ARM: expect_machine = "armv*"; break;
4172 // XXX: fill in some more of these
4173 default: expect_machine = "?"; break;
4174 }
4175
4176 if (! debug_filename) debug_filename = main_filename;
4177 if (! debug_filename) debug_filename = name;
4178
4179 if (fnmatch (expect_machine.c_str(), sess_machine.c_str(), 0) != 0)
4180 {
4181 stringstream msg;
4182 msg << "ELF machine " << expect_machine << " (code " << elf_machine
4183 << ") mismatch with target " << sess_machine
4184 << " in '" << debug_filename << "'";
4185 throw semantic_error(msg.str ());
4186 }
4187
4188 if (q->sess.verbose>2)
4189 clog << "focused on module '" << q->dw.module_name
4190 << " = [0x" << hex << q->dw.module_start
4191 << "-0x" << q->dw.module_end
4192 << ", bias 0x" << q->dw.module_bias << "]" << dec
4193 << " file " << debug_filename
4194 << " ELF machine " << expect_machine
4195 << " (code " << elf_machine << ")"
4196 << "\n";
4197}
1d3a40b6 4198
91af0778
FCE
4199
4200
4201static Dwarf_Addr
4202lookup_symbol_address (Dwfl_Module *m, const char* wanted)
4203{
4204 int syments = dwfl_module_getsymtab(m);
4205 assert(syments);
4206 for (int i = 1; i < syments; ++i)
4207 {
4208 GElf_Sym sym;
4209 const char *name = dwfl_module_getsym(m, i, &sym, NULL);
4210 if (name != NULL && strcmp(name, wanted) == 0)
4211 return sym.st_value;
4212 }
4213
4214 return 0;
4215}
4216
4217
4218
bd2b1e68 4219static int
b8da0ad1 4220query_module (Dwfl_Module *mod,
91af0778 4221 void **,
b8da0ad1 4222 const char *name,
6f4c1275 4223 Dwarf_Addr addr,
b8da0ad1 4224 void *arg)
bd2b1e68 4225{
91af0778 4226 base_query *q = static_cast<base_query *>(arg);
bd2b1e68 4227
39bcd429 4228 try
e38d6504 4229 {
91af0778
FCE
4230 module_info* mi = q->sess.module_cache->cache[name];
4231 if (mi == 0)
4232 {
4233 mi = q->sess.module_cache->cache[name] = new module_info(name);
4234
6f4c1275
FCE
4235 mi->mod = mod;
4236 mi->addr = addr;
91af0778 4237
6f4c1275
FCE
4238 const char* debug_filename = "";
4239 const char* main_filename = "";
4240 (void) dwfl_module_info (mod, NULL, NULL,
4241 NULL, NULL, NULL,
4242 & main_filename,
4243 & debug_filename);
4244
4245 if (q->sess.ignore_vmlinux && name == TOK_KERNEL)
91af0778
FCE
4246 {
4247 // report_kernel() in elfutils found vmlinux, but pretend it didn't.
4248 // Given a non-null path, returning 1 means keep reporting modules.
4249 mi->dwarf_status = info_absent;
4250 }
6f4c1275 4251 else if (debug_filename || main_filename)
91af0778 4252 {
6f4c1275
FCE
4253 mi->elf_path = debug_filename ?: main_filename;
4254 }
4255 else if (name == TOK_KERNEL)
4256 {
4257 mi->dwarf_status = info_absent;
91af0778 4258 }
91af0778
FCE
4259 }
4260 // OK, enough of that module_info caching business.
4261
5f0a03a6 4262 q->dw.focus_on_module(mod, mi);
d9b516ca 4263
39bcd429
FCE
4264 // If we have enough information in the pattern to skip a module and
4265 // the module does not match that information, return early.
b8da0ad1 4266 if (!q->dw.module_name_matches(q->module_val))
39bcd429 4267 return DWARF_CB_OK;
0cbbf9d1
FCE
4268
4269 // Don't allow module("*kernel*") type expressions to match the
4270 // elfutils module "kernel", which we refer to in the probe
4271 // point syntax exclusively as "kernel.*".
4272 if (q->dw.module_name == TOK_KERNEL && ! q->has_kernel)
4273 return DWARF_CB_OK;
b5d77020 4274
5f0a03a6
JK
4275 if (mod)
4276 validate_module_elf(mod, name, q);
4277 else
91af0778
FCE
4278 assert(q->has_kernel); // and no vmlinux to examine
4279
4280 if (q->sess.verbose>2)
4281 cerr << "focused on module '" << q->dw.module_name << "'\n";
4282
4283
4284 // Collect a few kernel addresses. XXX: these belong better
4285 // to the sess.module_info["kernel"] struct.
4286 if (q->dw.module_name == TOK_KERNEL)
c931ec8a 4287 {
91af0778
FCE
4288 if (! q->sess.sym_kprobes_text_start)
4289 q->sess.sym_kprobes_text_start = lookup_symbol_address (mod, "__kprobes_text_start");
4290 if (! q->sess.sym_kprobes_text_end)
4291 q->sess.sym_kprobes_text_end = lookup_symbol_address (mod, "__kprobes_text_end");
4292 if (! q->sess.sym_stext)
4293 q->sess.sym_stext = lookup_symbol_address (mod, "_stext");
c931ec8a
FCE
4294 }
4295
91af0778 4296 // Finally, search the module for matches of the probe point.
2c384610 4297 q->handle_query_module();
bb788f9f 4298
91af0778 4299
b8da0ad1
FCE
4300 // If we know that there will be no more matches, abort early.
4301 if (q->dw.module_name_final_match(q->module_val))
4302 return DWARF_CB_ABORT;
4303 else
4304 return DWARF_CB_OK;
7a053d3b 4305 }
39bcd429 4306 catch (const semantic_error& e)
bd2b1e68 4307 {
39bcd429
FCE
4308 q->sess.print_error (e);
4309 return DWARF_CB_ABORT;
bd2b1e68 4310 }
bd2b1e68
GH
4311}
4312
5f0a03a6 4313void
c4ce66a1 4314dwflpp::query_modules(base_query *q)
5f0a03a6 4315{
91af0778 4316 iterate_over_modules(&query_module, q);
5f0a03a6 4317}
2930abc7 4318
de688825 4319struct var_expanding_visitor: public update_visitor
77de5e9e 4320{
77de5e9e 4321 static unsigned tick;
e57b735a 4322 stack<functioncall**> target_symbol_setter_functioncalls;
77de5e9e 4323
de688825 4324 var_expanding_visitor() {}
35d4ab18
FCE
4325 void visit_assignment (assignment* e);
4326};
4327
4328
de688825 4329struct dwarf_var_expanding_visitor: public var_expanding_visitor
35d4ab18 4330{
77de5e9e 4331 dwarf_query & q;
bcc12710 4332 Dwarf_Die *scope_die;
77de5e9e 4333 Dwarf_Addr addr;
8c819921 4334 block *add_block;
8fc05e57 4335 probe *add_probe;
cd5b28b2 4336 std::map<std::string, symbol *> return_ts_map;
b95e2b79 4337 bool visited;
77de5e9e 4338
de688825 4339 dwarf_var_expanding_visitor(dwarf_query & q, Dwarf_Die *sd, Dwarf_Addr a):
b95e2b79 4340 q(q), scope_die(sd), addr(a), add_block(NULL), add_probe(NULL), visited(false) {}
d7f3e0c5 4341 void visit_target_symbol (target_symbol* e);
c24447be 4342 void visit_cast_op (cast_op* e);
77de5e9e
GH
4343};
4344
4345
35d4ab18 4346
de688825 4347unsigned var_expanding_visitor::tick = 0;
77de5e9e 4348
77de5e9e 4349void
de688825 4350var_expanding_visitor::visit_assignment (assignment* e)
77de5e9e 4351{
e57b735a
GH
4352 // Our job would normally be to require() the left and right sides
4353 // into a new assignment. What we're doing is slightly trickier:
4354 // we're pushing a functioncall** onto a stack, and if our left
4355 // child sets the functioncall* for that value, we're going to
4356 // assume our left child was a target symbol -- transformed into a
4357 // set_target_foo(value) call, and it wants to take our right child
4358 // as the argument "value".
4359 //
4360 // This is why some people claim that languages with
4361 // constructor-decomposing case expressions have a leg up on
4362 // visitors.
4363
4364 functioncall *fcall = NULL;
4365 expression *new_left, *new_right;
d9b516ca 4366
e57b735a 4367 target_symbol_setter_functioncalls.push (&fcall);
4ed05b15 4368 new_left = require (e->left);
e57b735a 4369 target_symbol_setter_functioncalls.pop ();
4ed05b15 4370 new_right = require (e->right);
e57b735a
GH
4371
4372 if (fcall != NULL)
77de5e9e 4373 {
e57b735a
GH
4374 // Our left child is informing us that it was a target variable
4375 // and it has been replaced with a set_target_foo() function
4376 // call; we are going to provide that function call -- with the
4377 // right child spliced in as sole argument -- in place of
de688825 4378 // ourselves, in the var expansion we're in the middle of making.
e57b735a
GH
4379
4380 // FIXME: for the time being, we only support plan $foo = bar,
4381 // not += or any other op= variant. This is fixable, but a bit
4382 // ugly.
4383 if (e->op != "=")
4384 throw semantic_error ("Operator-assign expressions on target "
4385 "variables not implemented", e->tok);
4386
4387 assert (new_left == fcall);
4388 fcall->args.push_back (new_right);
4ed05b15 4389 provide (fcall);
77de5e9e 4390 }
e57b735a
GH
4391 else
4392 {
de688825
JS
4393 e->left = new_left;
4394 e->right = new_right;
4395 provide (e);
e57b735a
GH
4396 }
4397}
d9b516ca 4398
d7f3e0c5 4399
e57b735a 4400void
de688825 4401dwarf_var_expanding_visitor::visit_target_symbol (target_symbol *e)
e57b735a
GH
4402{
4403 assert(e->base_name.size() > 0 && e->base_name[0] == '$');
b95e2b79 4404 visited = true;
e57b735a 4405
cf2a1f85
DS
4406 bool lvalue = is_active_lvalue(e);
4407 if (lvalue && !q.sess.guru_mode)
4408 throw semantic_error("write to target variable not permitted", e->tok);
4409
a43ba433
FCE
4410 // See if we need to generate a new probe to save/access function
4411 // parameters from a return probe. PR 1382.
4412 if (q.has_return
4413 && e->base_name != "$return" // not the special return-value variable handled below
4414 && e->base_name != "$$return") // nor the other special variable handled below
85ecf79a
DS
4415 {
4416 if (lvalue)
4417 throw semantic_error("write to target variable not permitted in .return probes", e->tok);
4418
cd5b28b2
DS
4419 // Get the full name of the target symbol.
4420 stringstream ts_name_stream;
4421 e->print(ts_name_stream);
4422 string ts_name = ts_name_stream.str();
4423
4424 // Check and make sure we haven't already seen this target
4425 // variable in this return probe. If we have, just return our
4426 // last replacement.
4427 map<string, symbol *>::iterator i = return_ts_map.find(ts_name);
4428 if (i != return_ts_map.end())
4429 {
4ed05b15 4430 provide (i->second);
cd5b28b2
DS
4431 return;
4432 }
4433
85ecf79a
DS
4434 // We've got to do several things here to handle target
4435 // variables in return probes.
4436
5e600bd6
DS
4437 // (1) Synthesize two global arrays. One is the cache of the
4438 // target variable and the other contains a thread specific
4439 // nesting level counter. The arrays will look like
4440 // this:
85ecf79a
DS
4441 //
4442 // _dwarf_tvar_{name}_{num}
85ecf79a
DS
4443 // _dwarf_tvar_{name}_{num}_ctr
4444
4445 string aname = (string("_dwarf_tvar_")
4446 + e->base_name.substr(1)
4447 + "_" + lex_cast<string>(tick++));
4448 vardecl* vd = new vardecl;
4449 vd->name = aname;
4450 vd->tok = e->tok;
4451 q.sess.globals.push_back (vd);
4452
4453 string ctrname = aname + "_ctr";
4454 vd = new vardecl;
4455 vd->name = ctrname;
4456 vd->tok = e->tok;
4457 q.sess.globals.push_back (vd);
4458
8c819921
DS
4459 // (2) Create a new code block we're going to insert at the
4460 // beginning of this probe to get the cached value into a
4461 // temporary variable. We'll replace the target variable
4462 // reference with the temporary variable reference. The code
4463 // will look like this:
4464 //
4465 // _dwarf_tvar_tid = tid()
4466 // _dwarf_tvar_{name}_{num}_tmp
4467 // = _dwarf_tvar_{name}_{num}[_dwarf_tvar_tid,
4468 // _dwarf_tvar_{name}_{num}_ctr[_dwarf_tvar_tid]]
4469 // delete _dwarf_tvar_{name}_{num}[_dwarf_tvar_tid,
4470 // _dwarf_tvar_{name}_{num}_ctr[_dwarf_tvar_tid]--]
46392da3
DS
4471 // if (! _dwarf_tvar_{name}_{num}_ctr[_dwarf_tvar_tid])
4472 // delete _dwarf_tvar_{name}_{num}_ctr[_dwarf_tvar_tid]
8c819921
DS
4473
4474 // (2a) Synthesize the tid temporary expression, which will look
85ecf79a
DS
4475 // like this:
4476 //
8c819921
DS
4477 // _dwarf_tvar_tid = tid()
4478 symbol* tidsym = new symbol;
4479 tidsym->name = string("_dwarf_tvar_tid");
4480 tidsym->tok = e->tok;
85ecf79a 4481
8c819921
DS
4482 if (add_block == NULL)
4483 {
8fc05e57
DS
4484 add_block = new block;
4485 add_block->tok = e->tok;
4486
4487 // Synthesize a functioncall to grab the thread id.
4488 functioncall* fc = new functioncall;
4489 fc->tok = e->tok;
4490 fc->function = string("tid");
4491
4492 // Assign the tid to '_dwarf_tvar_tid'.
4493 assignment* a = new assignment;
4494 a->tok = e->tok;
4495 a->op = "=";
4496 a->left = tidsym;
4497 a->right = fc;
4498
4499 expr_statement* es = new expr_statement;
4500 es->tok = e->tok;
4501 es->value = a;
4502 add_block->statements.push_back (es);
8c819921
DS
4503 }
4504
4505 // (2b) Synthesize an array reference and assign it to a
4506 // temporary variable (that we'll use as replacement for the
4507 // target variable reference). It will look like this:
4508 //
4509 // _dwarf_tvar_{name}_{num}_tmp
4510 // = _dwarf_tvar_{name}_{num}[_dwarf_tvar_tid,
4511 // _dwarf_tvar_{name}_{num}_ctr[_dwarf_tvar_tid]]
4512
8fc05e57
DS
4513 arrayindex* ai_tvar_base = new arrayindex;
4514 ai_tvar_base->tok = e->tok;
85ecf79a
DS
4515
4516 symbol* sym = new symbol;
4517 sym->name = aname;
4518 sym->tok = e->tok;
8fc05e57 4519 ai_tvar_base->base = sym;
8c819921 4520
8fc05e57 4521 ai_tvar_base->indexes.push_back(tidsym);
85ecf79a 4522
8c819921
DS
4523 // We need to create a copy of the array index in its current
4524 // state so we can have 2 variants of it (the original and one
4525 // that post-decrements the second index).
8fc05e57
DS
4526 arrayindex* ai_tvar = new arrayindex;
4527 arrayindex* ai_tvar_postdec = new arrayindex;
4528 *ai_tvar = *ai_tvar_base;
4529 *ai_tvar_postdec = *ai_tvar_base;
85ecf79a 4530
8c819921
DS
4531 // Synthesize the
4532 // "_dwarf_tvar_{name}_{num}_ctr[_dwarf_tvar_tid]" used as the
85ecf79a 4533 // second index into the array.
8c819921
DS
4534 arrayindex* ai_ctr = new arrayindex;
4535 ai_ctr->tok = e->tok;
5e600bd6 4536
85ecf79a
DS
4537 sym = new symbol;
4538 sym->name = ctrname;
4539 sym->tok = e->tok;
8c819921
DS
4540 ai_ctr->base = sym;
4541 ai_ctr->indexes.push_back(tidsym);
4542 ai_tvar->indexes.push_back(ai_ctr);
4543
4544 symbol* tmpsym = new symbol;
4545 tmpsym->name = aname + "_tmp";
4546 tmpsym->tok = e->tok;
4547
4548 assignment* a = new assignment;
4549 a->tok = e->tok;
4550 a->op = "=";
4551 a->left = tmpsym;
4552 a->right = ai_tvar;
4553
4554 expr_statement* es = new expr_statement;
4555 es->tok = e->tok;
4556 es->value = a;
4557
4558 add_block->statements.push_back (es);
4559
4560 // (2c) Add a post-decrement to the second array index and
4561 // delete the array value. It will look like this:
4562 //
4563 // delete _dwarf_tvar_{name}_{num}[_dwarf_tvar_tid,
4564 // _dwarf_tvar_{name}_{num}_ctr[_dwarf_tvar_tid]--]
5e600bd6 4565
85ecf79a
DS
4566 post_crement* pc = new post_crement;
4567 pc->tok = e->tok;
4568 pc->op = "--";
8c819921 4569 pc->operand = ai_ctr;
8fc05e57 4570 ai_tvar_postdec->indexes.push_back(pc);
8c819921
DS
4571
4572 delete_statement* ds = new delete_statement;
4573 ds->tok = e->tok;
8fc05e57 4574 ds->value = ai_tvar_postdec;
8c819921
DS
4575
4576 add_block->statements.push_back (ds);
85ecf79a 4577
46392da3
DS
4578 // (2d) Delete the counter value if it is 0. It will look like
4579 // this:
4580 // if (! _dwarf_tvar_{name}_{num}_ctr[_dwarf_tvar_tid])
4581 // delete _dwarf_tvar_{name}_{num}_ctr[_dwarf_tvar_tid]
4baf0e53 4582
46392da3
DS
4583 ds = new delete_statement;
4584 ds->tok = e->tok;
4585 ds->value = ai_ctr;
4586
4587 unary_expression *ue = new unary_expression;
4588 ue->tok = e->tok;
4589 ue->op = "!";
4590 ue->operand = ai_ctr;
4591
4592 if_statement *ifs = new if_statement;
4593 ifs->tok = e->tok;
4594 ifs->condition = ue;
4595 ifs->thenblock = ds;
4596 ifs->elseblock = NULL;
4baf0e53 4597
46392da3
DS
4598 add_block->statements.push_back (ifs);
4599
85ecf79a 4600 // (3) We need an entry probe that saves the value for us in the
8fc05e57
DS
4601 // global array we created. Create the entry probe, which will
4602 // look like this:
85ecf79a 4603 //
85ecf79a 4604 // probe kernel.function("{function}") {
8fc05e57
DS
4605 // _dwarf_tvar_tid = tid()
4606 // _dwarf_tvar_{name}_{num}[_dwarf_tvar_tid,
4607 // ++_dwarf_tvar_{name}_{num}_ctr[_dwarf_tvar_tid]]
85ecf79a
DS
4608 // = ${param}
4609 // }
4610
8fc05e57 4611 if (add_probe == NULL)
85ecf79a 4612 {
8fc05e57
DS
4613 add_probe = new probe;
4614 add_probe->tok = e->tok;
4615
4616 // We need the name of the current probe point, minus the
4617 // ".return" (or anything after it, such as ".maxactive(N)").
4618 // Create a new probe point, copying all the components,
4619 // stopping when we see the ".return" component.
4620 probe_point* pp = new probe_point;
4621 for (unsigned c = 0; c < q.base_loc->components.size(); c++)
4622 {
4623 if (q.base_loc->components[c]->functor == "return")
4624 break;
4625 else
4626 pp->components.push_back(q.base_loc->components[c]);
4627 }
4628 pp->tok = e->tok;
4629 pp->optional = q.base_loc->optional;
4630 add_probe->locations.push_back(pp);
4631
4632 add_probe->body = new block;
4633 add_probe->body->tok = e->tok;
4634
4635 // Synthesize a functioncall to grab the thread id.
4636 functioncall* fc = new functioncall;
4637 fc->tok = e->tok;
4638 fc->function = string("tid");
4639
4640 // Assign the tid to '_dwarf_tvar_tid'.
4641 assignment* a = new assignment;
4642 a->tok = e->tok;
4643 a->op = "=";
4644 a->left = tidsym;
4645 a->right = fc;
4646
4647 expr_statement* es = new expr_statement;
4648 es->tok = e->tok;
4649 es->value = a;
ba6f838d 4650 add_probe->body = new block(add_probe->body, es);
8fc05e57
DS
4651
4652 vardecl* vd = new vardecl;
4653 vd->tok = e->tok;
4654 vd->name = tidsym->name;
4655 vd->type = pe_long;
4656 vd->set_arity(0);
4657 add_probe->locals.push_back(vd);
85ecf79a 4658 }
8fc05e57
DS
4659
4660 // Save the value, like this:
4661 // _dwarf_tvar_{name}_{num}[_dwarf_tvar_tid,
4662 // ++_dwarf_tvar_{name}_{num}_ctr[_dwarf_tvar_tid]]
4663 // = ${param}
4664 arrayindex* ai_tvar_preinc = new arrayindex;
4665 *ai_tvar_preinc = *ai_tvar_base;
4baf0e53 4666
8fc05e57
DS
4667 pre_crement* preinc = new pre_crement;
4668 preinc->tok = e->tok;
4669 preinc->op = "++";
4670 preinc->operand = ai_ctr;
4671 ai_tvar_preinc->indexes.push_back(preinc);
4baf0e53 4672
8fc05e57
DS
4673 a = new assignment;
4674 a->tok = e->tok;
4675 a->op = "=";
4676 a->left = ai_tvar_preinc;
4677 a->right = e;
4678
4679 es = new expr_statement;
4680 es->tok = e->tok;
4681 es->value = a;
4682
ba6f838d 4683 add_probe->body = new block(add_probe->body, es);
85ecf79a 4684
8c819921
DS
4685 // (4) Provide the '_dwarf_tvar_{name}_{num}_tmp' variable to
4686 // our parent so it can be used as a substitute for the target
4687 // symbol.
4ed05b15 4688 provide (tmpsym);
cd5b28b2
DS
4689
4690 // (5) Remember this replacement since we might be able to reuse
4691 // it later if the same return probe references this target
4692 // symbol again.
4693 return_ts_map[ts_name] = tmpsym;
85ecf79a
DS
4694 return;
4695 }
cf2a1f85 4696
2cb3fe26
SC
4697 if (e->base_name == "$$vars"
4698 || e->base_name == "$$parms"
a43ba433
FCE
4699 || e->base_name == "$$locals"
4700 || (q.has_return && (e->base_name == "$$return")))
2cb3fe26
SC
4701 {
4702 Dwarf_Die *scopes;
4703 if (dwarf_getscopes_die (scope_die, &scopes) == 0)
4704 return;
41c262f3 4705
2cb3fe26
SC
4706 target_symbol *tsym = new target_symbol;
4707 print_format* pf = new print_format;
4708
4709 // Convert $$parms to sprintf of a list of parms and active local vars
4710 // which we recursively evaluate
a43ba433
FCE
4711
4712 // NB: we synthesize a new token here rather than reusing
4713 // e->tok, because print_format::print likes to use
4714 // its tok->content.
4715 token* pf_tok = new token;
4716 pf_tok->location = e->tok->location;
4717 pf_tok->type = tok_identifier;
4718 pf_tok->content = "sprint";
4719
4720 pf->tok = pf_tok;
2cb3fe26
SC
4721 pf->print_to_stream = false;
4722 pf->print_with_format = true;
4723 pf->print_with_delim = false;
4724 pf->print_with_newline = false;
4725 pf->print_char = false;
4726
a43ba433
FCE
4727 if (q.has_return && (e->base_name == "$$return"))
4728 {
4729 tsym->tok = e->tok;
4730 tsym->base_name = "$return";
41c262f3 4731
a43ba433
FCE
4732 // Ignore any variable that isn't accessible.
4733 tsym->saved_conversion_error = 0;
4ed05b15
JS
4734 expression *texp = tsym;
4735 texp = require (texp); // NB: throws nothing ...
a43ba433
FCE
4736 if (tsym->saved_conversion_error) // ... but this is how we know it happened.
4737 {
2cb3fe26 4738
a43ba433
FCE
4739 }
4740 else
4741 {
fd574705 4742 pf->raw_components += "return";
a43ba433 4743 pf->raw_components += "=%#x ";
4ed05b15 4744 pf->args.push_back(texp);
a43ba433
FCE
4745 }
4746 }
4747 else
4748 {
4749 // non-.return probe: support $$parms, $$vars, $$locals
4750 Dwarf_Die result;
4751 if (dwarf_child (&scopes[0], &result) == 0)
4752 do
00cf3709 4753 {
a43ba433
FCE
4754 switch (dwarf_tag (&result))
4755 {
4756 case DW_TAG_variable:
4757 if (e->base_name == "$$parms")
4758 continue;
4759 break;
4760 case DW_TAG_formal_parameter:
4761 if (e->base_name == "$$locals")
4762 continue;
4763 break;
41c262f3 4764
a43ba433
FCE
4765 default:
4766 continue;
4767 }
41c262f3 4768
a43ba433 4769 const char *diename = dwarf_diename (&result);
f76427a2
FCE
4770 if (! diename) continue;
4771
a43ba433
FCE
4772 tsym->tok = e->tok;
4773 tsym->base_name = "$";
4774 tsym->base_name += diename;
41c262f3 4775
a43ba433
FCE
4776 // Ignore any variable that isn't accessible.
4777 tsym->saved_conversion_error = 0;
4ed05b15
JS
4778 expression *texp = tsym;
4779 texp = require (texp); // NB: throws nothing ...
a43ba433
FCE
4780 if (tsym->saved_conversion_error) // ... but this is how we know it happened.
4781 {
12b44fb3
FCE
4782 if (q.sess.verbose>2)
4783 {
4784 for (semantic_error *c = tsym->saved_conversion_error;
4785 c != 0;
4786 c = c->chain) {
4787 clog << "variable location problem: " << c->what() << endl;
4788 }
4789 }
4790
a43ba433
FCE
4791 pf->raw_components += diename;
4792 pf->raw_components += "=? ";
4793 }
4794 else
4795 {
4796 pf->raw_components += diename;
4797 pf->raw_components += "=%#x ";
4ed05b15 4798 pf->args.push_back(texp);
a43ba433 4799 }
00cf3709 4800 }
a43ba433
FCE
4801 while (dwarf_siblingof (&result, &result) == 0);
4802 }
2cb3fe26 4803
2cb3fe26 4804 pf->components = print_format::string_to_components(pf->raw_components);
4ed05b15 4805 provide (pf);
2cb3fe26
SC
4806
4807 return;
4808 }
4809
e57b735a 4810 // Synthesize a function.
d7f3e0c5 4811 functiondecl *fdecl = new functiondecl;
7b99c7d3 4812 fdecl->tok = e->tok;
d7f3e0c5 4813 embeddedcode *ec = new embeddedcode;
5e309481 4814 ec->tok = e->tok;
e8fbc5e8 4815
1b07c728 4816 string fname = (string(lvalue ? "_dwarf_tvar_set" : "_dwarf_tvar_get")
20e4a32c 4817 + "_" + e->base_name.substr(1)
e57b735a
GH
4818 + "_" + lex_cast<string>(tick++));
4819
66d284f4 4820 try
e57b735a 4821 {
a43ba433 4822 if (q.has_return && (e->base_name == "$return"))
e19fda4e
DS
4823 {
4824 ec->code = q.dw.literal_stmt_for_return (scope_die,
4825 addr,
4826 e->components,
4827 lvalue,
4828 fdecl->type);
4829 }
4830 else
4831 {
4832 ec->code = q.dw.literal_stmt_for_local (scope_die,
4833 addr,
4834 e->base_name.substr(1),
4835 e->components,
4836 lvalue,
4837 fdecl->type);
4838 }
4839
1b07c728
FCE
4840 if (! lvalue)
4841 ec->code += "/* pure */";
66d284f4
FCE
4842 }
4843 catch (const semantic_error& er)
4844 {
3bd0d4df
RA
4845 if (!q.sess.skip_badvars)
4846 {
4847 // We suppress this error message, and pass the unresolved
4848 // target_symbol to the next pass. We hope that this value ends
4849 // up not being referenced after all, so it can be optimized out
4850 // quietly.
4851 provide (e);
4852 semantic_error* saveme = new semantic_error (er); // copy it
4853 saveme->tok1 = e->tok; // XXX: token not passed to q.dw code generation routines
4854 // NB: we can have multiple errors, since a $target variable
4855 // may be expanded in several different contexts:
4856 // function ("*") { $var }
4857 saveme->chain = e->saved_conversion_error;
4858 e->saved_conversion_error = saveme;
4859 }
4860 else
4861 {
4862 // Upon user request for ignoring context, the symbol is replaced
4863 // with a literal 0 and a warning message displayed
4864 literal_number* ln_zero = new literal_number (0);
4865 ln_zero->tok = e->tok;
4866 provide (ln_zero);
4867 q.sess.print_warning ("Bad variable being substituted with literal 0",
4868 e->tok);
4869 }
1cde5ba5
JS
4870 delete fdecl;
4871 delete ec;
cbfbbf69 4872 return;
66d284f4 4873 }
e57b735a 4874
d7f3e0c5
GH
4875 fdecl->name = fname;
4876 fdecl->body = ec;
e57b735a
GH
4877 if (lvalue)
4878 {
4879 // Modify the fdecl so it carries a single pe_long formal
4880 // argument called "value".
4881
4882 // FIXME: For the time being we only support setting target
4883 // variables which have base types; these are 'pe_long' in
4884 // stap's type vocabulary. Strings and pointers might be
4885 // reasonable, some day, but not today.
4886
4887 vardecl *v = new vardecl;
4888 v->type = pe_long;
4889 v->name = "value";
4890 v->tok = e->tok;
4891 fdecl->formal_args.push_back(v);
4892 }
f76427a2 4893 q.sess.functions[fdecl->name]=fdecl;
d9b516ca 4894
e57b735a 4895 // Synthesize a functioncall.
d7f3e0c5
GH
4896 functioncall* n = new functioncall;
4897 n->tok = e->tok;
4898 n->function = fname;
35d4ab18 4899 n->referent = 0; // NB: must not resolve yet, to ensure inclusion in session
e57b735a
GH
4900
4901 if (lvalue)
4902 {
4903 // Provide the functioncall to our parent, so that it can be
4904 // used to substitute for the assignment node immediately above
4905 // us.
4906 assert(!target_symbol_setter_functioncalls.empty());
4907 *(target_symbol_setter_functioncalls.top()) = n;
4908 }
4909
4ed05b15 4910 provide (n);
77de5e9e
GH
4911}
4912
4913
c24447be
JS
4914void
4915dwarf_var_expanding_visitor::visit_cast_op (cast_op *e)
4916{
4917 // Fill in our current module context if needed
4918 if (e->module.empty())
4919 e->module = q.dw.module_name;
4920
4921 var_expanding_visitor::visit_cast_op(e);
4922}
4923
4924
c4ce66a1
JS
4925struct dwarf_cast_query : public base_query
4926{
4927 const cast_op& e;
4928 const bool lvalue;
c4ce66a1 4929
abb41d92
JS
4930 exp_type& pe_type;
4931 string& code;
c4ce66a1 4932
abb41d92
JS
4933 dwarf_cast_query(dwflpp& dw, const string& module, const cast_op& e,
4934 bool lvalue, exp_type& pe_type, string& code):
4935 base_query(dw, module), e(e), lvalue(lvalue),
4936 pe_type(pe_type), code(code) {}
c4ce66a1
JS
4937
4938 void handle_query_module();
4939 int handle_query_cu(Dwarf_Die * cudie);
4940
4941 static int cast_query_cu (Dwarf_Die * cudie, void * arg);
4942};
4943
4944
c4ce66a1
JS
4945void
4946dwarf_cast_query::handle_query_module()
4947{
abb41d92 4948 if (!code.empty())
c4ce66a1
JS
4949 return;
4950
4951 // look for the type in each CU
4952 dw.iterate_over_cus(cast_query_cu, this);
4953}
4954
4955
4956int
4957dwarf_cast_query::handle_query_cu(Dwarf_Die * cudie)
4958{
abb41d92 4959 if (!code.empty())
c4ce66a1
JS
4960 return DWARF_CB_ABORT;
4961
4962 dw.focus_on_cu (cudie);
4963 Dwarf_Die* type_die = dw.declaration_resolve(e.type.c_str());
4964 if (type_die)
4965 {
4966 try
4967 {
4968 code = dw.literal_stmt_for_pointer (type_die, e.components,
4969 lvalue, pe_type);
4970 }
4971 catch (const semantic_error& e)
4972 {
4973 // XXX might be better to save the error
4974 // and try again in another CU
4975 sess.print_error (e);
c4ce66a1 4976 }
c4ce66a1
JS
4977 return DWARF_CB_ABORT;
4978 }
4979 return DWARF_CB_OK;
4980}
4981
4982
4983int
4984dwarf_cast_query::cast_query_cu (Dwarf_Die * cudie, void * arg)
4985{
4986 dwarf_cast_query * q = static_cast<dwarf_cast_query *>(arg);
4987 if (pending_interrupts) return DWARF_CB_ABORT;
4988 return q->handle_query_cu(cudie);
4989}
4990
4991
4992struct dwarf_cast_expanding_visitor: public var_expanding_visitor
4993{
4994 systemtap_session& s;
4995 dwarf_builder& db;
4996
4997 dwarf_cast_expanding_visitor(systemtap_session& s, dwarf_builder& db):
4998 s(s), db(db) {}
4999 void visit_cast_op (cast_op* e);
5000};
5001
5002
5003void dwarf_cast_expanding_visitor::visit_cast_op (cast_op* e)
5004{
5005 bool lvalue = is_active_lvalue(e);
5006 if (lvalue && !s.guru_mode)
5007 throw semantic_error("write to typecast value not permitted", e->tok);
5008
5009 if (e->module.empty())
5010 e->module = "kernel"; // "*" may also be reasonable to search all kernel modules
5011
c4ce66a1
JS
5012 string code;
5013 exp_type type = pe_long;
abb41d92
JS
5014 size_t mod_end = -1;
5015 do
c4ce66a1 5016 {
abb41d92
JS
5017 // split the module string by ':' for alternatives
5018 size_t mod_begin = mod_end + 1;
5019 mod_end = e->module.find(':', mod_begin);
139dee87 5020 string module = e->module.substr(mod_begin, mod_end - mod_begin);
abb41d92 5021
c4ce66a1
JS
5022 // NB: This uses '/' to distinguish between kernel modules and userspace,
5023 // which means that userspace modules won't get any PATH searching.
5024 dwflpp* dw;
abb41d92 5025 if (module.find('/') == string::npos)
c4ce66a1
JS
5026 {
5027 // kernel or kernel module target
5028 if (! db.kern_dw)
5029 {
5030 db.kern_dw = new dwflpp(s);
5031 db.kern_dw->setup_kernel(true);
5032 }
5033 dw = db.kern_dw;
5034 }
5035 else
5036 {
abb41d92 5037 module = find_executable (module); // canonicalize it
c4ce66a1
JS
5038
5039 // user-space target; we use one dwflpp instance per module name
5040 // (= program or shared library)
abb41d92 5041 if (db.user_dw.find(module) == db.user_dw.end())
c4ce66a1
JS
5042 {
5043 dw = new dwflpp(s);
abb41d92
JS
5044 dw->setup_user(module);
5045 db.user_dw[module] = dw;
c4ce66a1
JS
5046 }
5047 else
abb41d92 5048 dw = db.user_dw[module];
c4ce66a1
JS
5049 }
5050
abb41d92
JS
5051 dwarf_cast_query q (*dw, module, *e, lvalue, type, code);
5052 dw->query_modules(&q);
c4ce66a1 5053 }
abb41d92
JS
5054 while (code.empty() && mod_end != string::npos);
5055
5056 if (code.empty())
c4ce66a1 5057 {
abb41d92 5058 // We generate an error message, and pass the unresolved
c4ce66a1
JS
5059 // cast_op to the next pass. We hope that this value ends
5060 // up not being referenced after all, so it can be optimized out
5061 // quietly.
abb41d92 5062 semantic_error* er = new semantic_error ("type definition not found", e->tok);
c4ce66a1
JS
5063 // NB: we can have multiple errors, since a @cast
5064 // may be expanded in several different contexts:
5065 // function ("*") { @cast(...) }
abb41d92
JS
5066 er->chain = e->saved_conversion_error;
5067 e->saved_conversion_error = er;
c4ce66a1
JS
5068 provide (e);
5069 return;
5070 }
5071
5072 string fname = (string(lvalue ? "_dwarf_tvar_set" : "_dwarf_tvar_get")
5073 + "_" + e->base_name.substr(1)
5074 + "_" + lex_cast<string>(tick++));
5075
5076 // Synthesize a function.
5077 functiondecl *fdecl = new functiondecl;
5078 fdecl->tok = e->tok;
5079 fdecl->type = type;
5080 fdecl->name = fname;
5081
5082 embeddedcode *ec = new embeddedcode;
5083 ec->tok = e->tok;
5084 ec->code = code;
5085 fdecl->body = ec;
5086
5087 // Give the fdecl an argument for the pointer we're trying to cast
5088 vardecl *v1 = new vardecl;
5089 v1->type = pe_long;
5090 v1->name = "pointer";
5091 v1->tok = e->tok;
5092 fdecl->formal_args.push_back(v1);
5093
5094 if (lvalue)
5095 {
5096 // Modify the fdecl so it carries a second pe_long formal
5097 // argument called "value".
5098
5099 // FIXME: For the time being we only support setting target
5100 // variables which have base types; these are 'pe_long' in
5101 // stap's type vocabulary. Strings and pointers might be
5102 // reasonable, some day, but not today.
5103
5104 vardecl *v2 = new vardecl;
5105 v2->type = pe_long;
5106 v2->name = "value";
5107 v2->tok = e->tok;
5108 fdecl->formal_args.push_back(v2);
5109 }
5110 else
5111 ec->code += "/* pure */";
5112
5113 s.functions[fdecl->name] = fdecl;
5114
5115 // Synthesize a functioncall.
5116 functioncall* n = new functioncall;
5117 n->tok = e->tok;
5118 n->function = fname;
5119 n->referent = 0; // NB: must not resolve yet, to ensure inclusion in session
5120 n->args.push_back(e->operand);
5121
5122 if (lvalue)
5123 {
5124 // Provide the functioncall to our parent, so that it can be
5125 // used to substitute for the assignment node immediately above
5126 // us.
5127 assert(!target_symbol_setter_functioncalls.empty());
5128 *(target_symbol_setter_functioncalls.top()) = n;
5129 }
5130
5131 provide (n);
5132}
5133
5134
b8da0ad1
FCE
5135void
5136dwarf_derived_probe::printsig (ostream& o) const
5137{
5138 // Instead of just printing the plain locations, we add a PC value
5139 // as a comment as a way of telling e.g. apart multiple inlined
5140 // function instances. This is distinct from the verbose/clog
5141 // output, since this part goes into the cache hash calculations.
5142 sole_location()->print (o);
6d0f3f0c 5143 o << " /* pc=" << section << "+0x" << hex << addr << dec << " */";
b8da0ad1
FCE
5144 printsig_nested (o);
5145}
5146
5147
5148
dc38c0ae 5149void
b20febf3
FCE
5150dwarf_derived_probe::join_group (systemtap_session& s)
5151{
5152 if (! s.dwarf_derived_probes)
5153 s.dwarf_derived_probes = new dwarf_derived_probe_group ();
5154 s.dwarf_derived_probes->enroll (this);
5155}
5156
5157
5158dwarf_derived_probe::dwarf_derived_probe(const string& funcname,
5159 const string& filename,
5160 int line,
91af0778 5161 // module & section specify a relocation
b20febf3
FCE
5162 // base for <addr>, unless section==""
5163 // (equivalently module=="kernel")
5164 const string& module,
5165 const string& section,
5166 // NB: dwfl_addr is the virtualized
5167 // address for this symbol.
5168 Dwarf_Addr dwfl_addr,
5169 // addr is the section-offset for
5170 // actual relocation.
5171 Dwarf_Addr addr,
5172 dwarf_query& q,
37ebca01 5173 Dwarf_Die* scope_die /* may be null */)
1939ea32 5174 : derived_probe (q.base_probe, new probe_point(*q.base_loc) /* .components soon rewritten */ ),
b20febf3 5175 module (module), section (section), addr (addr),
c9bad430
DS
5176 has_return (q.has_return),
5177 has_maxactive (q.has_maxactive),
5178 maxactive_val (q.maxactive_val)
bd2b1e68 5179{
b20febf3 5180 // Assert relocation invariants
4baf0e53 5181 if (section == "" && dwfl_addr != addr) // addr should be absolute
84048984
FCE
5182 throw semantic_error ("missing relocation base against", q.base_loc->tok);
5183 if (section != "" && dwfl_addr == addr) // addr should be an offset
b20febf3 5184 throw semantic_error ("inconsistent relocation address", q.base_loc->tok);
df8fadee 5185
b20febf3 5186 this->tok = q.base_probe->tok;
b95e2b79 5187 this->access_vars = false;
2930abc7 5188
21beacc9
FCE
5189 // XXX: hack for strange g++/gcc's
5190#ifndef USHRT_MAX
5191#define USHRT_MAX 32767
5192#endif
5193
606fd9c8
FCE
5194 // Range limit maxactive() value
5195 if (q.has_maxactive && (q.maxactive_val < 0 || q.maxactive_val > USHRT_MAX))
5196 throw semantic_error ("maxactive value out of range [0,"
5197 + lex_cast<string>(USHRT_MAX) + "]",
5198 q.base_loc->tok);
5199
de688825 5200 // Expand target variables in the probe body
5f0a03a6 5201 if (!null_die(scope_die))
8fc05e57 5202 {
de688825 5203 dwarf_var_expanding_visitor v (q, scope_die, dwfl_addr);
4ed05b15 5204 this->body = v.require (this->body);
b95e2b79 5205 this->access_vars = v.visited;
37ebca01
FCE
5206
5207 // If during target-variable-expanding the probe, we added a new block
5208 // of code, add it to the start of the probe.
5209 if (v.add_block)
ba6f838d 5210 this->body = new block(v.add_block, this->body);
37ebca01
FCE
5211 // If when target-variable-expanding the probe, we added a new
5212 // probe, add it in a new file to the list of files to be processed.
5213 if (v.add_probe)
5214 {
5215 stapfile *f = new stapfile;
5216 f->probes.push_back(v.add_probe);
5217 q.sess.files.push_back(f);
5218 }
8fc05e57 5219 }
37ebca01 5220 // else - null scope_die - $target variables will produce an error during translate phase
8fc05e57 5221
5d23847d 5222 // Reset the sole element of the "locations" vector as a
b20febf3
FCE
5223 // "reverse-engineered" form of the incoming (q.base_loc) probe
5224 // point. This allows a user to see what function / file / line
5225 // number any particular match of the wildcards.
2930abc7 5226
a229fcd7 5227 vector<probe_point::component*> comps;
91af0778
FCE
5228 if (q.has_kernel)
5229 comps.push_back (new probe_point::component(TOK_KERNEL));
5230 else if(q.has_module)
5231 comps.push_back (new probe_point::component(TOK_MODULE, new literal_string(module)));
5232 else if(q.has_process)
5233 comps.push_back (new probe_point::component(TOK_PROCESS, new literal_string(module)));
5234 else
5235 assert (0);
b5d77020 5236
db520b00
FCE
5237 string fn_or_stmt;
5238 if (q.has_function_str || q.has_function_num)
5239 fn_or_stmt = "function";
5240 else
5241 fn_or_stmt = "statement";
a229fcd7 5242
b8da0ad1 5243 if (q.has_function_str || q.has_statement_str)
db520b00 5244 {
4cd232e4 5245 string retro_name = funcname;
b20febf3 5246 if (filename != "")
cee35f73 5247 {
fb84c077 5248 retro_name += ("@" + string (filename));
cee35f73 5249 if (line > 0)
fb84c077 5250 retro_name += (":" + lex_cast<string> (line));
cee35f73 5251 }
db520b00
FCE
5252 comps.push_back
5253 (new probe_point::component
5254 (fn_or_stmt, new literal_string (retro_name)));
5255 }
b8da0ad1 5256 else if (q.has_function_num || q.has_statement_num)
db520b00
FCE
5257 {
5258 Dwarf_Addr retro_addr;
5259 if (q.has_function_num)
5260 retro_addr = q.function_num_val;
5261 else
5262 retro_addr = q.statement_num_val;
db520b00
FCE
5263 comps.push_back (new probe_point::component
5264 (fn_or_stmt,
5265 new literal_number(retro_addr))); // XXX: should be hex if possible
37ebca01
FCE
5266
5267 if (q.has_absolute)
5268 comps.push_back (new probe_point::component (TOK_ABSOLUTE));
a229fcd7
GH
5269 }
5270
b8da0ad1
FCE
5271 if (q.has_call)
5272 comps.push_back (new probe_point::component(TOK_CALL));
5273 if (q.has_inline)
5274 comps.push_back (new probe_point::component(TOK_INLINE));
db520b00 5275 if (has_return)
b8da0ad1
FCE
5276 comps.push_back (new probe_point::component(TOK_RETURN));
5277 if (has_maxactive)
5278 comps.push_back (new probe_point::component
5279 (TOK_MAXACTIVE, new literal_number(maxactive_val)));
d9b516ca 5280
5d23847d
FCE
5281 // Overwrite it.
5282 this->sole_location()->components = comps;
2930abc7
FCE
5283}
5284
bd2b1e68 5285
7a053d3b 5286void
20c6c071 5287dwarf_derived_probe::register_statement_variants(match_node * root,
bd2b1e68
GH
5288 dwarf_builder * dw)
5289{
54efe513 5290 root->bind(dw);
54efe513
GH
5291}
5292
7a053d3b 5293void
fd6602a0 5294dwarf_derived_probe::register_function_variants(match_node * root,
c9bad430 5295 dwarf_builder * dw)
bd2b1e68 5296{
fd6602a0 5297 root->bind(dw);
b8da0ad1
FCE
5298 root->bind(TOK_INLINE)->bind(dw);
5299 root->bind(TOK_CALL)->bind(dw);
fd6602a0 5300 root->bind(TOK_RETURN)->bind(dw);
c9bad430 5301 root->bind(TOK_RETURN)->bind_num(TOK_MAXACTIVE)->bind(dw);
bd2b1e68
GH
5302}
5303
7a053d3b 5304void
20c6c071 5305dwarf_derived_probe::register_function_and_statement_variants(match_node * root,
bd2b1e68
GH
5306 dwarf_builder * dw)
5307{
5308 // Here we match 4 forms:
5309 //
5310 // .function("foo")
5311 // .function(0xdeadbeef)
5312 // .statement("foo")
5313 // .statement(0xdeadbeef)
5314
fd6602a0
FCE
5315 register_function_variants(root->bind_str(TOK_FUNCTION), dw);
5316 register_function_variants(root->bind_num(TOK_FUNCTION), dw);
20c6c071
GH
5317 register_statement_variants(root->bind_str(TOK_STATEMENT), dw);
5318 register_statement_variants(root->bind_num(TOK_STATEMENT), dw);
bd2b1e68
GH
5319}
5320
5321void
c4ce66a1 5322dwarf_derived_probe::register_patterns(systemtap_session& s)
bd2b1e68 5323{
c4ce66a1 5324 match_node* root = s.pattern_root;
bd2b1e68
GH
5325 dwarf_builder *dw = new dwarf_builder();
5326
c4ce66a1
JS
5327 update_visitor *filter = new dwarf_cast_expanding_visitor(s, *dw);
5328 s.code_filters.push_back(filter);
5329
20c6c071
GH
5330 register_function_and_statement_variants(root->bind(TOK_KERNEL), dw);
5331 register_function_and_statement_variants(root->bind_str(TOK_MODULE), dw);
37ebca01 5332 root->bind(TOK_KERNEL)->bind_num(TOK_STATEMENT)->bind(TOK_ABSOLUTE)->bind(dw);
0f336e95
SC
5333 root->bind(TOK_KERNEL)->bind_str(TOK_FUNCTION)->bind_str(TOK_LABEL)->bind(dw);
5334 root->bind_str(TOK_PROCESS)->bind_str(TOK_FUNCTION)->bind_str(TOK_LABEL)->bind(dw);
37ebca01 5335
7a24d422 5336 register_function_and_statement_variants(root->bind_str(TOK_PROCESS), dw);
f28a8c28
SC
5337 root->bind_str(TOK_PROCESS)->bind_str(TOK_MARK)->bind(dw);
5338 root->bind_str(TOK_PROCESS)->bind_num(TOK_MARK)->bind(dw);
bd2b1e68
GH
5339}
5340
9020300d
FCE
5341void
5342dwarf_derived_probe::emit_probe_local_init(translator_output * o)
5343{
b95e2b79
MH
5344 if (access_vars)
5345 {
5346 // if accessing $variables, emit bsp cache setup for speeding up
5347 o->newline() << "bspcache(c->unwaddr, c->regs);";
5348 }
9020300d 5349}
2930abc7 5350
b20febf3 5351// ------------------------------------------------------------------------
46b84a80
DS
5352
5353void
b20febf3 5354dwarf_derived_probe_group::enroll (dwarf_derived_probe* p)
46b84a80 5355{
b20febf3 5356 probes_by_module.insert (make_pair (p->module, p));
b8da0ad1
FCE
5357
5358 // XXX: probes put at the same address should all share a
5359 // single kprobe/kretprobe, and have their handlers executed
5360 // sequentially.
b55bc428
FCE
5361}
5362
2930abc7 5363
7a053d3b 5364void
775d51e5 5365dwarf_derived_probe_group::emit_module_decls (systemtap_session& s)
ec4373ff 5366{
b20febf3 5367 if (probes_by_module.empty()) return;
2930abc7 5368
775d51e5
DS
5369 s.op->newline() << "/* ---- dwarf probes ---- */";
5370
5371 // Warn of misconfigured kernels
f41595cc
FCE
5372 s.op->newline() << "#if ! defined(CONFIG_KPROBES)";
5373 s.op->newline() << "#error \"Need CONFIG_KPROBES!\"";
5374 s.op->newline() << "#endif";
775d51e5 5375 s.op->newline();
f41595cc 5376
b20febf3
FCE
5377 // Forward declare the master entry functions
5378 s.op->newline() << "static int enter_kprobe_probe (struct kprobe *inst,";
5379 s.op->line() << " struct pt_regs *regs);";
5380 s.op->newline() << "static int enter_kretprobe_probe (struct kretprobe_instance *inst,";
5381 s.op->line() << " struct pt_regs *regs);";
5382
42cb22bd
MH
5383 // Emit an array of kprobe/kretprobe pointers
5384 s.op->newline() << "#if defined(STAPCONF_UNREGISTER_KPROBES)";
5385 s.op->newline() << "static void * stap_unreg_kprobes[" << probes_by_module.size() << "];";
5386 s.op->newline() << "#endif";
5387
b20febf3 5388 // Emit the actual probe list.
606fd9c8
FCE
5389
5390 // NB: we used to plop a union { struct kprobe; struct kretprobe } into
5391 // struct stap_dwarf_probe, but it being initialized data makes it add
5392 // hundreds of bytes of padding per stap_dwarf_probe. (PR5673)
4c2732a1 5393 s.op->newline() << "static struct stap_dwarf_kprobe {";
b20febf3 5394 s.op->newline(1) << "union { struct kprobe kp; struct kretprobe krp; } u;";
e4cb375f
MH
5395 s.op->newline() << "#ifdef __ia64__";
5396 s.op->newline() << "struct kprobe dummy;";
5397 s.op->newline() << "#endif";
606fd9c8
FCE
5398 s.op->newline(-1) << "} stap_dwarf_kprobes[" << probes_by_module.size() << "];";
5399 // NB: bss!
5400
4c2732a1 5401 s.op->newline() << "static struct stap_dwarf_probe {";
b0986e7a
DS
5402 s.op->newline(1) << "const unsigned return_p:1;";
5403 s.op->newline() << "const unsigned maxactive_p:1;";
b20febf3 5404 s.op->newline() << "unsigned registered_p:1;";
b0986e7a 5405 s.op->newline() << "const unsigned short maxactive_val;";
606fd9c8
FCE
5406
5407 // Let's find some stats for the three embedded strings. Maybe they
5408 // are small and uniform enough to justify putting char[MAX]'s into
5409 // the array instead of relocated char*'s.
5410 size_t module_name_max = 0, section_name_max = 0, pp_name_max = 0;
5411 size_t module_name_tot = 0, section_name_tot = 0, pp_name_tot = 0;
5412 size_t all_name_cnt = probes_by_module.size(); // for average
5413 for (p_b_m_iterator it = probes_by_module.begin(); it != probes_by_module.end(); it++)
5414 {
5415 dwarf_derived_probe* p = it->second;
5416#define DOIT(var,expr) do { \
5417 size_t var##_size = (expr) + 1; \
5418 var##_max = max (var##_max, var##_size); \
5419 var##_tot += var##_size; } while (0)
5420 DOIT(module_name, p->module.size());
5421 DOIT(section_name, p->section.size());
5422 DOIT(pp_name, lex_cast_qstring(*p->sole_location()).size());
5423#undef DOIT
5424 }
5425
5426 // Decide whether it's worthwhile to use char[] or char* by comparing
5427 // the amount of average waste (max - avg) to the relocation data size
5428 // (3 native long words).
5429#define CALCIT(var) \
5430 if ((var##_name_max-(var##_name_tot/all_name_cnt)) < (3 * sizeof(void*))) \
5431 { \
5432 s.op->newline() << "const char " << #var << "[" << var##_name_max << "];"; \
5433 if (s.verbose > 2) clog << "stap_dwarf_probe " << #var \
5434 << "[" << var##_name_max << "]" << endl; \
5435 } \
5436 else \
5437 { \
b0986e7a 5438 s.op->newline() << "const char * const " << #var << ";"; \
606fd9c8
FCE
5439 if (s.verbose > 2) clog << "stap_dwarf_probe *" << #var << endl; \
5440 }
5441
5442 CALCIT(module);
5443 CALCIT(section);
5444 CALCIT(pp);
5445
b0986e7a
DS
5446 s.op->newline() << "const unsigned long address;";
5447 s.op->newline() << "void (* const ph) (struct context*);";
b20febf3
FCE
5448 s.op->newline(-1) << "} stap_dwarf_probes[] = {";
5449 s.op->indent(1);
5450
5451 for (p_b_m_iterator it = probes_by_module.begin(); it != probes_by_module.end(); it++)
2930abc7 5452 {
b20febf3
FCE
5453 dwarf_derived_probe* p = it->second;
5454 s.op->newline() << "{";
5455 if (p->has_return)
5456 s.op->line() << " .return_p=1,";
c9bad430 5457 if (p->has_maxactive)
606fd9c8
FCE
5458 {
5459 s.op->line() << " .maxactive_p=1,";
5460 assert (p->maxactive_val >= 0 && p->maxactive_val <= USHRT_MAX);
5461 s.op->line() << " .maxactive_val=" << p->maxactive_val << ",";
5462 }
dc38c256 5463 s.op->line() << " .address=(unsigned long)0x" << hex << p->addr << dec << "ULL,";
84048984
FCE
5464 s.op->line() << " .module=\"" << p->module << "\",";
5465 s.op->line() << " .section=\"" << p->section << "\",";
b20febf3
FCE
5466 s.op->line() << " .pp=" << lex_cast_qstring (*p->sole_location()) << ",";
5467 s.op->line() << " .ph=&" << p->name;
5468 s.op->line() << " },";
2930abc7 5469 }
2930abc7 5470
b20febf3
FCE
5471 s.op->newline(-1) << "};";
5472
5473 // Emit the kprobes callback function
5474 s.op->newline();
5475 s.op->newline() << "static int enter_kprobe_probe (struct kprobe *inst,";
5476 s.op->line() << " struct pt_regs *regs) {";
606fd9c8
FCE
5477 // NB: as of PR5673, the kprobe|kretprobe union struct is in BSS
5478 s.op->newline(1) << "int kprobe_idx = ((uintptr_t)inst-(uintptr_t)stap_dwarf_kprobes)/sizeof(struct stap_dwarf_kprobe);";
5479 // Check that the index is plausible
5480 s.op->newline() << "struct stap_dwarf_probe *sdp = &stap_dwarf_probes[";
5481 s.op->line() << "((kprobe_idx >= 0 && kprobe_idx < " << probes_by_module.size() << ")?";
5482 s.op->line() << "kprobe_idx:0)"; // NB: at least we avoid memory corruption
5483 // XXX: it would be nice to give a more verbose error though; BUG_ON later?
5484 s.op->line() << "];";
c12d974f 5485 common_probe_entryfn_prologue (s.op, "STAP_SESSION_RUNNING", "sdp->pp");
b20febf3
FCE
5486 s.op->newline() << "c->regs = regs;";
5487 s.op->newline() << "(*sdp->ph) (c);";
5488 common_probe_entryfn_epilogue (s.op);
5489 s.op->newline() << "return 0;";
5490 s.op->newline(-1) << "}";
5491
5492 // Same for kretprobes
5493 s.op->newline();
5494 s.op->newline() << "static int enter_kretprobe_probe (struct kretprobe_instance *inst,";
5495 s.op->line() << " struct pt_regs *regs) {";
5496 s.op->newline(1) << "struct kretprobe *krp = inst->rp;";
606fd9c8
FCE
5497
5498 // NB: as of PR5673, the kprobe|kretprobe union struct is in BSS
a36378d7 5499 s.op->newline() << "int kprobe_idx = ((uintptr_t)krp-(uintptr_t)stap_dwarf_kprobes)/sizeof(struct stap_dwarf_kprobe);";
606fd9c8
FCE
5500 // Check that the index is plausible
5501 s.op->newline() << "struct stap_dwarf_probe *sdp = &stap_dwarf_probes[";
5502 s.op->line() << "((kprobe_idx >= 0 && kprobe_idx < " << probes_by_module.size() << ")?";
5503 s.op->line() << "kprobe_idx:0)"; // NB: at least we avoid memory corruption
5504 // XXX: it would be nice to give a more verbose error though; BUG_ON later?
5505 s.op->line() << "];";
5506
c12d974f 5507 common_probe_entryfn_prologue (s.op, "STAP_SESSION_RUNNING", "sdp->pp");
b20febf3
FCE
5508 s.op->newline() << "c->regs = regs;";
5509 s.op->newline() << "c->pi = inst;"; // for assisting runtime's backtrace logic
5510 s.op->newline() << "(*sdp->ph) (c);";
5511 common_probe_entryfn_epilogue (s.op);
5512 s.op->newline() << "return 0;";
5513 s.op->newline(-1) << "}";
20c6c071 5514}
ec4373ff 5515
20c6c071 5516
dc38c0ae 5517void
b20febf3
FCE
5518dwarf_derived_probe_group::emit_module_init (systemtap_session& s)
5519{
5520 s.op->newline() << "for (i=0; i<" << probes_by_module.size() << "; i++) {";
5521 s.op->newline(1) << "struct stap_dwarf_probe *sdp = & stap_dwarf_probes[i];";
a36378d7 5522 s.op->newline() << "struct stap_dwarf_kprobe *kp = & stap_dwarf_kprobes[i];";
f1bad60c 5523 s.op->newline() << "unsigned long relocated_addr = _stp_module_relocate (sdp->module, sdp->section, sdp->address);";
b20febf3 5524 s.op->newline() << "if (relocated_addr == 0) continue;"; // quietly; assume module is absent
6d0f3f0c 5525 s.op->newline() << "probe_point = sdp->pp;"; // for error messages
b20febf3 5526 s.op->newline() << "if (sdp->return_p) {";
606fd9c8 5527 s.op->newline(1) << "kp->u.krp.kp.addr = (void *) relocated_addr;";
c9bad430 5528 s.op->newline() << "if (sdp->maxactive_p) {";
606fd9c8 5529 s.op->newline(1) << "kp->u.krp.maxactive = sdp->maxactive_val;";
c9bad430 5530 s.op->newline(-1) << "} else {";
606fd9c8 5531 s.op->newline(1) << "kp->u.krp.maxactive = max(10, 4*NR_CPUS);";
c9bad430 5532 s.op->newline(-1) << "}";
606fd9c8 5533 s.op->newline() << "kp->u.krp.handler = &enter_kretprobe_probe;";
e4cb375f
MH
5534 // to ensure safeness of bspcache, always use aggr_kprobe on ia64
5535 s.op->newline() << "#ifdef __ia64__";
5536 s.op->newline() << "kp->dummy.addr = kp->u.krp.kp.addr;";
5537 s.op->newline() << "kp->dummy.pre_handler = NULL;";
5538 s.op->newline() << "rc = register_kprobe (& kp->dummy);";
5539 s.op->newline() << "if (rc == 0) {";
5540 s.op->newline(1) << "rc = register_kretprobe (& kp->u.krp);";
5541 s.op->newline() << "if (rc != 0)";
5542 s.op->newline(1) << "unregister_kprobe (& kp->dummy);";
5543 s.op->newline(-2) << "}";
5544 s.op->newline() << "#else";
606fd9c8 5545 s.op->newline() << "rc = register_kretprobe (& kp->u.krp);";
e4cb375f 5546 s.op->newline() << "#endif";
b20febf3 5547 s.op->newline(-1) << "} else {";
e4cb375f 5548 // to ensure safeness of bspcache, always use aggr_kprobe on ia64
606fd9c8
FCE
5549 s.op->newline(1) << "kp->u.kp.addr = (void *) relocated_addr;";
5550 s.op->newline() << "kp->u.kp.pre_handler = &enter_kprobe_probe;";
e4cb375f
MH
5551 s.op->newline() << "#ifdef __ia64__";
5552 s.op->newline() << "kp->dummy.addr = kp->u.kp.addr;";
5553 s.op->newline() << "kp->dummy.pre_handler = NULL;";
5554 s.op->newline() << "rc = register_kprobe (& kp->dummy);";
5555 s.op->newline() << "if (rc == 0) {";
5556 s.op->newline(1) << "rc = register_kprobe (& kp->u.kp);";
5557 s.op->newline() << "if (rc != 0)";
5558 s.op->newline(1) << "unregister_kprobe (& kp->dummy);";
5559 s.op->newline(-2) << "}";
5560 s.op->newline() << "#else";
606fd9c8 5561 s.op->newline() << "rc = register_kprobe (& kp->u.kp);";
e4cb375f 5562 s.op->newline() << "#endif";
b20febf3 5563 s.op->newline(-1) << "}";
9063462a
FCE
5564 s.op->newline() << "if (rc) {"; // PR6749: tolerate a failed register_*probe.
5565 s.op->newline(1) << "sdp->registered_p = 0;";
5566 s.op->newline() << "_stp_warn (\"probe %s registration error (rc %d)\", probe_point, rc);";
5567 s.op->newline() << "rc = 0;"; // continue with other probes
5568 // XXX: shall we increment numskipped?
5569 s.op->newline(-1) << "}";
5570
5571#if 0 /* pre PR 6749; XXX consider making an option */
c48cb0cc 5572 s.op->newline(1) << "for (j=i-1; j>=0; j--) {"; // partial rollback
b20febf3 5573 s.op->newline(1) << "struct stap_dwarf_probe *sdp2 = & stap_dwarf_probes[j];";
606fd9c8
FCE
5574 s.op->newline() << "struct stap_dwarf_kprobe *kp2 = & stap_dwarf_kprobes[j];";
5575 s.op->newline() << "if (sdp2->return_p) unregister_kretprobe (&kp2->u.krp);";
5576 s.op->newline() << "else unregister_kprobe (&kp2->u.kp);";
e4cb375f
MH
5577 s.op->newline() << "#ifdef __ia64__";
5578 s.op->newline() << "unregister_kprobe (&kp2->dummy);";
5579 s.op->newline() << "#endif";
c48cb0cc
FCE
5580 // NB: we don't have to clear sdp2->registered_p, since the module_exit code is
5581 // not run for this early-abort case.
5582 s.op->newline(-1) << "}";
5583 s.op->newline() << "break;"; // don't attempt to register any more probes
b20febf3 5584 s.op->newline(-1) << "}";
9063462a
FCE
5585#endif
5586
b20febf3
FCE
5587 s.op->newline() << "else sdp->registered_p = 1;";
5588 s.op->newline(-1) << "}"; // for loop
dc38c0ae
DS
5589}
5590
5591
46b84a80 5592void
b20febf3 5593dwarf_derived_probe_group::emit_module_exit (systemtap_session& s)
46b84a80 5594{
42cb22bd
MH
5595 //Unregister kprobes by batch interfaces.
5596 s.op->newline() << "#if defined(STAPCONF_UNREGISTER_KPROBES)";
5597 s.op->newline() << "j = 0;";
5598 s.op->newline() << "for (i=0; i<" << probes_by_module.size() << "; i++) {";
5599 s.op->newline(1) << "struct stap_dwarf_probe *sdp = & stap_dwarf_probes[i];";
5600 s.op->newline() << "struct stap_dwarf_kprobe *kp = & stap_dwarf_kprobes[i];";
5601 s.op->newline() << "if (! sdp->registered_p) continue;";
5602 s.op->newline() << "if (!sdp->return_p)";
5603 s.op->newline(1) << "stap_unreg_kprobes[j++] = &kp->u.kp;";
5604 s.op->newline(-2) << "}";
5605 s.op->newline() << "unregister_kprobes((struct kprobe **)stap_unreg_kprobes, j);";
5606 s.op->newline() << "j = 0;";
5607 s.op->newline() << "for (i=0; i<" << probes_by_module.size() << "; i++) {";
5608 s.op->newline(1) << "struct stap_dwarf_probe *sdp = & stap_dwarf_probes[i];";
5609 s.op->newline() << "struct stap_dwarf_kprobe *kp = & stap_dwarf_kprobes[i];";
5610 s.op->newline() << "if (! sdp->registered_p) continue;";
5611 s.op->newline() << "if (sdp->return_p)";
5612 s.op->newline(1) << "stap_unreg_kprobes[j++] = &kp->u.krp;";
5613 s.op->newline(-2) << "}";
5614 s.op->newline() << "unregister_kretprobes((struct kretprobe **)stap_unreg_kprobes, j);";
e4cb375f
MH
5615 s.op->newline() << "#ifdef __ia64__";
5616 s.op->newline() << "j = 0;";
5617 s.op->newline() << "for (i=0; i<" << probes_by_module.size() << "; i++) {";
5618 s.op->newline(1) << "struct stap_dwarf_probe *sdp = & stap_dwarf_probes[i];";
5619 s.op->newline() << "struct stap_dwarf_kprobe *kp = & stap_dwarf_kprobes[i];";
5620 s.op->newline() << "if (! sdp->registered_p) continue;";
5621 s.op->newline() << "stap_unreg_kprobes[j++] = &kp->dummy;";
5622 s.op->newline(-1) << "}";
5623 s.op->newline() << "unregister_kprobes((struct kprobe **)stap_unreg_kprobes, j);";
5624 s.op->newline() << "#endif";
42cb22bd
MH
5625 s.op->newline() << "#endif";
5626
b20febf3
FCE
5627 s.op->newline() << "for (i=0; i<" << probes_by_module.size() << "; i++) {";
5628 s.op->newline(1) << "struct stap_dwarf_probe *sdp = & stap_dwarf_probes[i];";
a36378d7 5629 s.op->newline() << "struct stap_dwarf_kprobe *kp = & stap_dwarf_kprobes[i];";
b20febf3
FCE
5630 s.op->newline() << "if (! sdp->registered_p) continue;";
5631 s.op->newline() << "if (sdp->return_p) {";
42cb22bd 5632 s.op->newline() << "#if !defined(STAPCONF_UNREGISTER_KPROBES)";
606fd9c8 5633 s.op->newline(1) << "unregister_kretprobe (&kp->u.krp);";
42cb22bd 5634 s.op->newline() << "#endif";
606fd9c8 5635 s.op->newline() << "atomic_add (kp->u.krp.nmissed, & skipped_count);";
73209876
FCE
5636 s.op->newline() << "#ifdef STP_TIMING";
5637 s.op->newline() << "if (kp->u.krp.nmissed)";
d01eaa30 5638 s.op->newline(1) << "_stp_warn (\"Skipped due to missed kretprobe/1 on '%s': %d\\n\", sdp->pp, kp->u.krp.nmissed);";
73209876 5639 s.op->newline(-1) << "#endif";
606fd9c8 5640 s.op->newline() << "atomic_add (kp->u.krp.kp.nmissed, & skipped_count);";
73209876
FCE
5641 s.op->newline() << "#ifdef STP_TIMING";
5642 s.op->newline() << "if (kp->u.krp.kp.nmissed)";
d01eaa30 5643 s.op->newline(1) << "_stp_warn (\"Skipped due to missed kretprobe/2 on '%s': %d\\n\", sdp->pp, kp->u.krp.kp.nmissed);";
73209876 5644 s.op->newline(-1) << "#endif";
557fb7a8 5645 s.op->newline(-1) << "} else {";
42cb22bd 5646 s.op->newline() << "#if !defined(STAPCONF_UNREGISTER_KPROBES)";
606fd9c8 5647 s.op->newline(1) << "unregister_kprobe (&kp->u.kp);";
42cb22bd 5648 s.op->newline() << "#endif";
606fd9c8 5649 s.op->newline() << "atomic_add (kp->u.kp.nmissed, & skipped_count);";
73209876
FCE
5650 s.op->newline() << "#ifdef STP_TIMING";
5651 s.op->newline() << "if (kp->u.kp.nmissed)";
d01eaa30 5652 s.op->newline(1) << "_stp_warn (\"Skipped due to missed kprobe on '%s': %d\\n\", sdp->pp, kp->u.kp.nmissed);";
73209876 5653 s.op->newline(-1) << "#endif";
b20febf3 5654 s.op->newline(-1) << "}";
e4cb375f
MH
5655 s.op->newline() << "#if !defined(STAPCONF_UNREGISTER_KPROBES) && defined(__ia64__)";
5656 s.op->newline() << "unregister_kprobe (&kp->dummy);";
5657 s.op->newline() << "#endif";
b20febf3
FCE
5658 s.op->newline() << "sdp->registered_p = 0;";
5659 s.op->newline(-1) << "}";
46b84a80
DS
5660}
5661
5662
20c6c071 5663void
5227f1ea 5664dwarf_builder::build(systemtap_session & sess,
7a053d3b 5665 probe * base,
20c6c071 5666 probe_point * location,
86bf665e 5667 literal_map_t const & parameters,
20c6c071
GH
5668 vector<derived_probe *> & finished_results)
5669{
b20febf3
FCE
5670 // NB: the kernel/user dwlfpp objects are long-lived.
5671 // XXX: but they should be per-session, as this builder object
5672 // may be reused if we try to cross-instrument multiple targets.
84048984 5673
7a24d422
FCE
5674 dwflpp* dw = 0;
5675
7a24d422
FCE
5676 string module_name;
5677 if (has_null_param (parameters, TOK_KERNEL)
5678 || get_param (parameters, TOK_MODULE, module_name))
b8da0ad1 5679 {
7a24d422
FCE
5680 // kernel or kernel module target
5681 if (! kern_dw)
5682 {
5683 kern_dw = new dwflpp(sess);
28d29bd3
FCE
5684 // XXX: PR 3498, PR 6864
5685 kern_dw->setup_kernel(true);
7a24d422
FCE
5686 }
5687 dw = kern_dw;
b8da0ad1 5688 }
7a24d422 5689 else if (get_param (parameters, TOK_PROCESS, module_name))
b8da0ad1 5690 {
d0a7f5a9
FCE
5691 module_name = find_executable (module_name); // canonicalize it
5692
7a24d422
FCE
5693 // user-space target; we use one dwflpp instance per module name
5694 // (= program or shared library)
5695 if (user_dw.find(module_name) == user_dw.end())
84048984 5696 {
7a24d422
FCE
5697 dw = new dwflpp(sess);
5698 // XXX: PR 3498
5699 dw->setup_user(module_name);
5700 user_dw[module_name] = dw;
84048984 5701 }
7a24d422
FCE
5702 else
5703 dw = user_dw[module_name];
c8959a29 5704 }
20c6c071 5705
f28a8c28 5706 if (((probe_point::component*)(location->components[1]))->functor == TOK_MARK)
349dc70e
SC
5707 {
5708 enum probe_types
f28a8c28 5709 {
7b534f48
SC
5710 probes_and_dwarf = 0, // Use statement address
5711 dwarf_no_probes = 1, // Use label name
5712 probes_no_dwarf = 2
349dc70e 5713 };
f28a8c28 5714
7b534f48
SC
5715 int probe_type = dwarf_no_probes;
5716 string probe_name = (char*) location->components[1]->arg->tok->content.c_str();
5717 __uint64_t probe_arg = 0;
349dc70e 5718 Dwarf_Addr bias;
1f0cfd98 5719 Elf* elf = dwfl_module_getelf (dw->module, &bias);
349dc70e 5720 size_t shstrndx;
349dc70e 5721 Elf_Scn *probe_scn = NULL;
59b2ec52 5722 bool probe_found = false;
9b753eda 5723 bool dynamic = (dwfl_module_relocations (dw->module) == 1);
7b534f48 5724
349dc70e 5725 dwfl_assert ("getshstrndx", elf_getshstrndx (elf, &shstrndx));
7b534f48
SC
5726 GElf_Shdr *shdr = NULL;
5727
5728 // Is there a .probes section?
349dc70e
SC
5729 while ((probe_scn = elf_nextscn (elf, probe_scn)))
5730 {
5731 GElf_Shdr shdr_mem;
7b534f48 5732 shdr = gelf_getshdr (probe_scn, &shdr_mem);
349dc70e
SC
5733 assert (shdr != NULL);
5734
7b534f48
SC
5735 if (strcmp (elf_strptr (elf, shstrndx, shdr->sh_name), ".probes") == 0)
5736 {
5737 probe_type = probes_and_dwarf;
5738 break;
5739 }
5740 }
9b753eda
SC
5741 if (dynamic || sess.listing_mode)
5742 probe_type = dwarf_no_probes;
7b534f48 5743
9b753eda 5744 if (probe_type == probes_and_dwarf)
7b534f48 5745 {
1f0cfd98 5746 Elf_Data *pdata = elf_getdata_rawchunk (elf, shdr->sh_offset, shdr->sh_size, ELF_T_BYTE);
349dc70e
SC
5747 assert (pdata != NULL);
5748 size_t probe_scn_offset = 0;
c1008fd0 5749 size_t probe_scn_addr = shdr->sh_addr;
349dc70e
SC
5750 while (probe_scn_offset < pdata->d_size)
5751 {
c1008fd0 5752 const int stap_sentinel = 0x31425250;
1f0cfd98 5753 probe_type = *((int*)((char*)pdata->d_buf + probe_scn_offset));
c1008fd0
SC
5754 if (probe_type != stap_sentinel)
5755 {
5756 probe_scn_offset += sizeof(int);
5757 continue;
5758 }
349dc70e 5759 probe_scn_offset += sizeof(int);
c1008fd0
SC
5760 if (probe_scn_offset % (sizeof(__uint64_t)))
5761 probe_scn_offset += sizeof(__uint64_t) - (probe_scn_offset % sizeof(__uint64_t));
5762
c1008fd0
SC
5763 probe_name = ((char*)((long)(pdata->d_buf) + (long)(*((int*)((long)pdata->d_buf + probe_scn_offset)) - probe_scn_addr)));
5764 probe_scn_offset += sizeof(void*);
1f0cfd98
SC
5765 if (probe_scn_offset % (sizeof(__uint64_t)))
5766 probe_scn_offset += sizeof(__uint64_t) - (probe_scn_offset % sizeof(__uint64_t));
5767 probe_arg = *((__uint64_t*)((char*)pdata->d_buf + probe_scn_offset));
1f0cfd98
SC
5768 if (probe_scn_offset % (sizeof(__uint64_t)*2))
5769 probe_scn_offset = (probe_scn_offset + sizeof(__uint64_t)*2) - (probe_scn_offset % (sizeof(__uint64_t)*2));
9e67aff9
SC
5770 if (strcmp (location->components[1]->arg->tok->content.c_str(), probe_name.c_str()) == 0)
5771 probe_found = true;
5772 else
5773 continue;
5774 const token* sv_tok = location->components[1]->arg->tok;
5775 location->components[1]->functor = TOK_STATEMENT;
5776 location->components[1]->arg = new literal_number((int)probe_arg);
5777 location->components[1]->arg->tok = sv_tok;
5778 ((literal_map_t&)parameters)[TOK_STATEMENT] = location->components[1]->arg;
5779 dwarf_query q(sess, base, location, *dw, parameters, finished_results);
5780 dw->query_modules(&q);
349dc70e 5781 }
9e67aff9
SC
5782 if (probe_found)
5783 return;
349dc70e 5784 }
59b2ec52
SC
5785
5786 if (probe_type == dwarf_no_probes || ! probe_found)
349dc70e 5787 {
7b534f48
SC
5788 location->components[1]->functor = TOK_FUNCTION;
5789 location->components[1]->arg = new literal_string("*");
5790 ((literal_map_t&)parameters)[TOK_FUNCTION] = location->components[1]->arg;
5791 location->components.push_back(new probe_point::component(TOK_LABEL));
5792 location->components[2]->arg = new literal_string("_stapprobe1_" + probe_name);
5793 ((literal_map_t&)parameters).erase(TOK_MARK);
5794 ((literal_map_t&)parameters).insert(pair<string,literal*>(TOK_LABEL, location->components[2]->arg));
349dc70e 5795 }
1f0cfd98 5796
349dc70e
SC
5797 dw->module = 0;
5798 }
5799
c8959a29 5800 dwarf_query q(sess, base, location, *dw, parameters, finished_results);
20c6c071 5801
7a24d422
FCE
5802
5803 // XXX: kernel.statement.absolute is a special case that requires no
5804 // dwfl processing. This code should be in a separate builder.
5805
5806 if (q.has_kernel && q.has_absolute)
37ebca01 5807 {
4baf0e53 5808 // assert guru mode for absolute probes
37ebca01
FCE
5809 if (! q.base_probe->privileged)
5810 {
5811 throw semantic_error ("absolute statement probe in unprivileged script", q.base_probe->tok);
5812 }
5813
5814 // For kernel.statement(NUM).absolute probe points, we bypass
5815 // all the debuginfo stuff: We just wire up a
5816 // dwarf_derived_probe right here and now.
4baf0e53 5817 dwarf_derived_probe* p =
b8da0ad1
FCE
5818 new dwarf_derived_probe ("", "", 0, "kernel", "",
5819 q.statement_num_val, q.statement_num_val,
5820 q, 0);
37ebca01 5821 finished_results.push_back (p);
1a0dbc5a 5822 sess.unwindsym_modules.insert ("kernel");
37ebca01
FCE
5823 return;
5824 }
5825
5f0a03a6
JK
5826 dw->query_modules(&q);
5827}
5828
5829symbol_table::~symbol_table()
5830{
2e67a43b
TM
5831 for (iterator_t i = list_by_addr.begin(); i != list_by_addr.end(); ++i)
5832 delete *i;
5f0a03a6
JK
5833}
5834
5835void
ab91b232
JK
5836symbol_table::add_symbol(const char *name, bool weak, Dwarf_Addr addr,
5837 Dwarf_Addr *high_addr)
5f0a03a6 5838{
ab91b232
JK
5839#ifdef __powerpc__
5840 // Map ".sys_foo" to "sys_foo".
5841 if (name[0] == '.')
5842 name++;
5843#endif
5f0a03a6
JK
5844 func_info *fi = new func_info();
5845 fi->addr = addr;
5846 fi->name = name;
ab91b232 5847 fi->weak = weak;
5f0a03a6
JK
5848 map_by_name[fi->name] = fi;
5849 // TODO: Use a multimap in case there are multiple static
5850 // functions with the same name?
2e67a43b 5851 list_by_addr.push_back(fi);
5f0a03a6
JK
5852}
5853
5854enum info_status
5855symbol_table::read_symbols(FILE *f, const string& path)
5856{
5857 // Based on do_kernel_symbols() in runtime/staprun/symbols.c
5858 int ret;
2e67a43b
TM
5859 char *name = 0;
5860 char *mod = 0;
5f0a03a6
JK
5861 char type;
5862 unsigned long long addr;
5863 Dwarf_Addr high_addr = 0;
5864 int line = 0;
5865
5866 // %as (non-POSIX) mallocs space for the string and stores its address.
5867 while ((ret = fscanf(f, "%llx %c %as [%as", &addr, &type, &name, &mod)) > 0)
5868 {
2e67a43b
TM
5869 auto_free free_name(name);
5870 auto_free free_mod(mod);
5f0a03a6
JK
5871 line++;
5872 if (ret < 3)
5873 {
41c262f3 5874 cerr << "Symbol table error: Line "
5f0a03a6
JK
5875 << line
5876 << " of symbol list from "
5877 << path
5878 << " is not in correct format: address type name [module]";
5879 // Caller should delete symbol_table object.
5880 return info_absent;
5881 }
2e67a43b 5882 else if (ret > 3)
5f0a03a6
JK
5883 {
5884 // Modules are loaded above the kernel, so if we're getting
5885 // modules, we're done.
2e67a43b 5886 break;
5f0a03a6 5887 }
ab91b232
JK
5888 if (type == 'T' || type == 't' || type == 'W')
5889 add_symbol(name, (type == 'W'), (Dwarf_Addr) addr, &high_addr);
5f0a03a6
JK
5890 }
5891
5f0a03a6
JK
5892 if (list_by_addr.size() < 1)
5893 {
5894 cerr << "Symbol table error: "
5895 << path << " contains no function symbols." << endl;
5896 return info_absent;
5897 }
2e67a43b 5898 sort();
5f0a03a6
JK
5899 return info_present;
5900}
5901
5902// NB: This currently unused. We use get_from_elf() instead because
5903// that gives us raw addresses -- which we need for modules -- whereas
5904// nm provides the address relative to the beginning of the section.
5905enum info_status
5906symbol_table::read_from_elf_file(const string &path)
5907{
5908 FILE *f;
5909 string cmd = string("/usr/bin/nm -n --defined-only ") + path;
5910 f = popen(cmd.c_str(), "r");
5911 if (!f)
5912 {
5913 // nm failures are detected by pclose, not popen.
5914 cerr << "Internal error reading symbol table from "
5915 << path << " -- " << strerror (errno);
5916 return info_absent;
5917 }
5918 enum info_status status = read_symbols(f, path);
5919 if (pclose(f) != 0)
5920 {
5921 if (status == info_present)
5922 cerr << "Warning: nm cannot read symbol table from " << path;
5923 return info_absent;
5924 }
5925 return status;
5926}
5927
5928enum info_status
5929symbol_table::read_from_text_file(const string& path)
5930{
5931 FILE *f = fopen(path.c_str(), "r");
5932 if (!f)
5933 {
5934 cerr << "Warning: cannot read symbol table from "
5935 << path << " -- " << strerror (errno);
5936 return info_absent;
5937 }
5938 enum info_status status = read_symbols(f, path);
5939 (void) fclose(f);
5940 return status;
5941}
5942
46f7b6be
JK
5943void
5944symbol_table::prepare_section_rejection(Dwfl_Module *mod)
5945{
5946#ifdef __powerpc__
5947 /*
5948 * The .opd section contains function descriptors that can look
5949 * just like function entry points. For example, there's a function
5950 * descriptor called "do_exit" that links to the entry point ".do_exit".
5951 * Reject all symbols in .opd.
5952 */
5953 opd_section = SHN_UNDEF;
5954 Dwarf_Addr bias;
5955 Elf* elf = (dwarf_getelf (dwfl_module_getdwarf (mod, &bias))
5956 ?: dwfl_module_getelf (mod, &bias));
5957 Elf_Scn* scn = 0;
5958 size_t shstrndx;
5959
5960 if (!elf)
5961 return;
5962 if (elf_getshstrndx(elf, &shstrndx) != 0)
5963 return;
5964 while ((scn = elf_nextscn(elf, scn)) != NULL)
5965 {
5966 GElf_Shdr shdr_mem;
5967 GElf_Shdr *shdr = gelf_getshdr(scn, &shdr_mem);
5968 if (!shdr)
5969 continue;
5970 const char *name = elf_strptr(elf, shstrndx, shdr->sh_name);
5971 if (!strcmp(name, ".opd"))
5972 {
5973 opd_section = elf_ndxscn(scn);
5974 return;
5975 }
5976 }
5977#endif
5978}
5979
5980bool
5981symbol_table::reject_section(GElf_Word section)
5982{
5983 if (section == SHN_UNDEF)
5984 return true;
5985#ifdef __powerpc__
5986 if (section == opd_section)
5987 return true;
5988#endif
5989 return false;
5990}
5991
5f0a03a6
JK
5992enum info_status
5993symbol_table::get_from_elf()
5994{
5995 Dwarf_Addr high_addr = 0;
5996 Dwfl_Module *mod = mod_info->mod;
5997 int syments = dwfl_module_getsymtab(mod);
5998 assert(syments);
46f7b6be 5999 prepare_section_rejection(mod);
5f0a03a6
JK
6000 for (int i = 1; i < syments; ++i)
6001 {
6002 GElf_Sym sym;
ab91b232
JK
6003 GElf_Word section;
6004 const char *name = dwfl_module_getsym(mod, i, &sym, &section);
46f7b6be
JK
6005 if (name && GELF_ST_TYPE(sym.st_info) == STT_FUNC &&
6006 !reject_section(section))
ab91b232
JK
6007 add_symbol(name, (GELF_ST_BIND(sym.st_info) == STB_WEAK),
6008 sym.st_value, &high_addr);
5f0a03a6 6009 }
2e67a43b 6010 sort();
5f0a03a6
JK
6011 return info_present;
6012}
6013
6014void
6015symbol_table::mark_dwarf_redundancies(dwflpp *dw)
6016{
6017 // dwflpp.cu_function_cache maps each module_name:cu_name to a
6018 // vector of Dwarf_Dies, one per function.
6019 string module_prefix = string(mod_info->name) + ":";
6020
73f289b2 6021 for (mod_cu_function_cache_t::iterator cu = dw->cu_function_cache.begin();
6561773f 6022 cu != dw->cu_function_cache.end(); cu++)
5f0a03a6
JK
6023 {
6024 string key = cu->first;
6025 if (key.find(module_prefix) == 0)
6026 {
6027 // Found a compilation unit in the module of interest.
6028 // Mark all its functions in the symbol table.
6561773f 6029 cu_function_cache_t* v = cu->second;
5f0a03a6 6030 assert(v);
6561773f 6031 for (cu_function_cache_t::iterator fc = v->begin(); fc != v->end(); fc++)
5f0a03a6 6032 {
6561773f
FCE
6033 Dwarf_Die func = fc->second;
6034 string func_name = fc->first; // == dwarf_diename(&func);
5f0a03a6
JK
6035 // map_by_name[func_name]->die = func;
6036 map<string, func_info*>::iterator i = map_by_name.find(func_name);
6037 // Func names can show up in the dwarf but not the symtab (!).
6038 if (i != map_by_name.end())
6039 {
6040 func_info *fi = i->second;
6041 fi->die = func;
6042 }
6043 }
6044 }
6045 }
6046}
6047
6048func_info *
6049symbol_table::get_func_containing_address(Dwarf_Addr addr)
6050{
2e67a43b
TM
6051 iterator_t iter = upper_bound(list_by_addr.begin(), list_by_addr.end(), addr,
6052 func_info::Compare());
6053 if (iter == list_by_addr.begin())
5f0a03a6 6054 return NULL;
2e67a43b
TM
6055 else
6056 return *(iter - 1);
5f0a03a6
JK
6057}
6058
6059func_info *
6060symbol_table::lookup_symbol(const string& name)
6061{
6062 map<string, func_info*>::iterator i = map_by_name.find(name);
6063 if (i == map_by_name.end())
6064 return NULL;
6065 return i->second;
6066}
6067
6068Dwarf_Addr
6069symbol_table::lookup_symbol_address(const string& name)
6070{
6071 func_info *fi = lookup_symbol(name);
6072 if (fi)
6073 return fi->addr;
6074 return 0;
6075}
6076
ab91b232
JK
6077// This is the kernel symbol table. The kernel macro cond_syscall creates
6078// a weak symbol for each system call and maps it to sys_ni_syscall.
6079// For system calls not implemented elsewhere, this weak symbol shows up
6080// in the kernel symbol table. Following the precedent of dwarfful stap,
6081// we refuse to consider such symbols. Here we delete them from our
6082// symbol table.
6083// TODO: Consider generalizing this and/or making it part of blacklist
6084// processing.
6085void
6086symbol_table::purge_syscall_stubs()
6087{
6088 Dwarf_Addr stub_addr = lookup_symbol_address("sys_ni_syscall");
6089 if (stub_addr == 0)
6090 return;
2e67a43b
TM
6091 range_t purge_range = equal_range(list_by_addr.begin(), list_by_addr.end(),
6092 stub_addr, func_info::Compare());
6093 for (iterator_t iter = purge_range.first;
6094 iter != purge_range.second;
6095 ++iter)
ab91b232 6096 {
2e67a43b
TM
6097 func_info *fi = *iter;
6098 if (fi->weak && fi->name != "sys_ni_syscall")
ab91b232 6099 {
2e67a43b
TM
6100 map_by_name.erase(fi->name);
6101 delete fi;
6102 *iter = 0;
6103 }
ab91b232 6104 }
2e67a43b
TM
6105 // Range might have null pointer entries that should be erased.
6106 list_by_addr.erase(remove(purge_range.first, purge_range.second,
6107 (func_info*)0),
6108 purge_range.second);
6109}
6110
6111void
6112symbol_table::sort()
6113{
6114 stable_sort(list_by_addr.begin(), list_by_addr.end(), func_info::Compare());
ab91b232
JK
6115}
6116
5f0a03a6
JK
6117void
6118module_info::get_symtab(dwarf_query *q)
6119{
6120 systemtap_session &sess = q->sess;
6121
6122 sym_table = new symbol_table(this);
6123 if (!elf_path.empty())
6124 {
6125 if (name == TOK_KERNEL && !sess.kernel_symtab_path.empty())
6126 cerr << "Warning: reading symbol table from "
6127 << elf_path
6128 << " -- ignoring "
6129 << sess.kernel_symtab_path
6130 << endl ;;
6131 symtab_status = sym_table->get_from_elf();
6132 }
6133 else
6134 {
6135 assert(name == TOK_KERNEL);
6136 if (sess.kernel_symtab_path.empty())
6137 {
6138 symtab_status = info_absent;
6139 cerr << "Error: Cannot find vmlinux."
6140 << " Consider using --kmap instead of --kelf."
6141 << endl;;
6142 }
6143 else
6144 {
6145 symtab_status =
6146 sym_table->read_from_text_file(sess.kernel_symtab_path);
6147 if (symtab_status == info_present)
6148 {
6149 sess.sym_kprobes_text_start =
6150 sym_table->lookup_symbol_address("__kprobes_text_start");
6151 sess.sym_kprobes_text_end =
6152 sym_table->lookup_symbol_address("__kprobes_text_end");
6153 sess.sym_stext = sym_table->lookup_symbol_address("_stext");
5f0a03a6
JK
6154 }
6155 }
6156 }
6157 if (symtab_status == info_absent)
6158 {
6159 delete sym_table;
6160 sym_table = NULL;
6161 return;
6162 }
6163
6164 // If we have dwarf for the same module, mark the redundant symtab
6165 // entries.
6166 //
6167 // In dwarf_query::handle_query_module(), the call to query_module_dwarf()
6168 // precedes the call to query_module_symtab(). So we should never read
6169 // a module's symbol table without first having tried to get its dwarf.
6170 sym_table->mark_dwarf_redundancies(&q->dw);
ab91b232
JK
6171
6172 if (name == TOK_KERNEL)
6173 sym_table->purge_syscall_stubs();
5f0a03a6
JK
6174}
6175
6176module_info::~module_info()
6177{
6178 if (sym_table)
6179 delete sym_table;
b55bc428
FCE
6180}
6181
6182
98afd80e 6183
935447c8
DS
6184// ------------------------------------------------------------------------
6185// task_finder derived 'probes': These don't really exist. The whole
6186// purpose of the task_finder_derived_probe_group is to make sure that
6187// stap_start_task_finder()/stap_stop_task_finder() get called only
6188// once and in the right place.
6189// ------------------------------------------------------------------------
6190
6191struct task_finder_derived_probe: public derived_probe
6192{
c295b10e
FCE
6193 // Dummy constructor for gcc 3.4 compatibility
6194 task_finder_derived_probe (): derived_probe (0) { assert(0); }
935447c8
DS
6195};
6196
6197
6198struct task_finder_derived_probe_group: public generic_dpg<task_finder_derived_probe>
6199{
6200public:
6201 static void create_session_group (systemtap_session& s);
6202
6203 void emit_module_decls (systemtap_session& ) { }
6204 void emit_module_init (systemtap_session& s);
6205 void emit_module_exit (systemtap_session& s);
6206};
6207
6208
6209void
6210task_finder_derived_probe_group::create_session_group (systemtap_session& s)
6211{
6212 if (! s.task_finder_derived_probes)
6d0f3f0c 6213 s.task_finder_derived_probes = new task_finder_derived_probe_group();
935447c8
DS
6214}
6215
6216
6217void
6218task_finder_derived_probe_group::emit_module_init (systemtap_session& s)
6219{
6220 s.op->newline();
6221 s.op->newline() << "/* ---- task finder ---- */";
6222 s.op->newline() << "rc = stap_start_task_finder();";
6223
6224 s.op->newline() << "if (rc) {";
6d0f3f0c 6225 s.op->newline(1) << "stap_stop_task_finder();";
935447c8
DS
6226 s.op->newline(-1) << "}";
6227}
6228
6229
6230void
6231task_finder_derived_probe_group::emit_module_exit (systemtap_session& s)
6232{
6233 s.op->newline();
6234 s.op->newline() << "/* ---- task finder ---- */";
6235 s.op->newline() << "stap_stop_task_finder();";
6236}
6237
a96d1db0
DN
6238// ------------------------------------------------------------------------
6239// itrace user-space probes
6240// ------------------------------------------------------------------------
6241
6242
6243struct itrace_derived_probe: public derived_probe
6244{
6245 bool has_path;
6246 string path;
6247 int64_t pid;
6248 int single_step;
6249
6250 itrace_derived_probe (systemtap_session &s, probe* p, probe_point* l,
6251 bool hp, string &pn, int64_t pd, int ss
6252 );
6253 void join_group (systemtap_session& s);
6254};
6255
6256
6257struct itrace_derived_probe_group: public generic_dpg<itrace_derived_probe>
6258{
6259private:
6260 map<string, vector<itrace_derived_probe*> > probes_by_path;
6261 typedef map<string, vector<itrace_derived_probe*> >::iterator p_b_path_iterator;
6262 map<int64_t, vector<itrace_derived_probe*> > probes_by_pid;
6263 typedef map<int64_t, vector<itrace_derived_probe*> >::iterator p_b_pid_iterator;
6264 unsigned num_probes;
6265
6266 void emit_probe_decl (systemtap_session& s, itrace_derived_probe *p);
6267
6268public:
6269 itrace_derived_probe_group(): num_probes(0) { }
6270
6271 void enroll (itrace_derived_probe* probe);
6272 void emit_module_decls (systemtap_session& s);
6273 void emit_module_init (systemtap_session& s);
6274 void emit_module_exit (systemtap_session& s);
6275};
6276
6277
6278itrace_derived_probe::itrace_derived_probe (systemtap_session &s,
6279 probe* p, probe_point* l,
6280 bool hp, string &pn, int64_t pd,
6281 int ss
6282 ):
6283 derived_probe(p, l), has_path(hp), path(pn), pid(pd), single_step(ss)
6284{
6285}
6286
6287
6288void
6289itrace_derived_probe::join_group (systemtap_session& s)
6290{
6291 if (! s.itrace_derived_probes)
6292 s.itrace_derived_probes = new itrace_derived_probe_group ();
6293
6294 s.itrace_derived_probes->enroll (this);
6295
6296 task_finder_derived_probe_group::create_session_group (s);
6297}
6298
6299struct itrace_builder: public derived_probe_builder
6300{
6301 itrace_builder() {}
6302 virtual void build(systemtap_session & sess,
6303 probe * base,
6304 probe_point * location,
6305 std::map<std::string, literal *> const & parameters,
6306 vector<derived_probe *> & finished_results)
6307 {
6308 string path;
28d29bd3 6309 int64_t pid = 0;
a96d1db0
DN
6310 int single_step;
6311
6312 bool has_path = get_param (parameters, TOK_PROCESS, path);
6313 bool has_pid = get_param (parameters, TOK_PROCESS, pid);
28d29bd3 6314 // XXX: PR 6445 needs !has_path && !has_pid support
a96d1db0
DN
6315 assert (has_path || has_pid);
6316
6317 single_step = 1;
6318
6319 // If we have a path, we need to validate it.
6320 if (has_path)
d0a7f5a9 6321 path = find_executable (path);
a96d1db0
DN
6322
6323 finished_results.push_back(new itrace_derived_probe(sess, base, location,
6324 has_path, path, pid,
d0a7f5a9 6325 single_step
a96d1db0
DN
6326 ));
6327 }
6328};
6329
6330
6331void
6332itrace_derived_probe_group::enroll (itrace_derived_probe* p)
6333{
6334 if (p->has_path)
6335 probes_by_path[p->path].push_back(p);
6336 else
6337 probes_by_pid[p->pid].push_back(p);
6338 num_probes++;
6339
6340 // XXX: multiple exec probes (for instance) for the same path (or
6341 // pid) should all share a itrace report function, and have their
6342 // handlers executed sequentially.
6343}
6344
6345
6346void
6347itrace_derived_probe_group::emit_probe_decl (systemtap_session& s,
6348 itrace_derived_probe *p)
6349{
6350 s.op->newline() << "{";
6351 s.op->line() << " .tgt={";
6352
6353 if (p->has_path)
6354 {
6355 s.op->line() << " .pathname=\"" << p->path << "\",";
6356 s.op->line() << " .pid=0,";
6357 }
6358 else
6359 {
6360 s.op->line() << " .pathname=NULL,";
6361 s.op->line() << " .pid=" << p->pid << ",";
6362 }
6363
6364 s.op->line() << " .callback=&_stp_itrace_probe_cb,";
6365 s.op->line() << " },";
6366 s.op->line() << " .pp=" << lex_cast_qstring (*p->sole_location()) << ",";
6367 s.op->line() << " .single_step=" << p->single_step << ",";
6368 s.op->line() << " .ph=&" << p->name << ",";
6369
6370 s.op->line() << " },";
6371}
6372
6373
6374void
6375itrace_derived_probe_group::emit_module_decls (systemtap_session& s)
6376{
6377 if (probes_by_path.empty() && probes_by_pid.empty())
6378 return;
6379
6380 s.op->newline();
6381 s.op->newline() << "/* ---- itrace probes ---- */";
1324cc82 6382 s.op->newline() << "#include \"task_finder.c\"";
a96d1db0
DN
6383 s.op->newline() << "struct stap_itrace_probe {";
6384 s.op->indent(1);
6385 s.op->newline() << "struct stap_task_finder_target tgt;";
6386 s.op->newline() << "const char *pp;";
6387 s.op->newline() << "void (*ph) (struct context*);";
6388 s.op->newline() << "int single_step;";
6389 s.op->newline(-1) << "};";
6390 s.op->newline() << "static void enter_itrace_probe(struct stap_itrace_probe *p, struct pt_regs *regs, void *data);";
6391 s.op->newline() << "#include \"itrace.c\"";
6392
6393 // output routine to call itrace probe
6394 s.op->newline() << "static void enter_itrace_probe(struct stap_itrace_probe *p, struct pt_regs *regs, void *data) {";
6395 s.op->indent(1);
6396
c12d974f 6397 common_probe_entryfn_prologue (s.op, "STAP_SESSION_RUNNING", "p->pp");
a96d1db0
DN
6398 s.op->newline() << "c->regs = regs;";
6399 s.op->newline() << "c->data = data;";
6400
6401 // call probe function
6402 s.op->newline() << "(*p->ph) (c);";
6403 common_probe_entryfn_epilogue (s.op);
6404
6405 s.op->newline() << "return;";
6406 s.op->newline(-1) << "}";
6407
6408 // Output task finder callback routine that gets called for all
6409 // itrace probe types.
46b3c6cd 6410 s.op->newline() << "static int _stp_itrace_probe_cb(struct stap_task_finder_target *tgt, struct task_struct *tsk, int register_p, int process_p) {";
a96d1db0
DN
6411 s.op->indent(1);
6412 s.op->newline() << "int rc = 0;";
6413 s.op->newline() << "struct stap_itrace_probe *p = container_of(tgt, struct stap_itrace_probe, tgt);";
6414
6415 s.op->newline() << "if (register_p) ";
6416 s.op->indent(1);
6417
6418 s.op->newline() << "rc = usr_itrace_init(p->single_step, tsk->pid, p);";
6419 s.op->newline(-1) << "else";
6420 s.op->newline(1) << "remove_usr_itrace_info(find_itrace_info(p->tgt.pid));";
6421 s.op->newline(-1) << "return rc;";
6422 s.op->newline(-1) << "}";
6423
4c2732a1 6424 s.op->newline() << "static struct stap_itrace_probe stap_itrace_probes[] = {";
a96d1db0
DN
6425 s.op->indent(1);
6426
6427 // Set up 'process(PATH)' probes
6428 if (! probes_by_path.empty())
6429 {
6430 for (p_b_path_iterator it = probes_by_path.begin();
6431 it != probes_by_path.end(); it++)
6432 {
6433 for (unsigned i = 0; i < it->second.size(); i++)
6434 {
6435 itrace_derived_probe *p = it->second[i];
6436 emit_probe_decl(s, p);
6437 }
6438 }
6439 }
6440
6441 // Set up 'process(PID)' probes
6442 if (! probes_by_pid.empty())
6443 {
6444 for (p_b_pid_iterator it = probes_by_pid.begin();
6445 it != probes_by_pid.end(); it++)
6446 {
6447 for (unsigned i = 0; i < it->second.size(); i++)
6448 {
6449 itrace_derived_probe *p = it->second[i];
6450 emit_probe_decl(s, p);
6451 }
6452 }
6453 }
6454 s.op->newline(-1) << "};";
6455}
6456
6457
6458void
6459itrace_derived_probe_group::emit_module_init (systemtap_session& s)
6460{
6461 if (probes_by_path.empty() && probes_by_pid.empty())
6462 return;
6463
6464 s.op->newline();
6465 s.op->newline() << "/* ---- itrace probes ---- */";
6466
6467 s.op->newline() << "for (i=0; i<" << num_probes << "; i++) {";
6468 s.op->indent(1);
6469 s.op->newline() << "struct stap_itrace_probe *p = &stap_itrace_probes[i];";
6470 s.op->newline() << "rc = stap_register_task_finder_target(&p->tgt);";
6471 s.op->newline(-1) << "}";
6472}
6473
6474
6475void
6476itrace_derived_probe_group::emit_module_exit (systemtap_session& s)
6477{
6478 if (probes_by_path.empty() && probes_by_pid.empty()) return;
6479 s.op->newline();
6480 s.op->newline() << "/* ---- itrace probes ---- */";
6481 s.op->newline() << "cleanup_usr_itrace();";
6482}
935447c8
DS
6483
6484// ------------------------------------------------------------------------
6485// utrace user-space probes
6486// ------------------------------------------------------------------------
6487
eff6ac72 6488static string TOK_THREAD("thread");
12b21830
DS
6489static string TOK_SYSCALL("syscall");
6490
eff6ac72
DS
6491// Note that these flags don't match up exactly with UTRACE_EVENT
6492// flags (and that's OK).
935447c8
DS
6493enum utrace_derived_probe_flags {
6494 UDPF_NONE,
eff6ac72
DS
6495 UDPF_BEGIN, // process begin
6496 UDPF_END, // process end
6497 UDPF_THREAD_BEGIN, // thread begin
6498 UDPF_THREAD_END, // thread end
6499 UDPF_SYSCALL, // syscall entry
6500 UDPF_SYSCALL_RETURN, // syscall exit
935447c8
DS
6501 UDPF_NFLAGS
6502};
6503
6504struct utrace_derived_probe: public derived_probe
6505{
6506 bool has_path;
6507 string path;
6508 int64_t pid;
6509 enum utrace_derived_probe_flags flags;
6510 bool target_symbol_seen;
6511
6512 utrace_derived_probe (systemtap_session &s, probe* p, probe_point* l,
6513 bool hp, string &pn, int64_t pd,
6514 enum utrace_derived_probe_flags f);
6515 void join_group (systemtap_session& s);
6516};
6517
6518
6519struct utrace_derived_probe_group: public generic_dpg<utrace_derived_probe>
6520{
6521private:
6522 map<string, vector<utrace_derived_probe*> > probes_by_path;
6523 typedef map<string, vector<utrace_derived_probe*> >::iterator p_b_path_iterator;
6524 map<int64_t, vector<utrace_derived_probe*> > probes_by_pid;
6525 typedef map<int64_t, vector<utrace_derived_probe*> >::iterator p_b_pid_iterator;
6526 unsigned num_probes;
6527 bool flags_seen[UDPF_NFLAGS];
6528
6529 void emit_probe_decl (systemtap_session& s, utrace_derived_probe *p);
a21d81ec
DS
6530 void emit_vm_callback_probe_decl (systemtap_session& s, bool has_path,
6531 string path, int64_t pid,
6532 string vm_callback);
935447c8
DS
6533
6534public:
6535 utrace_derived_probe_group(): num_probes(0), flags_seen() { }
6536
6537 void enroll (utrace_derived_probe* probe);
6538 void emit_module_decls (systemtap_session& s);
6539 void emit_module_init (systemtap_session& s);
6540 void emit_module_exit (systemtap_session& s);
6541};
6542
6543
de688825 6544struct utrace_var_expanding_visitor: public var_expanding_visitor
935447c8 6545{
de688825
JS
6546 utrace_var_expanding_visitor(systemtap_session& s, const string& pn,
6547 enum utrace_derived_probe_flags f):
935447c8
DS
6548 sess (s), probe_name (pn), flags (f), target_symbol_seen (false) {}
6549
6550 systemtap_session& sess;
6551 string probe_name;
6552 enum utrace_derived_probe_flags flags;
6553 bool target_symbol_seen;
6554
6270adc1 6555 void visit_target_symbol_arg (target_symbol* e);
5d67b47c 6556 void visit_target_symbol_context (target_symbol* e);
935447c8
DS
6557 void visit_target_symbol (target_symbol* e);
6558};
6559
6560
a7a68293 6561
935447c8
DS
6562utrace_derived_probe::utrace_derived_probe (systemtap_session &s,
6563 probe* p, probe_point* l,
6564 bool hp, string &pn, int64_t pd,
6565 enum utrace_derived_probe_flags f):
d0a7f5a9
FCE
6566 derived_probe (p, new probe_point (*l) /* .components soon rewritten */ ),
6567 has_path(hp), path(pn), pid(pd), flags(f),
935447c8
DS
6568 target_symbol_seen(false)
6569{
de688825
JS
6570 // Expand local variables in the probe body
6571 utrace_var_expanding_visitor v (s, name, flags);
6572 this->body = v.require (this->body);
935447c8 6573 target_symbol_seen = v.target_symbol_seen;
d0a7f5a9
FCE
6574
6575 // Reset the sole element of the "locations" vector as a
6576 // "reverse-engineered" form of the incoming (q.base_loc) probe
6577 // point. This allows a user to see what program etc.
6578 // number any particular match of the wildcards.
6579
6580 vector<probe_point::component*> comps;
6581 if (hp)
6582 comps.push_back (new probe_point::component(TOK_PROCESS, new literal_string(path)));
e56e51c9 6583 else if (pid != 0)
06aca46a 6584 comps.push_back (new probe_point::component(TOK_PROCESS, new literal_number(pid)));
e56e51c9
FCE
6585 else
6586 comps.push_back (new probe_point::component(TOK_PROCESS));
6587
d0a7f5a9
FCE
6588 switch (flags)
6589 {
6590 case UDPF_THREAD_BEGIN:
6591 comps.push_back (new probe_point::component(TOK_THREAD));
6592 comps.push_back (new probe_point::component(TOK_BEGIN));
6593 break;
6594 case UDPF_THREAD_END:
6595 comps.push_back (new probe_point::component(TOK_THREAD));
6596 comps.push_back (new probe_point::component(TOK_END));
6597 break;
6598 case UDPF_SYSCALL:
6599 comps.push_back (new probe_point::component(TOK_SYSCALL));
6600 break;
6601 case UDPF_SYSCALL_RETURN:
6602 comps.push_back (new probe_point::component(TOK_SYSCALL));
6603 comps.push_back (new probe_point::component(TOK_RETURN));
6604 break;
6605 case UDPF_BEGIN:
6606 comps.push_back (new probe_point::component(TOK_BEGIN));
6607 break;
6608 case UDPF_END:
6609 comps.push_back (new probe_point::component(TOK_END));
6610 break;
06aca46a 6611 default:
d0a7f5a9
FCE
6612 assert (0);
6613 }
6614
6615 // Overwrite it.
6616 this->sole_location()->components = comps;
935447c8
DS
6617}
6618
6619
6620void
6621utrace_derived_probe::join_group (systemtap_session& s)
6622{
6623 if (! s.utrace_derived_probes)
14cdaa0b 6624 {
935447c8 6625 s.utrace_derived_probes = new utrace_derived_probe_group ();
14cdaa0b 6626 }
935447c8
DS
6627 s.utrace_derived_probes->enroll (this);
6628
6629 task_finder_derived_probe_group::create_session_group (s);
6630}
6631
6632
6633void
de688825 6634utrace_var_expanding_visitor::visit_target_symbol_arg (target_symbol* e)
935447c8 6635{
6270adc1 6636 string argnum_s = e->base_name.substr(4,e->base_name.length()-4);
3a4e19b8 6637 int argnum = lex_cast<int>(argnum_s);
935447c8 6638
6270adc1
MH
6639 if (flags != UDPF_SYSCALL)
6640 throw semantic_error ("only \"process(PATH_OR_PID).syscall\" support $argN.", e->tok);
935447c8 6641
6270adc1
MH
6642 if (e->components.size() > 0)
6643 {
6644 switch (e->components[0].first)
6645 {
6646 case target_symbol::comp_literal_array_index:
6647 throw semantic_error("utrace target variable '$argN' may not be used as array",
6648 e->tok);
6649 break;
6650 case target_symbol::comp_struct_member:
6651 throw semantic_error("utrace target variable '$argN' may not be used as a structure",
6652 e->tok);
6653 break;
6654 default:
6655 throw semantic_error ("invalid use of utrace target variable '$argN'",
6656 e->tok);
6657 break;
6658 }
6659 }
6660
6661 // FIXME: max argnument number should not be hardcoded.
6662 if (argnum < 1 || argnum > 6)
6663 throw semantic_error ("invalid syscall argument number (1-6)", e->tok);
6664
6665 bool lvalue = is_active_lvalue(e);
6666 if (lvalue)
6667 throw semantic_error("utrace '$argN' variable is read-only", e->tok);
935447c8 6668
6270adc1
MH
6669 // Remember that we've seen a target variable.
6670 target_symbol_seen = true;
6671
6672 // We're going to substitute a synthesized '_utrace_syscall_arg'
6673 // function call for the '$argN' reference.
6674 functioncall* n = new functioncall;
6675 n->tok = e->tok;
6676 n->function = "_utrace_syscall_arg";
6677 n->referent = 0; // NB: must not resolve yet, to ensure inclusion in session
6678
6679 literal_number *num = new literal_number(argnum - 1);
6680 num->tok = e->tok;
6681 n->args.push_back(num);
6682
4ed05b15 6683 provide (n);
6270adc1
MH
6684}
6685
6686void
de688825 6687utrace_var_expanding_visitor::visit_target_symbol_context (target_symbol* e)
6270adc1 6688{
5d67b47c
MH
6689 string sname = e->base_name;
6690
935447c8
DS
6691 if (e->components.size() > 0)
6692 {
6693 switch (e->components[0].first)
6694 {
6695 case target_symbol::comp_literal_array_index:
5d67b47c 6696 throw semantic_error("utrace target variable '" + sname + "' may not be used as array",
935447c8
DS
6697 e->tok);
6698 break;
6699 case target_symbol::comp_struct_member:
5d67b47c 6700 throw semantic_error("utrace target variable '" + sname + "' may not be used as a structure",
935447c8
DS
6701 e->tok);
6702 break;
6703 default:
5d67b47c 6704 throw semantic_error ("invalid use of utrace target variable '" + sname + "'",
935447c8
DS
6705 e->tok);
6706 break;
6707 }
6708 }
6709
6710 bool lvalue = is_active_lvalue(e);
6711 if (lvalue)
5d67b47c
MH
6712 throw semantic_error("utrace '" + sname + "' variable is read-only", e->tok);
6713
6714 string fname;
6715 if (sname == "$return")
6716 {
6717 if (flags != UDPF_SYSCALL_RETURN)
6718 throw semantic_error ("only \"process(PATH_OR_PID).syscall.return\" support $return.", e->tok);
6719 fname = "_utrace_syscall_return";
6720 }
6721 else
6722 fname = "_utrace_syscall_nr";
935447c8
DS
6723
6724 // Remember that we've seen a target variable.
6725 target_symbol_seen = true;
6726
6270adc1 6727 // We're going to substitute a synthesized '_utrace_syscall_nr'
a7a68293 6728 // function call for the '$syscall' reference.
935447c8
DS
6729 functioncall* n = new functioncall;
6730 n->tok = e->tok;
5d67b47c 6731 n->function = fname;
935447c8
DS
6732 n->referent = 0; // NB: must not resolve yet, to ensure inclusion in session
6733
4ed05b15 6734 provide (n);
935447c8
DS
6735}
6736
6270adc1 6737void
de688825 6738utrace_var_expanding_visitor::visit_target_symbol (target_symbol* e)
6270adc1
MH
6739{
6740 assert(e->base_name.size() > 0 && e->base_name[0] == '$');
6741
6742 if (flags != UDPF_SYSCALL && flags != UDPF_SYSCALL_RETURN)
6743 throw semantic_error ("only \"process(PATH_OR_PID).syscall\" and \"process(PATH_OR_PID).syscall.return\" probes support target symbols",
6744 e->tok);
6745
6746 if (e->base_name.substr(0,4) == "$arg")
6747 visit_target_symbol_arg(e);
5d67b47c
MH
6748 else if (e->base_name == "$syscall" || e->base_name == "$return")
6749 visit_target_symbol_context(e);
6270adc1 6750 else
5d67b47c 6751 throw semantic_error ("invalid target symbol for utrace probe, $syscall, $return or $argN expected",
6270adc1
MH
6752 e->tok);
6753}
6754
935447c8
DS
6755
6756struct utrace_builder: public derived_probe_builder
6757{
6758 utrace_builder() {}
6759 virtual void build(systemtap_session & sess,
6760 probe * base,
6761 probe_point * location,
86bf665e 6762 literal_map_t const & parameters,
935447c8
DS
6763 vector<derived_probe *> & finished_results)
6764 {
6765 string path;
6766 int64_t pid;
6767
6768 bool has_path = get_param (parameters, TOK_PROCESS, path);
6769 bool has_pid = get_param (parameters, TOK_PROCESS, pid);
6770 enum utrace_derived_probe_flags flags = UDPF_NONE;
d0a7f5a9 6771
eff6ac72
DS
6772 if (has_null_param (parameters, TOK_THREAD))
6773 {
6774 if (has_null_param (parameters, TOK_BEGIN))
6775 flags = UDPF_THREAD_BEGIN;
6776 else if (has_null_param (parameters, TOK_END))
6777 flags = UDPF_THREAD_END;
6778 }
12b21830 6779 else if (has_null_param (parameters, TOK_SYSCALL))
935447c8
DS
6780 {
6781 if (has_null_param (parameters, TOK_RETURN))
eff6ac72 6782 flags = UDPF_SYSCALL_RETURN;
935447c8 6783 else
eff6ac72 6784 flags = UDPF_SYSCALL;
935447c8 6785 }
eff6ac72
DS
6786 else if (has_null_param (parameters, TOK_BEGIN))
6787 flags = UDPF_BEGIN;
6788 else if (has_null_param (parameters, TOK_END))
6789 flags = UDPF_END;
935447c8 6790
986e98de
DS
6791 // If we didn't get a path or pid, this means to probe everything.
6792 // Convert this to a pid-based probe.
6793 if (! has_path && ! has_pid)
6794 {
6795 has_path = false;
6796 path.clear();
6797 has_pid = true;
6798 pid = 0;
6799 }
c569c2e4
FCE
6800 else if (has_path)
6801 {
6802 path = find_executable (path);
6803 sess.unwindsym_modules.insert (path);
6804 }
986e98de 6805 else if (has_pid)
6cdf2889 6806 {
c569c2e4 6807 // We can't probe 'init' (pid 1). XXX: where does this limitation come from?
6cdf2889
DS
6808 if (pid < 2)
6809 throw semantic_error ("process pid must be greater than 1",
6810 location->tok);
28d29bd3
FCE
6811
6812 // XXX: could we use /proc/$pid/exe in unwindsym_modules and elsewhere?
6cdf2889 6813 }
0744f531 6814
935447c8
DS
6815 finished_results.push_back(new utrace_derived_probe(sess, base, location,
6816 has_path, path, pid,
6817 flags));
6818 }
6819};
6820
6821
6822void
6823utrace_derived_probe_group::enroll (utrace_derived_probe* p)
6824{
6825 if (p->has_path)
6826 probes_by_path[p->path].push_back(p);
6827 else
6828 probes_by_pid[p->pid].push_back(p);
6829 num_probes++;
6830 flags_seen[p->flags] = true;
6831
6832 // XXX: multiple exec probes (for instance) for the same path (or
6833 // pid) should all share a utrace report function, and have their
6834 // handlers executed sequentially.
6835}
6836
6837
6838void
6839utrace_derived_probe_group::emit_probe_decl (systemtap_session& s,
6840 utrace_derived_probe *p)
6841{
6842 s.op->newline() << "{";
6843 s.op->line() << " .tgt={";
6844
6845 if (p->has_path)
6846 {
6847 s.op->line() << " .pathname=\"" << p->path << "\",";
6848 s.op->line() << " .pid=0,";
6849 }
6850 else
6851 {
6852 s.op->line() << " .pathname=NULL,";
6853 s.op->line() << " .pid=" << p->pid << ",";
6854 }
6855
6856 s.op->line() << " .callback=&_stp_utrace_probe_cb,";
8253e3b8 6857 s.op->line() << " .vm_callback=NULL,";
935447c8
DS
6858 s.op->line() << " },";
6859 s.op->line() << " .pp=" << lex_cast_qstring (*p->sole_location()) << ",";
6860 s.op->line() << " .ph=&" << p->name << ",";
6861
6862 // Handle flags
6863 switch (p->flags)
6864 {
b20bac3a
DS
6865 // Notice that we'll just call the probe directly when we get
6866 // notified, since the task_finder layer stops the thread for us.
eff6ac72
DS
6867 case UDPF_BEGIN: // process begin
6868 s.op->line() << " .flags=(UDPF_BEGIN),";
935447c8 6869 break;
eff6ac72
DS
6870 case UDPF_THREAD_BEGIN: // thread begin
6871 s.op->line() << " .flags=(UDPF_THREAD_BEGIN),";
159cb109 6872 break;
eff6ac72
DS
6873
6874 // Notice we're not setting up a .ops/.report_death handler for
6875 // either UDPF_END or UDPF_THREAD_END. Instead, we'll just call
6876 // the probe directly when we get notified.
6877 case UDPF_END: // process end
6878 s.op->line() << " .flags=(UDPF_END),";
935447c8 6879 break;
eff6ac72
DS
6880 case UDPF_THREAD_END: // thread end
6881 s.op->line() << " .flags=(UDPF_THREAD_END),";
6882 break;
6883
6884 // For UDPF_SYSCALL/UDPF_SYSCALL_RETURN probes, the .report_death
6885 // handler isn't strictly necessary. However, it helps to keep
b20bac3a
DS
6886 // our attaches/detaches symmetrical. Since the task_finder layer
6887 // stops the thread, that works around bug 6841.
eff6ac72
DS
6888 case UDPF_SYSCALL:
6889 s.op->line() << " .flags=(UDPF_SYSCALL),";
b20bac3a
DS
6890 s.op->line() << " .ops={ .report_syscall_entry=stap_utrace_probe_syscall, .report_death=stap_utrace_task_finder_report_death },";
6891 s.op->line() << " .events=(UTRACE_EVENT(SYSCALL_ENTRY)|UTRACE_EVENT(DEATH)),";
935447c8 6892 break;
eff6ac72
DS
6893 case UDPF_SYSCALL_RETURN:
6894 s.op->line() << " .flags=(UDPF_SYSCALL_RETURN),";
b20bac3a
DS
6895 s.op->line() << " .ops={ .report_syscall_exit=stap_utrace_probe_syscall, .report_death=stap_utrace_task_finder_report_death },";
6896 s.op->line() << " .events=(UTRACE_EVENT(SYSCALL_EXIT)|UTRACE_EVENT(DEATH)),";
935447c8 6897 break;
930a1798 6898
a21d81ec
DS
6899 case UDPF_NONE:
6900 s.op->line() << " .flags=(UDPF_NONE),";
6901 s.op->line() << " .ops={ },";
6902 s.op->line() << " .events=0,";
6903 break;
935447c8
DS
6904 default:
6905 throw semantic_error ("bad utrace probe flag");
6906 break;
6907 }
6908 s.op->line() << " .engine_attached=0,";
6909 s.op->line() << " },";
6910}
6911
6912
a21d81ec
DS
6913void
6914utrace_derived_probe_group::emit_vm_callback_probe_decl (systemtap_session& s,
6915 bool has_path,
6916 string path,
6917 int64_t pid,
6918 string vm_callback)
6919{
6920 s.op->newline() << "{";
6921 s.op->line() << " .tgt={";
6922
6923 if (has_path)
6924 {
6925 s.op->line() << " .pathname=\"" << path << "\",";
6926 s.op->line() << " .pid=0,";
6927 }
6928 else
6929 {
6930 s.op->line() << " .pathname=NULL,";
6931 s.op->line() << " .pid=" << pid << ",";
6932 }
6933
6934 s.op->line() << " .callback=NULL,";
6935 s.op->line() << " .vm_callback=&" << vm_callback << ",";
6936 s.op->line() << " },";
6937 s.op->line() << " .pp=\"internal\",";
6938 s.op->line() << " .ph=NULL,";
6939 s.op->line() << " .flags=(UDPF_NONE),";
6940 s.op->line() << " .ops={ NULL },";
6941 s.op->line() << " .events=0,";
6942 s.op->line() << " .engine_attached=0,";
6943 s.op->line() << " },";
6944}
6945
6946
935447c8
DS
6947void
6948utrace_derived_probe_group::emit_module_decls (systemtap_session& s)
6949{
6950 if (probes_by_path.empty() && probes_by_pid.empty())
6951 return;
6952
6953 s.op->newline();
6954 s.op->newline() << "/* ---- utrace probes ---- */";
104c6237
FCE
6955 s.op->newline() << "#include \"task_finder.c\"";
6956
eff6ac72
DS
6957 s.op->newline() << "enum utrace_derived_probe_flags {";
6958 s.op->indent(1);
6959 s.op->newline() << "UDPF_NONE,";
6960 s.op->newline() << "UDPF_BEGIN,";
6961 s.op->newline() << "UDPF_END,";
6962 s.op->newline() << "UDPF_THREAD_BEGIN,";
6963 s.op->newline() << "UDPF_THREAD_END,";
6964 s.op->newline() << "UDPF_SYSCALL,";
6965 s.op->newline() << "UDPF_SYSCALL_RETURN,";
6966 s.op->newline() << "UDPF_NFLAGS";
6967 s.op->newline(-1) << "};";
6968
935447c8
DS
6969 s.op->newline() << "struct stap_utrace_probe {";
6970 s.op->indent(1);
6971 s.op->newline() << "struct stap_task_finder_target tgt;";
6972 s.op->newline() << "const char *pp;";
6973 s.op->newline() << "void (*ph) (struct context*);";
eff6ac72 6974 s.op->newline() << "enum utrace_derived_probe_flags flags;";
935447c8 6975 s.op->newline() << "struct utrace_engine_ops ops;";
eff6ac72 6976 s.op->newline() << "unsigned long events;";
935447c8
DS
6977 s.op->newline() << "int engine_attached;";
6978 s.op->newline(-1) << "};";
6979
eff6ac72 6980
b20bac3a
DS
6981 // Output handler function for UDPF_BEGIN, UDPF_THREAD_BEGIN,
6982 // UDPF_END, and UDPF_THREAD_END
6983 if (flags_seen[UDPF_BEGIN] || flags_seen[UDPF_THREAD_BEGIN]
6984 || flags_seen[UDPF_END] || flags_seen[UDPF_THREAD_END])
159cb109 6985 {
935447c8
DS
6986 s.op->newline() << "static void stap_utrace_probe_handler(struct task_struct *tsk, struct stap_utrace_probe *p) {";
6987 s.op->indent(1);
6988
c12d974f 6989 common_probe_entryfn_prologue (s.op, "STAP_SESSION_RUNNING", "p->pp");
935447c8
DS
6990
6991 // call probe function
6992 s.op->newline() << "(*p->ph) (c);";
6993 common_probe_entryfn_epilogue (s.op);
6994
6995 s.op->newline() << "return;";
6996 s.op->newline(-1) << "}";
159cb109 6997 }
935447c8
DS
6998
6999 // Output handler function for SYSCALL_ENTRY and SYSCALL_EXIT events
eff6ac72 7000 if (flags_seen[UDPF_SYSCALL] || flags_seen[UDPF_SYSCALL_RETURN])
935447c8 7001 {
4550733e 7002 s.op->newline() << "#ifdef UTRACE_ORIG_VERSION";
935447c8 7003 s.op->newline() << "static u32 stap_utrace_probe_syscall(struct utrace_attached_engine *engine, struct task_struct *tsk, struct pt_regs *regs) {";
4550733e
DS
7004 s.op->newline() << "#else";
7005 s.op->newline() << "static u32 stap_utrace_probe_syscall(enum utrace_resume_action action, struct utrace_attached_engine *engine, struct task_struct *tsk, struct pt_regs *regs) {";
7006 s.op->newline() << "#endif";
7007
935447c8
DS
7008 s.op->indent(1);
7009 s.op->newline() << "struct stap_utrace_probe *p = (struct stap_utrace_probe *)engine->data;";
7010
c12d974f 7011 common_probe_entryfn_prologue (s.op, "STAP_SESSION_RUNNING", "p->pp");
935447c8
DS
7012 s.op->newline() << "c->regs = regs;";
7013
7014 // call probe function
7015 s.op->newline() << "(*p->ph) (c);";
7016 common_probe_entryfn_epilogue (s.op);
7017
b20bac3a
DS
7018 s.op->newline() << "if ((atomic_read (&session_state) != STAP_SESSION_STARTING) && (atomic_read (&session_state) != STAP_SESSION_RUNNING)) {";
7019 s.op->indent(1);
7020 s.op->newline() << "debug_task_finder_detach();";
7021 s.op->newline() << "return UTRACE_DETACH;";
7022 s.op->newline(-1) << "}";
4550733e 7023 s.op->newline() << "return UTRACE_RESUME;";
935447c8
DS
7024 s.op->newline(-1) << "}";
7025 }
7026
eff6ac72 7027 // Output task_finder callback routine that gets called for all
935447c8 7028 // utrace probe types.
46b3c6cd 7029 s.op->newline() << "static int _stp_utrace_probe_cb(struct stap_task_finder_target *tgt, struct task_struct *tsk, int register_p, int process_p) {";
935447c8
DS
7030 s.op->indent(1);
7031 s.op->newline() << "int rc = 0;";
7032 s.op->newline() << "struct stap_utrace_probe *p = container_of(tgt, struct stap_utrace_probe, tgt);";
7033 s.op->newline() << "struct utrace_attached_engine *engine;";
7034
935447c8
DS
7035 s.op->newline() << "if (register_p) {";
7036 s.op->indent(1);
7037
0744f531 7038 s.op->newline() << "switch (p->flags) {";
935447c8 7039 s.op->indent(1);
eff6ac72
DS
7040
7041 // When receiving a UTRACE_EVENT(CLONE) event, we can't call the
7042 // begin/thread.begin probe directly. So, we'll just attach an
7043 // engine that waits for the thread to quiesce. When the thread
7044 // quiesces, then call the probe.
7045 if (flags_seen[UDPF_BEGIN])
7046 {
7047 s.op->newline() << "case UDPF_BEGIN:";
37e24fbe 7048 s.op->indent(1);
eff6ac72 7049 s.op->newline() << "if (process_p) {";
37e24fbe 7050 s.op->indent(1);
b20bac3a 7051 s.op->newline() << "stap_utrace_probe_handler(tsk, p);";
37e24fbe
DS
7052 s.op->newline(-1) << "}";
7053 s.op->newline() << "break;";
7054 s.op->indent(-1);
eff6ac72
DS
7055 }
7056 if (flags_seen[UDPF_THREAD_BEGIN])
7057 {
7058 s.op->newline() << "case UDPF_THREAD_BEGIN:";
0744f531 7059 s.op->indent(1);
eff6ac72 7060 s.op->newline() << "if (! process_p) {";
cfac4b1f 7061 s.op->indent(1);
b20bac3a 7062 s.op->newline() << "stap_utrace_probe_handler(tsk, p);";
cfac4b1f 7063 s.op->newline(-1) << "}";
0744f531
DS
7064 s.op->newline() << "break;";
7065 s.op->indent(-1);
eff6ac72
DS
7066 }
7067
7068 // For end/thread_end probes, do nothing at registration time.
7069 // We'll handle these in the 'register_p == 0' case.
7070 if (flags_seen[UDPF_END] || flags_seen[UDPF_THREAD_END])
0744f531 7071 {
eff6ac72
DS
7072 s.op->newline() << "case UDPF_END:";
7073 s.op->newline() << "case UDPF_THREAD_END:";
0744f531
DS
7074 s.op->indent(1);
7075 s.op->newline() << "break;";
7076 s.op->indent(-1);
7077 }
eff6ac72 7078
37e24fbe 7079 // Attach an engine for SYSCALL_ENTRY and SYSCALL_EXIT events.
eff6ac72 7080 if (flags_seen[UDPF_SYSCALL] || flags_seen[UDPF_SYSCALL_RETURN])
0744f531 7081 {
eff6ac72
DS
7082 s.op->newline() << "case UDPF_SYSCALL:";
7083 s.op->newline() << "case UDPF_SYSCALL_RETURN:";
0744f531 7084 s.op->indent(1);
eff6ac72
DS
7085 s.op->newline() << "rc = stap_utrace_attach(tsk, &p->ops, p, p->events);";
7086 s.op->newline() << "if (rc == 0) {";
0744f531 7087 s.op->indent(1);
0744f531
DS
7088 s.op->newline() << "p->engine_attached = 1;";
7089 s.op->newline(-1) << "}";
7090 s.op->newline() << "break;";
7091 s.op->indent(-1);
7092 }
eff6ac72
DS
7093
7094 s.op->newline() << "default:";
7095 s.op->indent(1);
7096 s.op->newline() << "_stp_error(\"unhandled flag value %d at %s:%d\", p->flags, __FUNCTION__, __LINE__);";
7097 s.op->newline() << "break;";
7098 s.op->indent(-1);
935447c8
DS
7099 s.op->newline(-1) << "}";
7100 s.op->newline(-1) << "}";
eff6ac72 7101
935447c8 7102 // Since this engine could be attached to multiple threads, don't
b20bac3a
DS
7103 // call stap_utrace_detach_ops() here, only call
7104 // stap_utrace_detach() as necessary.
0744f531 7105 s.op->newline() << "else {";
935447c8 7106 s.op->indent(1);
37e24fbe
DS
7107 s.op->newline() << "switch (p->flags) {";
7108 s.op->indent(1);
0744f531 7109 // For death probes, go ahead and call the probe directly.
eff6ac72 7110 if (flags_seen[UDPF_END])
0744f531 7111 {
eff6ac72 7112 s.op->newline() << "case UDPF_END:";
37e24fbe 7113 s.op->indent(1);
eff6ac72 7114 s.op->newline() << "if (process_p) {";
0744f531 7115 s.op->indent(1);
0744f531
DS
7116 s.op->newline() << "stap_utrace_probe_handler(tsk, p);";
7117 s.op->newline(-1) << "}";
37e24fbe
DS
7118 s.op->newline() << "break;";
7119 s.op->indent(-1);
0744f531 7120 }
eff6ac72 7121 if (flags_seen[UDPF_THREAD_END])
37e24fbe 7122 {
eff6ac72 7123 s.op->newline() << "case UDPF_THREAD_END:";
37e24fbe 7124 s.op->indent(1);
eff6ac72
DS
7125 s.op->newline() << "if (! process_p) {";
7126 s.op->indent(1);
7127 s.op->newline() << "stap_utrace_probe_handler(tsk, p);";
7128 s.op->newline(-1) << "}";
7129 s.op->newline() << "break;";
7130 s.op->indent(-1);
7131 }
7132
b20bac3a
DS
7133 // For begin/thread_begin probes, we don't need to do anything.
7134 if (flags_seen[UDPF_BEGIN] || flags_seen[UDPF_THREAD_BEGIN])
7135 {
eff6ac72
DS
7136 s.op->newline() << "case UDPF_BEGIN:";
7137 s.op->newline() << "case UDPF_THREAD_BEGIN:";
b20bac3a
DS
7138 s.op->indent(1);
7139 s.op->newline() << "break;";
7140 s.op->indent(-1);
7141 }
28d29bd3 7142
b20bac3a
DS
7143 if (flags_seen[UDPF_SYSCALL] || flags_seen[UDPF_SYSCALL_RETURN])
7144 {
eff6ac72
DS
7145 s.op->newline() << "case UDPF_SYSCALL:";
7146 s.op->newline() << "case UDPF_SYSCALL_RETURN:";
37e24fbe 7147 s.op->indent(1);
41211ba3 7148 s.op->newline() << "stap_utrace_detach(tsk, &p->ops);";
37e24fbe
DS
7149 s.op->newline() << "break;";
7150 s.op->indent(-1);
7151 }
eff6ac72
DS
7152
7153 s.op->newline() << "default:";
7154 s.op->indent(1);
7155 s.op->newline() << "_stp_error(\"unhandled flag value %d at %s:%d\", p->flags, __FUNCTION__, __LINE__);";
7156 s.op->newline() << "break;";
7157 s.op->indent(-1);
37e24fbe 7158 s.op->newline(-1) << "}";
935447c8
DS
7159 s.op->newline(-1) << "}";
7160 s.op->newline() << "return rc;";
7161 s.op->newline(-1) << "}";
7162
4c2732a1 7163 s.op->newline() << "static struct stap_utrace_probe stap_utrace_probes[] = {";
935447c8
DS
7164 s.op->indent(1);
7165
7166 // Set up 'process(PATH)' probes
7167 if (! probes_by_path.empty())
7168 {
7169 for (p_b_path_iterator it = probes_by_path.begin();
7170 it != probes_by_path.end(); it++)
7171 {
a21d81ec
DS
7172 // Emit a "fake" probe decl that is really a hook for to get
7173 // our vm_callback called.
7174 string path = it->first;
7175 s.op->newline() << "#ifdef DEBUG_TASK_FINDER_VMA";
7176 emit_vm_callback_probe_decl (s, true, path, (int64_t)0,
7177 "__stp_tf_vm_cb");
7178 s.op->newline() << "#endif";
7179
935447c8
DS
7180 for (unsigned i = 0; i < it->second.size(); i++)
7181 {
7182 utrace_derived_probe *p = it->second[i];
7183 emit_probe_decl(s, p);
7184 }
7185 }
7186 }
7187
7188 // Set up 'process(PID)' probes
7189 if (! probes_by_pid.empty())
7190 {
7191 for (p_b_pid_iterator it = probes_by_pid.begin();
7192 it != probes_by_pid.end(); it++)
7193 {
a21d81ec
DS
7194 // Emit a "fake" probe decl that is really a hook for to get
7195 // our vm_callback called.
7196 s.op->newline() << "#ifdef DEBUG_TASK_FINDER_VMA";
5e86a4ee 7197 emit_vm_callback_probe_decl (s, false, "", it->first,
a21d81ec
DS
7198 "__stp_tf_vm_cb");
7199 s.op->newline() << "#endif";
7200
935447c8
DS
7201 for (unsigned i = 0; i < it->second.size(); i++)
7202 {
7203 utrace_derived_probe *p = it->second[i];
7204 emit_probe_decl(s, p);
7205 }
7206 }
7207 }
7208 s.op->newline(-1) << "};";
7209}
7210
7211
7212void
7213utrace_derived_probe_group::emit_module_init (systemtap_session& s)
7214{
7215 if (probes_by_path.empty() && probes_by_pid.empty())
7216 return;
7217
7218 s.op->newline();
7219 s.op->newline() << "/* ---- utrace probes ---- */";
278def10 7220 s.op->newline() << "for (i=0; i<ARRAY_SIZE(stap_utrace_probes); i++) {";
935447c8
DS
7221 s.op->indent(1);
7222 s.op->newline() << "struct stap_utrace_probe *p = &stap_utrace_probes[i];";
7223 s.op->newline() << "rc = stap_register_task_finder_target(&p->tgt);";
7224 s.op->newline(-1) << "}";
7225
7226 // rollback all utrace probes
7227 s.op->newline() << "if (rc) {";
7228 s.op->indent(1);
7229 s.op->newline() << "for (j=i-1; j>=0; j--) {";
7230 s.op->indent(1);
7231 s.op->newline() << "struct stap_utrace_probe *p = &stap_utrace_probes[j];";
7232
7233 s.op->newline() << "if (p->engine_attached) {";
7234 s.op->indent(1);
7235 s.op->newline() << "stap_utrace_detach_ops(&p->ops);";
7236 s.op->newline(-1) << "}";
7237 s.op->newline(-1) << "}";
7238
7239 s.op->newline(-1) << "}";
7240}
7241
7242
7243void
7244utrace_derived_probe_group::emit_module_exit (systemtap_session& s)
7245{
7246 if (probes_by_path.empty() && probes_by_pid.empty()) return;
7247
7248 s.op->newline();
7249 s.op->newline() << "/* ---- utrace probes ---- */";
278def10 7250 s.op->newline() << "for (i=0; i<ARRAY_SIZE(stap_utrace_probes); i++) {";
935447c8
DS
7251 s.op->indent(1);
7252 s.op->newline() << "struct stap_utrace_probe *p = &stap_utrace_probes[i];";
7253
7254 s.op->newline() << "if (p->engine_attached) {";
7255 s.op->indent(1);
7256 s.op->newline() << "stap_utrace_detach_ops(&p->ops);";
7257 s.op->newline(-1) << "}";
7258 s.op->newline(-1) << "}";
7259}
7260
7261
888af770
FCE
7262// ------------------------------------------------------------------------
7263// user-space probes
7264// ------------------------------------------------------------------------
7265
888af770
FCE
7266
7267struct uprobe_derived_probe_group: public generic_dpg<uprobe_derived_probe>
7268{
7269public:
7270 void emit_module_decls (systemtap_session& s);
7271 void emit_module_init (systemtap_session& s);
7272 void emit_module_exit (systemtap_session& s);
7273};
7274
7275
6d0f3f0c
FCE
7276uprobe_derived_probe::uprobe_derived_probe (const string& function,
7277 const string& filename,
7278 int line,
7279 const string& module,
7280 int pid,
7281 const string& section,
7282 Dwarf_Addr dwfl_addr,
7283 Dwarf_Addr addr,
7284 dwarf_query & q,
7285 Dwarf_Die* scope_die /* may be null */):
7286 derived_probe (q.base_probe, new probe_point (*q.base_loc) /* .components soon rewritten */ ),
7287 return_p (q.has_return), module (module), pid (pid), section (section), address (addr)
4baf0e53 7288{
17c128f2
FCE
7289 // We may receive probes on two types of ELF objects: ET_EXEC or ET_DYN.
7290 // ET_EXEC ones need no further relocation on the addr(==dwfl_addr), whereas
7291 // ET_DYN ones do (addr += run-time mmap base address). We tell these apart
7292 // by the incoming section value (".absolute" vs. ".dynamic").
6d0f3f0c
FCE
7293
7294 this->tok = q.base_probe->tok;
7295
de688825 7296 // Expand target variables in the probe body
6d0f3f0c
FCE
7297 if (!null_die(scope_die))
7298 {
de688825 7299 dwarf_var_expanding_visitor v (q, scope_die, dwfl_addr); // XXX: user-space deref's!
4ed05b15 7300 this->body = v.require (this->body);
6d0f3f0c
FCE
7301
7302 // If during target-variable-expanding the probe, we added a new block
7303 // of code, add it to the start of the probe.
7304 if (v.add_block)
7305 this->body = new block(v.add_block, this->body);
7306
7307 // If when target-variable-expanding the probe, we added a new
7308 // probe, add it in a new file to the list of files to be processed.
7309 if (v.add_probe)
7310 {
7311 stapfile *f = new stapfile;
7312 f->probes.push_back(v.add_probe);
7313 q.sess.files.push_back(f);
7314 }
7315 }
7316 // else - null scope_die - $target variables will produce an error during translate phase
7317
7318 // Reset the sole element of the "locations" vector as a
7319 // "reverse-engineered" form of the incoming (q.base_loc) probe
7320 // point. This allows a user to see what function / file / line
7321 // number any particular match of the wildcards.
7322
7323 vector<probe_point::component*> comps;
7324 if(q.has_process)
7325 comps.push_back (new probe_point::component(TOK_PROCESS, new literal_string(module)));
7326 else
7327 assert (0);
06aca46a 7328
6d0f3f0c
FCE
7329 string fn_or_stmt;
7330 if (q.has_function_str || q.has_function_num)
7331 fn_or_stmt = "function";
7332 else
7333 fn_or_stmt = "statement";
7334
7335 if (q.has_function_str || q.has_statement_str)
7336 {
7337 string retro_name = function;
7338 if (filename != "")
fb84c077
FCE
7339 {
7340 retro_name += ("@" + string (filename));
7341 if (line > 0)
7342 retro_name += (":" + lex_cast<string> (line));
7343 }
6d0f3f0c
FCE
7344 comps.push_back
7345 (new probe_point::component
7346 (fn_or_stmt, new literal_string (retro_name)));
7347 }
7348 else if (q.has_function_num || q.has_statement_num)
7349 {
7350 Dwarf_Addr retro_addr;
7351 if (q.has_function_num)
7352 retro_addr = q.function_num_val;
7353 else
7354 retro_addr = q.statement_num_val;
7355 comps.push_back (new probe_point::component
7356 (fn_or_stmt,
7357 new literal_number(retro_addr))); // XXX: should be hex if possible
7358
7359 if (q.has_absolute)
7360 comps.push_back (new probe_point::component (TOK_ABSOLUTE));
7361 }
7362
7363 if (q.has_call)
7364 comps.push_back (new probe_point::component(TOK_CALL));
7365 if (q.has_inline)
7366 comps.push_back (new probe_point::component(TOK_INLINE));
7367 if (return_p)
7368 comps.push_back (new probe_point::component(TOK_RETURN));
7369 /*
7370 if (has_maxactive)
7371 comps.push_back (new probe_point::component
7372 (TOK_MAXACTIVE, new literal_number(maxactive_val)));
7373 */
7374
7375 // Overwrite it.
7376 this->sole_location()->components = comps;
7377}
7378
7379
0973d815
FCE
7380uprobe_derived_probe::uprobe_derived_probe (probe *base,
7381 probe_point *location,
7382 int pid,
7383 Dwarf_Addr addr,
7384 bool has_return):
7385 derived_probe (base, location), // location is not rewritten here
7386 return_p (has_return), pid (pid), address (addr)
7387{
7388}
7389
7390
6d0f3f0c
FCE
7391void
7392uprobe_derived_probe::printsig (ostream& o) const
7393{
7394 // Same as dwarf_derived_probe.
7395 sole_location()->print (o);
7396 o << " /* pc=" << section << "+0x" << hex << address << dec << " */";
7397 printsig_nested (o);
888af770
FCE
7398}
7399
7400
7401void
7402uprobe_derived_probe::join_group (systemtap_session& s)
7403{
7404 if (! s.uprobe_derived_probes)
7405 s.uprobe_derived_probes = new uprobe_derived_probe_group ();
7406 s.uprobe_derived_probes->enroll (this);
6d0f3f0c 7407 task_finder_derived_probe_group::create_session_group (s);
888af770
FCE
7408}
7409
7410
7411struct uprobe_builder: public derived_probe_builder
7412{
7413 uprobe_builder() {}
7414 virtual void build(systemtap_session & sess,
7415 probe * base,
7416 probe_point * location,
86bf665e 7417 literal_map_t const & parameters,
888af770
FCE
7418 vector<derived_probe *> & finished_results)
7419 {
7420 int64_t process, address;
7421
7422 bool b1 = get_param (parameters, TOK_PROCESS, process);
ced347a9 7423 (void) b1;
888af770 7424 bool b2 = get_param (parameters, TOK_STATEMENT, address);
ced347a9 7425 (void) b2;
888af770
FCE
7426 bool rr = has_null_param (parameters, TOK_RETURN);
7427 assert (b1 && b2); // by pattern_root construction
4baf0e53 7428
0973d815 7429 finished_results.push_back(new uprobe_derived_probe(base, location, process, address, rr));
888af770
FCE
7430 }
7431};
7432
7433
7434void
775d51e5 7435uprobe_derived_probe_group::emit_module_decls (systemtap_session& s)
888af770
FCE
7436{
7437 if (probes.empty()) return;
775d51e5 7438 s.op->newline() << "/* ---- user probes ---- */";
4baf0e53 7439
6d0f3f0c
FCE
7440 s.need_uprobes = true; // Ask buildrun.cxx to build extra module if needed
7441
c480bf3d 7442 // If uprobes isn't in the kernel, pull it in from the runtime.
6274464e 7443 s.op->newline() << "#if defined(CONFIG_UPROBES) || defined(CONFIG_UPROBES_MODULE)";
888af770 7444 s.op->newline() << "#include <linux/uprobes.h>";
c480bf3d 7445 s.op->newline() << "#else";
6274464e 7446 s.op->newline() << "#include \"uprobes/uprobes.h\"";
c480bf3d 7447 s.op->newline() << "#endif";
6d0f3f0c
FCE
7448 s.op->newline() << "#include \"task_finder.c\"";
7449
01b05e2e 7450 s.op->newline() << "#ifndef MULTIPLE_UPROBES";
478c850f
FCE
7451 s.op->newline() << "#define MULTIPLE_UPROBES 256"; // maximum possible armed uprobes per process() probe point
7452 // or apprx. max number of processes mapping a shared library
01b05e2e 7453 s.op->newline() << "#endif";
6d0f3f0c 7454 s.op->newline() << "#ifndef MAXUPROBES";
01b05e2e 7455 s.op->newline() << "#define MAXUPROBES (MULTIPLE_UPROBES * " << probes.size() << ")";
6d0f3f0c 7456 s.op->newline() << "#endif";
888af770 7457
5e112f92
FCE
7458 // In .bss, the shared pool of uprobe/uretprobe structs. These are
7459 // too big to embed in the initialized .data stap_uprobe_spec array.
4c2732a1 7460 s.op->newline() << "static struct stap_uprobe {";
888af770 7461 s.op->newline(1) << "union { struct uprobe up; struct uretprobe urp; };";
6d0f3f0c 7462 s.op->newline() << "int spec_index;"; // index into stap_uprobe_specs; <0 == free && unregistered
01b05e2e 7463 s.op->newline(-1) << "} stap_uprobes [MAXUPROBES];";
5e112f92 7464 s.op->newline() << "DEFINE_MUTEX(stap_uprobes_lock);"; // protects against concurrent registration/unregistration
6d0f3f0c 7465
4c2732a1 7466 s.op->newline() << "static struct stap_uprobe_spec {";
5e112f92 7467 s.op->newline(1) << "struct stap_task_finder_target finder;";
888af770 7468 s.op->newline() << "unsigned long address;";
17c128f2 7469 s.op->newline() << "const char *pathname;";
888af770
FCE
7470 s.op->newline() << "const char *pp;";
7471 s.op->newline() << "void (*ph) (struct context*);";
6d0f3f0c
FCE
7472 s.op->newline() << "unsigned return_p:1;";
7473 s.op->newline(-1) << "} stap_uprobe_specs [] = {";
888af770
FCE
7474 s.op->indent(1);
7475 for (unsigned i =0; i<probes.size(); i++)
7476 {
7477 uprobe_derived_probe* p = probes[i];
7478 s.op->newline() << "{";
0973d815
FCE
7479 s.op->line() << " .finder = {";
7480 if (p->pid != 0)
17c128f2
FCE
7481 s.op->line() << " .pid=" << p->pid;
7482 else if (p->section == ".absolute")
0973d815 7483 s.op->line() << " .pathname=" << lex_cast_qstring(p->module) << ", ";
06aca46a 7484 // else ".dynamic" gets pathname=0, pid=0, activating task_finder "global tracing"
0973d815 7485 s.op->line() << "},";
17c128f2
FCE
7486 if (p->section != ".absolute")
7487 s.op->line() << " .pathname=" << lex_cast_qstring(p->module) << ", ";
dc38c256 7488 s.op->line() << " .address=(unsigned long)0x" << hex << p->address << dec << "ULL,";
888af770
FCE
7489 s.op->line() << " .pp=" << lex_cast_qstring (*p->sole_location()) << ",";
7490 s.op->line() << " .ph=&" << p->name << ",";
7491 if (p->return_p) s.op->line() << " .return_p=1,";
7492 s.op->line() << " },";
7493 }
7494 s.op->newline(-1) << "};";
7495
48e685da 7496 s.op->newline() << "static void enter_uprobe_probe (struct uprobe *inst, struct pt_regs *regs) {";
888af770 7497 s.op->newline(1) << "struct stap_uprobe *sup = container_of(inst, struct stap_uprobe, up);";
6d0f3f0c 7498 s.op->newline() << "struct stap_uprobe_spec *sups = &stap_uprobe_specs [sup->spec_index];";
c12d974f 7499 common_probe_entryfn_prologue (s.op, "STAP_SESSION_RUNNING", "sups->pp");
6d0f3f0c
FCE
7500 s.op->newline() << "if (sup->spec_index < 0 ||"
7501 << "sup->spec_index >= " << probes.size() << ") return;"; // XXX: should not happen
888af770 7502 s.op->newline() << "c->regs = regs;";
6d0f3f0c 7503 s.op->newline() << "(*sups->ph) (c);";
888af770
FCE
7504 common_probe_entryfn_epilogue (s.op);
7505 s.op->newline(-1) << "}";
7506
48e685da 7507 s.op->newline() << "static void enter_uretprobe_probe (struct uretprobe_instance *inst, struct pt_regs *regs) {";
888af770 7508 s.op->newline(1) << "struct stap_uprobe *sup = container_of(inst->rp, struct stap_uprobe, urp);";
6d0f3f0c 7509 s.op->newline() << "struct stap_uprobe_spec *sups = &stap_uprobe_specs [sup->spec_index];";
c12d974f 7510 common_probe_entryfn_prologue (s.op, "STAP_SESSION_RUNNING", "sups->pp");
6d0f3f0c
FCE
7511 s.op->newline() << "if (sup->spec_index < 0 ||"
7512 << "sup->spec_index >= " << probes.size() << ") return;"; // XXX: should not happen
888af770
FCE
7513 // XXX: kretprobes saves "c->pi = inst;" too
7514 s.op->newline() << "c->regs = regs;";
6d0f3f0c 7515 s.op->newline() << "(*sups->ph) (c);";
888af770
FCE
7516 common_probe_entryfn_epilogue (s.op);
7517 s.op->newline(-1) << "}";
6d0f3f0c 7518
17c128f2
FCE
7519
7520
6d0f3f0c
FCE
7521 // NB: Because these utrace callbacks only occur before / after
7522 // userspace instructions run, there is no concurrency control issue
7523 // between active uprobe callbacks and these registration /
06aca46a 7524 // unregistration pieces.
6d0f3f0c
FCE
7525
7526 // We protect the stap_uprobe->spec_index (which also serves as a
d41d451c
FCE
7527 // free/busy flag) value with the outer protective stap_probes_lock
7528 // spinlock, to protect it against concurrent registration /
7529 // unregistration.
6d0f3f0c
FCE
7530
7531 s.op->newline();
17c128f2
FCE
7532 s.op->newline() << "static int stap_uprobe_change (struct task_struct *tsk, int register_p, unsigned long relocation, struct stap_uprobe_spec *sups) {";
7533 s.op->newline(1) << "int spec_index = (sups - stap_uprobe_specs);";
6d0f3f0c 7534 s.op->newline() << "int handled_p = 0;";
d41d451c 7535 s.op->newline() << "int slotted_p = 0;";
6d0f3f0c
FCE
7536 s.op->newline() << "int rc = 0;";
7537 s.op->newline() << "int i;";
3568f1dd 7538
d41d451c 7539 s.op->newline() << "mutex_lock (& stap_uprobes_lock);";
01b05e2e 7540 s.op->newline() << "for (i=0; i<MAXUPROBES; i++) {"; // XXX: slow linear search
5e112f92 7541 s.op->newline(1) << "struct stap_uprobe *sup = & stap_uprobes[i];";
6d0f3f0c
FCE
7542
7543 // register new uprobe
7544 s.op->newline() << "if (register_p && sup->spec_index < 0) {";
80b4ad8b
FCE
7545 // PR6829: we need to check that the sup we're about to reuse is really completely free.
7546 // See PR6829 notes below.
7547 s.op->newline(1) << "if (sup->spec_index == -1 && sup->up.kdata != NULL) continue;";
7548 s.op->newline() << "else if (sup->spec_index == -2 && sup->urp.u.kdata != NULL) continue;";
7549 s.op->newline() << "sup->spec_index = spec_index;";
d41d451c
FCE
7550 s.op->newline() << "slotted_p = 1;";
7551 s.op->newline() << "break;";
7552 s.op->newline(-1) << "} else if (!register_p && "
7553 << "sup->spec_index == spec_index && " // a u[ret]probe set up for this probe point
7554 << "((sups->return_p && sup->urp.u.pid == tsk->tgid && sup->urp.u.vaddr == relocation + sups->address) ||" // dying uretprobe
7555 << "(!sups->return_p && sup->up.pid == tsk->tgid && sup->up.vaddr == relocation + sups->address))) {"; // dying uprobe
7556 s.op->newline(1) << "slotted_p = 1;";
7557 s.op->newline() << "break;"; // exit to-free slot search
7558 s.op->newline(-1) << "}";
7559
7560 s.op->newline(-1) << "}";
7561 s.op->newline() << "mutex_unlock (& stap_uprobes_lock);";
7562
7563 s.op->newline() << "#ifdef DEBUG_UPROBES";
7564 s.op->newline() << "printk (KERN_INFO \"%cuprobe spec %d idx %d process %s[%d] reloc %p pp '%s'\\n\", ";
7565 s.op->line() << "(register_p ? '+' : '-'), spec_index, (slotted_p ? i : -1), tsk->comm, tsk->tgid, (void*) relocation, sups->pp);";
7566 s.op->newline() << "#endif";
7567
7568 // Here, slotted_p implies that `i' points to the single
7569 // stap_uprobes[] element that has been slotted in for registration
7570 // or unregistration processing. !slotted_p implies that the table
7571 // was full (registration; MAXUPROBES) or that no matching entry was
7572 // found (unregistration; should not happen).
7573
7574 s.op->newline() << "if (register_p && slotted_p) {";
7575 s.op->newline(1) << "struct stap_uprobe *sup = & stap_uprobes[i];";
6d0f3f0c
FCE
7576 s.op->newline() << "if (sups->return_p) {";
7577 s.op->newline(1) << "sup->urp.u.pid = tsk->tgid;";
17c128f2 7578 s.op->newline() << "sup->urp.u.vaddr = relocation + sups->address;";
6d0f3f0c
FCE
7579 s.op->newline() << "sup->urp.handler = &enter_uretprobe_probe;";
7580 s.op->newline() << "rc = register_uretprobe (& sup->urp);";
7581 s.op->newline(-1) << "} else {";
7582 s.op->newline(1) << "sup->up.pid = tsk->tgid;";
17c128f2 7583 s.op->newline() << "sup->up.vaddr = relocation + sups->address;";
6d0f3f0c
FCE
7584 s.op->newline() << "sup->up.handler = &enter_uprobe_probe;";
7585 s.op->newline() << "rc = register_uprobe (& sup->up);";
7586 s.op->newline(-1) << "}";
6d0f3f0c 7587 s.op->newline() << "if (rc) {"; // failed to register
d41d451c
FCE
7588 s.op->newline(1) << "printk (KERN_WARNING \"uprobe failed %s[%d] '%s' addr %p rc %d\\n\", tsk->comm, tsk->tgid, sups->pp, (void*)(relocation + sups->address), rc);";
7589 // NB: we need to release this slot, so we need to borrow the mutex temporarily.
7590 s.op->newline() << "mutex_lock (& stap_uprobes_lock);";
3568f1dd 7591 s.op->newline() << "sup->spec_index = -1;";
d41d451c 7592 s.op->newline() << "mutex_unlock (& stap_uprobes_lock);";
6d0f3f0c
FCE
7593 s.op->newline(-1) << "} else {";
7594 s.op->newline(1) << "handled_p = 1;"; // success
7595 s.op->newline(-1) << "}";
6d0f3f0c 7596
d41d451c
FCE
7597 s.op->newline(-1) << "} else if (!register_p && slotted_p) {";
7598 s.op->newline(1) << "struct stap_uprobe *sup = & stap_uprobes[i];";
7599 // NB: we need to release this slot, so we need to borrow the mutex temporarily.
7600 s.op->newline() << "mutex_lock (& stap_uprobes_lock);";
7601 // NB: We must not actually uregister u[ret]probes when a target process execs or exits;
80b4ad8b 7602 // uprobes does that by itself asynchronously. We can reuse the up/urp struct after
d41d451c 7603 // uprobes clears the sup->{up,urp}->kdata pointer. PR6829. To tell the two
80b4ad8b 7604 // cases apart, we use spec_index -2 vs -1.
d41d451c 7605 s.op->newline() << "sup->spec_index = (sups->return_p ? -2 : -1);";
5e112f92 7606 s.op->newline() << "mutex_unlock (& stap_uprobes_lock);";
d41d451c
FCE
7607 s.op->newline() << "handled_p = 1;";
7608 s.op->newline(-1) << "}"; // if slotted_p
7609
7610 // NB: handled_p implies slotted_p
7611
6d0f3f0c 7612 s.op->newline() << "if (! handled_p) {";
73209876
FCE
7613 s.op->newline(1) << "#ifdef STP_TIMING";
7614 s.op->newline() << "atomic_inc (register_p ? & skipped_count_uprobe_reg : & skipped_count_uprobe_unreg);";
7615 s.op->newline() << "#endif";
7616 // NB: duplicates common_entryfn_epilogue, but then this is not a probe entry fn epilogue.
7617 s.op->newline() << "if (unlikely (atomic_inc_return (& skipped_count) > MAXSKIPPED)) {";
6d0f3f0c
FCE
7618 s.op->newline(1) << "atomic_set (& session_state, STAP_SESSION_ERROR);";
7619 s.op->newline() << "_stp_exit ();";
7620 s.op->newline(-1) << "}";
7621 s.op->newline(-1) << "}";
06aca46a 7622
6d0f3f0c
FCE
7623 s.op->newline() << "return 0;"; // XXX: or rc?
7624 s.op->newline(-1) << "}";
7625 s.op->assert_0_indent();
7626
17c128f2
FCE
7627
7628 // The task_finder_callback we use for ET_EXEC targets.
7629 s.op->newline();
7630 s.op->newline() << "static int stap_uprobe_process_found (struct stap_task_finder_target *tgt, struct task_struct *tsk, int register_p, int process_p) {";
7631
7632 s.op->newline(1) << "struct stap_uprobe_spec *sups = container_of(tgt, struct stap_uprobe_spec, finder);";
7633 s.op->newline() << "if (! process_p) return 0;";
7634 s.op->newline(0) << "return stap_uprobe_change (tsk, register_p, 0, sups);";
7635 s.op->newline(-1) << "}";
7636
7637 // The task_finder_vm_callback we use for ET_DYN targets.
7638 s.op->newline();
7639 s.op->newline() << "static int stap_uprobe_vmchange_found (struct stap_task_finder_target *tgt, struct task_struct *tsk, int map_p, char *vm_path, unsigned long vm_start, unsigned long vm_end, unsigned long vm_pgoff) {";
7640 s.op->newline(1) << "struct stap_uprobe_spec *sups = container_of(tgt, struct stap_uprobe_spec, finder);";
7641 // 1 - shared libraries' executable segments load from offset 0 - ld.so convention
06aca46a 7642 s.op->newline() << "if (vm_pgoff != 0) return 0;";
17c128f2 7643 // 2 - the shared library we're interested in
06aca46a 7644 s.op->newline() << "if (vm_path == NULL || strcmp (vm_path, sups->pathname)) return 0;";
17c128f2 7645 // 3 - probe address within the mapping limits; test should not fail
06aca46a
FCE
7646 s.op->newline() << "if (vm_end <= vm_start + sups->address) return 0;";
7647
c16d425a
FCE
7648 s.op->newline() << "#ifdef DEBUG_TASK_FINDER_VMA";
7649 s.op->newline() << "printk (KERN_INFO \"vmchange pid %d map_p %d path %s vms %p vme %p vmp %p\\n\", tsk->tgid, map_p, vm_path, (void*) vm_start, (void*) vm_end, (void*) vm_pgoff);";
7650 s.op->newline() << "printk (KERN_INFO \"sups %p pp %s path %s address %p\\n\", sups, sups->pp, sups->pathname ?: \"\", (void*) sups->address);";
7651 s.op->newline() << "#endif";
7652
17c128f2
FCE
7653 s.op->newline(0) << "return stap_uprobe_change (tsk, map_p, vm_start, sups);";
7654 s.op->newline(-1) << "}";
7655 s.op->assert_0_indent();
7656
7657
6d0f3f0c 7658 s.op->newline();
888af770
FCE
7659}
7660
7661
7662void
7663uprobe_derived_probe_group::emit_module_init (systemtap_session& s)
7664{
7665 if (probes.empty()) return;
5e112f92
FCE
7666 s.op->newline() << "/* ---- user probes ---- */";
7667
01b05e2e 7668 s.op->newline() << "for (j=0; j<MAXUPROBES; j++) {";
5e112f92
FCE
7669 s.op->newline(1) << "struct stap_uprobe *sup = & stap_uprobes[j];";
7670 s.op->newline() << "sup->spec_index = -1;"; // free slot
80b4ad8b
FCE
7671 // NB: we assume the rest of the struct (specificaly, sup->up) is
7672 // initialized to zero. This is so that we can use
7673 // sup->up->kdata = NULL for "really free!" PR 6829.
5e112f92
FCE
7674 s.op->newline(-1) << "}";
7675 s.op->newline() << "mutex_init (& stap_uprobes_lock);";
888af770
FCE
7676
7677 s.op->newline() << "for (i=0; i<" << probes.size() << "; i++) {";
6d0f3f0c
FCE
7678 s.op->newline(1) << "struct stap_uprobe_spec *sups = & stap_uprobe_specs[i];";
7679 s.op->newline() << "probe_point = sups->pp;"; // for error messages
17c128f2
FCE
7680 s.op->newline() << "if (sups->finder.pathname) sups->finder.callback = & stap_uprobe_process_found;";
7681 s.op->newline() << "else if (sups->pathname) sups->finder.vm_callback = & stap_uprobe_vmchange_found;";
6d0f3f0c 7682 s.op->newline() << "rc = stap_register_task_finder_target (& sups->finder);";
5e112f92
FCE
7683
7684 // NB: if (rc), there is no need (XXX: nor any way) to clean up any
7685 // finders already registered, since mere registration does not
7686 // cause any utrace or memory allocation actions. That happens only
7687 // later, once the task finder engine starts running. So, for a
7688 // partial initialization requiring unwind, we need do nothing.
7689 s.op->newline() << "if (rc) break;";
7690
888af770
FCE
7691 s.op->newline(-1) << "}";
7692}
7693
7694
7695void
7696uprobe_derived_probe_group::emit_module_exit (systemtap_session& s)
7697{
7698 if (probes.empty()) return;
7699 s.op->newline() << "/* ---- user probes ---- */";
7700
6d0f3f0c
FCE
7701 // NB: there is no stap_unregister_task_finder_target call;
7702 // important stuff like utrace cleanups are done by
d41d451c
FCE
7703 // __stp_task_finder_cleanup() via stap_stop_task_finder().
7704 //
7705 // This function blocks until all callbacks are completed, so there
7706 // is supposed to be no possibility of any registration-related code starting
7707 // to run in parallel with our shutdown here. So we don't need to protect the
7708 // stap_uprobes[] array with the mutex.
5e112f92 7709
01b05e2e 7710 s.op->newline() << "for (j=0; j<MAXUPROBES; j++) {";
5e112f92
FCE
7711 s.op->newline(1) << "struct stap_uprobe *sup = & stap_uprobes[j];";
7712 s.op->newline() << "struct stap_uprobe_spec *sups = &stap_uprobe_specs [sup->spec_index];";
6d0f3f0c 7713 s.op->newline() << "if (sup->spec_index < 0) continue;"; // free slot
3568f1dd
FCE
7714
7715 s.op->newline() << "if (sups->return_p) {";
7716 s.op->newline(1) << "#ifdef DEBUG_UPROBES";
d41d451c 7717 s.op->newline() << "printk (KERN_INFO \"-uretprobe spec %d index %d pid %d addr %p\\n\", sup->spec_index, j, sup->up.pid, (void*) sup->up.vaddr);";
3568f1dd 7718 s.op->newline() << "#endif";
80b4ad8b
FCE
7719 // NB: PR6829 does not change that we still need to unregister at
7720 // *this* time -- when the script as a whole exits.
3568f1dd
FCE
7721 s.op->newline() << "unregister_uretprobe (& sup->urp);";
7722 s.op->newline(-1) << "} else {";
7723 s.op->newline(1) << "#ifdef DEBUG_UPROBES";
d41d451c 7724 s.op->newline() << "printk (KERN_INFO \"-uprobe spec %d index %d pid %d addr %p\\n\", sup->spec_index, j, sup->urp.u.pid, (void*) sup->urp.u.vaddr);";
3568f1dd
FCE
7725 s.op->newline() << "#endif";
7726 s.op->newline() << "unregister_uprobe (& sup->up);";
7727 s.op->newline(-1) << "}";
7728
6d0f3f0c 7729 s.op->newline() << "sup->spec_index = -1;";
3568f1dd
FCE
7730
7731 // XXX: uprobe missed counts?
7732
6d0f3f0c 7733 s.op->newline(-1) << "}";
5e112f92
FCE
7734
7735 s.op->newline() << "mutex_destroy (& stap_uprobes_lock);";
888af770
FCE
7736}
7737
7738
7739
98afd80e
FCE
7740// ------------------------------------------------------------------------
7741// timer derived probes
7742// ------------------------------------------------------------------------
7743
7744
12b21830
DS
7745static string TOK_TIMER("timer");
7746
98afd80e
FCE
7747struct timer_derived_probe: public derived_probe
7748{
7749 int64_t interval, randomize;
b20febf3 7750 bool time_is_msecs; // NB: hrtimers get ms-based probes on modern kernels instead
422d1ceb 7751 timer_derived_probe (probe* p, probe_point* l, int64_t i, int64_t r, bool ms=false);
b20febf3
FCE
7752 virtual void join_group (systemtap_session& s);
7753};
98afd80e 7754
dc38c0ae 7755
b20febf3
FCE
7756struct timer_derived_probe_group: public generic_dpg<timer_derived_probe>
7757{
d006ef4f 7758 void emit_interval (translator_output* o);
b20febf3
FCE
7759public:
7760 void emit_module_decls (systemtap_session& s);
7761 void emit_module_init (systemtap_session& s);
7762 void emit_module_exit (systemtap_session& s);
98afd80e
FCE
7763};
7764
7765
422d1ceb
FCE
7766timer_derived_probe::timer_derived_probe (probe* p, probe_point* l, int64_t i, int64_t r, bool ms):
7767 derived_probe (p, l), interval (i), randomize (r), time_is_msecs(ms)
98afd80e
FCE
7768{
7769 if (interval <= 0 || interval > 1000000) // make i and r fit into plain ints
7770 throw semantic_error ("invalid interval for jiffies timer");
7771 // randomize = 0 means no randomization
7772 if (randomize < 0 || randomize > interval)
7773 throw semantic_error ("invalid randomize for jiffies timer");
7774
7775 if (locations.size() != 1)
7776 throw semantic_error ("expect single probe point");
7777 // so we don't have to loop over them in the other functions
7778}
7779
7780
dc38c0ae 7781void
b20febf3 7782timer_derived_probe::join_group (systemtap_session& s)
dc38c0ae 7783{
b20febf3
FCE
7784 if (! s.timer_derived_probes)
7785 s.timer_derived_probes = new timer_derived_probe_group ();
7786 s.timer_derived_probes->enroll (this);
dc38c0ae
DS
7787}
7788
7789
d006ef4f
JS
7790void
7791timer_derived_probe_group::emit_interval (translator_output* o)
7792{
7793 o->line() << "({";
7794 o->newline(1) << "unsigned i = stp->intrv;";
7795 o->newline() << "if (stp->rnd != 0)";
7796 o->newline(1) << "i += _stp_random_pm(stp->rnd);";
7797 o->newline(-1) << "stp->ms ? msecs_to_jiffies(i) : i;";
7798 o->newline(-1) << "})";
7799}
7800
7801
98afd80e 7802void
b20febf3 7803timer_derived_probe_group::emit_module_decls (systemtap_session& s)
98afd80e 7804{
b20febf3 7805 if (probes.empty()) return;
46b84a80 7806
b20febf3 7807 s.op->newline() << "/* ---- timer probes ---- */";
46b84a80 7808
4c2732a1 7809 s.op->newline() << "static struct stap_timer_probe {";
b20febf3
FCE
7810 s.op->newline(1) << "struct timer_list timer_list;";
7811 s.op->newline() << "const char *pp;";
7812 s.op->newline() << "void (*ph) (struct context*);";
7813 s.op->newline() << "unsigned intrv, ms, rnd;";
7814 s.op->newline(-1) << "} stap_timer_probes [" << probes.size() << "] = {";
7815 s.op->indent(1);
7816 for (unsigned i=0; i < probes.size(); i++)
7817 {
4baf0e53
RM
7818 s.op->newline () << "{";
7819 s.op->line() << " .pp="
b20febf3
FCE
7820 << lex_cast_qstring (*probes[i]->sole_location()) << ",";
7821 s.op->line() << " .ph=&" << probes[i]->name << ",";
7822 s.op->line() << " .intrv=" << probes[i]->interval << ",";
7823 s.op->line() << " .ms=" << probes[i]->time_is_msecs << ",";
7824 s.op->line() << " .rnd=" << probes[i]->randomize;
7825 s.op->line() << " },";
7826 }
7827 s.op->newline(-1) << "};";
7828 s.op->newline();
98afd80e 7829
b20febf3
FCE
7830 s.op->newline() << "static void enter_timer_probe (unsigned long val) {";
7831 s.op->newline(1) << "struct stap_timer_probe* stp = & stap_timer_probes [val];";
e0d86324
JS
7832 s.op->newline() << "if ((atomic_read (&session_state) == STAP_SESSION_STARTING) ||";
7833 s.op->newline() << " (atomic_read (&session_state) == STAP_SESSION_RUNNING))";
7834 s.op->newline(1) << "mod_timer (& stp->timer_list, jiffies + ";
d006ef4f
JS
7835 emit_interval (s.op);
7836 s.op->line() << ");";
e0d86324
JS
7837 s.op->newline(-1) << "{";
7838 s.op->indent(1);
c12d974f 7839 common_probe_entryfn_prologue (s.op, "STAP_SESSION_RUNNING", "stp->pp");
b20febf3
FCE
7840 s.op->newline() << "(*stp->ph) (c);";
7841 common_probe_entryfn_epilogue (s.op);
7842 s.op->newline(-1) << "}";
e0d86324 7843 s.op->newline(-1) << "}";
98afd80e
FCE
7844}
7845
7846
7847void
b20febf3 7848timer_derived_probe_group::emit_module_init (systemtap_session& s)
dc38c0ae 7849{
b20febf3 7850 if (probes.empty()) return;
dc38c0ae 7851
b20febf3
FCE
7852 s.op->newline() << "for (i=0; i<" << probes.size() << "; i++) {";
7853 s.op->newline(1) << "struct stap_timer_probe* stp = & stap_timer_probes [i];";
6f313a73 7854 s.op->newline() << "probe_point = stp->pp;";
b20febf3
FCE
7855 s.op->newline() << "init_timer (& stp->timer_list);";
7856 s.op->newline() << "stp->timer_list.function = & enter_timer_probe;";
7857 s.op->newline() << "stp->timer_list.data = i;"; // NB: important!
7858 // copy timer renew calculations from above :-(
d006ef4f
JS
7859 s.op->newline() << "stp->timer_list.expires = jiffies + ";
7860 emit_interval (s.op);
7861 s.op->line() << ";";
7862 s.op->newline() << "add_timer (& stp->timer_list);";
b20febf3
FCE
7863 // note: no partial failure rollback is needed: add_timer cannot fail.
7864 s.op->newline(-1) << "}"; // for loop
dc38c0ae
DS
7865}
7866
7867
46b84a80 7868void
b20febf3 7869timer_derived_probe_group::emit_module_exit (systemtap_session& s)
46b84a80 7870{
b20febf3 7871 if (probes.empty()) return;
46b84a80 7872
b20febf3
FCE
7873 s.op->newline() << "for (i=0; i<" << probes.size() << "; i++)";
7874 s.op->newline(1) << "del_timer_sync (& stap_timer_probes[i].timer_list);";
7875 s.op->indent(-1);
46b84a80
DS
7876}
7877
7878
b20febf3 7879
39e57ce0
FCE
7880// ------------------------------------------------------------------------
7881// profile derived probes
7882// ------------------------------------------------------------------------
7883// On kernels < 2.6.10, this uses the register_profile_notifier API to
7884// generate the timed events for profiling; on kernels >= 2.6.10 this
7885// uses the register_timer_hook API. The latter doesn't currently allow
7886// simultaneous users, so insertion will fail if the profiler is busy.
7887// (Conflicting users may include OProfile, other SystemTap probes, etc.)
7888
7889
7890struct profile_derived_probe: public derived_probe
7891{
6dce2125 7892 profile_derived_probe (systemtap_session &s, probe* p, probe_point* l);
b20febf3
FCE
7893 void join_group (systemtap_session& s);
7894};
39e57ce0 7895
dc38c0ae 7896
b20febf3
FCE
7897struct profile_derived_probe_group: public generic_dpg<profile_derived_probe>
7898{
7899public:
7900 void emit_module_decls (systemtap_session& s);
7901 void emit_module_init (systemtap_session& s);
7902 void emit_module_exit (systemtap_session& s);
39e57ce0
FCE
7903};
7904
7905
78f6bba6 7906profile_derived_probe::profile_derived_probe (systemtap_session &, probe* p, probe_point* l):
6dce2125 7907 derived_probe(p, l)
4baf0e53 7908{
39e57ce0
FCE
7909}
7910
7911
dc38c0ae 7912void
b20febf3 7913profile_derived_probe::join_group (systemtap_session& s)
dc38c0ae 7914{
b20febf3
FCE
7915 if (! s.profile_derived_probes)
7916 s.profile_derived_probes = new profile_derived_probe_group ();
7917 s.profile_derived_probes->enroll (this);
dc38c0ae
DS
7918}
7919
7920
b20febf3 7921struct profile_builder: public derived_probe_builder
39e57ce0 7922{
b20febf3
FCE
7923 profile_builder() {}
7924 virtual void build(systemtap_session & sess,
7925 probe * base,
7926 probe_point * location,
86bf665e 7927 literal_map_t const &,
b20febf3
FCE
7928 vector<derived_probe *> & finished_results)
7929 {
682f5024 7930 sess.unwindsym_modules.insert ("kernel");
b20febf3
FCE
7931 finished_results.push_back(new profile_derived_probe(sess, base, location));
7932 }
7933};
46b84a80 7934
39e57ce0 7935
b20febf3
FCE
7936// timer.profile probe handlers are hooked up in an entertaining way
7937// to the underlying kernel facility. The fact that 2.6.11+ era
7938// "register_timer_hook" API allows only one consumer *system-wide*
7939// will give a hint. We will have a single entry function (and thus
7940// trivial registration / unregistration), and it will call all probe
7941// handler functions in sequence.
39e57ce0 7942
6dce2125 7943void
b20febf3 7944profile_derived_probe_group::emit_module_decls (systemtap_session& s)
6dce2125 7945{
b20febf3 7946 if (probes.empty()) return;
39e57ce0 7947
b20febf3
FCE
7948 // kernels < 2.6.10: use register_profile_notifier API
7949 // kernels >= 2.6.10: use register_timer_hook API
7950 s.op->newline() << "/* ---- profile probes ---- */";
39e57ce0 7951
b20febf3
FCE
7952 // This function calls all the profiling probe handlers in sequence.
7953 // The only tricky thing is that the context will be reused amongst
7954 // them. While a simple sequence of calls to the individual probe
7955 // handlers is unlikely to go terribly wrong (with c->last_error
7956 // being set causing an early return), but for extra assurance, we
7957 // open-code the same logic here.
39e57ce0 7958
b20febf3
FCE
7959 s.op->newline() << "static void enter_all_profile_probes (struct pt_regs *regs) {";
7960 s.op->indent(1);
c12d974f
FCE
7961 string pp = lex_cast_qstring("timer.profile"); // hard-coded for convenience
7962 common_probe_entryfn_prologue (s.op, "STAP_SESSION_RUNNING", pp);
29b0069b 7963 s.op->newline() << "c->regs = regs;";
39e57ce0 7964
b20febf3
FCE
7965 for (unsigned i=0; i<probes.size(); i++)
7966 {
7967 if (i > 0)
7968 {
4baf0e53 7969 // Some lightweight inter-probe context resetting
6f313a73 7970 // XXX: not quite right: MAXERRORS not respected
29fdb4e4 7971 s.op->newline() << "c->actionremaining = MAXACTION;";
b20febf3
FCE
7972 }
7973 s.op->newline() << "if (c->last_error == NULL) " << probes[i]->name << " (c);";
7974 }
7975 common_probe_entryfn_epilogue (s.op);
7976 s.op->newline(-1) << "}";
7977
7978 s.op->newline() << "#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,10)"; // == using_rpn of yore
7979
4c2732a1 7980 s.op->newline() << "static int enter_profile_probes (struct notifier_block *self,"
b20febf3
FCE
7981 << " unsigned long val, void *data) {";
7982 s.op->newline(1) << "(void) self; (void) val;";
7983 s.op->newline() << "enter_all_profile_probes ((struct pt_regs *) data);";
7984 s.op->newline() << "return 0;";
7985 s.op->newline(-1) << "}";
7986 s.op->newline() << "struct notifier_block stap_profile_notifier = {"
7987 << " .notifier_call = & enter_profile_probes };";
4baf0e53 7988
b20febf3 7989 s.op->newline() << "#else";
6dce2125 7990
4c2732a1 7991 s.op->newline() << "static int enter_profile_probes (struct pt_regs *regs) {";
b20febf3
FCE
7992 s.op->newline(1) << "enter_all_profile_probes (regs);";
7993 s.op->newline() << "return 0;";
7994 s.op->newline(-1) << "}";
39e57ce0 7995
b20febf3 7996 s.op->newline() << "#endif";
39e57ce0
FCE
7997}
7998
7999
dc38c0ae 8000void
b20febf3 8001profile_derived_probe_group::emit_module_init (systemtap_session& s)
dc38c0ae 8002{
b20febf3
FCE
8003 if (probes.empty()) return;
8004
6f313a73 8005 s.op->newline() << "probe_point = \"timer.profile\";"; // NB: hard-coded for convenience
b20febf3
FCE
8006 s.op->newline() << "#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,10)"; // == using_rpn of yore
8007 s.op->newline() << "rc = register_profile_notifier (& stap_profile_notifier);";
8008 s.op->newline() << "#else";
8009 s.op->newline() << "rc = register_timer_hook (& enter_profile_probes);";
8010 s.op->newline() << "#endif";
dc38c0ae
DS
8011}
8012
8013
46b84a80 8014void
b20febf3 8015profile_derived_probe_group::emit_module_exit (systemtap_session& s)
46b84a80 8016{
b20febf3 8017 if (probes.empty()) return;
46b84a80 8018
b20febf3
FCE
8019 s.op->newline() << "for (i=0; i<" << probes.size() << "; i++)";
8020 s.op->newline(1) << "#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,10)"; // == using_rpn of yore
8021 s.op->newline() << "unregister_profile_notifier (& stap_profile_notifier);";
8022 s.op->newline() << "#else";
8023 s.op->newline() << "unregister_timer_hook (& enter_profile_probes);";
8024 s.op->newline() << "#endif";
8025 s.op->indent(-1);
46b84a80
DS
8026}
8027
ce82316f 8028
342d3f96 8029
604eef3b
MH
8030// ------------------------------------------------------------------------
8031// procfs file derived probes
8032// ------------------------------------------------------------------------
8033
ce82316f 8034
12b21830
DS
8035static string TOK_PROCFS("procfs");
8036static string TOK_READ("read");
8037static string TOK_WRITE("write");
8038
604eef3b
MH
8039struct procfs_derived_probe: public derived_probe
8040{
8041 string path;
8042 bool write;
87ebf4cb
DS
8043 bool target_symbol_seen;
8044
604eef3b
MH
8045 procfs_derived_probe (systemtap_session &, probe* p, probe_point* l, string ps, bool w);
8046 void join_group (systemtap_session& s);
8047};
8048
8049
87ebf4cb
DS
8050struct procfs_probe_set
8051{
8052 procfs_derived_probe* read_probe;
8053 procfs_derived_probe* write_probe;
8054
8055 procfs_probe_set () : read_probe (NULL), write_probe (NULL) {}
8056};
8057
8058
604eef3b
MH
8059struct procfs_derived_probe_group: public generic_dpg<procfs_derived_probe>
8060{
87ebf4cb
DS
8061private:
8062 map<string, procfs_probe_set*> probes_by_path;
8063 typedef map<string, procfs_probe_set*>::iterator p_b_p_iterator;
8064 bool has_read_probes;
8065 bool has_write_probes;
8066
604eef3b 8067public:
87ebf4cb
DS
8068 procfs_derived_probe_group () :
8069 has_read_probes(false), has_write_probes(false) {}
8070
8071 void enroll (procfs_derived_probe* probe);
604eef3b
MH
8072 void emit_module_decls (systemtap_session& s);
8073 void emit_module_init (systemtap_session& s);
8074 void emit_module_exit (systemtap_session& s);
8075};
8076
8077
de688825 8078struct procfs_var_expanding_visitor: public var_expanding_visitor
87ebf4cb 8079{
de688825
JS
8080 procfs_var_expanding_visitor(systemtap_session& s, const string& pn,
8081 string path, bool write_probe):
87ebf4cb
DS
8082 sess (s), probe_name (pn), path (path), write_probe (write_probe),
8083 target_symbol_seen (false) {}
8084
8085 systemtap_session& sess;
8086 string probe_name;
8087 string path;
8088 bool write_probe;
8089 bool target_symbol_seen;
8090
8091 void visit_target_symbol (target_symbol* e);
8092};
8093
8094
8095procfs_derived_probe::procfs_derived_probe (systemtap_session &s, probe* p,
8096 probe_point* l, string ps, bool w):
8097 derived_probe(p, l), path(ps), write(w), target_symbol_seen(false)
604eef3b 8098{
de688825
JS
8099 // Expand local variables in the probe body
8100 procfs_var_expanding_visitor v (s, name, path, write);
8101 this->body = v.require (this->body);
87ebf4cb 8102 target_symbol_seen = v.target_symbol_seen;
604eef3b
MH
8103}
8104
8105
8106void
8107procfs_derived_probe::join_group (systemtap_session& s)
8108{
8109 if (! s.procfs_derived_probes)
8110 s.procfs_derived_probes = new procfs_derived_probe_group ();
8111 s.procfs_derived_probes->enroll (this);
8112}
8113
ce82316f 8114
604eef3b 8115void
87ebf4cb 8116procfs_derived_probe_group::enroll (procfs_derived_probe* p)
604eef3b 8117{
87ebf4cb 8118 procfs_probe_set *pset;
ce82316f 8119
87ebf4cb
DS
8120 if (probes_by_path.count(p->path) == 0)
8121 {
8122 pset = new procfs_probe_set;
8123 probes_by_path[p->path] = pset;
8124 }
8125 else
8126 {
8127 pset = probes_by_path[p->path];
8128
8129 // You can only specify 1 read and 1 write probe.
8130 if (p->write && pset->write_probe != NULL)
8131 throw semantic_error("only one write procfs probe can exist for procfs path \"" + p->path + "\"");
8132 else if (! p->write && pset->read_probe != NULL)
8133 throw semantic_error("only one read procfs probe can exist for procfs path \"" + p->path + "\"");
5d23847d
FCE
8134
8135 // XXX: multiple writes should be acceptable
87ebf4cb
DS
8136 }
8137
8138 if (p->write)
8139 {
8140 pset->write_probe = p;
8141 has_write_probes = true;
8142 }
8143 else
8144 {
8145 pset->read_probe = p;
8146 has_read_probes = true;
8147 }
604eef3b
MH
8148}
8149
ce82316f 8150
604eef3b 8151void
87ebf4cb 8152procfs_derived_probe_group::emit_module_decls (systemtap_session& s)
604eef3b 8153{
87ebf4cb 8154 if (probes_by_path.empty())
ce82316f 8155 return;
604eef3b 8156
87ebf4cb 8157 s.op->newline() << "/* ---- procfs probes ---- */";
4bca766b 8158 s.op->newline() << "#include \"procfs.c\"";
87ebf4cb
DS
8159
8160 // Emit the procfs probe data list
4c2732a1 8161 s.op->newline() << "static struct stap_procfs_probe {";
87ebf4cb
DS
8162 s.op->newline(1)<< "const char *path;";
8163 s.op->newline() << "const char *read_pp;";
8164 s.op->newline() << "void (*read_ph) (struct context*);";
8165 s.op->newline() << "const char *write_pp;";
8166 s.op->newline() << "void (*write_ph) (struct context*);";
8167 s.op->newline(-1) << "} stap_procfs_probes[] = {";
8168 s.op->indent(1);
8169
8170 for (p_b_p_iterator it = probes_by_path.begin(); it != probes_by_path.end();
8171 it++)
8172 {
8173 procfs_probe_set *pset = it->second;
8174
8175 s.op->newline() << "{";
8176 s.op->line() << " .path=" << lex_cast_qstring (it->first) << ",";
8177
8178 if (pset->read_probe != NULL)
8179 {
8180 s.op->line() << " .read_pp="
8181 << lex_cast_qstring (*pset->read_probe->sole_location())
8182 << ",";
8183 s.op->line() << " .read_ph=&" << pset->read_probe->name << ",";
8184 }
8185 else
ce82316f 8186 {
87ebf4cb
DS
8187 s.op->line() << " .read_pp=NULL,";
8188 s.op->line() << " .read_ph=NULL,";
604eef3b 8189 }
ce82316f 8190
87ebf4cb
DS
8191 if (pset->write_probe != NULL)
8192 {
8193 s.op->line() << " .write_pp="
8194 << lex_cast_qstring (*pset->write_probe->sole_location())
8195 << ",";
8196 s.op->line() << " .write_ph=&" << pset->write_probe->name;
8197 }
ce82316f 8198 else
87ebf4cb
DS
8199 {
8200 s.op->line() << " .write_pp=NULL,";
8201 s.op->line() << " .write_ph=NULL";
8202 }
8203 s.op->line() << " },";
8204 }
8205 s.op->newline(-1) << "};";
8206
8207 if (has_read_probes)
8208 {
8209 // Output routine to fill in 'page' with our data.
8210 s.op->newline();
8211
8212 s.op->newline() << "static int _stp_procfs_read(char *page, char **start, off_t off, int count, int *eof, void *data) {";
8213
8214 s.op->newline(1) << "struct stap_procfs_probe *spp = (struct stap_procfs_probe *)data;";
8215 s.op->newline() << "int bytes = 0;";
8216 s.op->newline() << "string_t strdata = {'\\0'};";
8217
c12d974f 8218 common_probe_entryfn_prologue (s.op, "STAP_SESSION_RUNNING", "spp->read_pp");
87ebf4cb
DS
8219
8220 s.op->newline() << "if (c->data == NULL)";
8221 s.op->newline(1) << "c->data = &strdata;";
007f0f1c
DS
8222 s.op->newline(-1) << "else {";
8223
8224 s.op->newline(1) << "if (unlikely (atomic_inc_return (& skipped_count) > MAXSKIPPED)) {";
8225 s.op->newline(1) << "atomic_set (& session_state, STAP_SESSION_ERROR);";
8226 s.op->newline() << "_stp_exit ();";
8227 s.op->newline(-1) << "}";
8228 s.op->newline() << "atomic_dec (& c->busy);";
8229 s.op->newline() << "goto probe_epilogue;";
8230 s.op->newline(-1) << "}";
87ebf4cb
DS
8231
8232 // call probe function (which copies data into strdata)
007f0f1c 8233 s.op->newline() << "(*spp->read_ph) (c);";
87ebf4cb
DS
8234
8235 // copy string data into 'page'
8236 s.op->newline() << "c->data = NULL;";
007f0f1c 8237 s.op->newline() << "bytes = strnlen(strdata, MAXSTRINGLEN - 1);";
87ebf4cb
DS
8238 s.op->newline() << "if (off >= bytes)";
8239 s.op->newline(1) << "*eof = 1;";
8240 s.op->newline(-1) << "else {";
8241 s.op->newline(1) << "bytes -= off;";
8242 s.op->newline() << "if (bytes > count)";
8243 s.op->newline(1) << "bytes = count;";
8244 s.op->newline(-1) << "memcpy(page, strdata + off, bytes);";
8245 s.op->newline() << "*start = page;";
8246 s.op->newline(-1) << "}";
8247
87ebf4cb 8248 common_probe_entryfn_epilogue (s.op);
87ebf4cb
DS
8249 s.op->newline() << "return bytes;";
8250
8251 s.op->newline(-1) << "}";
8252 }
8253 if (has_write_probes)
8254 {
8255 s.op->newline() << "static int _stp_procfs_write(struct file *file, const char *buffer, unsigned long count, void *data) {";
8256
8257 s.op->newline(1) << "struct stap_procfs_probe *spp = (struct stap_procfs_probe *)data;";
007f0f1c
DS
8258 s.op->newline() << "string_t strdata = {'\\0'};";
8259
c12d974f 8260 common_probe_entryfn_prologue (s.op, "STAP_SESSION_RUNNING", "spp->write_pp");
87ebf4cb 8261
007f0f1c
DS
8262 s.op->newline() << "if (count > (MAXSTRINGLEN - 1))";
8263 s.op->newline(1) << "count = MAXSTRINGLEN - 1;";
8264 s.op->newline(-1) << "_stp_copy_from_user(strdata, buffer, count);";
8265
8266 s.op->newline() << "if (c->data == NULL)";
8267 s.op->newline(1) << "c->data = &strdata;";
8268 s.op->newline(-1) << "else {";
8269
8270 s.op->newline(1) << "if (unlikely (atomic_inc_return (& skipped_count) > MAXSKIPPED)) {";
8271 s.op->newline(1) << "atomic_set (& session_state, STAP_SESSION_ERROR);";
8272 s.op->newline() << "_stp_exit ();";
8273 s.op->newline(-1) << "}";
8274 s.op->newline() << "atomic_dec (& c->busy);";
8275 s.op->newline() << "goto probe_epilogue;";
8276 s.op->newline(-1) << "}";
8277
8278 // call probe function (which copies data out of strdata)
8279 s.op->newline() << "(*spp->write_ph) (c);";
8280
8281 s.op->newline() << "c->data = NULL;";
8282 common_probe_entryfn_epilogue (s.op);
8283
8284 s.op->newline() << "return count;";
87ebf4cb 8285 s.op->newline(-1) << "}";
604eef3b 8286 }
87ebf4cb
DS
8287}
8288
8289
8290void
8291procfs_derived_probe_group::emit_module_init (systemtap_session& s)
8292{
8293 if (probes_by_path.empty())
8294 return;
8295
8296 s.op->newline() << "for (i = 0; i < " << probes_by_path.size() << "; i++) {";
8297 s.op->newline(1) << "struct stap_procfs_probe *spp = &stap_procfs_probes[i];";
8298
8299 s.op->newline() << "if (spp->read_pp)";
8300 s.op->newline(1) << "probe_point = spp->read_pp;";
8301 s.op->newline(-1) << "else";
8302 s.op->newline(1) << "probe_point = spp->write_pp;";
8303
8304 s.op->newline(-1) << "rc = _stp_create_procfs(spp->path, i);";
8305
8306 s.op->newline() << "if (rc) {";
8307 s.op->newline(1) << "_stp_close_procfs();";
8308 s.op->newline() << "break;";
8309 s.op->newline(-1) << "}";
8310
4baf0e53 8311 if (has_read_probes)
bcf31db4
DS
8312 {
8313 s.op->newline() << "if (spp->read_pp)";
8314 s.op->newline(1) << "_stp_procfs_files[i]->read_proc = &_stp_procfs_read;";
8315 s.op->newline(-1) << "else";
8316 s.op->newline(1) << "_stp_procfs_files[i]->read_proc = NULL;";
8317 s.op->indent(-1);
8318 }
8319 else
8320 s.op->newline() << "_stp_procfs_files[i]->read_proc = NULL;";
87ebf4cb 8321
bcf31db4
DS
8322 if (has_write_probes)
8323 {
cf8dc3c7 8324 s.op->newline() << "if (spp->write_pp)";
bcf31db4
DS
8325 s.op->newline(1) << "_stp_procfs_files[i]->write_proc = &_stp_procfs_write;";
8326 s.op->newline(-1) << "else";
8327 s.op->newline(1) << "_stp_procfs_files[i]->write_proc = NULL;";
8328 s.op->indent(-1);
8329 }
8330 else
8331 s.op->newline() << "_stp_procfs_files[i]->write_proc = NULL;";
87ebf4cb 8332
bcf31db4 8333 s.op->newline() << "_stp_procfs_files[i]->data = spp;";
87ebf4cb 8334 s.op->newline(-1) << "}"; // for loop
604eef3b
MH
8335}
8336
ce82316f 8337
604eef3b
MH
8338void
8339procfs_derived_probe_group::emit_module_exit (systemtap_session& s)
8340{
87ebf4cb
DS
8341 if (probes_by_path.empty())
8342 return;
8343
4baf0e53 8344 s.op->newline() << "_stp_close_procfs();";
604eef3b
MH
8345}
8346
ce82316f 8347
87ebf4cb 8348void
de688825 8349procfs_var_expanding_visitor::visit_target_symbol (target_symbol* e)
87ebf4cb 8350{
87ebf4cb
DS
8351 assert(e->base_name.size() > 0 && e->base_name[0] == '$');
8352
8353 if (e->base_name != "$value")
8354 throw semantic_error ("invalid target symbol for procfs probe, $value expected",
8355 e->tok);
8356
4ec2f7d0
DS
8357 if (e->components.size() > 0)
8358 {
8359 switch (e->components[0].first)
8360 {
8361 case target_symbol::comp_literal_array_index:
8362 throw semantic_error("procfs target variable '$value' may not be used as array",
8363 e->tok);
8364 break;
8365 case target_symbol::comp_struct_member:
8366 throw semantic_error("procfs target variable '$value' may not be used as a structure",
8367 e->tok);
8368 break;
8369 default:
8370 throw semantic_error ("invalid use of procfs target variable '$value'",
8371 e->tok);
8372 break;
8373 }
8374 }
8375
87ebf4cb
DS
8376 bool lvalue = is_active_lvalue(e);
8377 if (write_probe && lvalue)
8378 throw semantic_error("procfs $value variable is read-only in a procfs write probe", e->tok);
cf8dc3c7
DS
8379 else if (! write_probe && ! lvalue)
8380 throw semantic_error("procfs $value variable cannot be read in a procfs read probe", e->tok);
87ebf4cb
DS
8381
8382 // Remember that we've seen a target variable.
8383 target_symbol_seen = true;
8384
8385 // Synthesize a function.
8386 functiondecl *fdecl = new functiondecl;
8387 fdecl->tok = e->tok;
8388 embeddedcode *ec = new embeddedcode;
8389 ec->tok = e->tok;
8390
8391 string fname = (string(lvalue ? "_procfs_value_set" : "_procfs_value_get")
8392 + "_" + lex_cast<string>(tick++));
8393 string locvalue = "CONTEXT->data";
8394
8395 if (! lvalue)
007f0f1c
DS
8396 ec->code = string("strlcpy (THIS->__retvalue, ") + locvalue
8397 + string(", MAXSTRINGLEN); /* pure */");
87ebf4cb
DS
8398 else
8399 ec->code = string("strlcpy (") + locvalue
8400 + string(", THIS->value, MAXSTRINGLEN);");
8401
8402 fdecl->name = fname;
8403 fdecl->body = ec;
8404 fdecl->type = pe_string;
8405
8406 if (lvalue)
8407 {
8408 // Modify the fdecl so it carries a single pe_string formal
8409 // argument called "value".
8410
8411 vardecl *v = new vardecl;
8412 v->type = pe_string;
8413 v->name = "value";
8414 v->tok = e->tok;
8415 fdecl->formal_args.push_back(v);
8416 }
f76427a2 8417 sess.functions[fdecl->name]=fdecl;
87ebf4cb
DS
8418
8419 // Synthesize a functioncall.
8420 functioncall* n = new functioncall;
8421 n->tok = e->tok;
8422 n->function = fname;
8423 n->referent = 0; // NB: must not resolve yet, to ensure inclusion in session
8424
8425 if (lvalue)
8426 {
8427 // Provide the functioncall to our parent, so that it can be
8428 // used to substitute for the assignment node immediately above
8429 // us.
8430 assert(!target_symbol_setter_functioncalls.empty());
8431 *(target_symbol_setter_functioncalls.top()) = n;
8432 }
8433
4ed05b15 8434 provide (n);
87ebf4cb
DS
8435}
8436
8437
604eef3b
MH
8438struct procfs_builder: public derived_probe_builder
8439{
ce82316f 8440 procfs_builder() {}
604eef3b
MH
8441 virtual void build(systemtap_session & sess,
8442 probe * base,
8443 probe_point * location,
86bf665e 8444 literal_map_t const & parameters,
ce82316f 8445 vector<derived_probe *> & finished_results);
604eef3b 8446};
39e57ce0 8447
ce82316f
DS
8448
8449void
8450procfs_builder::build(systemtap_session & sess,
8451 probe * base,
8452 probe_point * location,
86bf665e 8453 literal_map_t const & parameters,
ce82316f
DS
8454 vector<derived_probe *> & finished_results)
8455{
8456 string path;
12b21830
DS
8457 bool has_procfs = get_param(parameters, TOK_PROCFS, path);
8458 bool has_read = (parameters.find(TOK_READ) != parameters.end());
8459 bool has_write = (parameters.find(TOK_WRITE) != parameters.end());
ce82316f 8460
87ebf4cb
DS
8461 // If no procfs path, default to "command". The runtime will do
8462 // this for us, but if we don't do it here, we'll think the
8463 // following 2 probes are attached to different paths:
8464 //
8465 // probe procfs("command").read {}"
8466 // probe procfs.write {}
4baf0e53 8467
ce82316f
DS
8468 if (! has_procfs)
8469 path = "command";
227cacb9
DS
8470 // If we have a path, we need to validate it.
8471 else
8472 {
8473 string::size_type start_pos, end_pos;
8474 string component;
8475 start_pos = 0;
8476 while ((end_pos = path.find('/', start_pos)) != string::npos)
8477 {
8478 // Make sure it doesn't start with '/'.
8479 if (end_pos == 0)
8480 throw semantic_error ("procfs path cannot start with a '/'",
8481 location->tok);
8482
8483 component = path.substr(start_pos, end_pos - start_pos);
8484 // Make sure it isn't empty.
8485 if (component.size() == 0)
8486 throw semantic_error ("procfs path component cannot be empty",
8487 location->tok);
8488 // Make sure it isn't relative.
8489 else if (component == "." || component == "..")
8490 throw semantic_error ("procfs path cannot be relative (and contain '.' or '..')", location->tok);
8491
8492 start_pos = end_pos + 1;
8493 }
8494 component = path.substr(start_pos);
8495 // Make sure it doesn't end with '/'.
8496 if (component.size() == 0)
8497 throw semantic_error ("procfs path cannot end with a '/'", location->tok);
8498 // Make sure it isn't relative.
8499 else if (component == "." || component == "..")
8500 throw semantic_error ("procfs path cannot be relative (and contain '.' or '..')", location->tok);
8501 }
ce82316f
DS
8502
8503 if (!(has_read ^ has_write))
8504 throw semantic_error ("need read/write component", location->tok);
8505
8506 finished_results.push_back(new procfs_derived_probe(sess, base, location,
8507 path, has_write));
8508}
8509
8510
342d3f96 8511
30a279be
FCE
8512// ------------------------------------------------------------------------
8513// statically inserted macro-based derived probes
8514// ------------------------------------------------------------------------
8515
12b21830 8516static string TOK_FORMAT("format");
30a279be 8517
2c384610
DS
8518struct mark_arg
8519{
8520 bool str;
8521 string c_type;
8522 exp_type stp_type;
8523};
8524
30a279be
FCE
8525struct mark_derived_probe: public derived_probe
8526{
8527 mark_derived_probe (systemtap_session &s,
eb973c2a 8528 const string& probe_name, const string& probe_format,
5d23847d 8529 probe* base_probe, probe_point* location);
30a279be 8530
35d4ab18 8531 systemtap_session& sess;
eb973c2a 8532 string probe_name, probe_format;
2c384610
DS
8533 vector <struct mark_arg *> mark_args;
8534 bool target_symbol_seen;
30a279be 8535
b20febf3 8536 void join_group (systemtap_session& s);
35d4ab18 8537 void emit_probe_context_vars (translator_output* o);
2c384610 8538 void initialize_probe_context_vars (translator_output* o);
89f3a125 8539 void printargs (std::ostream &o) const;
2c384610 8540
eb973c2a 8541 void parse_probe_format ();
30a279be
FCE
8542};
8543
8544
b20febf3
FCE
8545struct mark_derived_probe_group: public generic_dpg<mark_derived_probe>
8546{
8547public:
2c384610
DS
8548 void emit_module_decls (systemtap_session& s);
8549 void emit_module_init (systemtap_session& s);
8550 void emit_module_exit (systemtap_session& s);
b20febf3
FCE
8551};
8552
8553
de688825 8554struct mark_var_expanding_visitor: public var_expanding_visitor
35d4ab18 8555{
de688825
JS
8556 mark_var_expanding_visitor(systemtap_session& s, const string& pn,
8557 vector <struct mark_arg *> &mark_args):
2c384610
DS
8558 sess (s), probe_name (pn), mark_args (mark_args),
8559 target_symbol_seen (false) {}
35d4ab18 8560 systemtap_session& sess;
35d4ab18 8561 string probe_name;
2c384610
DS
8562 vector <struct mark_arg *> &mark_args;
8563 bool target_symbol_seen;
35d4ab18
FCE
8564
8565 void visit_target_symbol (target_symbol* e);
0a63c36f 8566 void visit_target_symbol_arg (target_symbol* e);
bc54e71c 8567 void visit_target_symbol_context (target_symbol* e);
35d4ab18
FCE
8568};
8569
8570
1969b5bc
DS
8571void
8572hex_dump(unsigned char *data, size_t len)
2c384610 8573{
1969b5bc
DS
8574 // Dump data
8575 size_t idx = 0;
8576 while (idx < len)
8577 {
8578 string char_rep;
8579
8580 clog << " 0x" << setfill('0') << setw(8) << hex << internal << idx;
8581
8582 for (int i = 0; i < 4; i++)
8583 {
8584 clog << " ";
8585 size_t limit = idx + 4;
8586 while (idx < len && idx < limit)
8587 {
8588 clog << setfill('0') << setw(2)
8589 << ((unsigned) *((unsigned char *)data + idx));
8590 if (isprint(*((char *)data + idx)))
8591 char_rep += *((char *)data + idx);
8592 else
8593 char_rep += '.';
8594 idx++;
8595 }
8596 while (idx < limit)
8597 {
8598 clog << " ";
8599 idx++;
8600 }
8601 }
8602 clog << " " << char_rep << dec << setfill(' ') << endl;
8603 }
8604}
8605
2c384610 8606
35d4ab18 8607void
de688825 8608mark_var_expanding_visitor::visit_target_symbol_arg (target_symbol* e)
35d4ab18 8609{
35d4ab18
FCE
8610 string argnum_s = e->base_name.substr(4,e->base_name.length()-4);
8611 int argnum = atoi (argnum_s.c_str());
2c384610
DS
8612
8613 if (argnum < 1 || argnum > (int)mark_args.size())
35d4ab18
FCE
8614 throw semantic_error ("invalid marker argument number", e->tok);
8615
2c384610
DS
8616 if (is_active_lvalue (e))
8617 throw semantic_error("write to marker parameter not permitted", e->tok);
8618
6f93ef37
DS
8619 if (e->components.size() > 0)
8620 {
8621 switch (e->components[0].first)
8622 {
8623 case target_symbol::comp_literal_array_index:
8624 throw semantic_error("marker argument may not be used as array",
8625 e->tok);
8626 break;
8627 case target_symbol::comp_struct_member:
8628 throw semantic_error("marker argument may not be used as a structure",
8629 e->tok);
8630 break;
8631 default:
8632 throw semantic_error ("invalid marker argument use", e->tok);
8633 break;
8634 }
8635 }
4baf0e53 8636
2c384610
DS
8637 // Remember that we've seen a target variable.
8638 target_symbol_seen = true;
35d4ab18
FCE
8639
8640 // Synthesize a function.
8641 functiondecl *fdecl = new functiondecl;
8642 fdecl->tok = e->tok;
8643 embeddedcode *ec = new embeddedcode;
8644 ec->tok = e->tok;
35d4ab18 8645
1b07c728
FCE
8646 string fname = string("_mark_tvar_get")
8647 + "_" + e->base_name.substr(1)
8648 + "_" + lex_cast<string>(tick++);
35d4ab18 8649
2c384610
DS
8650 if (mark_args[argnum-1]->stp_type == pe_long)
8651 ec->code = string("THIS->__retvalue = CONTEXT->locals[0].")
8652 + probe_name + string(".__mark_arg")
8653 + lex_cast<string>(argnum) + string (";");
8654 else
8655 ec->code = string("strlcpy (THIS->__retvalue, CONTEXT->locals[0].")
8656 + probe_name + string(".__mark_arg")
8657 + lex_cast<string>(argnum) + string (", MAXSTRINGLEN);");
1b07c728 8658 ec->code += "/* pure */";
35d4ab18
FCE
8659 fdecl->name = fname;
8660 fdecl->body = ec;
2c384610 8661 fdecl->type = mark_args[argnum-1]->stp_type;
f76427a2 8662 sess.functions[fdecl->name]=fdecl;
35d4ab18
FCE
8663
8664 // Synthesize a functioncall.
8665 functioncall* n = new functioncall;
8666 n->tok = e->tok;
8667 n->function = fname;
8668 n->referent = 0; // NB: must not resolve yet, to ensure inclusion in session
4ed05b15 8669 provide (n);
35d4ab18
FCE
8670}
8671
8672
0a63c36f 8673void
de688825 8674mark_var_expanding_visitor::visit_target_symbol_context (target_symbol* e)
0a63c36f 8675{
bc54e71c 8676 string sname = e->base_name;
0a63c36f
DS
8677
8678 if (is_active_lvalue (e))
bc54e71c 8679 throw semantic_error("write to marker '" + sname + "' not permitted", e->tok);
0a63c36f
DS
8680
8681 if (e->components.size() > 0)
8682 {
8683 switch (e->components[0].first)
8684 {
8685 case target_symbol::comp_literal_array_index:
bc54e71c 8686 throw semantic_error("marker '" + sname + "' may not be used as array",
0a63c36f
DS
8687 e->tok);
8688 break;
8689 case target_symbol::comp_struct_member:
bc54e71c 8690 throw semantic_error("marker '" + sname + "' may not be used as a structure",
0a63c36f
DS
8691 e->tok);
8692 break;
8693 default:
bc54e71c 8694 throw semantic_error ("invalid marker '" + sname + "' use", e->tok);
0a63c36f
DS
8695 break;
8696 }
8697 }
4baf0e53 8698
bc54e71c
MH
8699 string fname;
8700 if (e->base_name == "$format") {
8701 fname = string("_mark_format_get");
8702 } else {
8703 fname = string("_mark_name_get");
8704 }
0a63c36f
DS
8705
8706 // Synthesize a functioncall.
8707 functioncall* n = new functioncall;
8708 n->tok = e->tok;
8709 n->function = fname;
8710 n->referent = 0; // NB: must not resolve yet, to ensure inclusion in session
4ed05b15 8711 provide (n);
0a63c36f
DS
8712}
8713
8714void
de688825 8715mark_var_expanding_visitor::visit_target_symbol (target_symbol* e)
0a63c36f
DS
8716{
8717 assert(e->base_name.size() > 0 && e->base_name[0] == '$');
8718
8719 if (e->base_name.substr(0,4) == "$arg")
8720 visit_target_symbol_arg (e);
bc54e71c
MH
8721 else if (e->base_name == "$format" || e->base_name == "$name")
8722 visit_target_symbol_context (e);
0a63c36f 8723 else
bc54e71c 8724 throw semantic_error ("invalid target symbol for marker, $argN, $name or $format expected",
0a63c36f
DS
8725 e->tok);
8726}
8727
8728
35d4ab18 8729
30a279be 8730mark_derived_probe::mark_derived_probe (systemtap_session &s,
35d4ab18 8731 const string& p_n,
eb973c2a 8732 const string& p_f,
5d23847d 8733 probe* base, probe_point* loc):
a10fa7f5 8734 derived_probe (base, new probe_point(*loc) /* .components soon rewritten */),
eb973c2a 8735 sess (s), probe_name (p_n), probe_format (p_f),
f781f849 8736 target_symbol_seen (false)
30a279be 8737{
5d23847d
FCE
8738 // create synthetic probe point name; preserve condition
8739 vector<probe_point::component*> comps;
12b21830
DS
8740 comps.push_back (new probe_point::component (TOK_KERNEL));
8741 comps.push_back (new probe_point::component (TOK_MARK, new literal_string (probe_name)));
8742 comps.push_back (new probe_point::component (TOK_FORMAT, new literal_string (probe_format)));
5d23847d 8743 this->sole_location()->components = comps;
cbbe8080 8744
eb973c2a
DS
8745 // expand the marker format
8746 parse_probe_format();
35d4ab18 8747
de688825
JS
8748 // Now expand the local variables in the probe body
8749 mark_var_expanding_visitor v (sess, name, mark_args);
8750 this->body = v.require (this->body);
2c384610 8751 target_symbol_seen = v.target_symbol_seen;
35d4ab18 8752
1969b5bc 8753 if (sess.verbose > 2)
eb973c2a
DS
8754 clog << "marker-based " << name << " mark=" << probe_name
8755 << " fmt='" << probe_format << "'" << endl;
30a279be
FCE
8756}
8757
8758
2c384610
DS
8759static int
8760skip_atoi(const char **s)
dc38c0ae 8761{
2c384610
DS
8762 int i = 0;
8763 while (isdigit(**s))
8764 i = i * 10 + *((*s)++) - '0';
8765 return i;
dc38c0ae
DS
8766}
8767
8768
30a279be 8769void
eb973c2a 8770mark_derived_probe::parse_probe_format()
35d4ab18 8771{
eb973c2a 8772 const char *fmt = probe_format.c_str();
2c384610
DS
8773 int qualifier; // 'h', 'l', or 'L' for integer fields
8774 mark_arg *arg;
8775
8776 for (; *fmt ; ++fmt)
35d4ab18 8777 {
2c384610 8778 if (*fmt != '%')
35d4ab18 8779 {
2c384610
DS
8780 /* Skip text */
8781 continue;
8782 }
35d4ab18 8783
2c384610
DS
8784repeat:
8785 ++fmt;
35d4ab18 8786
2c384610
DS
8787 // skip conversion flags (if present)
8788 switch (*fmt)
8789 {
8790 case '-':
8791 case '+':
8792 case ' ':
8793 case '#':
8794 case '0':
8795 goto repeat;
8796 }
30a279be 8797
2c384610
DS
8798 // skip minimum field witdh (if present)
8799 if (isdigit(*fmt))
8800 skip_atoi(&fmt);
30a279be 8801
2c384610
DS
8802 // skip precision (if present)
8803 if (*fmt == '.')
35d4ab18 8804 {
2c384610
DS
8805 ++fmt;
8806 if (isdigit(*fmt))
8807 skip_atoi(&fmt);
8808 }
30a279be 8809
2c384610
DS
8810 // get the conversion qualifier (if present)
8811 qualifier = -1;
8812 if (*fmt == 'h' || *fmt == 'l' || *fmt == 'L')
8813 {
8814 qualifier = *fmt;
8815 ++fmt;
8816 if (qualifier == 'l' && *fmt == 'l')
8817 {
8818 qualifier = 'L';
8819 ++fmt;
8820 }
8821 }
30a279be 8822
2c384610
DS
8823 // get the conversion type
8824 switch (*fmt)
8825 {
8826 case 'c':
8827 arg = new mark_arg;
8828 arg->str = false;
8829 arg->c_type = "int";
8830 arg->stp_type = pe_long;
8831 mark_args.push_back(arg);
8832 continue;
8833
8834 case 's':
8835 arg = new mark_arg;
8836 arg->str = true;
8837 arg->c_type = "char *";
8838 arg->stp_type = pe_string;
8839 mark_args.push_back(arg);
8840 continue;
8841
8842 case 'p':
8843 arg = new mark_arg;
8844 arg->str = false;
38c963a9
DS
8845 // This should really be 'void *'. But, then we'll get a
8846 // compile error when we assign the void pointer to an
8847 // integer without a cast. So, we use 'long' instead, since
8848 // it should have the same size as 'void *'.
8849 arg->c_type = "long";
2c384610
DS
8850 arg->stp_type = pe_long;
8851 mark_args.push_back(arg);
8852 continue;
8853
8854 case '%':
8855 continue;
8856
8857 case 'o':
8858 case 'X':
8859 case 'x':
8860 case 'd':
8861 case 'i':
8862 case 'u':
8863 // fall through...
8864 break;
30a279be 8865
2c384610
DS
8866 default:
8867 if (!*fmt)
8868 --fmt;
8869 continue;
8870 }
30a279be 8871
2c384610
DS
8872 arg = new mark_arg;
8873 arg->str = false;
8874 arg->stp_type = pe_long;
8875 switch (qualifier)
8876 {
8877 case 'L':
8878 arg->c_type = "long long";
8879 break;
30a279be 8880
2c384610
DS
8881 case 'l':
8882 arg->c_type = "long";
8883 break;
e38d6504 8884
2c384610
DS
8885 case 'h':
8886 arg->c_type = "short";
8887 break;
46b84a80 8888
2c384610
DS
8889 default:
8890 arg->c_type = "int";
8891 break;
8892 }
8893 mark_args.push_back(arg);
8894 }
46b84a80
DS
8895}
8896
f781f849 8897
46b84a80 8898void
2c384610 8899mark_derived_probe::join_group (systemtap_session& s)
46b84a80 8900{
2c384610 8901 if (! s.mark_derived_probes)
775d51e5
DS
8902 {
8903 s.mark_derived_probes = new mark_derived_probe_group ();
8904
8905 // Make sure <linux/marker.h> is included early.
8906 embeddedcode *ec = new embeddedcode;
8907 ec->tok = NULL;
8908 ec->code = string("#if ! defined(CONFIG_MARKERS)\n")
8909 + string("#error \"Need CONFIG_MARKERS!\"\n")
8910 + string("#endif\n")
8911 + string("#include <linux/marker.h>\n");
8912
8913 s.embeds.push_back(ec);
8914 }
2c384610 8915 s.mark_derived_probes->enroll (this);
30a279be
FCE
8916}
8917
35d4ab18 8918
30a279be 8919void
2c384610 8920mark_derived_probe::emit_probe_context_vars (translator_output* o)
30a279be 8921{
2c384610
DS
8922 // If we haven't seen a target symbol for this probe, quit.
8923 if (! target_symbol_seen)
8924 return;
30a279be 8925
2c384610
DS
8926 for (unsigned i = 0; i < mark_args.size(); i++)
8927 {
8928 string localname = "__mark_arg" + lex_cast<string>(i+1);
8929 switch (mark_args[i]->stp_type)
8930 {
8931 case pe_long:
8932 o->newline() << "int64_t " << localname << ";";
8933 break;
8934 case pe_string:
8935 o->newline() << "string_t " << localname << ";";
8936 break;
8937 default:
8938 throw semantic_error ("cannot expand unknown type");
8939 break;
8940 }
8941 }
30a279be
FCE
8942}
8943
8944
dc38c0ae 8945void
2c384610 8946mark_derived_probe::initialize_probe_context_vars (translator_output* o)
dc38c0ae 8947{
2c384610
DS
8948 // If we haven't seen a target symbol for this probe, quit.
8949 if (! target_symbol_seen)
8950 return;
8951
d09fee57 8952 bool deref_fault_needed = false;
2c384610 8953 for (unsigned i = 0; i < mark_args.size(); i++)
dc38c0ae 8954 {
2c384610
DS
8955 string localname = "l->__mark_arg" + lex_cast<string>(i+1);
8956 switch (mark_args[i]->stp_type)
8957 {
8958 case pe_long:
3b0c565c 8959 o->newline() << localname << " = va_arg(*c->mark_va_list, "
2c384610
DS
8960 << mark_args[i]->c_type << ");";
8961 break;
8962
8963 case pe_string:
8964 // We're assuming that this is a kernel string (this code is
8965 // basically the guts of kernel_string), not a user string.
8966 o->newline() << "{ " << mark_args[i]->c_type
3b0c565c 8967 << " tmp_str = va_arg(*c->mark_va_list, "
2c384610
DS
8968 << mark_args[i]->c_type << ");";
8969 o->newline() << "deref_string (" << localname
d09fee57
DS
8970 << ", tmp_str, MAXSTRINGLEN); }";
8971 deref_fault_needed = true;
2c384610
DS
8972 break;
8973
8974 default:
8975 throw semantic_error ("cannot expand unknown type");
8976 break;
8977 }
dc38c0ae 8978 }
d09fee57
DS
8979 if (deref_fault_needed)
8980 // Need to report errors?
8981 o->newline() << "deref_fault: ;";
dc38c0ae
DS
8982}
8983
89f3a125
WH
8984void
8985mark_derived_probe::printargs(std::ostream &o) const
8986{
8987 for (unsigned i = 0; i < mark_args.size(); i++)
8988 {
8989 string localname = "$arg" + lex_cast<string>(i+1);
8990 switch (mark_args[i]->stp_type)
8991 {
8992 case pe_long:
8993 o << " " << localname << ":long";
8994 break;
8995 case pe_string:
8996 o << " " << localname << ":string";
8997 break;
8998 default:
8999 o << " " << localname << ":unknown";
9000 break;
9001 }
9002 }
9003}
9004
30a279be 9005
342d3f96
DS
9006void
9007mark_derived_probe_group::emit_module_decls (systemtap_session& s)
9008{
9009 if (probes.empty())
9010 return;
9011
9012 s.op->newline() << "/* ---- marker probes ---- */";
46b84a80 9013
4c2732a1 9014 s.op->newline() << "static struct stap_marker_probe {";
0a63c36f
DS
9015 s.op->newline(1) << "const char * const name;";
9016 s.op->newline() << "const char * const format;";
9017 s.op->newline() << "const char * const pp;";
9018 s.op->newline() << "void (* const ph) (struct context *);";
46b84a80 9019
2c384610
DS
9020 s.op->newline(-1) << "} stap_marker_probes [" << probes.size() << "] = {";
9021 s.op->indent(1);
9022 for (unsigned i=0; i < probes.size(); i++)
46b84a80 9023 {
4baf0e53 9024 s.op->newline () << "{";
2c384610
DS
9025 s.op->line() << " .name=" << lex_cast_qstring(probes[i]->probe_name)
9026 << ",";
eb973c2a 9027 s.op->line() << " .format=" << lex_cast_qstring(probes[i]->probe_format)
2c384610
DS
9028 << ",";
9029 s.op->line() << " .pp=" << lex_cast_qstring (*probes[i]->sole_location())
9030 << ",";
9031 s.op->line() << " .ph=&" << probes[i]->name;
9032 s.op->line() << " },";
46b84a80 9033 }
2c384610
DS
9034 s.op->newline(-1) << "};";
9035 s.op->newline();
4baf0e53 9036
2c384610
DS
9037
9038 // Emit the marker callback function
9039 s.op->newline();
3b0c565c
DS
9040 s.op->newline() << "static void enter_marker_probe (void *probe_data, void *call_data, const char *fmt, va_list *args) {";
9041 s.op->newline(1) << "struct stap_marker_probe *smp = (struct stap_marker_probe *)probe_data;";
c12d974f 9042 common_probe_entryfn_prologue (s.op, "STAP_SESSION_RUNNING", "smp->pp");
bc54e71c
MH
9043 s.op->newline() << "c->marker_name = smp->name;";
9044 s.op->newline() << "c->marker_format = smp->format;";
3b0c565c 9045 s.op->newline() << "c->mark_va_list = args;";
2c384610 9046 s.op->newline() << "(*smp->ph) (c);";
3b0c565c 9047 s.op->newline() << "c->mark_va_list = NULL;";
0a63c36f
DS
9048 s.op->newline() << "c->data = NULL;";
9049
2c384610
DS
9050 common_probe_entryfn_epilogue (s.op);
9051 s.op->newline(-1) << "}";
46b84a80 9052
2c384610 9053 return;
46b84a80
DS
9054}
9055
9056
2c384610
DS
9057void
9058mark_derived_probe_group::emit_module_init (systemtap_session &s)
30a279be 9059{
2c384610
DS
9060 if (probes.size () == 0)
9061 return;
30a279be 9062
2c384610
DS
9063 s.op->newline() << "/* init marker probes */";
9064 s.op->newline() << "for (i=0; i<" << probes.size() << "; i++) {";
9065 s.op->newline(1) << "struct stap_marker_probe *smp = &stap_marker_probes[i];";
9066 s.op->newline() << "probe_point = smp->pp;";
38c963a9 9067 s.op->newline() << "rc = marker_probe_register(smp->name, smp->format, enter_marker_probe, smp);";
3b0c565c 9068 s.op->newline() << "if (rc) {";
2c384610
DS
9069 s.op->newline(1) << "for (j=i-1; j>=0; j--) {"; // partial rollback
9070 s.op->newline(1) << "struct stap_marker_probe *smp2 = &stap_marker_probes[j];";
3b0c565c 9071 s.op->newline() << "marker_probe_unregister(smp2->name, enter_marker_probe, smp2);";
2c384610
DS
9072 s.op->newline(-1) << "}";
9073 s.op->newline() << "break;"; // don't attempt to register any more probes
9074 s.op->newline(-1) << "}";
9075 s.op->newline(-1) << "}"; // for loop
9076}
9077
9078
9079void
9080mark_derived_probe_group::emit_module_exit (systemtap_session& s)
9081{
9082 if (probes.empty())
9083 return;
9084
9085 s.op->newline() << "/* deregister marker probes */";
9086 s.op->newline() << "for (i=0; i<" << probes.size() << "; i++) {";
9087 s.op->newline(1) << "struct stap_marker_probe *smp = &stap_marker_probes[i];";
3b0c565c 9088 s.op->newline() << "marker_probe_unregister(smp->name, enter_marker_probe, smp);";
2c384610
DS
9089 s.op->newline(-1) << "}"; // for loop
9090}
30a279be
FCE
9091
9092
9093struct mark_builder: public derived_probe_builder
9094{
9095private:
f781f849 9096 bool cache_initialized;
eb973c2a
DS
9097 typedef multimap<string, string> mark_cache_t;
9098 typedef multimap<string, string>::const_iterator mark_cache_const_iterator_t;
9099 typedef pair<mark_cache_const_iterator_t, mark_cache_const_iterator_t>
9100 mark_cache_const_iterator_pair_t;
9101 mark_cache_t mark_cache;
30a279be
FCE
9102
9103public:
f781f849 9104 mark_builder(): cache_initialized(false) {}
2c384610
DS
9105
9106 void build_no_more (systemtap_session &s)
9107 {
f781f849 9108 if (! mark_cache.empty())
2c384610
DS
9109 {
9110 if (s.verbose > 3)
f781f849
DS
9111 clog << "mark_builder releasing cache" << endl;
9112 mark_cache.clear();
2c384610
DS
9113 }
9114 }
9115
30a279be
FCE
9116 void build(systemtap_session & sess,
9117 probe * base,
9118 probe_point * location,
86bf665e 9119 literal_map_t const & parameters,
30a279be
FCE
9120 vector<derived_probe *> & finished_results);
9121};
9122
9123
30a279be
FCE
9124void
9125mark_builder::build(systemtap_session & sess,
2c384610 9126 probe * base,
cbbe8080 9127 probe_point *loc,
86bf665e 9128 literal_map_t const & parameters,
2c384610 9129 vector<derived_probe *> & finished_results)
30a279be 9130{
f781f849 9131 string mark_str_val;
12b21830 9132 bool has_mark_str = get_param (parameters, TOK_MARK, mark_str_val);
eb973c2a 9133 string mark_format_val;
12b21830 9134 bool has_mark_format = get_param (parameters, TOK_FORMAT, mark_format_val);
f781f849 9135 assert (has_mark_str);
ced347a9 9136 (void) has_mark_str;
30a279be 9137
f781f849
DS
9138 if (! cache_initialized)
9139 {
9140 cache_initialized = true;
b5e66ada
FCE
9141 string module_markers_path = sess.kernel_build_tree + "/Module.markers";
9142
f781f849
DS
9143 ifstream module_markers;
9144 module_markers.open(module_markers_path.c_str(), ifstream::in);
9145 if (! module_markers)
9146 {
9147 if (sess.verbose>3)
9148 clog << module_markers_path << " cannot be opened: "
9149 << strerror(errno) << endl;
9150 return;
9151 }
30a279be 9152
f781f849
DS
9153 string name, module, format;
9154 do
9155 {
9156 module_markers >> name >> module;
9157 getline(module_markers, format);
9158
9159 // trim leading whitespace
9160 string::size_type notwhite = format.find_first_not_of(" \t");
9161 format.erase(0, notwhite);
9162
a53c9645
DS
9163 // If the format is empty, make sure we add back a space
9164 // character, which is what MARK_NOARGS expands to.
9165 if (format.length() == 0)
9166 format = " ";
9167
f781f849
DS
9168 if (sess.verbose>3)
9169 clog << "'" << name << "' '" << module << "' '" << format
9170 << "'" << endl;
4baf0e53 9171
eb973c2a
DS
9172 if (mark_cache.count(name) > 0)
9173 {
9174 // If we have 2 markers with the same we've got 2 cases:
9175 // different format strings or duplicate format strings.
9176 // If an existing marker in the cache doesn't have the
9177 // same format string, add this marker.
9178 mark_cache_const_iterator_pair_t ret;
9179 mark_cache_const_iterator_t it;
9180 bool matching_format_string = false;
41c262f3 9181
eb973c2a
DS
9182 ret = mark_cache.equal_range(name);
9183 for (it = ret.first; it != ret.second; ++it)
9184 {
9185 if (format == it->second)
9186 {
9187 matching_format_string = true;
9188 break;
9189 }
9190 }
9191
9192 if (! matching_format_string)
9193 mark_cache.insert(pair<string,string>(name, format));
9194 }
9195 else
9196 mark_cache.insert(pair<string,string>(name, format));
f781f849
DS
9197 }
9198 while (! module_markers.eof());
9199 module_markers.close();
30a279be
FCE
9200 }
9201
f781f849 9202 // Search marker list for matching markers
eb973c2a 9203 for (mark_cache_const_iterator_t it = mark_cache.begin();
f781f849
DS
9204 it != mark_cache.end(); it++)
9205 {
9206 // Below, "rc" has negative polarity: zero iff matching.
9207 int rc = fnmatch(mark_str_val.c_str(), it->first.c_str(), 0);
9208 if (! rc)
9209 {
eb973c2a
DS
9210 bool add_result = true;
9211
9212 // Match format strings (if the user specified one)
9213 if (has_mark_format && fnmatch(mark_format_val.c_str(),
9214 it->second.c_str(), 0))
9215 add_result = false;
9216
9217 if (add_result)
9218 {
9219 derived_probe *dp
9220 = new mark_derived_probe (sess,
9221 it->first, it->second,
9222 base, loc);
9223 finished_results.push_back (dp);
9224 }
f781f849
DS
9225 }
9226 }
30a279be
FCE
9227}
9228
9229
342d3f96 9230
0a6f5a3f
JS
9231// ------------------------------------------------------------------------
9232// statically inserted kernel-tracepoint derived probes
9233// ------------------------------------------------------------------------
9234
6fb70fb7
JS
9235struct tracepoint_arg
9236{
9237 string name, c_type;
f8a968bc
JS
9238 bool used, isptr;
9239 Dwarf_Die type_die;
9240 tracepoint_arg(): used(false), isptr(false) {}
6fb70fb7 9241};
0a6f5a3f
JS
9242
9243struct tracepoint_derived_probe: public derived_probe
9244{
79189b84
JS
9245 tracepoint_derived_probe (systemtap_session& s,
9246 dwflpp& dw, Dwarf_Die& func_die,
9247 const string& tracepoint_name,
9248 probe* base_probe, probe_point* location);
9249
9250 systemtap_session& sess;
6fb70fb7
JS
9251 string tracepoint_name, header;
9252 vector <struct tracepoint_arg> args;
79189b84 9253
6fb70fb7 9254 void build_args(dwflpp& dw, Dwarf_Die& func_die);
e2086848 9255 void printargs (std::ostream &o) const;
79189b84 9256 void join_group (systemtap_session& s);
f8a968bc 9257 void emit_probe_context_vars (translator_output* o);
0a6f5a3f
JS
9258};
9259
9260
9261struct tracepoint_derived_probe_group: public generic_dpg<tracepoint_derived_probe>
9262{
79189b84
JS
9263 void emit_module_decls (systemtap_session& s);
9264 void emit_module_init (systemtap_session& s);
9265 void emit_module_exit (systemtap_session& s);
0a6f5a3f
JS
9266};
9267
9268
f8a968bc
JS
9269struct tracepoint_var_expanding_visitor: public var_expanding_visitor
9270{
9271 tracepoint_var_expanding_visitor(dwflpp& dw, const string& probe_name,
9272 vector <struct tracepoint_arg>& args):
9273 dw (dw), probe_name (probe_name), args (args) {}
9274 dwflpp& dw;
9275 const string& probe_name;
9276 vector <struct tracepoint_arg>& args;
9277
9278 void visit_target_symbol (target_symbol* e);
9279 void visit_target_symbol_arg (target_symbol* e);
9280 void visit_target_symbol_context (target_symbol* e);
9281};
9282
9283
9284void
9285tracepoint_var_expanding_visitor::visit_target_symbol_arg (target_symbol* e)
9286{
9287 string argname = e->base_name.substr(1);
9288
9289 // search for a tracepoint parameter matching this name
9290 tracepoint_arg *arg = NULL;
9291 for (unsigned i = 0; i < args.size(); ++i)
9292 if (args[i].name == argname)
9293 {
9294 arg = &args[i];
9295 arg->used = true;
9296 break;
9297 }
9298
9299 if (arg == NULL)
9300 {
9301 stringstream alternatives;
9302 for (unsigned i = 0; i < args.size(); ++i)
9303 alternatives << " $" << args[i].name;
046e7190 9304 alternatives << " $$name $$parms $$vars";
f8a968bc
JS
9305
9306 // We hope that this value ends up not being referenced after all, so it
9307 // can be optimized out quietly.
9308 semantic_error* saveme =
9309 new semantic_error("unable to find tracepoint variable '" + e->base_name
9310 + "' (alternatives:" + alternatives.str () + ")", e->tok);
9311 // NB: we can have multiple errors, since a target variable
9312 // may be expanded in several different contexts:
9313 // trace ("*") { $foo->bar }
9314 saveme->chain = e->saved_conversion_error;
9315 e->saved_conversion_error = saveme;
9316 provide (e);
9317 return;
9318 }
9319
9320 // make sure we're not dereferencing base types
9321 if (!e->components.empty() && !arg->isptr)
9322 switch (e->components[0].first)
9323 {
9324 case target_symbol::comp_literal_array_index:
9325 throw semantic_error("tracepoint variable '" + e->base_name
9326 + "' may not be used as array", e->tok);
9327 case target_symbol::comp_struct_member:
9328 throw semantic_error("tracepoint variable '" + e->base_name
9329 + "' may not be used as a structure", e->tok);
9330 default:
9331 throw semantic_error("invalid use of tracepoint variable '"
9332 + e->base_name + "'", e->tok);
9333 }
9334
9335 // we can only write to dereferenced fields, and only if guru mode is on
9336 bool lvalue = is_active_lvalue(e);
9337 if (lvalue && (!dw.sess.guru_mode || e->components.empty()))
9338 throw semantic_error("write to tracepoint variable '" + e->base_name
9339 + "' not permitted", e->tok);
9340
9341 if (e->components.empty())
9342 {
9343 // Synthesize a simple function to grab the parameter
9344 functiondecl *fdecl = new functiondecl;
9345 fdecl->tok = e->tok;
9346 embeddedcode *ec = new embeddedcode;
9347 ec->tok = e->tok;
9348
9349 string fname = (string("_tracepoint_tvar_get")
9350 + "_" + e->base_name.substr(1)
9351 + "_" + lex_cast<string>(tick++));
9352
9353 fdecl->name = fname;
9354 fdecl->body = ec;
9355 fdecl->type = pe_long;
9356
9357 ec->code = (string("THIS->__retvalue = CONTEXT->locals[0].")
9358 + probe_name + string(".__tracepoint_arg_")
9359 + arg->name + string (";/* pure */"));
9360
9361 dw.sess.functions[fdecl->name] = fdecl;
9362
9363 // Synthesize a functioncall.
9364 functioncall* n = new functioncall;
9365 n->tok = e->tok;
9366 n->function = fname;
9367 n->referent = 0; // NB: must not resolve yet, to ensure inclusion in session
9368
9369 provide (n);
9370 }
9371 else
9372 {
9373 // Synthesize a function to dereference the dwarf fields,
9374 // with a pointer parameter that is the base tracepoint variable
9375 functiondecl *fdecl = new functiondecl;
9376 fdecl->tok = e->tok;
9377 embeddedcode *ec = new embeddedcode;
9378 ec->tok = e->tok;
9379
9380 string fname = (string(lvalue ? "_tracepoint_tvar_set" : "_tracepoint_tvar_get")
9381 + "_" + e->base_name.substr(1)
9382 + "_" + lex_cast<string>(tick++));
9383
9384 fdecl->name = fname;
9385 fdecl->body = ec;
9386
9387 try
9388 {
9389 ec->code = dw.literal_stmt_for_pointer (&arg->type_die, e->components,
9390 lvalue, fdecl->type);
9391 }
9392 catch (const semantic_error& er)
9393 {
9394 // We suppress this error message, and pass the unresolved
9395 // variable to the next pass. We hope that this value ends
9396 // up not being referenced after all, so it can be optimized out
9397 // quietly.
9398 semantic_error* saveme = new semantic_error (er); // copy it
9399 saveme->tok1 = e->tok; // XXX: token not passed to dw code generation routines
9400 // NB: we can have multiple errors, since a target variable
9401 // may be expanded in several different contexts:
9402 // trace ("*") { $foo->bar }
9403 saveme->chain = e->saved_conversion_error;
9404 e->saved_conversion_error = saveme;
9405 provide (e);
9406 return;
9407 }
9408
9409 // Give the fdecl an argument for the raw tracepoint value
9410 vardecl *v1 = new vardecl;
9411 v1->type = pe_long;
9412 v1->name = "pointer";
9413 v1->tok = e->tok;
9414 fdecl->formal_args.push_back(v1);
9415
9416 if (lvalue)
9417 {
9418 // Modify the fdecl so it carries a pe_long formal
9419 // argument called "value".
9420
9421 // FIXME: For the time being we only support setting target
9422 // variables which have base types; these are 'pe_long' in
9423 // stap's type vocabulary. Strings and pointers might be
9424 // reasonable, some day, but not today.
9425
9426 vardecl *v2 = new vardecl;
9427 v2->type = pe_long;
9428 v2->name = "value";
9429 v2->tok = e->tok;
9430 fdecl->formal_args.push_back(v2);
9431 }
9432 else
9433 ec->code += "/* pure */";
9434
9435 dw.sess.functions[fdecl->name] = fdecl;
9436
9437 // Synthesize a functioncall.
9438 functioncall* n = new functioncall;
9439 n->tok = e->tok;
9440 n->function = fname;
9441 n->referent = 0; // NB: must not resolve yet, to ensure inclusion in session
9442
9443 // make the original a bare target symbol for the tracepoint value,
9444 // which will be passed into the dwarf dereferencing code
9445 e->components.clear();
9446 n->args.push_back(require(e));
9447
9448 if (lvalue)
9449 {
9450 // Provide the functioncall to our parent, so that it can be
9451 // used to substitute for the assignment node immediately above
9452 // us.
9453 assert(!target_symbol_setter_functioncalls.empty());
9454 *(target_symbol_setter_functioncalls.top()) = n;
9455 }
9456
9457 provide (n);
9458 }
9459}
9460
9461
9462void
9463tracepoint_var_expanding_visitor::visit_target_symbol_context (target_symbol* e)
9464{
9465 if (is_active_lvalue (e))
9466 throw semantic_error("write to tracepoint '" + e->base_name + "' not permitted", e->tok);
9467
9468 if (!e->components.empty())
9469 switch (e->components[0].first)
9470 {
9471 case target_symbol::comp_literal_array_index:
9472 throw semantic_error("tracepoint '" + e->base_name + "' may not be used as array",
9473 e->tok);
9474 case target_symbol::comp_struct_member:
9475 throw semantic_error("tracepoint '" + e->base_name + "' may not be used as a structure",
9476 e->tok);
9477 default:
9478 throw semantic_error("invalid tracepoint '" + e->base_name + "' use", e->tok);
9479 }
9480
9481 if (e->base_name == "$$name")
9482 {
9483 // Synthesize a functioncall.
9484 functioncall* n = new functioncall;
9485 n->tok = e->tok;
9486 n->function = "_mark_name_get";
9487 n->referent = 0; // NB: must not resolve yet, to ensure inclusion in session
9488 provide (n);
9489 }
046e7190 9490 else if (e->base_name == "$$vars" || e->base_name == "$$parms")
f8a968bc
JS
9491 {
9492 target_symbol *tsym = new target_symbol;
9493 print_format* pf = new print_format;
9494
9495 // Convert $$vars to sprintf of a list of vars which we recursively evaluate
9496 // NB: we synthesize a new token here rather than reusing
9497 // e->tok, because print_format::print likes to use
9498 // its tok->content.
9499 token* pf_tok = new token(*e->tok);
9500 pf_tok->content = "sprintf";
9501
9502 pf->tok = pf_tok;
9503 pf->print_to_stream = false;
9504 pf->print_with_format = true;
9505 pf->print_with_delim = false;
9506 pf->print_with_newline = false;
9507 pf->print_char = false;
9508
9509 for (unsigned i = 0; i < args.size(); ++i)
9510 {
9511 if (i > 0)
9512 pf->raw_components += " ";
9513 pf->raw_components += args[i].name;
9514 tsym->tok = e->tok;
9515 tsym->base_name = "$" + args[i].name;
9516
9517 // every variable should always be accessible!
9518 tsym->saved_conversion_error = 0;
9519 expression *texp = require (tsym); // NB: throws nothing ...
9520 assert (!tsym->saved_conversion_error); // ... but this is how we know it happened.
9521
9522 pf->raw_components += "=%#x";
9523 pf->args.push_back(texp);
9524 }
9525
9526 pf->components = print_format::string_to_components(pf->raw_components);
9527 provide (pf);
9528 }
9529 else
9530 assert(0); // shouldn't get here
9531}
9532
9533void
9534tracepoint_var_expanding_visitor::visit_target_symbol (target_symbol* e)
9535{
9536 assert(e->base_name.size() > 0 && e->base_name[0] == '$');
9537
046e7190
JS
9538 if (e->base_name == "$$name" ||
9539 e->base_name == "$$parms" ||
9540 e->base_name == "$$vars")
f8a968bc
JS
9541 visit_target_symbol_context (e);
9542 else
9543 visit_target_symbol_arg (e);
9544}
9545
9546
9547
79189b84
JS
9548tracepoint_derived_probe::tracepoint_derived_probe (systemtap_session& s,
9549 dwflpp& dw, Dwarf_Die& func_die,
9550 const string& tracepoint_name,
9551 probe* base, probe_point* loc):
9552 derived_probe (base, new probe_point(*loc) /* .components soon rewritten */),
9553 sess (s), tracepoint_name (tracepoint_name)
9554{
9555 // create synthetic probe point name; preserve condition
9556 vector<probe_point::component*> comps;
9557 comps.push_back (new probe_point::component (TOK_KERNEL));
9558 comps.push_back (new probe_point::component (TOK_TRACE, new literal_string (tracepoint_name)));
9559 this->sole_location()->components = comps;
9560
6fb70fb7
JS
9561 // fill out the available arguments in this tracepoint
9562 build_args(dw, func_die);
9563
9564 // determine which header defined this tracepoint
9565 string decl_file = dwarf_decl_file(&func_die);
9566 size_t header_pos = decl_file.rfind("trace/");
9567 if (header_pos == string::npos)
9568 throw semantic_error ("cannot parse header location for tracepoint '"
9569 + tracepoint_name + "' in '"
9570 + decl_file + "'");
9571 header = decl_file.substr(header_pos);
9572
9573 // tracepoints from FOO_event_types.h should really be included from FOO.h
9574 // XXX can dwarf tell us the include hierarchy? it would be better to
9575 // ... walk up to see which one was directly included by tracequery.c
9576 header_pos = header.find("_event_types");
9577 if (header_pos != string::npos)
9578 header.erase(header_pos, 12);
9579
f8a968bc
JS
9580 // Now expand the local variables in the probe body
9581 tracepoint_var_expanding_visitor v (dw, name, args);
9582 this->body = v.require (this->body);
9583
79189b84
JS
9584 if (sess.verbose > 2)
9585 clog << "tracepoint-based " << name << " tracepoint='" << tracepoint_name
9586 << "'" << endl;
9587}
9588
9589
6fb70fb7
JS
9590static bool
9591dwarf_type_name(Dwarf_Die& type_die, string& c_type)
9592{
9593 // if this die has a direct name, then we're done
9594 const char *diename = dwarf_diename_integrate(&type_die);
9595 if (diename != NULL)
9596 {
9597 switch (dwarf_tag(&type_die))
9598 {
9599 case DW_TAG_structure_type:
9600 c_type.append("struct ");
9601 break;
9602 case DW_TAG_union_type:
9603 c_type.append("union ");
9604 break;
9605 }
9606 c_type.append(diename);
9607 return true;
9608 }
9609
9610 // otherwise, this die is a type modifier.
9611
9612 // recurse into the referent type
9613 Dwarf_Attribute subtype_attr;
9614 Dwarf_Die subtype_die;
9615 if (!dwarf_attr_integrate(&type_die, DW_AT_type, &subtype_attr)
9616 || !dwarf_formref_die(&subtype_attr, &subtype_die)
9617 || !dwarf_type_name(subtype_die, c_type))
9618 return false;
9619
9620 const char *suffix = NULL;
9621 switch (dwarf_tag(&type_die))
9622 {
9623 case DW_TAG_pointer_type:
9624 suffix = "*";
9625 break;
9626 case DW_TAG_array_type:
9627 suffix = "[]";
9628 break;
9629 case DW_TAG_const_type:
9630 suffix = " const";
9631 break;
9632 case DW_TAG_volatile_type:
9633 suffix = " volatile";
9634 break;
9635 default:
9636 return false;
9637 }
9638 c_type.append(suffix);
9639 return true;
9640}
9641
9642
f8a968bc
JS
9643static bool
9644resolve_tracepoint_arg_type(Dwarf_Die& type_die, bool& isptr)
9645{
9646 Dwarf_Attribute type_attr;
9647 switch (dwarf_tag(&type_die))
9648 {
9649 case DW_TAG_typedef:
9650 case DW_TAG_const_type:
9651 case DW_TAG_volatile_type:
9652 // iterate on the referent type
9653 return (dwarf_attr_integrate(&type_die, DW_AT_type, &type_attr)
9654 && dwarf_formref_die(&type_attr, &type_die)
9655 && resolve_tracepoint_arg_type(type_die, isptr));
9656 case DW_TAG_base_type:
9657 // base types will simply be treated as script longs
9658 isptr = false;
9659 return true;
9660 case DW_TAG_pointer_type:
9661 // pointers can be either script longs,
9662 // or dereferenced with their referent type
9663 isptr = true;
9664 return (dwarf_attr_integrate(&type_die, DW_AT_type, &type_attr)
9665 && dwarf_formref_die(&type_attr, &type_die));
9666 default:
9667 // should we consider other types too?
9668 return false;
9669 }
9670}
9671
9672
6fb70fb7
JS
9673void
9674tracepoint_derived_probe::build_args(dwflpp& dw, Dwarf_Die& func_die)
9675{
9676 Dwarf_Die arg;
9677 if (dwarf_child(&func_die, &arg) == 0)
9678 do
9679 if (dwarf_tag(&arg) == DW_TAG_formal_parameter)
9680 {
9681 // build a tracepoint_arg for this parameter
9682 tracepoint_arg tparg;
9683 tparg.name = dwarf_diename_integrate(&arg);
9684
9685 // read the type of this parameter
9686 Dwarf_Attribute type_attr;
6fb70fb7 9687 if (!dwarf_attr_integrate (&arg, DW_AT_type, &type_attr)
f8a968bc
JS
9688 || !dwarf_formref_die (&type_attr, &tparg.type_die)
9689 || !dwarf_type_name(tparg.type_die, tparg.c_type)
9690 || !resolve_tracepoint_arg_type(tparg.type_die, tparg.isptr))
6fb70fb7
JS
9691 throw semantic_error ("cannot get type of tracepoint '"
9692 + tracepoint_name + "' parameter '"
9693 + tparg.name + "'");
9694
9695 args.push_back(tparg);
9696 if (sess.verbose > 4)
9697 clog << "found parameter for tracepoint '" << tracepoint_name
9698 << "': type:'" << tparg.c_type
9699 << "' name:'" << tparg.name << "'" << endl;
9700 }
9701 while (dwarf_siblingof(&arg, &arg) == 0);
9702}
9703
e2086848
WH
9704void
9705tracepoint_derived_probe::printargs(std::ostream &o) const
9706{
9707 for (unsigned i = 0; i < args.size(); ++i)
9708 o << " $" << args[i].name << ":" << args[i].c_type;
9709}
6fb70fb7 9710
79189b84
JS
9711void
9712tracepoint_derived_probe::join_group (systemtap_session& s)
9713{
9714 if (! s.tracepoint_derived_probes)
9715 s.tracepoint_derived_probes = new tracepoint_derived_probe_group ();
9716 s.tracepoint_derived_probes->enroll (this);
9717}
9718
9719
f8a968bc
JS
9720void
9721tracepoint_derived_probe::emit_probe_context_vars (translator_output* o)
9722{
9723 for (unsigned i = 0; i < args.size(); i++)
9724 if (args[i].used)
9725 o->newline() << "int64_t __tracepoint_arg_" << args[i].name << ";";
9726}
9727
9728
79189b84
JS
9729void
9730tracepoint_derived_probe_group::emit_module_decls (systemtap_session& s)
9731{
9732 if (probes.empty())
9733 return;
9734
9735 s.op->newline() << "/* ---- tracepointer probes ---- */";
9736
6fb70fb7
JS
9737 for (unsigned i = 0; i < probes.size(); ++i)
9738 {
9739 tracepoint_derived_probe *p = probes[i];
9740 s.op->newline();
9741 s.op->newline() << "#include <" << p->header << ">";
9742 s.op->newline() << "static void enter_tracepoint_probe_" << i << "(";
9743 for (unsigned j = 0; j < p->args.size(); ++j)
9744 {
9745 if (j > 0)
9746 s.op->line() << ", ";
9747 s.op->line() << p->args[j].c_type << " __tracepoint_arg_" << p->args[j].name;
9748 }
9749 s.op->line() << ") {";
9750 s.op->indent(1);
c12d974f
FCE
9751 common_probe_entryfn_prologue (s.op, "STAP_SESSION_RUNNING",
9752 lex_cast_qstring (*p->sole_location()));
f8a968bc 9753 s.op->newline() << "c->marker_name = "
c12d974f
FCE
9754 << lex_cast_qstring (p->tracepoint_name)
9755 << ";";
f8a968bc
JS
9756 for (unsigned j = 0; j < p->args.size(); ++j)
9757 if (p->args[j].used)
9758 {
9759 s.op->newline() << "c->locals[0]." << p->name << ".__tracepoint_arg_"
9760 << p->args[j].name << " = (int64_t)";
9761 if (p->args[j].isptr)
9762 s.op->line() << "(intptr_t)";
9763 s.op->line() << "__tracepoint_arg_" << p->args[j].name << ";";
9764 }
6fb70fb7
JS
9765 s.op->newline() << p->name << " (c);";
9766 common_probe_entryfn_epilogue (s.op);
9767 s.op->newline(-1) << "}";
9768 s.op->newline();
9769 }
79189b84
JS
9770}
9771
9772
9773void
9774tracepoint_derived_probe_group::emit_module_init (systemtap_session &s)
9775{
9776 if (probes.size () == 0)
9777 return;
9778
9779 s.op->newline() << "/* init tracepoint probes */";
9780
6fb70fb7
JS
9781 // We can't use a simple runtime loop because the probe registration
9782 // functions are distinct inlines. Instead, this will generate nesting as
9783 // deep as the number of probe points. Gotos are also possible, but the end
9784 // result is the same.
9785
9786 for (unsigned i = 0; i < probes.size(); ++i)
9787 {
9788 s.op->newline() << "if (!rc) {";
9789 s.op->newline(1) << "probe_point = "
9790 << lex_cast_qstring (*probes[i]->sole_location()) << ";";
9791 s.op->newline() << "rc = register_trace_" << probes[i]->tracepoint_name
9792 << "(enter_tracepoint_probe_" << i << ");";
9793 }
9794
9795 for (unsigned i = probes.size() - 1; i < probes.size(); --i)
9796 {
9797 s.op->newline() << "if (rc)";
9798 s.op->newline(1) << "unregister_trace_" << probes[i]->tracepoint_name
9799 << "(enter_tracepoint_probe_" << i << ");";
9800 s.op->newline(-2) << "}";
9801 }
bc9a523d
FCE
9802
9803 // This would be technically proper (on those autoconf-detectable
9804 // kernels that include this function in tracepoint.h), however we
9805 // already make several calls to synchronze_sched() during our
9806 // shutdown processes.
9807
9808 // s.op->newline() << "if (rc)";
9809 // s.op->newline(1) << "tracepoint_synchronize_unregister();";
9810 // s.op->indent(-1);
79189b84
JS
9811}
9812
9813
9814void
9815tracepoint_derived_probe_group::emit_module_exit (systemtap_session& s)
9816{
9817 if (probes.empty())
9818 return;
9819
9820 s.op->newline() << "/* deregister tracepointer probes */";
6fb70fb7
JS
9821 for (unsigned i = 0; i < probes.size(); ++i)
9822 s.op->newline() << "unregister_trace_" << probes[i]->tracepoint_name
9823 << "(enter_tracepoint_probe_" << i << ");";
bc9a523d
FCE
9824
9825 // Not necessary: see above.
9826
9827 // s.op->newline() << "tracepoint_synchronize_unregister();";
79189b84
JS
9828}
9829
9830
75ead1f7
JS
9831struct tracepoint_query : public base_query
9832{
9833 tracepoint_query(dwflpp & dw, const string & tracepoint,
9834 probe * base_probe, probe_point * base_loc,
9835 vector<derived_probe *> & results):
9836 base_query(dw, "*"), tracepoint(tracepoint),
9837 base_probe(base_probe), base_loc(base_loc),
9838 results(results) {}
9839
9840 const string& tracepoint;
9841
9842 probe * base_probe;
9843 probe_point * base_loc;
9844 vector<derived_probe *> & results;
9845
9846 void handle_query_module();
9847 int handle_query_cu(Dwarf_Die * cudie);
9848 int handle_query_func(Dwarf_Die * func);
9849
9850 static int tracepoint_query_cu (Dwarf_Die * cudie, void * arg);
9851 static int tracepoint_query_func (Dwarf_Die * func, base_query * query);
9852};
9853
9854
9855void
9856tracepoint_query::handle_query_module()
9857{
9858 // look for the tracepoints in each CU
9859 dw.iterate_over_cus(tracepoint_query_cu, this);
9860}
9861
9862
9863int
9864tracepoint_query::handle_query_cu(Dwarf_Die * cudie)
9865{
9866 dw.focus_on_cu (cudie);
9867
9868 // look at each function to see if it's a tracepoint
9869 string function = "stapprobe_" + tracepoint;
9870 return dw.iterate_over_functions (tracepoint_query_func, this, function);
9871}
9872
9873
9874int
9875tracepoint_query::handle_query_func(Dwarf_Die * func)
9876{
9877 dw.focus_on_function (func);
9878
9879 assert(dw.function_name.compare(0, 10, "stapprobe_") == 0);
9880 string tracepoint_instance = dw.function_name.substr(10);
79189b84
JS
9881 derived_probe *dp = new tracepoint_derived_probe (dw.sess, dw, *func,
9882 tracepoint_instance,
9883 base_probe, base_loc);
9884 results.push_back (dp);
75ead1f7
JS
9885 return DWARF_CB_OK;
9886}
9887
9888
9889int
9890tracepoint_query::tracepoint_query_cu (Dwarf_Die * cudie, void * arg)
9891{
9892 tracepoint_query * q = static_cast<tracepoint_query *>(arg);
9893 if (pending_interrupts) return DWARF_CB_ABORT;
9894 return q->handle_query_cu(cudie);
9895}
9896
9897
9898int
9899tracepoint_query::tracepoint_query_func (Dwarf_Die * func, base_query * query)
9900{
9901 tracepoint_query * q = static_cast<tracepoint_query *>(query);
9902 if (pending_interrupts) return DWARF_CB_ABORT;
9903 return q->handle_query_func(func);
9904}
9905
9906
0a6f5a3f
JS
9907struct tracepoint_builder: public derived_probe_builder
9908{
9909private:
9910 dwflpp *dw;
9911 bool init_dw(systemtap_session& s);
9912
9913public:
9914 tracepoint_builder(): dw(0) {}
9915 ~tracepoint_builder() { delete dw; }
9916
9917 void build_no_more (systemtap_session& s)
9918 {
9919 if (dw && s.verbose > 3)
9920 clog << "tracepoint_builder releasing dwflpp" << endl;
9921 delete dw;
9922 dw = NULL;
9923 }
9924
9925 void build(systemtap_session& s,
9926 probe *base, probe_point *location,
9927 literal_map_t const& parameters,
9928 vector<derived_probe*>& finished_results);
9929};
9930
9931
9932bool
9933tracepoint_builder::init_dw(systemtap_session& s)
9934{
9935 if (dw != NULL)
9936 return true;
9937
9938 string tracequery_ko;
9939 int rc = make_tracequery(s, tracequery_ko);
9940 if (rc != 0)
9941 return false;
9942
9943 // TODO cache tracequery.ko
9944
9945 dw = new dwflpp(s);
9946 dw->setup_user(tracequery_ko);
9947 return true;
9948}
9949
9950
9951void
9952tracepoint_builder::build(systemtap_session& s,
9953 probe *base, probe_point *location,
9954 literal_map_t const& parameters,
9955 vector<derived_probe*>& finished_results)
9956{
9957 if (!init_dw(s))
9958 return;
9959
75ead1f7
JS
9960 string tracepoint;
9961 assert(get_param (parameters, TOK_TRACE, tracepoint));
9962
9963 tracepoint_query q(*dw, tracepoint, base, location, finished_results);
9964 dw->query_modules(&q);
0a6f5a3f
JS
9965}
9966
9967
9968
56894e91
JS
9969// ------------------------------------------------------------------------
9970// hrtimer derived probes
9971// ------------------------------------------------------------------------
9972// This is a new timer interface that provides more flexibility in specifying
9973// intervals, and uses the hrtimer APIs when available for greater precision.
39014506
JS
9974// While hrtimers were added in 2.6.16, the API's weren't exported until
9975// 2.6.17, so we must check this kernel version before attempting to use
9976// hrtimers.
56894e91 9977//
56894e91 9978// * hrtimer_derived_probe: creates a probe point based on the hrtimer APIs.
56894e91
JS
9979
9980
9981struct hrtimer_derived_probe: public derived_probe
9982{
9983 // set a (generous) maximum of one day in ns
9984 static const int64_t max_ns_interval = 1000000000LL * 60LL * 60LL * 24LL;
9985
9986 // 100us seems like a reasonable minimum
9987 static const int64_t min_ns_interval = 100000LL;
9988
9989 int64_t interval, randomize;
9990
9991 hrtimer_derived_probe (probe* p, probe_point* l, int64_t i, int64_t r):
9992 derived_probe (p, l), interval (i), randomize (r)
9993 {
9994 if ((i < min_ns_interval) || (i > max_ns_interval))
9995 throw semantic_error("interval value out of range");
9996
9997 // randomize = 0 means no randomization
9998 if ((r < 0) || (r > i))
9999 throw semantic_error("randomization value out of range");
56894e91
JS
10000 }
10001
b20febf3
FCE
10002 void join_group (systemtap_session& s);
10003};
dc38c0ae 10004
56894e91 10005
b20febf3
FCE
10006struct hrtimer_derived_probe_group: public generic_dpg<hrtimer_derived_probe>
10007{
10008 void emit_interval (translator_output* o);
10009public:
10010 void emit_module_decls (systemtap_session& s);
10011 void emit_module_init (systemtap_session& s);
10012 void emit_module_exit (systemtap_session& s);
56894e91
JS
10013};
10014
10015
dc38c0ae 10016void
b20febf3 10017hrtimer_derived_probe::join_group (systemtap_session& s)
dc38c0ae 10018{
b20febf3
FCE
10019 if (! s.hrtimer_derived_probes)
10020 s.hrtimer_derived_probes = new hrtimer_derived_probe_group ();
10021 s.hrtimer_derived_probes->enroll (this);
dc38c0ae
DS
10022}
10023
10024
56894e91 10025void
b20febf3 10026hrtimer_derived_probe_group::emit_interval (translator_output* o)
56894e91
JS
10027{
10028 o->line() << "({";
ffb0b3ad 10029 o->newline(1) << "unsigned long nsecs;";
b20febf3
FCE
10030 o->newline() << "int64_t i = stp->intrv;";
10031 o->newline() << "if (stp->rnd != 0) {";
10032 // XXX: why not use stp_random_pm instead of this?
10033 o->newline(1) << "int64_t r;";
10034 o->newline() << "get_random_bytes(&r, sizeof(r));";
10035 // ensure that r is positive
10036 o->newline() << "r &= ((uint64_t)1 << (8*sizeof(r) - 1)) - 1;";
10037 o->newline() << "r = _stp_mod64(NULL, r, (2*stp->rnd+1));";
10038 o->newline() << "r -= stp->rnd;";
10039 o->newline() << "i += r;";
10040 o->newline(-1) << "}";
10041 o->newline() << "if (unlikely(i < stap_hrtimer_resolution))";
10042 o->newline(1) << "i = stap_hrtimer_resolution;";
197a4d62 10043 o->indent(-1);
ffb0b3ad
JS
10044 o->newline() << "nsecs = do_div(i, NSEC_PER_SEC);";
10045 o->newline() << "ktime_set(i, nsecs);";
56894e91
JS
10046 o->newline(-1) << "})";
10047}
10048
10049
10050void
b20febf3 10051hrtimer_derived_probe_group::emit_module_decls (systemtap_session& s)
46b84a80 10052{
b20febf3 10053 if (probes.empty()) return;
46b84a80 10054
b20febf3 10055 s.op->newline() << "/* ---- hrtimer probes ---- */";
46b84a80 10056
4c2732a1
JS
10057 s.op->newline() << "static unsigned long stap_hrtimer_resolution;"; // init later
10058 s.op->newline() << "static struct stap_hrtimer_probe {";
b20febf3
FCE
10059 s.op->newline(1) << "struct hrtimer hrtimer;";
10060 s.op->newline() << "const char *pp;";
10061 s.op->newline() << "void (*ph) (struct context*);";
10062 s.op->newline() << "int64_t intrv, rnd;";
10063 s.op->newline(-1) << "} stap_hrtimer_probes [" << probes.size() << "] = {";
10064 s.op->indent(1);
10065 for (unsigned i=0; i < probes.size(); i++)
10066 {
4baf0e53 10067 s.op->newline () << "{";
b20febf3
FCE
10068 s.op->line() << " .pp=" << lex_cast_qstring (*probes[i]->sole_location()) << ",";
10069 s.op->line() << " .ph=&" << probes[i]->name << ",";
10070 s.op->line() << " .intrv=" << probes[i]->interval << "LL,";
10071 s.op->line() << " .rnd=" << probes[i]->randomize << "LL";
10072 s.op->line() << " },";
10073 }
10074 s.op->newline(-1) << "};";
10075 s.op->newline();
10076
d9d9f852
JS
10077 // autoconf: add get/set expires if missing (pre 2.6.28-rc1)
10078 s.op->newline() << "#ifndef STAPCONF_HRTIMER_GETSET_EXPIRES";
10079 s.op->newline() << "#define hrtimer_get_expires(timer) ((timer)->expires)";
10080 s.op->newline() << "#define hrtimer_set_expires(timer, time) (void)((timer)->expires = (time))";
10081 s.op->newline() << "#endif";
10082
255e4c68
FCE
10083 // autoconf: adapt to HRTIMER_REL -> HRTIMER_MODE_REL renaming near 2.6.21
10084 s.op->newline() << "#ifdef STAPCONF_HRTIMER_REL";
10085 s.op->newline() << "#define HRTIMER_MODE_REL HRTIMER_REL";
10086 s.op->newline() << "#endif";
4baf0e53 10087
5dbd55d7 10088 // The function signature changed in 2.6.21.
255e4c68
FCE
10089 s.op->newline() << "#ifdef STAPCONF_HRTIMER_REL";
10090 s.op->newline() << "static int ";
10091 s.op->newline() << "#else";
10092 s.op->newline() << "static enum hrtimer_restart ";
10093 s.op->newline() << "#endif";
10094 s.op->newline() << "enter_hrtimer_probe (struct hrtimer *timer) {";
5dbd55d7 10095
4baf0e53 10096 s.op->newline(1) << "int rc = HRTIMER_NORESTART;";
e0d86324
JS
10097 s.op->newline() << "struct stap_hrtimer_probe *stp = container_of(timer, struct stap_hrtimer_probe, hrtimer);";
10098 s.op->newline() << "if ((atomic_read (&session_state) == STAP_SESSION_STARTING) ||";
10099 s.op->newline() << " (atomic_read (&session_state) == STAP_SESSION_RUNNING)) {";
b20febf3 10100 // Compute next trigger time
d9d9f852 10101 s.op->newline(1) << "hrtimer_set_expires(timer, ktime_add (hrtimer_get_expires(timer),";
b20febf3 10102 emit_interval (s.op);
f7674e54 10103 s.op->line() << "));";
d9d9f852 10104 s.op->newline() << "rc = HRTIMER_RESTART;";
e0d86324
JS
10105 s.op->newline(-1) << "}";
10106 s.op->newline() << "{";
10107 s.op->indent(1);
c12d974f 10108 common_probe_entryfn_prologue (s.op, "STAP_SESSION_RUNNING", "stp->pp");
b20febf3
FCE
10109 s.op->newline() << "(*stp->ph) (c);";
10110 common_probe_entryfn_epilogue (s.op);
e0d86324
JS
10111 s.op->newline(-1) << "}";
10112 s.op->newline() << "return rc;";
b20febf3 10113 s.op->newline(-1) << "}";
56894e91
JS
10114}
10115
10116
10117void
b20febf3 10118hrtimer_derived_probe_group::emit_module_init (systemtap_session& s)
56894e91 10119{
b20febf3 10120 if (probes.empty()) return;
56894e91 10121
b20febf3
FCE
10122 s.op->newline() << "{";
10123 s.op->newline(1) << "struct timespec res;";
10124 s.op->newline() << "hrtimer_get_res (CLOCK_MONOTONIC, &res);";
10125 s.op->newline() << "stap_hrtimer_resolution = timespec_to_ns (&res);";
10126 s.op->newline(-1) << "}";
a68f81a2 10127
b20febf3
FCE
10128 s.op->newline() << "for (i=0; i<" << probes.size() << "; i++) {";
10129 s.op->newline(1) << "struct stap_hrtimer_probe* stp = & stap_hrtimer_probes [i];";
6f313a73 10130 s.op->newline() << "probe_point = stp->pp;";
255e4c68 10131 s.op->newline() << "hrtimer_init (& stp->hrtimer, CLOCK_MONOTONIC, HRTIMER_MODE_REL);";
b20febf3
FCE
10132 s.op->newline() << "stp->hrtimer.function = & enter_hrtimer_probe;";
10133 // There is no hrtimer field to identify *this* (i-th) probe handler
10134 // callback. So instead we'll deduce it at entry time.
10135 s.op->newline() << "(void) hrtimer_start (& stp->hrtimer, ";
10136 emit_interval (s.op);
255e4c68 10137 s.op->line() << ", HRTIMER_MODE_REL);";
b20febf3
FCE
10138 // Note: no partial failure rollback is needed: hrtimer_start only
10139 // "fails" if the timer was already active, which cannot be.
10140 s.op->newline(-1) << "}"; // for loop
56894e91
JS
10141}
10142
10143
dc38c0ae 10144void
b20febf3 10145hrtimer_derived_probe_group::emit_module_exit (systemtap_session& s)
dc38c0ae 10146{
b20febf3 10147 if (probes.empty()) return;
197a4d62 10148
b20febf3
FCE
10149 s.op->newline() << "for (i=0; i<" << probes.size() << "; i++)";
10150 s.op->newline(1) << "hrtimer_cancel (& stap_hrtimer_probes[i].hrtimer);";
10151 s.op->indent(-1);
dc38c0ae
DS
10152}
10153
10154
56894e91 10155
197a4d62
JS
10156struct timer_builder: public derived_probe_builder
10157{
10158 virtual void build(systemtap_session & sess,
10159 probe * base, probe_point * location,
86bf665e 10160 literal_map_t const & parameters,
197a4d62 10161 vector<derived_probe *> & finished_results);
e38d6504 10162
c4ce66a1 10163 static void register_patterns(systemtap_session& s);
56894e91
JS
10164};
10165
197a4d62
JS
10166void
10167timer_builder::build(systemtap_session & sess,
10168 probe * base,
10169 probe_point * location,
86bf665e 10170 literal_map_t const & parameters,
197a4d62 10171 vector<derived_probe *> & finished_results)
56894e91 10172{
197a4d62 10173 int64_t period, rand=0;
56894e91 10174
197a4d62
JS
10175 if (!get_param(parameters, "randomize", rand))
10176 rand = 0;
56894e91 10177
197a4d62 10178 if (get_param(parameters, "jiffies", period))
56894e91 10179 {
197a4d62
JS
10180 // always use basic timers for jiffies
10181 finished_results.push_back(
10182 new timer_derived_probe(base, location, period, rand, false));
10183 return;
56894e91 10184 }
197a4d62 10185 else if (get_param(parameters, "hz", period))
56894e91 10186 {
197a4d62
JS
10187 if (period <= 0)
10188 throw semantic_error ("frequency must be greater than 0");
10189 period = (1000000000 + period - 1)/period;
10190 }
10191 else if (get_param(parameters, "s", period)
10192 || get_param(parameters, "sec", period))
10193 {
10194 period *= 1000000000;
10195 rand *= 1000000000;
10196 }
10197 else if (get_param(parameters, "ms", period)
10198 || get_param(parameters, "msec", period))
10199 {
10200 period *= 1000000;
10201 rand *= 1000000;
10202 }
10203 else if (get_param(parameters, "us", period)
10204 || get_param(parameters, "usec", period))
10205 {
10206 period *= 1000;
10207 rand *= 1000;
10208 }
10209 else if (get_param(parameters, "ns", period)
10210 || get_param(parameters, "nsec", period))
10211 {
10212 // ok
10213 }
10214 else
10215 throw semantic_error ("unrecognized timer variant");
56894e91 10216
b20febf3
FCE
10217 // Redirect wallclock-time based probes to hrtimer code on recent
10218 // enough kernels.
197a4d62
JS
10219 if (strverscmp(sess.kernel_base_release.c_str(), "2.6.17") < 0)
10220 {
10221 // hrtimers didn't exist, so use the old-school timers
10222 period = (period + 1000000 - 1)/1000000;
10223 rand = (rand + 1000000 - 1)/1000000;
56894e91 10224
197a4d62
JS
10225 finished_results.push_back(
10226 new timer_derived_probe(base, location, period, rand, true));
10227 }
10228 else
10229 finished_results.push_back(
10230 new hrtimer_derived_probe(base, location, period, rand));
10231}
56894e91 10232
197a4d62 10233void
c4ce66a1 10234timer_builder::register_patterns(systemtap_session& s)
197a4d62 10235{
c4ce66a1 10236 match_node* root = s.pattern_root;
197a4d62 10237 derived_probe_builder *builder = new timer_builder();
56894e91 10238
12b21830 10239 root = root->bind(TOK_TIMER);
56894e91 10240
197a4d62
JS
10241 root->bind_num("s")->bind(builder);
10242 root->bind_num("s")->bind_num("randomize")->bind(builder);
10243 root->bind_num("sec")->bind(builder);
10244 root->bind_num("sec")->bind_num("randomize")->bind(builder);
56894e91 10245
197a4d62
JS
10246 root->bind_num("ms")->bind(builder);
10247 root->bind_num("ms")->bind_num("randomize")->bind(builder);
10248 root->bind_num("msec")->bind(builder);
10249 root->bind_num("msec")->bind_num("randomize")->bind(builder);
56894e91 10250
197a4d62
JS
10251 root->bind_num("us")->bind(builder);
10252 root->bind_num("us")->bind_num("randomize")->bind(builder);
10253 root->bind_num("usec")->bind(builder);
10254 root->bind_num("usec")->bind_num("randomize")->bind(builder);
56894e91 10255
197a4d62
JS
10256 root->bind_num("ns")->bind(builder);
10257 root->bind_num("ns")->bind_num("randomize")->bind(builder);
10258 root->bind_num("nsec")->bind(builder);
10259 root->bind_num("nsec")->bind_num("randomize")->bind(builder);
56894e91 10260
197a4d62
JS
10261 root->bind_num("jiffies")->bind(builder);
10262 root->bind_num("jiffies")->bind_num("randomize")->bind(builder);
4baf0e53 10263
197a4d62 10264 root->bind_num("hz")->bind(builder);
56894e91
JS
10265}
10266
10267
342d3f96 10268
47dd066d
WC
10269// ------------------------------------------------------------------------
10270// perfmon derived probes
10271// ------------------------------------------------------------------------
10272// This is a new interface to the perfmon hw.
10273//
10274
10275
de688825 10276struct perfmon_var_expanding_visitor: public var_expanding_visitor
47dd066d
WC
10277{
10278 systemtap_session & sess;
10279 unsigned counter_number;
de688825 10280 perfmon_var_expanding_visitor(systemtap_session & s, unsigned c):
47dd066d
WC
10281 sess(s), counter_number(c) {}
10282 void visit_target_symbol (target_symbol* e);
10283};
10284
10285
10286void
de688825 10287perfmon_var_expanding_visitor::visit_target_symbol (target_symbol *e)
47dd066d
WC
10288{
10289 assert(e->base_name.size() > 0 && e->base_name[0] == '$');
10290
10291 // Synthesize a function.
10292 functiondecl *fdecl = new functiondecl;
10293 fdecl->tok = e->tok;
10294 embeddedcode *ec = new embeddedcode;
10295 ec->tok = e->tok;
10296 bool lvalue = is_active_lvalue(e);
10297
10298 if (lvalue )
10299 throw semantic_error("writes to $counter not permitted");
10300
10301 string fname = string("_perfmon_tvar_get")
10302 + "_" + e->base_name.substr(1)
10303 + "_" + lex_cast<string>(counter_number);
10304
10305 if (e->base_name != "$counter")
10306 throw semantic_error ("target variables not available to perfmon probes");
10307
af304783
DS
10308 if (e->components.size() > 0)
10309 {
10310 switch (e->components[0].first)
10311 {
10312 case target_symbol::comp_literal_array_index:
10313 throw semantic_error("perfmon probe '$counter' variable may not be used as array",
10314 e->tok);
10315 break;
10316 case target_symbol::comp_struct_member:
10317 throw semantic_error("perfmon probe '$counter' variable may not be used as a structure",
10318 e->tok);
10319 break;
10320 default:
10321 throw semantic_error ("invalid use of perfmon probe '$counter' variable",
10322 e->tok);
10323 break;
10324 }
10325 }
10326
4baf0e53 10327 ec->code = "THIS->__retvalue = _pfm_pmd_x[" +
47dd066d
WC
10328 lex_cast<string>(counter_number) + "].reg_num;";
10329 ec->code += "/* pure */";
10330 fdecl->name = fname;
10331 fdecl->body = ec;
10332 fdecl->type = pe_long;
f76427a2 10333 sess.functions[fdecl->name]=fdecl;
47dd066d
WC
10334
10335 // Synthesize a functioncall.
10336 functioncall* n = new functioncall;
10337 n->tok = e->tok;
10338 n->function = fname;
10339 n->referent = 0; // NB: must not resolve yet, to ensure inclusion in session
10340
4ed05b15 10341 provide (n);
47dd066d
WC
10342}
10343
10344
10345enum perfmon_mode
10346{
10347 perfmon_count,
10348 perfmon_sample
10349};
10350
10351
10352struct perfmon_derived_probe: public derived_probe
10353{
10354protected:
10355 static unsigned probes_allocated;
10356
10357public:
10358 systemtap_session & sess;
10359 string event;
10360 perfmon_mode mode;
10361
10362 perfmon_derived_probe (probe* p, probe_point* l, systemtap_session &s,
10363 string e, perfmon_mode m);
b20febf3 10364 virtual void join_group (systemtap_session& s);
47dd066d
WC
10365};
10366
10367
b20febf3 10368struct perfmon_derived_probe_group: public generic_dpg<perfmon_derived_probe>
47dd066d 10369{
47dd066d 10370public:
78f6bba6
FCE
10371 void emit_module_decls (systemtap_session&) {}
10372 void emit_module_init (systemtap_session&) {}
10373 void emit_module_exit (systemtap_session&) {}
47dd066d
WC
10374};
10375
10376
10377struct perfmon_builder: public derived_probe_builder
10378{
10379 perfmon_builder() {}
10380 virtual void build(systemtap_session & sess,
10381 probe * base,
10382 probe_point * location,
86bf665e 10383 literal_map_t const & parameters,
47dd066d
WC
10384 vector<derived_probe *> & finished_results)
10385 {
10386 string event;
10387 if (!get_param (parameters, "counter", event))
10388 throw semantic_error("perfmon requires an event");
10389
10390 sess.perfmon++;
10391
4baf0e53 10392 // XXX: need to revise when doing sampling
47dd066d
WC
10393 finished_results.push_back(new perfmon_derived_probe(base, location,
10394 sess, event,
10395 perfmon_count));
10396 }
10397};
10398
b20febf3 10399
47dd066d
WC
10400unsigned perfmon_derived_probe::probes_allocated;
10401
10402perfmon_derived_probe::perfmon_derived_probe (probe* p, probe_point* l,
10403 systemtap_session &s,
10404 string e, perfmon_mode m)
10405 : derived_probe (p, l), sess(s), event(e), mode(m)
10406{
10407 ++probes_allocated;
10408
de688825
JS
10409 // Now expand the local variables in the probe body
10410 perfmon_var_expanding_visitor v (sess, probes_allocated-1);
10411 this->body = v.require (this->body);
47dd066d
WC
10412
10413 if (sess.verbose > 1)
10414 clog << "perfmon-based probe" << endl;
10415}
10416
10417
10418void
b20febf3 10419perfmon_derived_probe::join_group (systemtap_session& s)
47dd066d 10420{
b20febf3
FCE
10421 throw semantic_error ("incomplete", this->tok);
10422
10423 if (! s.perfmon_derived_probes)
10424 s.perfmon_derived_probes = new perfmon_derived_probe_group ();
10425 s.perfmon_derived_probes->enroll (this);
47dd066d
WC
10426}
10427
10428
b20febf3 10429#if 0
47dd066d
WC
10430void
10431perfmon_derived_probe::emit_registrations_start (translator_output* o,
10432 unsigned index)
10433{
10434 for (unsigned i=0; i<locations.size(); i++)
10435 o->newline() << "enter_" << name << "_" << i << " ();";
10436}
10437
10438
10439void
10440perfmon_derived_probe::emit_registrations_end (translator_output * o,
10441 unsigned index)
10442{
10443}
10444
10445
10446void
10447perfmon_derived_probe::emit_deregistrations (translator_output * o)
10448{
10449}
10450
10451
10452void
10453perfmon_derived_probe::emit_probe_entries (translator_output * o)
10454{
10455 o->newline() << "#ifdef STP_TIMING";
dbb68664 10456 // NB: This variable may be multiply (but identically) defined.
47dd066d
WC
10457 o->newline() << "static __cacheline_aligned Stat " << "time_" << basest()->name << ";";
10458 o->newline() << "#endif";
10459
10460 for (unsigned i=0; i<locations.size(); i++)
10461 {
10462 probe_point *l = locations[i];
10463 o->newline() << "/* location " << i << ": " << *l << " */";
10464 o->newline() << "static void enter_" << name << "_" << i << " (void) {";
10465
10466 o->indent(1);
10467 o->newline() << "const char* probe_point = "
10468 << lex_cast_qstring(*l) << ";";
10469 emit_probe_prologue (o,
10470 (mode == perfmon_count ?
10471 "STAP_SESSION_STARTING" :
c12d974f
FCE
10472 "STAP_SESSION_RUNNING"),
10473 "probe_point");
47dd066d
WC
10474
10475 // NB: locals are initialized by probe function itself
10476 o->newline() << name << " (c);";
10477
10478 emit_probe_epilogue (o);
10479
10480 o->newline(-1) << "}\n";
10481 }
10482}
b20febf3 10483#endif
47dd066d
WC
10484
10485
b20febf3 10486#if 0
47dd066d
WC
10487void no_pfm_event_error (string s)
10488{
10489 string msg(string("Cannot find event:" + s));
10490 throw semantic_error(msg);
10491}
10492
10493
10494void no_pfm_mask_error (string s)
10495{
10496 string msg(string("Cannot find mask:" + s));
10497 throw semantic_error(msg);
10498}
10499
10500
10501void
10502split(const string& s, vector<string>& v, const string & separator)
10503{
10504 string::size_type last_pos = s.find_first_not_of(separator, 0);
10505 string::size_type pos = s.find_first_of(separator, last_pos);
10506
10507 while (string::npos != pos || string::npos != last_pos) {
10508 v.push_back(s.substr(last_pos, pos - last_pos));
10509 last_pos = s.find_first_not_of(separator, pos);
10510 pos = s.find_first_of(separator, last_pos);
10511 }
10512}
10513
10514
10515void
10516perfmon_derived_probe_group::emit_probes (translator_output* op, unparser* up)
10517{
10518 for (unsigned i=0; i < probes.size(); i++)
10519 {
10520 op->newline ();
10521 up->emit_probe (probes[i]);
10522 }
10523}
10524
10525
10526void
10527perfmon_derived_probe_group::emit_module_init (translator_output* o)
10528{
10529 int ret;
10530 pfmlib_input_param_t inp;
10531 pfmlib_output_param_t outp;
10532 pfarg_pmd_t pd[PFMLIB_MAX_PMDS];
10533 pfarg_pmc_t pc[PFMLIB_MAX_PMCS];
10534 pfarg_ctx_t ctx;
10535 pfarg_load_t load_args;
10536 pfmlib_options_t pfmlib_options;
10537 unsigned int max_counters;
10538
10539 if ( probes.size() == 0)
10540 return;
10541 ret = pfm_initialize();
10542 if (ret != PFMLIB_SUCCESS)
10543 throw semantic_error("Unable to generate performance monitoring events (no libpfm)");
10544
10545 pfm_get_num_counters(&max_counters);
10546
10547 memset(&pfmlib_options, 0, sizeof(pfmlib_options));
10548 pfmlib_options.pfm_debug = 0; /* set to 1 for debug */
10549 pfmlib_options.pfm_verbose = 0; /* set to 1 for debug */
10550 pfm_set_options(&pfmlib_options);
10551
10552 memset(pd, 0, sizeof(pd));
10553 memset(pc, 0, sizeof(pc));
10554 memset(&ctx, 0, sizeof(ctx));
10555 memset(&load_args, 0, sizeof(load_args));
10556
10557 /*
10558 * prepare parameters to library.
10559 */
10560 memset(&inp,0, sizeof(inp));
10561 memset(&outp,0, sizeof(outp));
10562
10563 /* figure out the events */
10564 for (unsigned i=0; i<probes.size(); ++i)
10565 {
10566 if (probes[i]->event == "cycles") {
10567 if (pfm_get_cycle_event( &inp.pfp_events[i].event) != PFMLIB_SUCCESS)
10568 no_pfm_event_error(probes[i]->event);
10569 } else if (probes[i]->event == "instructions") {
10570 if (pfm_get_inst_retired_event( &inp.pfp_events[i].event) !=
10571 PFMLIB_SUCCESS)
10572 no_pfm_event_error(probes[i]->event);
10573 } else {
10574 unsigned int event_id = 0;
10575 unsigned int mask_id = 0;
10576 vector<string> event_spec;
10577 split(probes[i]->event, event_spec, ":");
10578 int num = event_spec.size();
10579 int masks = num - 1;
10580
10581 if (num == 0)
10582 throw semantic_error("No events found");
10583
10584 /* setup event */
10585 if (pfm_find_event(event_spec[0].c_str(), &event_id) != PFMLIB_SUCCESS)
10586 no_pfm_event_error(event_spec[0]);
10587 inp.pfp_events[i].event = event_id;
10588
10589 /* set up masks */
10590 if (masks > PFMLIB_MAX_MASKS_PER_EVENT)
10591 throw semantic_error("Too many unit masks specified");
10592
10593 for (int j=0; j < masks; j++) {
10594 if (pfm_find_event_mask(event_id, event_spec[j+1].c_str(),
10595 &mask_id) != PFMLIB_SUCCESS)
10596 no_pfm_mask_error(string(event_spec[j+1]));
10597 inp.pfp_events[i].unit_masks[j] = mask_id;
10598 }
10599 inp.pfp_events[i].num_masks = masks;
10600 }
10601 }
10602
10603 /* number of counters in use */
10604 inp.pfp_event_count = probes.size();
10605
10606 // XXX: no elimination of duplicated counters
10607 if (inp.pfp_event_count>max_counters)
10608 throw semantic_error("Too many performance monitoring events.");
10609
10610 /* count events both in kernel and user-space */
10611 inp.pfp_dfl_plm = PFM_PLM0 | PFM_PLM3;
10612
4baf0e53 10613 /* XXX: some cases a perfmon register might be used of watch dog
47dd066d
WC
10614 this code doesn't handle that case */
10615
10616 /* figure out the pmcs for the events */
10617 if ((ret=pfm_dispatch_events(&inp, NULL, &outp, NULL)) != PFMLIB_SUCCESS)
10618 throw semantic_error("Cannot configure events");
10619
10620 for (unsigned i=0; i < outp.pfp_pmc_count; i++) {
10621 pc[i].reg_num = outp.pfp_pmcs[i].reg_num;
10622 pc[i].reg_value = outp.pfp_pmcs[i].reg_value;
10623 }
10624
10625 /*
10626 * There could be more pmc settings than pmd.
10627 * Figure out the actual pmds to use.
10628 */
10629 for (unsigned i=0, j=0; i < inp.pfp_event_count; i++) {
10630 pd[i].reg_num = outp.pfp_pmcs[j].reg_pmd_num;
10631 for(; j < outp.pfp_pmc_count; j++)
10632 if (outp.pfp_pmcs[j].reg_evt_idx != i) break;
10633 }
10634
10635 // Output the be probes create function
10636 o->newline() << "static int register_perfmon_probes (void) {";
10637 o->newline(1) << "int rc = 0;";
10638
10639 o->newline() << "/* data for perfmon */";
10640 o->newline() << "static int _pfm_num_pmc = " << outp.pfp_pmc_count << ";";
10641 o->newline() << "static struct pfarg_pmc _pfm_pmc[" << outp.pfp_pmc_count
10642 << "] = {";
10643 /* output the needed bits for pmc here */
10644 for (unsigned i=0; i < outp.pfp_pmc_count; i++) {
10645 o->newline() << "{.reg_num=" << pc[i].reg_num << ", "
10646 << ".reg_value=" << lex_cast_hex<string>(pc[i].reg_value)
10647 << "},";
10648 }
10649
10650 o->newline() << "};";
10651 o->newline() << "static int _pfm_num_pmd = " << inp.pfp_event_count << ";";
10652 o->newline() << "static struct pfarg_pmd _pfm_pmd[" << inp.pfp_event_count
10653 << "] = {";
10654 /* output the needed bits for pmd here */
10655 for (unsigned i=0; i < inp.pfp_event_count; i++) {
10656 o->newline() << "{.reg_num=" << pd[i].reg_num << ", "
10657 << ".reg_value=" << pd[i].reg_value << "},";
10658 }
10659 o->newline() << "};";
10660 o->newline();
10661
10662 o->newline() << "_pfm_pmc_x=_pfm_pmc;";
10663 o->newline() << "_pfm_num_pmc_x=_pfm_num_pmc;";
10664 o->newline() << "_pfm_pmd_x=_pfm_pmd;";
10665 o->newline() << "_pfm_num_pmd_x=_pfm_num_pmd;";
10666
10667 // call all the function bodies associated with perfcounters
10668 for (unsigned i=0; i < probes.size (); i++)
10669 probes[i]->emit_registrations_start (o,i);
10670
10671 /* generate call to turn on instrumentation */
10672 o->newline() << "_pfm_context.ctx_flags |= PFM_FL_SYSTEM_WIDE;";
10673 o->newline() << "rc = rc || _stp_perfmon_setup(&_pfm_desc, &_pfm_context,";
10674 o->newline(1) << "_pfm_pmc, _pfm_num_pmc,";
10675 o->newline() << "_pfm_pmd, _pfm_num_pmd);";
10676 o->newline(-1);
10677
10678 o->newline() << "return rc;";
10679 o->newline(-1) << "}\n";
10680
10681 // Output the be probes destroy function
10682 o->newline() << "static void unregister_perfmon_probes (void) {";
10683 o->newline(1) << "_stp_perfmon_shutdown(_pfm_desc);";
10684 o->newline(-1) << "}\n";
10685}
b20febf3 10686#endif
47dd066d 10687
47dd066d 10688
b55bc428 10689// ------------------------------------------------------------------------
bd2b1e68 10690// Standard tapset registry.
b55bc428
FCE
10691// ------------------------------------------------------------------------
10692
7a053d3b 10693void
f8220a7b 10694register_standard_tapsets(systemtap_session & s)
b55bc428 10695{
12b21830
DS
10696 s.pattern_root->bind(TOK_BEGIN)->bind(new be_builder(BEGIN));
10697 s.pattern_root->bind_num(TOK_BEGIN)->bind(new be_builder(BEGIN));
10698 s.pattern_root->bind(TOK_END)->bind(new be_builder(END));
10699 s.pattern_root->bind_num(TOK_END)->bind(new be_builder(END));
10700 s.pattern_root->bind(TOK_ERROR)->bind(new be_builder(ERROR));
10701 s.pattern_root->bind_num(TOK_ERROR)->bind(new be_builder(ERROR));
16e8f21f 10702
12b21830 10703 s.pattern_root->bind(TOK_NEVER)->bind(new never_builder());
6e3347a9 10704
c4ce66a1 10705 timer_builder::register_patterns(s);
12b21830
DS
10706 s.pattern_root->bind(TOK_TIMER)->bind("profile")->bind(new profile_builder());
10707 s.pattern_root->bind("perfmon")->bind_str("counter")
10708 ->bind(new perfmon_builder());
b98a8d73 10709
7a24d422 10710 // dwarf-based kprobe/uprobe parts
c4ce66a1 10711 dwarf_derived_probe::register_patterns(s);
30a279be 10712
888af770
FCE
10713 // XXX: user-space starter set
10714 s.pattern_root->bind_num(TOK_PROCESS)
10715 ->bind_num(TOK_STATEMENT)->bind(TOK_ABSOLUTE)
10716 ->bind(new uprobe_builder ());
10717 s.pattern_root->bind_num(TOK_PROCESS)
10718 ->bind_num(TOK_STATEMENT)->bind(TOK_ABSOLUTE)->bind(TOK_RETURN)
10719 ->bind(new uprobe_builder ());
10720
935447c8 10721 // utrace user-space probes
eff6ac72
DS
10722 s.pattern_root->bind_str(TOK_PROCESS)->bind(TOK_BEGIN)
10723 ->bind(new utrace_builder ());
10724 s.pattern_root->bind_num(TOK_PROCESS)->bind(TOK_BEGIN)
10725 ->bind(new utrace_builder ());
986e98de
DS
10726 s.pattern_root->bind(TOK_PROCESS)->bind(TOK_BEGIN)
10727 ->bind(new utrace_builder ());
eff6ac72 10728 s.pattern_root->bind_str(TOK_PROCESS)->bind(TOK_END)
935447c8 10729 ->bind(new utrace_builder ());
eff6ac72 10730 s.pattern_root->bind_num(TOK_PROCESS)->bind(TOK_END)
935447c8 10731 ->bind(new utrace_builder ());
986e98de
DS
10732 s.pattern_root->bind(TOK_PROCESS)->bind(TOK_END)
10733 ->bind(new utrace_builder ());
eff6ac72 10734 s.pattern_root->bind_str(TOK_PROCESS)->bind(TOK_THREAD)->bind(TOK_BEGIN)
159cb109 10735 ->bind(new utrace_builder ());
eff6ac72
DS
10736 s.pattern_root->bind_num(TOK_PROCESS)->bind(TOK_THREAD)->bind(TOK_BEGIN)
10737 ->bind(new utrace_builder ());
986e98de
DS
10738 s.pattern_root->bind(TOK_PROCESS)->bind(TOK_THREAD)->bind(TOK_BEGIN)
10739 ->bind(new utrace_builder ());
eff6ac72
DS
10740 s.pattern_root->bind_str(TOK_PROCESS)->bind(TOK_THREAD)->bind(TOK_END)
10741 ->bind(new utrace_builder ());
10742 s.pattern_root->bind_num(TOK_PROCESS)->bind(TOK_THREAD)->bind(TOK_END)
159cb109 10743 ->bind(new utrace_builder ());
986e98de
DS
10744 s.pattern_root->bind(TOK_PROCESS)->bind(TOK_THREAD)->bind(TOK_END)
10745 ->bind(new utrace_builder ());
12b21830 10746 s.pattern_root->bind_str(TOK_PROCESS)->bind(TOK_SYSCALL)
935447c8 10747 ->bind(new utrace_builder ());
12b21830 10748 s.pattern_root->bind_num(TOK_PROCESS)->bind(TOK_SYSCALL)
935447c8 10749 ->bind(new utrace_builder ());
480f38d3
DS
10750 s.pattern_root->bind(TOK_PROCESS)->bind(TOK_SYSCALL)
10751 ->bind(new utrace_builder ());
12b21830 10752 s.pattern_root->bind_str(TOK_PROCESS)->bind(TOK_SYSCALL)->bind(TOK_RETURN)
935447c8 10753 ->bind(new utrace_builder ());
12b21830 10754 s.pattern_root->bind_num(TOK_PROCESS)->bind(TOK_SYSCALL)->bind(TOK_RETURN)
935447c8 10755 ->bind(new utrace_builder ());
480f38d3
DS
10756 s.pattern_root->bind(TOK_PROCESS)->bind(TOK_SYSCALL)->bind(TOK_RETURN)
10757 ->bind(new utrace_builder ());
10758
10759 // itrace user-space probes
10760 s.pattern_root->bind_str(TOK_PROCESS)->bind("itrace")
10761 ->bind(new itrace_builder ());
10762 s.pattern_root->bind_num(TOK_PROCESS)->bind("itrace")
10763 ->bind(new itrace_builder ());
935447c8 10764
f781f849 10765 // marker-based parts
12b21830
DS
10766 s.pattern_root->bind(TOK_KERNEL)->bind_str(TOK_MARK)
10767 ->bind(new mark_builder());
10768 s.pattern_root->bind(TOK_KERNEL)->bind_str(TOK_MARK)->bind_str(TOK_FORMAT)
eb973c2a 10769 ->bind(new mark_builder());
f781f849 10770
0a6f5a3f
JS
10771 // kernel tracepoint probes
10772 s.pattern_root->bind(TOK_KERNEL)->bind_str(TOK_TRACE)
10773 ->bind(new tracepoint_builder());
10774
ce82316f 10775 // procfs parts
12b21830
DS
10776 s.pattern_root->bind(TOK_PROCFS)->bind(TOK_READ)->bind(new procfs_builder());
10777 s.pattern_root->bind_str(TOK_PROCFS)->bind(TOK_READ)
10778 ->bind(new procfs_builder());
10779 s.pattern_root->bind(TOK_PROCFS)->bind(TOK_WRITE)->bind(new procfs_builder());
10780 s.pattern_root->bind_str(TOK_PROCFS)->bind(TOK_WRITE)
10781 ->bind(new procfs_builder());
b55bc428 10782}
dc38c0ae
DS
10783
10784
b20febf3
FCE
10785vector<derived_probe_group*>
10786all_session_groups(systemtap_session& s)
dc38c0ae 10787{
b20febf3
FCE
10788 vector<derived_probe_group*> g;
10789#define DOONE(x) if (s. x##_derived_probes) g.push_back (s. x##_derived_probes)
ab655cf8
DS
10790
10791 // Note that order *is* important here. We want to make sure we
10792 // register (actually run) begin probes before any other probe type
10793 // is run. Similarly, when unregistering probes, we want to
10794 // unregister (actually run) end probes after every other probe type
10795 // has be unregistered. To do the latter,
10796 // c_unparser::emit_module_exit() will run this list backwards.
b20febf3
FCE
10797 DOONE(be);
10798 DOONE(dwarf);
888af770 10799 DOONE(uprobe);
b20febf3
FCE
10800 DOONE(timer);
10801 DOONE(profile);
10802 DOONE(mark);
0a6f5a3f 10803 DOONE(tracepoint);
b20febf3
FCE
10804 DOONE(hrtimer);
10805 DOONE(perfmon);
ce82316f 10806 DOONE(procfs);
935447c8
DS
10807
10808 // Another "order is important" item. We want to make sure we
10809 // "register" the dummy task_finder probe group after all probe
10810 // groups that use the task_finder.
10811 DOONE(utrace);
a96d1db0 10812 DOONE(itrace);
935447c8 10813 DOONE(task_finder);
b20febf3
FCE
10814#undef DOONE
10815 return g;
46b84a80 10816}
73267b89
JS
10817
10818/* vim: set sw=2 ts=8 cino=>4,n-2,{2,^-2,t0,(0,u0,w1,M1 : */
This page took 1.65814 seconds and 5 git commands to generate.