From 2735b708d35210dd3a55c42851271ef33f7ecf47 Mon Sep 17 00:00:00 2001 From: tangxifan Date: Mon, 27 Feb 2023 22:59:44 -0800 Subject: [PATCH] [core] reworked the tapping XML syntax --- libs/libclkarchopenfpga/arch/example.xml | 26 +++------- .../src/base/clock_network.cpp | 24 ++++++---- .../src/base/clock_network.h | 13 ++--- .../src/io/clock_network_xml_constants.h | 5 +- .../src/io/read_xml_clock_network.cpp | 48 +++++++++++++------ .../src/io/write_xml_clock_network.cpp | 20 +++++--- .../src/annotation/append_clock_rr_graph.cpp | 2 +- 7 files changed, 77 insertions(+), 61 deletions(-) diff --git a/libs/libclkarchopenfpga/arch/example.xml b/libs/libclkarchopenfpga/arch/example.xml index 6defe943a..ac6e722dd 100644 --- a/libs/libclkarchopenfpga/arch/example.xml +++ b/libs/libclkarchopenfpga/arch/example.xml @@ -12,29 +12,15 @@ - + + + + + - - - - - - - - - - - - - - - - - - - + diff --git a/libs/libclkarchopenfpga/src/base/clock_network.cpp b/libs/libclkarchopenfpga/src/base/clock_network.cpp index f505ed4c2..0b13d49e4 100644 --- a/libs/libclkarchopenfpga/src/base/clock_network.cpp +++ b/libs/libclkarchopenfpga/src/base/clock_network.cpp @@ -232,15 +232,15 @@ vtr::Point ClockNetwork::spine_switch_point( return spine_switch_coords_[spine_id][size_t(switch_point_id)]; } -std::vector ClockNetwork::spine_taps(const ClockSpineId& spine_id) const { - VTR_ASSERT(valid_spine_id(spine_id)); - return spine_taps_[spine_id]; +std::vector ClockNetwork::tree_taps(const ClockTreeId& tree_id) const { + VTR_ASSERT(valid_tree_id(tree_id)); + return tree_taps_[tree_id]; } -std::vector ClockNetwork::spine_flatten_taps(const ClockSpineId& spine_id) const { - VTR_ASSERT(valid_spine_id(spine_id)); +std::vector ClockNetwork::tree_flatten_taps(const ClockTreeId& tree_id, const ClockTreePinId& clk_pin_id) const { + VTR_ASSERT(valid_tree_id(tree_id)); std::vector flatten_taps; - for (const std::string& tap_name : spine_taps_[spine_id]) { + for (const std::string& tap_name : tree_taps_[tree_id]) { StringToken tokenizer(tap_name); std::vector pin_tokens = tokenizer.split("."); if (pin_tokens.size() != 2) { @@ -262,6 +262,9 @@ std::vector ClockNetwork::spine_flatten_taps(const ClockSpineId& sp for (size_t& tile_idx : tile_info.pins()) { std::string flatten_tile_str = tile_info.get_name() + "[" + std::to_string(tile_idx) + "]"; for (size_t& pin_idx : pin_info.pins()) { + if (pin_idx != size_t(clk_pin_id)) { + continue; + } std::string flatten_pin_str = pin_info.get_name() + "[" + std::to_string(pin_idx) + "]"; flatten_taps.push_back(flatten_tile_str + "." + flatten_pin_str); } @@ -307,6 +310,7 @@ void ClockNetwork::reserve_trees(const size_t& num_trees) { tree_names_.reserve(num_trees); tree_widths_.reserve(num_trees); tree_top_spines_.reserve(num_trees); + tree_taps_.reserve(num_trees); } void ClockNetwork::set_default_segment(const RRSegmentId& seg_id) { @@ -333,6 +337,7 @@ ClockTreeId ClockNetwork::create_tree(const std::string& name, size_t width) { tree_names_.push_back(name); tree_widths_.push_back(width); tree_depths_.emplace_back(); + tree_taps_.emplace_back(); tree_top_spines_.emplace_back(); /* Register to fast look-up */ @@ -372,7 +377,6 @@ ClockSpineId ClockNetwork::create_spine(const std::string& name) { spine_parents_.emplace_back(); spine_children_.emplace_back(); spine_parent_trees_.emplace_back(); - spine_taps_.emplace_back(); /* Register to the lookup */ VTR_ASSERT(valid_spine_id(spine_id)); @@ -429,9 +433,9 @@ void ClockNetwork::add_spine_switch_point(const ClockSpineId& spine_id, spine_children_[spine_id].push_back(drive_spine_id); } -void ClockNetwork::add_spine_tap(const ClockSpineId& spine_id, const std::string& pin_name) { - VTR_ASSERT(valid_spine_id(spine_id)); - spine_taps_[spine_id].push_back(pin_name); +void ClockNetwork::add_tree_tap(const ClockTreeId& tree_id, const std::string& pin_name) { + VTR_ASSERT(valid_tree_id(tree_id)); + tree_taps_[tree_id].push_back(pin_name); } bool ClockNetwork::link() { diff --git a/libs/libclkarchopenfpga/src/base/clock_network.h b/libs/libclkarchopenfpga/src/base/clock_network.h index 53e3259c5..99951d055 100644 --- a/libs/libclkarchopenfpga/src/base/clock_network.h +++ b/libs/libclkarchopenfpga/src/base/clock_network.h @@ -105,12 +105,13 @@ class ClockNetwork { const ClockSpineId& spine_id, const ClockSwitchPointId& switch_point_id) const; /* Return the original list of tap pins that is in storage; useful for parsers */ - std::vector spine_taps(const ClockSpineId& spine_id) const; - /* Return the list of flatten tap pins. For example: clb[0:1].clk[2:3] is flatten to - * { clb[0].clk[2], clb[1].clk[2], clb[0].clk[3], clb[1].clk[3] } + std::vector tree_taps(const ClockTreeId& tree_id) const; + /* Return the list of flatten tap pins. For example: clb[0:1].clk[2:2] is flatten to + * { clb[0].clk[2], clb[1].clk[2] } * Useful to build clock routing resource graph + * Note that the clk_pin_id limits only 1 clock to be accessed */ - std::vector spine_flatten_taps(const ClockSpineId& spine_id) const; + std::vector tree_flatten_taps(const ClockTreeId& tree_id, const ClockTreePinId& clk_pin_id) const; /* Find a spine with a given name, if not found, return an valid id, otherwise * return an invalid one */ ClockSpineId find_spine(const std::string& name) const; @@ -153,7 +154,7 @@ class ClockNetwork { void add_spine_switch_point(const ClockSpineId& spine_id, const ClockSpineId& drive_spine_id, const vtr::Point& coord); - void add_spine_tap(const ClockSpineId& spine_id, const std::string& pin_name); + void add_tree_tap(const ClockTreeId& tree_id, const std::string& pin_name); /* Build internal links between clock tree, spines etc. This is also an * validator to verify the correctness of the clock network. Must run before * using the data! */ @@ -202,6 +203,7 @@ class ClockNetwork { vtr::vector tree_widths_; vtr::vector tree_depths_; vtr::vector> tree_top_spines_; + vtr::vector> tree_taps_; /* Basic information of each spine */ vtr::vector spine_ids_; @@ -209,7 +211,6 @@ class ClockNetwork { vtr::vector spine_levels_; vtr::vector> spine_start_points_; vtr::vector> spine_end_points_; - vtr::vector> spine_taps_; vtr::vector> spine_switch_points_; vtr::vector>> spine_switch_coords_; vtr::vector spine_parents_; diff --git a/libs/libclkarchopenfpga/src/io/clock_network_xml_constants.h b/libs/libclkarchopenfpga/src/io/clock_network_xml_constants.h index 8dc9871ec..569fdde7a 100644 --- a/libs/libclkarchopenfpga/src/io/clock_network_xml_constants.h +++ b/libs/libclkarchopenfpga/src/io/clock_network_xml_constants.h @@ -21,7 +21,8 @@ constexpr const char* XML_CLOCK_SPINE_SWITCH_POINT_NODE_NAME = "switch_point"; constexpr const char* XML_CLOCK_SPINE_SWITCH_POINT_ATTRIBUTE_TAP = "tap"; constexpr const char* XML_CLOCK_SPINE_SWITCH_POINT_ATTRIBUTE_X = "x"; constexpr const char* XML_CLOCK_SPINE_SWITCH_POINT_ATTRIBUTE_Y = "y"; -constexpr const char* XML_CLOCK_SPINE_TAP_NODE_NAME = "tap"; -constexpr const char* XML_CLOCK_SPINE_TAP_ATTRIBUTE_TILE_PIN = "tile_pin"; +constexpr const char* XML_CLOCK_TREE_TAPS_NODE_NAME = "taps"; +constexpr const char* XML_CLOCK_TREE_TAP_NODE_NAME = "tap"; +constexpr const char* XML_CLOCK_TREE_TAP_ATTRIBUTE_TILE_PIN = "tile_pin"; #endif diff --git a/libs/libclkarchopenfpga/src/io/read_xml_clock_network.cpp b/libs/libclkarchopenfpga/src/io/read_xml_clock_network.cpp index ee1ee34f9..3791be016 100644 --- a/libs/libclkarchopenfpga/src/io/read_xml_clock_network.cpp +++ b/libs/libclkarchopenfpga/src/io/read_xml_clock_network.cpp @@ -27,19 +27,36 @@ namespace openfpga { // Begin namespace openfpga /******************************************************************** * Parse XML codes of a to an object of ClockNetwork *******************************************************************/ -static void read_xml_clock_spine_tap( - pugi::xml_node& xml_switch_point, const pugiutil::loc_data& loc_data, - ClockNetwork& clk_ntwk, const ClockSpineId& spine_id) { - if (!clk_ntwk.valid_spine_id(spine_id)) { - archfpga_throw(loc_data.filename_c_str(), loc_data.line(xml_switch_point), - "Invalid id of a clock spine!\n"); +static void read_xml_clock_tree_tap( + pugi::xml_node& xml_tap, const pugiutil::loc_data& loc_data, + ClockNetwork& clk_ntwk, const ClockTreeId& tree_id) { + if (!clk_ntwk.valid_tree_id(tree_id)) { + archfpga_throw(loc_data.filename_c_str(), loc_data.line(xml_tap), + "Invalid id of a clock tree!\n"); } std::string tile_pin_name = - get_attribute(xml_switch_point, XML_CLOCK_SPINE_TAP_ATTRIBUTE_TILE_PIN, + get_attribute(xml_tap, XML_CLOCK_TREE_TAP_ATTRIBUTE_TILE_PIN, loc_data) .as_string(); - clk_ntwk.add_spine_tap(spine_id, tile_pin_name); + clk_ntwk.add_tree_tap(tree_id, tile_pin_name); +} + + +static void read_xml_clock_tree_taps( + pugi::xml_node& xml_taps, const pugiutil::loc_data& loc_data, + ClockNetwork& clk_ntwk, const ClockTreeId& tree_id) { + for (pugi::xml_node xml_tap : xml_taps.children()) { + /* Error out if the XML child has an invalid name! */ + if (xml_tap.name() == + std::string(XML_CLOCK_TREE_TAP_NODE_NAME)) { + read_xml_clock_tree_tap(xml_tap, loc_data, clk_ntwk, + tree_id); + } else { + bad_tag(xml_taps, loc_data, xml_tap, + {XML_CLOCK_TREE_TAP_NODE_NAME}); + } + } } /******************************************************************** @@ -131,12 +148,9 @@ static void read_xml_clock_spine(pugi::xml_node& xml_spine, std::string(XML_CLOCK_SPINE_SWITCH_POINT_NODE_NAME)) { read_xml_clock_spine_switch_point(xml_switch_point, loc_data, clk_ntwk, spine_id); - } else if (xml_switch_point.name() == - std::string(XML_CLOCK_SPINE_TAP_NODE_NAME)) { - read_xml_clock_spine_tap(xml_switch_point, loc_data, clk_ntwk, spine_id); } else { bad_tag(xml_switch_point, loc_data, xml_spine, - {XML_CLOCK_SPINE_SWITCH_POINT_NODE_NAME, XML_CLOCK_SPINE_TAP_NODE_NAME}); + {XML_CLOCK_SPINE_SWITCH_POINT_NODE_NAME}); } } } @@ -164,10 +178,14 @@ static void read_xml_clock_tree(pugi::xml_node& xml_clk_tree, for (pugi::xml_node xml_spine : xml_clk_tree.children()) { /* Error out if the XML child has an invalid name! */ - if (xml_spine.name() != std::string(XML_CLOCK_SPINE_NODE_NAME)) { - bad_tag(xml_spine, loc_data, xml_clk_tree, {XML_CLOCK_SPINE_NODE_NAME}); + if (xml_spine.name() == std::string(XML_CLOCK_SPINE_NODE_NAME)) { + read_xml_clock_spine(xml_spine, loc_data, clk_ntwk, tree_id); + } else if (xml_spine.name() == + std::string(XML_CLOCK_TREE_TAPS_NODE_NAME)) { + read_xml_clock_tree_taps(xml_spine, loc_data, clk_ntwk, tree_id); + } else { + bad_tag(xml_spine, loc_data, xml_clk_tree, {XML_CLOCK_SPINE_NODE_NAME, XML_CLOCK_TREE_TAPS_NODE_NAME}); } - read_xml_clock_spine(xml_spine, loc_data, clk_ntwk, tree_id); } } diff --git a/libs/libclkarchopenfpga/src/io/write_xml_clock_network.cpp b/libs/libclkarchopenfpga/src/io/write_xml_clock_network.cpp index 7910d6333..b350cafd1 100644 --- a/libs/libclkarchopenfpga/src/io/write_xml_clock_network.cpp +++ b/libs/libclkarchopenfpga/src/io/write_xml_clock_network.cpp @@ -23,19 +23,24 @@ namespace openfpga { // Begin namespace openfpga -static int write_xml_clock_spine_taps( - std::fstream& fp, const ClockNetwork& clk_ntwk, const ClockSpineId& spine_id) { - for (const std::string& tile_pin_name : clk_ntwk.spine_taps(spine_id)) { - openfpga::write_tab_to_file(fp, 3); - fp << "<" << XML_CLOCK_SPINE_TAP_NODE_NAME << ""; +static int write_xml_clock_tree_taps( + std::fstream& fp, const ClockNetwork& clk_ntwk, const ClockTreeId& tree_id) { + openfpga::write_tab_to_file(fp, 3); + fp << "<" << XML_CLOCK_TREE_TAPS_NODE_NAME << ">\n"; + for (const std::string& tile_pin_name : clk_ntwk.tree_taps(tree_id)) { + openfpga::write_tab_to_file(fp, 4); + fp << "<" << XML_CLOCK_TREE_TAP_NODE_NAME << ""; write_xml_attribute( - fp, XML_CLOCK_SPINE_TAP_ATTRIBUTE_TILE_PIN, + fp, XML_CLOCK_TREE_TAP_ATTRIBUTE_TILE_PIN, tile_pin_name.c_str()); fp << "/>" << "\n"; } + openfpga::write_tab_to_file(fp, 3); + fp << "\n"; + return 0; } @@ -82,7 +87,6 @@ static int write_xml_clock_spine(std::fstream& fp, const ClockNetwork& clk_ntwk, clk_ntwk.spine_switch_points(spine_id)) { write_xml_clock_spine_switch_point(fp, clk_ntwk, spine_id, switch_point_id); } - write_xml_clock_spine_taps(fp, clk_ntwk, spine_id); openfpga::write_tab_to_file(fp, 2); fp << "" diff --git a/openfpga/src/annotation/append_clock_rr_graph.cpp b/openfpga/src/annotation/append_clock_rr_graph.cpp index 692127a9e..51c96c046 100644 --- a/openfpga/src/annotation/append_clock_rr_graph.cpp +++ b/openfpga/src/annotation/append_clock_rr_graph.cpp @@ -363,7 +363,7 @@ void try_find_and_add_clock_track2ipin_node(std::vector& des_nodes, const ClockTreeId& clk_tree, const ClockTreePinId& clk_pin) { t_physical_tile_type_ptr grid_type = grids[grid_coord.x()][grid_coord.y()].type; - for (std::string tap_pin_name : clk_ntwk.spine_flatten_taps(clk_tree, clk_pin)) { + for (std::string tap_pin_name : clk_ntwk.tree_flatten_taps(clk_tree, clk_pin)) { /* tap pin name could be 'io[5:5].a2f[0]' */ int grid_pin_idx = find_physical_tile_pin_index(grid_type, tap_pin_name); if (grid_pin_idx == grid_type->num_pins) {