(including pads,topcell=wrap_qmults)
This design flow expects that you are working in a design directory (e.g. ~/design/ams/ams_demo) with a number of sub-directories containing files created during the preceding synthesis stage:
This directory contains a gate-level verilog netlist <topcell>.v (e.g. wrap_qmults.v) and an associated delay file <topcell>.sdf (e.g. wrap_qmults.sdf)
This directory contains a design constraints file <topcell>.sdc (e.g. wrap_qmults.sdc)
This directory contains a pad ring specification file <topcell>.io (e.g. wrap_qmults.io)
If your files aren't in these directories or don't have these names, then the first thing to do is to create any missing directories and copy the files into place with the correct names.
If you don't have a pad ring specification file (and if the example wrap_qmults.io file is not what you want) then you can generate the .io file from a simple text file using the "process_pad_ring" script. The format of the text file can be seen in this example: qmults_pads.txt
Note - if you read the whole of the preparation section before typing any commands you may save yourself some time and some typing.
Within your working directory (e.g. ~/design/ams/ams_demo), create a new sub-directory for the place and route files and change to the new directory:
mkdir place_and_route cd place_and_routeNow run the ams_edis script with appropriate options to specify a 4-metal 0.35µm process running at 3.3 volts with core cells from the CORELIB library and pad cells from the IOLIB library:
ams_edis -tech c35 \ -vn <topcell>.v -vt <topcell> \ -metlay thin4M \ -corelib CORELIB \ -corevolt _3.3V \ -corevolt_wc _3.3V \ -corevolt_bc _3.3V \ -iolib IOLIB \ -iovolt _3.3V \ -iovolt_wc _3.3V \ -iovolt_bc _3.3V \ -ediver EDI13.1ISR4Following this, you will need to add symbolic links for the gate-level netlist and the constraints file mentioned above to ensure that the place and route software can find them:
ln -s ../../gate_level/<topcell>.v VERILOG/<topcell>.v ln -s ../../constraints/<topcell>.sdc CONSTRAINTS/<topcell>_func.sdc ln -s ../../constraints/<topcell>.sdc CONSTRAINTS/<topcell>_test.sdc
Note that the AMS scripts expect separate constraints files for functional mode (<topcell>_func.sdc) and test mode (<topcell>_test.sdc). This might allow us to specify tight timing constraints for the functional mode and looser constraints (e.g. a slower clock speed) for the test mode. For this walkthrogh we have generated only one set of timing constraints, so we link both of the expected files to the single constraints file (design.sdc).
Finally save a copy of the edi_custom_c35b4.tcl TCL script file into this directory.
If the source files are as specified in the prerequisites section above and you do not want to change any of the options to the ams_edis script, you can use the following sequence of commands in place of those above:
prepare_edi <topcell> place_and_route cd place_and_route
Within your new place and route directory (e.g. ~/design/ams/ams_demo/place_and_route), use the "encounter" command to start the place and route tool:
encounter
You should see a new GUI window where you will later see the chip layout take shape. For now you should look at the terminal window where you should find the encounter prompt: "encounter 1>". Here you should type the following sequence of commands to import the design:
set io_filename ../padring/<topcell>.io
source edi_custom_c35b4.tcl
amsDbSetup
specifyScanChain ScanChain0 -start SDI -stop SDO
amsSetMMMC amsSetAnalysisView minmax {func test}
Note that commands in the list above which start with "ams" are AMS specific commands. These commands are defined in the "amsSetup.tcl" file which is a TCL script created by the "ams_edis" script. This "amsSetup.tcl" script invokes Cadence commands; later you will write your own TCL script to invoke the commands needed to place and route your design.
loadIoFile $io_filename
fit
If all goes well, you will see your pre-defined padring in the GUI window following the fit command.
At the floor planning stage we divide the chip into different areas some of which may be used for standard cells while others will be used for macro blocks such as ROMs and RAMs. In this simple design a single area for all of the standard cells should be enough.
floorPlan -r 1 0.7 60 60 60 60
Filler cells are needed for the pad ring to join the pad power rings.
snap_ams_pads
this command is defined in the edi_custom_c35b4.tcl script.
amsFillperi
amsGlobalConnect both
globalNetConnect gnd! -type pgpin -pin A -inst CORE_GND_* -module {} globalNetConnect vdd! -type pgpin -pin A -inst CORE_VDD_* -module {}note that these commands assume that the instance names for the core power pads in the gate-level verilog netlist have names beginning "CORE_GND_" and "CORE_VDD_".
addRing \ -type core_rings \ -nets {gnd! vdd!} \ -center 1 \ -layer {bottom MET3 top MET3 right MET4 left MET4} \ -width 20 -spacing 2
Once the power rings have been added we can perform the power routing for the connections to the pad cells and the core rows which will later hold the standard cells.
sroute \ -connect { blockPin padPin padRing corePin floatingStripe } \ -layerChangeRange { MET1 MET4 } \ -blockPinTarget { nearestTarget } \ -padPinPortConnect { allPort oneGeom } \ -padPinTarget { nearestTarget } \ -corePinTarget { firstAfterRowEnd } \ -floatingStripeTarget { blockring padring ring stripe ringpin blockpin followpin } \ -allowJogging 1 \ -crossoverViaLayerRange { MET1 MET4 } \ -nets { vdd! gnd! } \ -allowLayerChange 1 \ -blockPin useLef \ -targetViaLayerRange { MET1 MET4 }
saveDesign floorplan.encThe "floorplan.enc" file specified in the command does not contain the design data itself but it does contain information required to restore the saved design later (the design data itself is stored in a Cadence library directory named "FEOADesignlib" with a cell name "<topcell>" and a view name "floorplan").
If you need to recover this version of the design later, you can start encounter with the following options: encounter -init floorplan.enc -win
The next stage is to place the standard cells in the core.
setDrawView place
placeDesign amsAddEndCaps
setTieHiLoMode -cell {LOGIC1 LOGIC0} -maxFanout 10 addTieHiLo
This will replace any '1' or '0' signals in the Verilog netlist with safer connections to the TieHi and TieLo cells.
saveDesign placed.enc
Note that the "placeDesign" command seems to have added wiring as well as cells. The wiring that you see is as a result of a trial routing stage and will later be replaced by the actual routing.
Also note that the row utilisation (at least for small designs) is much less than the 70% specified during the "floorPlan" command above. The row utilisation is less than 70% for small designs because the design is pad limited rather than core limited (i.e. the size of the design is primarily a function of the number of pads rather than a function of the number of gates in the design).
During optimisation the tool can add buffers to reduce delays in high capacitance paths. Other optimisations that can take place at this stage include the re-sizing of gates (to increase drive strength or to decrease capacitive load) and the movement of gates to reduce path lengths.
optDesign -preCTS
This is the first of three optimisation stages, identified as "Pre-CTS" because it happens before Clock Tree Synthesis.
If all is well, you will see a section marked "optDesign Final Summary" which shows no "Setup mode" "Violating Paths" and no nets with design rule violations (DRVs).
If there are oustanding problems at this stage, seek advice. It may be worthwhile running a further optimisation at this stage in order to improve the design before proceding.
setCTSMode -engine ck setCTSMode -traceDPinAsLeaf true -traceIOPinAsLeaf true createClockTreeSpec \ -bufferList {CLKBU2 CLKBU4 CLKBU6 CLKBU8 CLKBU12 CLKBU15 CLKIN0 CLKIN1 CLKIN2 CLKIN3 CLKIN4 CLKIN6 CLKIN8 CLKIN10 CLKIN12 CLKIN15} \ -routeClkNet -output CONSTRAINTS/clock.clk
specifyClockTree -file CONSTRAINTS/clock.clk ckSynthesis
saveDesign inc_clock_tree.enc
The original constraints file included instructions to set the clock latency, clock transition and clock uncertainty in order to model the predicted delay through the clock tree and the jitter in the input clock. Now that we have a real clock tree we need to update the constraints to reflect the delays through this tree.
set_interactive_constraint_modes {func test}
set_propagated_clock [all_clocks]
set_clock_uncertainty -setup 0.5 [get_clocks master_clock] set_clock_uncertainty -hold 0.1 [get_clocks master_clock]This time we split the uncertainty for the setup and hold tests since jitter affects setup calculations but not hold calculations. Having a non-zero value for the clock uncertainty related to hold increases our confidence that the design will work if the skew in the clock tree is miscalculated.
Based on the design including the clock tree and the updated constraints a new round of optimisations is run. At this stage we are interested in particular in hold vioalations caused by problems with clock skew.
set_analysis_view -setup {func_max func_typ func_min} -hold {func_max func_typ func_min}
optDesign -postCTS -hold
As before you should check the "optDesign Final Summary" from each of the "optDesign" commands to check for problems.
Although various trial routing has already taken place during the optimisation and clock tree synthesis stages, onlt the power routing that we did at the beginning of the process is fixed. Now that all the cells are in place, we are ready to route the design for real.
routeDesign -globalDetail
At this stage the design is nominally complete but may have errors. The final optimisation stage aims to identify and resolve any remaining problems.
setDelayCalMode -engine default -siAware true setAnalysisMode -analysisType onChipVariation optDesign -postRoute -hold optDesign -postRoute optDesign -postRoute -drv
Filler cells are needed for the core to join the wells and to add well and substrate taps.
amsFillcore
While the tools will do their best to generate a design rule correct layout which matches the connectivity of the original design, things do go wrong. At this stage you should run the following verify commands and check for any violations.
verifyConnectivity
verifyGeometry
dbGet top.fPlan.boxes
(the numbers returned are the x and y co-ordinates of the lower left corner of the chip followed by the x and y co-ordinates of the upper right corner)
saveDesign routed.enc
amsWrite final
amsWriteSDF4View {func_max}
The whole procedure can be automated using a tcl script. This is especially useful if having created a chip layout, you make a minor change to the design and need to go through the whole process again.
Within encounter, the script can be executed using the command: source <scriptname>.tcl
# set the io file name and boolean for scan path (these lines will need to be customised) set io_filename ../padring/<topcell>.io set scan_path_included <true|false> # load custom script source edi_custom_c35b4.tcl # initialise the database (load in the design) amsDbSetup # if your design supports one, specify a scan chain if { $scan_path_included } { specifyScanChain ScanChain0 -start SDI -stop SDO } # timing setup amsSetMMMC amsSetAnalysisView minmax {func test} # Place the pad cells (including corners and power) loadIoFile $io_filename # view design in gui fit # create some space for the power rings # 60um spacing is plenty for 2x 20 um power rings floorPlan -r 1 0.7 60 60 60 60 # Snap the pad cells to the 0.1 um grid with spacing divisible by 1 um snap_ams_pads # Add peripheral filler cells amsFillperi # specify the connectivity of for the power nets amsGlobalConnect both globalNetConnect gnd! -type pgpin -pin A -inst CORE_GND_* -module {} globalNetConnect vdd! -type pgpin -pin A -inst CORE_VDD_* -module {} # add the power rings (note a 20um ring is classed as "wide metal" - >10um) # spacing of 2um is minimum for thick MET4 addRing \ -type core_rings \ -nets {gnd! vdd!} \ -center 1 \ -layer {bottom MET3 top MET3 right MET4 left MET4} \ -width 20 -spacing 2 # add power and ground routing (special route) sroute \ -connect { blockPin padPin padRing corePin floatingStripe } \ -layerChangeRange { MET1 MET4 } \ -blockPinTarget { nearestTarget } \ -padPinPortConnect { allPort oneGeom } \ -padPinTarget { nearestTarget } \ -corePinTarget { firstAfterRowEnd } \ -floatingStripeTarget { blockring padring ring stripe ringpin blockpin followpin } \ -allowJogging 1 \ -crossoverViaLayerRange { MET1 MET4 } \ -nets { vdd! gnd! } \ -allowLayerChange 1 \ -blockPin useLef \ -targetViaLayerRange { MET1 MET4 } # Save intermediate design saveDesign floorplan.enc # ------------------- # to start again here type: encounter -init floorplan.enc -win # ------------------- # Placement setDrawView place placeDesign amsAddEndCaps # Add Tiehi/Tielo cells setTieHiLoMode -cell {LOGIC1 LOGIC0} -maxFanout 10 addTieHiLo # Save intermediate design saveDesign placed.enc # ------------------- # to start again here type: encounter -init placed.enc -win # ------------------- # Pre-CTS Optimisation optDesign -preCTS # Clock Tree Synthesis setCTSMode -engine ck setCTSMode -traceDPinAsLeaf true -traceIOPinAsLeaf true createClockTreeSpec \ -bufferList {CLKBU2 CLKBU4 CLKBU6 CLKBU8 CLKBU12 CLKBU15 CLKIN0 CLKIN1 CLKIN2 CLKIN3 CLKIN4 CLKIN6 CLKIN8 CLKIN10 CLKIN12 CLKIN15} \ -routeClkNet -output CONSTRAINTS/clock.clk specifyClockTree -file CONSTRAINTS/clock.clk ckSynthesis # Save intermediate design saveDesign inc_clock_tree.enc # ------------------- # to start again here type: encounter -init inc_clock_tree.enc -win # ------------------- # Post-CTS - update constraints set_interactive_constraint_modes {func test} # replace predicted latency and transition with actual values through clock tree set_propagated_clock [all_clocks] # set jitter to 0.5 ns (clock skew is no longer important) set_clock_uncertainty -setup 0.5 [get_clocks master_clock] set_clock_uncertainty -hold 0.1 [get_clocks master_clock] # Post-CTS Optimisation set_analysis_view -setup {func_max func_typ func_min} -hold {func_max func_typ func_min} optDesign -postCTS -hold # route with nanoRoute routeDesign -globalDetail # Post-route optimisation setDelayCalMode -engine default -siAware true setAnalysisMode -analysisType onChipVariation optDesign -postRoute -hold optDesign -postRoute optDesign -postRoute -drv # Add core filler cells after optimisation as suggested by Michael Nydegger (but not by RAL) amsFillcore # Verify connectivity and geometry verifyConnectivity verifyGeometry # Get size of design set size [ dbGet top.fPlan.boxes ] print "CHIP SIZE IS $size" # Save final design saveDesign routed.enc amsWrite final amsWriteSDF4View {func_max} # ------------------- # to start again here type: encounter -init routed.enc -win # -------------------
While this first script does everything that we need, it doesn't care about the results of an individual operation and will carry on regardless of failures such as unresolved timing violations during the optimisation stages.
A more advanced script will use the timeDesign and get_metric commands to halt operations if a problem is identified.
# set the io file name and boolean for scan path (these lines will need to be customised) set io_filename ../padring/<topcell>.io set scan_path_included <true|false> # load custom script source edi_custom_c35b4.tcl # initialise the database (load in the design) amsDbSetup # if your design supports one, specify a scan chain if { $scan_path_included } { specifyScanChain ScanChain0 -start SDI -stop SDO } # timing setup amsSetMMMC amsSetAnalysisView minmax {func test} # Place the pad cells (including corners and power) if { ! [file exists $io_filename] } { print "NO I/O FILE: $io_filename - GIVING UP" return } loadIoFile $io_filename # view design in gui fit # create some space for the power rings # 60um spacing is plenty for 2x 20 um power rings floorPlan -r 1 0.7 60 60 60 60 # Snap the pad cells to the 0.1 um grid with spacing divisible by 1 um snap_ams_pads # Add peripheral filler cells amsFillperi # specify the connectivity of for the power nets amsGlobalConnect both globalNetConnect gnd! -type pgpin -pin A -inst CORE_GND_* -module {} globalNetConnect vdd! -type pgpin -pin A -inst CORE_VDD_* -module {} # add the power rings (note a 20um ring is classed as "wide metal" - >10um) # spacing of 2um is minimum for thick MET4 addRing \ -type core_rings \ -nets {gnd! vdd!} \ -center 1 \ -layer {bottom MET3 top MET3 right MET4 left MET4} \ -width 20 -spacing 2 # add power and ground routing (special route) sroute \ -connect { blockPin padPin padRing corePin floatingStripe } \ -layerChangeRange { MET1 MET4 } \ -blockPinTarget { nearestTarget } \ -padPinPortConnect { allPort oneGeom } \ -padPinTarget { nearestTarget } \ -corePinTarget { firstAfterRowEnd } \ -floatingStripeTarget { blockring padring ring stripe ringpin blockpin followpin } \ -allowJogging 1 \ -crossoverViaLayerRange { MET1 MET4 } \ -nets { vdd! gnd! } \ -allowLayerChange 1 \ -blockPin useLef \ -targetViaLayerRange { MET1 MET4 } # Check to see if there are problems with the floorplan (e.g. gaps between pad cells) verifyGeometry if { [get_metric -value verify.geom.total] != 0 } { print "FLOORPLAN GEOMETRY CHECK FAILED - GIVING UP" return } # Save intermediate design saveDesign floorplan.enc # ------------------- # to start again here type: encounter -init floorplan.enc -win # ------------------- # Placement setDrawView place placeDesign amsAddEndCaps # Add Tiehi/Tielo cells setTieHiLoMode -cell {LOGIC1 LOGIC0} -maxFanout 10 addTieHiLo # Save intermediate design saveDesign placed.enc # ------------------- # to start again here type: encounter -init placed.enc -win # ------------------- # Pre-CTS Optimisation optDesign -preCTS # Check Timing timeDesign -preCTS if { [get_metric -value timing.setup.numViolatingPaths.all] != 0 } { print "PRECTS SETUP CHECK FAILED - GIVING UP" return } # Clock Tree Synthesis setCTSMode -engine ck setCTSMode -traceDPinAsLeaf true -traceIOPinAsLeaf true createClockTreeSpec \ -bufferList {CLKBU2 CLKBU4 CLKBU6 CLKBU8 CLKBU12 CLKBU15 CLKIN0 CLKIN1 CLKIN2 CLKIN3 CLKIN4 CLKIN6 CLKIN8 CLKIN10 CLKIN12 CLKIN15} \ -routeClkNet -output CONSTRAINTS/clock.clk specifyClockTree -file CONSTRAINTS/clock.clk ckSynthesis # Save intermediate design saveDesign inc_clock_tree.enc # ------------------- # to start again here type: encounter -init inc_clock_tree.enc -win # ------------------- # Post-CTS - update constraints set_interactive_constraint_modes {func test} # replace predicted latency and transition with actual values through clock tree set_propagated_clock [all_clocks] # set jitter to 0.5 ns (clock skew is no longer important) set_clock_uncertainty -setup 0.5 [get_clocks master_clock] set_clock_uncertainty -hold 0.1 [get_clocks master_clock] # Post-CTS Optimisation set_analysis_view -setup {func_max func_typ func_min} -hold {func_max func_typ func_min} optDesign -postCTS -hold # Check Timing timeDesign -postCTS -hold if { [get_metric -value timing.setup.numViolatingPaths.all] != 0 } { print "POSTCTS SETUP CHECK FAILED - GIVING UP" return } if { [get_metric -value timing.hold.numViolatingPaths.all] != 0 } { print "POSTCTS HOLD CHECK FAILED - GIVING UP" return } # route with nanoRoute routeDesign -globalDetail # Post-route optimisation setDelayCalMode -engine default -siAware true setAnalysisMode -analysisType onChipVariation optDesign -postRoute -hold optDesign -postRoute optDesign -postRoute -drv # Check Timing timeDesign -postRoute -hold if { [get_metric -value timing.setup.numViolatingPaths.all] != 0 } { print "POSTROUTE SETUP CHECK FAILED - GIVING UP" return } if { [get_metric -value timing.hold.numViolatingPaths.all] != 0 } { print "POSTROUTE HOLD CHECK FAILED - GIVING UP" return } # Add core filler cells after optimisation as suggested by Michael Nydegger (but not by RAL) amsFillcore # Verify connectivity and geometry verifyConnectivity if { [get_metric -value verify.conn] != 0 } { print "CONNECTIVITY CHECK FAILED - GIVING UP" return } verifyGeometry if { [get_metric -value verify.geom.total] != 0 } { print "GEOMETRY CHECK FAILED - GIVING UP" return } # Get size of design set size [ dbGet top.fPlan.boxes ] print "CHIP SIZE IS $size" # Save final design saveDesign routed.enc amsWrite final amsWriteSDF4View {func_max} # ------------------- # to start again here type: encounter -init routed.enc -win # ------------------- print "PLACE AND ROUTE COMPLETED"
All Encounter documentation is available on-line via Cadence Help. Type the following at the unix command prompt in order to invoke Cadence Help:
cdnshelp_for encounter &
On-line manuals of particular interest to this tutorial are:
Iain McNally
18-11-2018