[DTrace-devel] [PATCH 11/47] Make flowindent work for general cases
Kris Van Hees
kris.van.hees at oracle.com
Sun May 3 20:16:58 PDT 2020
Flowindent was disabled when probe data buffer processing was updated
because there was no support for implementing the heuristic that
requires lookahead for the next probe data sample. While the heuristic
is still not supported with the current code, there is no need to keep
flowindent disabled because for most cases there is no need to provide
support for epid lookahead.
This patch still allows for a later implementation of lookahead to be
added to dt_consume_cpu() and the value of the next epid is to be passed
to dt_consume_one() and from there to dt_flowindent().
Orabug: 31220522
Signed-off-by: Kris Van Hees <kris.van.hees at oracle.com>
Reviewed-by: Kris Van Hees <kris.van.hees at oracle.com>
Reviewed-by: Eugene Loh <eugene.loh at oracle.com>
---
libdtrace/dt_consume.c | 98 +++++++++++++++++-------------------------
1 file changed, 40 insertions(+), 58 deletions(-)
diff --git a/libdtrace/dt_consume.c b/libdtrace/dt_consume.c
index 68e6b1c8..60a16b70 100644
--- a/libdtrace/dt_consume.c
+++ b/libdtrace/dt_consume.c
@@ -363,21 +363,21 @@ dt_stddev(uint64_t *data, uint64_t normal)
static int
dt_flowindent(dtrace_hdl_t *dtp, dtrace_probedata_t *data, dtrace_epid_t last,
- dtrace_bufdesc_t *buf, size_t offs)
+ dtrace_epid_t next)
{
- dtrace_probedesc_t *pd = data->dtpda_pdesc, *npd;
- dtrace_datadesc_t *dd = data->dtpda_ddesc, *ndd;
- dtrace_flowkind_t flow = DTRACEFLOW_NONE;
- const char *p = pd->prv;
- const char *n = pd->prb;
- const char *str = NULL;
- char *sub;
- static const char *e_str[2] = { " -> ", " => " };
- static const char *r_str[2] = { " <- ", " <= " };
- static const char *ent = "entry", *ret = "return";
- static int entlen = 0, retlen = 0;
- dtrace_epid_t next, id = data->dtpda_epid;
- int rval;
+ dtrace_probedesc_t *pd = data->dtpda_pdesc, *npd;
+ dtrace_datadesc_t *dd = data->dtpda_ddesc, *ndd;
+ dtrace_flowkind_t flow = DTRACEFLOW_NONE;
+ const char *p = pd->prv;
+ const char *n = pd->prb;
+ const char *str = NULL;
+ char *sub;
+ static const char *e_str[2] = { " -> ", " => " };
+ static const char *r_str[2] = { " <- ", " <= " };
+ static const char *ent = "entry", *ret = "return";
+ static int entlen = 0, retlen = 0;
+ dtrace_epid_t id = data->dtpda_epid;
+ int rval;
if (entlen == 0) {
assert(retlen == 0);
@@ -398,7 +398,7 @@ dt_flowindent(dtrace_hdl_t *dtp, dtrace_probedata_t *data, dtrace_epid_t last,
flow = DTRACEFLOW_ENTRY;
str = e_str[strcmp(p, "syscall") == 0];
} else if ((sub = strstr(n, ret)) != NULL && sub[retlen] == '\0' &&
- (sub == n || sub[-1] == '-')) {
+ (sub == n || sub[-1] == '-')) {
flow = DTRACEFLOW_RETURN;
str = r_str[strcmp(p, "syscall") == 0];
}
@@ -410,8 +410,8 @@ dt_flowindent(dtrace_hdl_t *dtp, dtrace_probedata_t *data, dtrace_epid_t last,
* this scheme -- it's a heuristic.)
*/
if (flow == DTRACEFLOW_ENTRY) {
- if ((last != DTRACE_EPIDNONE && id != last &&
- pd->id == dtp->dt_pdesc[last]->id))
+ if (last != DTRACE_EPIDNONE && id != last &&
+ pd->id == dtp->dt_pdesc[last]->id)
flow = DTRACEFLOW_NONE;
}
@@ -420,48 +420,28 @@ dt_flowindent(dtrace_hdl_t *dtp, dtrace_probedata_t *data, dtrace_epid_t last,
* we don't actually want to unindent it -- we need to look at the
* _next_ EPID.
*/
- if (flow == DTRACEFLOW_RETURN) {
- offs += dd->dtdd_size;
-
- do {
- if (offs >= buf->dtbd_size) {
- /*
- * We're at the end -- maybe. If the oldest
- * record is non-zero, we need to wrap.
- */
- if (buf->dtbd_oldest != 0) {
- offs = 0;
- } else {
- goto out;
- }
- }
-
- next = *(uint32_t *)((uintptr_t)buf->dtbd_data + offs);
-
- if (next == DTRACE_EPIDNONE)
- offs += sizeof (id);
- } while (next == DTRACE_EPIDNONE);
-
- if ((rval = dt_epid_lookup(dtp, next, &ndd, &npd)) != 0)
- return (rval);
+ if (flow == DTRACEFLOW_RETURN && next != DTRACE_EPIDNONE &&
+ next != id) {
+ rval = dt_epid_lookup(dtp, next, &ndd, &npd);
+ if (rval != 0)
+ return rval;
- if (next != id && npd->id == pd->id)
+ if (npd->id == pd->id)
flow = DTRACEFLOW_NONE;
}
out:
- if (flow == DTRACEFLOW_ENTRY || flow == DTRACEFLOW_RETURN) {
+ if (flow == DTRACEFLOW_ENTRY || flow == DTRACEFLOW_RETURN)
data->dtpda_prefix = str;
- } else {
+ else
data->dtpda_prefix = "| ";
- }
if (flow == DTRACEFLOW_RETURN && data->dtpda_indent > 0)
data->dtpda_indent -= 2;
data->dtpda_flow = flow;
- return (0);
+ return 0;
}
static int
@@ -2277,15 +2257,11 @@ nextepid:
int
dt_consume_one(dtrace_hdl_t *dtp, FILE *fp, int cpu, char *buf,
dtrace_consume_probe_f *efunc, dtrace_consume_rec_f *rfunc,
- void *arg)
+ int flow, int quiet, dtrace_epid_t last, void *arg)
{
char *data = buf;
struct perf_event_header *hdr;
int rval;
- int flow, quiet;
-
- flow = (dtp->dt_options[DTRACEOPT_FLOWINDENT] != DTRACEOPT_UNSET);
- quiet = (dtp->dt_options[DTRACEOPT_QUIET] != DTRACEOPT_UNSET);
hdr = (struct perf_event_header *)data;
data += sizeof(struct perf_event_header);
@@ -2305,7 +2281,7 @@ dt_consume_one(dtrace_hdl_t *dtp, FILE *fp, int cpu, char *buf,
* uint32_t tag;
* uint64_t data[n];
* }
- * and data points to the 'size' member at this point.
+ * and 'data' points to the 'size' member at this point.
* (Note that 'n' may be 0.)
*/
if (ptr > buf + hdr->size)
@@ -2342,19 +2318,15 @@ dt_consume_one(dtrace_hdl_t *dtp, FILE *fp, int cpu, char *buf,
if (rval != 0)
return rval;
-#if 0
if (flow)
- dt_flowindent(dtp, &pdat, last, data, 0); /* FIXME */
-#endif
+ dt_flowindent(dtp, &pdat, last, DTRACE_EPIDNONE);
rval = (*efunc)(&pdat, arg);
-#if 0
if (flow) {
if (pdat.dtpda_flow == DTRACEFLOW_ENTRY)
pdat.dtpda_indent += 2;
}
-#endif
if (rval == DTRACE_CONSUME_NEXT)
return 0;
@@ -2398,6 +2370,8 @@ dt_consume_one(dtrace_hdl_t *dtp, FILE *fp, int cpu, char *buf,
* that we're done processing this EPID.
*/
rval = (*rfunc)(&pdat, NULL, arg);
+
+ return epid;
} else if (hdr->type == PERF_RECORD_LOST) {
uint64_t lost;
@@ -2411,6 +2385,8 @@ dt_consume_one(dtrace_hdl_t *dtp, FILE *fp, int cpu, char *buf,
*/
lost = *(uint64_t *)(data + sizeof(uint64_t));
+ /* FIXME: To be implemented */
+ return -1;
} else
return -1;
}
@@ -2422,12 +2398,17 @@ dt_consume_cpu(dtrace_hdl_t *dtp, FILE *fp, int cpu, dt_peb_t *peb,
{
struct perf_event_mmap_page *rb_page = (void *)peb->base;
struct perf_event_header *hdr;
+ dtrace_epid_t last = DTRACE_EPIDNONE;
char *base;
char *event;
uint32_t len;
uint64_t head, tail;
dt_pebset_t *pebset = dtp->dt_pebset;
uint64_t data_size = pebset->data_size;
+ int flow, quiet;
+
+ flow = (dtp->dt_options[DTRACEOPT_FLOWINDENT] != DTRACEOPT_UNSET);
+ quiet = (dtp->dt_options[DTRACEOPT_QUIET] != DTRACEOPT_UNSET);
/*
* Set base to be the start of the buffer data, i.e. we skip the first
@@ -2469,7 +2450,8 @@ dt_consume_cpu(dtrace_hdl_t *dtp, FILE *fp, int cpu, dt_peb_t *peb,
event = dst;
}
- dt_consume_one(dtp, fp, cpu, event, efunc, rfunc, arg);
+ last = dt_consume_one(dtp, fp, cpu, event, efunc, rfunc,
+ flow, quiet, last, arg);
tail += hdr->size;
} while (tail != head);
--
2.26.0
More information about the DTrace-devel
mailing list