os/persistentdata/persistentstorage/sqlite3api/TEST/TCL/tcldistribution/tests/basic.test
author sl@SLION-WIN7.fritz.box
Fri, 15 Jun 2012 03:10:57 +0200
changeset 0 bde4ae8d615e
permissions -rw-r--r--
First public contribution.
sl@0
     1
# This file contains tests for the tclBasic.c source file. Tests appear in
sl@0
     2
# the same order as the C code that they test. The set of tests is
sl@0
     3
# currently incomplete since it currently includes only new tests for
sl@0
     4
# code changed for the addition of Tcl namespaces. Other variable-
sl@0
     5
# related tests appear in several other test files including
sl@0
     6
# assocd.test, cmdInfo.test, eval.test, expr.test, interp.test,
sl@0
     7
# and trace.test.
sl@0
     8
#
sl@0
     9
# Sourcing this file into Tcl runs the tests and generates output for
sl@0
    10
# errors. No output means no errors were found.
sl@0
    11
#
sl@0
    12
# Copyright (c) 1997 Sun Microsystems, Inc.
sl@0
    13
# Copyright (c) 1998-1999 by Scriptics Corporation.
sl@0
    14
#
sl@0
    15
# See the file "license.terms" for information on usage and redistribution
sl@0
    16
# of this file, and for a DISCLAIMER OF ALL WARRANTIES.
sl@0
    17
#
sl@0
    18
# RCS: @(#) $Id: basic.test,v 1.25.2.7 2005/03/18 16:33:43 dgp Exp $
sl@0
    19
#
sl@0
    20
sl@0
    21
package require tcltest 2
sl@0
    22
namespace import -force ::tcltest::*
sl@0
    23
sl@0
    24
testConstraint testcmdtoken [llength [info commands testcmdtoken]]
sl@0
    25
testConstraint testcmdtrace [llength [info commands testcmdtrace]]
sl@0
    26
testConstraint testcreatecommand [llength [info commands testcreatecommand]]
sl@0
    27
testConstraint testevalex [llength [info commands testevalex]]
sl@0
    28
testConstraint exec [llength [info commands exec]]
sl@0
    29
sl@0
    30
# This variable needs to be changed when the major or minor version number for
sl@0
    31
# Tcl changes.
sl@0
    32
set tclvers 8.4
sl@0
    33
sl@0
    34
catch {namespace delete test_ns_basic}
sl@0
    35
catch {interp delete test_interp}
sl@0
    36
catch {rename p ""}
sl@0
    37
catch {rename q ""}
sl@0
    38
catch {rename cmd ""}
sl@0
    39
catch {unset x}
sl@0
    40
sl@0
    41
test basic-1.1 {Tcl_CreateInterp, creates interp's global namespace} {
sl@0
    42
    catch {interp delete test_interp}
sl@0
    43
    interp create test_interp
sl@0
    44
    interp eval test_interp {
sl@0
    45
        namespace eval test_ns_basic {
sl@0
    46
            proc p {} {
sl@0
    47
                return [namespace current]
sl@0
    48
            }
sl@0
    49
        }
sl@0
    50
    }
sl@0
    51
    list [interp eval test_interp {test_ns_basic::p}] \
sl@0
    52
         [interp delete test_interp]
sl@0
    53
} {::test_ns_basic {}}
sl@0
    54
sl@0
    55
test basic-2.1 {TclHideUnsafeCommands} {emptyTest} {
sl@0
    56
} {}
sl@0
    57
sl@0
    58
test basic-3.1 {Tcl_CallWhenDeleted: see dcall.test} {emptyTest} {
sl@0
    59
} {}
sl@0
    60
sl@0
    61
test basic-4.1 {Tcl_DontCallWhenDeleted: see dcall.test} {emptyTest} {
sl@0
    62
} {}
sl@0
    63
sl@0
    64
test basic-5.1 {Tcl_SetAssocData: see assoc.test} {emptyTest} {
sl@0
    65
} {}
sl@0
    66
sl@0
    67
test basic-6.1 {Tcl_DeleteAssocData: see assoc.test} {emptyTest} {
sl@0
    68
} {}
sl@0
    69
sl@0
    70
test basic-7.1 {Tcl_GetAssocData: see assoc.test} {emptyTest} {
sl@0
    71
} {}
sl@0
    72
sl@0
    73
test basic-8.1 {Tcl_InterpDeleted} {emptyTest} {
sl@0
    74
} {}
sl@0
    75
sl@0
    76
test basic-9.1 {Tcl_DeleteInterp: see interp.test} {emptyTest} {
sl@0
    77
} {}
sl@0
    78
sl@0
    79
test basic-10.1 {DeleteInterpProc, destroys interp's global namespace} {
sl@0
    80
    catch {interp delete test_interp}
sl@0
    81
    interp create test_interp
sl@0
    82
    interp eval test_interp {
sl@0
    83
        namespace eval test_ns_basic {
sl@0
    84
            namespace export p
sl@0
    85
            proc p {} {
sl@0
    86
                return [namespace current]
sl@0
    87
            }
sl@0
    88
        }
sl@0
    89
        namespace eval test_ns_2 {
sl@0
    90
            namespace import ::test_ns_basic::p
sl@0
    91
            variable v 27
sl@0
    92
            proc q {} {
sl@0
    93
                variable v
sl@0
    94
                return "[p] $v"
sl@0
    95
            }
sl@0
    96
        }
sl@0
    97
    }
sl@0
    98
    list [interp eval test_interp {test_ns_2::q}] \
sl@0
    99
         [interp eval test_interp {namespace delete ::}] \
sl@0
   100
         [catch {interp eval test_interp {set a 123}} msg] $msg \
sl@0
   101
         [interp delete test_interp]
sl@0
   102
} {{::test_ns_basic 27} {} 1 {invalid command name "set"} {}}
sl@0
   103
sl@0
   104
test basic-11.1 {HiddenCmdsDeleteProc, invalidate cached refs to deleted hidden cmd} {
sl@0
   105
    catch {interp delete test_interp}
sl@0
   106
    interp create test_interp
sl@0
   107
    interp eval test_interp {
sl@0
   108
        proc p {} {
sl@0
   109
            return 27
sl@0
   110
        }
sl@0
   111
    }
sl@0
   112
    interp alias {} localP test_interp p
sl@0
   113
    list [interp eval test_interp {p}] \
sl@0
   114
         [localP] \
sl@0
   115
         [test_interp hide p] \
sl@0
   116
         [catch {localP} msg] $msg \
sl@0
   117
         [interp delete test_interp] \
sl@0
   118
         [catch {localP} msg] $msg
sl@0
   119
} {27 27 {} 1 {invalid command name "p"} {} 1 {invalid command name "localP"}}
sl@0
   120
sl@0
   121
# NB: More tests about hide/expose are found in interp.test
sl@0
   122
sl@0
   123
test basic-12.1 {Tcl_HideCommand, names of hidden cmds can't have namespace qualifiers} {
sl@0
   124
    catch {interp delete test_interp}
sl@0
   125
    interp create test_interp
sl@0
   126
    interp eval test_interp {
sl@0
   127
        namespace eval test_ns_basic {
sl@0
   128
            proc p {} {
sl@0
   129
                return [namespace current]
sl@0
   130
            }
sl@0
   131
        }
sl@0
   132
    }
sl@0
   133
    list [catch {test_interp hide test_ns_basic::p x} msg] $msg \
sl@0
   134
	 [catch {test_interp hide x test_ns_basic::p} msg1] $msg1 \
sl@0
   135
         [interp delete test_interp]
sl@0
   136
} {1 {can only hide global namespace commands (use rename then hide)} 1 {cannot use namespace qualifiers in hidden command token (rename)} {}}
sl@0
   137
sl@0
   138
test basic-12.2 {Tcl_HideCommand, a hidden cmd remembers its containing namespace} {
sl@0
   139
    catch {namespace delete test_ns_basic}
sl@0
   140
    catch {rename cmd ""}
sl@0
   141
    proc cmd {} {   ;# note that this is global
sl@0
   142
        return [namespace current]
sl@0
   143
    }
sl@0
   144
    namespace eval test_ns_basic {
sl@0
   145
        proc hideCmd {} {
sl@0
   146
            interp hide {} cmd
sl@0
   147
        }
sl@0
   148
        proc exposeCmd {} {
sl@0
   149
            interp expose {} cmd
sl@0
   150
        }
sl@0
   151
        proc callCmd {} {
sl@0
   152
            cmd
sl@0
   153
        }
sl@0
   154
    }
sl@0
   155
    list [test_ns_basic::callCmd] \
sl@0
   156
         [test_ns_basic::hideCmd] \
sl@0
   157
         [catch {cmd} msg] $msg \
sl@0
   158
         [test_ns_basic::exposeCmd] \
sl@0
   159
         [test_ns_basic::callCmd] \
sl@0
   160
         [namespace delete test_ns_basic]
sl@0
   161
} {:: {} 1 {invalid command name "cmd"} {} :: {}}
sl@0
   162
sl@0
   163
test basic-13.1 {Tcl_ExposeCommand, a command stays in the global namespace and can not go to another namespace} {
sl@0
   164
    catch {namespace delete test_ns_basic}
sl@0
   165
    catch {rename cmd ""}
sl@0
   166
    proc cmd {} {   ;# note that this is global
sl@0
   167
        return [namespace current]
sl@0
   168
    }
sl@0
   169
    namespace eval test_ns_basic {
sl@0
   170
        proc hideCmd {} {
sl@0
   171
            interp hide {} cmd
sl@0
   172
        }
sl@0
   173
        proc exposeCmdFailing {} {
sl@0
   174
            interp expose {} cmd ::test_ns_basic::newCmd
sl@0
   175
        }
sl@0
   176
        proc exposeCmdWorkAround {} {
sl@0
   177
            interp expose {} cmd;
sl@0
   178
	    rename cmd ::test_ns_basic::newCmd;
sl@0
   179
        }
sl@0
   180
        proc callCmd {} {
sl@0
   181
            cmd
sl@0
   182
        }
sl@0
   183
    }
sl@0
   184
    list [test_ns_basic::callCmd] \
sl@0
   185
         [test_ns_basic::hideCmd] \
sl@0
   186
         [catch {test_ns_basic::exposeCmdFailing} msg] $msg \
sl@0
   187
         [test_ns_basic::exposeCmdWorkAround] \
sl@0
   188
         [test_ns_basic::newCmd] \
sl@0
   189
         [namespace delete test_ns_basic]
sl@0
   190
} {:: {} 1 {can not expose to a namespace (use expose to toplevel, then rename)} {} ::test_ns_basic {}}
sl@0
   191
test basic-13.2 {Tcl_ExposeCommand, invalidate cached refs to cmd now being exposed} {
sl@0
   192
    catch {rename p ""}
sl@0
   193
    catch {rename cmd ""}
sl@0
   194
    proc p {} {
sl@0
   195
        cmd
sl@0
   196
    }
sl@0
   197
    proc cmd {} {
sl@0
   198
        return 42
sl@0
   199
    }
sl@0
   200
    list [p] \
sl@0
   201
         [interp hide {} cmd] \
sl@0
   202
         [proc cmd {} {return Hello}] \
sl@0
   203
         [cmd] \
sl@0
   204
         [rename cmd ""] \
sl@0
   205
         [interp expose {} cmd] \
sl@0
   206
         [p]
sl@0
   207
} {42 {} {} Hello {} {} 42}
sl@0
   208
sl@0
   209
test basic-14.1 {Tcl_CreateCommand, new cmd goes into a namespace specified in its name, if any} {testcreatecommand} {
sl@0
   210
    catch {eval namespace delete [namespace children :: test_ns_*]}
sl@0
   211
    list [testcreatecommand create] \
sl@0
   212
	 [test_ns_basic::createdcommand] \
sl@0
   213
	 [testcreatecommand delete]
sl@0
   214
} {{} {CreatedCommandProc in ::test_ns_basic} {}}
sl@0
   215
test basic-14.2 {Tcl_CreateCommand, namespace code ignore single ":"s in middle or end of names} {testcreatecommand} {
sl@0
   216
    catch {eval namespace delete [namespace children :: test_ns_*]}
sl@0
   217
    catch {rename value:at: ""}
sl@0
   218
    list [testcreatecommand create2] \
sl@0
   219
	 [value:at:] \
sl@0
   220
	 [testcreatecommand delete2]
sl@0
   221
} {{} {CreatedCommandProc2 in ::} {}}
sl@0
   222
sl@0
   223
test basic-15.1 {Tcl_CreateObjCommand, new cmd goes into a namespace specified in its name, if any} {
sl@0
   224
    catch {eval namespace delete [namespace children :: test_ns_*]}
sl@0
   225
    namespace eval test_ns_basic {}
sl@0
   226
    proc test_ns_basic::cmd {} {  ;# proc requires that ns already exist
sl@0
   227
        return [namespace current]
sl@0
   228
    }
sl@0
   229
    list [test_ns_basic::cmd] \
sl@0
   230
         [namespace delete test_ns_basic]
sl@0
   231
} {::test_ns_basic {}}
sl@0
   232
sl@0
   233
test basic-16.1 {TclInvokeStringCommand} {emptyTest} {
sl@0
   234
} {}
sl@0
   235
sl@0
   236
test basic-17.1 {TclInvokeObjCommand} {emptyTest} {
sl@0
   237
} {}
sl@0
   238
sl@0
   239
test basic-18.1 {TclRenameCommand, name of existing cmd can have namespace qualifiers} {
sl@0
   240
    catch {eval namespace delete [namespace children :: test_ns_*]}
sl@0
   241
    catch {rename cmd ""}
sl@0
   242
    namespace eval test_ns_basic {
sl@0
   243
        proc p {} {
sl@0
   244
            return "p in [namespace current]"
sl@0
   245
        }
sl@0
   246
    }
sl@0
   247
    list [test_ns_basic::p] \
sl@0
   248
         [rename test_ns_basic::p test_ns_basic::q] \
sl@0
   249
         [test_ns_basic::q] 
sl@0
   250
} {{p in ::test_ns_basic} {} {p in ::test_ns_basic}}
sl@0
   251
test basic-18.2 {TclRenameCommand, existing cmd must be found} {
sl@0
   252
    catch {eval namespace delete [namespace children :: test_ns_*]}
sl@0
   253
    list [catch {rename test_ns_basic::p test_ns_basic::q} msg] $msg
sl@0
   254
} {1 {can't rename "test_ns_basic::p": command doesn't exist}}
sl@0
   255
test basic-18.3 {TclRenameCommand, delete cmd if new name is empty} {
sl@0
   256
    catch {eval namespace delete [namespace children :: test_ns_*]}
sl@0
   257
    namespace eval test_ns_basic {
sl@0
   258
        proc p {} {
sl@0
   259
            return "p in [namespace current]"
sl@0
   260
        }
sl@0
   261
    }
sl@0
   262
    list [info commands test_ns_basic::*] \
sl@0
   263
         [rename test_ns_basic::p ""] \
sl@0
   264
         [info commands test_ns_basic::*]
sl@0
   265
} {::test_ns_basic::p {} {}}
sl@0
   266
test basic-18.4 {TclRenameCommand, bad new name} {
sl@0
   267
    catch {eval namespace delete [namespace children :: test_ns_*]}
sl@0
   268
    namespace eval test_ns_basic {
sl@0
   269
        proc p {} {
sl@0
   270
            return "p in [namespace current]"
sl@0
   271
        }
sl@0
   272
    }
sl@0
   273
    rename test_ns_basic::p :::george::martha
sl@0
   274
} {}
sl@0
   275
test basic-18.5 {TclRenameCommand, new name must not already exist} {
sl@0
   276
    namespace eval test_ns_basic {
sl@0
   277
        proc q {} {
sl@0
   278
            return 42
sl@0
   279
        }
sl@0
   280
    }
sl@0
   281
    list [catch {rename test_ns_basic::q :::george::martha} msg] $msg
sl@0
   282
} {1 {can't rename to ":::george::martha": command already exists}}
sl@0
   283
test basic-18.6 {TclRenameCommand, check for command shadowing by newly renamed cmd} {
sl@0
   284
    catch {eval namespace delete [namespace children :: test_ns_*]}
sl@0
   285
    catch {rename p ""}
sl@0
   286
    catch {rename q ""}
sl@0
   287
    proc p {} {
sl@0
   288
        return "p in [namespace current]"
sl@0
   289
    }
sl@0
   290
    proc q {} {
sl@0
   291
        return "q in [namespace current]"
sl@0
   292
    }
sl@0
   293
    namespace eval test_ns_basic {
sl@0
   294
        proc callP {} {
sl@0
   295
            p
sl@0
   296
        }
sl@0
   297
    }
sl@0
   298
    list [test_ns_basic::callP] \
sl@0
   299
         [rename q test_ns_basic::p] \
sl@0
   300
         [test_ns_basic::callP]
sl@0
   301
} {{p in ::} {} {q in ::test_ns_basic}}
sl@0
   302
sl@0
   303
test basic-19.1 {Tcl_SetCommandInfo} {emptyTest} {
sl@0
   304
} {}
sl@0
   305
sl@0
   306
test basic-20.1 {Tcl_GetCommandInfo, names for commands created inside namespaces} {testcmdtoken} {
sl@0
   307
    catch {eval namespace delete [namespace children :: test_ns_*]}
sl@0
   308
    catch {rename p ""}
sl@0
   309
    catch {rename q ""}
sl@0
   310
    catch {unset x}
sl@0
   311
    set x [namespace eval test_ns_basic::test_ns_basic2 {
sl@0
   312
        # the following creates a cmd in the global namespace
sl@0
   313
        testcmdtoken create p
sl@0
   314
    }]
sl@0
   315
    list [testcmdtoken name $x] \
sl@0
   316
         [rename ::p q] \
sl@0
   317
         [testcmdtoken name $x]
sl@0
   318
} {{p ::p} {} {q ::q}}
sl@0
   319
test basic-20.2 {Tcl_GetCommandInfo, names for commands created outside namespaces} {testcmdtoken} {
sl@0
   320
    catch {rename q ""}
sl@0
   321
    set x [testcmdtoken create test_ns_basic::test_ns_basic2::p]
sl@0
   322
    list [testcmdtoken name $x] \
sl@0
   323
         [rename test_ns_basic::test_ns_basic2::p q] \
sl@0
   324
         [testcmdtoken name $x]
sl@0
   325
} {{p ::test_ns_basic::test_ns_basic2::p} {} {q ::q}}
sl@0
   326
sl@0
   327
test basic-21.1 {Tcl_GetCommandName} {emptyTest} {
sl@0
   328
} {}
sl@0
   329
sl@0
   330
test basic-22.1 {Tcl_GetCommandFullName} {
sl@0
   331
    catch {eval namespace delete [namespace children :: test_ns_*]}
sl@0
   332
    namespace eval test_ns_basic1 {
sl@0
   333
        namespace export cmd*
sl@0
   334
        proc cmd1 {} {}
sl@0
   335
        proc cmd2 {} {}
sl@0
   336
    }
sl@0
   337
    namespace eval test_ns_basic2 {
sl@0
   338
        namespace export *
sl@0
   339
        namespace import ::test_ns_basic1::*
sl@0
   340
        proc p {} {}
sl@0
   341
    }
sl@0
   342
    namespace eval test_ns_basic3 {
sl@0
   343
        namespace import ::test_ns_basic2::*
sl@0
   344
        proc q {} {}
sl@0
   345
        list [namespace which -command foreach] \
sl@0
   346
             [namespace which -command q] \
sl@0
   347
             [namespace which -command p] \
sl@0
   348
             [namespace which -command cmd1] \
sl@0
   349
             [namespace which -command ::test_ns_basic2::cmd2]
sl@0
   350
    }
sl@0
   351
} {::foreach ::test_ns_basic3::q ::test_ns_basic3::p ::test_ns_basic3::cmd1 ::test_ns_basic2::cmd2}
sl@0
   352
sl@0
   353
test basic-23.1 {Tcl_DeleteCommand} {emptyTest} {
sl@0
   354
} {}
sl@0
   355
sl@0
   356
test basic-24.1 {Tcl_DeleteCommandFromToken, invalidate all compiled code if cmd has compile proc} {
sl@0
   357
    catch {interp delete test_interp}
sl@0
   358
    catch {unset x}
sl@0
   359
    interp create test_interp
sl@0
   360
    interp eval test_interp {
sl@0
   361
        proc useSet {} {
sl@0
   362
            return [set a 123]
sl@0
   363
        }
sl@0
   364
    }
sl@0
   365
    set x [interp eval test_interp {useSet}]
sl@0
   366
    interp eval test_interp {
sl@0
   367
        rename set ""
sl@0
   368
        proc set {args} {
sl@0
   369
            return "set called with $args"
sl@0
   370
        }
sl@0
   371
    }
sl@0
   372
    list $x \
sl@0
   373
         [interp eval test_interp {useSet}] \
sl@0
   374
         [interp delete test_interp]
sl@0
   375
} {123 {set called with a 123} {}}
sl@0
   376
test basic-24.2 {Tcl_DeleteCommandFromToken, deleting commands changes command epoch} {
sl@0
   377
    catch {eval namespace delete [namespace children :: test_ns_*]}
sl@0
   378
    catch {rename p ""}
sl@0
   379
    proc p {} {
sl@0
   380
        return "global p"
sl@0
   381
    }
sl@0
   382
    namespace eval test_ns_basic {
sl@0
   383
        proc p {} {
sl@0
   384
            return "namespace p"
sl@0
   385
        }
sl@0
   386
        proc callP {} {
sl@0
   387
            p
sl@0
   388
        }
sl@0
   389
    }
sl@0
   390
    list [test_ns_basic::callP] \
sl@0
   391
         [rename test_ns_basic::p ""] \
sl@0
   392
         [test_ns_basic::callP]
sl@0
   393
} {{namespace p} {} {global p}}
sl@0
   394
test basic-24.3 {Tcl_DeleteCommandFromToken, delete imported cmds that refer to a deleted cmd} {
sl@0
   395
    catch {eval namespace delete [namespace children :: test_ns_*]}
sl@0
   396
    catch {rename p ""}
sl@0
   397
    namespace eval test_ns_basic {
sl@0
   398
        namespace export p
sl@0
   399
        proc p {} {return 42}
sl@0
   400
    }
sl@0
   401
    namespace eval test_ns_basic2 {
sl@0
   402
        namespace import ::test_ns_basic::*
sl@0
   403
        proc callP {} {
sl@0
   404
            p
sl@0
   405
        }
sl@0
   406
    }
sl@0
   407
    list [test_ns_basic2::callP] \
sl@0
   408
         [info commands test_ns_basic2::*] \
sl@0
   409
         [rename test_ns_basic::p ""] \
sl@0
   410
         [catch {test_ns_basic2::callP} msg] $msg \
sl@0
   411
         [info commands test_ns_basic2::*]
sl@0
   412
} {42 {::test_ns_basic2::callP ::test_ns_basic2::p} {} 1 {invalid command name "p"} ::test_ns_basic2::callP}
sl@0
   413
sl@0
   414
test basic-25.1 {TclCleanupCommand} {emptyTest} {
sl@0
   415
} {}
sl@0
   416
sl@0
   417
test basic-26.1 {Tcl_EvalObj: preserve object while evaling it} {
sl@0
   418
    # If object isn't preserved, errorInfo would be set to
sl@0
   419
    # "foo\n    while executing\n\"garbage bytes\"" because the object's
sl@0
   420
    # string would have been freed, leaving garbage bytes for the error
sl@0
   421
    # message.
sl@0
   422
sl@0
   423
    proc bgerror {args} {set ::x $::errorInfo}
sl@0
   424
    set fName [makeFile {} test1]
sl@0
   425
    set f [open $fName w]
sl@0
   426
    fileevent $f writable "fileevent $f writable {}; error foo"
sl@0
   427
    set x {}
sl@0
   428
    vwait x
sl@0
   429
    close $f
sl@0
   430
    removeFile test1
sl@0
   431
    rename bgerror {}
sl@0
   432
    set x
sl@0
   433
} "foo\n    while executing\n\"error foo\""
sl@0
   434
sl@0
   435
test basic-26.2 {Tcl_EvalObjEx, pure-list branch: preserve "objv"} {
sl@0
   436
    #
sl@0
   437
    # Follow the pure-list branch in a manner that
sl@0
   438
    #   a - the pure-list internal rep is destroyed by shimmering
sl@0
   439
    #   b - the command returns an error
sl@0
   440
    # As the error code in Tcl_EvalObjv accesses the list elements, this will
sl@0
   441
    # cause a segfault if [Bug 1119369] has not been fixed.
sl@0
   442
    #
sl@0
   443
sl@0
   444
    set SRC [list foo 1] ;# pure-list command 
sl@0
   445
    proc foo str {
sl@0
   446
	# Shimmer pure-list to cmdName, cleanup and error
sl@0
   447
	proc $::SRC {} {}; $::SRC
sl@0
   448
	error "BAD CALL"
sl@0
   449
    }
sl@0
   450
    catch {eval $SRC}
sl@0
   451
} 1
sl@0
   452
sl@0
   453
test basic-27.1 {Tcl_ExprLong} {emptyTest} {
sl@0
   454
} {}
sl@0
   455
sl@0
   456
test basic-28.1 {Tcl_ExprDouble} {emptyTest} {
sl@0
   457
} {}
sl@0
   458
sl@0
   459
test basic-29.1 {Tcl_ExprBoolean} {emptyTest} {
sl@0
   460
} {}
sl@0
   461
sl@0
   462
test basic-30.1 {Tcl_ExprLongObj} {emptyTest} {
sl@0
   463
} {}
sl@0
   464
sl@0
   465
test basic-31.1 {Tcl_ExprDoubleObj} {emptyTest} {
sl@0
   466
} {}
sl@0
   467
sl@0
   468
test basic-32.1 {Tcl_ExprBooleanObj} {emptyTest} {
sl@0
   469
} {}
sl@0
   470
sl@0
   471
test basic-33.1 {TclInvoke} {emptyTest} {
sl@0
   472
} {}
sl@0
   473
sl@0
   474
test basic-34.1 {TclGlobalInvoke} {emptyTest} {
sl@0
   475
} {}
sl@0
   476
sl@0
   477
test basic-35.1 {TclObjInvokeGlobal} {emptyTest} {
sl@0
   478
} {}
sl@0
   479
sl@0
   480
test basic-36.1 {TclObjInvoke, lookup of "unknown" command} {
sl@0
   481
    catch {eval namespace delete [namespace children :: test_ns_*]}
sl@0
   482
    catch {interp delete test_interp}
sl@0
   483
    interp create test_interp
sl@0
   484
    interp eval test_interp {
sl@0
   485
        proc unknown {args} {
sl@0
   486
            return "global unknown"
sl@0
   487
        }
sl@0
   488
        namespace eval test_ns_basic {
sl@0
   489
            proc unknown {args} {
sl@0
   490
                return "namespace unknown"
sl@0
   491
            }
sl@0
   492
        }
sl@0
   493
    }
sl@0
   494
    list [interp alias test_interp newAlias test_interp doesntExist] \
sl@0
   495
         [catch {interp eval test_interp {newAlias}} msg] $msg \
sl@0
   496
         [interp delete test_interp]
sl@0
   497
} {newAlias 0 {global unknown} {}}
sl@0
   498
sl@0
   499
test basic-37.1 {Tcl_ExprString: see expr.test} {emptyTest} {
sl@0
   500
} {}
sl@0
   501
sl@0
   502
test basic-38.1 {Tcl_ExprObj} {emptyTest} {
sl@0
   503
} {}
sl@0
   504
sl@0
   505
test basic-39.1 {Tcl_CreateTrace, correct command and argc/argv arguments of trace proc} {testcmdtrace} {
sl@0
   506
    testcmdtrace tracetest {set stuff [expr 14 + 16]}
sl@0
   507
} {{expr 14 + 16} {expr 14 + 16} {set stuff [expr 14 + 16]} {set stuff 30}}
sl@0
   508
test basic-39.2 {Tcl_CreateTrace, correct command and argc/argv arguments of trace proc} {testcmdtrace} {
sl@0
   509
    testcmdtrace tracetest {set stuff [info tclversion]}
sl@0
   510
} [list {info tclversion} {info tclversion} {set stuff [info tclversion]} "set stuff $tclvers"]
sl@0
   511
test basic-39.3 {Tcl_CreateTrace, correct command and argc/argv arguments of trace proc} {testcmdtrace} {
sl@0
   512
    testcmdtrace deletetest {set stuff [info tclversion]}
sl@0
   513
} $tclvers
sl@0
   514
test basic-39.4 {Tcl_CreateTrace, check that tracing doesn't cause memory faults} {testcmdtrace} {
sl@0
   515
    # Note that the proc call is the same as the variable name, and that
sl@0
   516
    # the call can be direct or indirect by way of another procedure
sl@0
   517
    proc tracer {args} {}
sl@0
   518
    proc tracedLoop {level} {
sl@0
   519
	incr level
sl@0
   520
	tracer
sl@0
   521
	foreach tracer [expr {$level==1 ? {1 2} : {}}] {tracedLoop $level}
sl@0
   522
    }
sl@0
   523
    testcmdtrace tracetest {tracedLoop 0}
sl@0
   524
} {{tracedLoop 0} {tracedLoop 0} {incr level} {incr level} tracer {tracer} {expr {$level==1 ? {1 2} : {}}} {expr {$level==1 ? {1 2} : {}}} {foreach tracer [expr {$level==1 ? {1 2} : {}}] {tracedLoop $level}} {foreach tracer {1 2} {tracedLoop $level}} {tracedLoop $level} {tracedLoop 1} {incr level} {incr level} tracer {tracer} {expr {$level==1 ? {1 2} : {}}} {expr {$level==1 ? {1 2} : {}}} {foreach tracer [expr {$level==1 ? {1 2} : {}}] {tracedLoop $level}} {foreach tracer {} {tracedLoop $level}} {tracedLoop $level} {tracedLoop 1} {incr level} {incr level} tracer {tracer} {expr {$level==1 ? {1 2} : {}}} {expr {$level==1 ? {1 2} : {}}} {foreach tracer [expr {$level==1 ? {1 2} : {}}] {tracedLoop $level}} {foreach tracer {} {tracedLoop $level}}}
sl@0
   525
catch {rename tracer {}}
sl@0
   526
catch {rename tracedLoop {}}
sl@0
   527
sl@0
   528
test basic-39.5 {Tcl_CreateObjTrace, status return TCL_ERROR} {testcmdtrace} {
sl@0
   529
    proc Error { args } { error "Shouldn't get here" }
sl@0
   530
    set x 1;
sl@0
   531
    list [catch {testcmdtrace resulttest {Error $x}} result] [set result]
sl@0
   532
} {1 {Error $x}}
sl@0
   533
sl@0
   534
test basic-39.6 {Tcl_CreateObjTrace, status return TCL_RETURN} {testcmdtrace} {
sl@0
   535
    proc Return { args } { error "Shouldn't get here" }
sl@0
   536
    set x 1;
sl@0
   537
    list [catch {testcmdtrace resulttest {Return $x}} result] [set result]
sl@0
   538
} {2 {}}
sl@0
   539
sl@0
   540
test basic-39.7 {Tcl_CreateObjTrace, status return TCL_BREAK} {testcmdtrace} {
sl@0
   541
    proc Break { args } { error "Shouldn't get here" }
sl@0
   542
    set x 1;
sl@0
   543
    list [catch {testcmdtrace resulttest {Break $x}} result] [set result]
sl@0
   544
} {3 {}}
sl@0
   545
sl@0
   546
test basic-39.8 {Tcl_CreateObjTrace, status return TCL_CONTINUE} {testcmdtrace} {
sl@0
   547
    proc Continue { args } { error "Shouldn't get here" }
sl@0
   548
    set x 1;
sl@0
   549
    list [catch {testcmdtrace resulttest {Continue $x}} result] [set result]
sl@0
   550
} {4 {}}
sl@0
   551
sl@0
   552
test basic-39.9 {Tcl_CreateObjTrace, status return unknown} {testcmdtrace} {
sl@0
   553
    proc OtherStatus { args } { error "Shouldn't get here" }
sl@0
   554
    set x 1;
sl@0
   555
    list [catch {testcmdtrace resulttest {OtherStatus $x}} result] [set result]
sl@0
   556
} {6 {}}
sl@0
   557
sl@0
   558
test basic-39.10 {Tcl_CreateTrace, correct level interpretation} {testcmdtrace} {
sl@0
   559
    proc foo {} {uplevel 1 bar}
sl@0
   560
    proc bar {} {uplevel 1 grok}
sl@0
   561
    proc grok {} {uplevel 1 spock}
sl@0
   562
    proc spock {} {uplevel 1 fascinating}
sl@0
   563
    proc fascinating {} {}
sl@0
   564
    testcmdtrace leveltest {foo}
sl@0
   565
} {foo {foo} {uplevel 1 bar} {uplevel 1 bar} bar {bar} {uplevel 1 grok} {uplevel 1 grok}}
sl@0
   566
sl@0
   567
test basic-40.1 {Tcl_DeleteTrace} {emptyTest} {
sl@0
   568
    # the above tests have tested Tcl_DeleteTrace
sl@0
   569
} {}
sl@0
   570
sl@0
   571
test basic-41.1 {Tcl_AddErrorInfo} {emptyTest} {
sl@0
   572
} {}
sl@0
   573
sl@0
   574
test basic-42.1 {Tcl_AddObjErrorInfo} {emptyTest} {
sl@0
   575
} {}
sl@0
   576
sl@0
   577
test basic-43.1 {Tcl_VarEval} {emptyTest} {
sl@0
   578
} {}
sl@0
   579
sl@0
   580
test basic-44.1 {Tcl_GlobalEval} {emptyTest} {
sl@0
   581
} {}
sl@0
   582
sl@0
   583
test basic-45.1 {Tcl_SetRecursionLimit: see interp.test} {emptyTest} {
sl@0
   584
} {}
sl@0
   585
sl@0
   586
test basic-46.1 {Tcl_AllowExceptions: exception return not allowed} {stdio} {
sl@0
   587
    catch {close $f}
sl@0
   588
    set res [catch {
sl@0
   589
	set f [open |[list [interpreter]] w+]
sl@0
   590
	fconfigure $f -buffering line
sl@0
   591
	puts $f {fconfigure stdout -buffering line}
sl@0
   592
	puts $f continue
sl@0
   593
	puts $f {puts $errorInfo}
sl@0
   594
	puts $f {puts DONE}
sl@0
   595
	set newMsg {}
sl@0
   596
	set msg {}
sl@0
   597
	while {$newMsg != "DONE"} {
sl@0
   598
	    set newMsg [gets $f]
sl@0
   599
	    append msg "${newMsg}\n"
sl@0
   600
	}
sl@0
   601
	close $f
sl@0
   602
    } error]
sl@0
   603
    list $res $msg
sl@0
   604
} {1 {invoked "continue" outside of a loop
sl@0
   605
    while executing
sl@0
   606
"continue"
sl@0
   607
DONE
sl@0
   608
}}
sl@0
   609
sl@0
   610
test basic-46.2 {Tcl_AllowExceptions: exception return not allowed} -setup {
sl@0
   611
    set fName [makeFile {
sl@0
   612
	puts hello
sl@0
   613
	break
sl@0
   614
    } BREAKtest]
sl@0
   615
} -constraints {
sl@0
   616
    exec
sl@0
   617
} -body {
sl@0
   618
    exec [interpreter] $fName
sl@0
   619
} -cleanup {
sl@0
   620
    removeFile BREAKtest
sl@0
   621
} -returnCodes error -match glob -result {hello
sl@0
   622
invoked "break" outside of a loop
sl@0
   623
    while executing
sl@0
   624
"break"
sl@0
   625
    (file "*BREAKtest" line 3)}    
sl@0
   626
sl@0
   627
test basic-46.3 {Tcl_AllowExceptions: exception return not allowed} -setup {
sl@0
   628
    set fName [makeFile {
sl@0
   629
	interp alias {} patch {} info patchlevel
sl@0
   630
	patch
sl@0
   631
	break
sl@0
   632
    } BREAKtest]
sl@0
   633
} -constraints {
sl@0
   634
    exec
sl@0
   635
} -body {
sl@0
   636
    exec [interpreter] $fName
sl@0
   637
} -cleanup {
sl@0
   638
    removeFile BREAKtest
sl@0
   639
} -returnCodes error -match glob -result {invoked "break" outside of a loop
sl@0
   640
    while executing
sl@0
   641
"break"
sl@0
   642
    (file "*BREAKtest" line 4)}    
sl@0
   643
sl@0
   644
test basic-46.4 {Tcl_AllowExceptions: exception return not allowed} -setup {
sl@0
   645
    set fName [makeFile {
sl@0
   646
	foo [set a 1] [break]
sl@0
   647
    } BREAKtest]
sl@0
   648
} -constraints {
sl@0
   649
    exec
sl@0
   650
} -body {
sl@0
   651
    exec [interpreter] $fName
sl@0
   652
} -cleanup {
sl@0
   653
    removeFile BREAKtest
sl@0
   654
} -returnCodes error -match glob -result {invoked "break" outside of a loop
sl@0
   655
    while executing*
sl@0
   656
"foo \[set a 1] \[break]"
sl@0
   657
    (file "*BREAKtest" line 2)}
sl@0
   658
sl@0
   659
test basic-46.5 {Tcl_AllowExceptions: exception return not allowed} -setup {
sl@0
   660
    set fName [makeFile {
sl@0
   661
	return -code return
sl@0
   662
    } BREAKtest]
sl@0
   663
} -constraints {
sl@0
   664
    exec
sl@0
   665
} -body {
sl@0
   666
    exec [interpreter] $fName
sl@0
   667
} -cleanup {
sl@0
   668
    removeFile BREAKtest
sl@0
   669
} -returnCodes error -match glob -result {command returned bad code: 2
sl@0
   670
    while executing
sl@0
   671
"return -code return"
sl@0
   672
    (file "*BREAKtest" line 2)}
sl@0
   673
sl@0
   674
test basic-47.1 {Tcl_EvalEx: check for missing close-bracket} -body {
sl@0
   675
    subst {a[set b [format cd]}
sl@0
   676
} -returnCodes error -result {missing close-bracket}
sl@0
   677
sl@0
   678
test basic-49.1 {Tcl_EvalEx: verify TCL_EVAL_GLOBAL operation} testevalex {
sl@0
   679
    set ::x global
sl@0
   680
    namespace eval ns {
sl@0
   681
        variable x namespace
sl@0
   682
        testevalex {set x changed} global
sl@0
   683
        set ::result [list $::x $x]
sl@0
   684
    } 
sl@0
   685
    namespace delete ns
sl@0
   686
    set ::result
sl@0
   687
} {changed namespace}
sl@0
   688
test basic-49.2 {Tcl_EvalEx: verify TCL_EVAL_GLOBAL operation} testevalex {
sl@0
   689
    set ::x global
sl@0
   690
    namespace eval ns {
sl@0
   691
        variable x namespace
sl@0
   692
        testevalex {set ::context $x} global
sl@0
   693
    }
sl@0
   694
    namespace delete ns
sl@0
   695
    set ::context
sl@0
   696
} {global}
sl@0
   697
sl@0
   698
# cleanup
sl@0
   699
catch {eval namespace delete [namespace children :: test_ns_*]}
sl@0
   700
catch {namespace delete george}
sl@0
   701
catch {interp delete test_interp}
sl@0
   702
catch {rename p ""}
sl@0
   703
catch {rename q ""}
sl@0
   704
catch {rename cmd ""}
sl@0
   705
catch {rename value:at: ""}
sl@0
   706
catch {unset x}
sl@0
   707
::tcltest::cleanupTests
sl@0
   708
return