锁定虚拟HAL宏加载阻断证据

This commit is contained in:
2026-06-18 05:21:30 +08:00
parent 506a6357c1
commit 014081f1f9
10 changed files with 221 additions and 6 deletions

View File

@@ -328,12 +328,15 @@ private page state.
browser diagnostics evidence, and the required virtual HAL reports for
QtDragon on-abort, PUMA seam-weld, and rose-engine promotion planning.
- `VIRTUAL_HAL_SIM_CONFIG_MACRO_LOAD_FIXTURES` and
`VIRTUAL_HAL_SIM_CONFIG_MACRO_LOAD_BLOCKED_FIXTURES` plus
`createVirtualHalSimConfigMacroLoadFixtureReport()` expose non-main
macro/load fixture evidence for virtual HAL diagnostics. The report keeps
`nonMainFixture === true`, separates fixture paths from manifest-backed
LinuxCNC source files, and prevents macro/load rows such as rose-engine
`rcone.ngc` or external-offsets `queuebuster.ngc` from being promoted as
standalone browser main programs.
standalone browser main programs. Blocked fixture rows such as SilverDragon
`tool_sensor.ngc` remain excluded until their Python UI/process boundary is
proven outside virtual HAL.
- `createVirtualHalSourceComplianceReport()` is the machine-readable gate for
the virtual HAL source rule. It maps replacement targets, runtime
capabilities, and HAL pin families back to LinuxCNC source files such as

View File

@@ -7,6 +7,7 @@ export {
VIRTUAL_HAL_COVERAGE_STATES,
VIRTUAL_HAL_MOTION_CONTROLLER_MATRIX_FIXTURES,
VIRTUAL_HAL_PROJECT_PIN_GROUPS,
VIRTUAL_HAL_SIM_CONFIG_MACRO_LOAD_BLOCKED_FIXTURES,
VIRTUAL_HAL_SIM_CONFIG_MACRO_LOAD_FIXTURES,
VIRTUAL_HAL_SIM_CONFIG_PROMOTION_CANDIDATES,
VIRTUAL_HAL_SIM_CONFIG_SOURCE_TARGETS,

View File

@@ -363,6 +363,25 @@ export const VIRTUAL_HAL_SIM_CONFIG_MACRO_LOAD_FIXTURES = Object.freeze([
}),
]);
export const VIRTUAL_HAL_SIM_CONFIG_MACRO_LOAD_BLOCKED_FIXTURES = Object.freeze([
Object.freeze({
id: "silverdragon-tool-sensor-python-ui-boundary",
fixturePath: "linuxcnc/configs/sim/gscreen/silverdragon/macros/tool_sensor.ngc",
owningIniPath: "linuxcnc/configs/sim/gscreen/silverdragon/silverdragon.ini",
blockedKind: "PYTHON-UI-PROCESS",
dependencyClass: "macro-load-python-ui-boundary",
reason: "Owning SilverDragon UI machine file is not available in the vendored manifest; promotion would require Python UI process boundary proof outside virtual HAL.",
}),
Object.freeze({
id: "gmoccapy-on-abort-python-remap-boundary",
fixturePath: "linuxcnc/configs/sim/gmoccapy/macros/on_abort.ngc",
owningIniPath: "linuxcnc/configs/sim/gmoccapy/6_axis.ini",
blockedKind: "L4-PYTHON-REMAP",
dependencyClass: "macro-load-python-remap-boundary",
reason: "gmoccapy macro/load rows remain locked behind LinuxCNC-owned Python remap/prolog/epilog runtime proof.",
}),
]);
export const VIRTUAL_HAL_COVERAGE_STATES = Object.freeze({
simulated: "simulated",
bridgeOnly: "bridge-only",
@@ -2852,6 +2871,7 @@ export function createVirtualHalSimConfigPromotionCandidateReport(options = {})
export function createVirtualHalSimConfigMacroLoadFixtureReport(options = {}) {
const fixtures = options.fixtures ?? VIRTUAL_HAL_SIM_CONFIG_MACRO_LOAD_FIXTURES;
const blockedFixtures = options.blockedFixtures ?? VIRTUAL_HAL_SIM_CONFIG_MACRO_LOAD_BLOCKED_FIXTURES;
const manifestProvided = typeof options.manifestText === "string" || Array.isArray(options.manifestEntries);
const manifestSet = new Set([
...sourceManifestSetFromText(options.manifestText ?? ""),
@@ -2908,11 +2928,30 @@ export function createVirtualHalSimConfigMacroLoadFixtureReport(options = {}) {
.filter((row) => row.nonMainFixture !== true || row.targetBrowserEvidence !== "non-main-fixture-diagnostics")
.map((row) => row.id);
const missingManifestFiles = [...new Set(rows.flatMap((row) => row.missingManifestFiles))];
const positiveFixturePaths = new Set(rows.map((row) => normalizeLinuxCncSourcePath(row.fixturePath)));
const blockedRows = blockedFixtures.map((fixture) => {
const excludedFromPositiveFixtures = !positiveFixturePaths.has(normalizeLinuxCncSourcePath(fixture.fixturePath));
return {
id: fixture.id,
source: "linuxcnc-configs-sim-source-derived-virtual-hal-macro-load-blocked-fixture",
fixturePath: fixture.fixturePath,
owningIniPath: fixture.owningIniPath,
blockedKind: fixture.blockedKind,
dependencyClass: fixture.dependencyClass,
excludedFromPositiveFixtures,
reason: fixture.reason,
complete: excludedFromPositiveFixtures,
};
});
const blockedFixturePromotionViolations = blockedRows
.filter((row) => row.excludedFromPositiveFixtures !== true)
.map((row) => row.id);
const complete = rows.length > 0 &&
missingFixtures.length === 0 &&
blockedFixtureIds.length === 0 &&
standaloneMainViolations.length === 0 &&
missingManifestFiles.length === 0;
missingManifestFiles.length === 0 &&
blockedFixturePromotionViolations.length === 0;
return {
apiName: "linuxcnc-wasm-virtual-hal-sim-config-macro-load-fixture-report",
reportVersion: 1,
@@ -2928,11 +2967,14 @@ export function createVirtualHalSimConfigMacroLoadFixtureReport(options = {}) {
missingFixtures,
blockedFixtureIds,
standaloneMainViolations,
blockedFixturePromotionViolations,
missingManifestFiles,
rows,
blockedRows,
summaryRows: [
{ id: "fixtures", label: "Macro/load fixtures", value: `${rows.length}` },
{ id: "non-main", label: "Non-main fixture gate", value: standaloneMainViolations.length === 0 ? "passed" : `violations ${standaloneMainViolations.length}` },
{ id: "blocked-fixture-lock", label: "Blocked fixture lock", value: blockedFixturePromotionViolations.length === 0 ? "passed" : `violations ${blockedFixturePromotionViolations.length}` },
{ id: "blocked-family", label: "Blocked-family exclusion", value: blockedFixtureIds.length === 0 ? "passed" : `blocked ${blockedFixtureIds.length}` },
{ id: "manifest", label: "Manifest check", value: manifestProvided ? (missingManifestFiles.length === 0 ? "passed" : "failed") : "not provided" },
{ id: "inventory-baseline", label: "Inventory baseline", value: "unchanged" },

View File

@@ -168,6 +168,19 @@ const REQUIRED_MACRO_LOAD_FIXTURES = [
},
];
const REQUIRED_BLOCKED_MACRO_LOAD_FIXTURES = [
{
id: "silverdragon-tool-sensor-python-ui-boundary",
fixturePath: "linuxcnc/configs/sim/gscreen/silverdragon/macros/tool_sensor.ngc",
blockedKind: "PYTHON-UI-PROCESS",
},
{
id: "gmoccapy-on-abort-python-remap-boundary",
fixturePath: "linuxcnc/configs/sim/gmoccapy/macros/on_abort.ngc",
blockedKind: "L4-PYTHON-REMAP",
},
];
function isVirtualHalSimConfigSourceCoverageReady(report) {
const coverage = objectOrEmpty(report);
return coverage.apiName === "linuxcnc-wasm-virtual-hal-sim-config-source-coverage-report" &&
@@ -206,6 +219,7 @@ function isVirtualHalSimConfigMacroLoadFixtureReportReady(report) {
arrayOrEmpty(fixtureReport.missingFixtures).length === 0 &&
arrayOrEmpty(fixtureReport.blockedFixtureIds).length === 0 &&
arrayOrEmpty(fixtureReport.standaloneMainViolations).length === 0 &&
arrayOrEmpty(fixtureReport.blockedFixturePromotionViolations).length === 0 &&
arrayOrEmpty(fixtureReport.missingManifestFiles).length === 0 &&
REQUIRED_MACRO_LOAD_FIXTURES.every((fixture) =>
rows.some((row) =>
@@ -216,6 +230,15 @@ function isVirtualHalSimConfigMacroLoadFixtureReportReady(report) {
row.fixturePath === fixture.fixturePath &&
fixture.sourceFiles.every((file) => arrayOrEmpty(row.sourceFiles).includes(file))
)
) &&
REQUIRED_BLOCKED_MACRO_LOAD_FIXTURES.every((fixture) =>
arrayOrEmpty(fixtureReport.blockedRows).some((row) =>
row.id === fixture.id &&
row.fixturePath === fixture.fixturePath &&
row.blockedKind === fixture.blockedKind &&
row.excludedFromPositiveFixtures === true &&
row.complete === true
)
);
}

View File

@@ -19,6 +19,7 @@ export {
VIRTUAL_HAL_AXES,
VIRTUAL_HAL_AXISUI_PINS,
VIRTUAL_HAL_MOTION_CONTROLLER_MATRIX_FIXTURES,
VIRTUAL_HAL_SIM_CONFIG_MACRO_LOAD_BLOCKED_FIXTURES,
VIRTUAL_HAL_SIM_CONFIG_MACRO_LOAD_FIXTURES,
VIRTUAL_HAL_SIM_CONFIG_PROMOTION_CANDIDATES,
VIRTUAL_HAL_SIM_CONFIG_SOURCE_TARGETS,