Home > Community > Blogs > Digital Implementation > capturing and processing encounter console output with quot redirect quot
 
Login with a Cadence account.
Not a member yet?
Create a permanent login account to make interactions with Cadence more convenient.

Register | Membership benefits
Get email delivery of the Digital Implementation blog (individual posts).
 

Email

* Required Fields

Recipients email * (separate multiple addresses with commas)

Your name *

Your email *

Message *

Contact Us

* Required Fields
First Name *

Last Name *

Email *

Company / Institution *

Comments: *

Capturing and Processing Encounter Console Output with "redirect"

Comments(2)Filed under: dbGet, encounter, Encounter Digital Implementation, TCL, EDI, Dwyer, Console output, redirect, write nets to file

In my last post I wrote about writing more compact db access scripts with dbGet's expression-based matching. We found all of the high fanout nets in the design which weren't clock nets:

dbGet [dbGet top.nets {.numInputTerms > 16 && .isClock == 0}].name

This writes the name of each net to the console. But how would we write those nets to a file? Say, for example, if we wanted to call optDesign -selectedNets on them? optDesign expects a file with a list of net names, one per line. How could we create that file? We could use the redirect command along with some clever scripting. More on that in a moment, but let's talk about redirect first.

The Basics

The redirect command as described here is available starting in release EDI release 11.1 (EDI stands for Encounter Digital Implementation System).

In its simplest form redirect takes the output that's written to the Encounter console and writes it to a file. This is useful when you want to process that output programatically and do something based on what's found in that file.

Take for example the checkPinAssignment command. It writes output like this:

encounter 1> checkPinAssignment

Start Checking pins of top cell: [top]
**WARN: (ENCPTN-562):   Pin [in] is [PLACED] at location (   0.330,   50.120 4 ) is NOT ON THE DESIGN BOUNDARY.
Summary report for top level: [top]
        Total Pads                         : 0
        Total Pins                         : 3
        Legally Assigned Pins              : 2
        Illegally Assigned Pins            : 0
        Unplaced Pins                      : 0
        Constant/Spl Net Pins              : 0
        Internal Pins                      : 1
        Legally Assigned Feedthrough Pins  : 0
        Illegally Assigned Feedthrough Pins: 0
End of Summary report
End Checking pins of top cell: [top]

The command doesn't return anything (ie, if you "set x checkPinAssignment", "x" wouldn't have a value) so if we want to query whether checkPinAssignment found any violations -or- check which specific pins were in violation we could do it by redirecting to a file and parsing the output. It's not necessarily pretty but sometimes you've got to do it. Here's how it works:

encounter 1> redirect checkPinAssignment.out checkPinAssignment
**Info: stdout is directed to file 'checkPinAssignment.out'...

Now, you could iterate through each line in checkPinAssignment.out and regexp for "WARN", find a pin name and operate on it in some way.

If the command you want to execute contains options, embed the options in curly brackets:

encounter 1> redirect queryPlaceDensity.out {queryPlaceDensity -userSpecified}
**Info: stdout is directed to file 'queryPlaceDensity.out'...

Intermediate 

We've talked before about writing to and reading from a file. I've got a couple more tips that extend on that idea and make things more compact.

First, check out the dbForEachFileLine command. It essentially does the same thing as:

set infile [open checkPinAssignment.out "r"]
while {[gets $infile line] >= 0} {
  if {[regexp WARN $line]} {
    Puts "$line"
  }
}
close $infile

If you're like me and have trouble remembering the infile/open/while/gets/close business try dbForEachFileLine instead:

dbForEachFileLine checkPinAssignment.out line {
  if {[regexp WARN $line]} {
    Puts "$line"
  }
}

But we can get even fancier with this approach, and avoid writing to a file altogether with redirect's -variable option:

redirect x checkPinAssignment -variable
set lines [split $x \n]
foreach line $lines {
  if {[regexp WARN $line]} {
    Puts "$line"
  }
}

Extra Credit

Back to the original puzzler I mentioned previously. How could we write to a file, one net per line, all of the nets with fanout greater than "n" so we could pass it to a command like "optDesign -selectNets <fileName>"? It's a little tricky, and probably exceedingly compound to be honest, but there is a way:

encounter 18> redirect high_fanout.nets {puts "[join [split [dbGet [dbGet top.nets {.numInputTerms > 16 && .isClock == 0}].name]] \n]"}   
**Info: stdout is directed to file 'high_fanout.nets'...

encounter 19> more high_fanout.nets
scan_enI
DTMF_INST/TDSP_CORE_INST/MPY_32_INST/n_7295
DTMF_INST/TDSP_CORE_INST/MPY_32_INST/n_6735
{DTMF_INST/TDSP_CORE_INST/MPY_32_INST/ab_a[15]}
{DTMF_INST/TDSP_CORE_INST/MPY_32_INST/ab_b[15]}

Pretty cool!

Here's the full usage for the redirect command:

encounter 1> help redirect

Usage: redirect [-help] [<file_or_var_name>] [<command>] [-tee] [-stdin | -append | -variable ] [-stderr | -stdin ]

-help                        # Prints out the command usage
<file_or_var_name>           # file name or variable name, for outputs to go
                             # (string, optional)
<command>                    # command to execute (string, optional)
-append                      # append stdout/stderr to file or variable
                             # (bool, optional)
-stderr                      # redirect stderr also (bool, optional)
-stdin                       # redirect stdin (bool, optional)
-tee                         # redirect output to both screen and file or
                             # variable (bool, optional)
-variable                    # redirect to a Tcl variable (bool, optional)

I hope there's a useful nugget or two in here.

Question of the Day: Any tips or tricks you'd like to share about reading from/writing to a file, capturing output as a variable, or redirecting it to a file? 

-Bob Dwyer

Comments(2)

By Harish on December 10, 2012
Bob, This is interesting indeed. However, I need to make the redirect work in a tcl script. I am not able to do so. Doing a "redirect fileName [ecoChangeCell -evaluateOnly -inst instName -upsize] works on encounter command prompt. But it does not work if I put the same in tcl script. Any suggestions?.  Regards, Harish.

By BobD on December 18, 2012
Hi Harish, As you've likely discovered by now (sorry for the delay) the command should be embedded within squiggly brackets rather than square: "redirect fileName {ecoChangeCell -evaluateOnly -inst instName -upsize}". Let me see if there's something we can do to improve the error messaging in Encounter on this - it may be a straight TCL thing, or maybe not.

Leave a Comment


Name
E-mail (will not be published)
Comment
 I have read and agree to the Terms of use and Community Guidelines.
Community Guidelines
The Cadence Design Communities support Cadence users and technologists interacting to exchange ideas, news, technical information, and best practices to solve problems and get the most from Cadence technology. The community is open to everyone, and to provide the most value, we require participants to follow our Community Guidelines that facilitate a quality exchange of ideas and information. By accessing, contributing, using or downloading any materials from the site, you agree to be bound by the full Community Guidelines.