Create an Architecture class and bind them to their entities.
This commit is contained in:
parent
dfa6370187
commit
30d689016a
|
|
@ -59,7 +59,7 @@ LIBS = @LIBS@ @EXTRALIBS@
|
||||||
|
|
||||||
M = StringHeap.o LineInfo.o
|
M = StringHeap.o LineInfo.o
|
||||||
|
|
||||||
O = main.o compiler.o entity.o entity_elaborate.o \
|
O = main.o architec.o compiler.o entity.o entity_elaborate.o \
|
||||||
lexor.o lexor_keyword.o parse.o vhdlreal.o vhdlint.o $M
|
lexor.o lexor_keyword.o parse.o vhdlreal.o vhdlint.o $M
|
||||||
|
|
||||||
all: dep vhdlpp@EXEEXT@
|
all: dep vhdlpp@EXEEXT@
|
||||||
|
|
@ -86,6 +86,10 @@ dep:
|
||||||
vhdlpp@EXEEXT@: $O
|
vhdlpp@EXEEXT@: $O
|
||||||
$(CXX) -o vhdlpp@EXEEXT@ $(LDFLAGS) $O $(LIBS)
|
$(CXX) -o vhdlpp@EXEEXT@ $(LDFLAGS) $O $(LIBS)
|
||||||
|
|
||||||
|
%.o: $(srcdir)/../libmisc/%.cc
|
||||||
|
$(CXX) $(CPPFLAGS) $(CXXFLAGS) @DEPENDENCY_FLAG@ -c $< -o $*.o
|
||||||
|
mv $*.d dep/$*.d
|
||||||
|
|
||||||
%.o: %.cc vhdlpp_config.h
|
%.o: %.cc vhdlpp_config.h
|
||||||
$(CXX) $(CPPFLAGS) $(CXXFLAGS) @DEPENDENCY_FLAG@ -c $< -o $*.o
|
$(CXX) $(CPPFLAGS) $(CXXFLAGS) @DEPENDENCY_FLAG@ -c $< -o $*.o
|
||||||
mv $*.d dep/$*.d
|
mv $*.d dep/$*.d
|
||||||
|
|
@ -123,4 +127,4 @@ stamp-vhdlpp_config-h: $(srcdir)/vhdlpp_config.h.in ../config.status
|
||||||
vhplpp_config.h: stamp-vhdlpp_config-h
|
vhplpp_config.h: stamp-vhdlpp_config-h
|
||||||
|
|
||||||
|
|
||||||
-include $(patsubst %.o, dep/%.d, $O)
|
-include $(patsubst %.o, dep/%.d, $O $M)
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,16 @@
|
||||||
|
|
||||||
|
vhdlpp COMMAND LINE FLAGS:
|
||||||
|
|
||||||
|
-D <token>
|
||||||
|
Debug flags. The token can be
|
||||||
|
|
||||||
|
* yydebug | no-yydebug
|
||||||
|
|
||||||
|
* entities=<path>
|
||||||
|
|
||||||
|
-V
|
||||||
|
Display version on stdout
|
||||||
|
|
||||||
|
-v
|
||||||
|
Verbose: Display version on stderr, and enable verbose messages to
|
||||||
|
stderr.
|
||||||
|
|
@ -0,0 +1,29 @@
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2011 Stephen Williams (steve@icarus.com)
|
||||||
|
*
|
||||||
|
* This source code is free software; you can redistribute it
|
||||||
|
* and/or modify it in source code form under the terms of the GNU
|
||||||
|
* General Public License as published by the Free Software
|
||||||
|
* Foundation; either version 2 of the License, or (at your option)
|
||||||
|
* any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software
|
||||||
|
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
|
||||||
|
*/
|
||||||
|
|
||||||
|
# include "architec.h"
|
||||||
|
|
||||||
|
Architecture::Architecture(perm_string name)
|
||||||
|
: name_(name)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
Architecture::~Architecture()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,41 @@
|
||||||
|
#ifndef __architec_H
|
||||||
|
#define __architec_H
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2011Stephen Williams (steve@icarus.com)
|
||||||
|
*
|
||||||
|
* This source code is free software; you can redistribute it
|
||||||
|
* and/or modify it in source code form under the terms of the GNU
|
||||||
|
* General Public License as published by the Free Software
|
||||||
|
* Foundation; either version 2 of the License, or (at your option)
|
||||||
|
* any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software
|
||||||
|
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
|
||||||
|
*/
|
||||||
|
|
||||||
|
# include "StringHeap.h"
|
||||||
|
# include "LineInfo.h"
|
||||||
|
|
||||||
|
class Architecture : public LineInfo {
|
||||||
|
|
||||||
|
public:
|
||||||
|
Architecture(perm_string name);
|
||||||
|
~Architecture();
|
||||||
|
|
||||||
|
perm_string get_name() const { return name_; }
|
||||||
|
|
||||||
|
void dump(ostream&out, perm_string of_entity) const;
|
||||||
|
|
||||||
|
private:
|
||||||
|
perm_string name_;
|
||||||
|
|
||||||
|
private: // Not implemented
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
||||||
|
|
@ -0,0 +1,83 @@
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2011 Stephen Williams (steve@icarus.com)
|
||||||
|
*
|
||||||
|
* This source code is free software; you can redistribute it
|
||||||
|
* and/or modify it in source code form under the terms of the GNU
|
||||||
|
* General Public License as published by the Free Software
|
||||||
|
* Foundation; either version 2 of the License, or (at your option)
|
||||||
|
* any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software
|
||||||
|
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
|
||||||
|
* Picture Elements, Inc., 777 Panoramic Way, Berkeley, CA 94704.
|
||||||
|
*/
|
||||||
|
|
||||||
|
# include "entity.h"
|
||||||
|
# include "architec.h"
|
||||||
|
# include <fstream>
|
||||||
|
# include <iomanip>
|
||||||
|
|
||||||
|
static ostream& operator << (ostream&out, port_mode_t that)
|
||||||
|
{
|
||||||
|
switch (that) {
|
||||||
|
case PORT_NONE:
|
||||||
|
out << "NO-PORT";
|
||||||
|
break;
|
||||||
|
case PORT_IN:
|
||||||
|
out << "IN";
|
||||||
|
break;
|
||||||
|
case PORT_OUT:
|
||||||
|
out << "OUT";
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
out << "PORT-????";
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
return out;
|
||||||
|
}
|
||||||
|
|
||||||
|
void dump_design_entities(const char*path)
|
||||||
|
{
|
||||||
|
ofstream file (path);
|
||||||
|
for (map<perm_string,Entity*>::iterator cur = design_entities.begin()
|
||||||
|
; cur != design_entities.end() ; ++cur) {
|
||||||
|
cur->second->dump(file);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void Entity::dump(ostream&out) const
|
||||||
|
{
|
||||||
|
out << "entity " << name_
|
||||||
|
<< " file=" << get_fileline() << endl;
|
||||||
|
if (ports.size() == 0) {
|
||||||
|
out << " No ports" << endl;
|
||||||
|
} else {
|
||||||
|
out << " PORTS:" << endl;
|
||||||
|
for (vector<InterfacePort*>::const_iterator cur = ports.begin()
|
||||||
|
; cur != ports.end() ; ++cur) {
|
||||||
|
InterfacePort*item = *cur;
|
||||||
|
out << setw(6) << "" << item->name
|
||||||
|
<< " : " << item->mode
|
||||||
|
<< ", type=" << item->type_name
|
||||||
|
<< ", file=" << item->get_fileline() << endl;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
for (map<perm_string,Architecture*>::const_iterator cur = arch_.begin()
|
||||||
|
; cur != arch_.end() ; ++cur) {
|
||||||
|
cur->second->dump(out, name_);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void Architecture::dump(ostream&out, perm_string of_entity) const
|
||||||
|
{
|
||||||
|
out << "architecture " << name_
|
||||||
|
<< " of entity " << of_entity
|
||||||
|
<< " file=" << get_fileline() << endl;
|
||||||
|
}
|
||||||
|
|
@ -19,55 +19,26 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
# include "entity.h"
|
# include "entity.h"
|
||||||
# include <fstream>
|
# include "architec.h"
|
||||||
# include <iomanip>
|
|
||||||
|
|
||||||
using namespace std;
|
using namespace std;
|
||||||
|
|
||||||
std::map<perm_string,Entity*> design_entities;
|
std::map<perm_string,Entity*> design_entities;
|
||||||
|
|
||||||
static ostream& operator << (ostream&out, port_mode_t that)
|
Entity::Entity(perm_string name)
|
||||||
|
: name_(name)
|
||||||
{
|
{
|
||||||
switch (that) {
|
|
||||||
case PORT_NONE:
|
|
||||||
out << "NO-PORT";
|
|
||||||
break;
|
|
||||||
case PORT_IN:
|
|
||||||
out << "IN";
|
|
||||||
break;
|
|
||||||
case PORT_OUT:
|
|
||||||
out << "OUT";
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
out << "PORT-????";
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
return out;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void dump_design_entity(ostream&out, Entity*obj)
|
Entity::~Entity()
|
||||||
{
|
{
|
||||||
out << "entity " << obj->name << " file=" << obj->get_fileline() << endl;
|
|
||||||
if (obj->ports.size() == 0) {
|
|
||||||
out << " No ports" << endl;
|
|
||||||
} else {
|
|
||||||
out << " PORTS:" << endl;
|
|
||||||
for (vector<InterfacePort*>::iterator cur = obj->ports.begin()
|
|
||||||
; cur != obj->ports.end() ; ++cur) {
|
|
||||||
InterfacePort*item = *cur;
|
|
||||||
out << setw(6) << "" << item->name
|
|
||||||
<< " : " << item->mode
|
|
||||||
<< ", type=" << item->type_name
|
|
||||||
<< ", file=" << item->get_fileline() << endl;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void dump_design_entities(const char*path)
|
Architecture* Entity::add_architecture(Architecture*that)
|
||||||
{
|
{
|
||||||
ofstream file (path);
|
if (Architecture*tmp = arch_ [that->get_name()]) {
|
||||||
for (map<perm_string,Entity*>::iterator cur = design_entities.begin()
|
return tmp;
|
||||||
; cur != design_entities.end() ; ++cur) {
|
|
||||||
dump_design_entity(file, cur->second);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return arch_[that->get_name()] = that;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -26,6 +26,8 @@
|
||||||
|
|
||||||
typedef enum { PORT_NONE=0, PORT_IN, PORT_OUT } port_mode_t;
|
typedef enum { PORT_NONE=0, PORT_IN, PORT_OUT } port_mode_t;
|
||||||
|
|
||||||
|
class Architecture;
|
||||||
|
|
||||||
class InterfacePort : public LineInfo {
|
class InterfacePort : public LineInfo {
|
||||||
public:
|
public:
|
||||||
// Port direction from the source code.
|
// Port direction from the source code.
|
||||||
|
|
@ -39,12 +41,31 @@ class InterfacePort : public LineInfo {
|
||||||
class Entity : public LineInfo {
|
class Entity : public LineInfo {
|
||||||
|
|
||||||
public:
|
public:
|
||||||
|
Entity(perm_string name);
|
||||||
|
~Entity();
|
||||||
|
|
||||||
|
// Entities have names.
|
||||||
|
perm_string get_name() const { return name_; }
|
||||||
|
|
||||||
|
// bind an architecture to the entity, and return the
|
||||||
|
// Architecture that was bound. If there was a previous
|
||||||
|
// architecture with the same name bound, then do not replace
|
||||||
|
// the architecture and instead return the old
|
||||||
|
// value. The caller can tell that the bind worked if the
|
||||||
|
// returned pointer is the same as the passed pointer.
|
||||||
|
Architecture* add_architecture(Architecture*);
|
||||||
|
|
||||||
int elaborate();
|
int elaborate();
|
||||||
|
|
||||||
|
void dump(ostream&out) const;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
perm_string name;
|
|
||||||
std::vector<InterfacePort*> ports;
|
std::vector<InterfacePort*> ports;
|
||||||
|
|
||||||
|
private:
|
||||||
|
perm_string name_;
|
||||||
|
|
||||||
|
std::map<perm_string,Architecture*>arch_;
|
||||||
};
|
};
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
|
|
||||||
|
|
@ -42,9 +42,9 @@ int Entity::elaborate()
|
||||||
int errors = 0;
|
int errors = 0;
|
||||||
|
|
||||||
if (verbose_flag)
|
if (verbose_flag)
|
||||||
cerr << "Elaborate entity " << name << "..." << endl;
|
cerr << "Elaborate entity " << name_ << "..." << endl;
|
||||||
|
|
||||||
cout << "module " << name;
|
cout << "module " << name_;
|
||||||
|
|
||||||
// If there are ports, emit them.
|
// If there are ports, emit them.
|
||||||
if (ports.size() > 0) {
|
if (ports.size() > 0) {
|
||||||
|
|
|
||||||
|
|
@ -24,7 +24,8 @@
|
||||||
# include "vhdlreal.h"
|
# include "vhdlreal.h"
|
||||||
# include "compiler.h"
|
# include "compiler.h"
|
||||||
# include "parse_api.h"
|
# include "parse_api.h"
|
||||||
# include <string.h>
|
# include "parse_misc.h"
|
||||||
|
# include "architec.h"
|
||||||
# include <cstdarg>
|
# include <cstdarg>
|
||||||
# include <list>
|
# include <list>
|
||||||
|
|
||||||
|
|
@ -100,6 +101,12 @@ architecture_body
|
||||||
K_of IDENTIFIER
|
K_of IDENTIFIER
|
||||||
K_is
|
K_is
|
||||||
K_begin architecture_statement_part K_end K_architecture_opt ';'
|
K_begin architecture_statement_part K_end K_architecture_opt ';'
|
||||||
|
{ Architecture*tmp = new Architecture(lex_strings.make($2));
|
||||||
|
FILE_NAME(tmp, @1);
|
||||||
|
bind_architecture_to_entity($4, tmp);
|
||||||
|
delete[]$2;
|
||||||
|
delete[]$4;
|
||||||
|
}
|
||||||
| K_architecture IDENTIFIER
|
| K_architecture IDENTIFIER
|
||||||
K_of IDENTIFIER
|
K_of IDENTIFIER
|
||||||
K_is
|
K_is
|
||||||
|
|
@ -150,11 +157,8 @@ design_units
|
||||||
/* As an entity is declared, add it to the map of design entities. */
|
/* As an entity is declared, add it to the map of design entities. */
|
||||||
entity_declaration
|
entity_declaration
|
||||||
: K_entity IDENTIFIER K_is entity_header K_end K_entity_opt ';'
|
: K_entity IDENTIFIER K_is entity_header K_end K_entity_opt ';'
|
||||||
{ Entity*tmp = new Entity;
|
{ Entity*tmp = new Entity(lex_strings.make($2));
|
||||||
FILE_NAME(tmp, @1);
|
FILE_NAME(tmp, @1);
|
||||||
// Store the name
|
|
||||||
tmp->name = lex_strings.make($2);
|
|
||||||
delete[]$2;
|
|
||||||
// Transfer the ports
|
// Transfer the ports
|
||||||
std::list<InterfacePort*>*ports = $4;
|
std::list<InterfacePort*>*ports = $4;
|
||||||
while (ports->size() > 0) {
|
while (ports->size() > 0) {
|
||||||
|
|
@ -163,15 +167,14 @@ entity_declaration
|
||||||
}
|
}
|
||||||
delete ports;
|
delete ports;
|
||||||
// Save the entity in the entity map.
|
// Save the entity in the entity map.
|
||||||
design_entities[tmp->name] = tmp;
|
design_entities[tmp->get_name()] = tmp;
|
||||||
|
delete[]$2;
|
||||||
}
|
}
|
||||||
| K_entity IDENTIFIER K_is entity_header K_end K_entity_opt IDENTIFIER ';'
|
| K_entity IDENTIFIER K_is entity_header K_end K_entity_opt IDENTIFIER ';'
|
||||||
{ Entity*tmp = new Entity;
|
{ Entity*tmp = new Entity(lex_strings.make($2));
|
||||||
FILE_NAME(tmp, @1);
|
FILE_NAME(tmp, @1);
|
||||||
// Store the name
|
if(tmp->get_name() != $7) {
|
||||||
tmp->name = lex_strings.make($2);
|
errormsg(@1, "Syntax error in entity clause. \n");
|
||||||
if(strcmp($2, $7) != 0) {
|
|
||||||
errormsg(@1, "Syntax error in entity clause. \n"); yyerrok;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
delete[]$2;
|
delete[]$2;
|
||||||
|
|
@ -184,7 +187,7 @@ entity_declaration
|
||||||
}
|
}
|
||||||
delete ports;
|
delete ports;
|
||||||
// Save the entity in the entity map.
|
// Save the entity in the entity map.
|
||||||
design_entities[tmp->name] = tmp;
|
design_entities[tmp->get_name()] = tmp;
|
||||||
}
|
}
|
||||||
;
|
;
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,51 @@
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2011 Stephen Williams (steve@icarus.com)
|
||||||
|
*
|
||||||
|
* This source code is free software; you can redistribute it
|
||||||
|
* and/or modify it in source code form under the terms of the GNU
|
||||||
|
* General Public License as published by the Free Software
|
||||||
|
* Foundation; either version 2 of the License, or (at your option)
|
||||||
|
* any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software
|
||||||
|
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
|
||||||
|
* Picture Elements, Inc., 777 Panoramic Way, Berkeley, CA 94704.
|
||||||
|
*/
|
||||||
|
|
||||||
|
# include "parse_misc.h"
|
||||||
|
# include "parse_api.h"
|
||||||
|
# include "entity.h"
|
||||||
|
# include "architec.h"
|
||||||
|
# include "compiler.h"
|
||||||
|
# include <iostream>
|
||||||
|
|
||||||
|
using namespace std;
|
||||||
|
|
||||||
|
void bind_architecture_to_entity(const char*ename, Architecture*arch)
|
||||||
|
{
|
||||||
|
perm_string ekey = lex_strings.make(ename);
|
||||||
|
std::map<perm_string,Entity*>::const_iterator idx = design_entities.find(ekey);
|
||||||
|
if (idx == design_entities.end()) {
|
||||||
|
cerr << arch->get_fileline() << ": error: No entity " << ekey
|
||||||
|
<< " for architecture " << arch->get_name()
|
||||||
|
<< "." << endl;
|
||||||
|
parse_errors += 1;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
Architecture*old_arch = idx->second->add_architecture(arch);
|
||||||
|
if (old_arch != arch) {
|
||||||
|
cerr << arch->get_fileline() << ": error: "
|
||||||
|
<< "Architecture " << arch->get_name()
|
||||||
|
<< " for entity " << idx->second->get_name()
|
||||||
|
<< " is already defined here: " << old_arch->get_fileline() << endl;
|
||||||
|
parse_errors += 1;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,26 @@
|
||||||
|
#ifndef __parse_misc_H
|
||||||
|
#define __parse_misc_H
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2011 Stephen Williams (steve@icarus.com)
|
||||||
|
*
|
||||||
|
* This source code is free software; you can redistribute it
|
||||||
|
* and/or modify it in source code form under the terms of the GNU
|
||||||
|
* General Public License as published by the Free Software
|
||||||
|
* Foundation; either version 2 of the License, or (at your option)
|
||||||
|
* any later version.
|
||||||
|
*
|
||||||
|
* This program is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
* GNU General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with this program; if not, write to the Free Software
|
||||||
|
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
|
||||||
|
*/
|
||||||
|
|
||||||
|
class Architecture;
|
||||||
|
|
||||||
|
extern void bind_architecture_to_entity(const char*ename, Architecture*arch);
|
||||||
|
|
||||||
|
#endif
|
||||||
Loading…
Reference in New Issue