Tcl represents all data as ordinary text strings. As you might expect, the string-handling features of Tcl are particularly strong. However, Tcl also provides a full complement of C-like arithmetic operators to manipulate strings that represent numbers.
The examples in the following sections exhibit some of the fundamental mechanisms of the Tcl language, in order to provide some of the flavor of working in Tcl. However, this is only an introduction.
For documentation on all Tcl interfaces in Tornado (as well as on C interfaces), see the Tornado API Guide from Wind River Systems.
For the Tcl language itself, the following generally available books are helpful:
The Tcl set command defines variables. Its result is the current value of the variable, as shown in the following examples:
|
|||||||||||||||||||
|
|||||||||||||||||||
set num 6 |
6 |
||||||||||||||||||
set y hello |
hello |
||||||||||||||||||
set z "hello world" |
hello world |
||||||||||||||||||
set t $z |
hello world |
||||||||||||||||||
set u "$z $y" |
hello world hello |
||||||||||||||||||
set v {$z $y} |
$z $y |
||||||||||||||||||
|
|||||||||||||||||||
The expressions above also illustrate the use of some special characters in Tcl:
Tcl provides special facilities for manipulating lists. In Tcl, a list is just a string, with the list elements delimited by spaces, as shown in the following examples:
|
|||||||||||||||||||
|
|||||||||||||||||||
llength $v |
2 |
||||||||||||||||||
lindex $u 1 |
world |
||||||||||||||||||
set long "a b c d e f g" |
a b c d e f g |
||||||||||||||||||
lrange $long 2 4 |
c d e |
||||||||||||||||||
lreplace $long 2 4 C D E |
a b C D E f g |
||||||||||||||||||
set V "{c d e} f {h {i j} k}" |
|
||||||||||||||||||
lindex $V 1 |
f |
||||||||||||||||||
lindex $V 0 |
c d e |
||||||||||||||||||
|
|||||||||||||||||||
The last examples use curly braces to delimit list items, yielding "lists of lists." This powerful technique, especially combined with recursive command substitution (see B.2.4 Command Substitution), can provide a little of the flavor of Lisp in Tcl programs.
Tcl arrays are all associative arrays, using a parenthesized key to select or define a particular element of an array: arrayName(keyString). The keyString may in fact represent a number, giving the effect of ordinary indexed arrays. The following are some examples of expressions involving Tcl arrays:
|
|||||||||||||||||||
|
|||||||||||||||||||
set taskId(tNetTask) |
0x4f300 |
||||||||||||||||||
set cpuFamily(5) m68k |
m68k |
||||||||||||||||||
set cpuFamily(10) sparc |
sparc |
||||||||||||||||||
set cpuId 10 |
10 |
||||||||||||||||||
set cpuFamily($cpuId) |
sparc |
||||||||||||||||||
|
|||||||||||||||||||
In Tcl, you can capture the result of the command as text by enclosing the command in square brackets [ ]. The Tcl interpreter substitutes the command result in the same process that is already running, which makes this an efficient operation.
|
|||||||||||||||||||
|
|||||||||||||||||||
set m [lrange $long 2 4] |
c d e |
||||||||||||||||||
set n [lindex $m 1] |
d |
||||||||||||||||||
set o [lindex [lrange $long 2 4] 1] |
d |
||||||||||||||||||
set x [lindex [lindex $V 2] 1] |
i j |
||||||||||||||||||
|
|||||||||||||||||||
The last example selects from a list of lists (defined among the examples in B.2.2 Lists in Tcl). This and the previous example show that you can nest Tcl command substitutions readily. The Tcl interpreter substitutes the most deeply nested command, then continues substituting recursively until it can evaluate the outermost command.
Tcl has an expr command to evaluate arithmetic expressions. The expr command understands numbers in decimal and hexadecimal, as in the following examples:
|
|||||||||||||||||||
|
|||||||||||||||||||
expr (2 << 2) + 3 |
11 |
||||||||||||||||||
expr 0xff00 & 0xf00 |
3840 |
||||||||||||||||||
|
|||||||||||||||||||
Tcl includes many commands for working with files and for formatted I/O. Tcl also has many facilities for interrogating file directories and attributes. The following examples illustrate some of the possibilities:
Procedure definition in Tcl is straightforward, and resembles many other languages. The command proc builds a procedure from its arguments, which give the procedure name, a list of its arguments, and a sequence of statements for the procedure body. In the body, the return command specifies the result of the procedure. For example, the following defines a procedure to compute the square of a number:
proc square {i} { return [expr $i * $i] }
If a procedure's argument list ends with the word args, the result is a procedure that can be called with any number of arguments. All trailing arguments are captured in a list $args. For example, the following procedure calculates the sum of all its arguments:
proc sum {args} { set accum 0 foreach item $args { incr accum $item } return $accum }
Defined Tcl procedures are called by name, and can be used just like any other Tcl command. The following examples illustrate some possibilities:
|
|||||||||||||||||||
|
|||||||||||||||||||
square 4 |
16 |
||||||||||||||||||
square [sum 1 2 3] |
36 |
||||||||||||||||||
set x "squ" |
squ |
||||||||||||||||||
set y "are" |
are |
||||||||||||||||||
$x$y 4 |
16 |
||||||||||||||||||
|
|||||||||||||||||||
The technique illustrated by the last example--constructing a procedure name "on the fly"--is used extensively in the Tornado tools to group a set of related procedures. The effect is similar to what can be achieved with function pointers in C.
For example, in Tornado tools, events are represented in Tcl as structured strings. The first element of the string is the name of the event. Tcl scripts that handle events can search for the appropriate procedure to handle a particular event by mapping the event name to a procedure name, and calling that procedure if it exists. The following Tcl script demonstrates this approach:
proc shEventDispatch {event} { set handlerProc "[lindex $event 0]_Handler" if {[info procs $handlerProc] != ""} { $handlerProc $event } { #event has no handler--do nothing. } }
Tcl provides all the popular control structures: conditionals (if), loops (while, for, and foreach), case statements (switch), and explicit variable-scope control (global, upvar, and uplevel variable declarations). By using these facilities, you can even define your own control structures. While there is nothing mysterious about these facilities, more detailed descriptions are beyond the scope of this summary. For detailed information, see the books cited in the introduction to B.2 A Taste of Tcl.
Every Tcl procedure, whether built-in or script, normally returns a string. Tcl procedures may signal an error instead: in a defined procedure, this is done with the error command. This starts a process called unwinding. When a procedure signals an error, it passes to its caller a string containing information about the error. Control is passed to the calling procedure. If that procedure did not provide for this possibility by using the Tcl catch command, control is passed to its caller in turn. This recursive unwinding continues until the top level, the Tcl interpreter, is reached.
As control is passed along, any procedure can catch the error and take one of two actions: signal another error and provide error information, or work around the error and return as usual, ending the unwinding process.
At each unwinding step, the Tcl interpreter adds a description of the current execution context to the Tcl variable errorInfo. After unwinding ends, you can display errorInfo to trace error information. Another variable, errorCode, may contain diagnostic information, such as an operating system dependent error code returned by a system call.
Tcl is designed to integrate with C applications. The Tcl interpreter itself is distributed as a library, ready to link with other applications. The core of the Tcl integration strategy is to allow each application to add its own commands to the Tcl language. This is accomplished primarily through the subroutine Tcl_CreateCommand( ) in the Tcl interpreter library, which associates a new Tcl command name and a pointer to an application-specific routine. For more details, consult the Tcl books cited in the introduction to B.2 A Taste of Tcl.