Update btop

This commit is contained in:
Raven Scott
2026-04-05 17:07:57 -04:00
parent 7c6b77ed62
commit f3c8ef1fc5
33 changed files with 9771 additions and 1090 deletions
+3 -2
View File
@@ -4,14 +4,15 @@ Authoritative **version alignment** with protocol and telemetry schema numbers l
## Maintenance
- **`baretop` snapshot**: **`ctx.bareOsReadBareTopSnapshot({ lite: true })`** returns a reduced **`files`** map (see **`BARE_TOP_SNAPSHOT_LITE_ENTRIES`** in **`packages/bare-os-coreutils/lib/baretop-snapshot.js`**). **`metrics_live`** JSON uses **`schema: 4`** with embedded **`processTable`** when present; kernel counters include optional **`vfs.readfile.samples`** ( **`BARE_OS_VFS_READ_METRICS`** ), **`initd.unit_failed_final`**, and **`shell.pipeline_last_stages`** gauge from the shell.
- **`baretop` snapshot**: **`ctx.bareOsReadBareTopSnapshot({ lite: true })`** returns a reduced **`files`** map (see **`BARE_TOP_SNAPSHOT_LITE_ENTRIES`** in **`packages/bare-os-coreutils/lib/baretop-snapshot.js`**). Full batch includes **`securityPosture`** → **`/proc/bare_os/security_posture.json`**. **`metrics_live`** JSON uses **`schema: 4`** with embedded **`processTable`** when present; kernel counters include optional **`vfs.readfile.samples`** ( **`BARE_OS_VFS_READ_METRICS`** ), **`initd.unit_failed_final`**, and **`shell.pipeline_last_stages`** gauge from the shell.
- **`/proc/bare_os/net_summary.json`**: **`schemaVersion` 2** adds scalar **`replicationQueueDepth`**, firewall session totals, optional **`BARE_OS_BSD_SOCKET_BRIDGE_STATS_JSON`** merge into **`bsdSocketGuestBridge`**; **`peer_firewall_stats`** field alignment documented in **`bare-os-protocol`** channel handler.
- **Host filesystem**: first-party booter and seeder sources use **`import … from '#host-fs'`** / **`#host-path`** (and seeder **`#host-fs-promises`**) so Bare resolves **`bare-fs`** / **`bare-path`** and Node resolves the built-in **`fs`** / **`path`** modules via the default **`imports`** condition. **`bare-fs`** is a direct **`dependencies`** entry of **`bare-os-booter`**. CI: **`scripts/verify-pear-no-static-node-import.mjs`** rejects bare **`fs`** / **`path`** specifiers.
- **POSIX / proc**: **`/proc/bare_os/syscalls.json`** schema **11** with **`susv4Refs`** on **`opsDetail`**, **`posixXsh` schema 3**, **`socketMsgSurface` schema 5** (`logicalScmRightsOnSend`); includes **`posix_fadvise`** simulated, **`fdModel`**, **`errnoHints`**; JSON text **cached** until **`vfs.bareOsClearWarmReadCaches`**. **`/proc/bare_os/process_table.json`** schema **7**; **`/proc/bare_os/protomux.json`** wire text schema **2**; **`/dev/shm`** in-memory named segments. **`/proc/bare_os/security_posture.json`** — **`blindRelayPosture`**, **`blindPeeringOperatorSketch`** env gate pointers; **`vaultCryptoPrimitives`**, **`bareCryptoReportedVersion`**, **`peerAdmission`**. **`/proc/bare_os/boot_budget_summary.json`** mirrors kernel **`/run/bare-os/boot-budget-summary.json`**. **`/proc/bare_os_features`**: **`protomuxAppChannel`**, optional **`protomuxCapChannel`**, **`pearIpcConservativeAdvertisement`**. Protocol export **`BARE_OS_POSIX_PROFILE_*`**.
- **Blind-relay / pairing / geo proc** (default): **`bareOsProcBlindPeerRelayHintsMinimal`** returns **schema 1** with **`operatorRedacted: true`**. The legacy export **`bareOsProcBlindPeerRelayHintsStub`** was removed; use **`bareOsProcBlindPeerRelayHintsMinimal`** only.
- **Vendored bundles**: post-esbuild **`scripts/sanitize-bare-bundles.mjs`** (from **`bare-os-bare-libs/build.mjs`**) strips CI-forbidden markers and replaces **`node:`** requires in **`bareDev.js`** with **`bare-*`** modules.
- **Boot hooks (naming)**: canonical **`bareOsRegisterBootStepHook`**, **`bareOsInvokeBootStepHooks`**, **`bareOsEmitBareBootStepHint`**; legacy **`*BootPhase*`** methods remain thin wrappers (**no `bareOsCtxApiVersion` bump**). See [docs/reference/naming-alias-matrix.md](../../docs/reference/naming-alias-matrix.md).
- **Pear / Bare**: [`lib/kernel-runner.js`](lib/kernel-runner.js) must not **static**-import **`node:module`** (Bares resolver cannot load **`node:`** builtins from a **`pear://`** bundle). Optional **`BARE_OS_BIN_WORKER_OFFLOAD`** now obtains **`createRequire`** via **dynamic** **`import('bare-module')`** when running outside Node.
- **`baretop`**: optional **`ctx.bareOsReadBareTopSnapshot()`** in [`index.js`](index.js) returns **`{ atMs, files }`** with the same keys as **`BARE_TOP_SNAPSHOT_PROC_ENTRIES`** in **`packages/bare-os-coreutils/lib/baretop-snapshot.js`** — keep those lists in sync when adding operator **`/proc/bare_os`** nodes.
- **`baretop`**: optional **`ctx.bareOsReadBareTopSnapshot()`** in [`index.js`](index.js) returns **`{ atMs, files, metricsLiveText }`** (**`metricsLiveText`** = coalesced **`metrics_live`** JSON string) with the same **`files`** keys as **`BARE_TOP_SNAPSHOT_PROC_ENTRIES`** in **`packages/bare-os-coreutils/lib/baretop-snapshot.js`** — keep those lists in sync when adding operator **`/proc/bare_os`** nodes.
- **hrpc allowlist**: shared parser in [`lib/bare-os-hrpc-allowlist.js`](lib/bare-os-hrpc-allowlist.js); **`ctx.bareOsHrpcRequest`** and **`ctx.bareOsHrpcAllowlistProbe`** stay aligned. Host passthrough copies **`BARE_OS_HRPC_ALLOWLIST_JSON`**, **`BARE_OS_CORESTORE_SNAPSHOT_WORKFLOW_JSON`**, **`BARE_OS_BLIND_RELAY_TOPOLOGY_JSON`**, **`BARE_OS_MIRROR_DRIVE_COMPOSITION_HINT_JSON`**, **`BARE_OS_REPLICATION_PLAN_JSON`**, and pear-doctor env keys into session env.
- **Snapshot hints**: **`ctx.bareOsReadSnapshotHintsJson()`** merges **`BARE_OS_CORESTORE_SNAPSHOT_WORKFLOW_JSON`** like **`/proc/bare_os/snapshot_hints.json`**.
+81 -8
View File
@@ -2555,8 +2555,71 @@ async function executeKernel(disk, store, swarm, initSource) {
seed && typeof seed === 'object' && 'error' in seed
? String(/** @type {{ error?: unknown }} */ (seed).error)
: null
/** Seeder `peer_firewall_stats` merges defaults with JSON from env (see bare-os-protocol channel.js bare_os.peer_firewall_stats). */
const repQ = disk.seedReplicationQueue
const repQObj =
repQ && typeof repQ === 'object'
? /** @type {Record<string, unknown>} */ (repQ)
: null
const replicationQueueDepth = repQObj
? (() => {
const n =
repQObj.depth ??
repQObj.pending ??
repQObj.pendingCount ??
repQObj.length ??
repQObj.size
if (typeof n === 'number' && Number.isFinite(n)) return Math.floor(n)
if (Array.isArray(repQObj.queue)) return repQObj.queue.length
if (Array.isArray(repQObj.items)) return repQObj.items.length
return null
})()
: null
const fw = disk.seedPeerFirewallStats
const fwO =
fw && typeof fw === 'object'
? /** @type {Record<string, unknown>} */ (fw)
: null
const peerFirewallAcceptedTotal =
typeof fwO?.acceptedSessionCount === 'number'
? fwO.acceptedSessionCount
: null
const peerFirewallRejectedTotal =
typeof fwO?.rejectedSessionCount === 'number'
? fwO.rejectedSessionCount
: null
const peerFirewallInboundTotal =
typeof fwO?.inboundSessionCount === 'number'
? fwO.inboundSessionCount
: null
const peerFirewallOutboundTotal =
typeof fwO?.outboundSessionCount === 'number'
? fwO.outboundSessionCount
: null
const bsdBridgeBase = {
schema: 1,
policyEnv: 'BARE_OS_BSD_SOCKET_POLICY',
note: 'POSIX-like sockets for guests map to UDX / bare-tcp helpers; see handbook networking gaps.'
}
let bsdSocketGuestBridge = bsdBridgeBase
const bsdStatsRaw = String(
shellEnv.BARE_OS_BSD_SOCKET_BRIDGE_STATS_JSON || ''
).trim()
if (bsdStatsRaw) {
try {
const j = JSON.parse(bsdStatsRaw)
if (j && typeof j === 'object')
bsdSocketGuestBridge = { ...bsdBridgeBase, .../** @type {object} */ (j) }
} catch {
bsdSocketGuestBridge = {
...bsdBridgeBase,
error: 'invalid BARE_OS_BSD_SOCKET_BRIDGE_STATS_JSON'
}
}
}
return `${JSON.stringify({
schema: 1,
schemaVersion: 2,
topicHex: b4a.toString(topicKey(), 'hex'),
peerCount: disk.peers?.size ?? 0,
seedHandshakeError: capErr,
@@ -2564,6 +2627,11 @@ async function executeKernel(disk, store, swarm, initSource) {
seed && typeof seed === 'object' && !('error' in seed)
? seed.role
: null,
replicationQueueDepth,
peerFirewallAcceptedTotal,
peerFirewallRejectedTotal,
peerFirewallInboundTotal,
peerFirewallOutboundTotal,
replicationQueue:
disk.seedReplicationQueue &&
typeof disk.seedReplicationQueue === 'object'
@@ -2622,11 +2690,7 @@ async function executeKernel(disk, store, swarm, initSource) {
return { error: 'invalid BARE_OS_HYPERSWARM_TUNING_JSON' }
}
})(),
bsdSocketGuestBridge: {
schema: 1,
policyEnv: 'BARE_OS_BSD_SOCKET_POLICY',
note: 'POSIX-like sockets for guests map to UDX / bare-tcp helpers; see handbook networking gaps.'
},
bsdSocketGuestBridge,
atMs: Date.now()
})}\n`
},
@@ -7692,7 +7756,7 @@ async function executeKernel(disk, store, swarm, initSource) {
/**
* Batch-read `/proc/bare_os/*` mirrors for baretop(1). Keys must stay aligned with
* `BARE_TOP_SNAPSHOT_PROC_ENTRIES` in packages/bare-os-coreutils/lib/baretop-snapshot.js.
* @returns {Promise<{ atMs: number, files: Record<string, string> }>}
* @returns {Promise<{ atMs: number, files: Record<string, string>, metricsLiveText?: string }>}
*/
async bareOsReadBareTopSnapshot(opts) {
const atMs = Date.now()
@@ -7747,7 +7811,8 @@ async function executeKernel(disk, store, swarm, initSource) {
['processTable', '/proc/bare_os/process_table.json'],
['syscalls', '/proc/bare_os/syscalls.json'],
['metricsProm', '/proc/bare_os/metrics.prom'],
['protomuxWire', '/proc/bare_os/protomux.json']
['protomuxWire', '/proc/bare_os/protomux.json'],
['securityPosture', '/proc/bare_os/security_posture.json']
]
const liteEntries = [
['index', '/proc/bare_os/index.json'],
@@ -7776,7 +7841,15 @@ async function executeKernel(disk, store, swarm, initSource) {
})
)
}
return { atMs, files }
let metricsLiveText = ''
try {
if (typeof this.procBareOsMetricsLiveText === 'function') {
metricsLiveText = this.procBareOsMetricsLiveText()
}
} catch {
/* ignore */
}
return { atMs, files, metricsLiveText }
},
/**
* Register `/run/bare-os/virtual/<name>` reader (cap-gated: `virtualRegisterFiles`).
+7 -1
View File
@@ -2,4 +2,10 @@
## Unreleased
- **`baretop` / `btop`**: Scrollable overview tab with pinned HUD (activity sparklines, session summary, delegate histogram); compact **`metrics_live`** panels (replication, kernel counters with delta mode, warm cache, IPC, boot budget, swarm lifecycle, initd readiness, worker hints, protomux collaboration); capped flatten and delegate inflight table; health score breakdown (**`BARE_TOP_HEALTH_DETAIL`**); optional lite snapshot batch (**`BARE_TOP_SNAPSHOT_LITE`**); export metadata + **`BARE_TOP_EXPORT_REDACT`**; process tab **TIME** column, **F6**/**S** sort, **V** tree view, state-based row color, optional mouse wheel/click; many layout/telemetry env toggles documented in **`src/baretop.js`** and **`man baretop`**.
- **`baretop` / `btop`**: **`BARE_TOP_FETCH_EWMA=1`** lowers parallel **`/proc`** batch concurrency when the previous fetch-time EWMA is high; **`BARE_TOP_SCROLL_REGION=1`** sets an experimental DECSTBM region around the process list (reset each frame). Sample fixture **`baretop-sample-metrics.json`** includes **`netSummaryNestedExample`** for nested net UI tests.
- **`baretop` / `btop`**: Network tab formats nested **`net_summary.json`** ( **`replicationQueue`**, **`peerFirewallStats`**, **`bsdSocketGuestBridge`** ) without **`[object Object]`**; optional **`BARE_TOP_NET_FILTER`** applies **`/`** on that tab; wide two-column merge when **`BARE_TOP_LAYOUT=even`** and cols ≥ 100; net byte-delta spark from iface counters. Overview gains **nethealth**, **diskstats**, **syscalls** summary, **delegate_red**, **security_posture**, **boot_budget_summary**, **peer health**, **capabilities diff**, **extensions**, **git** deltas (with **`d`** + prev snap), larger kernel counter sample, **IPC** backpressure line from proc JSON, **session wall** spark, **worker/sandbox** hints, **readErrPaths** listing, **MemUsed** bar + swap line + logical CPU count in HUD; process columns **NI**/**PRI**/**CPU%** when present, **`BARE_TOP_CMD_ELLIPSIS_MIDDLE`**, extended sort keys, tree ancestor dimming + ASCII **`+--`**, **x** toggles initd raw JSON, features flattened table, catalog version line, pear pack depth **8**, host-tab worker/sandbox one-liners, mouse click-scroll on list tabs **29**. Snapshot batch adds **`security_posture.json`**; **`readErrPaths`** on failed **`readFile`** paths.
- **`baretop` / `btop`**: Health score no longer penalizes operational **`replicationLive.stallHint`** values (**`no_peers`**, **`length_unavailable`**, **`ok`**); delegate inflight penalties use active (count>0) kinds with a combined cap; optional **`replicationStall: true`** forces the stall penalty. **`bareOsReadBareTopSnapshot`** may return **`metricsLiveText`** (same payload as **`metrics_live.json`**) to avoid an extra read when the booter builds both. **`BARE_TOP_INCREMENTAL=2`** experimental CSI line-diff redraws; **`BARE_TOP_LAYOUT_AUTO`**, **F2** setup overlay, **F3**/**F4** process row jump, **F10** quit; overview **limits** / **p2p** sections, network tab interface sort, tab intro lines, filter-match row highlight, **`layoutVersion` `baretop-ui-3`**. Default **`BARE_TOP_FETCH_CONCURRENCY`** **8**. QA script **`scripts/qa-baretop-health.mjs`**.
- **`baretop` / `btop`** (prior): Scrollable overview tab with pinned HUD (activity sparklines, session summary, delegate histogram); compact **`metrics_live`** panels (replication, kernel counters with delta mode, warm cache, IPC, boot budget, swarm lifecycle, initd readiness, worker hints, protomux collaboration); capped flatten and delegate inflight table; health score breakdown (**`BARE_TOP_HEALTH_DETAIL`**); optional lite snapshot batch (**`BARE_TOP_SNAPSHOT_LITE`**); export metadata + **`BARE_TOP_EXPORT_REDACT`**; process tab **TIME** column, **F6**/**S** sort, **V** tree view, state-based row color, optional mouse wheel/click; many layout/telemetry env toggles documented in **`src/baretop.js`** and **`man baretop`**.
+1 -1
View File
@@ -39,7 +39,7 @@ Or `node packages/bare-os-coreutils/build.mjs`.
**`edit`** is a full-screen TTY buffer editor (syntax highlighting, search, save). **`nano`** is built from the same **`src/edit.js`** with the same **`lib/edit-*.js`** preamble; **`/bin/nano`** exists for familiarity, and the stock shell alias **`nano``edit`** routes **`nano`** to that utility (see **`packages/bare-os-booter/lib/shell.js`**). Both require a real TTY (**`stdout.isTTY`**).
**`baretop`** is the stock **`top`** alias target: a multi-tab TTY dashboard over **`/proc/bare_os/*`** (session metrics, Pear, replication, initd, scrollable overview, process tree/sort, optional mouse, …). **`btop`** is the same bundle as **`/bin/baretop`** (short name); the stock shell alias **`btop``baretop`** matches **`nano``edit`**. The booter may expose **`ctx.bareOsReadBareTopSnapshot`** (optional **`{ lite: true }`**) to batch-read the same mirrors **`baretop`** would **`vfs.readFile`** individually. Rebuild **`kernel/bin/baretop`** and **`kernel/bin/btop`** with **`node packages/bare-os-coreutils/build.mjs`** after editing **`lib/baretop-snapshot.js`**, **`lib/baretop-ui-helpers.js`**, or **`lib/baretop-tui.js`**.
**`baretop`** is the stock **`top`** alias target: a multi-tab TTY dashboard over **`/proc/bare_os/*`** (session metrics, Pear, replication, initd, scrollable overview, process tree/sort, optional mouse, …). **`btop`** is the same bundle as **`/bin/baretop`** (short name); the stock shell alias **`btop``baretop`** matches **`nano``edit`**. The booter may expose **`ctx.bareOsReadBareTopSnapshot`** (optional **`{ lite: true }`**) to batch-read the same mirrors **`baretop`** would **`vfs.readFile`** individually; the return value can include **`metricsLiveText`** so **`metrics_live.json`** need not be read twice. **`BARE_TOP_INCREMENTAL=2`** enables experimental line-diff redraws; **`BARE_TOP_LAYOUT_AUTO=1`** picks a wide split on large terminals. Rebuild **`kernel/bin/baretop`** and **`kernel/bin/btop`** with **`node packages/bare-os-coreutils/build.mjs`** after editing **`lib/baretop-snapshot.js`**, **`lib/baretop-ui-helpers.js`**, or **`lib/baretop-tui.js`**.
**`ls`** prepends **[`bare-os-lscolors`](../bare-os-lscolors/bare-os-lscolors.js)** for **`LS_COLORS`** / dircolors parsing. **`dircolors`** and **`theme`** integrate with the booters **`bare-os-theme-presets.js`** (see [docs/themes/README.md](../../docs/themes/README.md)).
@@ -1,5 +1,8 @@
/** Fetch /proc and ctx snapshots for /bin/baretop (preamble; no import). */
/** EWMA of last fetch wall time (ms); used when `BARE_TOP_FETCH_EWMA=1`. */
var bareTopFetchEwmaMs = -1
/**
* Keep in sync with `bareOsReadBareTopSnapshot` path list in packages/bare-os-booter/index.js
* @type {readonly [string, string][]}
@@ -49,7 +52,8 @@ var BARE_TOP_SNAPSHOT_PROC_ENTRIES = [
['processTable', '/proc/bare_os/process_table.json'],
['syscalls', '/proc/bare_os/syscalls.json'],
['metricsProm', '/proc/bare_os/metrics.prom'],
['protomuxWire', '/proc/bare_os/protomux.json']
['protomuxWire', '/proc/bare_os/protomux.json'],
['securityPosture', '/proc/bare_os/security_posture.json']
]
/** Subset for BARE_TOP_SNAPSHOT_LITE=1 — keep keys subset of full list above. */
@@ -115,15 +119,32 @@ async function bareTopReadProc(ctx, path) {
* @param {number} concurrency
* @returns {Promise<Record<string, string>>}
*/
async function bareTopReadProcBatch(ctx, entries, concurrency) {
/**
* @param {Record<string, unknown>} ctx
* @param {readonly [string, string][]} entries
* @param {number} concurrency
* @param {string[] | null} [errPaths] push failed paths (optional)
*/
async function bareTopReadProcBatch(ctx, entries, concurrency, errPaths) {
/** @type {Record<string, string>} */
const out = {}
const vfs = ctx.vfs
const conc = Math.max(1, Math.min(16, concurrency | 0) || 6)
for (let i = 0; i < entries.length; i += conc) {
const slice = entries.slice(i, i + conc)
await Promise.all(
slice.map(async ([key, path]) => {
out[key] = await bareTopReadProc(ctx, path)
if (!vfs || typeof vfs.readFile !== 'function') {
out[key] = ''
return
}
try {
const buf = await vfs.readFile(path)
out[key] = bareTopBufToString(buf, ctx.b4a)
} catch {
out[key] = ''
if (errPaths) errPaths.push(path)
}
})
)
}
@@ -172,9 +193,16 @@ function bareTopHealthScore(m, peers, readErr) {
}
/**
* Subtractive score from 100: healthy sessions read ~95100; issues pull it down.
* Weights: read/metrics gaps, delegate inflight keys + sum, replication stall,
* boot budgets, initd failures, peer sanity / mismatch.
* Subtractive score from 100 (penalty table):
* - read_err: -28
* - no_metrics: -22
* - delegate_inflight: capped combined from active keys (count>0) + total inflight sum; max -12
* - replication stall: -20 when stallHint is a fault token OR replicationStall===true;
* benign hints no_peers | length_unavailable | ok do not penalize (operational, not fault)
* - boot_cold exceeded: -12; boot_stdlib exceeded: -12
* - initd_readiness.failed: up to -18; kernel initd.unit_failed_final: up to -10
* - peer_mismatch (replication.peerCount vs metrics peers): -8 when both finite and |Δ|>2
* - peers_invalid (peers<0): -5
* @param {Record<string, unknown> | null} m
* @param {number} peers
* @param {string | null | undefined} readErr
@@ -205,20 +233,28 @@ function bareTopHealthScoreDetail(m, peers, readErr) {
if (delI != null && typeof delI === 'object') {
const o = /** @type {Record<string, unknown>} */ (delI)
const keys = Object.keys(o)
const n = keys.length
const penK = Math.min(14, n * 2)
if (penK > 0) {
score -= penK
parts.push('inflight_k_' + n + '=-' + penK)
}
let nActive = 0
let sum = 0
for (let i = 0; i < keys.length; i++) {
sum += Math.max(0, Number(o[keys[i]]) || 0)
const v = Math.max(0, Number(o[keys[i]]) || 0)
sum += v
if (v > 0) nActive++
}
const penS = Math.min(28, sum * 3)
if (penS > 0) {
score -= penS
parts.push('inflight_sum_' + sum + '=-' + penS)
const penK = Math.min(10, nActive * 2)
const penS = Math.min(20, sum * 2)
const inflightCap = 12
const inflightTotal = Math.min(inflightCap, penK + penS)
if (inflightTotal > 0) {
score -= inflightTotal
parts.push(
'inflight_-' +
inflightTotal +
'(activeKinds=' +
nActive +
',sum=' +
sum +
')'
)
}
}
@@ -226,21 +262,31 @@ function bareTopHealthScoreDetail(m, peers, readErr) {
live.replicationLive && typeof live.replicationLive === 'object'
? /** @type {Record<string, unknown>} */ (live.replicationLive)
: null
const stallExplicit =
rep && rep.replicationStall === true ? true : false
const hintRaw = rep && rep.stallHint
if (hintRaw != null) {
const benignStallHints = new Set([
'',
'ok',
'no_peers',
'length_unavailable',
'0',
'false',
'none',
'off',
'null',
'undefined'
])
if (stallExplicit) {
const pen = 20
score -= pen
parts.push('replication_stall_flag=-' + pen)
} else if (hintRaw != null) {
const hs = String(hintRaw).trim().toLowerCase()
if (
hs &&
hs !== '0' &&
hs !== 'false' &&
hs !== 'none' &&
hs !== 'off' &&
hs !== 'null' &&
hs !== 'undefined'
) {
if (hs && !benignStallHints.has(hs)) {
const pen = 20
score -= pen
parts.push('stall=-' + pen)
parts.push('stall_hint=-' + pen + '(' + hs + ')')
}
}
@@ -284,7 +330,14 @@ function bareTopHealthScoreDetail(m, peers, readErr) {
}
}
if (rep && typeof rep.peerCount === 'number' && Number.isFinite(peers)) {
if (
rep &&
typeof rep.peerCount === 'number' &&
Number.isFinite(rep.peerCount) &&
rep.peerCount >= 0 &&
Number.isFinite(peers) &&
peers >= 0
) {
if (Math.abs(rep.peerCount - peers) > 2) {
score -= 8
parts.push('peer_mismatch=-8')
@@ -341,8 +394,10 @@ async function bareTopFetchSnapshot(ctx) {
ctx.env && typeof ctx.env === 'object'
? /** @type {Record<string, string>} */ (ctx.env)
: {}
const concRaw = parseInt(env.BARE_TOP_FETCH_CONCURRENCY || '6', 10)
const concurrency = Number.isFinite(concRaw) ? concRaw : 6
const concRaw = parseInt(env.BARE_TOP_FETCH_CONCURRENCY || '8', 10)
const concurrency = Number.isFinite(concRaw) ? concRaw : 8
const fetchEwmaOn =
env.BARE_TOP_FETCH_EWMA === '1' || env.BARE_TOP_FETCH_EWMA === 'true'
const snapshotLite =
env.BARE_TOP_SNAPSHOT_LITE === '1' ||
env.BARE_TOP_SNAPSHOT_LITE === 'true'
@@ -353,6 +408,8 @@ async function bareTopFetchSnapshot(ctx) {
/** @type {Record<string, string>} */
let fileTexts = {}
let fastAtMs = 0
/** @type {Record<string, unknown> | null} */
let metricsLiveFromSnap = null
try {
if (typeof ctx.bareOsReadBareTopSnapshot === 'function') {
@@ -370,20 +427,41 @@ async function bareTopFetchSnapshot(ctx) {
}
const am = o.atMs
if (typeof am === 'number' && Number.isFinite(am)) fastAtMs = am
const mlRaw = o.metricsLiveText
if (typeof mlRaw === 'string' && mlRaw.trim()) {
const mp = bareTopJsonParse(mlRaw)
if (mp && typeof mp === 'object') {
metricsLiveFromSnap = /** @type {Record<string, unknown>} */ (mp)
}
}
}
}
} catch (e) {
readErr = (e && /** @type {{ message?: string }} */ (e).message) || String(e)
}
/** @type {string[]} */
const readErrPaths = []
if (Object.keys(fileTexts).length === 0) {
fileTexts = await bareTopReadProcBatch(ctx, procEntryList, concurrency)
let useConc = concurrency
if (fetchEwmaOn && bareTopFetchEwmaMs >= 0) {
const e = bareTopFetchEwmaMs
if (e > 900) useConc = Math.max(2, concurrency - 3)
else if (e > 500) useConc = Math.max(2, concurrency - 2)
else if (e > 280) useConc = Math.max(2, concurrency - 1)
}
fileTexts = await bareTopReadProcBatch(
ctx,
procEntryList,
useConc,
readErrPaths
)
}
const atMs = fastAtMs || Date.now()
/** @type {Record<string, unknown> | null} */
let metricsLive = null
let metricsLive = metricsLiveFromSnap
/** @type {Record<string, unknown> | null} */
let resources = null
/** @type {Record<string, unknown> | null} */
@@ -484,14 +562,31 @@ async function bareTopFetchSnapshot(ctx) {
const loadavgLine = (await bareTopReadProc(ctx, '/proc/loadavg')).split('\n')[0]?.trim() || ''
let cpuLine = ''
let cpuCoreCount = 0
const cpuRaw = await bareTopReadProc(ctx, '/proc/cpuinfo')
for (const line of cpuRaw.split('\n')) {
if (line.startsWith('model name') || line.startsWith('Model')) {
cpuLine = line.replace(/^[^:]+:\s*/, '').trim().slice(0, 72)
break
}
const L = line.trim().toLowerCase()
if (L.startsWith('processor') && L.includes(':')) cpuCoreCount++
}
if (!cpuCoreCount) {
const m = cpuRaw.match(/^processor\s*:/gim)
if (m) cpuCoreCount = m.length
}
let swapinfoLine = ''
for (const line of memRaw.split('\n')) {
const L = line.trim()
if (L.startsWith('SwapTotal:') || L.startsWith('SwapFree:')) {
swapinfoLine = swapinfoLine ? swapinfoLine + ' ' + L : L
}
}
const diskstatsRaw = await bareTopReadProc(ctx, '/proc/diskstats')
const diskstatsLine = diskstatsRaw.split('\n')[0]?.trim() || ''
const hostOs = bareTopParsedFile(fileTexts, 'hostOs')
const metaAt =
metricsLive && typeof metricsLive.atMs === 'number' ? metricsLive.atMs : atMs
@@ -514,6 +609,10 @@ async function bareTopFetchSnapshot(ctx) {
}
const fetchWallMs = Date.now() - fetchStart
bareTopFetchEwmaMs =
bareTopFetchEwmaMs < 0
? fetchWallMs
: bareTopFetchEwmaMs * 0.82 + fetchWallMs * 0.18
const peersN = Number(metricsLive && metricsLive.peers) || 0
const healthD = bareTopHealthScoreDetail(metricsLive, peersN, readErr)
@@ -524,12 +623,16 @@ async function bareTopFetchSnapshot(ctx) {
initdGraph,
netSummary,
meminfoLine,
swapinfoLine,
loadavgLine,
cpuLine,
cpuCoreCount,
diskstatsLine,
hostOs,
atMs,
metaAtMs: metaAt,
readErr,
readErrPaths,
fileTexts,
extra,
fairnessSnapshot,
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
@@ -5,17 +5,25 @@
"synopsis": [
"baretop [OPTION]... [OPERAND]..."
],
"description": "Full-screen terminal dashboard (htop-inspired) over /proc/bare_os/*, metrics_live, and optional ctx fast paths. Logical process PIDs from process_table.json — not host OS PIDs. Overview scrolls with a pinned HUD (sparklines, delegates). BARE_TOP_OVERVIEW_COMPACT and BARE_TOP_OVERVIEW_SECTIONS tune sections; BARE_TOP_LAYOUT=even enables a wide split. Processes: sort pid|name|state|time (BARE_TOP_PROC_SORT, F6/S, </>), tree (V), filter (/), optional BARE_TOP_MOUSE. See src/baretop.js --help for the full environment list (BARE_TOP_SNAPSHOT_LITE, BARE_TOP_EXPORT_REDACT, BARE_TOP_HEALTH_DETAIL, …).",
"description": "Full-screen terminal dashboard (htop-inspired) over /proc/bare_os/*, metrics_live, and optional ctx fast paths. Logical process PIDs from process_table.json — not host OS PIDs. Overview scrolls with a pinned HUD (sparklines, delegates) and extra sections (network summary line, diskstats, syscalls summary, security_posture, boot_budget_summary, peer health, capabilities diff, extensions, git deltas in delta mode). BARE_TOP_OVERVIEW_COMPACT and BARE_TOP_OVERVIEW_SECTIONS tune sections. Network tab formats nested net_summary objects (replicationQueue, peerFirewallStats, bsdSocketGuestBridge). BARE_TOP_INCREMENTAL=2 builds a full text frame each tick but patches only changed terminal lines. See src/baretop.js --help for the full environment list.",
"options": [],
"environment": [
"BARE_TOP_INTERVAL_MS — refresh period (ms).",
"BARE_TOP_SNAPSHOT_LITE=1 — smaller bareOsReadBareTopSnapshot batch.",
"BARE_TOP_OVERVIEW_COMPACT=1 — hide low-priority overview sections.",
"BARE_TOP_OVERVIEW_SECTIONS — comma list of section tokens.",
"BARE_TOP_PROC_SORT — pid | name | state | time.",
"BARE_TOP_MOUSE=1 — SGR mouse (wheel; row click on processes tab).",
"BARE_TOP_PROC_SORT — pid | name | state | time | nice | pri | cpu.",
"BARE_TOP_NET_FILTER=1 — / filter applies on network tab.",
"BARE_TOP_CMD_ELLIPSIS_MIDDLE=1 — middle-ellipsis long process names.",
"BARE_TOP_MOUSE=1 — SGR mouse (wheel; row click processes; click-scroll other list tabs).",
"BARE_TOP_EXPORT_REDACT=1 — omit fileTexts from JSON export.",
"BARE_TOP_HEALTH_DETAIL=1 — show health score penalty breakdown."
"BARE_TOP_HEALTH_DETAIL=1 — show health score penalty breakdown.",
"BARE_TOP_INCREMENTAL=2 — line-diff terminal output (layout still computed each tick).",
"BARE_TOP_DEBUG_TIMINGS=1 — throttled fetch/draw timing on stderr.",
"BARE_TOP_FETCH_EWMA=1 — reduce parallel /proc batch reads when recent fetches are slow.",
"BARE_TOP_SCROLL_REGION=1 — DECSTBM scroll region around the process list (experimental).",
"BARE_TOP_LAYOUT_AUTO=1 — use even layout when terminal is wide.",
"bareOsReadBareTopSnapshot — may include metricsLiveText to skip a separate metrics_live read."
],
"keywords": [
"baretop",
+1 -1
View File
@@ -6,6 +6,6 @@
"description": "Build JS /bin utilities for bare-operating-system (concat + stage to kernel/)",
"scripts": {
"build": "node ./scripts/ensure-man-pages.mjs && node ./build.mjs",
"test": "node ./test/help-bin-list.test.mjs && node ./test/edit-key-parse.test.mjs && node ./test/edit-teardown.test.mjs && node ./test/baretop-bundle.test.mjs && node ./test/baretop-fixture.test.mjs && node ./test/baretop-ui-helpers.test.mjs && node ./test/posix-test-int-compare.test.mjs && node ./test/posix-utils-edge.test.mjs && node ./test/posix-golden-issue7.test.mjs && node ./test/getconf-pathconf-union-mirror.test.mjs && node ./test/getconf-posix-shm.test.mjs && node ./test/awk-sed-posix-smoke.test.mjs && node ./test/xattr-acl-utils.test.mjs && node ./test/xcu-issue7-sweep.test.mjs && node ./test/expand-tab-stops.test.mjs"
"test": "node ./test/help-bin-list.test.mjs && node ./test/edit-key-parse.test.mjs && node ./test/edit-teardown.test.mjs && node ./test/baretop-bundle.test.mjs && node ./test/baretop-fixture.test.mjs && node ./test/baretop-incremental.test.mjs && node ./test/baretop-ui-helpers.test.mjs && node ./test/posix-test-int-compare.test.mjs && node ./test/posix-utils-edge.test.mjs && node ./test/posix-golden-issue7.test.mjs && node ./test/getconf-pathconf-union-mirror.test.mjs && node ./test/getconf-posix-shm.test.mjs && node ./test/awk-sed-posix-smoke.test.mjs && node ./test/xattr-acl-utils.test.mjs && node ./test/xcu-issue7-sweep.test.mjs && node ./test/expand-tab-stops.test.mjs"
}
}
@@ -0,0 +1,16 @@
#!/usr/bin/env node
/**
* Manual QA checklist for baretop health score (run inside a Bare OS TTY session).
* 1. Run: baretop
* 2. With zero peers and idle delegates, health should read 100 (not stuck at 73).
* 3. Run with: BARE_TOP_HEALTH_DETAIL=1 baretop overview shows penalty breakdown.
* 4. Optional: BARE_TOP_INCREMENTAL=2 baretop stderr with BARE_TOP_DEBUG_TIMINGS=1 may show patchLen < outLen when idle.
* 5. Network tab (tab 4): nested net_summary fields render as lines/JSON no literal [object Object].
* 6. Optional: BARE_TOP_NET_FILTER=1 then / on network tab filters lines.
*/
console.log(`baretop health QA:
- Expect health 100 on single-node idle (operational stallHint no longer penalized).
- Use BARE_TOP_HEALTH_DETAIL=1 to verify breakdown text.
- Use BARE_TOP_DEBUG_TIMINGS=1 to inspect fetchMs / outLen / patchLen.
- Network tab: replicationQueue / peerFirewallStats / bsdSocketGuestBridge should show structured text.
- BARE_TOP_NET_FILTER=1 enables / filter on the network tab.`)
+13 -8
View File
@@ -11,15 +11,19 @@ async function run(ctx, argv) {
'Requires a TTY.\n' +
'\n' +
'Tabs: 1 overview 2 processes 3 initd 4 network 5 features 6 diagnostics\n' +
' 7 operator 8 pear 9 catalog [ ] host 0 keys (F1 help, F5 refresh, F9 signal)\n' +
' 7 operator 8 pear 9 catalog [ ] host 0 keys\n' +
' F1 help F2 setup F3/F4 proc row F5 refresh F9 signal F10 quit\n' +
'\n' +
'Environment:\n' +
' BARE_TOP_INTERVAL_MS Refresh period (default 1000; clamped 25010000)\n' +
' BARE_TOP_UI_MIN_MS Minimum ms between full redraws (0 = off)\n' +
' BARE_TOP_FETCH_CONCURRENCY Parallel /proc reads per batch (default 6)\n' +
' BARE_TOP_SNAPSHOT_LITE Set to 1 for smaller bareOsReadBareTopSnapshot batch\n' +
' BARE_TOP_FETCH_CONCURRENCY Parallel /proc reads per batch (default 8)\n' +
' BARE_TOP_FETCH_EWMA Set to 1 to reduce batch concurrency when recent fetches are slow\n' +
' BARE_TOP_SNAPSHOT_LITE Set to 1 for smaller bareOsReadBareTopSnapshot batch (net_summary still read)\n' +
' BARE_TOP_NET_FILTER Set to 1 so / filter applies on network tab\n' +
' BARE_TOP_CMD_ELLIPSIS_MIDDLE Set to 1 for middle-ellipsis on long process names\n' +
' BARE_TOP_NO_ALTSCREEN Any non-empty value skips alternate-screen mode\n' +
' BARE_TOP_INCREMENTAL Set to 1 to skip full 2J clear (may flicker)\n' +
' BARE_TOP_INCREMENTAL 1 = soft home (no 2J) 2 = line-diff patches (full frame each tick; terminal patched)\n' +
' BARE_TOP_NO_2J_AFTER_FIRST Set to 1 to use soft clear after first full paint\n' +
' BARE_TOP_ASCII_GRAPH Set to 1 for ASCII sparklines\n' +
' BARE_TOP_ASCII_UI Set to 1 for ASCII box/spark fallbacks\n' +
@@ -32,6 +36,7 @@ async function run(ctx, argv) {
' BARE_TOP_COLOR256 Set to 1 to force 256-color bar hints\n' +
' BARE_TOP_VI_KEYS Set to 1 for hjkl focus in vi-style mode\n' +
' BARE_TOP_LAYOUT stacked | even (wide overview split + mini jobs)\n' +
' BARE_TOP_LAYOUT_AUTO Set to 1 to pick even layout when cols >= 100\n' +
' BARE_TOP_FRAMES Set to 1 for left rule on scroll regions\n' +
' BARE_TOP_FULLSCREEN_HIDE_TABS Set to 1 to hide tab strip in fullscreen (f)\n' +
' BARE_TOP_OVERVIEW_COMPACT Set to 1 to hide low-priority overview sections\n' +
@@ -50,11 +55,11 @@ async function run(ctx, argv) {
' BARE_TOP_SCROLL_REGION Set to 1 only with compatible terminals (see help)\n' +
' NO_COLOR Disable ANSI colors\n' +
'\n' +
'Keys: q quit r F5 refresh+burst sp pause . step d delta e export f fullscreen\n' +
' t UTC [ ] tabs arrows scroll / move selection g G top/bottom h F1 help\n' +
'Keys: q F10 quit r F5 refresh+burst sp pause . step d delta e export f fullscreen\n' +
' t UTC [ ] tabs arrows scroll / move selection g G top/bottom h F1 help F2 setup\n' +
' / filter (overview sections, initd, or processes) V tree (processes)\n' +
' F6 S sort menu (processes) <> cycle sort Enter detail k F9 signal\n' +
' Esc closes help or filter\n' +
' F3 F4 next/prev process row F6 S sort menu (processes) <> cycle sort\n' +
' Enter detail k F9 signal Esc closes help, setup, or filter\n' +
'\n' +
'Contributors: /bin bundles cannot use node:crypto or node:module; use ctx.vfs and\n' +
'JSON.parse only. See holepunch-repos/docs/05-BARE-RUNTIME.md (Bare module stack).'
@@ -17,6 +17,10 @@ test('baretop-tui uses alternate screen teardown pattern', async (t) => {
(src.match(/\\x1b\[2J\\x1b\[H/g) || []).length >= 1,
'expected full clear fallback in finally'
)
t.ok(
src.includes('incrementalFrameDiff'),
'expected incremental frame diff gate in tui source'
)
})
test('shipped kernel/bin/baretop includes snapshot + TUI', async (t) => {
@@ -19,6 +19,10 @@ test('fixture metrics_live-shaped JSON parses with expected keys', async (t) =>
t.ok(typeof o.delegateInflight === 'object')
t.ok(o.replicationLive && typeof o.replicationLive === 'object')
t.ok(o.kernelCounters && typeof o.kernelCounters === 'object')
t.ok(
o.netSummaryNestedExample &&
typeof o.netSummaryNestedExample.replicationQueue === 'object'
)
})
test('baretop-snapshot preamble lists batch proc entries', async (t) => {
@@ -29,6 +33,7 @@ test('baretop-snapshot preamble lists batch proc entries', async (t) => {
t.ok(src.includes('bareTopHealthScore'))
t.ok(src.includes('BARE_TOP_SNAPSHOT_LITE_ENTRIES'))
t.ok(src.includes('bootBudgetSummary'))
t.ok(src.includes('security_posture.json'))
})
test('bareTopHealthScore penalizes stall and inflight cardinality', async (t) => {
@@ -49,6 +54,44 @@ test('bareTopHealthScore penalizes stall and inflight cardinality', async (t) =>
t.is(ctx.bareTopHealthScore(good, 2), 100)
})
test('bareTopHealthScore: no_peers + idle delegates is not stuck at 73', async (t) => {
const src = await readFile(snapPath, 'utf8')
const ctx = createContext({})
runInContext(src, ctx)
const idle = {
peers: 0,
delegateInflight: {},
replicationLive: { peerCount: 0, stallHint: 'no_peers' }
}
t.is(ctx.bareTopHealthScore(idle, 0), 100)
const lightInflight = {
peers: 0,
delegateInflight: { http: 1, dns: 0 },
replicationLive: { peerCount: 0, stallHint: 'no_peers' }
}
const s2 = ctx.bareTopHealthScore(lightInflight, 0)
t.ok(s2 >= 90)
t.not(s2, 73)
})
test('bareTopHealthScoreDetail: benign stall hints and replicationStall flag', async (t) => {
const src = await readFile(snapPath, 'utf8')
const ctx = createContext({})
runInContext(src, ctx)
const lenOk = {
peers: 0,
replicationLive: { stallHint: 'length_unavailable', peerCount: 0 }
}
t.is(ctx.bareTopHealthScore(lenOk, 0), 100)
const explicit = {
peers: 1,
replicationLive: { stallHint: 'ok', peerCount: 1, replicationStall: true }
}
t.is(ctx.bareTopHealthScore(explicit, 1), 80)
const d = ctx.bareTopHealthScoreDetail(explicit, 1, null)
t.ok(String(d.breakdown).includes('replication_stall_flag'))
})
test('process_table fixture maps to sorted PID rows via helpers', async (t) => {
const raw = await readFile(processTableFixture, 'utf8')
const pt = JSON.parse(raw)
@@ -0,0 +1,39 @@
import test from 'brittle'
/**
* Mirrors baretop-tui incrementalFrameDiff patch builder (line CUP + EL + line).
* @param {string[]} prevLines
* @param {string[]} nextLines
*/
function bareTopLineDiffPatch(prevLines, nextLines) {
let patch = '\x1b[?25l'
let nch = 0
for (let i = 0; i < nextLines.length; i++) {
if (prevLines[i] !== nextLines[i]) {
nch++
const r = Math.max(1, Math.min(Math.floor(i + 1), 9999))
const c = 1
patch += '\x1b[' + r + ';' + c + 'H' + '\x1b[K' + nextLines[i] + '\r\n'
}
}
patch += '\x1b[?25h'
return { patch, nch }
}
test('incremental line-diff patch is smaller than full frame when one line changes', async (t) => {
const n = 48
const prev = Array.from({ length: n }, (_, i) => 'row-' + i + ' ' + 'x'.repeat(40))
const next = prev.slice()
next[22] = 'row-22 ' + 'CHANGED'.repeat(6)
const full = next.join('\r\n') + '\r\n'
const { patch, nch } = bareTopLineDiffPatch(prev, next)
t.is(nch, 1)
t.ok(
patch.length < full.length,
'expected patch bytes < full frame (' +
patch.length +
' vs ' +
full.length +
')'
)
})
@@ -120,6 +120,91 @@ test('bareTopOverviewLines keeps ASCII section lines within cols', async (t) =>
}
})
test('bareTopNetTabLines sorts interfaces by rx+tx', async (t) => {
const code = await readFile(helpersPath, 'utf8')
const ctx = createContext({})
runInContext(code, ctx)
const lines = ctx.bareTopNetTabLines(
{
interfaces: [
{ name: 'lo', rxBytes: 1, txBytes: 1 },
{ name: 'eth0', rxBytes: 100, txBytes: 50 }
]
},
100
)
t.ok(lines.some((l) => l.includes('interfaces')))
t.ok(lines.some((l) => l.includes('eth0')))
})
test('bareTopNetTabLines expands nested objects (no [object Object])', async (t) => {
const code = await readFile(helpersPath, 'utf8')
const ctx = createContext({})
runInContext(code, ctx)
const raw = await readFile(
join(__dirname, 'fixtures/baretop-net-summary-nested.json'),
'utf8'
)
const net = JSON.parse(raw)
const lines = ctx.bareTopNetTabLines(net, 100, { maxLines: 200 })
const blob = lines.join('\n')
t.ok(!blob.includes('[object Object]'), 'should not stringify objects blindly')
t.ok(blob.includes('replicationQueue'), 'section for queue')
t.ok(blob.includes('peerFirewallStats'), 'section for firewall')
t.ok(blob.includes('bsdSocketGuestBridge'), 'section for bridge')
t.ok(blob.includes('acceptedSessionCount') || blob.includes('10'), 'firewall scalar')
})
test('bareTopNetTabLines respects maxLines cap', async (t) => {
const code = await readFile(helpersPath, 'utf8')
const ctx = createContext({})
runInContext(code, ctx)
const big = { a: 1 }
for (let i = 0; i < 80; i++) big['k' + i] = i
const lines = ctx.bareTopNetTabLines(big, 80, { maxLines: 12 })
t.ok(lines.length <= 12)
t.ok(lines[lines.length - 1].includes('truncated'))
})
test('bareTopSortProcessRows supports nice and cpu keys', async (t) => {
const code = await readFile(helpersPath, 'utf8')
const ctx = createContext({})
runInContext(code, ctx)
const rows = [
{ pid: 1, name: 'a', nice: 0 },
{ pid: 2, name: 'b', nice: 5 }
]
const byNice = ctx.bareTopSortProcessRows(rows, 'nice', true)
t.is(bareTopProcessPidLocal(byNice[0]), 1)
const rows2 = [
{ pid: 1, name: 'a', cpuPct: 10 },
{ pid: 2, name: 'b', cpuPct: 99 }
]
const byCpu = ctx.bareTopSortProcessRows(rows2, 'cpu', false)
t.is(bareTopProcessPidLocal(byCpu[0]), 2)
})
test('bareTopLimitsMergedLines flattens quotas and rlimits', async (t) => {
const code = await readFile(helpersPath, 'utf8')
const ctx = createContext({})
runInContext(code, ctx)
const snap = {
extra: { quotas: { pipe: 8 }, rlimits: { nofile: 1024 } }
}
const lines = ctx.bareTopLimitsMergedLines(snap)
t.ok(lines.some((l) => l.includes('pipe=8')))
t.ok(lines.some((l) => l.includes('nofile=1024')))
})
test('bareTopDelegateInflightTableLines right-aligns counts', async (t) => {
const code = await readFile(helpersPath, 'utf8')
const ctx = createContext({})
runInContext(code, ctx)
const lines = ctx.bareTopDelegateInflightTableLines({ a: 3, b: 12 }, 5, 8)
t.ok(lines[0].includes('b') && lines[0].includes('12'))
t.ok(lines[1].includes('a') && lines[1].includes('3'))
})
test('bareTopParseMeminfoMetrics derives MemTotal and MemAvailable', async (t) => {
const code = await readFile(helpersPath, 'utf8')
const ctx = createContext({})
@@ -0,0 +1,27 @@
{
"schema": 1,
"schemaVersion": 2,
"topicHex": "deadbeef",
"peerCount": 3,
"seedHandshakeError": null,
"replicationQueueDepth": 2,
"replicationQueue": {
"depth": 2,
"pending": 1,
"items": [{ "id": "a" }]
},
"peerFirewallStats": {
"acceptedSessionCount": 10,
"rejectedSessionCount": 1,
"inboundSessionCount": 4,
"outboundSessionCount": 6,
"wave9": { "x": 1 }
},
"bsdSocketGuestBridge": {
"schema": 1,
"policyEnv": "BARE_OS_BSD_SOCKET_POLICY",
"note": "test bridge",
"activeBridgedFds": 0
},
"atMs": 1700000000000
}
@@ -28,5 +28,27 @@
"swarmLifecycle": { "phase": "steady" },
"initdReadiness": { "failed": 0, "starting": 1, "active": 4 },
"workerBudgetHints": { "wallMsMax": 60000 },
"processTable": { "schema": 7, "rows": [] }
"processTable": { "schema": 7, "rows": [] },
"netSummaryNestedExample": {
"schemaVersion": 2,
"topicHex": "deadbeef",
"peerCount": 2,
"seedHandshakeError": "",
"replicationQueueDepth": 4,
"peerFirewallBlockedSessions": 0,
"peerFirewallAllowedSessions": 12,
"replicationQueue": {
"depth": 4,
"lastError": null,
"batches": [{ "id": 1, "state": "pending" }]
},
"peerFirewallStats": {
"sessions": { "blocked": 0, "allowed": 12 }
},
"bsdSocketGuestBridge": {
"schema": 1,
"policyEnv": "default",
"note": "fixture"
}
}
}
+1
View File
@@ -4,6 +4,7 @@ Cross-package **version alignment** (ctx API, feature-bits doc, lifecycle schema
## Documentation (rolling)
- **`peer_firewall_stats` / `net_summary`** — [`lib/channel.js`](lib/channel.js) comment ties default firewall counters to **`/proc/bare_os/net_summary.json`** scalars (**`peerFirewallBlockedSessions`**, **`peerFirewallAllowedSessions`**) and the **`peerFirewallStats`** object when present.
- **`0.9.1` / `BARE_OS_KERNEL_FEATURE_BITS_DOC` `16`** — Protomux cap-channel constant (**`PROTOCOL_CAP_CHANNEL_NAME`**) + **`BARE_OS_FEATURE8_PROTOMUX_CAP_CHANNEL`** documentation bump (stock **`bare-os-booter`** surfaces); **`stock-booter-capability-contract.json`** **`expectedFeatureBitsDoc`** aligned.
- **Wire stack pins** — Re-verified **2026-04-05**: root **`package-lock.json`** hoisted **`protomux`** / **`hyperswarm`** versions still match [`packages/bare-os-booter/fixtures/protomux-hyperswarm-lock.json`](../packages/bare-os-booter/fixtures/protomux-hyperswarm-lock.json) (**`BARE_OS_PROTOMUX_CHANNEL_SCHEMA_VERSION`** unchanged).
- **`BARE_OS_POSIX_PROFILE_VERSION` `1.0.15`** — Multi-account personal layout (**`BARE_OS_PERSONAL_ACCT_PREFIX`**), scoped **`/.bare/**`** routing, **`clock_gettime`**-shaped **`ctx.bareOsSyscall`** / proc **`syscalls.json` schema 9**, stock **`hrpc`** routes **`bare_os.replication_operator_sketch`** + **`bare_os.replication_snapshot`**, **`hyper_multisig_trust_pointer` proc schema 2** (**`BARE_OS_VAULT_MULTISIG_CONTINUITY_JSON`**), and related matrix / handbook alignment (see [`bare-os-posix-profile.js`](lib/bare-os-posix-profile.js), [`docs/reference/posix-compliance-matrix.json`](../../docs/reference/posix-compliance-matrix.json), [`docs/architecture/POSIX_DECLARED_PROFILE.md`](../../docs/architecture/POSIX_DECLARED_PROFILE.md)).
+1
View File
@@ -702,6 +702,7 @@ export function setupSeedChannel(mux, localRAM, replicateDrive, opts = {}) {
return
}
if (m.module === 'bare_os' && m.method === 'peer_firewall_stats') {
/** Default counter fields mirrored in `/proc/bare_os/net_summary.json` scalar totals + `peerFirewallStats` object for baretop. */
/** @type {Record<string, unknown>} */
let stats = {
acceptedSessionCount: 0,
File diff suppressed because it is too large Load Diff
File diff suppressed because it is too large Load Diff
@@ -1,7 +1,7 @@
{
"schema": 2,
"profileId": "bare-os-posix-like",
"generatedAt": "2026-04-05T20:29:19.862Z",
"generatedAt": "2026-04-05T21:06:07.548Z",
"note": "Sparse POSIX Issue 7 coverage hints for /bin utilities. Omitted command names are not yet profiled here.",
"commandIndex": [
{
@@ -1,18 +1,18 @@
{
"version": 1,
"bundles": [
{
"path": "/lib/bare/bundles/b4a.js",
"keys": [
"b4a"
]
},
{
"path": "/lib/bare/bundles/safetyCatch.js",
"keys": [
"safetyCatch"
]
},
{
"path": "/lib/bare/bundles/b4a.js",
"keys": [
"b4a"
]
},
{
"path": "/lib/bare/bundles/hypercoreIdEncoding.js",
"keys": [
@@ -43,12 +43,6 @@
"bareEncoding"
]
},
{
"path": "/lib/bare/bundles/bareEvents.js",
"keys": [
"bareEvents"
]
},
{
"path": "/lib/bare/bundles/barePath.js",
"keys": [
@@ -56,9 +50,9 @@
]
},
{
"path": "/lib/bare/bundles/bareAbort.js",
"path": "/lib/bare/bundles/bareEvents.js",
"keys": [
"bareAbort"
"bareEvents"
]
},
{
@@ -68,9 +62,9 @@
]
},
{
"path": "/lib/bare/bundles/bareAnsiEscapes.js",
"path": "/lib/bare/bundles/bareAbort.js",
"keys": [
"bareAnsiEscapes"
"bareAbort"
]
},
{
@@ -79,6 +73,12 @@
"bareAddonResolve"
]
},
{
"path": "/lib/bare/bundles/bareAnsiEscapes.js",
"keys": [
"bareAnsiEscapes"
]
},
{
"path": "/lib/bare/bundles/bareReadline.js",
"keys": [
@@ -97,18 +97,6 @@
"bareApk"
]
},
{
"path": "/lib/bare/bundles/bareAsyncHooks.js",
"keys": [
"bareAsyncHooks"
]
},
{
"path": "/lib/bare/bundles/bareAssert.js",
"keys": [
"bareAssert"
]
},
{
"path": "/lib/bare/bundles/bareAppKit.js",
"keys": [
@@ -116,9 +104,9 @@
]
},
{
"path": "/lib/bare/bundles/fetch.js",
"path": "/lib/bare/bundles/bareAsyncHooks.js",
"keys": [
"fetch"
"bareAsyncHooks"
]
},
{
@@ -128,15 +116,21 @@
]
},
{
"path": "/lib/bare/bundles/bareBmp.js",
"path": "/lib/bare/bundles/bareAssert.js",
"keys": [
"bareBmp"
"bareAssert"
]
},
{
"path": "/lib/bare/bundles/bareBundleCompile.js",
"path": "/lib/bare/bundles/fetch.js",
"keys": [
"bareBundleCompile"
"fetch"
]
},
{
"path": "/lib/bare/bundles/bareBmp.js",
"keys": [
"bareBmp"
]
},
{
@@ -146,15 +140,15 @@
]
},
{
"path": "/lib/bare/bundles/bareBuffer.js",
"path": "/lib/bare/bundles/bareBundleCompile.js",
"keys": [
"bareBuffer"
"bareBundleCompile"
]
},
{
"path": "/lib/bare/bundles/bareBundleEvaluate.js",
"path": "/lib/bare/bundles/bareBuffer.js",
"keys": [
"bareBundleEvaluate"
"bareBuffer"
]
},
{
@@ -164,15 +158,15 @@
]
},
{
"path": "/lib/bare/bundles/bareBoot.js",
"path": "/lib/bare/bundles/bareBundleEvaluate.js",
"keys": [
"bareBoot"
"bareBundleEvaluate"
]
},
{
"path": "/lib/bare/bundles/bareBundleId.js",
"path": "/lib/bare/bundles/bareBoot.js",
"keys": [
"bareBundleId"
"bareBoot"
]
},
{
@@ -182,9 +176,9 @@
]
},
{
"path": "/lib/bare/bundles/bareDebugLog.js",
"path": "/lib/bare/bundles/bareBundleId.js",
"keys": [
"bareDebugLog"
"bareBundleId"
]
},
{
@@ -194,9 +188,9 @@
]
},
{
"path": "/lib/bare/bundles/bareDaemon.js",
"path": "/lib/bare/bundles/bareDebugLog.js",
"keys": [
"bareDaemon"
"bareDebugLog"
]
},
{
@@ -206,9 +200,9 @@
]
},
{
"path": "/lib/bare/bundles/bareDns.js",
"path": "/lib/bare/bundles/bareDaemon.js",
"keys": [
"bareDns"
"bareDaemon"
]
},
{
@@ -217,6 +211,12 @@
"bareDiagnosticsChannel"
]
},
{
"path": "/lib/bare/bundles/bareDns.js",
"keys": [
"bareDns"
]
},
{
"path": "/lib/bare/bundles/bareEnv.js",
"keys": [
@@ -229,12 +229,6 @@
"bareExif"
]
},
{
"path": "/lib/bare/bundles/bareDgram.js",
"keys": [
"bareDgram"
]
},
{
"path": "/lib/bare/bundles/bareCov.js",
"keys": [
@@ -242,9 +236,9 @@
]
},
{
"path": "/lib/bare/bundles/bareFfmpeg.js",
"path": "/lib/bare/bundles/bareDgram.js",
"keys": [
"bareFfmpeg"
"bareDgram"
]
},
{
@@ -253,6 +247,12 @@
"bareFormat"
]
},
{
"path": "/lib/bare/bundles/bareFormData.js",
"keys": [
"bareFormData"
]
},
{
"path": "/lib/bare/bundles/bareFfmpegEncodings.js",
"keys": [
@@ -260,9 +260,9 @@
]
},
{
"path": "/lib/bare/bundles/bareFormData.js",
"path": "/lib/bare/bundles/bareFfmpeg.js",
"keys": [
"bareFormData"
"bareFfmpeg"
]
},
{
@@ -289,12 +289,6 @@
"bareHeif"
]
},
{
"path": "/lib/bare/bundles/bareFs.js",
"keys": [
"bareFs"
]
},
{
"path": "/lib/bare/bundles/bareHrtime.js",
"keys": [
@@ -308,9 +302,9 @@
]
},
{
"path": "/lib/bare/bundles/bareIco.js",
"path": "/lib/bare/bundles/bareFs.js",
"keys": [
"bareIco"
"bareFs"
]
},
{
@@ -319,6 +313,12 @@
"bareImageResample"
]
},
{
"path": "/lib/bare/bundles/bareIco.js",
"keys": [
"bareIco"
]
},
{
"path": "/lib/bare/bundles/bareHttp1.js",
"keys": [
@@ -337,24 +337,6 @@
"bareInspect"
]
},
{
"path": "/lib/bare/bundles/bareJpeg.js",
"keys": [
"bareJpeg"
]
},
{
"path": "/lib/bare/bundles/bareIpc.js",
"keys": [
"bareIpc"
]
},
{
"path": "/lib/bare/bundles/bareLief.js",
"keys": [
"bareLief"
]
},
{
"path": "/lib/bare/bundles/bareIntl.js",
"keys": [
@@ -362,9 +344,9 @@
]
},
{
"path": "/lib/bare/bundles/bareLogger.js",
"path": "/lib/bare/bundles/bareJpeg.js",
"keys": [
"bareLogger"
"bareJpeg"
]
},
{
@@ -373,54 +355,48 @@
"bareInspector"
]
},
{
"path": "/lib/bare/bundles/bareLief.js",
"keys": [
"bareLief"
]
},
{
"path": "/lib/bare/bundles/bareIpc.js",
"keys": [
"bareIpc"
]
},
{
"path": "/lib/bare/bundles/bareLogger.js",
"keys": [
"bareLogger"
]
},
{
"path": "/lib/bare/bundles/bareLink.js",
"keys": [
"bareLink"
]
},
{
"path": "/lib/bare/bundles/bareMake.js",
"keys": [
"bareMake"
]
},
{
"path": "/lib/bare/bundles/bareModuleLexer.js",
"keys": [
"bareModuleLexer"
]
},
{
"path": "/lib/bare/bundles/bareModuleResolve.js",
"keys": [
"bareModuleResolve"
]
},
{
"path": "/lib/bare/bundles/bareModuleLexer.js",
"keys": [
"bareModuleLexer"
]
},
{
"path": "/lib/bare/bundles/bareModule.js",
"keys": [
"bareModule"
]
},
{
"path": "/lib/bare/bundles/bareModuleTraverse.js",
"keys": [
"bareModuleTraverse"
]
},
{
"path": "/lib/bare/bundles/bareNdk.js",
"keys": [
"bareNdk"
]
},
{
"path": "/lib/bare/bundles/bareNodeFetch.js",
"keys": [
"bareNodeFetch"
]
},
{
"path": "/lib/bare/bundles/bareNative.js",
"keys": [
@@ -428,15 +404,27 @@
]
},
{
"path": "/lib/bare/bundles/bareMedia.js",
"path": "/lib/bare/bundles/bareMake.js",
"keys": [
"bareMedia"
"bareMake"
]
},
{
"path": "/lib/bare/bundles/bareNet.js",
"path": "/lib/bare/bundles/bareNdk.js",
"keys": [
"bareNet"
"bareNdk"
]
},
{
"path": "/lib/bare/bundles/bareModuleTraverse.js",
"keys": [
"bareModuleTraverse"
]
},
{
"path": "/lib/bare/bundles/bareNodeFetch.js",
"keys": [
"bareNodeFetch"
]
},
{
@@ -451,24 +439,24 @@
"bareOs"
]
},
{
"path": "/lib/bare/bundles/bareMedia.js",
"keys": [
"bareMedia"
]
},
{
"path": "/lib/bare/bundles/bareNet.js",
"keys": [
"bareNet"
]
},
{
"path": "/lib/bare/bundles/barePack.js",
"keys": [
"barePack"
]
},
{
"path": "/lib/bare/bundles/barePackDrive.js",
"keys": [
"barePackDrive"
]
},
{
"path": "/lib/bare/bundles/barePerformance.js",
"keys": [
"barePerformance"
]
},
{
"path": "/lib/bare/bundles/barePng.js",
"keys": [
@@ -476,15 +464,15 @@
]
},
{
"path": "/lib/bare/bundles/barePipe.js",
"path": "/lib/bare/bundles/barePerformance.js",
"keys": [
"barePipe"
"barePerformance"
]
},
{
"path": "/lib/bare/bundles/barePrebuild.js",
"path": "/lib/bare/bundles/barePackDrive.js",
"keys": [
"barePrebuild"
"barePackDrive"
]
},
{
@@ -494,9 +482,9 @@
]
},
{
"path": "/lib/bare/bundles/bareProcess.js",
"path": "/lib/bare/bundles/barePipe.js",
"keys": [
"bareProcess"
"barePipe"
]
},
{
@@ -511,6 +499,18 @@
"bareQuerystring"
]
},
{
"path": "/lib/bare/bundles/bareQueueMicrotask.js",
"keys": [
"bareQueueMicrotask"
]
},
{
"path": "/lib/bare/bundles/barePrebuild.js",
"keys": [
"barePrebuild"
]
},
{
"path": "/lib/bare/bundles/bareRealm.js",
"keys": [
@@ -518,9 +518,15 @@
]
},
{
"path": "/lib/bare/bundles/bareQueueMicrotask.js",
"path": "/lib/bare/bundles/bareDev.js",
"keys": [
"bareQueueMicrotask"
"bareDev"
]
},
{
"path": "/lib/bare/bundles/bareProcess.js",
"keys": [
"bareProcess"
]
},
{
@@ -536,9 +542,9 @@
]
},
{
"path": "/lib/bare/bundles/bareRpc.js",
"path": "/lib/bare/bundles/bareSdl.js",
"keys": [
"bareRpc"
"bareSdl"
]
},
{
@@ -548,9 +554,9 @@
]
},
{
"path": "/lib/bare/bundles/bareSdl.js",
"path": "/lib/bare/bundles/bareRpc.js",
"keys": [
"bareSdl"
"bareRpc"
]
},
{
@@ -560,15 +566,15 @@
]
},
{
"path": "/lib/bare/bundles/bareSemver.js",
"path": "/lib/bare/bundles/bareSidecar.js",
"keys": [
"bareSemver"
"bareSidecar"
]
},
{
"path": "/lib/bare/bundles/bareDev.js",
"path": "/lib/bare/bundles/bareSemver.js",
"keys": [
"bareDev"
"bareSemver"
]
},
{
@@ -577,24 +583,12 @@
"bareSignals"
]
},
{
"path": "/lib/bare/bundles/bareSidecar.js",
"keys": [
"bareSidecar"
]
},
{
"path": "/lib/bare/bundles/bareStorage.js",
"keys": [
"bareStorage"
]
},
{
"path": "/lib/bare/bundles/bareStringDecoder.js",
"keys": [
"bareStringDecoder"
]
},
{
"path": "/lib/bare/bundles/bareStream.js",
"keys": [
@@ -607,6 +601,12 @@
"bareStdio"
]
},
{
"path": "/lib/bare/bundles/bareStringDecoder.js",
"keys": [
"bareStringDecoder"
]
},
{
"path": "/lib/bare/bundles/bareSvg.js",
"keys": [
@@ -619,12 +619,24 @@
"bareStructuredClone"
]
},
{
"path": "/lib/bare/bundles/bareSubprocess.js",
"keys": [
"bareSubprocess"
]
},
{
"path": "/lib/bare/bundles/bareSystemLogger.js",
"keys": [
"bareSystemLogger"
]
},
{
"path": "/lib/bare/bundles/bareTap.js",
"keys": [
"bareTap"
]
},
{
"path": "/lib/bare/bundles/bareTiff.js",
"keys": [
@@ -632,15 +644,15 @@
]
},
{
"path": "/lib/bare/bundles/bareSubprocess.js",
"path": "/lib/bare/bundles/bareTcp.js",
"keys": [
"bareSubprocess"
"bareTcp"
]
},
{
"path": "/lib/bare/bundles/bareTap.js",
"path": "/lib/bare/bundles/bareThread.js",
"keys": [
"bareTap"
"bareThread"
]
},
{
@@ -656,21 +668,9 @@
]
},
{
"path": "/lib/bare/bundles/bareThread.js",
"path": "/lib/bare/bundles/bareType.js",
"keys": [
"bareThread"
]
},
{
"path": "/lib/bare/bundles/bareTcp.js",
"keys": [
"bareTcp"
]
},
{
"path": "/lib/bare/bundles/bareTls.js",
"keys": [
"bareTls"
"bareType"
]
},
{
@@ -680,9 +680,9 @@
]
},
{
"path": "/lib/bare/bundles/bareV8.js",
"path": "/lib/bare/bundles/bareTls.js",
"keys": [
"bareV8"
"bareTls"
]
},
{
@@ -698,15 +698,9 @@
]
},
{
"path": "/lib/bare/bundles/bareType.js",
"path": "/lib/bare/bundles/bareV8.js",
"keys": [
"bareType"
]
},
{
"path": "/lib/bare/bundles/bareVm.js",
"keys": [
"bareVm"
"bareV8"
]
},
{
@@ -716,15 +710,27 @@
]
},
{
"path": "/lib/bare/bundles/bareWebp.js",
"path": "/lib/bare/bundles/bareVm.js",
"keys": [
"bareWebp"
"bareVm"
]
},
{
"path": "/lib/bare/bundles/bareWebKitGtk.js",
"path": "/lib/bare/bundles/bareUnionBundle.js",
"keys": [
"bareWebKitGtk"
"bareUnionBundle"
]
},
{
"path": "/lib/bare/bundles/bareWebKit.js",
"keys": [
"bareWebKit"
]
},
{
"path": "/lib/bare/bundles/bareV8ToIstanbul.js",
"keys": [
"bareV8ToIstanbul"
]
},
{
@@ -734,9 +740,9 @@
]
},
{
"path": "/lib/bare/bundles/bareWebKit.js",
"path": "/lib/bare/bundles/bareWebp.js",
"keys": [
"bareWebKit"
"bareWebp"
]
},
{
@@ -751,6 +757,12 @@
"bareWinUi"
]
},
{
"path": "/lib/bare/bundles/bareWebKitGtk.js",
"keys": [
"bareWebKitGtk"
]
},
{
"path": "/lib/bare/bundles/bareXdiff.js",
"keys": [
@@ -758,21 +770,9 @@
]
},
{
"path": "/lib/bare/bundles/bareUnionBundle.js",
"path": "/lib/bare/bundles/bareZmq.js",
"keys": [
"bareUnionBundle"
]
},
{
"path": "/lib/bare/bundles/bareV8ToIstanbul.js",
"keys": [
"bareV8ToIstanbul"
]
},
{
"path": "/lib/bare/bundles/bareWs.js",
"keys": [
"bareWs"
"bareZmq"
]
},
{
@@ -788,9 +788,9 @@
]
},
{
"path": "/lib/bare/bundles/bareZmq.js",
"path": "/lib/bare/bundles/bareWs.js",
"keys": [
"bareZmq"
"bareWs"
]
}
],
@@ -1595,8 +1595,8 @@
],
"bundleProvenance": {
"schemaVersion": 1,
"generatedAt": "2026-04-05T20:21:22.752Z",
"gitCommit": "64a1270d183372403fdf27cc963dda87561b6f0c",
"generatedAt": "2026-04-05T21:06:08.393Z",
"gitCommit": "7c6b77ed6230e65eb83542fe29a8c079f02878e4",
"nodeVersion": "v22.22.0",
"bundleTier": "all",
"normativeManifest": "packages/bare-os-booter/lib/bare-module-manifest.json",
@@ -1,6 +1,6 @@
{
"schema": 1,
"atMs": 1775420959862,
"atMs": 1775423167547,
"commands": [
"arch",
"awk",
File diff suppressed because one or more lines are too long