Try to synthesize a single
(vl-latchcode-synth-always x scary-regs vars cvtregs delta careful-p vecp) → (mv new-x? cvtregs delta)
Function:
(defun vl-latchcode-synth-always (x scary-regs vars cvtregs delta careful-p vecp) (declare (xargs :guard (and (vl-always-p x) (and (string-listp scary-regs) (setp scary-regs)) (vl-vardecllist-p vars) (string-listp cvtregs) (vl-delta-p delta) (booleanp careful-p)))) (let ((__function__ 'vl-latchcode-synth-always)) (declare (ignorable __function__)) (b* (((vl-always x) x) ((unless (or (eq x.type :vl-always) (eq x.type :vl-always-latch))) (mv x cvtregs delta)) ((when (eq x.type :vl-always-latch)) (mv x cvtregs (dwarn :type :vl-latchcode-fail :msg "~a0: always_latch blocks are not yet implemented." :args (list x)))) (warnings (vl-delta->warnings delta)) ((mv warnings test lhs rhs delay) (if careful-p (vl-careful-match-latch x warnings) (vl-careless-match-latch x warnings))) (delta (change-vl-delta delta :warnings warnings)) ((unless test) (mv x cvtregs delta)) (lhs-names (mergesort (vl-expr-names lhs))) ((unless (consp lhs-names)) (mv x cvtregs (dwarn :type :vl-latchcode-fail :msg "~a0: not synthesize a latch since the lhs doesn't ~ even have any names? lhs: ~a1." :args (list x lhs-names)))) (warning (vl-always-check-regs lhs-names vars x)) ((when warning) (mv x cvtregs (vl-warn-delta warning))) (lhs-scary (intersect lhs-names scary-regs)) ((unless (emptyp lhs-scary)) (mv x cvtregs (dwarn :type :vl-latchcode-fail :msg "~a0: cowardly refusing to synthesize always block ~ for ~a1 since other always blocks write to ~a1." :args (list x lhs-scary)))) ((unless (eql (vl-expr->finalwidth test) 1)) (mv x cvtregs (dwarn :type :vl-latchcode-fail :msg "~a0: statement is too complex to synthesize. The ~ enable for this latch is ~a1, which we expected ~ to have width 1, but its width is ~a2." :args (list x test (vl-expr->finalwidth test))))) (width (vl-expr->finalwidth lhs)) ((unless (posp width)) (mv x cvtregs (dwarn :type :vl-latchcode-fail :msg "~a0: can't synthesize always block becasue the width ~ of the lhs, ~a1, hasn't been computed or isn't a ~ positive number. Its width is ~a2." :args (list x lhs width)))) ((vl-delta delta) delta) (lhs-name (car lhs-names)) ((mv inst-name nf) (vl-namefactory-plain-name (cat lhs-name "_latch") delta.nf)) ((when vecp) (b* ((addmods (vl-make-n-bit-latch-vec width (or delay 0))) (latchmod (car addmods)) (inst (vl-simple-instantiate latchmod inst-name (list lhs test rhs) :loc x.loc)) (delta (change-vl-delta delta :nf nf :modinsts (cons inst delta.modinsts) :addmods (append-without-guard addmods delta.addmods)))) (mv nil (append lhs-names cvtregs) delta))) ((mv next-name nf) (vl-namefactory-plain-name (cat lhs-name "_next") nf)) ((mv delfree-name nf) (vl-namefactory-plain-name (cat lhs-name "_delfree") nf)) ((mv next-expr next-decl) (vl-occform-mkwire next-name width :loc x.loc)) ((mv delfree-expr delfree-decl) (vl-occform-mkwire delfree-name width :loc x.loc)) (delfree-decl (change-vl-vardecl delfree-decl :atts (acons "VL_TARGET_REG" lhs (vl-vardecl->atts delfree-decl)))) (next-ass (make-vl-assign :lvalue next-expr :expr rhs :loc x.loc)) (addmods (vl-make-n-bit-latch width)) (inst (vl-simple-instantiate (car addmods) inst-name (list delfree-expr test next-expr) :loc x.loc)) (main-ass (make-vl-assign :lvalue lhs :expr delfree-expr :loc x.loc :delay (and delay (let ((amt-expr (vl-make-index delay))) (make-vl-gatedelay :rise amt-expr :fall amt-expr :high amt-expr))))) (cvtregs (append lhs-names cvtregs)) (delta (change-vl-delta delta :nf nf :vardecls (list* next-decl delfree-decl delta.vardecls) :assigns (list* next-ass main-ass delta.assigns) :modinsts (cons inst delta.modinsts) :addmods (append-without-guard addmods delta.addmods)))) (mv nil cvtregs delta))))
Theorem:
(defthm return-type-of-vl-latchcode-synth-always.new-x? (implies (and (force (vl-always-p x)) (force (if (string-listp scary-regs) (setp scary-regs) 'nil)) (force (vl-vardecllist-p vars)) (force (string-listp cvtregs)) (force (vl-delta-p delta)) (force (booleanp careful-p))) (b* (((mv ?new-x? ?cvtregs ?delta) (vl-latchcode-synth-always x scary-regs vars cvtregs delta careful-p vecp))) (equal (vl-always-p new-x?) (if new-x? t nil)))) :rule-classes :rewrite)
Theorem:
(defthm string-listp-of-vl-latchcode-synth-always.cvtregs (implies (and (force (vl-always-p x)) (force (if (string-listp scary-regs) (setp scary-regs) 'nil)) (force (vl-vardecllist-p vars)) (force (string-listp cvtregs)) (force (vl-delta-p delta)) (force (booleanp careful-p))) (b* (((mv ?new-x? ?cvtregs ?delta) (vl-latchcode-synth-always x scary-regs vars cvtregs delta careful-p vecp))) (string-listp cvtregs))) :rule-classes :rewrite)
Theorem:
(defthm vl-delta-p-of-vl-latchcode-synth-always.delta (implies (and (force (vl-always-p x)) (force (if (string-listp scary-regs) (setp scary-regs) 'nil)) (force (vl-vardecllist-p vars)) (force (string-listp cvtregs)) (force (vl-delta-p delta)) (force (booleanp careful-p))) (b* (((mv ?new-x? ?cvtregs ?delta) (vl-latchcode-synth-always x scary-regs vars cvtregs delta careful-p vecp))) (vl-delta-p delta))) :rule-classes :rewrite)