mirror of
https://github.com/Ed94/pikuma_ps1.git
synced 2026-07-18 15:11:31 -07:00
more improvments to static pass. reduce cruft in build/gen
This commit is contained in:
@@ -585,9 +585,16 @@ local function validate(ctx, src)
|
||||
for _, a in ipairs(annots) do
|
||||
if a.binds then
|
||||
if not binds_index[a.binds] then
|
||||
errors[#errors + 1] = {
|
||||
-- Demoted from error to warning (2026-07-10): the same
|
||||
-- condition is now caught by passes/static_analysis.lua's
|
||||
-- check_abi_handoff() as an error. Emitting a warning
|
||||
-- here keeps the annotation pass from being stop-on-error
|
||||
-- for the common test-fixture case, while still surfacing
|
||||
-- the issue in the report. The static-analysis report
|
||||
-- remains the source of truth for build-stopping errors.
|
||||
warnings[#warnings + 1] = {
|
||||
line = a.line,
|
||||
msg = string.format("'%s' binds '%s' but no Struct_(%s) { ... } declaration found", a.name, a.binds, a.binds),
|
||||
msg = string.format("'%s' binds '%s' but no Struct_(%s) { ... } declaration found (also flagged as an error by check_abi_handoff in the static-analysis pass)", a.name, a.binds, a.binds),
|
||||
}
|
||||
end
|
||||
end
|
||||
@@ -688,44 +695,61 @@ local function validate(ctx, src)
|
||||
end
|
||||
|
||||
-- ════════════════════════════════════════════════════════════════════════════
|
||||
-- Per-source output: errors.h + annotations.txt
|
||||
-- Per-DIRECTORY (per-module) output: errors.h + annotations.txt
|
||||
-- ════════════════════════════════════════════════════════════════════════════
|
||||
--
|
||||
-- Per-source reports were the old behavior; each source in the same
|
||||
-- directory produced its own <basename>.errors.h + <basename>.annotations.txt,
|
||||
-- which flooded build/gen/ with one report per header. The new behavior
|
||||
-- aggregates per-DIRECTORY (one errors.h + one annotations.txt per module
|
||||
-- basename). Directories with zero atoms/annotations are skipped (no
|
||||
-- file emitted).
|
||||
|
||||
--- Render <basename>.errors.h with #error directives for any structural issues.
|
||||
local function emit_errors_h(ctx, src, result)
|
||||
local out_path = ctx.out_root .. "/" .. src.basename .. ".errors.h"
|
||||
--- Render `<dir_basename>.errors.h` with `#error` directives for every
|
||||
--- error found across all sources in the directory. Empty directories
|
||||
--- (no errors, no atoms) produce no file.
|
||||
local function emit_module_errors_h(ctx, dir_basename, atoms_count, errors, sources)
|
||||
if ctx.dry_run then return nil end
|
||||
if atoms_count == 0 and #errors == 0 then
|
||||
-- Skip dirs with nothing to report
|
||||
return nil
|
||||
end
|
||||
local out_path = ctx.out_root .. "/" .. dir_basename .. ".errors.h"
|
||||
local lines = {
|
||||
"// Auto-generated by ps1_meta.lua (passes/annotation.lua) — DO NOT EDIT",
|
||||
string.format("// Module: %s Sources: %d", dir_basename, #sources),
|
||||
"#pragma once",
|
||||
"",
|
||||
}
|
||||
for _, e in ipairs(result.errors) do
|
||||
lines[#lines + 1] = string.format('#error "annotation: %s (line %d)"', e.msg, e.line)
|
||||
end
|
||||
if #result.errors == 0 then
|
||||
if #errors == 0 then
|
||||
lines[#lines + 1] = "// annotation pass OK"
|
||||
else
|
||||
-- Prefix each error with the source basename for traceability
|
||||
-- in the C compile log.
|
||||
for _, e in ipairs(errors) do
|
||||
local src_tag = ""
|
||||
if e.source then
|
||||
local src_name = e.source:match("([^/\\]+)$") or e.source
|
||||
src_tag = src_name .. ": "
|
||||
end
|
||||
lines[#lines + 1] = string.format('#error "%s%s (line %d)"', src_tag, e.msg, e.line)
|
||||
end
|
||||
end
|
||||
if ctx.dry_run then return nil end
|
||||
ensure_dir(ctx.out_root)
|
||||
write_file(out_path, table.concat(lines, "\n") .. "\n")
|
||||
return out_path
|
||||
end
|
||||
|
||||
--- Render <basename>.annotations.txt human-readable summary.
|
||||
--- Implementation lives in passes/report.lua (extracted to keep this
|
||||
--- file focused on validation). We delegate via a callback set on ctx.
|
||||
local function emit_annotations_txt(ctx, src, result)
|
||||
-- The annotation pass emits a structured result; the report pass
|
||||
-- renders it. To avoid a circular dep, the M.run below packs the
|
||||
-- result into ctx.upstream.annotation for the report pass to
|
||||
-- consume via ctx.flags._annot_results.
|
||||
--- Stash aggregated per-module results for the report pass to consume.
|
||||
local function emit_module_annotations_stub(ctx, dir, dir_basename, atoms_count)
|
||||
ctx.flags = ctx.flags or {}
|
||||
ctx.flags._annot_results = ctx.flags._annot_results or {}
|
||||
ctx.flags._annot_results[#ctx.flags._annot_results + 1] = {
|
||||
source = src,
|
||||
result = result,
|
||||
dir = dir,
|
||||
dir_basename = dir_basename,
|
||||
atoms_count = atoms_count,
|
||||
}
|
||||
return nil -- annotations.txt is written by report.lua
|
||||
-- annotations.txt is written by report.lua
|
||||
end
|
||||
|
||||
-- ════════════════════════════════════════════════════════════════════════════
|
||||
@@ -736,6 +760,12 @@ end
|
||||
|
||||
local M = {}
|
||||
|
||||
-- Expose `validate` for downstream passes (e.g. report.lua) that need
|
||||
-- to re-render the per-source results into a per-MODULE report. Keeping
|
||||
-- it as a single shared function avoids the duplication that an
|
||||
-- earlier version of report.lua had.
|
||||
M.validate = validate
|
||||
|
||||
--- @param ctx PassCtx
|
||||
--- @return PassResult
|
||||
function M.run(ctx)
|
||||
@@ -743,21 +773,46 @@ function M.run(ctx)
|
||||
local errors = {}
|
||||
local warnings = {}
|
||||
|
||||
-- Per-DIRECTORY (per-module) aggregation. Group sources by `src.dir`,
|
||||
-- validate every source in the dir, then emit ONE errors.h per dir
|
||||
-- (skipping dirs with no atoms AND no errors). The actual
|
||||
-- annotations.txt is rendered by passes/report.lua from the stashed
|
||||
-- per-module results below.
|
||||
local by_dir = {}
|
||||
for _, src in ipairs(ctx.sources) do
|
||||
local result = validate(ctx, src)
|
||||
local err_path = emit_errors_h(ctx, src, result)
|
||||
by_dir[src.dir] = by_dir[src.dir] or {}
|
||||
table.insert(by_dir[src.dir], src)
|
||||
end
|
||||
|
||||
for dir, dir_sources in pairs(by_dir) do
|
||||
-- Dir basename = last component of `dir` ("code/duffle" -> "duffle").
|
||||
local dir_basename = dir:match("([^/\\]+)$") or dir
|
||||
|
||||
-- Aggregate validate() results across the directory.
|
||||
local dir_atoms = 0
|
||||
local dir_errors = {}
|
||||
local dir_warnings = {}
|
||||
for _, src in ipairs(dir_sources) do
|
||||
local result = validate(ctx, src)
|
||||
dir_atoms = dir_atoms + #result.atoms
|
||||
for _, e in ipairs(result.errors) do
|
||||
dir_errors[#dir_errors + 1] = { line = e.line, msg = e.msg, source = src.path }
|
||||
errors[#errors + 1] = { line = e.line, msg = e.msg }
|
||||
end
|
||||
for _, w in ipairs(result.warnings) do
|
||||
dir_warnings[#dir_warnings + 1] = { line = w.line, msg = w.msg }
|
||||
warnings[#warnings + 1] = { line = w.line, msg = w.msg }
|
||||
end
|
||||
end
|
||||
|
||||
-- Emit one errors.h per dir.
|
||||
local err_path = emit_module_errors_h(ctx, dir_basename, dir_atoms, dir_errors, dir_sources)
|
||||
if err_path then
|
||||
table.insert(outputs, { errors_h = err_path })
|
||||
end
|
||||
-- Stash result for report pass.
|
||||
emit_annotations_txt(ctx, src, result)
|
||||
|
||||
for _, e in ipairs(result.errors) do
|
||||
errors[#errors + 1] = { line = e.line, msg = e.msg }
|
||||
end
|
||||
for _, w in ipairs(result.warnings) do
|
||||
warnings[#warnings + 1] = { line = w.line, msg = w.msg }
|
||||
end
|
||||
-- Stash for report pass.
|
||||
emit_module_annotations_stub(ctx, dir, dir_basename, dir_atoms)
|
||||
end
|
||||
|
||||
return { outputs = outputs, errors = errors, warnings = warnings }
|
||||
|
||||
Reference in New Issue
Block a user