diff --git a/src/com/xilinx/rapidwright/rwroute/RWRoute.java b/src/com/xilinx/rapidwright/rwroute/RWRoute.java index e729c452a..da5ac3448 100644 --- a/src/com/xilinx/rapidwright/rwroute/RWRoute.java +++ b/src/com/xilinx/rapidwright/rwroute/RWRoute.java @@ -1911,6 +1911,7 @@ private float getNodeCost(RouteNode rnode, Connection connection, int countSameS // CRoute paper states that the bias factor cannot be more than half of the wire cost // (it may exceed this here because we may not be using the minimum-sized bounding box) float biasCost = rnode.getBaseCost() * Math.min(distToCenter * net.getBiasFactor(), 0.5f); + biasCost = 0; return rnode.getBaseCost() * rnode.getHistoricalCongestionCost() * presentCongestionCost / sharingFactor + biasCost; } diff --git a/src/com/xilinx/rapidwright/rwroute/RouteNode.java b/src/com/xilinx/rapidwright/rwroute/RouteNode.java index 42c380d35..d45c42527 100644 --- a/src/com/xilinx/rapidwright/rwroute/RouteNode.java +++ b/src/com/xilinx/rapidwright/rwroute/RouteNode.java @@ -147,6 +147,7 @@ private void setBaseCost() { baseCost = 0.4f; switch (type) { case LAGUNA_I: + assert(length == 0); // Make all approaches to SLLs zero-cost to encourage exploration // Assigning a base cost of zero would normally break congestion resolution // (since RWroute.getNodeCost() would return zero) but doing it here should be @@ -155,7 +156,7 @@ private void setBaseCost() { break; case SUPER_LONG_LINE: assert(length == RouteNodeGraph.SUPER_LONG_LINE_LENGTH_IN_TILES); - baseCost = 0.3f * length; + baseCost = 36f - 4f; break; case WIRE: // NOTE: IntentCode is device-dependent @@ -170,49 +171,54 @@ private void setBaseCost() { break; case NODE_LOCAL: case INTENT_DEFAULT: - assert(length <= 1); + if (length != 0) { + assert(length == 1); + baseCost = 0.6f; // 0.8 if staying in same tile + // 0.0 if towards target + } break; case NODE_SINGLE: - assert(length <= 2); - if (length == 2) baseCost *= length; + if (length != 0) { + // NODE_SINGLE could be length == 2, e.g. INT/WW1_W_BEG7 which + // feeds-through to the tile above + baseCost = 0.6f - 0.1f; + } break; case NODE_DOUBLE: if (endTileXCoordinate != getTile().getTileXCoordinate()) { - assert(length <= 2); - // Typically, length = 1 (since tile X is not equal) - // In US, have seen length = 2, e.g. VU440's INT_X171Y827/EE2_E_BEG7. - if (length == 2) baseCost *= length; + assert(length == 1); + // (EE|WW)2_[EW]_BEG[0-7] + baseCost = 0.6f - 0.1f; } else { - // Typically, length = 2 except for horizontal U-turns (length = 0) - // or vertical U-turns (length = 1). - // In US, have seen length = 3, e.g. VU440's INT_X171Y827/NN2_E_BEG7. - assert(length <= 3); + // (NN|SS)2_[EW]_BEG[0-7] + baseCost = 1.2f - 0.2f; // VSINGLE (-0.1) + 0.4 + VSINGLE (-0.1) + 0.4 = +0.6 -> -0.2 (-0.8) } break; case NODE_HQUAD: - assert (length != 0 || getAllDownhillNodes().isEmpty()); - baseCost = 0.35f * length; + baseCost = 1.2f - 0.2f; // HDOUBLE (-0.1) + 0.4 + HDOUBLE (-0.1) + 0.4 = +0.6 -> -0.2 (-0.8) break; case NODE_VQUAD: - // In case of U-turn nodes - if (length != 0) baseCost = 0.15f * length;// VQUADs have length 4 and 5 + baseCost = 2.4f - 1.2f; // VDOUBLE (-0.2) + 0.4 + VDOUBLE (-0.2) + 0.4 = +0.4 -> -1.2 (-1.6) break; case NODE_HLONG: - assert (length != 0 || getAllDownhillNodes().isEmpty()); - baseCost = 0.15f * length;// HLONGs have length 6 and 7 + baseCost = 3.6f - 2.0f; // HQUAD (-0.6) + 0.4 + HQUAD (-0.6) + 0.4 = -0.4 -> -2.0 (-1.6) break; case NODE_VLONG: - baseCost = 0.7f; + baseCost = 7.2f - 4.8f; // VQUAD (-1.2) + 0.4 + VQUAD (-1.2) + 0.4 = -1.6 -> -4.8 (-3.2) break; default: throw new RuntimeException(ic.toString()); } + assert(baseCost > 0.0f); break; - case PINFEED_I: case PINBOUNCE: + if (length != 0) { + assert(length == 1); + baseCost = 0.6f; + } break; + case PINFEED_I: case PINFEED_O: - baseCost = 1f; break; default: throw new RuntimeException(type.toString()); diff --git a/src/com/xilinx/rapidwright/rwroute/RouteNodeGraph.java b/src/com/xilinx/rapidwright/rwroute/RouteNodeGraph.java index f66cd5167..e0846cc35 100644 --- a/src/com/xilinx/rapidwright/rwroute/RouteNodeGraph.java +++ b/src/com/xilinx/rapidwright/rwroute/RouteNodeGraph.java @@ -560,9 +560,9 @@ public boolean isAccessible(RouteNode childRnode, Connection connection) { } int childX = childTile.getTileXCoordinate(); - if (connection.isCrossSLR() && nextLagunaColumn[childX] == childX) { - // Connection crosses SLR and this is a Laguna column - return true; + if (connection.getSinkRnode().getSLRIndex() != childRnode.getSLRIndex()) { + // Only accessible if connection needs to cross SLRs and this is a Laguna column + return nextLagunaColumn[childX] == childX; } Tile sinkTile = connection.getSinkRnode().getTile(); diff --git a/test/src/com/xilinx/rapidwright/rwroute/TestRWRoute.java b/test/src/com/xilinx/rapidwright/rwroute/TestRWRoute.java index aeefccf1a..856e3967e 100644 --- a/test/src/com/xilinx/rapidwright/rwroute/TestRWRoute.java +++ b/test/src/com/xilinx/rapidwright/rwroute/TestRWRoute.java @@ -272,37 +272,38 @@ void testSingleConnectionHelper(String partName, @CsvSource({ // One SLR crossing // (Too) Close - "SLICE_X9Y299,SLICE_X9Y300,500", // On Laguna column + "SLICE_X9Y299,SLICE_X9Y300,300", // On Laguna column "SLICE_X9Y300,SLICE_X9Y299,300", - "SLICE_X0Y299,SLICE_X0Y300,400", // Far from Laguna column - "SLICE_X0Y300,SLICE_X0Y299,100", - "SLICE_X53Y299,SLICE_X53Y300,200", // Equidistant from two Laguna columns - "SLICE_X53Y300,SLICE_X53Y299,700", + "SLICE_X0Y299,SLICE_X0Y300,300", // Far from Laguna column + "SLICE_X0Y300,SLICE_X0Y299,200", + "SLICE_X53Y299,SLICE_X53Y300,300", // Equidistant from two Laguna columns + "SLICE_X53Y300,SLICE_X53Y299,200", + // Perfect "SLICE_X9Y241,SLICE_X9Y300,200", "SLICE_X9Y300,SLICE_X9Y241,100", - "SLICE_X9Y358,SLICE_X9Y299,100", + "SLICE_X9Y358,SLICE_X9Y299,200", "SLICE_X9Y299,SLICE_X9Y358,200", - "SLICE_X53Y241,SLICE_X69Y300,500", - "SLICE_X53Y358,SLICE_X69Y299,500", + "SLICE_X53Y241,SLICE_X69Y300,300", + "SLICE_X53Y358,SLICE_X69Y299,600", // Far "SLICE_X9Y240,SLICE_X9Y359,100", // On Laguna - "SLICE_X9Y359,SLICE_X9Y240,200", + "SLICE_X9Y359,SLICE_X9Y240,100", "SLICE_X162Y240,SLICE_X162Y430,200", - "SLICE_X162Y430,SLICE_X162Y240,300", + "SLICE_X162Y430,SLICE_X162Y240,100", "SLICE_X0Y240,SLICE_X12Y430,400", // Far from Laguna "SLICE_X0Y430,SLICE_X12Y240,200", // Two SLR crossings "SLICE_X162Y299,SLICE_X162Y599,200", - "SLICE_X162Y599,SLICE_X162Y299,100", + "SLICE_X162Y599,SLICE_X162Y299,300", // Three SLR crossings "SLICE_X79Y0,SLICE_X79Y899,200", // Straight up: next to Laguna column - "SLICE_X0Y0,SLICE_X0Y899,600", // Straight up: far from Laguna column - "SLICE_X168Y0,SLICE_X168Y899,400", // Straight up: far from Laguna column - "SLICE_X9Y0,SLICE_X162Y899,1000", // Up and right - "SLICE_X168Y162,SLICE_X9Y899,800", // Up and left + "SLICE_X0Y0,SLICE_X0Y899,200", // Straight up: far from Laguna column + "SLICE_X168Y0,SLICE_X168Y899,200", // Straight up: far from Laguna column + "SLICE_X9Y0,SLICE_X162Y899,200", // Up and right + "SLICE_X168Y162,SLICE_X9Y899,200", // Up and left }) public void testSLRCrossingNonTimingDriven(String srcSiteName, String dstSiteName, long nodesPoppedLimit) { testSingleConnectionHelper(Device.AWS_F1, srcSiteName, "AQ", dstSiteName, "A1", nodesPoppedLimit);