aboutsummaryrefslogtreecommitdiffstats
path: root/common/placer_heap.cc
diff options
context:
space:
mode:
Diffstat (limited to 'common/placer_heap.cc')
-rw-r--r--common/placer_heap.cc46
1 files changed, 34 insertions, 12 deletions
diff --git a/common/placer_heap.cc b/common/placer_heap.cc
index 8a3b427f..3ee8503c 100644
--- a/common/placer_heap.cc
+++ b/common/placer_heap.cc
@@ -49,6 +49,7 @@
#include "nextpnr.h"
#include "place_common.h"
#include "placer1.h"
+#include "scope_lock.h"
#include "timing.h"
#include "util.h"
@@ -138,16 +139,19 @@ template <typename T> struct EquationSystem
class HeAPPlacer
{
public:
- HeAPPlacer(Context *ctx, PlacerHeapCfg cfg) : ctx(ctx), cfg(cfg), fast_bels(ctx, /*check_bel_available=*/true, -1)
+ HeAPPlacer(Context *ctx, PlacerHeapCfg cfg)
+ : ctx(ctx), cfg(cfg), fast_bels(ctx, /*check_bel_available=*/true, -1), tmg(ctx)
{
Eigen::initParallel();
+ tmg.setup_only = true;
+ tmg.setup();
}
bool place()
{
auto startt = std::chrono::high_resolution_clock::now();
- ctx->lock();
+ nextpnr::ScopeLock<Context> lock(ctx);
place_constraints();
build_fast_bels();
seed_placement();
@@ -268,7 +272,7 @@ class HeAPPlacer
// Update timing weights
if (cfg.timing_driven)
- get_criticalities(ctx, &net_crit);
+ tmg.run();
if (legal_hpwl < best_hpwl) {
best_hpwl = legal_hpwl;
@@ -312,7 +316,24 @@ class HeAPPlacer
log_info("AP soln: %s -> %s\n", cell.first.c_str(ctx), ctx->nameOfBel(cell.second->bel));
}
- ctx->unlock();
+ bool any_bad_placements = false;
+ for (auto bel : ctx->getBels()) {
+ CellInfo *cell = ctx->getBoundBelCell(bel);
+ if (!ctx->isBelLocationValid(bel)) {
+ std::string cell_text = "no cell";
+ if (cell != nullptr)
+ cell_text = std::string("cell '") + ctx->nameOf(cell) + "'";
+ log_warning("post-placement validity check failed for Bel '%s' "
+ "(%s)\n",
+ ctx->nameOfBel(bel), cell_text.c_str());
+ any_bad_placements = true;
+ }
+ }
+
+ if (any_bad_placements) {
+ return false;
+ }
+
auto endtt = std::chrono::high_resolution_clock::now();
log_info("HeAP Placer Time: %.02fs\n", std::chrono::duration<double>(endtt - startt).count());
log_info(" of which solving equations: %.02fs\n", solve_time);
@@ -320,8 +341,11 @@ class HeAPPlacer
log_info(" of which strict legalisation: %.02fs\n", sl_time);
ctx->check();
+ lock.unlock_early();
- placer1_refine(ctx, Placer1Cfg(ctx));
+ if (!placer1_refine(ctx, Placer1Cfg(ctx))) {
+ return false;
+ }
return true;
}
@@ -334,6 +358,8 @@ class HeAPPlacer
FastBels fast_bels;
std::unordered_map<IdString, std::tuple<int, int>> bel_types;
+ TimingAnalyser tmg;
+
struct BoundingBox
{
// Actual bounding box
@@ -371,8 +397,6 @@ class HeAPPlacer
// Performance counting
double solve_time = 0, cl_time = 0, sl_time = 0;
- NetCriticalityMap net_crit;
-
// Place cells with the BEL attribute set to constrain them
void place_constraints()
{
@@ -715,11 +739,9 @@ class HeAPPlacer
std::max<double>(1, (yaxis ? cfg.hpwl_scale_y : cfg.hpwl_scale_x) *
std::abs(o_pos - this_pos)));
- if (user_idx != -1 && net_crit.count(ni->name)) {
- auto &nc = net_crit.at(ni->name);
- if (user_idx < int(nc.criticality.size()))
- weight *= (1.0 + cfg.timingWeight *
- std::pow(nc.criticality.at(user_idx), cfg.criticalityExponent));
+ if (user_idx != -1) {
+ weight *= (1.0 + cfg.timingWeight * std::pow(tmg.get_criticality(CellPortKey(port)),
+ cfg.criticalityExponent));
}
// If cell 0 is not fixed, it will stamp +w on its equation and -w on the other end's equation,