-
Notifications
You must be signed in to change notification settings - Fork 3
[Rule] 3SAT to REGISTER SUFFICIENCY #872
Description
Source: 3-SATISFIABILITY (3SAT)
Target: REGISTER SUFFICIENCY
Motivation: Establishes NP-completeness of Register Sufficiency — determining the minimum number of registers to evaluate an expression DAG without recomputation. This is the foundational NP-completeness result for compiler register allocation by Sethi (1975), connecting Boolean satisfiability to compiler optimization.
Reference: Garey & Johnson, Computers and Intractability, A11 PO1; Sethi, R. (1975). "Complete Register Allocation Problems." SIAM Journal on Computing, 4(3), pp. 226–248.
GJ Source Entry
[PO1] REGISTER SUFFICIENCY
INSTANCE: Directed acyclic graph G = (V,A), positive integer K.
QUESTION: Is there a computation for G that uses K or fewer registers?Reference: [Sethi, 1975]. Transformation from 3SAT.
Comment: Remains NP-complete even if all vertices have out-degree 2 or less.
Reduction Algorithm
Given a KSatisfiability<K3> instance with n variables and m clauses, construct a RegisterSufficiency instance (G', K) as follows:
Variable gadgets (diamond sub-DAGs)
For each variable x_i (i = 1, ..., n), create 4 vertices forming a diamond:
s_i(source): no predecessors if i = 1; depends on k_{i-1} otherwiset_i(true literal): depends on s_if_i(false literal): depends on s_ik_i(kill): depends on t_i and f_i
The variable gadgets form a chain: s_i depends on k_{i-1} for i > 1.
Clause gadgets
For each clause C_j = (l_1 ∨ l_2 ∨ l_3), create a vertex c_j with dependencies:
- If literal l is positive (x_i): c_j depends on t_i
- If literal l is negative (¬x_i): c_j depends on f_i
Sink
A single sink vertex σ depends on k_n and all clause vertices c_1, ..., c_m.
Vertex numbering (0-indexed)
- Variable gadget i (0-based): s_i = 4i, t_i = 4i+1, f_i = 4i+2, k_i = 4i+3
- Clause vertices: c_j = 4n + j
- Sink: σ = 4n + m
Register bound
K is set to the peak register pressure of the constructive ordering for the worst-case satisfying assignment. The constructive ordering processes variable gadgets sequentially (s_i, then one literal, then the other, then k_i), then clause vertices, then the sink. During variable i processing, registers hold at most: the chain predecessor + source + one literal + clause-referenced literals from earlier variables that are still alive. The bound is determined by the clause structure.
Solution extraction
From an evaluation ordering (config vector):
- τ(x_i) = 1 if config[t_i] > config[f_i], else τ(x_i) = 0
Correctness
- (⇒) If the formula is satisfiable, the constructive ordering achieves ≤ K registers. For each variable, the "chosen" literal (matching the satisfying assignment) is evaluated second; its live range is short because clause vertices consuming it are evaluated soon after. The "unchosen" literal is evaluated first and consumed by k_i immediately.
- (⇐) If an ordering achieves ≤ K registers, the variable gadget chain forces sequential processing. The register pressure constraint forces at least one literal per clause to have a short live range (be "chosen"), which means that literal's truth value satisfies the clause.
Size Overhead
| Target metric (code name) | Expression |
|---|---|
num_vertices |
4 * num_vars + num_clauses + 1 |
num_arcs |
4 * num_vars - 1 + 4 * num_clauses + 1 |
bound |
Computed from clause structure (peak register pressure) |
Derivation: 4 vertices per variable (diamond) + 1 per clause + 1 sink. Arcs: 3 per diamond + (n-1) chain edges + 3 per clause + m sink-to-clause arcs + 1 sink-to-k_n arc.
Implementation Note
RegisterSufficiency currently has 0 outgoing reductions (no ILP solver). A RegisterSufficiency → ILP rule should be implemented alongside this rule:
- Binary assignment matrix: x[v][t] ∈ {0,1} (vertex v at position t in evaluation order)
- Permutation constraints: each row/col sums to 1
- Topological: for arc (u,v), position(u) < position(v)
- Live-range tracking: binary liveness indicators l[v][t] = 1 if vertex v is alive at step t (computed but has unfinished dependents)
- Register bound: for each step t, Σ_v l[v][t] ≤ K
- Feasibility objective (Value = Or)
Example
Source (KSatisfiability):
n = 4 variables (x_1, x_2, x_3, x_4), m = 3 clauses:
- C_1 = (x_1 ∨ ¬x_2 ∨ x_3)
- C_2 = (¬x_1 ∨ x_4 ∨ ¬x_3)
- C_3 = (x_2 ∨ ¬x_4 ∨ x_3)
Target (RegisterSufficiency):
- 4·4 + 3 + 1 = 20 vertices
- Variable gadget vertices (16):
- x_1: s_0=0, t_0=1, f_0=2, k_0=3
- x_2: s_1=4, t_1=5, f_1=6, k_1=7
- x_3: s_2=8, t_2=9, f_2=10, k_2=11
- x_4: s_3=12, t_3=13, f_3=14, k_3=15
- Clause vertices (3): c_0=16, c_1=17, c_2=18
- Sink: σ=19
Arcs (diamond chain):
- x_1 diamond: (1,0), (2,0), (3,1), (3,2)
- Chain: (4,3)
- x_2 diamond: (5,4), (6,4), (7,5), (7,6)
- Chain: (8,7)
- x_3 diamond: (9,8), (10,8), (11,9), (11,10)
- Chain: (12,11)
- x_4 diamond: (13,12), (14,12), (15,13), (15,14)
Clause arcs:
- C_1 = (x_1 ∨ ¬x_2 ∨ x_3): (16,1), (16,6), (16,9)
- C_2 = (¬x_1 ∨ x_4 ∨ ¬x_3): (17,2), (17,13), (17,10)
- C_3 = (x_2 ∨ ¬x_4 ∨ x_3): (18,5), (18,14), (18,9)
Sink arcs: (19,15), (19,16), (19,17), (19,18)
Satisfying assignment: x_1=1, x_2=0, x_3=1, x_4=1
- C_1: x_1=T ✓, C_2: x_4=T ✓, C_3: x_3=T ✓
Evaluation order (encoding x_1=1, x_2=0, x_3=1, x_4=1):
s_0, f_0, t_0, k_0, s_1, t_1, f_1, k_1, s_2, f_2, t_2, k_2, s_3, f_3, t_3, k_3, c_0, c_1, c_2, σ
Each "chosen" literal (t_0, f_1, t_2, t_3) is evaluated second in its diamond, encoding the truth value. Clause vertices are evaluated after all variable gadgets, consuming their literal dependencies.
Non-satisfying: x_1=0, x_2=1, x_3=0, x_4=0 → C_1: (F ∨ F ∨ F) fails. Under this assignment, all three literals referenced by C_1 (t_0, f_1, t_2) are "unchosen" (evaluated first, long live ranges), causing register pressure to exceed K.
Validation Method
- Closed-loop test: reduce KSatisfiability to RegisterSufficiency, solve via ILP, extract truth assignment from evaluation ordering, verify all clauses satisfied
- Test with both satisfiable and unsatisfiable instances
- Verified by PR docs: batch verify-reduction — 34 implementable reductions verified #992 with 11K automated checks (constructor + adversary scripts)
References
- Sethi, R. (1975). "Complete Register Allocation Problems." SIAM Journal on Computing, 4(3), pp. 226–248.
- Garey, M. R., & Johnson, D. S. (1979). Computers and Intractability, A11 PO1.
Metadata
Metadata
Assignees
Labels
Type
Projects
Status