Re: [PATCH v4] trace: print alloca pointers as actual pointer values
Eugene Loh <[email protected]>
| Newsgroups | dev.linux.lists.dtrace |
|---|---|
| Message-ID | <[email protected]> |
Reviewed-by: Eugene Loh <[email protected]> On 9/16/25 14:26, Kris Van Hees wrote: > Because alloca pointers are stored internally as offsets into the > scratchmem area, they were printed as small integers. They are > now printed as actual pointer values into kernel space. > > Signed-off-by: Kris Van Hees <[email protected]> > --- > libdtrace/dt_cg.c | 46 ++++++++++++++++------ > test/unittest/actions/trace/tst.alloca.d | 24 +++++++++++ > test/unittest/actions/trace/tst.alloca.r | 1 + > test/unittest/actions/trace/tst.alloca.r.p | 11 ++++++ > 4 files changed, 71 insertions(+), 11 deletions(-) > create mode 100644 test/unittest/actions/trace/tst.alloca.d > create mode 100644 test/unittest/actions/trace/tst.alloca.r > create mode 100755 test/unittest/actions/trace/tst.alloca.r.p > > diff --git a/libdtrace/dt_cg.c b/libdtrace/dt_cg.c > index 7d542521..1f120e1d 100644 > --- a/libdtrace/dt_cg.c > +++ b/libdtrace/dt_cg.c > @@ -1687,18 +1687,42 @@ dt_cg_store_val(dt_pcb_t *pcb, dt_node_t *dnp, dtrace_actkind_t kind, > align = vtype.dtdt_align; > > /* > - * A DEREF of a REF node does not get resolved in dt_cg_node() > - * because the ref node already holds the pointer. But for > - * alloca pointers, that will be the offset into scratchmem so > - * we still need to turn it into a real pointer here. > + * Alloca pointers are stored as an offset into scratchmem, so > + * they need to be converted into real pointers before we go on. > + * An alloca pointer value either has the ALLOCA flag set, or > + * the value node is a DEREF of an alloca pointer child. > + * If the alloca pointer is a REF or ref-by-value is requested, > + * we need to do bounds checking before turning the alloca > + * pointer into a real pointer. > + * If not, we should scalarize it so that the BPF verifier does > + * not complain. > */ > - if (dnp->dn_kind == DT_NODE_OP1 && > - dnp->dn_op == DT_TOK_DEREF && (dnp->dn_flags & DT_NF_REF) && > - (dnp->dn_child->dn_flags & DT_NF_ALLOCA)) { > - dt_cg_alloca_access_check(dlp, drp, dnp->dn_reg, > - DT_ISIMM, size); > - dt_cg_alloca_ptr(dlp, drp, dnp->dn_reg, dnp->dn_reg); > - not_null = 1; > + if ((dnp->dn_flags & DT_NF_ALLOCA) || > + (dnp->dn_kind == DT_NODE_OP1 && > + dnp->dn_op == DT_TOK_DEREF && > + (dnp->dn_flags & DT_NF_REF) && > + (dnp->dn_child->dn_flags & DT_NF_ALLOCA))) { > + if ((dnp->dn_flags & DT_NF_REF) || (arg & DT_NF_REF)) { > + dt_cg_alloca_access_check(dlp, drp, dnp->dn_reg, > + DT_ISIMM, size); > + > + dt_cg_alloca_ptr(dlp, drp, dnp->dn_reg, dnp->dn_reg); > + not_null = 1; > + } else { > + int reg; > + > + dt_regset_xalloc(drp, BPF_REG_0); > + emit(dlp, BPF_LOAD(BPF_DW, BPF_REG_0, BPF_REG_FP, DT_STK_DCTX)); > + if ((reg = dt_regset_alloc(drp)) == -1) > + longjmp(yypcb->pcb_jmpbuf, EDT_NOREG); > + emit(dlp, BPF_LOAD(BPF_DW, reg, BPF_REG_0, DCTX_SCRATCHMEM)); > + emit(dlp, BPF_LOAD(BPF_DW, BPF_REG_0, BPF_REG_0, DCTX_MST)); > + emit(dlp, BPF_STORE(BPF_DW, BPF_REG_0, DMST_SCALARIZER, reg)); > + emit(dlp, BPF_LOAD(BPF_DW, reg, BPF_REG_0, DMST_SCALARIZER)); > + dt_regset_free(drp, BPF_REG_0); > + emit(dlp, BPF_ALU64_REG(BPF_ADD, dnp->dn_reg, reg)); > + dt_regset_free(drp, reg); > + } > } > } > > diff --git a/test/unittest/actions/trace/tst.alloca.d b/test/unittest/actions/trace/tst.alloca.d > new file mode 100644 > index 00000000..d2ff5152 > --- /dev/null > +++ b/test/unittest/actions/trace/tst.alloca.d > @@ -0,0 +1,24 @@ > +#pragma D option quiet > + > +BEGIN > +{ > + arr = (int *)alloca(5 * sizeof(int)); > + idx = 4; > + arr[0] = 1; > + arr[1] = 22; > + arr[2] = 333; > + arr[3] = 4444; > + arr[4] = 55555; > + trace(arr); > + trace(" "); > + trace(*arr); > + trace(" "); > + trace(arr + 2); > + trace(" "); > + trace(*(arr + 2)); > + trace(" "); > + trace(arr + idx); > + trace(" "); > + trace(*(arr + idx)); > + exit(0); > +} > diff --git a/test/unittest/actions/trace/tst.alloca.r b/test/unittest/actions/trace/tst.alloca.r > new file mode 100644 > index 00000000..e9bbf2f5 > --- /dev/null > +++ b/test/unittest/actions/trace/tst.alloca.r > @@ -0,0 +1 @@ > +OK 1 OK 333 OK 55555 > diff --git a/test/unittest/actions/trace/tst.alloca.r.p b/test/unittest/actions/trace/tst.alloca.r.p > new file mode 100755 > index 00000000..8515861a > --- /dev/null > +++ b/test/unittest/actions/trace/tst.alloca.r.p > @@ -0,0 +1,11 @@ > +#!/usr/bin/gawk -f > + > +{ > + $1 = $1 > 0x7fffffff ? "OK" : "BAD"; > + $3 = $3 > 0x7fffffff ? "OK" : "BAD"; > + $5 = $5 > 0x7fffffff ? "OK" : "BAD"; > +} > + > +{ > + print; > +}