How to get a physical intra-site net in RapidWright?

68 views
Skip to first unread message

wenchen

unread,
Dec 7, 2020, 2:37:14 AM12/7/20
to RapidWright
Hi RapidWright!

I'm a little bit confuse about how to get a physical intra-site net.
下载 (1).png
Suppose minus_op[28] is an intraSite net, and the design is already placed and routed.
I can get a inter-site net in both physical and logical level, but I can only get an intra-site net in logical level as shown below
下载.png

Note that "zcu104_fpx_i/FPDiv_0/inst/SelFunctionTable7/fR0_d1_reg[26]_i_1_n_0" is an inter-site net. 

Is it possible to get the intra-site physical net in RapidWright? 

Wen Chen

RapidWright

unread,
Dec 7, 2020, 1:58:36 PM12/7/20
to RapidWright
Hi Wen Chen,

This is a good question.  RapidWright has the Net object to capture intersite routing (routing that connects sites).  It contains the PIPs that connect site pins to each other, crossing tile boundaries to do so.  For intrasite routing (routing inside a site), the information is actually stored on the SiteInst object.  The SiteInst keeps a mapping between a site wire and the associated physical net name.  

In your example above, you would have two site wires that connect the output of a CARRY8 to the input of a FF:



The two disjoint yellow wires are the two site wires (CARRY8_O3 and FFMUXD1_OUT1 in this case).  If you were to query SiteInst.getNetFromSiteWire("CARRY8_O3"), you would potentially get a Net object with the appropriate intra-site name, but it would have no PIPs.  

Are there specific changes you would like to make to intra-site routing?  Let me know what you would like to do and I can try helping formulate a plan.

Thanks,

Chris
Message has been deleted

wenchen

unread,
Dec 8, 2020, 8:54:10 AM12/8/20
to RapidWright
Hi Chris!

Thank you very much for your answer, I have got the physical intra-site net!

I'm trying to develop an online slack monitor that measures when the rising edge reachs the FF/D. To achieve this, the OSM's input should be connected to D port of the FF to be monitored. 
1.png
At logical netlist level, I just want to add OSM/I to minusOp[28] and then route the design. And I have to modify the physical netlist to match the changes in the logical netlist. 
I think I should find the physical minusOp[28] net and add OSM/I's corresponding SitePin to it. And that's why I asked this question.

After I got the physical net successfully, I tried two method.

I first tried to add the OSM's port and pin to the net to be monitored in both logical level and phyiscal level, this method is simpler but I failed to open the modified dcp file. 

Then I turned to create a new net, and add related ports to it. However, minusOp[28] is an intra-site net and does not have any Pins in it. So I don't know how to connect the new net with the BELPins of minusOp[28].

The code and corresponding dcp file are already uploaded to 

Thank you again for your patient reply! 

Wen Chen

RapidWright

unread,
Dec 10, 2020, 1:44:06 PM12/10/20
to RapidWright
Hi Wen Chen,

I wrote up some example code (sorry its in Java, but you can port it to Python syntax pretty easily) that performs the manipulation you want.  The first step is to get the logical netlist to be connected in the way you want, after that, it is just cleaning up the physical implementation to match the logical.  Since you want to connect something across hierarchy, that can be a little tricky.  Luckily, in RapidWright there is an API that handles the heavy lifting called EDIFTools.connectLogicalNetAcrossHierarchy() that will create all the intermediate ports and nets in between the desired source and destination (added nets in magenta):

Here is the example code:

package com.xilinx.rapidwright.examples;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.Map;

import com.xilinx.rapidwright.design.Cell;
import com.xilinx.rapidwright.design.Design;
import com.xilinx.rapidwright.design.SiteInst;
import com.xilinx.rapidwright.design.SitePinInst;
import com.xilinx.rapidwright.edif.EDIFHierPortInst;
import com.xilinx.rapidwright.edif.EDIFNet;
import com.xilinx.rapidwright.edif.EDIFNetlist;
import com.xilinx.rapidwright.edif.EDIFTools;
import com.xilinx.rapidwright.router.Router;

public class OSMExample {

    public static void main(String[] args) {
        Design design = Design.readCheckpoint("osmlock_routed.dcp");
        EDIFNetlist netlist = design.getNetlist();
        // Need to flatten netlist to use connectLogicalNetAcrossHierarchy()
        EDIFTools.flattenNetlist(design);

        String srcPortName = "zcu104_fpx_i/FPDiv_0/inst/SelFunctionTable7/fR0_d1_reg[28]_i_1/O[1]";
        String snkPortName = "zcu104_fpx_i/OSM_Array_0/inst/generate_osm_array[0].osm_inst/Q1_reg/C";
        EDIFHierPortInst src = netlist.getHierPortInstFromName(srcPortName);
        EDIFHierPortInst sink = netlist.getHierPortInstFromName(snkPortName);
        Cell srcCell = design.getCell(src.getFullHierarchicalInstName());
        Cell sinkCell = design.getCell(sink.getFullHierarchicalInstName());
        
        // Propagate logical net minusOp[28] into the target instance of the OSM
        Map<String,EDIFNet> parentInstNameToLogNetMap = new HashMap<String, EDIFNet>();
        parentInstNameToLogNetMap.put(src.getHierarchicalInstName(), src.getNet());
        EDIFNet dstNet = EDIFTools.connectLogicalNetAcrossHierarchy(sink.getHierarchicalInstName(), 
                                src.getHierarchicalInstName(), parentInstNameToLogNetMap, netlist);
        
        // Disconnect the C input and connect it to the propagated D[0] net
        EDIFNet netToDisconnect = sink.getPortInst().getNet();
        netToDisconnect.removePortInst(sink.getPortInst());
        dstNet.addPortInst(sink.getPortInst());
        
        // Gets the physical net and creates output pin for routing, routes intra-site net
        // in source site 
        Net physNet = design.getNet(netlist.getParentNetName(src.getHierarchicalNetName()));
        SiteInst siteInst = srcCell.getSiteInst();
        SitePinInst newPin = physNet.createPin(true, "BMUX", siteInst);
        siteInst.routeIntraSiteNet(physNet, srcCell.getBELPin(src), newPin.getBELPin());
        
        // Gets the destination sink pin and updates intra-site routing accordingly
        SitePinInst sinkPin = sinkCell.getSitePinFromPortInst(sink.getPortInst(), null);
        sinkPin.getNet().removePin(sinkPin, true);
        sinkCell.unrouteLogicalPinInSite(sink.getPortInst().getName());
        sinkPin.setNet(physNet);
        siteInst = sinkCell.getSiteInst();
        siteInst.routeIntraSiteNet(physNet, sinkPin.getBELPin(), sinkCell.getBELPin(sink));
        
        // Routes the inter-site net with the new pin using the RapidWright router 
        // (not robust in the face of high congestion, but works here)
        Router rtr = new Router(design);
        ArrayList<SitePinInst> sinks = new ArrayList<SitePinInst>();
        sinks.add(sinkPin);
        rtr.routePinsReEntrant(sinks, false);
        
        design.writeCheckpoint("osmlock_modified.dcp");
    }
}

Let me know if you have questions.

Chris

wenchen

unread,
Dec 11, 2020, 1:48:41 AM12/11/20
to RapidWright
Hi Chris!

Thank you so much for your patience and efforts!
Your code did solve my problem and I do not have any question about  your code.

WenChen
Message has been deleted
Message has been deleted
Message has been deleted

wenchen

unread,
Dec 14, 2020, 4:15:16 AM12/14/20
to RapidWright
Hi Chris

I am trying to modify your code and encounter a question.
In your code, the sinkCell is unrouted and routeIntraSiteNet again

SitePinInst sinkPin = sinkCell.getSitePinFromPortInst(sink.getPortInst(), null);
sinkPin.getNet().removePin(sinkPin, true);
sinkCell.unrouteLogicalPinInSite(sink.getPortInst().getName());
sinkPin.setNet(physNet);
siteInst = sinkCell.getSiteInst();
siteInst.routeIntraSiteNet(physNet, sinkPin.getBELPin(), sinkCell.getBELPin(sink));

Unlike the srcCell, the sinkCell does not create a new SitePin and a new SiteWire, the following code also works
sinkPin = sinkCell.getSitePinFromPortInst(sink.getPortInst(), None)
sinkPin.getNet().removePin(sinkPin, True)
sinkPin.setNet(physNet)
physNet.addPin(sinkPin)

I want to know why the sinkCell is unrouted and routeIntraSiteNet again in your code, what's your consideration?  
 
Best Regards,
Wen Chen

RapidWright

unread,
Dec 14, 2020, 3:01:49 PM12/14/20
to RapidWright
Hi Wen Chen,

In the case of the sink, the path has already been routed as the 'C' pin is already connected in the original implementation.  The modification is to switch the source from the net:

zcu104_fpx_i/clk_wiz_0/inst/CLK_CORE_DRP_I/clk_inst/s_axi_aclk_0
to 
zcu104_fpx_i/FPDiv_0/inst/SelFunctionTable7/D[9]

The site routing will stay the same, but the new net needs to be associated with the routing and the best way to do that in RapidWright is through routeInstraSiteNet().  The SitePinInst also stays the same but must be associated with the new net.

In the case of the source, nothing is unrouted because a new path is being added.  The changes are only additive, nothing is modified.

Hope that helps.

Chris

wenchen

unread,
Dec 15, 2020, 9:19:40 AM12/15/20
to RapidWright
Hi Chris 

Thank you again for your patient explaination. 

Best Regards!

Wen Chen
Reply all
Reply to author
Forward
0 new messages