 SYMBOL: live-ins
 
 : live-in ( basic-block -- set ) live-ins get at ;
+
+! Assoc mapping basic blocks to sequences of sets of vregs; each sequence
+! is in conrrespondence with a predecessor
+SYMBOL: phi-live-ins
+
+: phi-live-in ( predecessor basic-block -- set )
+    [ predecessors>> index ] keep phi-live-ins get at
+    dup [ nth ] [ 2drop f ] if ;
 
 ! Assoc mapping basic blocks to sets of vregs
 SYMBOL: live-outs

: map-unique ( seq quot -- assoc )
    map concat unique ; inline

: gen-set ( basic-block -- seq )
    instructions>> [ uses-vregs ] map-unique ;

: kill-set ( basic-block -- seq )
    instructions>> [ defs-vregs ] map-unique ;

: update-live-in ( basic-block -- changed? )
    [
        [ [ gen-set ] [ live-out ] bi assoc-union ]
        [ kill-set ]
        bi assoc-diff
    ] keep live-ins get maybe-set-at ;

: update-live-out ( basic-block -- changed? )
    [ successors>> [ live-in ] map assoc-combine ] keep
    live-outs get maybe-set-at ;

: liveness-step ( basic-block -- )

: compute-liveness ( rpo -- )
    <hashed-dlist> work-list set
    H{ } clone live-ins set
    H{ } clone phi-live-ins set
    H{ } clone live-outs set
    <reversed> add-to-work-list
    work-list get [ liveness-step ] slurp-deque ;