You are on page 1of 73

Basic Tcl Training

Based on Verdi/Siloti 2011.07 Allen Shieh

SpringSoft Notifications
Copyright
2011 SpringSoft, Inc. All rights reserved. No part of this training may be reproduced in any form or by any means without written permission of SpringSoft, Inc.

Trademarks
The product names used in this document are the trademarks or registered trademarks of their respective owners.

Confidentiality
The information in this document is confidential and is covered by a license agreement between SpringSoft and your organization. Distribution and disclosure are restricted.

Overview
Tcl Introduction Basic Tcl Syntax
Lab 1

Basic Tcl Data Types


Lab 2

Control Tcl Programs


Lab 3

Use Tcl in Verdi Case Study 1 Case Study 2 Lab 4 Resource

Tcl Introduction
Basic Introduction What is Tcl?
Tcl stands for Tool Command Language A String basis scripting language Use source your_script.tcl to execute your Tcl script under tclsh

What is Tk?
Tk is an associated toolkit to create window-based interactive applications using Tcl

Tcl Introduction
What Can You Do in Verdi with Tcl? Use Tcl to combine Verdi commands to make your own feature to improve efficiency Add your new feature, which was created by Tcl scripts, to the Verdi menu command or bind-key Use NPI (Novas Programming Interface) to traverse the design without Verdi GUI

Tcl Introduction
Possible Applications in Verdi with Tcl Application of FSDB
Calculate FSDB results. For example, duty cycles Search and sort FSDB results. For example, search for small pulses

Interoperability with 3rd party tools


Read 3rd party tool reports and translate into Verdis format

Application of KDB
Access to Verdi database to do calculations and queries. For example, extract snake path from the design

Tcl Introduction
Tcl Command Sets in Verdi
Verdi provides Tcl commands for each action in the GUI. All Tcl commands are categorized by module and have a set prefix. Prefix sys deb src wv sch tfg nMem fsm reg eco ta sid lx Module System Debussy (Verdi) nTrace nWave nSchema Temporal Flow View Memory/MDA nState nRegister nECO Transaction Siloti ListX

Tcl Introduction
Execute Tcl in Prompt Tcl is a Unix shell language, and it can be executed under /usr/local/bin/tclsh
Add #!/usr/local/bin/tclsh in the first line of your Tcl script Execute your Tcl script in the prompt Example: hello.tcl

In terminal

#!/usr/bin/tclsh puts Hello!!

>chmod +x hello.tcl

>hello.tcl Hello!!

Basic Tcl Syntax


Basic Syntax Tcl is a combination of commands enter and semicolon (;) needs to be used to separate different commands If the next line is an extension of previous line, a backslash (\) needs to be added in the end of the line If a line begins with #, the line will be treated as a comment; Tcl will ignore this line Use spaces to separate arguments in a command
The first word in a command line is the command, following are arguments The command line will return string

Basic Tcl Syntax


Some Examples Some examples for basic syntax:
set a 22 set value of variable to 22

It is not necessary to declare a in advance, the variable in Tcl will be declared automatically after you assign a value to it.

unset a to erase variable a set x 4; set y Hello use semicolon (;) to separate two commands set text This line is \ use backslash to connect to next line split into two lines
NOTE: space cannot be added after the backslash (this is a common error)

#This line is comment create a comment; Tcl will not execute this line

Basic Tcl Syntax


Use Variables Syntax: $varName or ${varName}
Use dollar sign $ to get the variable value Use curly brackets { } to separate the variable and following words The variable can be formed by letter, number, and underscore Examples:

set set set set set set

b a a a a w

66 b $b $b+$b+$b $b.3 ${a}fix

66 b 66 66+66+66 66.3 66.3fix $b

To keep the dollar sign $, add the backslash \ in front of $

set a \$b

NOTE: Use info exist a to check whether variable a exists. If it exists, then 1 will be returned; otherwise, 0 will be returned.

Basic Tcl Syntax


Square Brackets [ ] Syntax: [script]
Will execute the command inside the square bracket [ ], and return the value Examples:

set b 8 set a [expr $b+2] set a b+2 = [expr $b+2]

8 10 b+2 = 10

To keep the square bracket [ ], add the backslash \ in front of [ ]

set a \[expr\]

[expr]

Basic Tcl Syntax


Curly Brace { } Syntax: {script}
The use of curly brace { } is similar to the double quotation mark ; the purpose is for grouping. However, the curly brace { } will ignore all replacements and calculations, all items inside the curly brace will be treated as a string. Example:

set set set set set

b a a a w

8 {[expr $b+2]} [expr $b+2] b+2 = [expr $b+2] ${b}fix

8 [expr $b+2] 10 b+2 = 10 8fix

NOTE: A common error is that a space is not inserted between } and {.

For example if { $x<1 }{ puts X=$x} will cause a syntax error

Basic Tcl Syntax


Double Quotation Marks " Tcl will add the double quotation mark automatically when analyzing arguments
C: Tcl: x = 4; y = x+10 set x 4; set y x+10 y 14 y x+10

The double quotation mark can avoid the effect of the semicolon ; (will be treated as a string), but all replacements and calculations will be executed
set a x is $x; y is $y x is 4; y is x+10

When the curly brace { } is inside the double quotation mark , the item inside the curly bracket will be calculated
Originally the items inside the curly brace { } will not be replaced and calculated Example:

set set

x CurlyBraces a x is {$x}

x is {CurlyBraces}

Basic Tcl Syntax


expr Syntax: expr function
The expr will replace and calculate all expressions in the function and return the result Example:

set b 5; set a 8 expr ($b*4) 3 expr $a * cos(2*$b)

5 8 17 -6.71257

Error prone examples:


expr 122/10 expr 122.0/10.0 expr (122*1.0)/10.0

12 (an integer divided by an integer) 12.2 12.2

expr will adjust the data type automatically based on the value in the expression

The value after the decimal point will be rounded down if you use integers in an expression

Basic Tcl Syntax


expr The built-in variable tcl_precision can be set to control the precision of the calculation result by expr
Examples:

expr 1/3 expr 1.0/3.0 set tcl_precision 10 expr 1.0/3.0 set tcl_precision 3 expr 1.0/3.0

0 0.333333 10 0.3333333333 3 0.333

NOTE: The value for tcl_precision means the total digit number (not including the decimal point and the first zero). For example, 333.333 is 6, 0.333 is 3.

Basic Tcl Syntax


incr Syntax: incr variable increment
The incr is equivalent to command: set variable [expr $variable + increment] If increment is not specified, the default value is 1. Examples:

set a 3 incr a incr a 6 incr a -2

3 4 10 8

Basic Tcl Syntax


Radix The value of integers are all in base-10 number system (decimal)
If the first digit is 0, then it becomes base-8 number system (octal) If the first digit is 0x, then it becomes base-16 number system (hexadecimal) Examples:

expr 243 expr 0363 expr 0xF3

243 243 243

A real number can also be presented in following ways:


5.5 3.7e+6 6E4 3.

Basic Tcl Syntax


Basic Execution Unit: Procedure Syntax:
proc Name {argument1 argument2 } { TCL command body } The return value will be the result of the last command in this procedure If use return command then you can return your expected result Example:
proc sum { A B } { set r [ expr $A+$B ] return $r }

Execute above procedure, and invoke from following command:

set result [sum 1 2]

The return value will be 3

NOTE: A procedure cannot be included by another procedure.

Lab 1
Practice with Basic Syntax
1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13.

set a 10 set b 22; set c 8 set a echo $a puts $a puts $a $b $c puts {$a $b $c} puts {$a $b $c} expr $a+$b+c set d [expr $a+$b+$c] set e $a+$b+$c set aa $d set bb \$d

10 (Create variable a and assign value 10) 8 (Use ; to write two commands in a line) 10 (Get the value of variable a) 10 (To invoke variable a) 10 (Print out variable a to terminal) 10 22 8 (Print out variable a, b, c to terminal) $a $b $c (Notice the usage of { and }) {10 22 8} ({ } will take no effect inside ) 40 (Use expr command to do calculation) 40 (Save the expression result to $d) 10+22+8 (Will not be calculated without expr) 40 (Assign the value of $d to variable aa) $d (\ to reserve special character)

Lab 1
Practice with Basic Syntax
14. 15. 16. 17. 18. 19. 20.

expr 10/3 3 (Result will be interger) expr 10.0/3 3.333333333333 (Result will be floating number, since 10.0 is floating number ) set tcl_precision 8 8 (Set precision to 8, default is 12) expr 10.0/3 3.3333333 (The valid digit number is 8, not including the decimal point ) expr 1.0/3 0.33333333 (The valid digit number is 8, not including the decimal point and the first integer zero) set k 0; incr k 1 (Equal to set k [expr $k+1], notice that the variable for incr does not need $) incr k 4 5 (Equal to set k [expr $k+4] )

Basic Tcl Data Types


Working with Lists What is a List?
A collection of words enclosed within curly braces and separated by whitespace characters (one or more blanks), tabs, or newline characters

NOTE: The double quotation mark can also be used to define a List, but the replacement and calculations will be executed inside the double quotation marks. set month {January February March April} set color red green blue

Example:

The curly brace can be used to group items in the List, for example:

a b {c d e} f {a b} { b {c d } } e {f g} H a b { c d e } f g {h I }

(4 words) (5 words) (6 words)

NOTE: The index in a List is starts from 0.

Basic Tcl Data Types


Working with Lists Frequently Used Commands list: Create a list
Syntax: list argument1 argument2 Example:

list a b {c d e} {f {g h}} a b {c d e} {f {g h}} set a [list a b c] a b c

lindex: Retrieve an element from a list


Syntax: lindex list index Example:

lindex

a b c 0

lrange: Return one or more adjacent elements from a list


Syntax: lrange list first last Example:

lrange a b c d 2 end set list {t p t s 1} set y [lrange $list 1 2]

c d p t

Basic Tcl Data Types


Working with Lists Frequently Used Commands lappend: Append list elements onto a variable
Syntax: lappend varName value1 value2 Example:

set CellList INV lappend CellList AND2 NOR2 lappend CellList AND2 NOR2

INV INV AND2 NOR2 INV {AND2 NOR2}

linsert: Insert elements into a list


Syntax: linsert list index element1 element2 ... Example:

linsert a d 1 b c linsert a d 1 b c

a b c d a {b c} d

Basic Tcl Data Types


Working with Lists Frequently Used Commands lsort: Sort the elements of a list
Syntax: lsort options list options: -ascii -dictionary -integer -real -command -increasing -decreasing -indices -index -stride -nocase -unique

Refer to Tcl Manual for detailed usage of above options Sorting a list using ASCII sorting: lsort {a10 B2 b1 a1 a2}

Examples:

B2 a1 a10 a2 b1

Sorting a list using Dictionary sorting: lsort -dictionary {a10 B2 b1 a1 a2} a1 a2 a10 b1 B2 Stripping duplicate values using sorting: lsort -unique {a b c a b c a b c}

a b c

Sorting with index list: lsort -integer -index 1 \ {{First 24} {Second 18} {Third 30}} {Second 18} {First 24} {Third 30}

Basic Tcl Data Types


Working with Lists Frequently Used Commands lreplace: Replace elements in a list with new elements
Syntax: lreplace list first last element1 element2 ... Example:

lreplace {a b c d} 1 2 Z Y X lreplace {a b c d} 1 2

a Z Y X d a d

llength: Count the number of elements in a list


Syntax: llength list Example:

llength {a b c d}

lsearch: See if a list contains a particular element, and return the index number. Returns -1 if no matching element.
Syntax: lsearch options list pattern

Refer to Tcl Manual for detailed usage of options lsearch exact {a b c d} c 2

Example:

Basic Tcl Data Types


Working with Lists Frequently Used Commands split: Split a list into a proper Tcl list
Syntax: split string splitChars Example:

set y /u/home/tcl/lists.tcl split $y / {} u home tcl lists.tcl split abcdef a b c d e f

join: Create a string by joining together list elements


Syntax: join list joinString Example:

set x {5 12 7} expr [join $x +]

24

( expr 5+12+7 )

concate: Join lists together (will expand one level)


Syntax: concate argument1 arguments Example:

concat {a b c} {d e} f {g h} { {i j} k} a b c d e f g h {i j} k

Basic Tcl Data Types


Working with Arrays Tcl supports associative arrays (also known as "hash tables") in which the index value is a string
The array is a better choice than the list when representing some complex data structures

The syntax of setting arrays:


set arrName(index) value set arrName(i,j) value NOTE: The index can be an integer or string.

Example to set an array:


set name(first) Allen Allen set name(last) Rita Rita puts "Full name: $name(first) $name(last) Full name: Allen Rita

Basic Tcl Data Types


Working with Arrays Commands to Manipulate Arrays array: Manipulate array variables
Syntax: array option arrayName arg1 arg2 ... Frequently used options:

array exists arrayName: Returns 1 if arrayName is an array variable, 0 if there is no variable by that name or if it is a scalar variable array get arrayName pattern: Get the index which matches the specified pattern and return index value array get name fi* first Allen array get name last Rita first Allen array set arrayName list: Convert list to array. list must have a form like that returned by array get, consisting of an even number of elements array set colorcount {red 1 green 5 blue 4 white 9} array get colorcount blue 4 white 9 green 5 red 1 array size arrayName: Returns a decimal string giving the number of elements in the array. If arrayName is not the name of an array then 0 is returned array size colorcount 4

Basic Tcl Data Types


Working with Strings string Command String is a basic data type in Tcl
Frequently used commands for manipulating strings are: string, append, format, and scan.

string: Manipulate strings


Syntax: string option arg1 arg2 ... To set a string:

set string_verdi Verdi Tcl

Verdi Tcl

To calculate the length of a string:

string length $string_verdi 9

To convert the string to upper case or lower case (upper: toupper; lower: tolower)

string toupper $string_verdi VERDI TCL

To compare whether two strings are the same:


string equal $string_verdi $string_verdi 1 string equal abc def 0

Basic Tcl Data Types


Working with Strings string Command Note for string comparison:
If you want to compare strings, use string equal or string compare instead of using ==. For example:
if {[string compare $s1 $s2] == 0} { # s1 and s2 are equal } if {[string equal $s1 $s2]} { # s1 and s2 are equal }

Do not use == to compare strings. In example below, although the two strings have different content, they will be treated the same with ==. Tcl will convert the string to numbers first, so that the hexadecimal (base-16) 0xa will be converted to decimal 10 this is not our expectation for comparing strings
if { 0xa == 10} { puts Correct }

Basic Tcl Data Types


Working with Strings string Command More options for string command:
To trim the leading and trailing characters (if no character is specified, white space will be removed):

set v_string "Verdi is Verdi string trim $v_string Verdi

Verdi is Verdi is

Trim the leading characters:

string trimleft $v_string Verdi

is Verdi

Trim the trailing characters:

string trimright $v_string Verdi

Verdi is

Return a range of a string:

string range $v_string 0 6

Verdi i

Judge the type of string content:


string is integer $v_string string is ascii $v_string Refer to Tcl manual for more types

0 1

Basic Tcl Data Types


Working with Strings String Match (1/2) Syntax: string match -nocase pattern string
See if pattern matches string; return 1 if it does, 0 if it does not

set str ControlInformation string match Control* $str

To describe a pattern:
* : Matches any sequence of characters in string, including a null string

string match tcl* tcltk string match tcl* allen

1 0

?: Matches any single character in string


string match all?? allen string match all? allenshieh

1 0

Basic Tcl Data Types


Working with Strings String Match (2/2)
[chars]: Matches any character in the set given by chars. [abc] matches any single character in abc; [a-z] matches any single character in lowercase; [a-e] matches any of a, b, c, d, and e.

string match {[a-z]} allen 0 string match {[a-z][a-z][a-z][a-z][a-z]} allen 1

\x: Matches the single character x. This provides a way of avoiding the special interpretation of the characters * ? [ ] \ in pattern.

set a a?bc; string match {[a-c][a-c][a-c][a-c]} $a string match {[a-c][\?][a-c][a-c]} $a

0 1

Basic Tcl Data Types


Working with Strings format Command format: Format a string in the style of sprintf
Syntax: format formatString arg1 arg2 ... Example:

set pi [expr 2*asin(1.0)] 3.14159265359 puts [format Value: %s = %07.3f PI $pi] Value: PI = 003.142 %s : No conversion; just insert string %07.3f : Convert number to signed decimal string of the form xx.yyy, where 7 means the digit of floating decimal number (the floating point is also one digit), 3 means the precision after floating point, 0 means to fill 0 for the blank.

Basic Tcl Data Types


Working with Strings scan Command scan: Parse string using conversion specifiers in the style of scanf
Syntax: scan string format varName1 varName2 ...

The scan command will search the string based on the defined format, and then save the matched string to variables sequentially set str AreaUsagePattern = scan $str %s %s %s key eq set Key set eq set value T3T57 value AreaUsagePattern = T3T57

Example:

Lab 2
Practice for basic data types
1. 2. 3. 4. 5. 6. 7. 8. 9. 10.

11. 12. 13. 14.

set traffic1 red green yellow red green yellow set traffic2 [list red green yellow] red green yellow set traffic3 red {green1 green2} yellow red {green1 green2} yellow lindex $traffic1 0 red (Notice the index starts from 0) lindex $traffic1 1 green lindex $traffic1 end yellow (Get the last item) lindex $traffic3 1 green1 green2 lappend traffic1 blue red green yellow blue (Append blue into list traffic1, notice here the traffic1 does not need $) lrange $traffic1 1 2 green yellow (Get 1~2 range) linsert $traffic1 2 pink white red green {pink white} yellow blue (Notice that linsert will not put the value to $traffic1, so the traffic1 will still be red green yellow blue) lsort ascii decreasing $traffic1 yellow red green blue lsearch regexp $traffic1 .*ee.+ 1 (Find green and return the index 1) set str happy; split $str h a p p y (Separate words) set str h a p p y; join $str happy (Combine words)

Control Tcl Programs


if Command (1/3) if: Execute scripts conditionally
Syntax: if condition then body1 else body2

Where the value of condition must be a Boolean expression If the condition is true then execute body1, if the condition is false then execute boody2

Example:
set A 10 set B 5 if {$A >= $B } { puts A >= B } else { puts A < B }

A >= B

Control Tcl Programs


if Command (2/3) Note the location of the Curly Brace { }
wrong If { . } { .. } Correct If { . } { .. } wrong If { .. } { . } else { ..} Correct If { .. } { . } else { .. }

Control Tcl Programs


if Command (3/3) if else nested styles:
An example for ifelseif nested style An example for ifelse nested style

if { } { } elseif { } { } elseif { } { } else { }

if { } { if { } } else } } else { if { } } else } }

{ {

{ {

Control Tcl Programs


while Command while: Execute script repeatedly as long as a condition is met
Syntax: while test body

Where test is a Boolean expression Body is the program to be executed when test is true

Example:

a
0 1 2 3 4 5 6 7 8 9 10

sum
0 0 1 3 6 10 15 21 28 36 45

new sum
0 1 3 6 10 15 21 28 36 45 55

## calculate the sum from 0~10 set a 0 set sum 0 while {$a <= 10} { set sum [expr $a+$sum] set a [expr $a + 1] } puts Total = $sum

Control Tcl Programs


for Command for: 'For' loop
Syntax: for start test next body The flow:
1. 2. 3. 4. 5.

Execute start Repeatedly evaluates test If the result of test is non-zero it invokes body Invokes the Tcl interpreter on next Back to step 2 to repeat the loop

Example:
## calculate the sum from 0~10 for {set a 0; set sum 0} {$a <= 10} {incr a} { set sum [expr $sum + $a] } puts Total = $sum

Control Tcl Programs


foreach Command foreach: Iterate over all elements in one or more lists
Syntax: foreach varname list body

List: a Tcl list Body: the Tcl script The flow: For each element of list (in order from first to last), foreach assigns the contents of the element to varname, then executes body.

Example: set sum 0 set numList [list 1 2 3 4 5 6 7 8 9 10] foreach a $numList { set sum [expr $sum+ $a] } puts Total = $sum

Control Tcl Programs


switch Command switch: Evaluate one of several scripts, depending on a given value
Syntax: switch options string {pattern1 body1 pattern2 body2 ...} Options: -exact, -glob, -regexp, -nocase, -matchvar, -indexvar, -

-exact : use exact matching, this is default -regexp : use regular expression matching -- : Marks the end of options. The argument following this one will be treated as string even if it starts with a Refer to the Tcl manual for detailed usage

NOTE: The comment in switch command is only allowed in body; otherwise, it may cause problems in Tcl parser.

Control Tcl Programs


switch Command switch example:
proc aa {value} { set b 0 switch -regexp -- $value { Verdi {set b caseA } {[0-9]+} {set b caseB } {^(c|d)} {set b caseC } default {set b caseD }} return $b } tcl>aa Verdi caseA tcl>aa 1 caseB tcl>aa c caseC tcl>aa abc caseD

Control Tcl Programs


Execute External Programs Tcl can use exec command to invoke external programs
The external program result, which directs to the standard output, will be returned The exec command supports output redirect < and > and pipeline | Example:

set date [exec date] set n [exec sort < /etc/passwd | uniq ]

If the external program gets error when executing, it will cause the exec command to get the unexpected value. To avoid this, you can use catch command to filter the error message:

catch {exec program arg1 arg2 } result NOTE: Use curly brace { } after catch command, this is because catch will invoke Tcl interpreter. The command will be executed before activate catch if you use the square bracket [ ]

Control Tcl Programs


Preventing Errors catch Command catch: Evaluate script and trap exceptional returns
Syntax: catch script resultVarName If the script raises an error:

catch returns a non-zero integer value and saves the error to resultVarName catch returns zero value and saves the return value to resultVarName proc cat {} { set fildid "" if { [catch { open ./abc.tcl r } fileid ] } { puts "opening file error: $fileid" } else { while { [ gets $fileid line ] } { puts $line } close $fileid } }

If the script does not have an error:

Example:

Manipulate Files
Commands for File Processing Frequently used commands for file processing:
open fileName access: Open a file-based or command pipeline channel puts channelId string: Write to a channel gets channelId varName: Read a line from a channel read channelId numChars: Read from a channel Close channelId r|w: Close an open channel

Example:
set filename input.data set input [open $filename r ] while { [gets $input read_line] >= 0 } { puts read_line=$read_line } close $input

Manipulate Files
File Processing open A better coding style for opening a file:
if { {catch { open data r } fileId } { puts cannot Open data : $fileId } else { ; close $fileId }

Access for open command:


r: Open a file for reading; the file must already exist r+: Open a file for reading and writing; the file must already exist w: Open a file for writing, create it if it doesnt exist w+: Open a file for reading and writing, create it if it doesnt exist a: Open a existing file for writing, new data is appended a+: Open a existing file for reading and writing, new data is appended

NOTE: Remember to close the file, otherwise the data may lost.

Manipulate Files
File Processing file file: Manipulate file names and attributes
Syntax: file option name arg1 arg2 ... Frequently used options:

file dirname name: Return the directory name of name file file executable name: Returns 1 if file name is executable, 0 otherwise. file exists name: Returns 1 if file name exists, 0 otherwise. file extension name: Returns the extension name of file name. file isdirectory name: Returns 1 if file name is a directory, 0 otherwise file size name: Returns the file size of file name. file mkdir name : Generate a directory name. file join path name: Concatenate path and name file rootname name: Returns name but filters the last component after .. file tail name: Returns name after the last directory separator.

Example:
file join work/verdi a.tcl file rootname /work/verdi/a.gds file tail /work/verdi/a.tcl work/verdi/a.tcl /work/verdi/a a.tcl

Lab 3
Write a simple Tcl script Refer to following while script for calculating (1+2+3++9+10), try to use for loop to write a script for calculating (1+3+5++9):
set a 0; set sum 0 while {$a <=10} { incr sum $a; incr a }; puts $sum

Use Tcl in Verdi


Execute Tcl in GUI In the Command Entry form:
When you execute any GUI command, the associated Tcl command will be logged in the Command Entry form Directly typing the Tcl command in the Command Entry form will execute the Tcl command Type source your_script.tcl in the Command Entry form to execute the Tcl script

Use Tcl in Verdi


Execute Tcl in GUI Open the Command Entry form:
Invoke the Preferences form from Tools Preferences

Go to General folder, enable the Enable TCL Command Entry Form option, the Command Entry form will be opened. The setting will be saved into novas.rc, and the Command Entry form will be opened automatically next time you invoke Verdi

Use Tcl in Verdi


Execute Tcl in Command Line Execute the Tcl script in Verdi command line:
% Verdi play your_script.tcl & All associated Tcl commands will be saved in ./VerdiLog/Verdi.cmd

Use replay to execute the Verdi.cmd file can reproduce previous steps

Automatically source the Tcl script


By setting NOVAS_AUTO_SOURCE environment variable:

% setenv NOVAS_AUTO_SOURCE your_script.tcl % verdi & Search for TclAutoSource tag in [General] section in the novas.rc file Specify your Tcl script for the TclAutoSource tag, for example: [General] TclAutoSource = MyTclScript.tcl

By modifying the novas.rc resource file:


Use Tcl in Verdi


Register Event Callbacks Register a Tk name for Verdi with tkname
% Verdi -tkName <Tk name>

Add an event callback with triggered reason


Syntax: AddEventCallback TkAppName CallbackFun Reason async

Check all available Reason in Introduction Tk Command Client Adding Event Callbacks to Your Tk Application section of the Novas Command Language document (tcl.pdf in <Novas_install>/doc directory)

NOTE: you can also register a callback with a triggered reason after invoking Verdi, for example:
AddEventCallback [tk appname] AutoLoadSignal wvCreateWindow 1 To execute the Tcl procedure AutoLoadSignal when a nWave window is created tk appname: returns the name of the application, the application name will be Verdi if you source the Tcl script after invoking Verdi

Use Tcl in Verdi


Register Event Callbacks Example (demo.tcl)
Add this line to declare this is Tcl script #!wish -f proc myFunc args { puts "Received CursorTime Change Event" puts "Parameters:" foreach i $args { The script body which you want to execute in Verdi puts $i } } exec Verdi -tkName abc & Invoke Verdi and give a Tk name while {1} { set s [winfo interps] if {-1 != [string first abc $s]} { break; To confirm the Tk application is } invoked before executing the next line after 500 } send abc {AddEventCallback demo.tcl myFunc wvCursorTimeChange 1} Register the callback: trigger myFunc when change cursor time in nWave

Case Study - 1
Requirement Users have a signal list file which was generated from another EDA tool; they want a direct way to load all signals into nWave from the file without selecting each one in Get Signals form. Script introduction
file.list: the signal list generated from other EDA tool load_menu.tcl: create banner menu load.menu: define the banner menu load_signal.tcl: the main body of the script

Case Study - 1
The Script
To execute the script: verdi play load_menu.tcl & Input file: file.list
/system/addr[7:0] /system/clock

load_menu.tcl
fmAppendBannerMenu -win window_id -file load.menu

load.menu
Menu Load { "Load Signals From File" _L f.tcl dummy "source load_signal2.tcl" }

Case Study - 1
The Script
To execute the script: verdi play load_menu.tcl & Input file: file.list
/system/addr[7:0] /system/clock

load_menu.tcl
fmAppendBannerMenu -win window_id -file load.menu Append a banner load.menu menu item Menu Load Could be $_nTrace1 or any string. The file which defines If meaningless string is specified, the the banner menu { menu will apply to all existing windows "Load Signals From File" _L f.tcl dummy "source load_signal2.tcl" }

Case Study - 1
The Script
To execute the script: verdi play load_menu.tcl & Input file: file.list
/system/addr[7:0] /system/clock Give the name for load_menu.tcl The bind-key for the command, the banner menu fmAppendBannerMenu -win window_id -file load.menu TCL file name, needs to be one of the could be any string command name characters

load.menu

Menu Load { "Load Signals From File" _L f.tcl dummy "source load_signal.tcl" } Execute the tcl script when f.tcl : execute a tcl script The command name invoking the banner menu f.exec: execute a Verdi command under the banner menu

Case Study - 1
The Script load_signal.tcl
proc load_signal {} { global file_str set w .load toplevel $w wm title $w "Load Signals From File" label $w.msg -justify left -text "Please specify file name" pack $w.msg -side top frame $w.file pack $w.file -side top -fill x -pady 1 entry $w.file.file -relief sunken -textvar file_str label $w.file.file_label -text "file name" pack $w.file.file_label -side left pack $w.file.file -side left button $w.file.load -text Load -command "load" button $w.file.dismiss -text Dismiss -command "destroy $w" pack $w.file.load $w.file.dismiss -side left }

Case Study - 1
The Script load_signal.tcl
proc load_signal {} { global file_str set w .load toplevel $w wm title $w "Load Signals From File" label $w.msg -justify left -text "Please specify file name" Set a global variable file_str. pack $w.msg topin another procedure the variable can-side be used frame $w.file pack $w.file -side top -fill x -pady 1 Create .load as the top window. entry $w.file.file -relief sunken -textvar file_str Note: a window name must start with .. label $w.file.file_label -text "file name" pack $w.file.file_label -side left Specify the title for the .load window The syntax: wm title window pack $w.file.file -side left string button $w.file.load -text Load -command "load" button $w.file.dismiss -text Dismiss -command "destroy $w" pack $w.file.load $w.file.dismiss -side left }

Case Study - 1
The Script load_signal.tcl
proc load_signal {} { global file_str set w .load toplevel $w wm title $w "Load Signals From File" label $w.msg -justify left -text "Please specify file name" pack $w.msg -side top
label: Create and manipulate the label widget. frame $w.file -justify : When multiple lines of text displays in a widget, this option determines pack -side topeach -fill x -pady 1 be one of left, center, or right. how the $w.file lines line up with other. Must entry $w.file.file -relief sunken -textvar -text : Specifies a string to be displayed insidefile_str the widget.

label $w.file.file_label -text "file name" pack : The pack command -side is used to communicate with the packer, a geometry pack $w.file.file_label left manager that arranges theleft children of a parent by packing them in order around pack $w.file.file -side the edges of the parent button $w.file.load -text Load -command "load" -side: Specifies which side of the master the slave(s) will be packed against. button $w.file.dismiss Dismiss -command Must be left , right, top, or -text bottom . Defaults to top. "destroy $w" pack $w.file.load $w.file.dismiss -side left }

Case Study - 1
The Script load_signal.tcl
procCreate load_signal {} { widget .w.file a frame global file_str set w .load toplevel $w -fill x: If the slave's parcel is larger than its requested dimensions, this option may wm title $w "Load Signals From File" be used to stretch the slave. The argument x will stretch the slave horizontally to fill the entire width of its parcel. label $w.msg -justify left -text "Please specify file name" -pady amount: Amount specifies how much vertical internal padding to leave on pack $w.msg -side top each side of the slave. Amount defaults to 0. frame $w.file pack $w.file -side top -fill x -pady 1 entry $w.file.file -relief sunken -textvar file_str label $w.file.file_label -text "file name" pack $w.file.file_label -side left pack $w.file.file -side left Create a entry widget .w.file.file and pack the widget to its parent (.w.file). $w.file.load -textfor Load "load" values are raised, -relief:button creates the 3-D effect the-command widget. Acceptable button $w.file.dismiss -text ,Dismiss -command "destroy $w" sunken , flat, ridge, solid and groove pack $w.file.load $w.file.dismiss -side left -textvar : specify the variable for the input text. File_str is a global variable. }

Case Study - 1
The Script load_signal.tcl
proc load_signal {} { global file_str set w .load toplevel $w wm title $w "Load Signals From File" Create a button widget .w.file.load label -justify leftto -text specify -text:$w.msg Specifies a string be "Please displayed insidefile thename" widget pack $w.msg -side top a Tcl command to associate with the button -command : Specifies frame $w.file Create a button widget .w.file.dismiss and associate with Tcl command pack $w.file top the -fill x -pady 1 destroy $w-side to close window. entry $w.file.file -relief sunken -textvar file_str label $w.file.file_label -text "file name" Pack $w.file.file_label two buttons into -side the frame pack left and specify the position pack $w.file.file -side left button $w.file.load -text Load -command "load" button $w.file.dismiss -text Dismiss -command "destroy $w" pack $w.file.load $w.file.dismiss -side left }

Case Study - 1
The Script load_signal.tcl
proc load {} { global file_str set file_id [open $file_str r] while {[gets $file_id sig_line] >= 0} { wvAddSignal "$sig_line" } } load_signal The load procedure will be invoked when clicking Load button in load_signal procedure Declare file_str as a global variable, the value is inherited from the entry .w.file.file in the load_signal procedure Open the file with read access, get each line in the file and add signal into nWave To invoke the load_signal procedure

Case Study - 1
How does it works? verdi f run.f ssf rtl.fsdb play load_menu.tcl &

1. Invoke the command

2. Fill in the file name, click Load

3. Signals in the list will be loaded

Case Study - 2
Readme File
[Function Abstract] This scripts generates an nWave session file before exiting and loads last session when nWave is invoked. When select Save and Close Win under File menu on nWave , it generates nWave session file named "<FSDBName>.rc" and "AutoSaveSignal.rc" automatically. If there is a file named "AutoSaveSignal.rc" when invoking nWave, it is loaded automatically. [Usage] % setenv NOVAS_AUTO_SOURCE AutoSave.tcl % verdi ... [Input File] [Output File] <FSDBNAME>.rc AutoSaveSignal.rc

Case Study - 2
The Script
proc AutoSaveSignal {} { global ary
Inherit $ary from GetFileName procedure

if { [file exists "AutoSaveSignal.rc"] } { file rename -force AutoSaveSignal.rc AutoSaveSignal.rc.bak }


Check whether the save file already exists, rename if it exists

set wid [wvGetCurrentWindow] $fname: get the FSDB name from GetFileName procedure. Note it uses $ary($wid) to get the set fname $ary($wid)
same FSDB name in GetFileName procedure when there are multiple FSDB files

if { $fname != "" } { Save signals to FSDB_name.rc file wvSaveSignal -win $wid "$fname.rc" } Save signals to wvSaveSignal -win $wid "AutoSaveSignal.rc AutoSaveSignal.rc file wvCloseWindow -win $wid }
Close current nWave window

Case Study - 2
The Script
proc AutoLoadSignal {p1 p2} {
Note: here the p1 and p2 argument will be: $P1: wvCreateWindow $P2: 2a97b46aa8 (the window ID)

if { [file exists "AutoSaveSignal.rc"] } { wvRestoreSignal -win $p2 "AutoSaveSignal.rc" }


Restore the AutoSaveSignal.rc file into nWave if the file already exists

eMenuAppendItem -win $p2 -menuName File -itemName "Save and Close Win" -tclCmd "AutoSaveSignal" }
Create a Save and Close Win command under File menu, invoking the command will execute the AutoSaveSignal procedure.

Case Study - 2
The Script
proc GetFileName {p1 p2} { global ary set lname "" set wid [wvGetCurrentWindow] set sid [string last / $p2] set lid [string last . $p2]
Note: here the p1 and p2 argument will be: P1: wvOpenFSDBFile P2: /verdi/home/allen_shieh/demo/rtl.fsdb Get the window ID for current nWave window $sid: get the index for last / in $p2 $lid: get the index for last . in $p2

set lname [string range $p2 [incr sid] [incr lid -1]] # puts "$p1 $p2 $lname" set ary($wid) $lname }
To store the fsdb name in $ary array with $wid index

$lname: get the string for fsdb name without .fsdb

AddEventCallback [tk appname] AutoLoadSignal wvCreateWindow 1 AddEventCallback [tk appname] GetFileName wvOpenFSDBFile 1
Register callbacks to: 1. Execute procedure AutoLoadSignal when opening nWave window 2. Execute procedure GetFileName when loading FSDB

Lab 4
Practice for Writing a Useful Tcl Script Requirement:
When there is any pulse in the signal which is smaller than the specified time range, dump the signal name and the time when the pulse happens.

Hints:
Create an entry for specifying the time range by:

Creating a menu item and question box for entry, or: Using an environment variable, or: Adding parameters in the script Check <Novas_install>/doc/tcl.pdf to find proper commands

Use nWave commands to traverse scopes and find matching signals

Output a report for matching signals

To see how other people write the script:


Download the Script package from web site, check the example under ./Scripts/ReportSmallPulse

Reference
Get Help from Resources
Novas Command Language:
<Novas_install>/doc/tcl.pdf

Useful web sites:


Tcl Developer Site: http://www.tcl.tk/ Tcl Tutorials: http://www.tcl.tk/man/tcl8.5/tutorial/tcltutorial.html Tcl Commands: http://www.tcl.tk/man/tcl8.5/TclCmd/contents.htm Tk Commands: http://www.tcl.tk/man/tcl8.5/TkCmd/contents.htm

Books:
Sams Teach Yourself Tcl/Tk in 24 Hours by Venkat V.S.S. Practical Programming in Tcl and Tk by Brent Welch and Ken Jones

Support you can find:


Training: Allen Shieh allen_shieh@springsoft.com