From: Kris Van Hees Date: Thu, 23 May 2013 14:52:00 +0000 (-0400) Subject: Finish the implementation of is-enabled USDT probes. X-Git-Tag: v4.1.12-111.0.20170907_2225~3^2~3^2~155 X-Git-Url: https://www.infradead.org/git/?a=commitdiff_plain;h=ae127d2b21531a2a512325e8df8f523e98fc7e5b;p=users%2Fjedix%2Flinux-maple.git Finish the implementation of is-enabled USDT probes. This commit completes the implementation of is-enabled USDT probes, i.e. probes that when fired cause an execution flow change. This makes it possible (when using USDT) to encode more complex code sections that are only executed if a specific USDT probe has been enabled, i.e. when a consumer is listening for s specific USDT probe. This is most commonly used for cases where a USDT probe might require additional computation for one or more of its arguments, and so it would be too expensive to always do that computation, whether the probe is enabled or not. With is-enabled probes, the overhead when DTrace is not used is negligible (2 NOPs), and when DTrace is in use but the guarded probe is not enabled, the cost is a single probe firing (without calling dtrace_probe()). Signed-off-by: Kris Van Hees --- diff --git a/dtrace/dtrace_dof.c b/dtrace/dtrace_dof.c index 833213eed3e31..58c67a0523e85 100644 --- a/dtrace/dtrace_dof.c +++ b/dtrace/dtrace_dof.c @@ -1651,7 +1651,7 @@ static void dtrace_helper_provide_one(dof_helper_t *dhp, dof_sec_t *sec, if (dof->dofh_ident[DOF_ID_VERSION] != DOF_VERSION_1 && prov->dofpv_prenoffs != DOF_SECT_NONE) { enoff_sec = (dof_sec_t *)(uintptr_t)(daddr + dof->dofh_secoff + - prov->dofpv_proffs * + prov->dofpv_prenoffs * dof->dofh_secsize); enoff = (uint32_t *)(uintptr_t)(daddr + enoff_sec->dofs_offset); diff --git a/dtrace/fasttrap_dev.c b/dtrace/fasttrap_dev.c index c399e311393f0..2711d9427ab42 100644 --- a/dtrace/fasttrap_dev.c +++ b/dtrace/fasttrap_dev.c @@ -73,24 +73,49 @@ static volatile uint64_t fasttrap_mod_gen; static void fasttrap_pid_cleanup(void); -static void fasttrap_pid_probe(fasttrap_machtp_t *mtp, struct pt_regs *regs) { +static int fasttrap_pid_probe(fasttrap_machtp_t *mtp, struct pt_regs *regs) { fasttrap_tracepoint_t *tp = container_of(mtp, fasttrap_tracepoint_t, ftt_mtp); fasttrap_id_t *id; + int is_enabled = 0; +pr_info("fasttrap_pid_probe(PID %d, PC %lx) regs(ip %lx, ax %lx)\n", tp->ftt_pid, tp->ftt_pc, regs->ip, regs->ax); pr_info("fasttrap_pid_probe(PID %d, PC %lx)\n", tp->ftt_pid, tp->ftt_pc); if (atomic64_read(&tp->ftt_proc->ftpc_acount) == 0) { pr_info(" Ignored (no longer active)\n"); - return; + return 0; } for (id = tp->ftt_ids; id != NULL; id = id->fti_next) { fasttrap_probe_t *ftp = id->fti_probe; + if (id->fti_ptype == DTFTP_IS_ENABLED) { +pr_info(" Probe ID %d for PID %d (is-enabled)\n", ftp->ftp_id, ftp->ftp_pid); + is_enabled = 1; + } else if (ftp->ftp_argmap == NULL) { pr_info(" Probe ID %d for PID %d\n", ftp->ftp_id, ftp->ftp_pid); - dtrace_probe(ftp->ftp_id, regs->di, regs->si, regs->dx, - regs->cx, regs->r8); + dtrace_probe(ftp->ftp_id, regs->di, regs->si, regs->dx, + regs->cx, regs->r8); + } else { + uintptr_t t[5]; + +#ifdef FIXME + fasttrap_usdt_args64(probe, regs, + sizeof(t) / sizeof(t[0]), t); +#endif +pr_info(" Probe ID %d for PID %d (arg-mapped)\n", ftp->ftp_id, ftp->ftp_pid); + dtrace_probe(ftp->ftp_id, t[0], t[1], t[2], t[3], + t[4]); + } } + + if (is_enabled) +{ +pr_info(" Setting EAX to 1 due to is-enabled probe\n"); + regs->ax = 1; +} + + return 0; } static void fasttrap_pid_provide(void *arg, const dtrace_probedesc_t *desc) @@ -183,6 +208,7 @@ static int fasttrap_tracepoint_enable(fasttrap_probe_t *probe, uint_t index) pid = probe->ftp_pid; pc = probe->ftp_tps[index].fit_tp->ftt_pc; id = &probe->ftp_tps[index].fit_id; +pr_info("fasttrap_tracepoint_enable(ID %d, index %d) -> (pid %d, pc %lx)\n", probe->ftp_id, index, pid, pc); ASSERT(probe->ftp_tps[index].fit_tp->ftt_pid == pid); @@ -529,6 +555,7 @@ static int fasttrap_pid_enable(void *arg, dtrace_id_t id, void *parg) * tracepoint's list of active probes. */ for (i = 0; i < probe->ftp_ntps; i++) { +pr_info("fasttrap_pid_enable() -> Calling fasttrap_tracepoint_enable(ID %d, i %d)\n", probe->ftp_id, i); if ((rc = fasttrap_tracepoint_enable(probe, i)) != 0) { /* * If enabling the tracepoint failed completely, @@ -772,6 +799,7 @@ void fasttrap_meta_create_probe(void *arg, void *parg, tp->ftt_proc = provider->ftp_proc; tp->ftt_pc = dhpb->dthpb_base + dhpb->dthpb_offs[i]; tp->ftt_pid = provider->ftp_pid; +pr_info("%s: Creating tp %d (pid %d, pc %lx) [regular]\n", __FUNCTION__, i, tp->ftt_pid, tp->ftt_pc); pp->ftp_tps[i].fit_tp = tp; pp->ftp_tps[i].fit_id.fti_probe = pp; @@ -791,6 +819,7 @@ void fasttrap_meta_create_probe(void *arg, void *parg, tp->ftt_proc = provider->ftp_proc; tp->ftt_pc = dhpb->dthpb_base + dhpb->dthpb_enoffs[j]; tp->ftt_pid = provider->ftp_pid; +pr_info("%s: Creating tp %d (pid %d, pc %lx) [is-enabled]\n", __FUNCTION__, i, tp->ftt_pid, tp->ftt_pc); pp->ftp_tps[i].fit_tp = tp; pp->ftp_tps[i].fit_id.fti_probe = pp;