This should disable allocation of the second per-CPU principal buffer
which is never used. This will also enable additional asserts
for buffers that are never switched.
Details
Diff Detail
- Repository
- rS FreeBSD src repository - subversion
- Lint
No Lint Coverage - Unit
No Test Coverage - Build Status
Buildable 43577 Build 40465: arc lint + arc unit
Event Timeline
@avg This seems to introduce a kernel panic when -x bufpolicy=ring is used:
# dtrace -x bufpolicy=ring -n 'BEGIN { trace(basename((char *)rand())); }'
results in mstate->dtms_scratch_ptr being NULL in dtrace_dif_emulate(). Unsure why, but we should probably fix it. FWIW, there is a test in the DTrace test suite (common/safety/tst.basename.d) which catches this, and might be an argument to run the test suite in CI somewhere to catch such regressions a bit earlier.
CC @lwhsu?
Looking at the code a little bit further, it seems that
/* * For ring buffers and fill buffers, the scratch space is always * the inactive buffer. */ mstate->dtms_scratch_base = (uintptr_t)buf->dtb_xamot; mstate->dtms_scratch_size = buf->dtb_size; mstate->dtms_scratch_ptr = mstate->dtms_scratch_base;
+
two places that have:
if (flags & DTRACEBUF_NOSWITCH) continue; if ((buf->dtb_xamot = kmem_zalloc(size, KM_NOSLEEP | KM_NORMALPRI)) == NULL) goto err;
are the cause. That is to say, buf->dtb_xamot likely does not get allocated, and therefore is NULL. However, when we have ringbuffers, we use that space as the scratch space. It seems like DTrace assumes that both buffers need to be allocated regardless of switching. I don't have time right now to test my understanding of the problems, but will have some more time tonight.
The comment at the end of dtrace_buffer_reserve() suggests that this commit is incorrect.
Looks like I assumed too much without paying attention to the scratch buffer.
I'll revert the change.