logo
 
 Main Menu
 Tutorials
 Forum
 Who's Online
9 user(s) are online (1 user(s) are browsing Tutorials)

Members: 0
Guests: 9

more...
 Top Posters
1
jgrad
298
2
ebrunvand
64
3 svchw 47
4
jbakos
36
5 ucgrad 35
6
jamesstine
33
7
ekalenda
33
8 pepet 25
9 reneezl 21
10 ashkan2000 20
General: TCL Scripting

TCL Scripting
Author: J. Grad
Published: Sat, 24-Dec-2005
Version: 0.08
Article ID: 16
Read: 6659 times
Article Size: 8.12 KB

Printer Friendly Page Tell a Friend

The TCL Scripting Language

Most software tools require a scripting/batch/macro language. In the past this meant that the user had to learn a new language for each software package. This is clearly inefficient, both for the user but also for the company. They shouldn't really spend their time creating languages.

This is where TCL comes into play. It is a scripting language that can readily be used in any application. As a result, essentially all modern EDA tools now use TCL (e.g. Cadence Encounter, RTL Compiler and Synopsys Design Compiler). It just makes sense.

Another plus for TCL is that there is also a graphical toolkit to build GUIs. That is called Tk. So the combination of both is known as "TCL/Tk", pronounced "tickle T-K".

Introduction

TCL is an interpreted language, no compiled binaries. So it is system independent. Unix systems usually come pre-installed with a TCL interpreter installed. Windows user can download the Activestate TCL release. But most likely you want to write a script for a particular tool. In that case no external interpreter is needed.

The original TCL shell can usually be started with "tcl", and the graphical TCL/TK shell is called "wish". Start either one and just type away TCL commands. Since we are mostly interested in EDA we will use Cadence Encounter for this tutorial. Start it with the command "encounter".

TCL Basics

TCL has a very simple structure. Each command is of the form

command param1 param2 ...

No parenthesis, nothing at the end of the line. Just a command and a number of parameters. There are no variable types either, they are derived from the context.

Let's begin with a quick "Hello World" example:

encounter 1> set a 1
1
encounter 2> set b [expr $a + $a]
2
encounter 3> puts "Hello World, $b"
Hello World, 2

We can conclude the following items:

  • Variables need not be defined
  • Variables are assigned using "set"
  • Functions to be evaluated are placed in "[" "]"
  • Math expressions are computed with the command "expr"
  • Variables are referenced using "$"
  • Text is output with "puts"

At first sight TCL code looks fairly different from C code, but its structure is very simple and intuitive.

Control Structures

As with any language there are the usual "if-then" and "for" structures. Here is a for-loop where $a is counted from 1 to 9. The sequence of parameters is similar to C, begin - check - next - command:

encounter 1> for {set a 1} {$a<10} {incr a} {puts $a}
1
2
3
4
5
6
7
8
9

We can readily add an if-command to only print odd numbers:

encounter 17> for {set a 1} {$a<10} {incr a} {if [expr $a%2] {puts $a}}
1
3
5
7
9

The if statement in the previous example works like this: The modulo of 2 for an even number is zero. And "zero" means "false" in TCL. To summarize, Boolean false values in TCL are "0", "false" and "no". Everything else is Boolean true.

Lists

A very powerful feature of TCL is the built in list handling. You may recall the pain of building a linked list in C, pointers everywhere. TCL has a built in list data-type and all the typical command to handle list elements. Consider this example:

encounter 36> set a my
my
encounter 37> lappend a name is joe
my name is joe
encounter 38> llength $a
4
encounter 39> set name [lindex $a 3]
joe
encounter 40> set sorted [lsort $a]
is joe my name

We see that a list is really just a string with all list elements separated by white spaces. We can use "lappend" to add elements, "llength" to query the number of elements and "lindex" to obtain a specific element. To sort a list we can use "lsort".

The next question is, once you built a list, what do you do with it? This is where the "foreach" command comes in handy. It provides a simple way to traverse all list elements. In the next example we use it to simply output each element:

encounter 41> foreach word $a {puts $word}
my
name
is
joe

In this last example we use "foreach" to loop over all elements in our list. At each iteration, the current value is stored in $word. Then we can act upon that value, in our case with "puts".

Procedures

Just like any other programming language TCL supports procedures. Usually the code is put into a separate file and then loaded at run time. After that the new procedures can be used just like TCL commands.

For the next example, create a file called "myproc.tcl" with this contents:

proc sum {a b} {
    expr $a+$b
}

This is a very simple procedure called "sum". It takes two parameters and returns the sum. Note there is no "return" command. TCL simply uses the last result as the return value.

To actually use this code we use the "source" command to read in our "myproc.tcl" file. This will not actually execute any code, only make "sum" available for use to use. After the "source" command we can use our new procedure just like any TCL command:

encounter 49> source myproc.tcl
encounter 50> sum 21 9
30

Local and Global Variables

Variables that are defined in the main section of a TCL file or on the command line are called "global variables". On the other hand, variables inside a procedure are "local variables". That makes sense because a procedure should be universal and should be able to use any variable name, regardless of which global variables are used.

But sometimes it is necessary to access a global variable. Especially in EDA software there are many switches that engineers typically use to control the implementation run. We will run an example to illustrate the problem, followed by a second example with the solution.

Let's go back to our file "myproc.tcl" and edit it like this:

proc sum {a b} {
    expr $a+$b+$c
}

We see that the new variable $c has been introduced. It has no assigned value, since it is not declared as a parameter of the procedure. We want to use whatever value $c has at the time "sum" is called. So in our example $c is a global variable.

However, when we run this example, it does not work like this:

encounter 61> source myproc.tcl
encounter 62> set c 1
1
encounter 63> sum 21 9
can't read "c": no such variable
encounter 64>

We can certainly assign a value to $c on the command line, but as we can see $c is not visible in our procedure.

The solution is the "global" keyword. It tells TCL that a certain variable should get the global value. So we can modify "myproc.tcl" as follows:

proc sum {a b} {
    global c
    expr $a+$b+$c
}

We add the "global" command to make $c a global variable. Now it will actually get the global value that is set when "sum" is run:

encounter 64> source try.tcl
encounter 65> set c 1
1
encounter 66> sum 21 9
31
encounter 67>

We see the correct result is produced, 31=21+9+1. The 21 and 9 are given to the procedure as parameters and the "1" is the current value of $c. Using this method we can readily access all global variables in a TCL session.

Conclusion

TCL is a great programming language with powerful built in features and a very easy to understand syntax. In EDA tools in particular we can collect our code in ".tcl" files and then use "source" to read it in at run time.




TCL Scripting © copyright 2013 http://www.chiptalk.org
Powered by XOOPS 2.0 © 2001-2003 The XOOPS Project