Sunteți pe pagina 1din 37

U & P U PATEL DEPARTMENT OF

COMPUTER ENGINEERING

LAB MANUAL
On

NS-2
Prepared By:
Ritesh Patel
Riteshpatel.ce@ecchanga.ac.in

Faculty of Technology & Engineering


Charotar University of Science and Technology, Changa

Sr. No.
1

Practical Title

Introduction and installation of NS-2


Introduction of NS-2
Feature of NS-2
Networks supported by NS-2?
Installation steps of NS-2 in Ubuntu and CentOS
Introduction to TCL script.
(i)
Introduction to TCL Syntax, looping, conditional check,
functions, execution of Mathematical Operations and
Execution of Unix Command
(ii)
Write a Program in TCL which takes number N from user and
prints factorialuse function call
(iii) Implement Basic Calculator operation in TCL-use function
call
Simulation of Wired topology of 4 Node

Creating Output files for Xgraph


Analyzing and plotting received traffic from 3 nodes.
-data rate
-delay
-speed of link
-size of data

Creating Wireless Simulation on NS to analyze the effects error on one link v/s
behavior of Sliding Window Size

Page No.

Practical-I
AIM: Introduction and installation of NS-2
Objectives:

Introduction of NS-2
Feature of NS-2
Networks supported by NS-2?
Installation steps of NS-2 in Ubuntu and CentOS

III.1. Downloading/Installing ns&nam


You can build ns either from the the various packages (Tcl/Tk, otcl, etc.), or you can
download an 'all-in-one' package. I would recommend that you start with the all-in-one
package,
especially if you're not entirely sure which packages are installed on your system, and where
exactly they are installed. The disadvantage of the all-in-one distribution is the size, since it
contains some components that you don't need anymore after you compiled ns and nam. It's
still good for first tests, and you can always switch to the single-package distribution later.
Note: The all-in-one package only works on Unix systems.
You can download the package from the ns download page at UCB. If you have any
problems with your installation, take a look at the installation problems page on their server.
If that
also doesn't solve your problem, you might want to ask the ns-users mailing list.
After the installation is complete, you should make sure that your path points to the 'nsallinone/bin' directory (if you installed the ns-allinone package) where links to the ns and nam
executables in the 'ns-2' and 'nam-1' directories can be found or (if you built ns and nam from
the pieces) let your path point directly to the directories with the ns and nam executables.
On some systems you will also have to make sure that ns can find the library 'libotcl.so'. If
you installed the ns-allinone package, it should be in 'ns-allinone/otcl/'. On Solaris systems
you
would have to add this path to the 'LD_LIBRARY_PATH' environment variable. For help
with other systems, consult the installation problem page, the ns-users mailing list or your
local
Unix gurus.
A note concerning the ns-allinone version 2.1b3: There is a bug in it which causes some
problems on Solaris systems when nam trace generation is turned on. You can either
download
ns-allinone version 2.1b2 instead or go to the ns web page to download a current snapshot of
ns. If you do that, you have to unzip and untar the file in your allinone directory. Then you

change into the new directory and run './configure', then 'make'.
III.2. Starting ns
You start ns with the command 'ns <tclscript>' (assuming that you are in the directory with
the ns executable, or that your path points to that directory), where '<tclscript>' is the name of
a Tcl script file which defines the simulation scenario (i.e. the topology and the events). You
could also just start ns without any arguments and enter the Tcl commands in the Tcl shell,
but that is definitely less comfortable. For information on how to write your own Tcl scripts
for ns, see section IV.
Everything else depends on the Tcl script. The script might create some output on stdout, it
might write a trace file or it might start nam to visualize the simulation. Or all of the above.
These possibilities will all be discussed in later sections.

III.3. Starting nam


You can either start nam with the command 'nam <nam-file>' where '<nam-file>' is the name
of a nam trace file that was generated by ns, or you can execute it directly out of the Tcl
simulation script for the simulation which you want to visualize. The latter possibility will be
described in Section IV. For additional parameters to nam, see the nam manual page. Below
you can see a screenshot of a nam window where the most important functions are being
explained.

Practical-II
AIM: Introduction to TCL script.
Objectives:

Introduction to TCL Syntax, looping, conditional check, functions, execution


of Mathematical Operations and Execution of Unix Command
Write a Program in TCL which takes number N from user and prints
factorialuse function call
Implement Basic Calculator operation in TCL-use function call

Tcl (originally from Tool Command Language, but conventionally spelled "Tcl" rather than
"TCL"; pronounced as "tickle" or "tee-see-ell"[3]) is a scripting language created by John
Ousterhout.[4] Originally "born out of frustration",[5] according to the author, with
programmers devising their own languages intended to be embedded into applications, Tcl
gained acceptance on its own. It is commonly used for rapid prototyping, scripted
applications, GUIs and testing. Tcl is used on embedded systems platforms, both in its full
form and in several other small-footprint versions.

When you have installed Tcl, the program you will then call to utilize it is tclsh. For
instance, if you write some code to a file "hello.tcl", and you want to execute it, you would do
it like so: tclsh hello.tcl. Depending on the version of Tcl installed, and the operating
system distribution you use, the tclsh program may be a link to the real executable, which
may be named tclsh8.6 or tclsh86.exe on Microsoft Windows.
The tclsh is a simple command-line interactive interpreter. You can either start it with a
script on the command line, in which case it runs the script to completion and then exits, or
you can start it without any arguments, in which case you will be presented with an
interactive prompt, usually using a % symbol to prompt for input. In interactive mode, you can
type in commands, which Tcl will then execute and display the result, or any error messages
that result. To exit the interpreter, type exit and press Return.
In Tcl, everything may be represented as a string, although internally it may be represented as
a list, integer, double, or other type, in order to make the language fast.
The assignment command in Tcl is set.
When set is called with two arguments, as in:
set fruit Cauliflower

it places the second argument (Cauliflower) in the memory space referenced by the first
argument (fruit). Set always returns the contents of the variable named in the first
argument. Thus, when set is called with two arguments, it places the second argument in the

memory space referenced by the first argument and then returns the second argument. In the
above example, for instance, it would return "Cauliflower", without the quotes.
The first argument to a set command can be either a single word, like fruit or pi , or it can
be a member of an array. Arrays will be discussed in greater detail later, for the time being
just remember that many data can be collected under a single variable name, and an
individual datum can be accessed by its index within that array. Indexing into an array in Tcl
is handled by putting the index within parentheses after the name of the variable.
Set

can also be invoked with only one argument. When called with just one argument, it will
return the contents of that argument.
Here's a summary of the set command.
set varName ?value?
If value is specified,

then the contents of the variable varName are set equal to value
.
If varName consists only of alphanumeric characters, and no parentheses, it is a scalar
variable.
If varName has the form varName(index) , it is a member of an associative array.

If you look at the example code, you'll notice that in the set command the first argument is
typed with only its name, but in the puts statement the argument is preceded with a $.
The dollar sign tells Tcl to use the value of the variable - in this case X or Y.
Tcl passes data to subroutines either by name or by value. Commands that don't change the
contents of a variable usually have their arguments passed by value. Commands that do
change the value of the data must have the data passed by name.
set X "This is a string"
set Y 1.24
puts $X
puts $Y
puts "..............................."
set label "The value in Y is: "
puts "$label $Y"

In Tcl, the evaluation of a command is done in 2 phases. The first phase is a single pass of
substitutions. The second phase is the evaluation of the resulting command. Note that only
one pass of substitutions is made. Thus in the command
puts $varName

the contents of the proper variable are substituted for $varName, and then the command is
executed. Assuming we have set varName to "Hello World", the sequence would look like
this: puts $varName puts "Hello World", which is then executed and prints out Hello
World.
During the substitution phase, several types of substitutions occur.

A command within square brackets ([]) is replaced with the result of the execution of that
command.
Words within double quotes or braces are grouped into a single argument. However, double
quotes and braces cause different behavior during the substitution phase. In this lesson, we
will concentrate on the behavior of double quotes during the substitution phase.
Grouping words within double quotes allows substitutions to occur within the quotations - or,
in fancier terms, "interpolation". The substituted group is then evaluated as a single argument.
Thus, in the command:
puts "The current stock value is $varName"

In general, the backslash (\) disables substitution for the single character immediately
following the backslash. Any character immediately following the backslash will stand
without substitution.
However, there are specific "Backslash Sequence" strings which are replaced by specific
values during the substitution phase. The following backslash strings will be substituted as
shown below.
String
\a
\b

Output
Hex Value
Audible Bell
0x07
Backspace
0x08
Form Feed (clear
\f
0x0c
screen)
\n
New Line
0x0a
\r
Carriage Return
0x0d
\t
Tab
0x09
\v
Vertical Tab
0x0b
\0dd
Octal Value
d is a digit from 0-7
H is a hex digit 0-9,AF,a-f. This represents
\uHHHH
a 16-bit Unicode
character.
H is a hex digit 0-9,A-F,a-f. Note that the \x substitution
"keeps going" as long as it has hex digits, and only uses the
\xHH.... Hex Value
last two, meaning that \xaa and \xaaaa are equal, and that
\xaaAnd anyway will "eat" the A of "And". Using the \u
notation is probably a better idea.
You obtain the results of a command by placing the command in square brackets ([]). This is
the functional equivalent of the back single quote (`) in sh programming, or using the return
value of a function in C.
As the Tcl interpreter reads in a line it replaces all the $variables with their values. If a
portion of the string is grouped with square brackets, then the string within the square
brackets is evaluated as a command by the interpreter, and the result of the command replaces
the square bracketed string.
Let's take the following code segment, for example:

puts [readsensor [selectsensor]]

The parser scans the entire command, and sees that there is a command substitution to
perform: readsensor [selectsensor] , which is sent to the interpreter for
evaluation.
The parser once again finds a command to be evaluated and substituted,
selectsensor

The fictitious selectsensor command is evaluated, and it presumably returns a


sensor to read.
At this point, readsensor has a sensor to read, and the readsensor command is
evaluated.
Finally, the value of readsensor is passed on back to the puts command, which prints
the output to the screen.

The exceptions to this rule are as follows:

A square bracket that is escaped with a \ is considered as a literal square bracket.


A square bracket within braces is not modified during the substitution phase.

For Example

set x abc
puts "A simple substitution: $x\n"
set y [set x "def"]
puts "Remember that set returns the new value of the variable: X: $x
Y: $y\n"
set z {[set x "This is a string within quotes within braces"]}
puts "Note the curly braces: $z\n"
set a "[set x {This is a string within braces within quotes}]"
puts "See how the set is executed: $a"
puts "\$x is: $x\n"
set b "\[set y {This is a string within braces within quotes}]"
# Note the \ escapes the bracket, and must be doubled to be a
# literal character in double quotes
puts "Note the \\ escapes the bracket:\n \$b is: $b"
puts "\$y is: $y"

The Tcl command for doing math type operations is expr. The following discussion of the
expr command is extracted and adapted from the expr man page. Many commands use expr
behind the scenes in order to evaluate test expressions, such as if, while and for loops,
discussed in later sections. All of the advice given here for expr also holds for these other
commands.
expr

takes all of its arguments ("2 + 2" for example) and evaluates the result as a Tcl
"expression" (rather than a normal command), and returns the value. The operators permitted
in Tcl expressions include all the standard math functions, logical operators, bitwise
operators, as well as math functions like rand(), sqrt(), cosh() and so on. Expressions
almost always yield numeric results (integer or floating-point values).
Performance tip: enclosing the arguments to expr in curly braces will result in faster code.
So do expr {$i * 10} instead of simply expr $i * 10

OPERANDS
A Tcl expression consists of a combination of operands, operators, and parentheses. White
space may be used between operands, operators and parentheses; it is ignored by the
expression processor. Where possible, operands are interpreted as integer values. Integer
values may be specified in decimal (the normal case), in octal (if the first character of the
operand is 0), or in hexadecimal (if the first two characters of the operand are 0x).
Note that the octal and hexadecimal conversion takes place differently in the expr command
than in the Tcl substitution phase. In the substitution phase, a \x32 would be converted to an
ascii "2", while expr would convert 0x32 to a decimal 50.
If an operand does not have one of the integer formats given above, then it is treated as a
floating-point number, if that is possible. Floating-point numbers may be specified in any of
the ways accepted by an ANSI-compliant C compiler. For example, all of the following are
valid floating-point numbers:
2.1
3.
6E4
7.91e+16
.000001

If no numeric interpretation is possible, then an operand is left as a string (and only a limited
set of operators may be applied to it).
Note however, that it does not support numbers of the following forms:
2,1
2,100

- a decimal comma, instead of a decimal point


- a thousands separator

It is possible to deal with numbers in that form, but you will have to convert these "strings" to
numbers in the standard form first.
Beware of leading zeros: 0700 is not interpreted as the decimal number 700 (seven hundred),
but as the octal number 700 = 7*8*8 = 448 (decimal).
Worse, if the number contains a digit 8 or 9 an error results:
% expr {0900+1}
expected integer but got "0900" (looks like invalid octal number)

Octal numbers are in fact a relic of the past, when such number formats were much more
common.
Operands may be specified in any of the following ways:

As an numeric value, either integer or floating-point.


As a Tcl variable, using standard $ notation. The variable's value will be used as the
operand.

OPERATORS
The valid operators are listed below, grouped in decreasing order of precedence:
-+~!

Unary minus, unary plus, bit-wise NOT, logical NOT. None of these operators may
be applied to string operands, and bit-wise NOT may be applied only to integers.
**
Exponentiation (works on both floating-point numbers and integers)
*/%
Multiply, divide, remainder. None of these operators may be applied to string
operands, and remainder may be applied only to integers. The remainder will always
have the same sign as the divisor and an absolute value smaller than the divisor.
+Add and subtract. Valid for any numeric operands.
<< >>
Left and right (bit) shift. Valid for integer operands only.
< > <= >=
Relational operators: less, greater, less than or equal, and greater than or equal. Each
operator produces 1 if the condition is true, 0 otherwise. These operators may be
applied to numeric operands as well as strings, in which case string comparison is
used.
eq ne in ni
compare two strings for equality (eq) or inequality (ne). and two operators for
checking if a string is contained in a list (in) or not (ni). These operators all return 1
(true) or 0 (false). Using these operators ensures that the operands are regarded
exclusively as strings (and lists), not as possible numbers:
% expr { "9" == "9.0"}
1
% expr { "9" eq "9.0"}
0

&
Bit-wise AND. Valid for integer operands only.
^
Bit-wise exclusive OR. Valid for integer operands only.
|
Bit-wise OR. Valid for integer operands only.
&&
Logical AND. Produces a 1 result if both operands are non-zero, 0 otherwise. Valid
for numeric operands only (integers or floating-point).
||
Logical OR. Produces a 0 result if both operands are zero, 1 otherwise. Valid for
numeric operands only (integers or floating-point).
x?y:z
If-then-else. If x evaluates to non-zero, then the result is the value of y. Otherwise the
result is the value of z. The x operand must have a numeric value.
% set x 1
% expr { $x>0? ($x+1) : ($x-1) }
2

MATH FUNCTIONS
Tcl supports the following mathematical functions in expressions:
abs
atan2
cosh
floor
isqrt
min
sin
tan

acos
bool
double
fmod
log
pow
sinh
tanh

asin
ceil
entier
hypot
log10
rand
sqrt
wide

atan
cos
exp
int
max
round
srand

Besides these functions, you can also apply commands within an expression. For instance:
% set x 1
% set w "Abcdef"
% expr { [string length $w]-2*$x }
4

TYPE CONVERSIONS
Tcl supports the following functions to convert from one representation of a number to
another:
double int wide entier

double() converts a number to a floating-point number.


int() converts a number to an ordinary integer number

(by truncating the decimal

part).

wide()

converts a number to a so-called wide integer number (these numbers have a


larger range).
entier() coerces a number to an integer of appropriate size to hold it without
truncation. This might return the same as int() or wide() or an integer of arbitrary size
(in Tcl 8.5 and above).

IF Condition
Like most languages, Tcl supports an if command. The syntax is:

if expr1 ?then? body1 elseif expr2 ?then? body2 elseif

... ?else? ?bodyN?

The words then and else are optional, although generally then is left out and else is used.
The test expression following if should return a value that can be interpreted as representing
"true" or "false":
False True
all others
a numeric value 0
no yes
yes/no
false true
true/false
If the test expression returns a string "yes"/"no" or "true"/"false", the case of the return is not
checked. True/FALSE or YeS/nO are legitimate returns.
If the test expression evaluates to True, then body1 will be executed.
If the test expression evaluates to False, then the word after body1 will be examined. If the
next word is elseif, then the next test expression will be tested as a condition. If the next
word is else then the final body will be evaluated as a command.
The test expression following the word if is evaluated in the same manner as in the expr
command.

The test expression following if may be enclosed within quotes, or braces. If it is enclosed
within braces, it will be evaluated within the if command, and if enclosed within quotes it
will be evaluated during the substitution phase, and then another round of substitutions will
be done within the if command.
Example:
set x 1
if {$x == 2} {puts "$x is 2"} else {puts "$x is not 2"}
if {$x != 1} {
puts "$x is != 1"
} else {
puts "$x is 1"
}
if $x==1 {puts "GOT 1"}
#
# Be careful, this is just an example
# Usually you should avoid such constructs,
# it is less than clear what is going on and it can be dangerous
#
set y x
if "$$y != 1" {
puts "$$y is != 1"
} else {
puts "$$y is 1"
}
#
# A dangerous example: due to the extra round of substitution,
# the script stops
#
set y {[exit]}
if "$$y != 1" {
puts "$$y is != 1"
} else {
puts "$$y is 1"
}

Switch Case
he switch command allows you to choose one of several options in your code. It is similar to
switch in C, except that it is more flexible, because you can switch on strings, instead of just
integers. The string will be compared to a set of patterns, and when a pattern matches the
string, the code associated with that pattern will be evaluated.
It's a good idea to use the switch command when you want to match a variable against
several possible values, and don't want to do a long series of if... elseif ... elseif
statements.
The syntax of the command is:

switch string pattern1 body1 ?pattern2 body2?

... ?patternN bodyN?

- or

switch string { pattern1 body1 ?pattern2 body2?...?patternN bodyN? }

String

is the string that you wish to test, and pattern1, pattern2, etc are the patterns
that the string will be compared to. If string matches a pattern, then the code within the
body associated with that pattern will be executed. The return value of the body will be
returned as the return value of the switch statement. Only one pattern will be matched.
If the last pattern argument is the string default, that pattern will match any string. This
guarantees that some set of code will be executed no matter what the contents of string are.
If there is no default argument, and none of the patterns match string, then the switch
command will return an empty string.
If you use the brace version of this command, there will be no substitutions done on the
patterns. The body of the command, however, will be parsed and evaluated just like any other
command, so there will be a pass of substitutions done on that, just as will be done in the first
syntax. The advantage of the second form is that you can write multiple line commands more
readably with the brackets.
Tcl includes two commands for looping, the while and for commands. Like the if
statement, they evaluate their test the same way that the expr does. In this lesson we discuss
the while command, and in the next lesson, the for command. In most circumstances where
one of these commands can be used, the other can be used as well.

while test body

The while command evaluates test as an expression. If test is true, the code in body is
executed. After the code in body has been executed, testis evaluated again.
A continue statement within body will stop the execution of the code and the test will be reevaluated. A break within body will break out of the while loop, and execution will continue
with the next line of code after body
In Tcl everything is a command, and everything goes through the same substitution phase.
For this reason, the test must be placed within braces. If test is placed within quotes, the
substitution phase will replace any variables with their current value, and will pass that test to
the while command to evaluate, and since the test has only numbers, it will always evaluate
the same, quite probably leading to an endless loop!
Look at the two loops in the example. If it weren't for the break command in the second loop,
it would loop forever.
set x 1
# This is a normal way to write a Tcl while loop.
while {$x < 5} {
puts "x is $x"
set x [expr {$x + 1}]
}
puts "exited first loop with X equal to $x\n"
# The next example shows the difference between ".." and {...}
# How many times does the following loop run? Why does it not
# print on each pass?
set x 0
while "$x < 5" {

set x [expr {$x + 1}]


if {$x > 7} break
if "$x > 3" continue
puts "x is $x"
}
puts "exited second loop with X equal to $x"

Tcl supports an iterated loop construct similar to the for loop in C. The for command in Tcl
takes four arguments; an initialization, a test, an increment, and the body of code to evaluate
on each pass through the loop. The syntax for the for command is:

for start test next body

During evaluation of the for command, the start code is evaluated once, before any other
arguments are evaluated. After the start code has been evaluated, the test is evaluated. If the
test evaluates to true, then the body is evaluated, and finally, the next argument is
evaluated. After evaluating the next argument, the interpreter loops back to the test, and
repeats the process. If the test evaluates as false, then the loop will exit immediately.
Start

is the initialization portion of the command. It is usually used to initialize the iteration
variable, but can contain any code that you wish to execute before the loop starts.
The test argument is evaluated as an expression, just as with the expr while and if
commands.
Next

is commonly an incrementing command, but may contain any command which the Tcl
interpreter can evaluate.
Body

is the body of code to execute.

Since you commonly do not want the Tcl interpreter's substitution phase to change variables
to their current values before passing control to the for command, it is common to group the
arguments with curly braces. When braces are used for grouping, the newline is not treated as
the end of a Tcl command. This makes it simpler to write multiple line commands. However,
the opening brace must be on the line with the for command, or the Tcl interpreter will treat
the close of the next brace as the end of the command, and you will get an error. This is
different than other languages like C or Perl, where it doesn't matter where you place your
braces.
Within the body code, the commands break and continue may be used just as they are used
with the while command. When a break is encountered, the loop exits immediately. When a
continue is encountered, evaluation of the body ceases, and the test is re-evaluated.
Because incrementing the iteration variable is so common, Tcl has a special command for
this:

incr varName ?increment?

This command adds the value in the second argument to the variable named in the first
argument. If no value is given for the second argument, it defaults to 1.

For Example:
for {set i 0} {$i < 10} {incr i} {
puts "I inside first loop: $i"
}
for {set i 3} {$i < 2} {incr i} {
puts "I inside second loop: $i"
}
puts "Start"
set i 0
while {$i < 10} {
puts "I inside third loop: $i"
incr i
puts "I after incr: $i"
}
set i 0
incr i
# This is equivalent to:
set i [expr {$i + 1}]

Procedure in TCL
In Tcl there is actually no distinction between commands (often known as 'functions' in other
languages) and "syntax". There are no reserved words (like if and while) as exist in C, Java,
Python, Perl, etc... When the Tcl interpreter starts up there is a list of known commands that
the interpreter uses to parse a line. These commands include while, for, set, puts, and
so on. They are, however, still just regular Tcl commands that obey the same syntax rules as
all Tcl commands, both built-in, and those that you create yourself with the proc command.
The proc command creates a new command. The syntax for the proc command is:

proc name args body

When proc is evaluated, it creates a new command with name name that takes arguments
args. When the procedure name is called, it then runs the code contained in body.
Args

is a list of arguments which will be passed to name. When name is invoked, local
variables with these names will be created, and the values to be passed to name will be copied
to the local variables.
The value that the body of a proc returns can be defined with the return command. The
return command will return its argument to the calling program. If there is no return, then
body will return to the caller when the last of its commands has been executed. The return
value of the last command becomes the return value of the procedure.
proc sum {arg1 arg2} {
set x [expr {$arg1 + $arg2}];
return $x
}
puts " The sum of 2 + 3 is: [sum 2 3]\n\n"
proc for {a b c} {
puts "The for command has been replaced by a puts";
puts "The arguments were: $a\n$b\n$c\n"
}

for {set i 1} {$i < 10} {incr i}

Return values of Procedure


A proc can be defined with a set number of required arguments (as was done with sum in the
previous lesson, or it can have a variable number of arguments. An argument can also be
defined to have a default value.
Variables can be defined with a default value by placing the variable name and the default
within braces within args. For example:
proc justdoit {a {b 1} {c -1}} {
}

Since there are default arguments for the b and c variables, you could call the procedure one
of three ways: justdoit 10, which would set a to 10, and leave b set to its default 1, and c at
-1. justdoit 10 20 would likewise set b to 20, and leave C to its default. Or call it with all
three parameters set to avoid any defaults.
A proc will accept a variable number of arguments if the last declared argument is the word
args. If the last argument to a proc argument list is args, then any arguments that aren't
already assigned to previous variables will be assigned to args.
The example procedure below is defined with three arguments. At least one argument *must*
be present when example is called. The second argument can be left out, and in that case it
will default to an empty string. By declaring args as the last argument, example can take a
variable number of arguments.
Note that if there is a variable other than args after a variable with a default, then the default
will never be used. For example, if you declare a proc such as:
proc function { a {b 1} c} {...}, you will always have to call it with 3 arguments.
Tcl assigns values to a proc's variables in the order that they are listed in the command. If you
provide 2 arguments when you call function they will be assigned to a and b, and Tcl will
generate an error because c is undefined.
You can, however, declare other arguments that may not have values as coming after an
argument with a default value. For example, this is valid:
proc example {required {default1 a} {default2 b} args} {...}

In this case, example requires one argument, which will be assigned to the variable
required. If there are two arguments, the second arg will be assigned to default1. If there
are 3 arguments, the first will be assigned to required, the second to default1, and the third
to default2. If example is called with more than 3 arguments, all the arguments after the
third will be assigned to args.
For Example
proc example {first {second ""} args} {
if {$second eq ""} {
puts "There is only one argument and it is: $first"
return 1
} else {
if {$args eq ""} {

puts "There are two arguments - $first and $second"


return 2
} else {
puts "There are many arguments - $first and $second and $args"
return "many"
}
}
}
set
set
set
set

count1
count2
count3
count4

[example
[example
[example
[example

ONE]
ONE TWO]
ONE TWO THREE ]
ONE TWO THREE FOUR]

puts "The example was called with $count1, $count2, $count3, and $count4
Arguments"

Variable Scope (Global)


Tcl evaluates variables within a scope delineated by procs, namespaces (see Building
reusable libraries - packages and namespaces), and at the topmost level, the global scope.
The scope in which a variable will be evaluated can be changed with the global and upvar
commands.
The global command will cause a variable in a local scope (inside a procedure) to refer to
the global variable of that name.
The upvar command is similar. It "ties" the name of a variable in the current scope to a
variable in a different scope. This is commonly used to simulate pass-by-reference to procs.
You might also encounter the variable command in others' Tcl code. It is part of the
namespace system and is discussed in detail in that chapter.
Normally, Tcl uses a type of "garbage collection" called reference counting in order to
automatically clean up variables when they are not used anymore, such as when they go "out
of scope" at the end of a procedure, so that you don't have to keep track of them yourself. It is
also possible to explicitly unset them with the aptly named unset command.
The syntax for upvar is:

upvar ?level? otherVar1 myVar1 ?otherVar2 myVar2? ... ?otherVarN myVarN?

The upvar command causes myVar1 to become a reference to otherVar1, and myVar2 to
become a reference to otherVar2, etc. The otherVar variable is declared to be at level
relative to the current procedure. By default level is 1, the next level up.
If a number is used for the level, then level references that many levels up the stack from the
current level.
If the level number is preceded by a # symbol, then it references that many levels down
from the global scope. If level is #0, then the reference is to a variable at the global level.
If you are using upvar with anything except #0 or 1, you are most likely asking for trouble,
unless you really know what you're doing.
You should avoid using global variables if possible. If you have a lot of globals, you should
reconsider the design of your program.

Note that since there is only one global space it is surprisingly easy to have name conflicts if
you are importing other peoples code and aren't careful. It is recommended that you start
global variables with an identifiable prefix to help avoid unexpected conflicts.
For Example
proc SetPositive {variable value } {
upvar $variable myvar
if {$value < 0} {
set myvar [expr {-$value}]
} else {
set myvar $value
}
return $myvar
}
SetPositive x 5
SetPositive y -5
puts "X : $x

Y: $y\n"

proc two {y} {


upvar 1 $y z
upvar 2 x a
puts "two: Z: $z A: $a"
set z 1
set a 2
}
proc one {y} {
upvar $y z
variable z
puts "one: Z: $z"
two z
value
}
one y
the call.
puts "\nX: $x

;#
;#
;#
;#
;#

tie the calling value to variable z


Tie variable x two levels up to a
Output the values, just to confirm
Set z, the passed variable to 1;
Set x, two layers up to 2;

;# This ties the calling value to


;# Output that value, to check it is 5
;# call proc two, which will change the

;# Call one, and output X and Y after


Y: $y"

proc existence {variable} {


upvar $variable testVar
if { [info exists testVar] } {
puts "$variable Exists"
} else {
puts "$variable Does Not Exist"
}
}
set x 1
set y 2
for {set i 0} {$i < 5} {incr i} {
set a($i) $i;
}
puts "\ntesting unsetting a simple variable"
# Confirm that x exists.
existence x
# Unset x
unset x
puts "x has been unset"
# Confirm that x no longer exists.
existence x

Example: Find out the Factorial of given number

Sources:
1)
2)
3)
4)

http://tmml.sourceforge.net/doc/tcl/
http://www.tcl.tk/man/tcl8.5/tutorial/tcltutorial.html
http://www.tcl.tk/about/language.html
http://users.belgacom.net/bruno.champagne/tcl.html

Questions:
1)
2)
3)
4)

Write down basic Constructs of TCL language.


What is Full form of TCL?
Write a TCL script to find whether entered number is prime OR not
Write a Program in TCL which simulates behavior of normal CALCULATOR with
basic operation(+,-,*,/)
5) By taking suitable example, explain importance of global keyword in TCL example

Practical-III
AIM: Simulation of Wired topology of 4 Node
Objectives:

Introduction to TCL Syntax, looping, conditional check, functions, execution


of Mathematical Operations and Execution of Unix Command
Write a Program in TCL which takes number N from user and prints
factorialuse function call
Implement Basic Calculator operation in TCL-use function call

The topology
As always, the first step is to define the topology. You should create a file 'example2.tcl',
using the code from section IV.1 as a template. As I said before, this code will always be
similar. You will always have to create a simulator object, you will always have to start the
simulation with the same command, and if you want to run nam automatically, you will
always have to open a trace file, initialize it, and define a procedure which closes it and starts
nam.
Now insert the following lines into the code to create four nodes.

set
set
set
set

n0
n1
n2
n3

[$ns
[$ns
[$ns
[$ns

node]
node]
node]
node]

The following piece of Tcl code creates three duplex links between the nodes.

$ns duplex-link $n0 $n2 1Mb 10ms DropTail


$ns duplex-link $n1 $n2 1Mb 10ms DropTail
$ns duplex-link $n3 $n2 1Mb 10ms DropTail

You can save and start the script now. You might notice that the topology looks a bit
awkward in nam. You can hit the 're-layout' button to make it look better, but it would be nice
to have some more control over the layout. Add the next three lines to your Tcl script and
start it again.

$ns duplex-link-op $n0 $n2 orient right-down


$ns duplex-link-op $n1 $n2 orient right-up
$ns duplex-link-op $n2 $n3 orient right

You will probably understand what this code does when you look at the topology in the nam
window now. It should look like the picture below.

Note that the autolayout related parts of nam


are gone, since now you have taken the
layout into your own hands. The options for
the orientation of a link are right, left, up,
down and combinations of these
orientations. You can experiment with these
settings later, but for now please leave the
topology the way it is.

V.2. The events


Now we create two UDP agents with CBR traffic sources and attach them to the nodes n0
and n1. Then we create a Null agent and attach it to node n3.

#Create a UDP agent and attach it to node n0


set udp0 [new Agent/UDP]
$ns attach-agent $n0 $udp0
# Create a CBR traffic source and attach it to udp0
set cbr0 [new Application/Traffic/CBR]
$cbr0 set packetSize_ 500
$cbr0 set interval_ 0.005
$cbr0 attach-agent $udp0
#Create a UDP agent and attach it to node n1
set udp1 [new Agent/UDP]
$ns attach-agent $n1 $udp1
# Create a CBR traffic source and attach it to udp1
set cbr1 [new Application/Traffic/CBR]
$cbr1 set packetSize_ 500
$cbr1 set interval_ 0.005
$cbr1 attach-agent $udp1
set null0 [new Agent/Null]
$ns attach-agent $n3 $null0

The two CBR agents have to be connected to the Null agent.

$ns connect $udp0 $null0


$ns connect $udp1 $null0

We want the first CBR agent to start sending at 0.5 seconds and to stop at 4.5 seconds while
the second CBR agent starts at 1.0 seconds and stops at 4.0 seconds.

$ns
$ns
$ns
$ns

at
at
at
at

0.5
1.0
4.0
4.5

"$cbr0
"$cbr1
"$cbr1
"$cbr0

start"
start"
stop"
stop"

When you start the script now with 'ns example2.tcl', you will notice that there is more traffic
on the links from n0 to n2 and n1 to n2 than the link from n2 to n3 can carry. A simple
calculation confirms this: We are sending 200 packets per second on each of the first two
links and the packet size is 500 bytes. This results in a bandwidth of 0.8 megabits per second
for the links from n0 to n2 and from n1 to n2. That's a total bandwidth of 1.6Mb/s, but the
link between n2 and n3 only has a capacity of 1Mb/s, so obviously some packets are being
discarded. But which ones? Both flows are black, so the only way to find out what is
happening to the packets is to monitor them in nam by clicking on them. In the next two
sections I'm going to show you how to distinguish between different flows and how to see
what is actually going on in the queue at the link from n2 to n3.

V.3. Marking flows


Add the following two lines to your CBR agent definitions.

$udp0 set class_ 1


$udp1 set class_ 2

The parameter 'fid_' stands for 'flow id'.


Now add the following piece of code to your Tcl script, preferably at the beginning after the
simulator object has been created, since this is a part of the simulator setup.

$ns color 1 Blue


$ns color 2 Red

This code allows you to set different colors


for each flow id.

Now you can start the script again and one


flow should be blue, while the other one is
red. Watch the link from node n2 to n3 for a
while, and you will notice that after some
time the distribution between blue and red
packets isn't too fair anymore (at least that's
the way it is on my system). In the next
section I'll show you how you can look

inside this link's queue to find out what is going on there.

V.4. Monitoring a queue


You only have to add the following line to your code to monitor the queue for the link from
n2 to n3.

$ns duplex-link-op $n2 $n3 queuePos 0.5

Start ns again and you will see a picture


similar to the one below after a few
moments.

You can see the packets in the queue now,


and after a while you can even see how the
packets are being dropped, though (at least
on my system, I guess it might be different
in later or earlier releases) only blue packets
are being dropped. But you can't really
expect too much 'fairness' from a simple
DropTail queue. So let's try to improve the queueing by using a SFQ (stochastic fair
queueing) queue for the link from n2 to n3. Change the link definition for the link between n2
and n3 to the following line.
$ns duplex-link $n3 $n2 1Mb 10ms SFQ

The queueing should be 'fair' now. The same amount of blue and red packets should be
dropped.

The full example

Practical-IV
AIM: Creating Output files for Xgraph
Objectives:

Analyzing and plotting received traffic from 3 nodes.


-data rate
-delay
-speed of link
-size of data

One part of the ns-allinone package is 'xgraph', a plotting program which can be used to
create graphic representations of simulation results. In this section, I will show you a simple
way how you can create output files in your Tcl scripts which can be used as data sets for
xgraph. On the way there, I will also show you how to use traffic generators.
A note: The technique I present here is one of many possible ways to create output files
suitable for xgraph. If you think there is a technique which is superior in terms of
understandablity (which is what I aim for in this tutorial), please let me know.
VIII.1. Topology and Traffic Sources
First of all, we create the following topology:

The following piece of code should look familiar to you by now if you read the first sections
of this tutorial.
set
set
set
set
set

n0
n1
n2
n3
n4

[$ns
[$ns
[$ns
[$ns
[$ns

node]
node]
node]
node]
node]

$ns
$ns
$ns
$ns

duplex-link
duplex-link
duplex-link
duplex-link

$n0
$n1
$n2
$n3

$n3
$n3
$n3
$n4

1Mb
1Mb
1Mb
1Mb

100ms
100ms
100ms
100ms

DropTail
DropTail
DropTail
DropTail

We are going to attach traffic sources to the nodes n0, n1 and n2, but first we write a
procedure that will make it easier for us to add the traffic sources and generators to the nodes:
proc attach-expoo-traffic { node sink size burst idle rate } {
#Get an instance of the simulator
set ns [Simulator instance]
#Create a UDP agent and attach it to the node
set source [new Agent/UDP]
$ns attach-agent $node $source
#Create an Expoo traffic agent and set its configuration parameters
set traffic [new Application/Traffic/Exponential]
$traffic set packetSize_ $size
$traffic set burst_time_ $burst
$traffic set idle_time_ $idle
$traffic set rate_ $rate
# Attach traffic source to the traffic generator
$traffic attach-agent $source
#Connect the source and the sink
$ns connect $source $sink
return $traffic
}

This procedure looks more complicated than it really is. It takes six arguments: A node, a
previously created traffic sink, the packet size for the traffic source, the burst and idle times
(for the exponential distribution) and the peak rate. For details about the Expoo traffic
sources, please refer to the documentation for ns.
First, the procedure creates a traffic source and attaches it to the node, then it creates a
Traffic/Expoo object, sets its configuration parameters and attaches it to the traffic source,
before eventually the source and the sink are connected. Finally, the procedure returns a
handle for the traffic source. This procedure is a good example how reoccuring tasks like
attaching a traffic source to several nodes can be handled. Now we use the procedure to
attach traffic sources with different peak rates to n0, n1 and n2 and to connect them to three
traffic sinks on n4 which have to be created first:
set
set
set
$ns
$ns

sink0 [new Agent/LossMonitor]


sink1 [new Agent/LossMonitor]
sink2 [new Agent/LossMonitor]
attach-agent $n4 $sink0
attach-agent $n4 $sink1

$ns attach-agent $n4 $sink2


set source0 [attach-expoo-traffic $n0 $sink0 200 2s 1s 100k]
set source1 [attach-expoo-traffic $n1 $sink1 200 2s 1s 200k]
set source2 [attach-expoo-traffic $n2 $sink2 200 2s 1s 300k]

In this example we use Agent/LossMonitor objects as traffic sinks, since they store the
amount of bytes received, which can be used to calculate the bandwidth.
VIII.2. Recording Data in Output Files
Now we have to open three output files. The following lines have to appear 'early' in the Tcl
script.
set f0 [open out0.tr w]
set f1 [open out1.tr w]
set f2 [open out2.tr w]

These files have to be closed at some point. We use a modified 'finish' procedure to do that.
proc finish {} {
global f0 f1 f2
#Close the output files
close $f0
close $f1
close $f2
#Call xgraph to display the results
exec xgraph out0.tr out1.tr out2.tr -geometry 800x400 &
exit 0
}

It not only closes the output files, but also calls xgraph to display the results. You may want
to adapt the window size (800x400) to your screen size.
Now we can write the procedure which actually writes the data to the output files.
proc record {} {
global sink0 sink1 sink2 f0 f1 f2
#Get an instance of the simulator
set ns [Simulator instance]
#Set the time after which the procedure should be called again
set time 0.5
#How many bytes have been received by the traffic sinks?
set bw0 [$sink0 set bytes_]
set bw1 [$sink1 set bytes_]
set bw2 [$sink2 set bytes_]
#Get the current time
set now [$ns now]
#Calculate the bandwidth (in MBit/s) and write it to the files
puts $f0 "$now [expr $bw0/$time*8/1000000]"
puts $f1 "$now [expr $bw1/$time*8/1000000]"
puts $f2 "$now [expr $bw2/$time*8/1000000]"
#Reset the bytes_ values on the traffic sinks
$sink0 set bytes_ 0
$sink1 set bytes_ 0

$sink2 set bytes_ 0


#Re-schedule the procedure
$ns at [expr $now+$time] "record"
}

This procedure reads the number of bytes received from the three traffic sinks. Then it
calculates the bandwidth (in MBit/s) and writes it to the three output files together with the
current time before it resets the bytes_ values on the traffic sinks. Then it re-schedules itself.
VIII.3. Running the Simulation
We can now schedule the following events:
$ns
$ns
$ns
$ns
$ns
$ns
$ns
$ns

at
at
at
at
at
at
at
at

0.0 "record"
10.0 "$source0
10.0 "$source1
10.0 "$source2
50.0 "$source0
50.0 "$source1
50.0 "$source2
60.0 "finish"

start"
start"
start"
stop"
stop"
stop"

$ns run

First, the 'record' procedure is called, and afterwards it will re-schedule itself periodically
every 0.5 seconds. Then the three traffic sources are started at 10 seconds and stopped at 50
seconds. At 60 seconds, the 'finish' procedure is called. You can find the full example script
here.
When you run the simulation, an xgraph window should open after some time which should
look similar to this one:

As you can see, the bursts of the first flow peak at 0.1Mbit/s, the second at 0.2Mbit/s and the
third at 0.3Mbit/s. Now you can try to modify the 'time' value in the 'record' procedure. Set it
to '0.1' and see what happens, and then try '1.0'. It is very important to find a good 'time' value
for each simulation scenario.

Note that the output files created by the 'record' procedure can also be used with gnuplot.
The Full Program:

Practical-V
AIM: Creating wired Simulation on NS to analyze the effects of error on one link v/s behavior of
Sliding Window Size

Objectives:

Create the topology as mentioned below


Create the Agents and Set the parameters as mentioned below
Introduce the random error rate of 0.2 on link between n2 and n3
Observer the traffic and plot the behavior of
o Window size with respect to time
o Window size with random error rate = 0.5

Explanation:
Error Model of NS-2

Full Program:

Output

S-ar putea să vă placă și