[DTrace-devel] [PATCH v3 15/19] Ignore clauses: some clauses are impossible regardless of uprp
Kris Van Hees
kris.van.hees at oracle.com
Fri Oct 25 14:35:12 UTC 2024
On Fri, Oct 25, 2024 at 02:34:23AM -0400, eugene.loh at oracle.com wrote:
> From: Eugene Loh <eugene.loh at oracle.com>
>
> In ignore_clauses, for an underlying probe uprp, we try to
> decide if we can safely ignore clause n.
>
> Meanwhile, for some clauses, the probe description tells us the
> clause will not be called for any USDT probe, regardless of the
> underlying probe. For example, "syscall::write:" can safely be
> ignored, for all uprp.
>
> Add clause flags to track a statement's status. Specifically,
> a flag may indicate that a statement can be excluded for every
> possible USDT probe or included because it might be needed for
> some possible USDT probe.
>
> Signed-off-by: Eugene Loh <eugene.loh at oracle.com>
Reviewed-by: Kris Van Hees <kris.van.hees at oracle.com>
> ---
> libdtrace/dt_program.c | 15 +++++++++++
> libdtrace/dt_program.h | 3 +++
> libdtrace/dt_prov_uprobe.c | 53 ++++++++++++++++++++++++++++++++++++--
> libdtrace/dtrace.h | 2 ++
> 4 files changed, 71 insertions(+), 2 deletions(-)
>
> diff --git a/libdtrace/dt_program.c b/libdtrace/dt_program.c
> index 45da4f206..23b91fb2e 100644
> --- a/libdtrace/dt_program.c
> +++ b/libdtrace/dt_program.c
> @@ -20,6 +20,21 @@
> #include <dt_probe.h>
> #include <dt_bpf.h>
>
> +int
> +dt_stmt_clsflag_set(dtrace_stmtdesc_t *stp, int flags) {
> + stp->dtsd_clauseflags |= flags;
> +
> + return 0;
> +}
> +
> +int
> +dt_stmt_clsflag_test(dtrace_stmtdesc_t *stp, int flags) {
> + if (stp->dtsd_clauseflags & flags)
> + return 1;
> +
> + return 0;
> +}
> +
> dtrace_prog_t *
> dt_program_create(dtrace_hdl_t *dtp)
> {
> diff --git a/libdtrace/dt_program.h b/libdtrace/dt_program.h
> index 5f57e3615..5f11ef3a6 100644
> --- a/libdtrace/dt_program.h
> +++ b/libdtrace/dt_program.h
> @@ -28,6 +28,9 @@ struct dtrace_prog {
> uint8_t dp_dofversion; /* DOF version this program requires */
> };
>
> +extern int dt_stmt_clsflag_set(dtrace_stmtdesc_t *stp, int flags);
> +extern int dt_stmt_clsflag_test(dtrace_stmtdesc_t *stp, int flags);
> +
> extern dtrace_prog_t *dt_program_create(dtrace_hdl_t *);
> extern void dt_program_destroy(dtrace_hdl_t *, dtrace_prog_t *);
>
> diff --git a/libdtrace/dt_prov_uprobe.c b/libdtrace/dt_prov_uprobe.c
> index 11ff01051..9ca190b72 100644
> --- a/libdtrace/dt_prov_uprobe.c
> +++ b/libdtrace/dt_prov_uprobe.c
> @@ -27,6 +27,7 @@
> */
> #include <sys/types.h>
> #include <assert.h>
> +#include <ctype.h>
> #include <errno.h>
> #include <string.h>
>
> @@ -37,6 +38,7 @@
> #include "dt_list.h"
> #include "dt_provider_tp.h"
> #include "dt_probe.h"
> +#include "dt_program.h"
> #include "dt_pid.h"
> #include "dt_string.h"
> #include "port.h"
> @@ -270,7 +272,53 @@ clean_usdt_probes(dtrace_hdl_t *dtp)
> static int
> ignore_clause(dtrace_hdl_t *dtp, int n, const dt_probe_t *uprp)
> {
> - /* To be safe, ignore nothing. */
> + dtrace_stmtdesc_t *stp = dtp->dt_stmts[n];
> + dtrace_probedesc_t *pdp = &stp->dtsd_ecbdesc->dted_probe;
> +
> + /*
> + * Some clauses could never be called for a USDT probe,
> + * regardless of the underlying probe uprp. Cache this
> + * status in the clause flags for dt_stmts[n].
> + */
> + if (dt_stmt_clsflag_test(stp, DT_CLSFLAG_USDT_INCLUDE | DT_CLSFLAG_USDT_EXCLUDE) == 0) {
> + char lastchar = pdp->prv[strlen(pdp->prv) - 1];
> +
> + /*
> + * If the last char in the provider description is
> + * neither '*' nor a digit, it cannot be a USDT probe.
> + */
> + if (lastchar != '*' && !isdigit(lastchar)) {
> + dt_stmt_clsflag_set(stp, DT_CLSFLAG_USDT_EXCLUDE);
> + return 1;
> + }
> +
> + /*
> + * If the provider description is "pid[0-9]*", it
> + * is a pid probe, not USDT.
> + */
> + if (strncmp(pdp->prv, "pid", 3) == 0) {
> + int i, l = strlen(pdp->prv);
> +
> + for (i = 3; i < l; i++)
> + if (!isdigit((pdp->prv[i])))
> + break;
> +
> + if (i == l) {
> + dt_stmt_clsflag_set(stp, DT_CLSFLAG_USDT_EXCLUDE);
> + return 1;
> + }
> + }
> +
> + /* Otherwise, it is possibly a USDT probe. */
> + dt_stmt_clsflag_set(stp, DT_CLSFLAG_USDT_INCLUDE);
> + }
> + if (dt_stmt_clsflag_test(stp, DT_CLSFLAG_USDT_EXCLUDE) == 1)
> + return 1;
> +
> + /*
> + * If we cannot ignore this statement, try to use uprp.
> + */
> +
> return 0;
> }
>
> @@ -453,7 +501,8 @@ static int discover(dtrace_hdl_t *dtp)
> stp = dtp->dt_stmts[i];
> if (stp == NULL)
> continue;
> - dt_pid_create_usdt_probes(&stp->dtsd_ecbdesc->dted_probe, dtp, &pcb);
> + if (dt_stmt_clsflag_test(stp, DT_CLSFLAG_USDT_EXCLUDE) != 1)
> + dt_pid_create_usdt_probes(&stp->dtsd_ecbdesc->dted_probe, dtp, &pcb);
> }
>
> return 0;
> diff --git a/libdtrace/dtrace.h b/libdtrace/dtrace.h
> index e636c5065..20672d3fc 100644
> --- a/libdtrace/dtrace.h
> +++ b/libdtrace/dtrace.h
> @@ -161,6 +161,8 @@ typedef struct dtrace_stmtdesc {
> #define DT_CLSFLAG_EXIT 16 /* exit */
> #define DT_CLSFLAG_DESTRUCT 32 /* destructive */
> #define DT_CLSFLAG_AGGREGATION 64 /* aggregation */
> +#define DT_CLSFLAG_USDT_INCLUDE 128 /* could be used in USDT clause */
> +#define DT_CLSFLAG_USDT_EXCLUDE 256 /* could not be used in USDT clause */
>
> typedef int dtrace_stmt_f(dtrace_hdl_t *dtp, dtrace_prog_t *pgp,
> dtrace_stmtdesc_t *sdp, void *data);
> --
> 2.43.5
>
More information about the DTrace-devel
mailing list