Silence routine diagnostic noise; fix a real CRLF double-submit bug
Two separate fixes, found and closed together after task 3.9/prompt-
format landed (Captain Bob: "finish the work first then we'll do
cleanup before 3.10 begins").
1. Logging noise (confirmed live via QMP screendump): three sources
were cluttering ordinary interactive console sessions.
- INFERENCE "Output validation failed, ignoring results"
(vm_runtime.c, kernel; vm_time.c, hosted mirror) and xhci "CSW
status = FAILED"/"unit not ready -- retrying" (xhci.c) were
already log_message(LOG_WARN/LOG_ERROR, ...) calls, just visible
at the default runtime LOG_WARN level -- downgraded to LOG_INFO,
all three fire routinely and self-resolve (xhci.c's own existing
comment already documents the retry as expected SCSI UNIT
ATTENTION behavior, not a driver defect).
- Stadium: dispatch cell=... (stadium.c's stadium_dispatch()) was a
genuine defect: an unconditional console_puts()/console_println()
sequence with no level gating at all, printing on every single
dispatch. Rewritten through log_message(LOG_DEBUG, ...).
2. CRLF double-submit (found while investigating why the cleaned-up
noise still didn't look like a normal single-VM session):
sk_console_readline() (repl.c) breaks on '\r' OR '\n' as independent
terminators, so a line sent as both bytes submits twice -- the real
line, then an immediate empty-line submit on the second byte, each
printing its own " ok". Pre-dates Stage D entirely, not an async-
relay artifact. Fixed with a single non-blocking peek-and-discard
for the paired byte right where the line terminates.
Verified live on all three architectures for both fixes: zero UNKNOWN
WORD, dict_hash identical to every prior acceptance run in this
document (both changes are display/interaction-only).
Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Sonnet 5
parent
5c07745c18
commit
d4f8a568ee
@@ -1306,6 +1306,26 @@ int sk_console_readline(char* buf, int size, VM* active_vm, int reanchor_prompt)
|
||||
if (c == '\r' || c == '\n') {
|
||||
console_fb_erase_cursor(); /* leaving this cell without drawing a char over it */
|
||||
console_putc('\n');
|
||||
/* CRLF pairing, found live 2026-09-22: a terminator sent as
|
||||
* both bytes (a real terminal in CRLF mode, or any scripted
|
||||
* sender writing "\r\n") used to submit TWICE -- this line
|
||||
* on the '\r' (or '\n'), then an immediate empty line on the
|
||||
* OTHER byte the next time this function is called, each
|
||||
* producing its own " ok" -- confirmed live as the doubled
|
||||
* "ok" this project's own session interaction showed, not an
|
||||
* async-relay artifact as first suspected. Non-blocking peek
|
||||
* for the paired byte right here, before returning -- discard
|
||||
* it if present, push it back via g_console_pending_key
|
||||
* (already the mechanism sk_console_key_available() uses for
|
||||
* exactly this "peeked but not this call's to consume" case)
|
||||
* if it's unrelated input for the NEXT line. A byte that
|
||||
* hasn't arrived yet by this point is not waited for --
|
||||
* matches every other non-blocking read in this function. */
|
||||
{
|
||||
int pair = (c == '\r') ? '\n' : '\r';
|
||||
int next = sk_console_getc_raw();
|
||||
if (next >= 0 && next != pair) g_console_pending_key = next;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
|
||||
@@ -2111,7 +2111,16 @@ void xhci_poll_events(void)
|
||||
if (csw_pass) {
|
||||
log_message(LOG_DEBUG, "xhci: CSW status = PASS");
|
||||
} else if (dev->bot_csw.bCSWStatus == USB_BOT_CSW_STATUS_FAILED) {
|
||||
log_message(LOG_ERROR, "xhci: CSW status = FAILED");
|
||||
/* 2026-09-22: downgraded from LOG_ERROR --
|
||||
* a fresh SCSI target's standard first-
|
||||
* command UNIT ATTENTION behavior (see this
|
||||
* block's own comment a few lines down),
|
||||
* not a driver defect; the bounded retry
|
||||
* below resolves it routinely. The genuine
|
||||
* terminal failure ("giving up" below,
|
||||
* after XHCI_BOT_TUR_MAX_RETRIES) stays at
|
||||
* LOG_ERROR. */
|
||||
log_message(LOG_INFO, "xhci: CSW status = FAILED");
|
||||
} else {
|
||||
log_message(LOG_ERROR, "xhci: CSW status = PHASE ERROR");
|
||||
}
|
||||
@@ -2142,7 +2151,11 @@ void xhci_poll_events(void)
|
||||
}
|
||||
} else if (dev->bot_tur_retries < XHCI_BOT_TUR_MAX_RETRIES) {
|
||||
dev->bot_tur_retries++;
|
||||
log_message(LOG_WARN, "xhci: unit not ready -- retrying TEST UNIT READY");
|
||||
/* 2026-09-22: downgraded from LOG_WARN,
|
||||
* same reasoning as the CSW FAILED
|
||||
* downgrade above -- expected, routinely
|
||||
* self-resolving. */
|
||||
log_message(LOG_INFO, "xhci: unit not ready -- retrying TEST UNIT READY");
|
||||
xms->next_action = XHCI_NEXT_ACTION_BOT_SEND_TUR;
|
||||
} else {
|
||||
log_message(LOG_ERROR, "xhci: unit still not ready -- giving up");
|
||||
|
||||
+17
-13
@@ -37,6 +37,7 @@
|
||||
#include "starkernel/kmalloc.h"
|
||||
#include "starkernel/pmm.h"
|
||||
#include "starkernel/console.h"
|
||||
#include "starkernel/log.h" /* log_message() -- stadium_dispatch()'s own trace, LOG_DEBUG */
|
||||
#include "starkernel/hal/hal.h"
|
||||
#include "starkernel/q48_16.h" /* Q48_ONE -- item 4.1's reservoir starts each VM's quota at 1.0 */
|
||||
#include "vm.h" /* VM_MEMORY_SIZE -- the per-VM footprint stadium_max_vm_count() budgets against */
|
||||
@@ -366,33 +367,36 @@ uint8_t *stadium_header_bitmap(void) {
|
||||
* integration of any kind exists yet (FABRIC-2.md §B).
|
||||
*/
|
||||
void stadium_dispatch(size_t cell_index, StadiumBehaviour behaviour) {
|
||||
console_puts("Stadium: dispatch cell=");
|
||||
console_put_u64((uint64_t)cell_index);
|
||||
console_puts(" behaviour=");
|
||||
/* 2026-09-22: was an unconditional console_puts()/console_println()
|
||||
* sequence -- the only Stadium trace with no level gating at all,
|
||||
* printing on every single dispatch regardless of log level
|
||||
* (confirmed live: interleaves visibly with ordinary interactive
|
||||
* console sessions). Routed through log_message(LOG_DEBUG, ...)
|
||||
* instead, matching every other diagnostic trace in this codebase --
|
||||
* silent at the default LOG_WARN runtime level, available with
|
||||
* --log-level=debug. */
|
||||
switch (behaviour) {
|
||||
case STADIUM_BEHAVIOUR_MIGRATE: {
|
||||
uint32_t lbn = (uint32_t)stadium_cell_array[cell_index].header.identity;
|
||||
console_puts("MIGRATE lbn=");
|
||||
console_put_u64((uint64_t)lbn);
|
||||
console_println("");
|
||||
log_message(LOG_DEBUG, "Stadium: dispatch cell=%zu behaviour=MIGRATE lbn=%u",
|
||||
cell_index, (unsigned)lbn);
|
||||
blk_flush(lbn);
|
||||
break;
|
||||
}
|
||||
case STADIUM_BEHAVIOUR_DELIVER: {
|
||||
uint64_t msg_idx = stadium_cell_array[cell_index].header.identity;
|
||||
console_puts("DELIVER msg_idx=");
|
||||
console_put_u64(msg_idx);
|
||||
console_println("");
|
||||
log_message(LOG_DEBUG, "Stadium: dispatch cell=%zu behaviour=DELIVER msg_idx=%llu",
|
||||
cell_index, (unsigned long long)msg_idx);
|
||||
break;
|
||||
}
|
||||
case STADIUM_BEHAVIOUR_EXPIRE:
|
||||
console_println("EXPIRE (stub)");
|
||||
log_message(LOG_DEBUG, "Stadium: dispatch cell=%zu behaviour=EXPIRE (stub)",
|
||||
cell_index);
|
||||
break;
|
||||
case STADIUM_BEHAVIOUR_COOL: {
|
||||
uint64_t identity = stadium_cell_array[cell_index].header.identity;
|
||||
console_puts("COOL identity=");
|
||||
console_put_u64(identity);
|
||||
console_println("");
|
||||
log_message(LOG_DEBUG, "Stadium: dispatch cell=%zu behaviour=COOL identity=%llu",
|
||||
cell_index, (unsigned long long)identity);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -677,7 +677,12 @@ void vm_tick_inference_engine(VM* vm)
|
||||
/* 3. Validate outputs */
|
||||
if (!inference_outputs_validate(vm->last_inference_outputs))
|
||||
{
|
||||
log_message(LOG_WARN,
|
||||
/* 2026-09-22: downgraded from LOG_WARN -- fires routinely
|
||||
* during normal operation and the runtime self-recovers
|
||||
* every time (the whole point of "ignoring results"), so it
|
||||
* does not warrant default-visible attention. Still
|
||||
* available with --log-level=info/debug. */
|
||||
log_message(LOG_INFO,
|
||||
"INFERENCE: Output validation failed, ignoring results");
|
||||
}
|
||||
|
||||
|
||||
+7
-1
@@ -674,7 +674,13 @@ void vm_tick_inference_engine(VM* vm)
|
||||
/* 3. Validate outputs */
|
||||
if (!inference_outputs_validate(vm->last_inference_outputs))
|
||||
{
|
||||
log_message(LOG_WARN,
|
||||
/* 2026-09-22: downgraded from LOG_WARN, matching the kernel
|
||||
* copy of this logic (src/starkernel/vm/vm_runtime.c) --
|
||||
* fires routinely during normal operation and the runtime
|
||||
* self-recovers every time (the whole point of "ignoring
|
||||
* results"), so it does not warrant default-visible
|
||||
* attention. Still available with --log-level=info/debug. */
|
||||
log_message(LOG_INFO,
|
||||
"INFERENCE: Output validation failed, ignoring results");
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user