diff --git a/vhdlpp/parse.y b/vhdlpp/parse.y index 156cce7ad..3a6df7ca1 100644 --- a/vhdlpp/parse.y +++ b/vhdlpp/parse.y @@ -251,7 +251,8 @@ const VType*parse_type_by_name(perm_string name) %type expression_logical expression_logical_and expression_logical_or %type expression_logical_xnor expression_logical_xor %type name -%type shift_expression simple_expression term waveform_element +%type shift_expression signal_declaration_assign_opt +%type simple_expression term waveform_element %type interface_element_expression %type waveform waveform_elements @@ -405,11 +406,12 @@ block_configuration_opt ; block_declarative_item - : K_signal identifier_list ':' subtype_indication ';' + : K_signal identifier_list ':' subtype_indication + signal_declaration_assign_opt ';' { /* Save the signal declaration in the block_signals map. */ for (std::list::iterator cur = $2->begin() ; cur != $2->end() ; ++cur) { - Signal*sig = new Signal(*cur, $4); + Signal*sig = new Signal(*cur, $4, $5); FILE_NAME(sig, @1); active_scope->bind_name(*cur, sig); } @@ -1715,6 +1717,11 @@ sequential_statement shift_expression : simple_expression { $$ = $1; } ; +signal_declaration_assign_opt + : VASSIGN expression { $$ = $2; } + | { $$ = 0; } + ; + /* * The LRM rule for simple_expression is: * simple_expression ::= [sign] term { adding_operator term } diff --git a/vhdlpp/vsignal.cc b/vhdlpp/vsignal.cc index de7685300..f0d60fee7 100644 --- a/vhdlpp/vsignal.cc +++ b/vhdlpp/vsignal.cc @@ -18,13 +18,14 @@ */ # include "vsignal.h" +# include "expression.h" # include "vtype.h" # include using namespace std; -SigVarBase::SigVarBase(perm_string nam, const VType*typ) -: name_(nam), type_(typ), refcnt_sequ_(0) +SigVarBase::SigVarBase(perm_string nam, const VType*typ, Expression*exp) +: name_(nam), type_(typ), init_expr_(exp), refcnt_sequ_(0) { } @@ -37,7 +38,7 @@ void SigVarBase::type_elaborate_(VType::decl_t&decl) decl.type = type_; } -int Signal::emit(ostream&out, Entity*, Architecture*) +int Signal::emit(ostream&out, Entity*ent, Architecture*arc) { int errors = 0; @@ -46,6 +47,12 @@ int Signal::emit(ostream&out, Entity*, Architecture*) if (peek_refcnt_sequ_() > 0) decl.reg_flag = true; errors += decl.emit(out, peek_name_()); + + Expression*init_expr = peek_init_expr(); + if (init_expr) { + out << " = "; + init_expr->emit(out, ent, arc); + } out << ";" << endl; return errors; } diff --git a/vhdlpp/vsignal.h b/vhdlpp/vsignal.h index 76d3167cb..14cbe586f 100644 --- a/vhdlpp/vsignal.h +++ b/vhdlpp/vsignal.h @@ -25,11 +25,12 @@ class Architecture; class Entity; +class Expression; class SigVarBase : public LineInfo { public: - SigVarBase(perm_string name, const VType*type); + SigVarBase(perm_string name, const VType*type, Expression*init_expr); virtual ~SigVarBase(); const VType* peek_type(void) const { return type_; } @@ -46,9 +47,12 @@ class SigVarBase : public LineInfo { void type_elaborate_(VType::decl_t&decl); + Expression* peek_init_expr() const { return init_expr_; } + private: perm_string name_; const VType*type_; + Expression*init_expr_; unsigned refcnt_sequ_; @@ -60,7 +64,7 @@ class SigVarBase : public LineInfo { class Signal : public SigVarBase { public: - Signal(perm_string name, const VType*type); + Signal(perm_string name, const VType*type, Expression*init_expr); int emit(ostream&out, Entity*ent, Architecture*arc); }; @@ -78,13 +82,13 @@ inline void SigVarBase::count_ref_sequ() refcnt_sequ_ += 1; } -inline Signal::Signal(perm_string name, const VType*type) -: SigVarBase(name, type) +inline Signal::Signal(perm_string name, const VType*type, Expression*init_expr) +: SigVarBase(name, type, init_expr) { } inline Variable::Variable(perm_string name, const VType*type) -: SigVarBase(name, type) +: SigVarBase(name, type, 0) { }