Update vlog95 target to handle buffers/tran_vps used to prevent port collapsing.

(cherry picked from commit 40d2a49b90)
This commit is contained in:
Martin Whitaker 2020-05-07 23:05:52 +01:00
parent b644d86e91
commit 7b4e5ffc84
2 changed files with 28 additions and 12 deletions

View File

@ -1,5 +1,5 @@
/*
* Copyright (C) 2011-2018 Cary R. (cygcary@yahoo.com)
* Copyright (C) 2011-2020 Cary R. (cygcary@yahoo.com)
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@ -294,16 +294,17 @@ static unsigned is_local_nexus(ivl_scope_t scope, ivl_nexus_t nex)
ivl_nexus_ptr_t nex_ptr = ivl_nexus_ptr(nex, idx);
ivl_signal_t sig = ivl_nexus_ptr_sig(nex_ptr);
if (! sig) continue;
/* Check to see if there is an output port driving into
* the local scope. */
/* Check to see if there is an output or inout port
* driving into the local scope. */
if ((scope == ivl_scope_parent(ivl_signal_scope(sig))) &&
(ivl_signal_port(sig) == IVL_SIP_OUTPUT)) {
((ivl_signal_port(sig) == IVL_SIP_OUTPUT) ||
(ivl_signal_port(sig) == IVL_SIP_INOUT))) {
has_output_driver = 1;
continue;
}
if (scope != ivl_signal_scope(sig)) continue;
if ((ivl_nexus_ptr_drive1(nex_ptr) != IVL_DR_HiZ) ||
(ivl_nexus_ptr_drive0(nex_ptr) != IVL_DR_HiZ)) continue;
(ivl_nexus_ptr_drive0(nex_ptr) != IVL_DR_HiZ)) continue;
if (ivl_signal_local(sig)) {
is_local = 1;
} else {
@ -311,9 +312,10 @@ static unsigned is_local_nexus(ivl_scope_t scope, ivl_nexus_t nex)
break;
}
}
/* We return is_local=true only if there is not an output driving
* into this scope. This is needed since some module outputs are
* combined with a concatenation. */
/* We return is_local=true only if there is not an output or inout
* driving into this scope. This is needed since some module outputs
* are combined with a concatenation and some inouts are connected
* with a tran_VP. */
return is_local && !has_output_driver;
}
@ -1707,7 +1709,8 @@ void emit_logic(ivl_scope_t scope, ivl_net_logic_t nlogic)
fprintf(vlog_out, "bufif1");
dly_count = 3;
break;
// case IVL_LO_BUFT:
case IVL_LO_BUFT:
return;
case IVL_LO_BUFZ:
emit_bufz(scope, nlogic);
return;

View File

@ -1,5 +1,5 @@
/*
* Copyright (C) 2011-2016 Cary R. (cygcary@yahoo.com)
* Copyright (C) 2011-2020 Cary R. (cygcary@yahoo.com)
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@ -711,6 +711,8 @@ static unsigned is_local_input(ivl_scope_t scope, ivl_nexus_t nex)
// HERE: Does this work correctly with an array reference created from @*?
void emit_name_of_nexus(ivl_scope_t scope, ivl_nexus_t nex, unsigned allow_UD)
{
unsigned idx;
ivl_scope_t mod_scope;
/* First look in the local scope for the nexus name. */
if (find_signal_in_nexus(scope, nex)) return;
@ -737,8 +739,19 @@ void emit_name_of_nexus(ivl_scope_t scope, ivl_nexus_t nex, unsigned allow_UD)
// multiples are found in a given scope. This all needs to be before
// the constant code.
/* It is possible that the nexus does not have a name. For this
* case do not print an actual name. */
/* It is possible that the nexus does not have a name. First check
if it drives another nexus through a transparent buffer. */
for (idx = 0; idx < ivl_nexus_ptrs(nex); idx += 1) {
ivl_nexus_ptr_t nex_ptr = ivl_nexus_ptr(nex, idx);
ivl_net_logic_t nlogic = ivl_nexus_ptr_log(nex_ptr);
if (nlogic && ivl_logic_type(nlogic) == IVL_LO_BUFT
&& ivl_logic_pin(nlogic, 1) == nex) {
emit_name_of_nexus(scope, ivl_logic_pin(nlogic, 0), allow_UD);
return;
}
}
/* If not, do not print an actual name. */
fprintf(vlog_out, "/* Empty */");
// dump_nexus_information(scope, nex);
}