Handle typedefs in $root scope.

This commit is contained in:
Stephen Williams 2013-12-15 04:07:31 +00:00
parent d1c9dd554b
commit b0491b9c54
5 changed files with 47 additions and 10 deletions

View File

@ -1081,7 +1081,7 @@ description /* IEEE1800-2005: A.1.2 */
| nature_declaration | nature_declaration
| package_declaration | package_declaration
| discipline_declaration | discipline_declaration
| timeunits_declaration | package_item
| KK_attribute '(' IDENTIFIER ',' STRING ',' STRING ')' | KK_attribute '(' IDENTIFIER ',' STRING ',' STRING ')'
{ perm_string tmp3 = lex_strings.make($3); { perm_string tmp3 = lex_strings.make($3);
pform_set_type_attrib(tmp3, $5, $7); pform_set_type_attrib(tmp3, $5, $7);
@ -2362,6 +2362,11 @@ struct_union_member /* IEEE 1800-2012 A.2.2.1 */
tmp->names .reset($3); tmp->names .reset($3);
$$ = tmp; $$ = tmp;
} }
| error ';'
{ yyerror(@2, "Error in struct/union member.");
yyerrok;
$$ = 0;
}
; ;
case_item case_item

View File

@ -28,6 +28,7 @@
class Module; class Module;
class PPackage; class PPackage;
class PUdp; class PUdp;
class data_type_t;
/* /*
* These are maps of the modules and primitives parsed from the * These are maps of the modules and primitives parsed from the
@ -36,6 +37,7 @@ class PUdp;
*/ */
extern std::map<perm_string,Module*> pform_modules; extern std::map<perm_string,Module*> pform_modules;
extern std::map<perm_string,PUdp*> pform_primitives; extern std::map<perm_string,PUdp*> pform_primitives;
extern std::map<perm_string,data_type_t*> pform_typedefs;
extern std::map<perm_string,PPackage*> pform_packages; extern std::map<perm_string,PPackage*> pform_packages;
extern void pform_dump(std::ostream&out, const PPackage*pac); extern void pform_dump(std::ostream&out, const PPackage*pac);

View File

@ -46,12 +46,15 @@
/* /*
* The pform_modules is a map of the modules that have been defined in * The pform_modules is a map of the modules that have been defined in
* the top level. This should not contain nested modules/programs. * the top level. This should not contain nested modules/programs.
* pform_primitives is similar, but for UDP primitives.
*/ */
map<perm_string,Module*> pform_modules; map<perm_string,Module*> pform_modules;
/*
*/
map<perm_string,PUdp*> pform_primitives; map<perm_string,PUdp*> pform_primitives;
/*
* typedefs in the $root scope go here.
*/
map<perm_string,data_type_t*>pform_typedefs;
std::string vlltype::get_fileline() const std::string vlltype::get_fileline() const
{ {
@ -505,7 +508,13 @@ PWire*pform_get_make_wire_in_scope(perm_string name, NetNet::Type net_type, NetN
void pform_set_typedef(perm_string name, data_type_t*data_type) void pform_set_typedef(perm_string name, data_type_t*data_type)
{ {
data_type_t*&ref = lexical_scope->typedefs[name]; // If we are in a lexical scope (i.e. a package or module)
// then put the typedef into that scope. Otherwise, put it
// into the $root scope.
data_type_t*&ref = lexical_scope
? lexical_scope->typedefs[name]
: pform_typedefs[name];
ivl_assert(*data_type, ref == 0); ivl_assert(*data_type, ref == 0);
ref = data_type; ref = data_type;
@ -514,15 +523,25 @@ void pform_set_typedef(perm_string name, data_type_t*data_type)
} }
} }
static data_type_t* test_type_identifier_in_root(perm_string name)
{
map<perm_string,data_type_t*>::iterator cur = pform_typedefs.find(name);
if (cur != pform_typedefs.end())
return cur->second;
else
return 0;
}
data_type_t* pform_test_type_identifier(const char*txt) data_type_t* pform_test_type_identifier(const char*txt)
{ {
// If there is no lexical_scope yet, then there is NO WAY the
// identifier can be a type_identifier.
if (lexical_scope == 0)
return 0;
perm_string name = lex_strings.make(txt); perm_string name = lex_strings.make(txt);
// If there is no lexical_scope yet, then look only in the
// $root scope for typedefs.
if (lexical_scope == 0) {
return test_type_identifier_in_root(name);
}
LexicalScope*cur_scope = lexical_scope; LexicalScope*cur_scope = lexical_scope;
do { do {
map<perm_string,data_type_t*>::iterator cur; map<perm_string,data_type_t*>::iterator cur;
@ -552,6 +571,10 @@ data_type_t* pform_test_type_identifier(const char*txt)
cur_scope = cur_scope->parent_scope(); cur_scope = cur_scope->parent_scope();
} while (cur_scope); } while (cur_scope);
// See if there is a typedef in the $root scope.
if (data_type_t*tmp = test_type_identifier_in_root(name))
return tmp;
return 0; return 0;
} }

View File

@ -170,7 +170,10 @@ void uarray_type_t::pform_dump(ostream&out, unsigned indent) const
void struct_type_t::pform_dump(ostream&out, unsigned indent) const void struct_type_t::pform_dump(ostream&out, unsigned indent) const
{ {
out << setw(indent) << "" << "Struct " << (packed_flag?"packed":"unpacked") out << setw(indent) << "" << "Struct " << (packed_flag?"packed":"unpacked")
<< " with " << members->size() << " members" << endl; << " with " << (members.get()==0? 0 : members->size()) << " members" << endl;
if (members.get()==0)
return;
for (list<struct_member_t*>::iterator cur = members->begin() for (list<struct_member_t*>::iterator cur = members->begin()
; cur != members->end() ; ++ cur) { ; cur != members->end() ; ++ cur) {
struct_member_t*curp = *cur; struct_member_t*curp = *cur;

View File

@ -26,8 +26,12 @@ ivl_variable_type_t struct_type_t::figure_packed_base_type(void) const
if (! packed_flag) if (! packed_flag)
return IVL_VT_NO_TYPE; return IVL_VT_NO_TYPE;
if (members.get() == 0)
return IVL_VT_NO_TYPE;
ivl_variable_type_t base_type = IVL_VT_BOOL; ivl_variable_type_t base_type = IVL_VT_BOOL;
ivl_assert(*this, members.get());
for (list<struct_member_t*>::iterator cur = members->begin() for (list<struct_member_t*>::iterator cur = members->begin()
; cur != members->end() ; ++ cur) { ; cur != members->end() ; ++ cur) {