code wiki / _hdl_build / nx_latency_metric.nx

nx_latency_metric.nx

buildroot/runtime/_hdl_build/nx_latency_metric.nx

7252 B148 linesdepth 6pulls 6 transitivereach 7 importersview sourcekind library
docsdependenciesstructsconstsfunctions

about

nx_latency_metric.nx -- the racing-crew's HONEST latency-metric organ. Given a built NxGsim word-level netlist (topologically ordered cells, each a kind with up to 3 fanin nets), compute the CRITICAL PATH = the longest dependency chain of cells from a primary input to an output. Two metrics: (1) UNIT depth -- every non-CONST cell costs 1. This is the cell-DEPTH the functional sim (nx_nxgate_sim) implicitly uses: it assigns depth-1 to every word-level cell, so a 64x64 MUL looks exactly as cheap as a 1-bit AND. That is the HONEST-METRIC TRAP, and the unit metric is the trap. (2) HONEST depth -- every cell costs its per-kind logic depth, weighted by the operand width W (data-driven, NOT hardcoded per call site): CONST / wire = 0 (no logic) AND/OR/XOR/NOT/NAND/... = 1 (one gate level) MUX = 1 (one 2:1 select level) ADD/SUB = ceil(log2 W) (carry-propagate / prefix adder) SHL/SHR/SAR = ceil(log2 W) (barrel shifter, log stages) EQ/NEQ/LT/LTU/GE/GEU = ceil(log2 W) (tree comparator) MUL = 2*ceil(log2 W) (Wallace/Dadda PP-reduction tree + final CPA -- the DEEPEST operator) So the honest metric does NOT treat a multiplier as depth-1: a MUL costs 2*log(W) gate levels, an ADD costs log(W), a boolean costs 1. This is the metric on which any LATENCY claim about a Newton (log(W) multiplies) vs a radix-2 (W subtracts) divider must be stated -- because a multiply being "one cell" in the sim is exactly the self-deception we must avoid. METRIC HONESTY (stated, per the racing doctrine): these weights are a STRUCTURAL gate-LEVEL model (counts of logic levels), not measured silicon nanoseconds and not a placed-and-routed delay. They are a faithful relative ordering of operator depth, sized by W, and they are DATA-DRIVEN here so a future PDK-calibrated table drops in without touching the traversal. The traversal itself is exact: it is the true longest weighted path through the DAG. Reuses nx_nxgate_sim's NxGsim/NxGsimCell structs + the NX_GATE_KIND_* enum (single source of truth -- DRY). Pure read-only analysis: it never mutates the netlist, only walks it. license_tier: ORIGINAL

dependencies 1 imports · 3 importers

nx_nxgate_sim.nx nx_latency_metric.nx nx_div_pick.nx nx_latency_metric_test.nx nx_superopt.nx

imports: nx_nxgate_sim.nx

imported by: nx_div_pick.nxnx_latency_metric_test.nxnx_superopt.nx

structs

none

consts

42const NX_LAT_OK: i64 = 0
43const NX_LAT_BAD_KIND: i64 = 1

functions

48func nx_lat_log2_ceil(w: i64) -> i64
60func nx_lat_kind_weight(kind: i64, w: i64) -> i64
102func nx_lat_critical_path(g: *NxGsim, depth: *i64, mode: i64, w: i64) -> i64
143func nx_lat_unit(g: *NxGsim, depth: *i64) -> i64
called by 1: main calls 1: nx_lat_critical_path
146func nx_lat_honest(g: *NxGsim, depth: *i64, w: i64) -> i64