From fbac35d67e9225195967aa6d43e895f9f49517a9 Mon Sep 17 00:00:00 2001 From: Chris Lavin Date: Wed, 20 Sep 2023 13:49:28 -0600 Subject: [PATCH 1/3] Properly add/remove dual-output pins (#825) Signed-off-by: Chris Lavin --- src/com/xilinx/rapidwright/rwroute/RWRoute.java | 14 +++++++++++++- 1 file changed, 13 insertions(+), 1 deletion(-) diff --git a/src/com/xilinx/rapidwright/rwroute/RWRoute.java b/src/com/xilinx/rapidwright/rwroute/RWRoute.java index e8519a83a..32f460f70 100644 --- a/src/com/xilinx/rapidwright/rwroute/RWRoute.java +++ b/src/com/xilinx/rapidwright/rwroute/RWRoute.java @@ -836,9 +836,10 @@ protected void postRouteProcess() { Net net = e.getKey(); SitePinInst source = net.getSource(); SitePinInst altSource = net.getAlternateSource(); + boolean altSourcePreviouslyRouted = altSource != null ? altSource.isRouted() : false; for (SitePinInst spi : Arrays.asList(source, altSource)) { if (spi != null) { - source.setRouted(false); + spi.setRouted(false); } } @@ -876,6 +877,17 @@ protected void postRouteProcess() { break; } } + // If the alt source was previously routed, and is no longer, let's remove it + if (altSource != null && altSourcePreviouslyRouted && !altSource.isRouted()) { + boolean sourceRouted = source.isRouted(); + altSource.getSiteInst().removePin(altSource); + net.removePin(altSource); + source.setRouted(sourceRouted); + if (altSource.getName().endsWith("_O") && source.getName().endsWith("MUX") && source.isRouted()) { + // Add site routing back if we are keeping the MUX pin + source.getSiteInst().routeIntraSiteNet(net, altSource.getBELPin(), altSource.getBELPin()); + } + } } } } From 95c7a5196c19567497805f76e3ae771d9f20ed8f Mon Sep 17 00:00:00 2001 From: eddieh-xlnx Date: Wed, 20 Sep 2023 12:50:39 -0700 Subject: [PATCH 2/3] Minor RWRoute and UltraScaleClockRouting fixes (#829) * [UltraScaleClockRouting] Disallow ability VROUTE -> HROUTE Signed-off-by: Eddie Hung * [RWRoute] saveRouting() to detect invalid backtracking Signed-off-by: Eddie Hung --------- Signed-off-by: Eddie Hung --- .../xilinx/rapidwright/router/UltraScaleClockRouting.java | 5 +++++ src/com/xilinx/rapidwright/rwroute/RWRoute.java | 6 +++++- 2 files changed, 10 insertions(+), 1 deletion(-) diff --git a/src/com/xilinx/rapidwright/router/UltraScaleClockRouting.java b/src/com/xilinx/rapidwright/router/UltraScaleClockRouting.java index b71dde068..d33adceb7 100644 --- a/src/com/xilinx/rapidwright/router/UltraScaleClockRouting.java +++ b/src/com/xilinx/rapidwright/router/UltraScaleClockRouting.java @@ -117,6 +117,11 @@ public static RouteNode routeToCentroid(Net clk, RouteNode startingRouteNode, Cl for (Wire w : curr.getWireConnections()) { RouteNode parent = curr.getParent(); if (parent != null) { + if (parent.getIntentCode() == IntentCode.NODE_GLOBAL_VROUTE && + w.getIntentCode() == IntentCode.NODE_GLOBAL_HROUTE) { + // Disallow ability to go from VROUTE back to HROUTE + continue; + } if (w.getIntentCode() == IntentCode.NODE_GLOBAL_VDISTR && curr.getIntentCode() == IntentCode.NODE_GLOBAL_VROUTE && parent.getIntentCode() == IntentCode.NODE_GLOBAL_VROUTE && diff --git a/src/com/xilinx/rapidwright/rwroute/RWRoute.java b/src/com/xilinx/rapidwright/rwroute/RWRoute.java index 32f460f70..bd6a781b5 100644 --- a/src/com/xilinx/rapidwright/rwroute/RWRoute.java +++ b/src/com/xilinx/rapidwright/rwroute/RWRoute.java @@ -1414,11 +1414,15 @@ private boolean saveRouting(Connection connection, RouteNode rnode) { RouteNode sourceRnode = rnodes.get(rnodes.size()-1); if (!sourceRnode.equals(connection.getSourceRnode())) { + if (!sourceRnode.equals(connection.getAltSourceRnode())) { + // Didn't backtrack to alternate source either -- invalid routing + return false; + } + // Used source node is different to the one set on the connection Net net = connection.getNetWrapper().getNet(); // Update connection's source SPI - assert(sourceRnode.equals(connection.getAltSourceRnode())); if (connection.getSource() == net.getSource()) { // Swap to alternate source connection.setSource(net.getAlternateSource()); From 106bf48869facfeffd7ee2c7d6eacc212b434262 Mon Sep 17 00:00:00 2001 From: Chris Lavin Date: Wed, 20 Sep 2023 14:50:57 -0600 Subject: [PATCH 3/3] [EDIFNetlist] - Ensure Macro Expansion Deep Copies Children (#828) * [EDIFNetlist] Fix deep copy children reference to netlist Signed-off-by: Chris Lavin * Add test Signed-off-by: Chris Lavin * Update test/src/com/xilinx/rapidwright/edif/TestEDIFHierPortInst.java Signed-off-by: Chris Lavin * Adding back missing import Signed-off-by: Chris Lavin * Use EDIFNetlist.getHDIPrimitive() instead Signed-off-by: Eddie Hung --------- Signed-off-by: Chris Lavin Signed-off-by: Eddie Hung Co-authored-by: Eddie Hung --- .../xilinx/rapidwright/edif/EDIFNetlist.java | 9 ++++++- .../edif/TestEDIFHierPortInst.java | 25 +++++++++++++++++++ 2 files changed, 33 insertions(+), 1 deletion(-) diff --git a/src/com/xilinx/rapidwright/edif/EDIFNetlist.java b/src/com/xilinx/rapidwright/edif/EDIFNetlist.java index 172a73dec..4117f3ca4 100644 --- a/src/com/xilinx/rapidwright/edif/EDIFNetlist.java +++ b/src/com/xilinx/rapidwright/edif/EDIFNetlist.java @@ -1652,7 +1652,14 @@ public void expandMacroUnisims(Series series) { } // Add copy to prim library to avoid destructive changes when collapsed // Needs to be a deep copy because it may have child instances that will get updated - new EDIFCell(netlistPrims, toAdd, cellName); + EDIFCell deepCopy = new EDIFCell(netlistPrims, toAdd, cellName); + for (EDIFCellInst inst : deepCopy.getCellInsts()) { + EDIFCell child = netlistPrims.getCell(inst.getCellName()); + if (child == null) { + EDIFCell childCopy = new EDIFCell(netlistPrims, inst.getCellType(), inst.getCellType().getName()); + inst.setCellType(childCopy); + } + } } // Update all cell references to macro versions diff --git a/test/src/com/xilinx/rapidwright/edif/TestEDIFHierPortInst.java b/test/src/com/xilinx/rapidwright/edif/TestEDIFHierPortInst.java index 84f8887c3..705e5f0cc 100644 --- a/test/src/com/xilinx/rapidwright/edif/TestEDIFHierPortInst.java +++ b/test/src/com/xilinx/rapidwright/edif/TestEDIFHierPortInst.java @@ -26,6 +26,8 @@ import com.xilinx.rapidwright.design.Design; import com.xilinx.rapidwright.design.Unisim; import com.xilinx.rapidwright.device.Device; +import com.xilinx.rapidwright.device.Series; + import org.junit.jupiter.api.Assertions; import org.junit.jupiter.api.Test; @@ -46,4 +48,27 @@ void testGetPhysicalCell() { // Check that we can still find it in this case Assertions.assertEquals(c, ehpi.getPhysicalCell(d)); } + + @Test + public void testGetPhysicalCellMacroHierarchy() { + Design design = new Design("design", "xcvc1902-vsvd1760-2MP-e-S"); + EDIFNetlist n = design.getNetlist(); + + EDIFCell macro = n.getHDIPrimitive(Unisim.RAM64X1D); + Assertions.assertSame(n.getHDIPrimitivesLibrary(), macro.getLibrary()); + n.getTopCell().createChildCellInst("inst", macro); + n.expandMacroUnisims(Series.Versal); + + String cellName = "inst/DP/RAMD64_INST"; + + // We can't instantiate RAM64X1D since it's a transformed prim, so we'll update + // the type after creation + Cell c = design.createAndPlaceCell(cellName, Unisim.LUT6, "SLICE_X235Y138/B6LUT"); + c.setType(Unisim.RAM64X1D.toString()); + + EDIFHierCellInst leafInst = n.getHierCellInstFromName("inst/DP/RAMD64_INST"); + + EDIFHierPortInst portInst = new EDIFHierPortInst(leafInst.getParent(), leafInst.getInst().getPortInst("O")); + Assertions.assertEquals(c, portInst.getPhysicalCell(design)); + } }