diff --git a/src/com/xilinx/rapidwright/design/DesignTools.java b/src/com/xilinx/rapidwright/design/DesignTools.java index 987ab92ab..2af2743aa 100644 --- a/src/com/xilinx/rapidwright/design/DesignTools.java +++ b/src/com/xilinx/rapidwright/design/DesignTools.java @@ -1556,6 +1556,10 @@ public static List unrouteCellPinSiteRouting(Cell cell, String logi case PORT: { // We found a site pin, add it to solution set sitePinNames.add(pin.getName()); + if (belPin.isInput() && pin.isInput() && siteInst.getSitePinInst(pin.getName()) != null) { + // This is an input BEL pin that feeds a used output site pin, mark it as an internal sink + internalSinks.add(pin); + } break; } case BEL: { @@ -1572,7 +1576,13 @@ public static List unrouteCellPinSiteRouting(Cell cell, String logi // Make sure we are coming in on the routed-thru pin String otherPinName = otherCell.getPinMappingsP2L().keySet().iterator().next(); if (pin.getName().equals(otherPinName)) { - otherPin = LUTTools.getLUTOutputPin(pin.getBEL()); + if (otherCell.isFFRoutethruCell()) { + otherPin = pin.getBEL().getPin("Q"); + } else if (LUTTools.isCellALUT(otherCell)) { + otherPin = LUTTools.getLUTOutputPin(pin.getBEL()); + } else { + throw new RuntimeException("ERROR: Unrecognized routethru cell: " + cell.getName()); + } } } if (otherPin != null) { @@ -1740,67 +1750,48 @@ public static void makeBlackBox(Design d, EDIFHierCellInst hierarchicalCell) { } t.stop().start("Remove p&r"); + String prefix = hierarchicalCell.getFullHierarchicalInstName() + EDIFTools.EDIF_HIER_SEP; + for (SiteInst si : d.getSiteInsts()) { + for (Cell c : new ArrayList<>(si.getCells())) { + if (!c.getName().startsWith(prefix)) + continue; - List allLeafs = d.getNetlist().getAllLeafDescendants(hierarchicalCell); - Set cells = new HashSet<>(); - for (EDIFHierCellInst i : allLeafs) { - // Get the physical cell, make sure we can unplace/unroute it first - Cell c = d.getCell(i.getFullHierarchicalInstName()); - if (c == null) { - continue; - } - cells.add(c); - } - - // Remove all placement and routing information related to the cell to be - // blackboxed - for (Cell c : cells) { - BEL bel = c.getBEL(); - SiteInst si = c.getSiteInst(); - - // Check for VCC on A6 and remove if needed - if (c.getBEL().isLUT() && c.getBELName().endsWith("5LUT")) { - SitePinInst vcc = c.getSiteInst().getSitePinInst(c.getBELName().charAt(0) + "6"); - if (vcc != null && vcc.getNet().getName().equals(Net.VCC_NET)) { - boolean hasOtherSink = false; - for (BELPin otherSink : si.getSiteWirePins(vcc.getBELPin().getSiteWireIndex())) { - if (otherSink.isOutput()) - continue; - Cell otherCell = si.getCell(otherSink.getBEL()); - if (otherCell != null && otherCell.getLogicalPinMapping(otherSink.getName()) != null) { - hasOtherSink = true; - break; + // Remove all placement and routing information related to the cell to be + // blackboxed + BEL bel = c.getBEL(); + + // Check for VCC on A6 and remove if needed + if (c.getBEL().isLUT() && c.getBELName().endsWith("5LUT")) { + SitePinInst vcc = c.getSiteInst().getSitePinInst(c.getBELName().charAt(0) + "6"); + if (vcc != null && vcc.getNet().getName().equals(Net.VCC_NET)) { + boolean hasOtherSink = false; + for (BELPin otherSink : si.getSiteWirePins(vcc.getBELPin().getSiteWireIndex())) { + if (otherSink.isOutput()) + continue; + Cell otherCell = si.getCell(otherSink.getBEL()); + if (otherCell != null && otherCell.getLogicalPinMapping(otherSink.getName()) != null) { + hasOtherSink = true; + break; + } + } + if (!hasOtherSink) { + pinsToRemove.computeIfAbsent(vcc.getNet(), $ -> new HashSet<>()).add(vcc); } - } - if (!hasOtherSink) { - pinsToRemove.computeIfAbsent(vcc.getNet(), $ -> new HashSet<>()).add(vcc); } } - } - // Remove all physical nets first - for (String logPin : c.getPinMappingsP2L().values()) { - List removePins = unrouteCellPinSiteRouting(c, logPin); - for (SitePinInst pin : removePins) { - pinsToRemove.computeIfAbsent(pin.getNet(), $ -> new HashSet<>()).add(pin); + // Remove all physical nets first + for (String logPin : c.getPinMappingsP2L().values()) { + List removePins = unrouteCellPinSiteRouting(c, logPin); + for (SitePinInst pin : removePins) { + pinsToRemove.computeIfAbsent(pin.getNet(), $ -> new HashSet<>()).add(pin); + } } - } - touched.add(c.getSiteInst()); + touched.add(c.getSiteInst()); - c.unplace(); - d.removeCell(c.getName()); - si.removeCell(bel); - } - - t.stop().start("cleanup t-prims"); - - // Clean up any cells from Transformed Prims - String keepPrefix = hierarchicalCell.getFullHierarchicalInstName() + EDIFTools.EDIF_HIER_SEP; - for (SiteInst si : d.getSiteInsts()) { - for (Cell c : si.getCells()) { - if (c.getName().startsWith(keepPrefix)) { - touched.add(si); - } + c.unplace(); + d.removeCell(c.getName()); + si.removeCell(bel); } } @@ -1816,12 +1807,9 @@ public static void makeBlackBox(Design d, EDIFHierCellInst hierarchicalCell) { } } - batchRemoveSitePins(pinsToRemove, true); - // Rename nets if source was removed Set netsToKeep = new HashSet<>(); for (Entry e : netsToUpdate.entrySet()) { - EDIFHierNet newSource = d.getNetlist().getHierNetFromName(e.getValue()); Net net = e.getKey(); if (!net.rename(e.getValue())) { throw new RuntimeException("ERROR: Failed to rename net '" + net.getName() + "'"); @@ -1841,8 +1829,11 @@ public static void makeBlackBox(Design d, EDIFHierCellInst hierarchicalCell) { } for (SiteInst siteInst : siteInstsToRemove) { - d.removeSiteInst(siteInst); + d.removeSiteInst(siteInst, pinsToRemove); } + t.stop().start("cleanup nets"); + + batchRemoveSitePins(pinsToRemove, true); // Remove any stray stubs on any remaining nets for (Net net : pinsToRemove.keySet()) { @@ -1850,6 +1841,7 @@ public static void makeBlackBox(Design d, EDIFHierCellInst hierarchicalCell) { net.unroute(); } } + pinsToRemove.clear(); t.stop().start("create bbox"); @@ -2478,18 +2470,20 @@ public static BELPin getLogicalBELPinDriver(SitePinInst sitePinInst) { } return pin; } - // Looks like the approach above failed (site may not be routed), try logical path + // Looks like the approach above failed (site may not be routed), try logical path if netlist exists Net net = sitePinInst.getNet(); if (net == null) return null; Design design = siteInst.getDesign(); EDIFNetlist netlist = design.getNetlist(); - EDIFHierNet hierNet = netlist.getHierNetFromName(net.getName()); - if (hierNet == null) return null; - List portInsts = hierNet.getNet().getSourcePortInsts(false); - for (EDIFPortInst portInst : portInsts) { - Cell c = design.getCell(hierNet.getHierarchicalInstName(portInst)); - if (c != null) { - return c.getBELPin(portInst); + if (netlist != null) { + EDIFHierNet hierNet = netlist.getHierNetFromName(net.getName()); + if (hierNet == null) return null; + List portInsts = hierNet.getNet().getSourcePortInsts(false); + for (EDIFPortInst portInst : portInsts) { + Cell c = design.getCell(hierNet.getHierarchicalInstName(portInst)); + if (c != null) { + return c.getBELPin(portInst); + } } } return null;