add instance name correlation between module and bitstream generation
This commit is contained in:
parent
cb147c1180
commit
4b7a9dfa63
|
@ -8,7 +8,9 @@
|
|||
#include "vtr_assert.h"
|
||||
|
||||
#include "sides.h"
|
||||
#include "vpr_types.h"
|
||||
#include "fpga_x2p_utils.h"
|
||||
#include "fpga_x2p_pbtypes_utils.h"
|
||||
#include "circuit_library_utils.h"
|
||||
#include "fpga_x2p_naming.h"
|
||||
|
||||
|
@ -372,6 +374,28 @@ std::string generate_grid_port_name(const vtr::Point<size_t>& coordinate,
|
|||
return port_name;
|
||||
}
|
||||
|
||||
/*********************************************************************
|
||||
* Generate the port name for a Grid
|
||||
* This is a wrapper function for generate_port_name()
|
||||
* which can automatically decode the port name by the pin side and height
|
||||
*********************************************************************/
|
||||
std::string generate_grid_side_port_name(const std::vector<std::vector<t_grid_tile>>& grids,
|
||||
const vtr::Point<size_t>& coordinate,
|
||||
const e_side& side,
|
||||
const size_t& pin_id) {
|
||||
/* Output the pins on the side*/
|
||||
size_t height = find_grid_pin_height(grids, coordinate, pin_id);
|
||||
if (1 != grids[coordinate.x()][coordinate.y()].type->pinloc[height][side][pin_id]) {
|
||||
Side side_manager(side);
|
||||
vpr_printf(TIO_MESSAGE_ERROR,
|
||||
"(File:%s, [LINE%d])Fail to generate a grid pin (x=%lu, y=%lu, height=%lu, side=%s, index=%d)\n",
|
||||
__FILE__, __LINE__,
|
||||
coordinate.x(), coordinate.y(), height, side_manager.c_str(), pin_id);
|
||||
exit(1);
|
||||
}
|
||||
return generate_grid_port_name(coordinate, height, side, pin_id, true);
|
||||
}
|
||||
|
||||
/*********************************************************************
|
||||
* Generate the port name for a reserved sram port, i.e., BLB/WL port
|
||||
* When port_type is BLB, a string denoting to the reserved BLB port is generated
|
||||
|
@ -742,13 +766,29 @@ std::string generate_sb_memory_instance_name(const std::string& prefix,
|
|||
const size_t& track_id,
|
||||
const std::string& postfix) {
|
||||
std::string instance_name(prefix);
|
||||
instance_name += std::string("_") + Side(sb_side).to_string();
|
||||
instance_name += Side(sb_side).to_string();
|
||||
instance_name += std::string("_track_") + std::to_string(track_id);
|
||||
instance_name += postfix;
|
||||
|
||||
return instance_name;
|
||||
}
|
||||
|
||||
/*********************************************************************
|
||||
* Generate the instance name for a configurable memory module in a Connection Block
|
||||
********************************************************************/
|
||||
std::string generate_cb_memory_instance_name(const std::string& prefix,
|
||||
const std::vector<std::vector<t_grid_tile>>& grids,
|
||||
const vtr::Point<size_t>& coordinate,
|
||||
const e_side& cb_side,
|
||||
const size_t& pin_id,
|
||||
const std::string& postfix) {
|
||||
std::string instance_name(prefix);
|
||||
|
||||
instance_name += generate_grid_side_port_name(grids, coordinate, cb_side, pin_id);
|
||||
instance_name += postfix;
|
||||
|
||||
return instance_name;
|
||||
}
|
||||
|
||||
/*********************************************************************
|
||||
* Generate the instance name of a grid block
|
||||
|
|
|
@ -81,12 +81,24 @@ std::string generate_sb_memory_instance_name(const std::string& prefix,
|
|||
const size_t& track_id,
|
||||
const std::string& postfix);
|
||||
|
||||
std::string generate_cb_memory_instance_name(const std::string& prefix,
|
||||
const std::vector<std::vector<t_grid_tile>>& grids,
|
||||
const vtr::Point<size_t>& coordinate,
|
||||
const e_side& cb_side,
|
||||
const size_t& pin_id,
|
||||
const std::string& postfix);
|
||||
|
||||
std::string generate_grid_port_name(const vtr::Point<size_t>& coordinate,
|
||||
const size_t& height,
|
||||
const e_side& side,
|
||||
const size_t& pin_id,
|
||||
const bool& for_top_netlist);
|
||||
|
||||
std::string generate_grid_side_port_name(const std::vector<std::vector<t_grid_tile>>& grids,
|
||||
const vtr::Point<size_t>& coordinate,
|
||||
const e_side& side,
|
||||
const size_t& pin_id);
|
||||
|
||||
std::string generate_reserved_sram_port_name(const e_spice_model_port_type& port_type);
|
||||
|
||||
std::string generate_formal_verification_sram_port_name(const CircuitLibrary& circuit_lib,
|
||||
|
|
|
@ -8,6 +8,7 @@
|
|||
#define FPGA_X2P_RESERVED_WORDS_H
|
||||
|
||||
constexpr char* SWITCH_BLOCK_MEM_INSTANCE_PREFIX = "mem_";
|
||||
constexpr char* CONNECTION_BLOCK_MEM_INSTANCE_PREFIX = "mem_";
|
||||
constexpr char* MEMORY_MODULE_POSTFIX = "_mem";
|
||||
|
||||
#endif
|
||||
|
|
|
@ -77,7 +77,7 @@ BitstreamManager build_device_bitstream(const t_vpr_setup& vpr_setup,
|
|||
ConfigBlockId top_block = bitstream_manager.add_block(top_block_name);
|
||||
|
||||
/* Create bitstream from routing architectures */
|
||||
build_routing_bitstream(bitstream_manager, top_block, module_manager, circuit_lib, mux_lib, rr_switches, L_rr_node, L_device_rr_gsb);
|
||||
build_routing_bitstream(bitstream_manager, top_block, module_manager, circuit_lib, mux_lib, grids, rr_switches, L_rr_node, L_device_rr_gsb);
|
||||
|
||||
/* End time count */
|
||||
clock_t t_end = clock();
|
||||
|
|
|
@ -59,7 +59,7 @@ void build_switch_block_mux_bitstream(BitstreamManager& bitstream_manager,
|
|||
);
|
||||
|
||||
/* Generate bitstream depend on both technology and structure of this MUX */
|
||||
std::vector<bool> mux_bitstream = build_mux_bitstream(circuit_lib, mux_model, mux_lib, datapath_mux_size, path_id);
|
||||
std::vector<bool> mux_bitstream = build_mux_bitstream(circuit_lib, mux_model, mux_lib, datapath_mux_size, path_id);
|
||||
|
||||
/* Find the module in module manager and ensure the bitstream size matches! */
|
||||
std::string mem_module_name = generate_mux_subckt_name(circuit_lib, mux_model, datapath_mux_size, std::string(MEMORY_MODULE_POSTFIX));
|
||||
|
@ -141,7 +141,7 @@ void build_switch_block_interc_bitstream(BitstreamManager& bitstream_manager,
|
|||
*******************************************************************/
|
||||
static
|
||||
void build_switch_block_bitstream(BitstreamManager& bitstream_manager,
|
||||
const ConfigBlockId& sb_configurable_block,
|
||||
const ConfigBlockId& sb_config_block,
|
||||
const ModuleManager& module_manager,
|
||||
const CircuitLibrary& circuit_lib,
|
||||
const MuxLibrary& mux_lib,
|
||||
|
@ -159,7 +159,7 @@ void build_switch_block_bitstream(BitstreamManager& bitstream_manager,
|
|||
if (OUT_PORT != rr_gsb.get_chan_node_direction(side_manager.get_side(), itrack)) {
|
||||
continue;
|
||||
}
|
||||
build_switch_block_interc_bitstream(bitstream_manager, sb_configurable_block,
|
||||
build_switch_block_interc_bitstream(bitstream_manager, sb_config_block,
|
||||
module_manager,
|
||||
circuit_lib, mux_lib, rr_switches, L_rr_node,
|
||||
rr_gsb, side_manager.get_side(), itrack);
|
||||
|
@ -167,6 +167,178 @@ void build_switch_block_bitstream(BitstreamManager& bitstream_manager,
|
|||
}
|
||||
}
|
||||
|
||||
/********************************************************************
|
||||
* This function generates bitstream for a routing multiplexer
|
||||
* in a Connection block
|
||||
* This function will identify if a node indicates a routing multiplexer
|
||||
* If not a routing multiplexer, no bitstream is needed here
|
||||
* If yes, we will generate the bitstream for the routing multiplexer
|
||||
*******************************************************************/
|
||||
static
|
||||
void build_connection_block_mux_bitstream(BitstreamManager& bitstream_manager,
|
||||
const ConfigBlockId& mux_mem_block,
|
||||
const ModuleManager& module_manager,
|
||||
const CircuitLibrary& circuit_lib,
|
||||
const MuxLibrary& mux_lib,
|
||||
const std::vector<t_switch_inf>& rr_switches,
|
||||
t_rr_node* L_rr_node,
|
||||
t_rr_node* src_rr_node) {
|
||||
/* Find the circuit model id of the mux, we need its design technology which matters the bitstream generation */
|
||||
int switch_index = src_rr_node->drive_switches[DEFAULT_SWITCH_ID];
|
||||
CircuitModelId mux_model = rr_switches[switch_index].circuit_model;
|
||||
|
||||
/* Find drive_rr_nodes*/
|
||||
size_t datapath_mux_size = (size_t)(src_rr_node->num_drive_rr_nodes);
|
||||
|
||||
/* Configuration bits for MUX*/
|
||||
int path_id = DEFAULT_PATH_ID;
|
||||
for (size_t inode = 0; inode < datapath_mux_size; ++inode) {
|
||||
if (src_rr_node->drive_rr_nodes[inode] == &(L_rr_node[src_rr_node->prev_node])) {
|
||||
path_id = (int)inode;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/* Ensure that our path id makes sense! */
|
||||
VTR_ASSERT( (DEFAULT_PATH_ID == path_id)
|
||||
|| ( (DEFAULT_PATH_ID < path_id) && (path_id < (int)datapath_mux_size) )
|
||||
);
|
||||
|
||||
/* Generate bitstream depend on both technology and structure of this MUX */
|
||||
std::vector<bool> mux_bitstream = build_mux_bitstream(circuit_lib, mux_model, mux_lib, datapath_mux_size, path_id);
|
||||
|
||||
/* Find the module in module manager and ensure the bitstream size matches! */
|
||||
std::string mem_module_name = generate_mux_subckt_name(circuit_lib, mux_model, datapath_mux_size, std::string(MEMORY_MODULE_POSTFIX));
|
||||
ModuleId mux_mem_module = module_manager.find_module(mem_module_name);
|
||||
VTR_ASSERT (true == module_manager.valid_module_id(mux_mem_module));
|
||||
ModulePortId mux_mem_out_port_id = module_manager.find_module_port(mux_mem_module, generate_configuration_chain_data_out_name());
|
||||
VTR_ASSERT(mux_bitstream.size() == module_manager.module_port(mux_mem_module, mux_mem_out_port_id).get_width());
|
||||
|
||||
/* Add the bistream to the bitstream manager */
|
||||
for (const bool& bit : mux_bitstream) {
|
||||
ConfigBitId config_bit = bitstream_manager.add_bit(bit);
|
||||
/* Link the memory bits to the mux mem block */
|
||||
bitstream_manager.add_bit_to_block(mux_mem_block, config_bit);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/********************************************************************
|
||||
* This function generates bitstream for an interconnection,
|
||||
* i.e., a routing multiplexer, in a Connection Block
|
||||
* This function will identify if a node indicates a routing multiplexer
|
||||
* If not a routing multiplexer, no bitstream is needed here
|
||||
* If yes, we will generate the bitstream for the routing multiplexer
|
||||
*******************************************************************/
|
||||
static
|
||||
void build_connection_block_interc_bitstream(BitstreamManager& bitstream_manager,
|
||||
const ConfigBlockId& cb_configurable_block,
|
||||
const ModuleManager& module_manager,
|
||||
const CircuitLibrary& circuit_lib,
|
||||
const MuxLibrary& mux_lib,
|
||||
const std::vector<std::vector<t_grid_tile>>& grids,
|
||||
const std::vector<t_switch_inf>& rr_switches,
|
||||
t_rr_node* L_rr_node,
|
||||
const RRGSB& rr_gsb,
|
||||
const e_side& cb_ipin_side,
|
||||
const size_t& ipin_index) {
|
||||
|
||||
t_rr_node* src_rr_node = rr_gsb.get_ipin_node(cb_ipin_side, ipin_index);
|
||||
if (1 == src_rr_node->fan_in) {
|
||||
/* No bitstream generation required by a special direct connection*/
|
||||
} else if (1 < src_rr_node->fan_in) {
|
||||
/* Create the block denoting the memory instances that drives this node in Switch Block */
|
||||
vtr::Point<size_t> ipin_coord(src_rr_node->xlow, src_rr_node->ylow);
|
||||
std::string mem_block_name = generate_cb_memory_instance_name(CONNECTION_BLOCK_MEM_INSTANCE_PREFIX, grids, ipin_coord, rr_gsb.get_ipin_node_grid_side(cb_ipin_side, ipin_index), src_rr_node->ptc_num, std::string(""));
|
||||
ConfigBlockId mux_mem_block = bitstream_manager.add_block(mem_block_name);
|
||||
bitstream_manager.add_child_block(cb_configurable_block, mux_mem_block);
|
||||
/* This is a routing multiplexer! Generate bitstream */
|
||||
build_connection_block_mux_bitstream(bitstream_manager, mux_mem_block,
|
||||
module_manager, circuit_lib, mux_lib, rr_switches,
|
||||
L_rr_node, src_rr_node);
|
||||
} /*Nothing should be done else*/
|
||||
}
|
||||
|
||||
/********************************************************************
|
||||
* This function generates bitstream for a Connection Block
|
||||
* and add it to the bitstream manager
|
||||
* This function will spot all the routing multiplexers in a Connection Block
|
||||
* using a simple but effective rule:
|
||||
* The fan-in of each output node.
|
||||
* If there are more than 2 fan-in, there is a routing multiplexer
|
||||
*
|
||||
* Note that the output nodes are the IPIN rr node in a Connection Block
|
||||
* So, we will iterate over that.
|
||||
*******************************************************************/
|
||||
static
|
||||
void build_connection_block_bitstream(BitstreamManager& bitstream_manager,
|
||||
const ConfigBlockId& cb_configurable_block,
|
||||
const ModuleManager& module_manager,
|
||||
const CircuitLibrary& circuit_lib,
|
||||
const MuxLibrary& mux_lib,
|
||||
const std::vector<std::vector<t_grid_tile>>& grids,
|
||||
const std::vector<t_switch_inf>& rr_switches,
|
||||
t_rr_node* L_rr_node,
|
||||
const RRGSB& rr_gsb,
|
||||
const t_rr_type& cb_type) {
|
||||
|
||||
/* Find routing multiplexers on the sides of a Connection block where IPIN nodes locate */
|
||||
std::vector<enum e_side> cb_sides = rr_gsb.get_cb_ipin_sides(cb_type);
|
||||
|
||||
for (size_t side = 0; side < cb_sides.size(); ++side) {
|
||||
enum e_side cb_ipin_side = cb_sides[side];
|
||||
Side side_manager(cb_ipin_side);
|
||||
for (size_t inode = 0; inode < rr_gsb.get_num_ipin_nodes(cb_ipin_side); ++inode) {
|
||||
build_connection_block_interc_bitstream(bitstream_manager, cb_configurable_block,
|
||||
module_manager, circuit_lib, mux_lib,
|
||||
grids, rr_switches, L_rr_node,
|
||||
rr_gsb,
|
||||
cb_ipin_side, inode);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/********************************************************************
|
||||
* Create bitstream for a X-direction or Y-direction Connection Blocks
|
||||
*******************************************************************/
|
||||
static
|
||||
void build_connection_block_bitstreams(BitstreamManager& bitstream_manager,
|
||||
const ConfigBlockId& top_configurable_block,
|
||||
const ModuleManager& module_manager,
|
||||
const CircuitLibrary& circuit_lib,
|
||||
const MuxLibrary& mux_lib,
|
||||
const std::vector<std::vector<t_grid_tile>>& grids,
|
||||
const std::vector<t_switch_inf>& rr_switches,
|
||||
t_rr_node* L_rr_node,
|
||||
const DeviceRRGSB& L_device_rr_gsb,
|
||||
const t_rr_type& cb_type) {
|
||||
|
||||
DeviceCoordinator cb_range = L_device_rr_gsb.get_gsb_range();
|
||||
|
||||
for (size_t ix = 0; ix < cb_range.get_x(); ++ix) {
|
||||
for (size_t iy = 0; iy < cb_range.get_y(); ++iy) {
|
||||
const RRGSB& rr_gsb = L_device_rr_gsb.get_gsb(ix, iy);
|
||||
/* Check if the connection block exists in the device!
|
||||
* Some of them do NOT exist due to heterogeneous blocks (height > 1)
|
||||
* We will skip those modules
|
||||
*/
|
||||
if ( (TRUE != is_cb_exist(cb_type, rr_gsb.get_cb_x(cb_type), rr_gsb.get_cb_y(cb_type)))
|
||||
|| (true != rr_gsb.is_cb_exist(cb_type))) {
|
||||
continue;
|
||||
}
|
||||
/* Create a block for the bitstream which corresponds to the Switch block */
|
||||
vtr::Point<size_t> cb_coord(rr_gsb.get_cb_x(cb_type), rr_gsb.get_cb_y(cb_type));
|
||||
ConfigBlockId cb_configurable_block = bitstream_manager.add_block(generate_connection_block_module_name(cb_type, cb_coord));
|
||||
/* Set switch block as a child of top block */
|
||||
bitstream_manager.add_child_block(top_configurable_block, cb_configurable_block);
|
||||
|
||||
build_connection_block_bitstream(bitstream_manager, cb_configurable_block, module_manager,
|
||||
circuit_lib, mux_lib, grids, rr_switches, L_rr_node,
|
||||
rr_gsb, cb_type);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/********************************************************************
|
||||
* Top-level function to create bitstream for global routing architecture
|
||||
* Two major tasks:
|
||||
|
@ -178,6 +350,7 @@ void build_routing_bitstream(BitstreamManager& bitstream_manager,
|
|||
const ModuleManager& module_manager,
|
||||
const CircuitLibrary& circuit_lib,
|
||||
const MuxLibrary& mux_lib,
|
||||
const std::vector<std::vector<t_grid_tile>>& grids,
|
||||
const std::vector<t_switch_inf>& rr_switches,
|
||||
t_rr_node* L_rr_node,
|
||||
const DeviceRRGSB& L_device_rr_gsb) {
|
||||
|
@ -208,30 +381,16 @@ void build_routing_bitstream(BitstreamManager& bitstream_manager,
|
|||
* To organize the bitstream in blocks, we create a block for each connection block
|
||||
* and give names which are same as they are in top-level module managers
|
||||
*/
|
||||
DeviceCoordinator cb_range = L_device_rr_gsb.get_gsb_range();
|
||||
vpr_printf(TIO_MESSAGE_INFO,"Generating bitstream for Connection blocks ...\n");
|
||||
vpr_printf(TIO_MESSAGE_INFO,"Generating bitstream for X-directionConnection blocks ...\n");
|
||||
|
||||
build_connection_block_bitstreams(bitstream_manager, top_configurable_block, module_manager,
|
||||
circuit_lib, mux_lib, grids, rr_switches, L_rr_node,
|
||||
L_device_rr_gsb, CHANX);
|
||||
|
||||
vpr_printf(TIO_MESSAGE_INFO,"Generating bitstream for Y-directionConnection blocks ...\n");
|
||||
|
||||
build_connection_block_bitstreams(bitstream_manager, top_configurable_block, module_manager,
|
||||
circuit_lib, mux_lib, grids, rr_switches, L_rr_node,
|
||||
L_device_rr_gsb, CHANY);
|
||||
|
||||
for (size_t ix = 0; ix < cb_range.get_x(); ++ix) {
|
||||
for (size_t iy = 0; iy < cb_range.get_y(); ++iy) {
|
||||
const RRGSB& rr_gsb = L_device_rr_gsb.get_gsb(ix, iy);
|
||||
/* X - channels [1...nx][0..ny]*/
|
||||
if ((TRUE == is_cb_exist(CHANX, ix, iy))
|
||||
&&(true == rr_gsb.is_cb_exist(CHANX))) {
|
||||
/*
|
||||
fpga_spice_generate_bitstream_routing_connection_box_subckt(fp,
|
||||
rr_gsb, CHANX,
|
||||
cur_sram_orgz_info);
|
||||
*/
|
||||
}
|
||||
/* Y - channels [1...ny][0..nx]*/
|
||||
if ((TRUE == is_cb_exist(CHANY, ix, iy))
|
||||
&&(true == rr_gsb.is_cb_exist(CHANY))) {
|
||||
/*
|
||||
fpga_spice_generate_bitstream_routing_connection_box_subckt(fp,
|
||||
rr_gsb, CHANY,
|
||||
cur_sram_orgz_info);
|
||||
*/
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -17,6 +17,7 @@ void build_routing_bitstream(BitstreamManager& bitstream_manager,
|
|||
const ModuleManager& module_manager,
|
||||
const CircuitLibrary& circuit_lib,
|
||||
const MuxLibrary& mux_lib,
|
||||
const std::vector<std::vector<t_grid_tile>>& grids,
|
||||
const std::vector<t_switch_inf>& rr_switches,
|
||||
t_rr_node* L_rr_node,
|
||||
const DeviceRRGSB& L_device_rr_gsb);
|
||||
|
|
|
@ -9,29 +9,6 @@
|
|||
#include "fpga_x2p_pbtypes_utils.h"
|
||||
#include "build_module_graph_utils.h"
|
||||
|
||||
/*********************************************************************
|
||||
* Generate the port name for a Grid
|
||||
* This is a wrapper function for generate_port_name()
|
||||
* which can automatically decode the port name by the pin side and height
|
||||
*********************************************************************/
|
||||
std::string generate_grid_side_port_name(const std::vector<std::vector<t_grid_tile>>& grids,
|
||||
const vtr::Point<size_t>& coordinate,
|
||||
const e_side& side,
|
||||
const size_t& pin_id) {
|
||||
/* Output the pins on the side*/
|
||||
size_t height = find_grid_pin_height(grids, coordinate, pin_id);
|
||||
if (1 != grids[coordinate.x()][coordinate.y()].type->pinloc[height][side][pin_id]) {
|
||||
Side side_manager(side);
|
||||
vpr_printf(TIO_MESSAGE_ERROR,
|
||||
"(File:%s, [LINE%d])Fail to generate a grid pin (x=%lu, y=%lu, height=%lu, side=%s, index=%d)\n",
|
||||
__FILE__, __LINE__,
|
||||
coordinate.x(), coordinate.y(), height, side_manager.c_str(), pin_id);
|
||||
exit(1);
|
||||
}
|
||||
return generate_grid_port_name(coordinate, height, side, pin_id, true);
|
||||
}
|
||||
|
||||
|
||||
/********************************************************************
|
||||
* Find input port of a buffer/inverter module
|
||||
********************************************************************/
|
||||
|
|
|
@ -13,11 +13,6 @@
|
|||
#include "module_manager.h"
|
||||
#include "circuit_library.h"
|
||||
|
||||
std::string generate_grid_side_port_name(const std::vector<std::vector<t_grid_tile>>& grids,
|
||||
const vtr::Point<size_t>& coordinate,
|
||||
const e_side& side,
|
||||
const size_t& pin_id);
|
||||
|
||||
ModulePortId find_inverter_buffer_module_port(const ModuleManager& module_manager,
|
||||
const ModuleId& module_id,
|
||||
const CircuitLibrary& circuit_lib,
|
||||
|
|
|
@ -693,8 +693,10 @@ void build_connection_block_mux_module(ModuleManager& module_manager,
|
|||
const CircuitLibrary& circuit_lib,
|
||||
const std::vector<std::vector<t_grid_tile>>& grids,
|
||||
const std::vector<t_switch_inf>& rr_switches,
|
||||
t_rr_node* cur_rr_node,
|
||||
const e_side& cb_ipin_side,
|
||||
const size_t& ipin_index,
|
||||
const std::map<ModulePortId, ModuleNetId>& input_port_to_module_nets) {
|
||||
t_rr_node* cur_rr_node = rr_gsb.get_ipin_node(cb_ipin_side, ipin_index);
|
||||
/* Check current rr_node is an input pin of a CLB */
|
||||
VTR_ASSERT(IPIN == cur_rr_node->type);
|
||||
|
||||
|
@ -770,6 +772,13 @@ void build_connection_block_mux_module(ModuleManager& module_manager,
|
|||
size_t mem_instance_id = module_manager.num_instance(cb_module, mem_module);
|
||||
module_manager.add_child_module(cb_module, mem_module);
|
||||
|
||||
/* Give an instance name: this name should be consistent with the block name given in bitstream manager,
|
||||
* If you want to bind the bitstream generation to modules
|
||||
*/
|
||||
vtr::Point<size_t> ipin_coord(cur_rr_node->xlow, cur_rr_node->ylow);
|
||||
std::string mem_instance_name = generate_cb_memory_instance_name(CONNECTION_BLOCK_MEM_INSTANCE_PREFIX, grids, ipin_coord, rr_gsb.get_ipin_node_grid_side(cb_ipin_side, ipin_index), cur_rr_node->ptc_num, std::string(""));
|
||||
module_manager.set_child_instance_name(cb_module, mem_module, mem_instance_id, mem_instance_name);
|
||||
|
||||
/* Add nets to connect regular and mode-select SRAM ports to the SRAM port of memory module */
|
||||
add_module_nets_between_logic_and_memory_sram_bus(module_manager, cb_module,
|
||||
mux_module, mux_instance_id,
|
||||
|
@ -794,8 +803,10 @@ void build_connection_block_interc_modules(ModuleManager& module_manager,
|
|||
const CircuitLibrary& circuit_lib,
|
||||
const std::vector<std::vector<t_grid_tile>>& grids,
|
||||
const std::vector<t_switch_inf>& rr_switches,
|
||||
t_rr_node* src_rr_node,
|
||||
const e_side& cb_ipin_side,
|
||||
const size_t& ipin_index,
|
||||
const std::map<ModulePortId, ModuleNetId>& input_port_to_module_nets) {
|
||||
t_rr_node* src_rr_node = rr_gsb.get_ipin_node(cb_ipin_side, ipin_index);
|
||||
if (1 > src_rr_node->fan_in) {
|
||||
return; /* This port has no driver, skip it */
|
||||
} else if (1 == src_rr_node->fan_in) {
|
||||
|
@ -807,7 +818,7 @@ void build_connection_block_interc_modules(ModuleManager& module_manager,
|
|||
build_connection_block_mux_module(module_manager,
|
||||
cb_module, rr_gsb, cb_type,
|
||||
circuit_lib, grids, rr_switches,
|
||||
src_rr_node,
|
||||
cb_ipin_side, ipin_index,
|
||||
input_port_to_module_nets);
|
||||
} /*Nothing should be done else*/
|
||||
}
|
||||
|
@ -967,7 +978,7 @@ void build_connection_block_module(ModuleManager& module_manager,
|
|||
build_connection_block_interc_modules(module_manager,
|
||||
cb_module, rr_gsb, cb_type,
|
||||
circuit_lib, grids, rr_switches,
|
||||
rr_gsb.get_ipin_node(cb_ipin_side, inode),
|
||||
cb_ipin_side, inode,
|
||||
input_port_to_module_nets);
|
||||
}
|
||||
}
|
||||
|
@ -1029,7 +1040,7 @@ void build_flatten_connection_block_modules(ModuleManager& module_manager,
|
|||
* We will skip those modules
|
||||
*/
|
||||
const RRGSB& rr_gsb = L_device_rr_gsb.get_gsb(ix, iy);
|
||||
if ( (TRUE != is_cb_exist(CHANX, rr_gsb.get_cb_x(cb_type), rr_gsb.get_cb_y(cb_type)))
|
||||
if ( (TRUE != is_cb_exist(cb_type, rr_gsb.get_cb_x(cb_type), rr_gsb.get_cb_y(cb_type)))
|
||||
|| (true != rr_gsb.is_cb_exist(cb_type))) {
|
||||
continue;
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue