Commit 8c6d0db8 authored by Christian Fibich's avatar Christian Fibich Committed by Stefan Tauner
Browse files

Switched to '/' as HIERSEP, Use instantiation path (<top>[/<cell>]/<net> as net paths

parent e972b096
......@@ -31,6 +31,7 @@ package FIJI::Netlist;
use strict;
use warnings;
use diagnostics;
use Scalar::Util 'blessed';
use Log::Log4perl qw(get_logger :easy);
......@@ -42,7 +43,7 @@ use Data::Dumper;
use FIJI::VHDL;
use constant HIERSEP => "|";
use constant HIERSEP => "/";
use constant FIJI_NAMESPACE_PREFIX => "fiji_";
use constant FIJI_PORT_IN_POSTFIX => "_inj_i";
use constant FIJI_PORT_OUT_POSTFIX => "_ori_o";
......@@ -166,8 +167,9 @@ sub get_nets {
# my $nets_ref = {'metadata' => [], 'names' => [], 'nets' => []};
my $nets_ref = [];
my $hier = "";
foreach my $mod ($self->{'nl'}->top_modules_sorted) {
$self->_get_subnets($nets_ref, $mod, $hier);
my $top = $self->get_toplevel_module();
if ($top->isa("Verilog::Netlist::Module")) {
$self->_get_subnets($nets_ref, $top, $hier);
}
return $nets_ref;
}
......@@ -197,11 +199,15 @@ sub _extract_low_high {
sub _get_subnets {
my $logger = get_logger("");
my ($self, $nets_ref, $mod, $hier) = @_;
my ($self, $nets_ref, $mod, $hier, $instname) = @_;
my $thishier = $hier;
$thishier .= HIERSEP if $thishier ne "";
$thishier .= $mod->name;
if (defined $instname) {
$thishier .= $instname;
} else {
$thishier .= $mod->name;
}
foreach my $n ($mod->nets) {
if (defined($n->msb) && defined($n->lsb)) {
......@@ -219,7 +225,7 @@ sub _get_subnets {
foreach my $cell ($mod->cells) {
if (defined($cell->submod)) {
$self->_get_subnets($nets_ref, $cell->submod, $thishier);
$self->_get_subnets($nets_ref, $cell->submod, $thishier, $cell->name);
}
}
}
......@@ -548,7 +554,7 @@ sub instrument_net {
if ($netname->{'netname'} eq $net->name) {
$netname->{'netname'} = $net_name_tmp; # FIXME: do we need to force a re-link (by deleting $connection->nets)?
# This net is a vector if the underlying net is a bus and we do not just select a single bit
if (defined($net->msb) || (!defined($netname->{'msb'}) || $netname->{'msb'} != $netname->{'lsb'})) {
if (defined($net->msb) && (!defined($netname->{'msb'}) || $netname->{'msb'} != $netname->{'lsb'})) {
$driver_is_vector = 1;
}
}
......@@ -1178,16 +1184,76 @@ sub _extract_netpath_elements {
return "Can not parse an empty net.";
}
my @net_split = split(/\|/, $netpath);
my $mod_name = $net_split[-2];
my $net_string = $net_split[-1];
my $hiersep = HIERSEP;
my @net_split;
# check if escaped identifiers are present
if ($netpath =~ /\\/) {
my $idx = 0;
# walk through string
# check if character at offset is backslash
# if yes, search for first space
# after space (or beginning, if no backslash) search for the HIERSEP
# if no HIERSEP, this is the net name
# push that substring
while($idx < length($netpath)) {
my $after_space = $idx;
if (substr($netpath,$idx,1) eq "\\") {
$after_space = index($netpath,' ',$idx);
return "Malformed extended identifier: missing trailing space as delimiter" if ($after_space == -1);
}
my $end = index($netpath,HIERSEP,$after_space);
$end = length($netpath) if ($end == -1);
push (@net_split, substr($netpath,$idx,$end-$idx));
$idx = $end+1;
}
} else {
# if not, we can split easily
@net_split = split(/\Q$hiersep\E/, $netpath);
}
if (@net_split < 2) {
return "Net description is not complete: <toplevel_mod>[|<cell>]|<net name>"
}
my $top_name = $net_split[0];
my $mod = $self->{'nl'}->find_module($top_name);
if (!(defined $mod && $mod->isa("Verilog::Netlist::Module") && $mod->is_top())) {
return "Net path toplevel module $top_name does not exist";
}
my $i;
for ($i = 1; $i < @net_split-1; $i++) {
my $cell = $mod->find_cell($net_split[$i]);
if (!(defined $cell && $cell->isa("Verilog::Netlist::Cell"))) {
return "Could not find cell ".$net_split[$i]." in $netpath in netlist $self->{'filename'}'";
}
$mod = $cell->submod();
}
my $netstring_elements = $self->_extract_netstring_elements($net_split[$i]);
return $netstring_elements if (ref($netstring_elements) ne "HASH");
my $net = $mod->find_net($netstring_elements->{'net_name'});
if (!(defined $net && $net->isa("Verilog::Netlist::Net"))) {
return "Could not find net ".$netstring_elements->{'net_name'}." in $netpath in netlist $self->{'filename'}'";
}
my $mod_name = $mod->name;
my $net_string = $net_split[$i];
if (defined($netpath_elements)) {
$netpath_elements->{'mod_name'} = $mod_name;
$netpath_elements->{'mod'} = $mod;
$netpath_elements->{'mod_name'} = $mod_name;
$netpath_elements->{'net'} = $net;
$netpath_elements->{'net_string'} = $net_string;
return undef;
}
return {'mod_name' => $mod_name, 'net_string' => $net_string};
return {'mod' => $mod, 'mod_name' => $mod_name, 'net' => $net, 'net_string' => $net_string};
}
## @method private _extract_netname_elements($net_string)
......@@ -1254,25 +1320,23 @@ sub get_netdescriptor_from_path {
return "$netpath is not a valid net path.";
}
if (ref($netpath_elements) ne "HASH") {
return $netpath_elements;
}
my $net_descr = $self->_extract_netstring_elements($netpath_elements->{'net_string'});
if (ref($net_descr) ne "HASH") {
return $net_descr;
}
my $mod = $self->{'nl'}->find_module($netpath_elements->{mod_name});
if (!blessed($mod) || !$mod->isa("Verilog::Netlist::Module")) {
return $mod;
}
my $mod = $netpath_elements->{'mod'};
$net_descr->{'mod'} = $mod;
my $net_name = $net_descr->{'net_name'};
my $msb = $net_descr->{'msb'};
my $lsb = $net_descr->{'lsb'};
my $net = $mod->find_net($net_name);
if (!blessed($net) || !$net->isa("Verilog::Netlist::Net")) {
return "Could not find net \"" . $mod->name . HIERSEP . $net_name . "\" in netlist $self->{'filename'}'";
}
my $net = $netpath_elements->{'net'};
$net_descr->{'net'} = $net;
# if the net in the netlist contains a pin range the input netpath...
......
......@@ -186,7 +186,7 @@ sub _match_nets {
$self->Busy;
# check if regex is valid:
eval {qr/$regex/};
eval {"" =~ m!$regex!};
if ($@) {
my $msg = "Error in regular expression:\n$@";
my $d = $self->FIJIModalDialog(-text=>$msg,-wraplength=>200,-title=>'Error')->Show();
......@@ -196,7 +196,7 @@ sub _match_nets {
# filter nets by regex
my @matching_nets;
for my $net (@{$self->{'nets'}}) {
push @matching_nets, $net if ($net =~ m/$regex/);
push @matching_nets, $net if ($net =~ m!$regex!);
}
my @filtered_nets = sort(@matching_nets);
......
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment