Store packages required with entity rather than globally

Add parent link to architecture and process so code generators can push things higher up
$display now prints blank lines
This commit is contained in:
Nick Gasson 2008-06-04 13:52:56 +01:00
parent dd30c1b39d
commit 4bf2e1669d
6 changed files with 59 additions and 39 deletions

View File

@ -31,8 +31,14 @@
*/
static int generate_vhdl_process(vhdl_entity *ent, ivl_process_t proc)
{
// Create a new process and store it in the entity's
// architecture. This needs to be done first or the
// parent link won't be valid (and draw_stmt needs this
// to add information to the architecture)
vhdl_process *vhdl_proc = new vhdl_process();
ent->get_arch()->add_stmt(vhdl_proc);
ivl_statement_t stmt = ivl_process_stmt(proc);
int rc = draw_stmt(vhdl_proc, stmt);
if (rc != 0)
@ -55,9 +61,6 @@ static int generate_vhdl_process(vhdl_entity *ent, ivl_process_t proc)
ss << ivl_scope_tname(scope);
vhdl_proc->set_comment(ss.str());
// Store it in the entity's architecture
ent->get_arch()->add_stmt(vhdl_proc);
return 0;
}

View File

@ -39,7 +39,8 @@
*/
static int draw_stask_display(vhdl_process *proc, ivl_statement_t stmt)
{
require_package("std.textio");
// Add the package requirement to the containing entity
proc->get_parent()->get_parent()->requires_package("std.textio");
const char *display_line = "Verilog_Display_Line";
@ -53,10 +54,10 @@ static int draw_stask_display(vhdl_process *proc, ivl_statement_t stmt)
// TODO: Write the data into the line
// Write_Line(Output, Verilog_Display_Line)
// WriteLine(Output, Verilog_Display_Line)
vhdl_var_ref *output_ref = new vhdl_var_ref("Output");
vhdl_var_ref *line_ref = new vhdl_var_ref(display_line);
vhdl_pcall_stmt *write_line = new vhdl_pcall_stmt("Write_Line");
vhdl_pcall_stmt *write_line = new vhdl_pcall_stmt("WriteLine");
write_line->add_expr(output_ref);
write_line->add_expr(line_ref);
proc->add_stmt(write_line);

View File

@ -33,11 +33,6 @@ static int g_errors = 0; // Total number of errors encountered
static entity_list_t g_entities; // All entities to emit
typedef std::string package_name_t;
typedef std::list<package_name_t> require_list_t;
static require_list_t g_requires; // External packages required
/*
* Called when an unrecoverable problem is encountered.
@ -78,21 +73,6 @@ void remember_entity(vhdl_entity* ent)
g_entities.push_back(ent);
}
/*
* Add a package to the list of packages that should be
* use-ed at the start of the program.
*/
void require_package(const char *name)
{
package_name_t pname(name);
require_list_t::iterator it;
for (it = g_requires.begin(); it != g_requires.end(); ++it) {
if (*it == pname)
return;
}
g_requires.push_back(pname);
}
extern "C" int target_design(ivl_design_t des)
{
ivl_scope_t *roots;
@ -108,14 +88,6 @@ extern "C" int target_design(ivl_design_t des)
const char *ofname = ivl_design_flag(des, "-o");
std::ofstream outfile(ofname);
// Write all the required packages (and libraries?)
//outfile << "library ieee;" << std::endl;
for (require_list_t::iterator it = g_requires.begin();
it != g_requires.end();
++it)
outfile << "use " << *it << ".all;" << std::endl;
outfile << std::endl;
for (entity_list_t::iterator it = g_entities.begin();
it != g_entities.end();
++it)

View File

@ -102,7 +102,7 @@ vhdl_entity::vhdl_entity(const char *name, const char *derived_from,
vhdl_arch *arch)
: name_(name), arch_(arch), derived_from_(derived_from)
{
arch->parent_ = this;
}
vhdl_entity::~vhdl_entity()
@ -110,8 +110,29 @@ vhdl_entity::~vhdl_entity()
delete arch_;
}
/*
* Add a package to the list of `use' statements before
* the entity.
*/
void vhdl_entity::requires_package(const char *spec)
{
std::string pname(spec);
std::list<std::string>::iterator it;
for (it = uses_.begin(); it != uses_.end(); ++it) {
if (*it == pname)
return;
}
uses_.push_back(spec);
}
void vhdl_entity::emit(std::ofstream &of, int level) const
{
for (std::list<std::string>::const_iterator it = uses_.begin();
it != uses_.end();
++it)
of << "use " << *it << ".all;" << std::endl;
of << std::endl;
emit_comment(of, level);
of << "entity " << name_ << " is";
// ...ports...
@ -123,7 +144,7 @@ void vhdl_entity::emit(std::ofstream &of, int level) const
}
vhdl_arch::vhdl_arch(const char *entity, const char *name)
: name_(name), entity_(entity)
: parent_(NULL), name_(name), entity_(entity)
{
}
@ -136,6 +157,7 @@ vhdl_arch::~vhdl_arch()
void vhdl_arch::add_stmt(vhdl_conc_stmt *stmt)
{
stmt->parent_ = this;
stmts_.push_back(stmt);
}
@ -144,6 +166,12 @@ void vhdl_arch::add_decl(vhdl_decl *decl)
decls_.push_back(decl);
}
vhdl_entity *vhdl_arch::get_parent() const
{
assert(parent_);
return parent_;
}
void vhdl_arch::emit(std::ofstream &of, int level) const
{
emit_comment(of, level);
@ -173,6 +201,12 @@ bool vhdl_arch::have_declared_component(const std::string &name) const
return false;
}
vhdl_arch *vhdl_conc_stmt::get_parent() const
{
assert(parent_);
return parent_;
}
vhdl_process::vhdl_process(const char *name)
: name_(name)
{

View File

@ -26,6 +26,7 @@
#include <string>
class vhdl_entity;
class vhdl_arch;
/*
* Any VHDL syntax element. Each element can also contain a comment.
@ -98,8 +99,14 @@ private:
* processes.
*/
class vhdl_conc_stmt : public vhdl_element {
friend class vhdl_arch; // Can set its parent
public:
vhdl_conc_stmt() : parent_(NULL) {}
virtual ~vhdl_conc_stmt() {}
vhdl_arch *get_parent() const;
private:
vhdl_arch *parent_;
};
typedef std::list<vhdl_conc_stmt*> conc_stmt_list_t;
@ -236,6 +243,7 @@ private:
* An architecture which implements an entity.
*/
class vhdl_arch : public vhdl_element {
friend class vhdl_entity; // Can set its parent
public:
vhdl_arch(const char *entity, const char *name="Behavioural");
virtual ~vhdl_arch();
@ -244,7 +252,9 @@ public:
bool have_declared_component(const std::string &name) const;
void add_decl(vhdl_decl *decl);
void add_stmt(vhdl_conc_stmt *stmt);
vhdl_entity *get_parent() const;
private:
vhdl_entity *parent_;
conc_stmt_list_t stmts_;
decl_list_t decls_;
std::string name_, entity_;
@ -265,12 +275,13 @@ public:
void emit(std::ofstream &of, int level=0) const;
vhdl_arch *get_arch() const { return arch_; }
const std::string &get_name() const { return name_; }
void requires_package(const char *spec);
const std::string &get_derived_from() const { return derived_from_; }
private:
std::string name_;
vhdl_arch *arch_; // Entity may only have a single architecture
std::string derived_from_;
std::list<std::string> uses_;
};
typedef std::list<vhdl_entity*> entity_list_t;

View File

@ -16,7 +16,6 @@ int draw_stmt(vhdl_process *proc, ivl_statement_t stmt);
void remember_entity(vhdl_entity *ent);
vhdl_entity *find_entity(const std::string &tname);
void require_package(const char *name);
#endif /* #ifndef INC_VHDL_TARGET_H */