The '''main script''' is the primary script that is executed by the interpreter, e.g. [tclsh] or [wish]. ** Description ** One common technique is to have a script run a self test if it detects that it is the main script. Naive approaches only compare `[info script]` with `$[argv0]`. A somewhat more robust approach that usually works with [pkg_mkIndex] looks only at the `[file tail]` of those two values. The most robust approach fully normalizes those two values, including the last component, which a simple `[file normalize]` does not resolve. The most complete approach: ====== if {[info exists argv0] && [ file dirname [file normalize [info script]/...]] eq [ file dirname [file normalize $argv0/...]]} { #do stuff } ====== The `/...` on the end of each path ensures that [file normalize] resolves the path completely. Normally, the last component will not be resolved (see documentation for details). A common and fairly robust approach: ====== if {[info exists argv0] && [file tail [info script]] eq [file tail $argv0]} { #do stuff } ====== The negative approach, also quite common: ====== if {![info exists argv0] || [file tail [info script]] ne [file tail $argv0]} { return } # test/standalone code follows ====== The more simple and naive approach to detection method directly compares `[info script]` with `$[argv0]`: ====== if {[info exists argv0] && $argv0 eq [info script]} { #do stuff } ====== or, as formulated in [https://groups.google.com/d/msg/comp.lang.tcl/JuSQaHOKq10/Fm4ciso0VSUJ%|%Methods for Justifying text output in TCL], [DKF], [comp.lang.tcl], 2001-06-15: ====== if {[string equal $::argv0 [info script]] || [array exists ::embed_args]} { main } ====== ''[AMG]: Which posting would that be? What is `::embed_args`? It must be something specific to the script [DKF] was describing.'' [PYK]: I migrated this example and the verbiage from another page (can't remember which one now), and unfortunately it was just as unclear on that other page as well. I just searched [comp.lang.tcl] though, found the conversation, and included it above. [AMG]: Here's a new way to do it, comparing device and inode numbers: ====== proc mainScript {} { global argv0 if {[info exists argv0] && [file exists [info script]] && [file exists $argv0]} { file stat $argv0 argv0Info file stat [info script] scriptInfo expr {$argv0Info(dev) == $scriptInfo(dev) && $argv0Info(ino) == $scriptInfo(ino)} } else { return 0 } } ====== And by request from [PYK], here's how to make the above callable as [[info main]]: ====== namespace ensemble configure info -map [dict replace\ [namespace ensemble configure info -map] main mainScript] ====== [PYK]: Actually, I was suggesting that since only [tclsh] itself really knows what is the main script, e.g. wouldn't get confused by `source [info script]`, that it should provide `[[info main]]` as an alternative to all the scripts on this page. [dbohdan] 2014-10-11: It appears that if a script is run from a network drive on [Windows] `$argv0Info(ino) == $scriptInfo(ino)` doesn't hold. [PYK] 2014-10-11: I just tried with Tcl version 8.6.2 under Windows XP, and didn't detect any problem. Can you provide more details? [dbohdan] 2014-10-12: Sure. I happened upon this problem when testing [2048.tcl] in a Windows XP VM in VirtualBox under Linux. To run the game more conveniently I mapped a [https://www.virtualbox.org/manual/ch04.html#sharedfolders%|%shared folder] to a networked drive letter (`\\vboxsvr\2048-tcl` to drive `T:`) but the game did not start when I tried to run it. Debugging the problem I found that in `mainScript` `$argv0Info(ino)` and `$scriptInfo(ino)` had different values, e.g., 60568 and 24584 or -28664 and 24584. This was true for both [ActiveTcl] 8.5 and [Binary Distributions%|%tombert's tcltk] 8.6.2. If you could not reproduce it then VirtualBox's shared folder mechanism rather than running from a network drive may be to blame. ** authors ** [dkf]: [CJL]: ''[AMG]: I'm not sure who this is... is a full name available? According to [http://www.intelius.com/results.php?ReportType=1&searchform=name&qf=cameron&qn=laird], it's not [Cameron Laird] whose middle initial is not J.'' [PYK]: [RS]: <>