1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206
|
#
# Tests for argument lists and method execution
# ----------------------------------------------------------------------
# AUTHOR: Michael J. McLennan
# Bell Labs Innovations for Lucent Technologies
# mmclennan@lucent.com
# http://www.tcltk.com/itcl
# ----------------------------------------------------------------------
# Copyright (c) 1993-1998 Lucent Technologies, Inc.
# ======================================================================
# See the file "license.terms" for information on usage and
# redistribution of this file, and for a DISCLAIMER OF ALL WARRANTIES.
package require tcltest 2.1
namespace import ::tcltest::test
::tcltest::loadTestedCommands
package require itcl
# ----------------------------------------------------------------------
# Methods with various argument lists
# ----------------------------------------------------------------------
test methods-1.1 {define a class with lots of methods and arg lists} {
itcl::class test_args {
method none {} {
return "none"
}
method two {x y} {
return "two: $x $y"
}
method defvals {x {y def1} {z def2}} {
return "defvals: $x $y $z"
}
method varargs {x {y def1} args} {
return "varargs: $x $y ($args)"
}
method nomagic {args x} {
return "nomagic: $args $x"
}
method clash {x bang boom} {
return "clash: $x $bang $boom"
}
method clash_time {x bang boom} {
time {set result "clash_time: $x $bang $boom"} 1
return $result
}
proc crash {x bang boom} {
return "crash: $x $bang $boom"
}
proc crash_time {x bang boom} {
time {set result "crash_time: $x $bang $boom"} 1
return $result
}
variable bang "ok"
common boom "no-problem"
}
} ""
test methods-1.2 {create an object to execute tests} {
test_args ta
} {ta}
test methods-1.3 {argument checking: not enough args} {
list [catch {ta two 1} msg] $msg
} {1 {wrong # args: should be "ta two x y"}}
test methods-1.4a {argument checking: too many args} {
list [catch {ta two 1 2 3} msg] $msg
} {1 {wrong # args: should be "ta two x y"}}
test methods-1.4b {argument checking: too many args} {
list [catch {ta none 1 2 3} msg] $msg
} {1 {wrong # args: should be "ta none"}}
test methods-1.5a {argument checking: just right} {
list [catch {ta two 1 2} msg] $msg
} {0 {two: 1 2}}
test methods-1.5b {argument checking: just right} {
list [catch {ta none} msg] $msg
} {0 none}
test methods-1.6a {default arguments: not enough args} {
list [catch {ta defvals} msg] $msg
} {1 {wrong # args: should be "ta defvals x ?y? ?z?"}}
test methods-1.6b {default arguments: missing arguments supplied} {
list [catch {ta defvals 1} msg] $msg
} {0 {defvals: 1 def1 def2}}
test methods-1.6c {default arguments: missing arguments supplied} {
list [catch {ta defvals 1 2} msg] $msg
} {0 {defvals: 1 2 def2}}
test methods-1.6d {default arguments: all arguments assigned} {
list [catch {ta defvals 1 2 3} msg] $msg
} {0 {defvals: 1 2 3}}
test methods-1.6e {default arguments: too many args} {
list [catch {ta defvals 1 2 3 4} msg] $msg
} {1 {wrong # args: should be "ta defvals x ?y? ?z?"}}
test methods-1.7a {variable arguments: not enough args} {
list [catch {ta varargs} msg] $msg
} {1 {wrong # args: should be "ta varargs x ?y? ?arg arg ...?"}}
test methods-1.7b {variable arguments: empty} {
list [catch {ta varargs 1 2} msg] $msg
} {0 {varargs: 1 2 ()}}
test methods-1.7c {variable arguments: one} {
list [catch {ta varargs 1 2 one} msg] $msg
} {0 {varargs: 1 2 (one)}}
test methods-1.7d {variable arguments: two} {
list [catch {ta varargs 1 2 one two} msg] $msg
} {0 {varargs: 1 2 (one two)}}
test methods-1.8 {magic "args" argument has no magic unless at end of list} {
list [catch {ta nomagic 1 2 3 4} msg] $msg
} {1 {wrong # args: should be "ta nomagic args x"}}
test methods-1.9 {formal args don't clobber class members} {
list [catch {ta clash 1 2 3} msg] $msg \
[ta info variable bang -value] \
[ta info variable boom -value]
} {0 {clash: 1 2 3} ok no-problem}
test methods-1.10 {formal args don't clobber class members} {
list [catch {test_args::crash 4 5 6} msg] $msg \
[ta info variable bang -value] \
[ta info variable boom -value]
} {0 {crash: 4 5 6} ok no-problem}
test methods-1.11 {formal args don't clobber class members, even in "time"} {
list [catch {ta clash_time 7 8 9} msg] $msg \
[ta info variable bang -value] \
[ta info variable boom -value]
} {0 {clash_time: 7 8 9} ok no-problem}
test methods-1.12 {formal args don't clobber class members, even in "time"} {
list [catch {test_args::crash_time a b c} msg] $msg \
[ta info variable bang -value] \
[ta info variable boom -value]
} {0 {crash_time: a b c} ok no-problem}
test methods-2.1 {covers leak condition test for compiled locals, no args} {
for {set i 0} {$i < 100} {incr i} {
::itcl::class LeakClass {
proc leakProc {} { set n 1 }
}
LeakClass::leakProc
::itcl::delete class LeakClass
}
list 0
} 0
test methods-2.2 {covers leak condition test for nested methods calls within eval, bug [8e632ce049]} -setup {
itcl::class C1 {
proc factory {} {
set obj [C1 #auto]
$obj myeval [list $obj read]
itcl::delete object $obj
}
method myeval {script} { eval $script }
method read {} { myeval {} }
}
} -body {
time { C1::factory } 50
list 0
} -result 0 -cleanup {
itcl::delete class C1
}
test methods-2.3 {call of method after object is destroyed inside other methods, SF-bug [c1289b1c32]} -setup {
proc c1test {} {
return c1test
}
itcl::class C1 {
public method m1 {} {
itcl::delete object $this
c1test
}
public method m2 {} {
rename $this {}
c1test
}
public method c1test {} {
return C1::c1test
}
}
} -body {
set result {}
set obj [C1 #auto]
lappend result [catch {$obj m1} v] $v [namespace which -command $obj]
set obj [C1 #auto]
lappend result [catch {$obj m2} v] $v [namespace which -command $obj]
} -match glob -result {1 * {} 1 * {}} -cleanup {
itcl::delete class C1
rename c1test {}
}
# ----------------------------------------------------------------------
# Clean up
# ----------------------------------------------------------------------
itcl::delete class test_args
::tcltest::cleanupTests
return
|