diff --git a/openfpga/src/annotation/device_rr_gsb.cpp b/openfpga/src/annotation/device_rr_gsb.cpp index b3189c055..f0155e339 100644 --- a/openfpga/src/annotation/device_rr_gsb.cpp +++ b/openfpga/src/annotation/device_rr_gsb.cpp @@ -562,58 +562,63 @@ size_t DeviceRRGSB::get_cb_unique_module_index( return cb_unique_module_id; } -void DeviceRRGSB::preload_unique_cbx_module(int x, int y) {} - -void DeviceRRGSB::preload_unique_cby_module(int x, int y) {} - -void DeviceRRGSB::preload_unique_sb_module(int ix, int iy) { - vtr::Point sb_coordinate(ix, iy); - bool is_unique_module = true; - - for (size_t id = 0; id < get_num_sb_unique_module(); ++id) { - /* Check whether the input module exists.*/ - if (sb_unique_module_[id].x() == ix && sb_unique_module_[id].y() == iy) { - is_unique_module = false; - sb_unique_module_id_[ix][iy] = id; +void DeviceRRGSB::preload_unique_cb_module( + const vtr::Point block_coordinate, + const std::vector> instance_coords, + const t_rr_type& cb_type) { + /* Add to list if this is a unique mirror*/ + size_t limit_x; + size_t limit_y; + switch(cb_type){ + case CHANX: + limit_x = cby_unique_module_id_.size(); + limit_y = cby_unique_module_id_[0].size(); break; - } + case CHANY: + limit_x = cby_unique_module_id_.size(); + limit_y = cby_unique_module_id_[0].size(); + break; + default: + VTR_LOG_ERROR("Invalid type"); } - if (true == is_unique_module) { - sb_unique_module_.push_back(sb_coordinate); + + VTR_ASSERT(block_coordinate.x() < limit_x); + VTR_ASSERT(block_coordinate.y() < limit_y); + add_cb_unique_module(cb_type, block_coordinate); + /* Record the id of unique mirror */ + set_cb_unique_module_id(cb_type, block_coordinate, + get_num_cb_unique_module(cb_type) - 1); + + /* Traverse the unique_mirror list and set up its module id */ + for (auto instance_location : instance_coords) { /* Record the id of unique mirror */ - sb_unique_module_id_[ix][iy] = sb_unique_module_.size() - 1; + VTR_ASSERT(instance_location.x() < limit_x); + VTR_ASSERT(instance_location.y() < limit_y); + set_cb_unique_module_id( + cb_type, instance_location, + cbx_unique_module_id_[block_coordinate.x()][block_coordinate.y()]); } } -/* need to preload after cb and sb are preloaded */ -void DeviceRRGSB::preload_unique_gsb_module(int ix, int iy) { - // vtr::Point gsb_coordinate(ix, iy); - // bool is_unique_module = true; +void DeviceRRGSB::preload_unique_sb_module( + const vtr::Point block_coordinate, + const std::vector> instance_coords) { + /*input block coordinate should be within gsb coord range*/ + VTR_ASSERT(block_coordinate.x() < sb_unique_module_id_.size()); + VTR_ASSERT(block_coordinate.y() < sb_unique_module_id_[0].size()); + sb_unique_module_.push_back(block_coordinate); + /* Record the id of unique module */ + sb_unique_module_id_[block_coordinate.x()][block_coordinate.y()] = + sb_unique_module_.size() - 1; - // for (size_t id = 0; id < get_num_gsb_unique_module(); ++id) { - // const vtr::Point& gsb_unique_module_coordinate = - // gsb_unique_module_[id]; - // if ((sb_unique_module_id_[ix][iy] == - // sb_unique_module_id_[gsb_unique_module_coordinate.x()] - // [gsb_unique_module_coordinate.y()]) && - // (cbx_unique_module_id_[ix][iy] == - // cbx_unique_module_id_[gsb_unique_module_coordinate.x()] - // [gsb_unique_module_coordinate.y()]) && - // (cby_unique_module_id_[ix][iy] == - // cby_unique_module_id_[gsb_unique_module_coordinate.x()] - // [gsb_unique_module_coordinate.y()])) { - // /* This is a mirror, raise the flag and we finish */ - // is_unique_module = false; - // /* Record the id of unique mirror */ - // gsb_unique_module_id_[ix][iy] = id; - // break; - // } - // } - // if (true == is_unique_module) { - // add_gsb_unique_module(gsb_coordinate); - // /* Record the id of unique mirror */ - // gsb_unique_module_id_[ix][iy] = get_num_gsb_unique_module() - 1; - // } + /* each mirror instance of the unique module will have the same module id as + * the unique module */ + for (auto instance_location : instance_coords) { + VTR_ASSERT(instance_location.x() < sb_unique_module_id_.size()); + VTR_ASSERT(instance_location.y() < sb_unique_module_id_[0].size()); + sb_unique_module_id_[instance_location.x()][instance_location.y()] = + sb_unique_module_id_[block_coordinate.x()][block_coordinate.y()]; + } } } /* End namespace openfpga*/ diff --git a/openfpga/src/annotation/device_rr_gsb.h b/openfpga/src/annotation/device_rr_gsb.h index 911ed31c4..b6928e91f 100644 --- a/openfpga/src/annotation/device_rr_gsb.h +++ b/openfpga/src/annotation/device_rr_gsb.h @@ -95,12 +95,16 @@ class DeviceRRGSB { automatically identify and update the lists of unique mirrors and rotatable mirrors */ void clear(); /* clean the content */ - void preload_unique_cbx_module(int x, int y); - void preload_unique_cby_module(int x, int y); - void preload_unique_sb_module(int x, int y); - void preload_unique_gsb_module(int x, int y); - private: /* Internal cleaners */ - void clear_gsb(); /* clean the content */ + void preload_unique_cb_module( + const vtr::Point block_coordinate, + const std::vector> instance_coords, + const t_rr_type& cb_type); + void preload_unique_sb_module( + const vtr::Point block_coordinate, + const std::vector> instance_coords); + + private: /* Internal cleaners */ + void clear_gsb(); /* clean the content */ void clear_cb_unique_module(const t_rr_type& cb_type); /* clean the content */ void clear_cb_unique_module_id( const t_rr_type& cb_type); /* clean the content */ diff --git a/openfpga/src/base/openfpga_build_fabric_template.h b/openfpga/src/base/openfpga_build_fabric_template.h index 3ba3c1d1a..7566e7d7f 100644 --- a/openfpga/src/base/openfpga_build_fabric_template.h +++ b/openfpga/src/base/openfpga_build_fabric_template.h @@ -20,12 +20,12 @@ #include "read_xml_io_name_map.h" #include "read_xml_module_name_map.h" #include "read_xml_tile_config.h" +#include "read_xml_unique_blocks.h" #include "rename_modules.h" #include "vtr_log.h" #include "vtr_time.h" #include "write_xml_fabric_pin_physical_location.h" #include "write_xml_module_name_map.h" -#include "read_xml_unique_blocks.h" /* begin namespace openfpga */ namespace openfpga { @@ -490,8 +490,13 @@ int read_unique_blocks_template(T& openfpga_ctx, const Command& cmd, std::string file_name = cmd_context.option_value(cmd, opt_file); std::string file_type = cmd_context.option_value(cmd, opt_type); /* Write hierarchy to a file */ - return read_xml_unique_blocks(openfpga_ctx, file_name.c_str(), file_type.c_str(), - cmd_context.option_enable(cmd, opt_verbose)); + if (file_type == "xml") { + return read_xml_unique_blocks(openfpga_ctx, file_name.c_str(), + file_type.c_str(), + cmd_context.option_enable(cmd, opt_verbose)); + } else { + VTR_LOG_ERROR("file type %s not supported", file_type); + } } template @@ -512,8 +517,9 @@ int write_unique_blocks_template(T& openfpga_ctx, const Command& cmd, std::string file_type = cmd_context.option_value(cmd, opt_type); /* Write hierarchy to a file */ - return read_xml_unique_blocks(openfpga_ctx, file_name.c_str(), file_type.c_str(), - cmd_context.option_enable(cmd, opt_verbose)); + return read_xml_unique_blocks(openfpga_ctx, file_name.c_str(), + file_type.c_str(), + cmd_context.option_enable(cmd, opt_verbose)); } } /* end namespace openfpga */ diff --git a/openfpga/src/fabric/read_xml_unique_blocks.h b/openfpga/src/fabric/read_xml_unique_blocks.h index b9b17ce91..32cb65d8d 100644 --- a/openfpga/src/fabric/read_xml_unique_blocks.h +++ b/openfpga/src/fabric/read_xml_unique_blocks.h @@ -23,61 +23,92 @@ /* Headers from libarchfpga */ #include "arch_error.h" +#include "device_rr_gsb_utils.h" #include "read_xml_unique_blocks.h" #include "read_xml_util.h" #include "rr_gsb.h" -/******************************************************************** - * Function declaration - *******************************************************************/ -template -int read_xml_unique_blocks(T& openfpga_ctx, const char* file_name, - const char* file_type, bool verbose); - /******************************************************************** * Parse XML codes of a to an object of unique_blocks *******************************************************************/ -template -void read_xml_unique_instance_info(T& device_rr_gsb, - pugi::xml_node& xml_instance_info, - const pugiutil::loc_data& loc_data, - std::string type) { +vtr::Point read_xml_unique_instance_info( + pugi::xml_node& xml_instance_info, const pugiutil::loc_data& loc_data) { int instance_x = get_attribute(xml_instance_info, "x", loc_data).as_int(); int instance_y = get_attribute(xml_instance_info, "y", loc_data).as_int(); - if (type == "sb") { - device_rr_gsb.preload_unique_sb_module(instance_x, instance_y); - } else if (type == "cb") { - // read_cb_unique_blocks(); - std::cout << "By pass here" << std::endl; - } else if (type == "gsb") { - /* should grab coordinates first and then by pass it to preload gsb*/ - std::cout << "By pass here" << std::endl; - // read_gsb_unique_blocks(); - } + vtr::Point instance_coordinate(instance_x, instance_y); + return instance_coordinate; } +template +void report_unique_module_status(T& openfpga_ctx, bool verbose_output) { + /* Report the stats */ + VTR_LOGV( + verbose_output, + "Detected %lu unique X-direction connection blocks from a total of %d " + "(compression rate=%.2f%)\n", + openfpga_ctx.device_rr_gsb().get_num_cb_unique_module(CHANX), + find_device_rr_gsb_num_cb_modules(openfpga_ctx.device_rr_gsb(), CHANX), + 100. * + ((float)find_device_rr_gsb_num_cb_modules(openfpga_ctx.device_rr_gsb(), + CHANX) / + (float)openfpga_ctx.device_rr_gsb().get_num_cb_unique_module(CHANX) - + 1.)); + + VTR_LOGV( + verbose_output, + "Detected %lu unique Y-direction connection blocks from a total of %d " + "(compression rate=%.2f%)\n", + openfpga_ctx.device_rr_gsb().get_num_cb_unique_module(CHANY), + find_device_rr_gsb_num_cb_modules(openfpga_ctx.device_rr_gsb(), CHANY), + 100. * + ((float)find_device_rr_gsb_num_cb_modules(openfpga_ctx.device_rr_gsb(), + CHANY) / + (float)openfpga_ctx.device_rr_gsb().get_num_cb_unique_module(CHANY) - + 1.)); + + VTR_LOGV( + verbose_output, + "Detected %lu unique switch blocks from a total of %d (compression " + "rate=%.2f%)\n", + openfpga_ctx.device_rr_gsb().get_num_sb_unique_module(), + find_device_rr_gsb_num_sb_modules(openfpga_ctx.device_rr_gsb(), + g_vpr_ctx.device().rr_graph), + 100. * ((float)find_device_rr_gsb_num_sb_modules( + openfpga_ctx.device_rr_gsb(), g_vpr_ctx.device().rr_graph) / + (float)openfpga_ctx.device_rr_gsb().get_num_sb_unique_module() - + 1.)); + + VTR_LOG( + "Detected %lu unique general switch blocks from a total of %d " + "(compression " + "rate=%.2f%)\n", + openfpga_ctx.device_rr_gsb().get_num_gsb_unique_module(), + find_device_rr_gsb_num_gsb_modules(openfpga_ctx.device_rr_gsb(), + g_vpr_ctx.device().rr_graph), + 100. * ((float)find_device_rr_gsb_num_gsb_modules( + openfpga_ctx.device_rr_gsb(), g_vpr_ctx.device().rr_graph) / + (float)openfpga_ctx.device_rr_gsb().get_num_gsb_unique_module() - + 1.)); +} /******************************************************************** * Parse XML codes about to an object of *RepackDesignConstraints *******************************************************************/ template int read_xml_unique_blocks(T& openfpga_ctx, const char* file_name, - const char* file_type, bool verbose) { + const char* file_type, bool verbose_output) { vtr::ScopedStartFinishTimer timer("Read unique blocks xml file"); - - // RepackDesignConstraints repack_design_constraints; - /* Parse the file */ pugi::xml_document doc; pugiutil::loc_data loc_data; - + VTR_ASSERT(strcmp(file_type, "xml") == 0); try { loc_data = pugiutil::load_xml(doc, file_name); pugi::xml_node xml_root = get_single_child(doc, "unique_blocks", loc_data); /* get device_rr_gsb data type and initialize it*/ - auto device_rr_gsb = openfpga_ctx.mutable_device_rr_gsb(); + openfpga::DeviceRRGSB& device_rr_gsb = openfpga_ctx.mutable_device_rr_gsb(); device_rr_gsb.clear(); /* load unique blocks xml file and set up device_rr_gdb */ @@ -86,23 +117,38 @@ int read_xml_unique_blocks(T& openfpga_ctx, const char* file_name, if (xml_block_info.name() == std::string("block")) { std::string type = get_attribute(xml_block_info, "type", loc_data).as_string(); - std::string block_x = - get_attribute(xml_block_info, "x", loc_data).as_string(); - std::string block_y = - get_attribute(xml_block_info, "y", loc_data).as_string(); + int block_x = get_attribute(xml_block_info, "x", loc_data).as_int(); + int block_y = get_attribute(xml_block_info, "y", loc_data).as_int(); + vtr::Point block_coordinate(block_x, block_y); + std::vector> instance_coords; for (pugi::xml_node xml_instance_info : xml_block_info.children()) { if (xml_instance_info.name() == std::string("instance")) { - read_xml_unique_instance_info(device_rr_gsb, xml_instance_info, - loc_data, type); + auto instance_coordinate = + read_xml_unique_instance_info(xml_instance_info, loc_data); + instance_coords.push_back(instance_coordinate); } - // read_xml_unique_instance_info(xml_instance_info, loc_data); + } + /* get block coordinate and instance coordinate, try to setup device rr + * gsb */ + if (type == "sb") { + device_rr_gsb.preload_unique_sb_module(block_coordinate, + instance_coords); + } else if (type == "cby") { + device_rr_gsb.preload_unique_cb_module(block_coordinate, + instance_coords, CHANY); + } else if (type == "cbx") { + device_rr_gsb.preload_unique_cb_module(block_coordinate, + instance_coords, CHANX); + } else { + VTR_LOG_ERROR("Unexpected type!"); } } else { bad_tag(xml_block_info, loc_data, xml_root, {"block"}); return 1; } - // std::cout << "what is the root name: " << xml_block_info.name() << - // std::endl; + } + if (verbose_output) { + report_unique_module_status(openfpga_ctx, true); } } catch (pugiutil::XmlError& e) { archfpga_throw(file_name, e.line(), "%s", e.what());