diff --git a/vpr/src/base/gen/vpr_constraints_uxsdcxx.h b/vpr/src/base/gen/vpr_constraints_uxsdcxx.h index f2cd1bf64c4..4983c68486c 100644 --- a/vpr/src/base/gen/vpr_constraints_uxsdcxx.h +++ b/vpr/src/base/gen/vpr_constraints_uxsdcxx.h @@ -25,9 +25,7 @@ #include "pugixml.hpp" #include "vpr_constraints_uxsdcxx_interface.h" - -//sentinel value for indicating that a subtile has not been specified -constexpr int NO_SUBTILE = -1; +#include "region.h" /* All uxsdcxx functions and structs live in this namespace. */ namespace uxsd { diff --git a/vpr/src/base/partition_region.cpp b/vpr/src/base/partition_region.cpp index 8fe004b8585..d06bfa37240 100644 --- a/vpr/src/base/partition_region.cpp +++ b/vpr/src/base/partition_region.cpp @@ -9,6 +9,10 @@ std::vector PartitionRegion::get_partition_region() { return partition_region; } +void PartitionRegion::set_partition_region(std::vector pr) { + partition_region = pr; +} + bool PartitionRegion::empty() { return partition_region.size() == 0; } @@ -26,7 +30,7 @@ bool PartitionRegion::is_loc_in_part_reg(t_pl_loc loc) { return is_in_pr; } -PartitionRegion intersection(PartitionRegion& pr1, PartitionRegion& pr2) { +PartitionRegion intersection(const PartitionRegion& cluster_pr, const PartitionRegion& new_pr) { /**for N regions in part_region and M in the calling object you can get anywhere from * 0 to M*N regions in the resulting vector. Only intersection regions with non-zero area rectangles and * equivalent subtiles are put in the resulting vector @@ -34,12 +38,10 @@ PartitionRegion intersection(PartitionRegion& pr1, PartitionRegion& pr2) { */ PartitionRegion pr; Region intersect_region; - bool regions_intersect; - for (unsigned int i = 0; i < pr1.partition_region.size(); i++) { - for (unsigned int j = 0; j < pr2.partition_region.size(); j++) { - regions_intersect = do_regions_intersect(pr1.partition_region[i], pr2.partition_region[j]); - if (regions_intersect) { - intersect_region = intersection(pr1.partition_region[i], pr2.partition_region[j]); + for (unsigned int i = 0; i < cluster_pr.partition_region.size(); i++) { + for (unsigned int j = 0; j < new_pr.partition_region.size(); j++) { + intersect_region = intersection(cluster_pr.partition_region[i], new_pr.partition_region[j]); + if (!intersect_region.empty()) { pr.partition_region.push_back(intersect_region); } } @@ -48,6 +50,20 @@ PartitionRegion intersection(PartitionRegion& pr1, PartitionRegion& pr2) { return pr; } +void update_cluster_part_reg(PartitionRegion& cluster_pr, const PartitionRegion& new_pr) { + Region intersect_region; + std::vector int_regions; + for (unsigned int i = 0; i < cluster_pr.partition_region.size(); i++) { + for (unsigned int j = 0; j < new_pr.partition_region.size(); j++) { + intersect_region = intersection(cluster_pr.partition_region[i], new_pr.partition_region[j]); + if (!intersect_region.empty()) { + int_regions.push_back(intersect_region); + } + } + } + cluster_pr.set_partition_region(int_regions); +} + void print_partition_region(FILE* fp, PartitionRegion pr) { std::vector part_region = pr.get_partition_region(); diff --git a/vpr/src/base/partition_region.h b/vpr/src/base/partition_region.h index 25aa4949c31..799a530cbdc 100644 --- a/vpr/src/base/partition_region.h +++ b/vpr/src/base/partition_region.h @@ -27,6 +27,11 @@ class PartitionRegion { */ std::vector get_partition_region(); + /** + * @brief Set the union of regions + */ + void set_partition_region(std::vector pr); + /** * @brief Check if the PartitionRegion is empty (meaning there is no constraint on the object the PartitionRegion belongs to) */ @@ -43,10 +48,19 @@ class PartitionRegion { /** * @brief Global friend function that returns the intersection of two PartitionRegions * - * @param pr1 One of the PartitionRegions to be intersected - * @param pr2 One of the PartitionRegions to be intersected + * @param cluster_pr One of the PartitionRegions to be intersected + * @param new_pr One of the PartitionRegions to be intersected + */ + friend PartitionRegion intersection(const PartitionRegion& cluster_pr, const PartitionRegion& new_pr); + + /** + * @brief Global friend function that updates the PartitionRegion of a cluster with the intersection + * of the cluster PartitionRegion and a new PartitionRegion + * + * @param cluster_pr The cluster PartitionRegion that is to be updated + * @param new_pr The new PartitionRegion that the cluster PartitionRegion will be intersected with */ - friend PartitionRegion intersection(PartitionRegion& pr1, PartitionRegion& pr2); + friend void update_cluster_part_reg(PartitionRegion& cluster_pr, const PartitionRegion& new_pr); private: std::vector partition_region; ///< union of rectangular regions that a partition can be placed in diff --git a/vpr/src/base/region.cpp b/vpr/src/base/region.cpp index 54150ab2cfd..2035a57e717 100644 --- a/vpr/src/base/region.cpp +++ b/vpr/src/base/region.cpp @@ -1,8 +1,5 @@ #include "region.h" -/// @brief sentinel value for indicating that a subtile has not been specified -constexpr int NO_SUBTILE = -1; - Region::Region() { sub_tile = NO_SUBTILE; @@ -14,7 +11,7 @@ Region::Region() { region_bounds.set_ymax(-1); } -vtr::Rect Region::get_region_rect() { +vtr::Rect Region::get_region_rect() const { return region_bounds; } @@ -25,7 +22,7 @@ void Region::set_region_rect(int _xmin, int _ymin, int _xmax, int _ymax) { region_bounds.set_ymax(_ymax); } -int Region::get_sub_tile() { +int Region::get_sub_tile() const { return sub_tile; } @@ -82,7 +79,7 @@ bool do_regions_intersect(Region r1, Region r2) { return intersect; } -Region intersection(Region r1, Region r2) { +Region intersection(const Region& r1, const Region& r2) { Region intersect; /** diff --git a/vpr/src/base/region.h b/vpr/src/base/region.h index 1240f55acbb..9069ba180f6 100644 --- a/vpr/src/base/region.h +++ b/vpr/src/base/region.h @@ -13,6 +13,9 @@ * */ +/// @brief sentinel value for indicating that a subtile has not been specified +constexpr int NO_SUBTILE = -1; + class Region { public: /** @@ -23,7 +26,7 @@ class Region { /** * @brief Accessor for the region's rectangle */ - vtr::Rect get_region_rect(); + vtr::Rect get_region_rect() const; /** * @brief Mutator for the region's rectangle @@ -33,7 +36,7 @@ class Region { /** * @brief Accessor for the region's subtile */ - int get_sub_tile(); + int get_sub_tile() const; /** * @brief Mutator for the region's subtile @@ -84,7 +87,7 @@ bool do_regions_intersect(Region r1, Region r2); * @param r2 One of the regions to intersect * */ -Region intersection(Region r1, Region r2); +Region intersection(const Region& r1, const Region& r2); ///@brief Used to print data from a Region void print_region(FILE* fp, Region region); diff --git a/vpr/src/pack/cluster.cpp b/vpr/src/pack/cluster.cpp index cef6943d0cb..e8a26d590a1 100644 --- a/vpr/src/pack/cluster.cpp +++ b/vpr/src/pack/cluster.cpp @@ -1726,17 +1726,15 @@ static enum e_block_pack_status atom_cluster_floorplanning_check(const AtomBlock PartitionRegion& temp_cluster_pr, bool& cluster_pr_needs_update) { auto& floorplanning_ctx = g_vpr_ctx.mutable_floorplanning(); - VprConstraints ctx_constraints = floorplanning_ctx.constraints; /*check if the atom can go in the cluster by checking if the atom and cluster have intersecting PartitionRegions*/ //get partition that atom belongs to PartitionId partid; - partid = ctx_constraints.get_atom_partition(blk_id); + partid = floorplanning_ctx.constraints.get_atom_partition(blk_id); PartitionRegion atom_pr; PartitionRegion cluster_pr; - PartitionRegion intersect_pr; //if the atom does not belong to a partition, it can be put in the cluster //regardless of what the cluster's PartitionRegion is because it has no constraints @@ -1748,7 +1746,7 @@ static enum e_block_pack_status atom_cluster_floorplanning_check(const AtomBlock return BLK_PASSED; } else { //get pr of that partition - atom_pr = ctx_constraints.get_partition_pr(partid); + atom_pr = floorplanning_ctx.constraints.get_partition_pr(partid); //intersect it with the pr of the current cluster cluster_pr = floorplanning_ctx.cluster_constraints[clb_index]; @@ -1761,10 +1759,12 @@ static enum e_block_pack_status atom_cluster_floorplanning_check(const AtomBlock } return BLK_PASSED; } else { - intersect_pr = intersection(cluster_pr, atom_pr); + //update cluster_pr with the intersection of the cluster's PartitionRegion + //and the atom's PartitionRegion + update_cluster_part_reg(cluster_pr, atom_pr); } - if (intersect_pr.empty() == true) { + if (cluster_pr.empty() == true) { if (verbosity > 3) { VTR_LOG("\t\t\t Intersect: Atom block %d failed floorplanning check for cluster %d \n", blk_id, clb_index); } @@ -1772,7 +1772,7 @@ static enum e_block_pack_status atom_cluster_floorplanning_check(const AtomBlock return BLK_FAILED_FLOORPLANNING; } else { //update the cluster's PartitionRegion with the intersecting PartitionRegion - temp_cluster_pr = intersect_pr; + temp_cluster_pr = cluster_pr; cluster_pr_needs_update = true; if (verbosity > 3) { VTR_LOG("\t\t\t Intersect: Atom block %d passed cluster %d, cluster PR was updated with intersection result \n", blk_id, clb_index); @@ -2229,8 +2229,6 @@ static void start_new_cluster(t_cluster_placement_stats* cluster_placement_stats auto& device_ctx = g_vpr_ctx.mutable_device(); auto& floorplanning_ctx = g_vpr_ctx.mutable_floorplanning(); - VprConstraints ctx_constraints = floorplanning_ctx.constraints; - /*Cluster's PartitionRegion is empty initially, meaning it has no floorplanning constraints*/ PartitionRegion empty_pr; floorplanning_ctx.cluster_constraints.push_back(empty_pr); diff --git a/vpr/src/place/place_constraints.cpp b/vpr/src/place/place_constraints.cpp index e17c78f2111..5f6014a835f 100644 --- a/vpr/src/place/place_constraints.cpp +++ b/vpr/src/place/place_constraints.cpp @@ -114,6 +114,10 @@ PartitionRegion constrained_macro_locs(const t_pl_macro& pl_macro) { } /*returns true if location is compatible with floorplanning constraints, false if not*/ +/* + * Even if the block passed in is from a macro, it will work because of the constraints + * propagation that was done during initial placement. + */ bool cluster_floorplanning_legal(ClusterBlockId blk_id, const t_pl_loc& loc) { auto& floorplanning_ctx = g_vpr_ctx.floorplanning(); diff --git a/vpr/src/place/place_constraints.h b/vpr/src/place/place_constraints.h index 14da580c87f..b9121ebdcd7 100644 --- a/vpr/src/place/place_constraints.h +++ b/vpr/src/place/place_constraints.h @@ -6,6 +6,7 @@ * Author: khalid88 */ #include "move_transactions.h" +#include "region.h" #include "clustered_netlist_utils.h" #ifndef VPR_SRC_PLACE_PLACE_CONSTRAINTS_H_