PEIdent::elaborate_{expr,lval}(): Use new symbol_search()

The PEIdent elaborate_expr() and elaborate_lval() are sort of open-coding
the path traversal implemented by the new symbol_search() using the old
symbol_search().

Switch them over to use the new symbol search as it is better at handling
the corner cases and is also less code.

Signed-off-by: Lars-Peter Clausen <lars@metafoo.de>
This commit is contained in:
Lars-Peter Clausen 2022-12-24 07:56:33 -08:00
parent cc2ba4f8cb
commit 862b118098
2 changed files with 29 additions and 57 deletions

View File

@ -4322,12 +4322,6 @@ NetExpr* PEIdent::elaborate_expr(Design*des, NetScope*scope,
{
bool need_const = NEED_CONST & flags;
NetNet* net = 0;
ivl_type_t cls_val = 0;
const NetExpr*par = 0;
ivl_type_t par_type = 0;
NetEvent* eve = 0;
NetScope*use_scope = scope;
if (package_) {
use_scope = des->find_package(package_->pscope_name());
@ -4338,50 +4332,44 @@ NetExpr* PEIdent::elaborate_expr(Design*des, NetScope*scope,
return tmp;
}
symbol_search(this, des, use_scope, path_, net, par, eve, par_type, cls_val);
symbol_search_results sr;
symbol_search(this, des, use_scope, path_, &sr);
if (net == 0 && gn_system_verilog() && path_.size() >= 2) {
// NOTE: this is assuming the member_path is only one
// component long, and that the use_path will wind up
// being the path to the variable. This is not
// necessarily true. Should fix this.
pform_name_t use_path = path_;
name_component_t member_comp = use_path.back();
use_path.pop_back();
if (!sr.net) {
cerr << get_fileline() << ": error: Unable to bind variable `"
<< path_ << "' in `" << scope_path(use_scope) << "'" << endl;
des->errors++;
return nullptr;
}
ivl_assert(*this, net == 0);
symbol_search(this, des, use_scope, use_path, net, par, eve,
par_type, cls_val);
NetNet *net = sr.net;
if (net == 0) {
// Nope, no struct/class with member.
if (!sr.path_tail.empty()) {
if (net->struct_type()) {
return check_for_struct_members(this, des, use_scope, net,
sr.path_head.back().index,
sr.path_tail);
} else if (net->class_type()) {
const name_component_t member_comp = sr.path_tail.front();
} else if (net->struct_type() != 0) {
pform_name_t member_path;
member_path.push_back( member_comp );
return check_for_struct_members(this, des, use_scope,
net, use_path.back().index,
member_path);
} else if (net->class_type()!=0) {
if (debug_elaborate) {
cerr << get_fileline() << ": PEIdent::elaborate_expr: "
<< "Ident " << use_path
<< "Ident " << sr.path_head
<< " look for property " << member_comp << endl;
}
if (sr.path_tail.size() > 1) {
cerr << get_fileline() << ": sorry: "
<< "Nested member path not yet supported in this context."
<< endl;
return nullptr;
}
return elaborate_expr_class_field_(des, scope, net,
member_comp, 0, flags);
}
}
if (net == 0) {
cerr << get_fileline() << ": error: Unable to bind variable `"
<< path_ << "' in `" << scope_path(use_scope) << "'" << endl;
des->errors += 1;
return 0;
}
if (debug_elaborate) {
cerr << get_fileline() << ": PEIdent::elaborate_expr: "
<< "Found net " << net->name() << " for expr " << *this << endl;

View File

@ -159,9 +159,6 @@ NetAssign_* PEIdent::elaborate_lval(Design*des,
bool is_cassign,
bool is_force) const
{
NetNet* reg = 0;
const NetExpr*par = 0;
NetEvent* eve = 0;
if (debug_elaborate) {
cerr << get_fileline() << ": PEIdent::elaborate_lval: "
@ -182,25 +179,12 @@ NetAssign_* PEIdent::elaborate_lval(Design*des,
ivl_assert(*this, use_scope);
}
/* Try to find the base part of the path that names the
variable. The remainer is the member path. For example, if
the path is a.b.c.d, and a.b is the path to a variable,
then a.b becomes the base_path and c.d becomes the
member_path. If we cannot find the variable with any
prefix, then the base_path will be empty after this loop
and reg will remain nil. */
pform_name_t base_path = path_;
pform_name_t member_path;
while (reg == 0 && !base_path.empty()) {
symbol_search(this, des, use_scope, base_path, reg, par, eve);
// Found it!
if (reg != 0) break;
// Not found. Try to pop another name off the base_path
// and push it to the front of the member_path.
member_path.push_front( base_path.back() );
base_path.pop_back();
}
symbol_search_results sr;
symbol_search(this, des, use_scope, path_, &sr);
NetNet *reg = sr.net;
pform_name_t &base_path = sr.path_head;
pform_name_t &member_path = sr.path_tail;
/* The l-value must be a variable. If not, then give up and
print a useful error message. */