Cleanup
This commit is contained in:
parent
306e4cfa6b
commit
11c944f5e9
3
t-dll.cc
3
t-dll.cc
|
|
@ -897,8 +897,7 @@ bool dll_target::bufz(const NetBUFZ*net)
|
||||||
// if it is an input / output buffer
|
// if it is an input / output buffer
|
||||||
// This is needed for the SDF interconnect feature
|
// This is needed for the SDF interconnect feature
|
||||||
// to access the buffers directly from the port_info
|
// to access the buffers directly from the port_info
|
||||||
if (obj->is_port_buffer)
|
if (obj->is_port_buffer) {
|
||||||
{
|
|
||||||
scop->module_ports_info[net->port_info_index()].buffer = obj;
|
scop->module_ports_info[net->port_info_index()].buffer = obj;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -160,15 +160,18 @@ program_version
|
||||||
hierarchy_divider
|
hierarchy_divider
|
||||||
: '(' K_DIVIDER '.' ')'
|
: '(' K_DIVIDER '.' ')'
|
||||||
{ sdf_use_hchar = '.';
|
{ sdf_use_hchar = '.';
|
||||||
if (sdf_flag_inform) vpi_printf("SDF INFO: %s:%d: Divider: \"%c\"\n", sdf_parse_path, @1.first_line, sdf_use_hchar);
|
if (sdf_flag_inform) vpi_printf("SDF INFO: %s:%d: Divider: \"%c\"\n",
|
||||||
|
sdf_parse_path, @1.first_line, sdf_use_hchar);
|
||||||
}
|
}
|
||||||
| '(' K_DIVIDER '/' ')'
|
| '(' K_DIVIDER '/' ')'
|
||||||
{ sdf_use_hchar = '/';
|
{ sdf_use_hchar = '/';
|
||||||
if (sdf_flag_inform) vpi_printf("SDF INFO: %s:%d: Divider: \"%c\"\n", sdf_parse_path, @1.first_line, sdf_use_hchar);
|
if (sdf_flag_inform) vpi_printf("SDF INFO: %s:%d: Divider: \"%c\"\n",
|
||||||
|
sdf_parse_path, @1.first_line, sdf_use_hchar);
|
||||||
}
|
}
|
||||||
| '(' K_DIVIDER HCHAR ')'
|
| '(' K_DIVIDER HCHAR ')'
|
||||||
{ /* sdf_use_hchar no-change */
|
{ /* sdf_use_hchar no-change */
|
||||||
if (sdf_flag_inform) vpi_printf("SDF INFO: %s:%d: Divider: \"%c\"\n", sdf_parse_path, @1.first_line, sdf_use_hchar);
|
if (sdf_flag_inform) vpi_printf("SDF INFO: %s:%d: Divider: \"%c\"\n",
|
||||||
|
sdf_parse_path, @1.first_line, sdf_use_hchar);
|
||||||
}
|
}
|
||||||
;
|
;
|
||||||
|
|
||||||
|
|
@ -176,11 +179,13 @@ voltage
|
||||||
: '(' K_VOLTAGE rtriple ')'
|
: '(' K_VOLTAGE rtriple ')'
|
||||||
{ /* The value must be defined. */
|
{ /* The value must be defined. */
|
||||||
if (! $3.defined) {
|
if (! $3.defined) {
|
||||||
vpi_printf("SDF ERROR: %s:%d: Chosen value not defined.\n", sdf_parse_path, @1.first_line);
|
vpi_printf("SDF ERROR: %s:%d: Chosen value not defined.\n",
|
||||||
}
|
sdf_parse_path, @1.first_line);
|
||||||
else if (sdf_flag_inform) vpi_printf("SDF INFO: %s:%d: Voltage: %f\n",
|
} else if (sdf_flag_inform) {
|
||||||
|
vpi_printf("SDF INFO: %s:%d: Voltage: %f\n",
|
||||||
sdf_parse_path, @2.first_line, $3.value);
|
sdf_parse_path, @2.first_line, $3.value);
|
||||||
}
|
}
|
||||||
|
}
|
||||||
| '(' K_VOLTAGE signed_real_number ')'
|
| '(' K_VOLTAGE signed_real_number ')'
|
||||||
{ if (sdf_flag_inform) vpi_printf("SDF INFO: %s:%d: Voltage: %f\n",
|
{ if (sdf_flag_inform) vpi_printf("SDF INFO: %s:%d: Voltage: %f\n",
|
||||||
sdf_parse_path, @2.first_line, $3);
|
sdf_parse_path, @2.first_line, $3);
|
||||||
|
|
@ -338,9 +343,11 @@ del_def
|
||||||
/* | '(' K_INTERCONNECT port_instance port_instance delval_list ')' */
|
/* | '(' K_INTERCONNECT port_instance port_instance delval_list ')' */
|
||||||
| '(' K_INTERCONNECT port_interconnect port_interconnect delval_list ')'
|
| '(' K_INTERCONNECT port_interconnect port_interconnect delval_list ')'
|
||||||
{
|
{
|
||||||
if (sdf_flag_inform) vpi_printf("SDF INFO: %s:%d: INTERCONNECT with "
|
if (sdf_flag_inform) {
|
||||||
|
vpi_printf("SDF INFO: %s:%d: INTERCONNECT with "
|
||||||
"port1 = %s index = %d, port2 = %s index = %d\n",
|
"port1 = %s index = %d, port2 = %s index = %d\n",
|
||||||
sdf_parse_path, @2.first_line, $3.name, $3.index, $4.name, $4.index);
|
sdf_parse_path, @2.first_line, $3.name, $3.index, $4.name, $4.index);
|
||||||
|
}
|
||||||
|
|
||||||
sdf_interconnect_delays($3, $4, &$5, @2.first_line);
|
sdf_interconnect_delays($3, $4, &$5, @2.first_line);
|
||||||
|
|
||||||
|
|
@ -349,7 +356,8 @@ del_def
|
||||||
}
|
}
|
||||||
| '(' K_INTERCONNECT error ')'
|
| '(' K_INTERCONNECT error ')'
|
||||||
{ vpi_printf("SDF ERROR: %s:%d: Invalid/malformed INTERCONNECT\n",
|
{ vpi_printf("SDF ERROR: %s:%d: Invalid/malformed INTERCONNECT\n",
|
||||||
sdf_parse_path, @2.first_line); }
|
sdf_parse_path, @2.first_line);
|
||||||
|
}
|
||||||
;
|
;
|
||||||
|
|
||||||
tchk_def_list
|
tchk_def_list
|
||||||
|
|
|
||||||
|
|
@ -60,11 +60,13 @@ struct interconnect_port_s {
|
||||||
|
|
||||||
extern void sdf_select_instance(const char*celltype, const char*inst,
|
extern void sdf_select_instance(const char*celltype, const char*inst,
|
||||||
const int sdf_lineno);
|
const int sdf_lineno);
|
||||||
|
|
||||||
extern void sdf_iopath_delays(int vpi_edge, const char*src, const char*dst,
|
extern void sdf_iopath_delays(int vpi_edge, const char*src, const char*dst,
|
||||||
const struct sdf_delval_list_s*delval,
|
const struct sdf_delval_list_s*delval,
|
||||||
const int sdf_lineno);
|
const int sdf_lineno);
|
||||||
|
|
||||||
extern void sdf_interconnect_delays(struct interconnect_port_s port1, struct interconnect_port_s port2,
|
extern void sdf_interconnect_delays(struct interconnect_port_s port1,
|
||||||
|
struct interconnect_port_s port2,
|
||||||
const struct sdf_delval_list_s*delval_list,
|
const struct sdf_delval_list_s*delval_list,
|
||||||
const int sdf_lineno);
|
const int sdf_lineno);
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -76,9 +76,11 @@ void sdf_select_instance(const char*celltype, const char*cellinst, const int sdf
|
||||||
|
|
||||||
/* Test for wildcard character */
|
/* Test for wildcard character */
|
||||||
if (cellinst == NULL) {
|
if (cellinst == NULL) {
|
||||||
if (sdf_flag_warning) vpi_printf("SDF WARNING: %s:%d: sorry: "
|
if (sdf_flag_warning) {
|
||||||
|
vpi_printf("SDF WARNING: %s:%d: sorry: "
|
||||||
"Wildcard cell instance specification (*) currently not supported.\n",
|
"Wildcard cell instance specification (*) currently not supported.\n",
|
||||||
sdf_fname, sdf_lineno);
|
sdf_fname, sdf_lineno);
|
||||||
|
}
|
||||||
sdf_cur_cell = 0;
|
sdf_cur_cell = 0;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
@ -151,8 +153,7 @@ vpiHandle get_port_handle(char* port_name, const int sdf_lineno)
|
||||||
// Get occurences of '.' in the name
|
// Get occurences of '.' in the name
|
||||||
int submodules = 0;
|
int submodules = 0;
|
||||||
|
|
||||||
for (int i=0; port_name[i] != '\0'; i++)
|
for (int i=0; port_name[i] != '\0'; i++) {
|
||||||
{
|
|
||||||
if (port_name[i] == '.') submodules++;
|
if (port_name[i] == '.') submodules++;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -160,8 +161,7 @@ vpiHandle get_port_handle(char* port_name, const int sdf_lineno)
|
||||||
char* token = strtok(port_name, ".");;
|
char* token = strtok(port_name, ".");;
|
||||||
|
|
||||||
// Change scope into submodule
|
// Change scope into submodule
|
||||||
while (submodules--)
|
while (submodules--) {
|
||||||
{
|
|
||||||
scope = vpi_handle_by_name(token, scope);
|
scope = vpi_handle_by_name(token, scope);
|
||||||
|
|
||||||
if (!scope) vpi_printf("SDF ERROR: %s:%d: Submodule %s in port path not found!\n", sdf_fname, sdf_lineno, token);
|
if (!scope) vpi_printf("SDF ERROR: %s:%d: Submodule %s in port path not found!\n", sdf_fname, sdf_lineno, token);
|
||||||
|
|
@ -175,14 +175,11 @@ vpiHandle get_port_handle(char* port_name, const int sdf_lineno)
|
||||||
vpiHandle port;
|
vpiHandle port;
|
||||||
vpiHandle port_handle = NULL;
|
vpiHandle port_handle = NULL;
|
||||||
|
|
||||||
while ((port=vpi_scan(port_i)) != NULL)
|
while ((port=vpi_scan(port_i)) != NULL) {
|
||||||
{
|
|
||||||
char *port_name_ = vpi_get_str(vpiName, port) ;
|
char *port_name_ = vpi_get_str(vpiName, port) ;
|
||||||
|
|
||||||
if (strcmp(port_name_, token) == 0)
|
if (strcmp(port_name_, token) == 0) {
|
||||||
{
|
if (port_handle != NULL) {
|
||||||
if (port_handle != NULL)
|
|
||||||
{
|
|
||||||
if (sdf_flag_warning) vpi_printf("SDF WARNING: %s:%d: Found multiple matching ports for %s !\n", sdf_fname, sdf_lineno, token);
|
if (sdf_flag_warning) vpi_printf("SDF WARNING: %s:%d: Found multiple matching ports for %s !\n", sdf_fname, sdf_lineno, token);
|
||||||
}
|
}
|
||||||
port_handle = port;
|
port_handle = port;
|
||||||
|
|
@ -203,13 +200,11 @@ void sdf_interconnect_delays(struct interconnect_port_s port1, struct interconne
|
||||||
vpiHandle port1_handle = get_port_handle(port1.name, sdf_lineno);
|
vpiHandle port1_handle = get_port_handle(port1.name, sdf_lineno);
|
||||||
vpiHandle port2_handle = get_port_handle(port2.name, sdf_lineno);
|
vpiHandle port2_handle = get_port_handle(port2.name, sdf_lineno);
|
||||||
|
|
||||||
if (port1_handle && port2_handle)
|
if (port1_handle && port2_handle) {
|
||||||
{
|
|
||||||
// Get interModPath for the two ports
|
// Get interModPath for the two ports
|
||||||
vpiHandle intermodpath = vpi_handle_multi(vpiInterModPath, port1_handle, port2_handle);
|
vpiHandle intermodpath = vpi_handle_multi(vpiInterModPath, port1_handle, port2_handle);
|
||||||
|
|
||||||
if (intermodpath)
|
if (intermodpath) {
|
||||||
{
|
|
||||||
if (sdf_flag_inform) vpi_printf("SDF INFO: %s:%d: Created a vpiInterModPath\n", sdf_fname, sdf_lineno);
|
if (sdf_flag_inform) vpi_printf("SDF INFO: %s:%d: Created a vpiInterModPath\n", sdf_fname, sdf_lineno);
|
||||||
|
|
||||||
s_vpi_delay delays;
|
s_vpi_delay delays;
|
||||||
|
|
@ -235,14 +230,10 @@ void sdf_interconnect_delays(struct interconnect_port_s port1, struct interconne
|
||||||
|
|
||||||
// Put the new delays
|
// Put the new delays
|
||||||
vpi_put_delays(intermodpath, &delays);
|
vpi_put_delays(intermodpath, &delays);
|
||||||
}
|
} else {
|
||||||
else
|
|
||||||
{
|
|
||||||
vpi_printf("SDF ERROR: %s:%d: Could not find intermodpath!\n", sdf_fname, sdf_lineno);
|
vpi_printf("SDF ERROR: %s:%d: Could not find intermodpath!\n", sdf_fname, sdf_lineno);
|
||||||
}
|
}
|
||||||
}
|
} else {
|
||||||
else
|
|
||||||
{
|
|
||||||
vpi_printf("SDF ERROR: %s:%d: Could not find handles for both ports!\n", sdf_fname, sdf_lineno);
|
vpi_printf("SDF ERROR: %s:%d: Could not find handles for both ports!\n", sdf_fname, sdf_lineno);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -409,10 +400,12 @@ static PLI_INT32 sys_sdf_annotate_calltf(ICARUS_VPI_CONST PLI_BYTE8*name)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (sdf_flag_inform) vpi_printf("SDF INFO: Loading %s from %s:%d\n",
|
if (sdf_flag_inform) {
|
||||||
|
vpi_printf("SDF INFO: Loading %s from %s:%d\n",
|
||||||
fname,
|
fname,
|
||||||
vpi_get_str(vpiFile, callh),
|
vpi_get_str(vpiFile, callh),
|
||||||
(int)vpi_get(vpiLineNo, callh));
|
(int)vpi_get(vpiLineNo, callh));
|
||||||
|
}
|
||||||
|
|
||||||
sdf_fd = fopen(fname, "r");
|
sdf_fd = fopen(fname, "r");
|
||||||
if (sdf_fd == 0) {
|
if (sdf_fd == 0) {
|
||||||
|
|
|
||||||
|
|
@ -1123,7 +1123,7 @@ vvp_fun_intermodpath::vvp_fun_intermodpath(vvp_net_t*net, unsigned width)
|
||||||
delay_[idx] = 0;
|
delay_[idx] = 0;
|
||||||
|
|
||||||
cur_vec4_ = vvp_vector4_t(width, BIT4_X);
|
cur_vec4_ = vvp_vector4_t(width, BIT4_X);
|
||||||
schedule_init_propagate(net_, cur_vec4_); // TODO is this needed?
|
schedule_init_propagate(net_, cur_vec4_);
|
||||||
}
|
}
|
||||||
|
|
||||||
vvp_fun_intermodpath::~vvp_fun_intermodpath()
|
vvp_fun_intermodpath::~vvp_fun_intermodpath()
|
||||||
|
|
@ -1252,12 +1252,11 @@ static vpiHandle intermodpath_iterate(int code, vpiHandle ref)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* This routine will put specific dimension of delay[] values
|
* This routine will put specific dimension of delay[] values
|
||||||
* into a vpiHandle. In this case, we will put
|
* into a vpiHandle. In this case, we will put
|
||||||
* specific delays values in a vpiInterModPath object
|
* specific delays values in a vpiInterModPath object
|
||||||
* TODO code duplication
|
*
|
||||||
*/
|
*/
|
||||||
static void intermodpath_put_delays (vpiHandle ref, p_vpi_delay delays)
|
static void intermodpath_put_delays (vpiHandle ref, p_vpi_delay delays)
|
||||||
{
|
{
|
||||||
|
|
|
||||||
|
|
@ -236,6 +236,8 @@ class vvp_fun_modpath_edge : public vvp_fun_modpath_src {
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* The intermodpath is used to implement the SDF INTERCONNECT feature
|
* The intermodpath is used to implement the SDF INTERCONNECT feature
|
||||||
|
* Upon a (INTERCONNECT ...) statement an intermodpath will be inserted
|
||||||
|
* between port1 and port2 and its delay can be annotated
|
||||||
*/
|
*/
|
||||||
class vvp_fun_intermodpath : public vvp_net_fun_t, private vvp_gen_event_s {
|
class vvp_fun_intermodpath : public vvp_net_fun_t, private vvp_gen_event_s {
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,5 +1,6 @@
|
||||||
/*
|
/*
|
||||||
* Copyright (c) 2008-2022 Stephen Williams (steve@icarus.com)
|
* Copyright (c) 2008-2023 Stephen Williams (steve@icarus.com)
|
||||||
|
* Copyright (c) 2023 Leo Moser (leo.moser@pm.me)
|
||||||
*
|
*
|
||||||
* This source code is free software; you can redistribute it
|
* This source code is free software; you can redistribute it
|
||||||
* and/or modify it in source code form under the terms of the GNU
|
* and/or modify it in source code form under the terms of the GNU
|
||||||
|
|
@ -33,16 +34,6 @@
|
||||||
# include <cmath>
|
# include <cmath>
|
||||||
# include <iostream>
|
# include <iostream>
|
||||||
|
|
||||||
# include "npmos.h"
|
|
||||||
# include "vvp_island.h"
|
|
||||||
# include "resolv.h"
|
|
||||||
# include "bufif.h"
|
|
||||||
# include "latch.h"
|
|
||||||
# include "dff.h"
|
|
||||||
# include "event.h"
|
|
||||||
# include "arith.h"
|
|
||||||
# include "part.h"
|
|
||||||
|
|
||||||
using namespace std;
|
using namespace std;
|
||||||
vpi_mode_t vpi_mode_flag = VPI_MODE_NONE;
|
vpi_mode_t vpi_mode_flag = VPI_MODE_NONE;
|
||||||
FILE*vpi_trace = 0;
|
FILE*vpi_trace = 0;
|
||||||
|
|
@ -1601,8 +1592,7 @@ vpiHandle vpi_handle_multi(PLI_INT32 type,
|
||||||
// even tho the intermodpath is correctly inserted
|
// even tho the intermodpath is correctly inserted
|
||||||
__vpiSignal* output_signal = nullptr;
|
__vpiSignal* output_signal = nullptr;
|
||||||
|
|
||||||
if (port1->get_direction() == vpiOutput && port2->get_direction() == vpiOutput)
|
if (port1->get_direction() == vpiOutput && port2->get_direction() == vpiOutput) {
|
||||||
{
|
|
||||||
vpiHandle scope_port2 = vpi_handle(vpiScope, ref2);
|
vpiHandle scope_port2 = vpi_handle(vpiScope, ref2);
|
||||||
assert(scope_port2);
|
assert(scope_port2);
|
||||||
std::string port2_name(vpi_get_str(vpiName, ref2));
|
std::string port2_name(vpi_get_str(vpiName, ref2));
|
||||||
|
|
@ -1611,13 +1601,11 @@ vpiHandle vpi_handle_multi(PLI_INT32 type,
|
||||||
vpiHandle net_i = vpi_iterate(vpiNet, scope_port2) ;
|
vpiHandle net_i = vpi_iterate(vpiNet, scope_port2) ;
|
||||||
vpiHandle net;
|
vpiHandle net;
|
||||||
|
|
||||||
while ((net = vpi_scan(net_i)) != NULL)
|
while ((net = vpi_scan(net_i)) != NULL) {
|
||||||
{
|
|
||||||
std::string net_name(vpi_get_str(vpiName, net));
|
std::string net_name(vpi_get_str(vpiName, net));
|
||||||
|
|
||||||
// Compare whether the net matches with the port name
|
// Compare whether the net matches with the port name
|
||||||
if (net_name == port2_name)
|
if (net_name == port2_name) {
|
||||||
{
|
|
||||||
output_signal = dynamic_cast<__vpiSignal*>(net);
|
output_signal = dynamic_cast<__vpiSignal*>(net);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -1626,29 +1614,25 @@ vpiHandle vpi_handle_multi(PLI_INT32 type,
|
||||||
vvp_net_t* net1 = port1->get_port();
|
vvp_net_t* net1 = port1->get_port();
|
||||||
vvp_net_t* net2 = port2->get_port();
|
vvp_net_t* net2 = port2->get_port();
|
||||||
|
|
||||||
if (net1 == nullptr || net2 == nullptr)
|
if (net1 == nullptr || net2 == nullptr) {
|
||||||
{
|
|
||||||
fprintf(stderr, "Error: Could not find net. "
|
fprintf(stderr, "Error: Could not find net. "
|
||||||
"Did you run iverilog with '-ginterconnect'?\n");
|
"Did you run iverilog with '-ginterconnect'?\n");
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (net1 == net2)
|
if (net1 == net2) {
|
||||||
{
|
|
||||||
fprintf(stderr, "Error: Net for both ports is the same. "
|
fprintf(stderr, "Error: Net for both ports is the same. "
|
||||||
"Did you pass the same port twice?\n");
|
"Did you pass the same port twice?\n");
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!dynamic_cast<vvp_fun_buft*>(net1->fun))
|
if (!dynamic_cast<vvp_fun_buft*>(net1->fun)) {
|
||||||
{
|
|
||||||
fprintf(stderr, "Error: functor of net1 must be"
|
fprintf(stderr, "Error: functor of net1 must be"
|
||||||
"vvp_fun_buft\n");
|
"vvp_fun_buft\n");
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!dynamic_cast<vvp_fun_buft*>(net2->fun))
|
if (!dynamic_cast<vvp_fun_buft*>(net2->fun)) {
|
||||||
{
|
|
||||||
fprintf(stderr, "Error: functor of net2 must be"
|
fprintf(stderr, "Error: functor of net2 must be"
|
||||||
"vvp_fun_buft\n");
|
"vvp_fun_buft\n");
|
||||||
return nullptr;
|
return nullptr;
|
||||||
|
|
@ -1658,38 +1642,33 @@ vpiHandle vpi_handle_multi(PLI_INT32 type,
|
||||||
vvp_net_ptr_t cur = net1->out_;
|
vvp_net_ptr_t cur = net1->out_;
|
||||||
vvp_net_ptr_t prev = vvp_net_ptr_t(nullptr, 0);
|
vvp_net_ptr_t prev = vvp_net_ptr_t(nullptr, 0);
|
||||||
|
|
||||||
while (cur.ptr())
|
while (cur.ptr()) {
|
||||||
{
|
|
||||||
// Port2 is directly connected to port1
|
// Port2 is directly connected to port1
|
||||||
if (cur.ptr() == net2)
|
if (cur.ptr() == net2) {
|
||||||
{
|
|
||||||
vvp_net_t*new_net = new vvp_net_t;
|
vvp_net_t*new_net = new vvp_net_t;
|
||||||
|
|
||||||
|
// Create new node with intermodpath and connect port2 to it
|
||||||
int width = 1; // TODO
|
int width = 1; // TODO
|
||||||
vvp_fun_intermodpath*obj = new vvp_fun_intermodpath(new_net, width);
|
vvp_fun_intermodpath*obj = new vvp_fun_intermodpath(new_net, width);
|
||||||
new_net->fun = obj;
|
new_net->fun = obj;
|
||||||
new_net->out_ = cur; // TODO pointer to current net
|
new_net->out_ = cur;
|
||||||
|
|
||||||
// Port2 is in the middle of the list
|
// Port2 is in the middle of the list
|
||||||
// Insert intermodpath before port2 and keep everything else intact
|
// Insert intermodpath before port2 and keep everything else intact
|
||||||
if (prev.ptr())
|
if (prev.ptr()) {
|
||||||
{
|
|
||||||
prev.ptr()->port[prev.port()] = vvp_net_ptr_t(new_net, 0); // Point to port 0 of vvp_fun_intermodpath
|
prev.ptr()->port[prev.port()] = vvp_net_ptr_t(new_net, 0); // Point to port 0 of vvp_fun_intermodpath
|
||||||
new_net->port[0] = cur.ptr()->port[cur.port()]; // Connect the next net in list
|
new_net->port[0] = cur.ptr()->port[cur.port()]; // Connect the next net in list
|
||||||
cur.ptr()->port[cur.port()] = vvp_net_ptr_t(nullptr, 0); // Only port2 is connected to intermodpath
|
cur.ptr()->port[cur.port()] = vvp_net_ptr_t(nullptr, 0); // Only port2 is connected to intermodpath
|
||||||
}
|
|
||||||
// Port2 is first in list
|
// Port2 is first in list
|
||||||
// Insert intermodpath before port2 and keep everything else intact
|
// Insert intermodpath before port2 and keep everything else intact
|
||||||
else
|
} else {
|
||||||
{
|
|
||||||
net1->out_ = vvp_net_ptr_t(new_net, 0); // Point to port 0 of vvp_fun_intermodpath
|
net1->out_ = vvp_net_ptr_t(new_net, 0); // Point to port 0 of vvp_fun_intermodpath
|
||||||
new_net->port[0] = cur.ptr()->port[cur.port()]; // Connect the next net in list
|
new_net->port[0] = cur.ptr()->port[cur.port()]; // Connect the next net in list
|
||||||
cur.ptr()->port[cur.port()] = vvp_net_ptr_t(nullptr, 0); // Only port2 is connected to intermodpath
|
cur.ptr()->port[cur.port()] = vvp_net_ptr_t(nullptr, 0); // Only port2 is connected to intermodpath
|
||||||
}
|
}
|
||||||
|
|
||||||
// If both ports are vpiOutput, we have to reassign the __vpiSignal
|
// If both ports are vpiOutput, we have to reassign the __vpiSignal
|
||||||
if (output_signal)
|
if (output_signal) {
|
||||||
{
|
|
||||||
net2->fil = net1->fil;
|
net2->fil = net1->fil;
|
||||||
net1->fil = nullptr;
|
net1->fil = nullptr;
|
||||||
output_signal->node = net2;
|
output_signal->node = net2;
|
||||||
|
|
@ -1707,7 +1686,7 @@ vpiHandle vpi_handle_multi(PLI_INT32 type,
|
||||||
cur = cur.ptr()->port[cur.port()]; // Next net in linked list
|
cur = cur.ptr()->port[cur.port()]; // Next net in linked list
|
||||||
}
|
}
|
||||||
|
|
||||||
std::cout << "sorry: Could not insert intermodpath!" << std::endl;
|
fprintf(stderr, "VPI error: Could not insert intermodpath!\n");
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1159,6 +1159,7 @@ class vvp_net_t {
|
||||||
public: // Method to support $countdrivers
|
public: // Method to support $countdrivers
|
||||||
void count_drivers(unsigned idx, unsigned counts[4]);
|
void count_drivers(unsigned idx, unsigned counts[4]);
|
||||||
|
|
||||||
|
// This needs to be public so that SDF interconnects can be inserted
|
||||||
public:
|
public:
|
||||||
vvp_net_ptr_t out_;
|
vvp_net_ptr_t out_;
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue