From c064ae6bc37e89c2b4879340051b67fb42cc522f Mon Sep 17 00:00:00 2001 From: Nick Gasson Date: Sat, 7 Jun 2008 14:54:00 +0100 Subject: [PATCH] Generate VHDL for non-blocking assignments --- tgt-vhdl/stmt.cc | 32 +++++++++++++++++++++++++++++++- tgt-vhdl/vhdl_element.cc | 9 +++++++++ tgt-vhdl/vhdl_element.hh | 5 ++++- 3 files changed, 44 insertions(+), 2 deletions(-) diff --git a/tgt-vhdl/stmt.cc b/tgt-vhdl/stmt.cc index eb96339e9..636c4f283 100644 --- a/tgt-vhdl/stmt.cc +++ b/tgt-vhdl/stmt.cc @@ -153,7 +153,37 @@ static int draw_noop(vhdl_process *proc, ivl_statement_t stmt) */ static int draw_nbassign(vhdl_process *proc, ivl_statement_t stmt) { - std::cout << "draw_nbassign" << std::endl; + int nlvals = ivl_stmt_lvals(stmt); + if (nlvals != 1) { + error("Can only have 1 lval at the moment (found %d)", nlvals); + return 1; + } + + ivl_lval_t lval = ivl_stmt_lval(stmt, 0); + ivl_signal_t sig; + if ((sig = ivl_lval_sig(lval))) { + const char *signame = ivl_signal_basename(sig); + + vhdl_expr *rhs = translate_expr(ivl_stmt_rval(stmt)); + if (NULL == rhs) + return 1; + + vhdl_decl *decl = proc->get_parent()->get_decl(signame); + assert(decl); + + vhdl_type *lval_type = decl->get_type()->clone(); + vhdl_var_ref *lval_ref = new vhdl_var_ref(signame, lval_type); + + // TODO: Internal sanity check: + // ensure rhs->get_type() == lval_type + + proc->add_stmt(new vhdl_nbassign_stmt(lval_ref, rhs)); + } + else { + error("Only signals as lvals supported at the moment"); + return 1; + } + return 0; } diff --git a/tgt-vhdl/vhdl_element.cc b/tgt-vhdl/vhdl_element.cc index 2411be773..a3b499a95 100644 --- a/tgt-vhdl/vhdl_element.cc +++ b/tgt-vhdl/vhdl_element.cc @@ -343,6 +343,15 @@ void vhdl_wait_stmt::emit(std::ofstream &of, int level) const of << "wait;"; } +/* + * Create a deep copy of this type, so it can appear in more + * than one place in the AST. + */ +vhdl_type *vhdl_scalar_type::clone() const +{ + return new vhdl_scalar_type(name_.c_str()); +} + vhdl_scalar_type *vhdl_scalar_type::std_logic() { return new vhdl_scalar_type("std_logic"); diff --git a/tgt-vhdl/vhdl_element.hh b/tgt-vhdl/vhdl_element.hh index 0a44e9a6d..28d38b6bf 100644 --- a/tgt-vhdl/vhdl_element.hh +++ b/tgt-vhdl/vhdl_element.hh @@ -54,6 +54,8 @@ public: vhdl_type(const char *name) : name_(name) {} virtual ~vhdl_type() {} + virtual vhdl_type *clone() const = 0; + const std::string &get_name() const { return name_; } protected: std::string name_; @@ -70,6 +72,7 @@ public: : vhdl_type(name) {} void emit(std::ofstream &of, int level) const; + vhdl_type *clone() const; // Common types static vhdl_scalar_type *std_logic(); @@ -179,7 +182,7 @@ public: vhdl_nbassign_stmt(vhdl_var_ref *lhs, vhdl_expr *rhs) : lhs_(lhs), rhs_(rhs) {} - void emit(std::ofstream &of, int level); + void emit(std::ofstream &of, int level) const; private: vhdl_var_ref *lhs_; vhdl_expr *rhs_;