I'm killing off features for whom their maintenance is not paying off.
One is the "tick" based usermode --breakpoint
feature, implemented on the command line as:
"--breakpoint" end (
c-debug-break-at to-integer param-or-die "BREAKPOINT"
)
The complex problem of taking a "tick" count to break on via a command line switch is that since command line processing is in usermode, you have a kind of observer-affects-the-experiment situation. The code for adding in the breakpoint messes with the tick count you're trying to reproduce.
I had ideas to work around this. So there's the /COMPENSATE feature of C-DEBUG-BREAK, which I don't even know if it works or if my idea is fundamentally flawed:
; Taking a command-line `--breakpoint NNN` parameter is helpful if a
; problem is reproducible, and you have a tick count in hand from a
; panic(), REBSER.tick, Frame.tick, REBVAL.extra.tick, etc. But there's
; an entanglement issue, as any otherwise-deterministic tick from a prior
; run would be thrown off by the **ticks added by the userspace parameter
; processing of the command-line for `--breakpoint`**! :-/
;
; The /COMPENSATE option addresses this problem. Pass it a reasonable
; upper bound for how many ticks you think could have been added to the
; parse, if `--breakpoint` was processed (even though it might not have
; been processed). Regardless of whether the switch was present or not,
; the tick count rounds up to a reproducible value, using this method:
;
; https://math.stackexchange.com/q/2521219/
;
; At time of writing, 1000 ticks should be *way* more than enough for both
; the PARSE steps and the evaluation steps `--breakpoint` adds. Yet some
; things could affect this, e.g. a complex userspace TRACE which was
; run during boot.
;
attempt [c-debug-break-at/compensate 1000] ; fails in release build
Here was more of it:
#if !defined(NDEBUG) && DEBUG_COUNT_TICKS
if (REF(compensate)) {
//
// Imagine two runs of Rebol console initialization. In the first,
// the tick count is 304 when C-DEBUG-BREAK/COMPENSATE is called,
// right after command line parsing. Later on a panic() is hit and
// reports tick count 1020 in the crash log.
//
// Wishing to pick apart the bug before it happens, the Rebol Core
// Developer then re-runs the program with `--breakpoint=1020`, hoping
// to break at that tick, to catch the downstream appearance of the
// tick in the panic(). But since command-line processing is in
// usermode, the addition of the parameter throws off the ticks!
//
// https://en.wikipedia.org/wiki/Observer_effect_(physics)
//
// Let's say that after the command line processing, it still runs
// C-DEBUG-BREAK/COMPENSATE, this time at tick 403. Imagine our goal
// is to make the parameter to /COMPENSATE something that can be used
// to conservatively guess the same value to set the tick to, and
// that /COMPENSATE ARG(bound) that gives a maximum of how far off we
// could possibly be from the "real" tick. (e.g. "argument processing
// took no more than 200 additional ticks", which this is consistent
// with...since 403-304 = 99).
//
// The reasoning for why the formula below works for this rounding is
// given in this StackExchange question and answer:
//
// https://math.stackexchange.com/q/2521219/
//
Tick one = 1; // MSVC gives misguided warning for cast(Tick, 1)
TG_tick =
(one << (ceil_log2(TG_tick) + 1))
+ VAL_INT64(ARG(tick))
- 1;
return nullptr;
}
Also, I've never used the /RELATIVE tick feature, killing that too:
if (REF(relative))
TG_break_at_tick = frame_->tick + 1 + VAL_INT64(ARG(tick));
I'm going to be deleting a lot of things, I think, in the pursuit of simplification--now that isotopes are showing the way.