Skip to content

Commit ef08d57

Browse files
committed
place: added placement priority and check direct pin mappings
Signed-off-by: Alessandro Comodi <[email protected]>
1 parent c85878d commit ef08d57

File tree

5 files changed

+86
-53
lines changed

5 files changed

+86
-53
lines changed

libs/libarchfpga/src/physical_types.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -609,6 +609,9 @@ struct t_physical_tile_type {
609609

610610
std::vector<std::string> equivalent_sites_names;
611611
std::vector<t_logical_block_type_ptr> equivalent_sites;
612+
613+
/* Unordered map indexed by the logical block index.
614+
* tile_block_pin_directs_map[logical block index][logical block pin] -> physical tile pin */
612615
std::unordered_map<int, std::unordered_map<int, int>> tile_block_pin_directs_map;
613616

614617
/* Returns the indices of pins that contain a clock for this physical logic block */
@@ -666,6 +669,7 @@ struct t_logical_block_type {
666669
int index = -1; /* index of type descriptor in array (allows for index referencing) */
667670

668671
std::vector<t_physical_tile_type_ptr> equivalent_tiles;
672+
std::map<int, std::vector<t_physical_tile_type_ptr>> placement_priority;
669673
};
670674

671675
/*************************************************************************************************

libs/libarchfpga/src/read_xml_arch_file.cpp

Lines changed: 58 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -220,13 +220,16 @@ e_side string_to_side(std::string side_str);
220220
static void link_physical_logical_types(std::vector<t_physical_tile_type>& PhysicalTileTypes,
221221
std::vector<t_logical_block_type>& LogicalBlockTypes);
222222

223-
static void check_port_equivalence(t_physical_tile_type& physical_tile, t_logical_block_type& logical_block);
223+
static void check_port_direct_mappings(t_physical_tile_type_ptr physical_tile, t_logical_block_type_ptr logical_block);
224224

225225
static const t_physical_tile_port* get_port_by_name(t_physical_tile_type_ptr type, const char* port_name);
226226
static const t_port* get_port_by_name(t_logical_block_type_ptr type, const char* port_name);
227227

228+
static const t_physical_tile_port* get_port_by_pin(t_physical_tile_type_ptr type, int pin);
229+
static const t_port* get_port_by_pin(t_logical_block_type_ptr type, int pin);
230+
228231
template<typename T>
229-
static T get_type_by_name(const char* type_name, std::vector<T>& types);
232+
static T* get_type_by_name(const char* type_name, std::vector<T>& types);
230233

231234
/*
232235
*
@@ -3221,7 +3224,10 @@ static void ProcessTileEquivalentSites(pugi::xml_node Parent,
32213224

32223225
auto LogicalBlockType = get_type_by_name<t_logical_block_type>(Prop.c_str(), LogicalBlockTypes);
32233226

3224-
ProcessEquivalentSiteDirects(CurSite, PhysicalTileType, &LogicalBlockType, Prop, loc_data);
3227+
auto priority = get_attribute(CurSite, "priority", loc_data, ReqOpt::OPTIONAL).as_int(0);
3228+
LogicalBlockType->placement_priority[priority].push_back(PhysicalTileType);
3229+
3230+
ProcessEquivalentSiteDirects(CurSite, PhysicalTileType, LogicalBlockType, Prop, loc_data);
32253231

32263232
CurSite = CurSite.next_sibling(CurSite.name());
32273233
}
@@ -4754,7 +4760,7 @@ static void link_physical_logical_types(std::vector<t_physical_tile_type>& Physi
47544760
physical_tile.equivalent_sites.push_back(&logical_block);
47554761
logical_block.equivalent_tiles.push_back(&physical_tile);
47564762

4757-
// TODO: Add check direct interconnect between site and tile add also pin mapping of integers
4763+
check_port_direct_mappings(&physical_tile, &logical_block);
47584764

47594765
logical_block_added++;
47604766
break;
@@ -4769,24 +4775,34 @@ static void link_physical_logical_types(std::vector<t_physical_tile_type>& Physi
47694775
}
47704776
}
47714777

4772-
static void check_port_equivalence(t_physical_tile_type& physical_tile, t_logical_block_type& logical_block) {
4773-
auto pb_type = logical_block.pb_type;
4774-
auto pb_type_ports = pb_type->ports;
4778+
static void check_port_direct_mappings(t_physical_tile_type_ptr physical_tile, t_logical_block_type_ptr logical_block) {
4779+
auto pb_type = logical_block->pb_type;
47754780

4776-
if (pb_type->num_ports != (int)physical_tile.ports.size()) {
4781+
if (pb_type->num_pins > physical_tile->num_pins) {
47774782
archfpga_throw(__FILE__, __LINE__,
4778-
"Logical and Physical types have a different number of ports.\n");
4783+
"Logical Block (%s) has more pins than the Physical Tile (%s).\n",
4784+
logical_block->name, physical_tile->name);
47794785
}
47804786

4781-
for (auto& tile_port : physical_tile.ports) {
4782-
auto block_port = pb_type_ports[tile_port.index];
4787+
auto& pin_direct_mapping = physical_tile->tile_block_pin_directs_map.at(logical_block->index);
47834788

4784-
if (0 != strcmp(tile_port.name, block_port.name)
4785-
|| tile_port.type != block_port.type
4786-
|| tile_port.num_pins != block_port.num_pins
4787-
|| tile_port.equivalent != block_port.equivalent) {
4789+
if (pb_type->num_pins != (int)pin_direct_mapping.size()) {
4790+
archfpga_throw(__FILE__, __LINE__,
4791+
"Logical Block (%s) has more pins than the one specified in the direct mapping.\n",
4792+
logical_block->name);
4793+
}
4794+
4795+
for (auto pin_map : pin_direct_mapping) {
4796+
auto block_port = get_port_by_pin(logical_block, pin_map.first);
4797+
auto tile_port = get_port_by_pin(physical_tile, pin_map.second);
4798+
4799+
if (0 != strcmp(tile_port->name, block_port->name)
4800+
|| tile_port->type != block_port->type
4801+
|| tile_port->num_pins != block_port->num_pins
4802+
|| tile_port->equivalent != block_port->equivalent) {
47884803
archfpga_throw(__FILE__, __LINE__,
4789-
"Logical and Physical types do not have equivalent port specifications.\n");
4804+
"Logical (%s) and Physical (%s) types do not have equivalent port specifications.\n",
4805+
logical_block->name, physical_tile->name);
47904806
}
47914807
}
47924808
}
@@ -4814,11 +4830,34 @@ static const t_port* get_port_by_name(t_logical_block_type_ptr type, const char*
48144830
return nullptr;
48154831
}
48164832

4833+
static const t_physical_tile_port* get_port_by_pin(t_physical_tile_type_ptr type, int pin) {
4834+
for (auto port : type->ports) {
4835+
if (pin >= port.absolute_first_pin_index && pin < port.num_pins) {
4836+
return &type->ports[port.index];
4837+
}
4838+
}
4839+
4840+
return nullptr;
4841+
}
4842+
4843+
static const t_port* get_port_by_pin(t_logical_block_type_ptr type, int pin) {
4844+
auto pb_type = type->pb_type;
4845+
4846+
for (int i = 0; i < pb_type->num_ports; i++) {
4847+
auto port = pb_type->ports[i];
4848+
if (pin >= port.absolute_first_pin_index && pin < port.num_pins) {
4849+
return &pb_type->ports[port.index];
4850+
}
4851+
}
4852+
4853+
return nullptr;
4854+
}
4855+
48174856
template<typename T>
4818-
static T get_type_by_name(const char* type_name, std::vector<T>& types) {
4819-
for (auto type : types) {
4857+
static T* get_type_by_name(const char* type_name, std::vector<T>& types) {
4858+
for (auto& type : types) {
48204859
if (0 == strcmp(type.name, type_name)) {
4821-
return type;
4860+
return &type;
48224861
}
48234862
}
48244863

vpr/src/place/place.cpp

Lines changed: 24 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -418,6 +418,8 @@ static void placement_inner_loop(float t,
418418

419419
static void recompute_costs_from_scratch(const t_placer_opts& placer_opts, const PlaceDelayModel* delay_model, t_placer_costs* costs);
420420

421+
static t_physical_tile_type_ptr pick_highest_priority_type(t_logical_block_type_ptr logical_block, int num_needed_types, int* free_locations);
422+
421423
static void calc_placer_stats(t_placer_statistics& stats, float& success_rat, double& std_dev, const t_placer_costs& costs, const int move_lim);
422424

423425
static void generate_post_place_timing_reports(const t_placer_opts& placer_opts,
@@ -2408,16 +2410,18 @@ static void initial_placement_pl_macros(int macros_max_num_tries, int* free_loca
24082410
// Assume that all the blocks in the macro are of the same type
24092411
blk_id = pl_macros[imacro].members[0].blk_index;
24102412
auto logical_block = cluster_ctx.clb_nlist.block_type(blk_id);
2411-
auto type = pick_random_placement_type(logical_block);
2412-
itype = type->index;
2413-
if (free_locations[itype] < int(pl_macros[imacro].members.size())) {
2413+
auto type = pick_highest_priority_type(logical_block, int(pl_macros[imacro].members.size()), free_locations);
2414+
2415+
if (type == nullptr) {
24142416
VPR_FATAL_ERROR(VPR_ERROR_PLACE,
24152417
"Initial placement failed.\n"
24162418
"Could not place macro length %zu with head block %s (#%zu); not enough free locations of type %s (#%d).\n"
24172419
"VPR cannot auto-size for your circuit, please resize the FPGA manually.\n",
24182420
pl_macros[imacro].members.size(), cluster_ctx.clb_nlist.block_name(blk_id).c_str(), size_t(blk_id), type->name, itype);
24192421
}
24202422

2423+
itype = type->index;
2424+
24212425
// Try to place the macro first, if can be placed - place them, otherwise try again
24222426
for (itry = 0; itry < macros_max_num_tries && macro_placed == false; itry++) {
24232427
// Choose a random position for the head
@@ -2484,15 +2488,17 @@ static void initial_placement_blocks(int* free_locations, enum e_pad_loc_type pa
24842488
* that location again, so remove it from the free_locations array.
24852489
*/
24862490

2487-
itype = pick_random_placement_type(logical_block)->index;
2491+
auto type = pick_highest_priority_type(logical_block, 1, free_locations);
24882492

2489-
if (free_locations[itype] <= 0) {
2493+
if (type == nullptr) {
24902494
VPR_FATAL_ERROR(VPR_ERROR_PLACE,
24912495
"Initial placement failed.\n"
24922496
"Could not place block %s (#%zu); no free locations of type %s (#%d).\n",
24932497
cluster_ctx.clb_nlist.block_name(blk_id).c_str(), size_t(blk_id), device_ctx.physical_tile_types[itype].name, itype);
24942498
}
24952499

2500+
itype = type->index;
2501+
24962502
t_pl_loc to;
24972503
initial_placement_location(free_locations, ipos, itype, to);
24982504

@@ -2844,6 +2850,19 @@ int check_macro_placement_consistency() {
28442850
return error;
28452851
}
28462852

2853+
static t_physical_tile_type_ptr pick_highest_priority_type(t_logical_block_type_ptr logical_block, int num_needed_types, int* free_locations) {
2854+
// Loop through the ordered map to get tiles in a decreasing priority order
2855+
for (auto& physical_tiles : logical_block->placement_priority) {
2856+
for (auto tile : physical_tiles.second) {
2857+
if (free_locations[tile->index] >= num_needed_types) {
2858+
return tile;
2859+
}
2860+
}
2861+
}
2862+
2863+
return nullptr;
2864+
}
2865+
28472866
#ifdef VERBOSE
28482867
static void print_clb_placement(const char* fname) {
28492868
/* Prints out the clb placements to a file. */

vpr/src/util/vpr_utils.cpp

Lines changed: 0 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -2283,34 +2283,6 @@ void place_sync_external_block_connections(ClusterBlockId iblk) {
22832283
place_ctx.block_locs[iblk].nets_and_pins_synced_to_z_coordinate = true;
22842284
}
22852285

2286-
void update_physical_pin_indices() {
2287-
auto& cluster_ctx = g_vpr_ctx.mutable_clustering();
2288-
auto& clb_nlist = cluster_ctx.clb_nlist;
2289-
2290-
for (auto blk : clb_nlist.blocks()) {
2291-
auto logical_block = clb_nlist.block_type(blk);
2292-
auto physical_tile = physical_tile_type(blk);
2293-
2294-
// Physical tile and logical block are already compatible
2295-
if (physical_tile == physical_tile_type(logical_block)) {
2296-
continue;
2297-
}
2298-
2299-
for (auto pin : clb_nlist.block_pins(blk)) {
2300-
int block_pin = clb_nlist.pin_logical_index(pin);
2301-
2302-
auto pin_directs_map = physical_tile->tile_block_pin_directs_map;
2303-
auto map_result = pin_directs_map.find(logical_block->index);
2304-
std::unordered_map<int, int> map = map_result->second;
2305-
2306-
auto pin_result = map.find(block_pin);
2307-
auto phys_pin = pin_result->second;
2308-
2309-
clb_nlist.set_pin_physical_index(pin, phys_pin);
2310-
}
2311-
}
2312-
}
2313-
23142286
int get_max_num_pins(t_logical_block_type_ptr logical_block) {
23152287
int max_num_pins = 0;
23162288

vpr/src/util/vpr_utils.h

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -172,7 +172,6 @@ void print_usage_by_wire_length();
172172
AtomBlockId find_memory_sibling(const t_pb* pb);
173173

174174
void place_sync_external_block_connections(ClusterBlockId iblk);
175-
void update_physical_pin_indices();
176175
int get_max_num_pins(t_logical_block_type_ptr logical_block);
177176

178177
bool is_tile_compatible(t_physical_tile_type_ptr physical_tile, t_logical_block_type_ptr logical_block);

0 commit comments

Comments
 (0)