" Vim script language tests
" Author: Servatius Brandt <Servatius.Brandt@fujitsu-siemens.com>
-" Last Change: 2019 Oct 08
+" Last Change: 2019 Nov 03
"-------------------------------------------------------------------------------
" Test environment {{{1
" END_OF_TEST_ENVIRONMENT - do not change or remove this line.
-" Tests 1 to 15 were moved to test_vimscript.vim
-let Xtest = 16
-
-"-------------------------------------------------------------------------------
-" Test 16: Double :else or :elseif after :else {{{1
-"
-" Multiple :elses or an :elseif after an :else are forbidden.
-"-------------------------------------------------------------------------------
-
-XpathINIT
-
-function! F() abort
- if 0
- Xpath 1 " X: 0
- else
- Xpath 2 " X: 2
- else " aborts function
- Xpath 4 " X: 0
- endif
-endfunction
-
-function! G() abort
- if 0
- Xpath 8 " X: 0
- else
- Xpath 16 " X: 16
- elseif 1 " aborts function
- Xpath 32 " X: 0
- else
- Xpath 64 " X: 0
- endif
-endfunction
-
-function! H() abort
- if 0
- Xpath 128 " X: 0
- elseif 0
- Xpath 256 " X: 0
- else
- Xpath 512 " X: 512
- else " aborts function
- Xpath 1024 " X: 0
- endif
-endfunction
-
-function! I() abort
- if 0
- Xpath 2048 " X: 0
- elseif 0
- Xpath 4096 " X: 0
- else
- Xpath 8192 " X: 8192
- elseif 1 " aborts function
- Xpath 16384 " X: 0
- else
- Xpath 32768 " X: 0
- endif
-endfunction
-
-call F()
-call G()
-call H()
-call I()
-
-delfunction F
-delfunction G
-delfunction H
-delfunction I
-
-Xcheck 8722
-
-
-"-------------------------------------------------------------------------------
-" Test 17: Nesting of unmatched :if or :endif inside a :while {{{1
-"
-" The :while/:endwhile takes precedence in nesting over an unclosed
-" :if or an unopened :endif.
-"-------------------------------------------------------------------------------
-
-XpathINIT
-
-function! MSG(enr, emsg)
- let english = v:lang == "C" || v:lang =~ '^[Ee]n'
- if a:enr == ""
- Xout "TODO: Add message number for:" a:emsg
- let v:errmsg = ":" . v:errmsg
- endif
- let match = 1
- if v:errmsg !~ '^'.a:enr.':' || (english && v:errmsg !~ a:emsg)
- let match = 0
- if v:errmsg == ""
- Xout "Message missing."
- else
- let v:errmsg = escape(v:errmsg, '"')
- Xout "Unexpected message:" v:errmsg
- endif
- endif
- return match
-endfunction
-
-let messages = ""
-
-" While loops inside a function are continued on error.
-function! F()
- let v:errmsg = ""
- XloopINIT 1 16
- let loops = 3
- while loops > 0
- let loops = loops - 1 " 2: 1: 0:
- Xloop 1 " X: 1 + 1*16 + 1*16*16
- if (loops == 1)
- Xloop 2 " X: 2*16
- XloopNEXT
- continue
- elseif (loops == 0)
- Xloop 4 " X: 4*16*16
- break
- elseif 1
- Xloop 8 " X: 8
- XloopNEXT
- " endif missing!
- endwhile " :endwhile after :if 1
- Xpath 4096 " X: 16*16*16
- if MSG('E171', "Missing :endif")
- let g:messages = g:messages . "A"
- endif
-
- let v:errmsg = ""
- XloopINIT! 8192 4
- let loops = 2
- while loops > 0 " 2: 1:
- XloopNEXT
- let loops = loops - 1
- Xloop 1 " X: 8192 + 8192*4
- if 0
- Xloop 2 " X: 0
- " endif missing
- endwhile " :endwhile after :if 0
- Xpath 131072 " X: 8192*4*4
- if MSG('E171', "Missing :endif")
- let g:messages = g:messages . "B"
- endif
-
- let v:errmsg = ""
- XloopINIT 262144 4
- let loops = 2
- while loops > 0 " 2: 1:
- let loops = loops - 1
- Xloop 1 " X: 262144 + 262144 * 4
- " if missing!
- endif " :endif without :if in while
- Xloop 2 " X: 524288 + 524288 * 4
- XloopNEXT
- endwhile
- Xpath 4194304 " X: 262144*4*4
- if MSG('E580', ":endif without :if")
- let g:messages = g:messages . "C"
- endif
-endfunction
-
-call F()
-
-" Error continuation outside a function is at the outermost :endwhile or :endif.
-let v:errmsg = ""
-XloopINIT! 8388608 4
-let loops = 2
-while loops > 0 " 2: 1:
- XloopNEXT
- let loops = loops - 1
- Xloop 1 " X: 8388608 + 0 * 4
- if 0
- Xloop 2 " X: 0
- " endif missing! Following :endwhile fails.
-endwhile | Xpath 134217728 " X: 0
-Xpath 268435456 " X: 2*8388608*4*4
-if MSG('E171', "Missing :endif")
- let messages = g:messages . "D"
-endif
-
-if messages != "ABCD"
- Xpath 536870912 " X: 0
- Xout "messages is" messages "instead of ABCD"
-endif
-
-unlet loops messages
-delfunction F
-delfunction MSG
-
-Xcheck 285127993
-
+" Tests 1 to 17 were moved to test_vimscript.vim
+let Xtest = 18
"-------------------------------------------------------------------------------
" Test 18: Interrupt (Ctrl-C pressed) {{{1
Xcheck 41
-
-"-------------------------------------------------------------------------------
-" Test 25: Executing :finally clauses on normal control flow {{{1
-"
-" Control flow in a :try conditional should always fall through to its
-" :finally clause. A :finally clause of a :try conditional inside an
-" inactive conditional should never be executed.
-"-------------------------------------------------------------------------------
-
-XpathINIT
-
-function! F()
- let loops = 3
- XloopINIT 1 256
- while loops > 0 " 3: 2: 1:
- Xloop 1 " X: 1 + 1*256 + 1*256*256
- if loops >= 2
- try
- Xloop 2 " X: 2 + 2*256
- if loops == 2
- try
- Xloop 4 " X: 4*256
- finally
- Xloop 8 " X: 8*256
- endtry
- endif
- finally
- Xloop 16 " X: 16 + 16*256
- if loops == 2
- try
- Xloop 32 " X: 32*256
- finally
- Xloop 64 " X: 64*256
- endtry
- endif
- endtry
- endif
- Xloop 128 " X: 128 + 128*256 + 128*256*256
- let loops = loops - 1
- XloopNEXT
- endwhile
- Xpath 16777216 " X: 16777216
-endfunction
-
-if 1
- try
- Xpath 33554432 " X: 33554432
- call F()
- Xpath 67108864 " X: 67108864
- finally
- Xpath 134217728 " X: 134217728
- endtry
-else
- try
- Xpath 268435456 " X: 0
- finally
- Xpath 536870912 " X: 0
- endtry
-endif
-
-delfunction F
-
-Xcheck 260177811
-
-
-"-------------------------------------------------------------------------------
-" Test 26: Executing :finally clauses after :continue or :break {{{1
-"
-" For a :continue or :break dynamically enclosed in a :try/:endtry
-" region inside the next surrounding :while/:endwhile, if the
-" :continue/:break is before the :finally, the :finally clause is
-" executed first. If the :continue/:break is after the :finally, the
-" :finally clause is broken (like an :if/:endif region).
-"-------------------------------------------------------------------------------
-
-XpathINIT
-
-try
- let loops = 3
- XloopINIT! 1 32
- while loops > 0
- XloopNEXT
- try
- try
- if loops == 2 " 3: 2: 1:
- Xloop 1 " X: 1*32
- let loops = loops - 1
- continue
- elseif loops == 1
- Xloop 2 " X: 2*32*32
- break
- finish
- endif
- Xloop 4 " X: 4
- endtry
- finally
- Xloop 8 " X: 8 + 8*32 + 8*32*32
- endtry
- Xloop 16 " X: 16
- let loops = loops - 1
- endwhile
- Xpath 32768 " X: 32768
-finally
- Xpath 65536 " X: 65536
- let loops = 3
- XloopINIT 131072 16
- while loops > 0
- try
- finally
- try
- if loops == 2
- Xloop 1 " X: 131072*16
- let loops = loops - 1
- XloopNEXT
- continue
- elseif loops == 1
- Xloop 2 " X: 131072*2*16*16
- break
- finish
- endif
- endtry
- Xloop 4 " X: 131072*4
- endtry
- Xloop 8 " X: 131072*8
- let loops = loops - 1
- XloopNEXT
- endwhile
- Xpath 536870912 " X: 536870912
-endtry
-Xpath 1073741824 " X: 1073741824
-
-unlet loops
-
-Xcheck 1681500476
+" Tests 25 and 26 were moved to test_trycatch.vim
+let Xtest = 27
"-------------------------------------------------------------------------------
Xcheck 190905173
+" Tests 32 and 33 were moved to test_trycatch.vim
+let Xtest = 34
+
"-------------------------------------------------------------------------------
-" Test 32: Remembering the :return value on :finally {{{1
+" Test 34: :finally reason discarded by :continue {{{1
"
-" If a :finally clause is executed due to a :return specifying
-" a value, this is the value visible to the caller if not overwritten
-" by a new :return in the :finally clause. A :return without a value
-" in the :finally clause overwrites with value 0.
+" When a :finally clause is executed due to a :continue, :break,
+" :return, :finish, error, interrupt or :throw, the jump reason is
+" discarded by a :continue in the finally clause.
"-------------------------------------------------------------------------------
XpathINIT
-function! F()
+if ExtraVim()
+
+ XloopINIT! 1 8
+
+ function! C(jump)
+ XloopNEXT
+ let loop = 0
+ while loop < 2
+ let loop = loop + 1
+ if loop == 1
+ try
+ if a:jump == "continue"
+ continue
+ elseif a:jump == "break"
+ break
+ elseif a:jump == "return" || a:jump == "finish"
+ return
+ elseif a:jump == "error"
+ asdf
+ elseif a:jump == "interrupt"
+ "INTERRUPT
+ let dummy = 0
+ elseif a:jump == "throw"
+ throw "abc"
+ endif
+ finally
+ continue " discards jump that caused the :finally
+ Xloop 1 " X: 0
+ endtry
+ Xloop 2 " X: 0
+ elseif loop == 2
+ Xloop 4 " X: 4*(1+8+64+512+4096+32768+262144)
+ endif
+ endwhile
+ endfunction
+
+ call C("continue")
+ Xpath 2097152 " X: 2097152
+ call C("break")
+ Xpath 4194304 " X: 4194304
+ call C("return")
+ Xpath 8388608 " X: 8388608
+ let g:jump = "finish"
+ ExecAsScript C
+ unlet g:jump
+ Xpath 16777216 " X: 16777216
try
- Xpath 1 " X: 1
+ call C("error")
+ Xpath 33554432 " X: 33554432
+ finally
+ Xpath 67108864 " X: 67108864
try
- Xpath 2 " X: 2
- return "ABCD"
- Xpath 4 " X: 0
+ call C("interrupt")
+ Xpath 134217728 " X: 134217728
finally
- Xpath 8 " X: 8
- endtry
- Xpath 16 " X: 0
- finally
- Xpath 32 " X: 32
- endtry
- Xpath 64 " X: 0
-endfunction
-
-function! G()
- try
- Xpath 128 " X: 128
- return 8
- Xpath 256 " X: 0
- finally
- Xpath 512 " X: 512
- return 16 + strlen(F())
- Xpath 1024 " X: 0
- endtry
- Xpath 2048 " X: 0
-endfunction
-
-function! H()
- try
- Xpath 4096 " X: 4096
- return 32
- Xpath 8192 " X: 0
- finally
- Xpath 16384 " X: 16384
- return
- Xpath 32768 " X: 0
- endtry
- Xpath 65536 " X: 0
-endfunction
-
-function! I()
- try
- Xpath 131072 " X: 131072
- finally
- Xpath 262144 " X: 262144
- return G() + H() + 64
- Xpath 524288 " X: 0
- endtry
- Xpath 1048576 " X: 0
-endfunction
-
-let retcode = I()
-Xpath 2097152 " X: 2097152
-
-if retcode < 0
- Xpath 4194304 " X: 0
-endif
-if retcode % 4
- Xpath 8388608 " X: 0
-endif
-if (retcode/4) % 2
- Xpath 16777216 " X: 16777216
-endif
-if (retcode/8) % 2
- Xpath 33554432 " X: 0
-endif
-if (retcode/16) % 2
- Xpath 67108864 " X: 67108864
-endif
-if (retcode/32) % 2
- Xpath 134217728 " X: 0
-endif
-if (retcode/64) % 2
- Xpath 268435456 " X: 268435456
-endif
-if retcode/128
- Xpath 536870912 " X: 0
-endif
-
-unlet retcode
-delfunction F
-delfunction G
-delfunction H
-delfunction I
-
-Xcheck 354833067
-
-
-"-------------------------------------------------------------------------------
-" Test 33: :return under :execute or user command and :finally {{{1
-"
-" A :return command may be executed under an ":execute" or from
-" a user command. Executing of :finally clauses and passing through
-" the return code works also then.
-"-------------------------------------------------------------------------------
-XpathINIT
-
-command! -nargs=? RETURN
- \ try | return <args> | finally | return <args> * 2 | endtry
-
-function! F()
- try
- RETURN 8
- Xpath 1 " X: 0
- finally
- Xpath 2 " X: 2
- endtry
- Xpath 4 " X: 0
-endfunction
-
-function! G()
- try
- RETURN 32
- Xpath 8 " X: 0
- finally
- Xpath 16 " X: 16
- RETURN 128
- Xpath 32 " X: 0
- endtry
- Xpath 64 " X: 0
-endfunction
-
-function! H()
- try
- execute "try | return 512 | finally | return 1024 | endtry"
- Xpath 128 " X: 0
- finally
- Xpath 256 " X: 256
- endtry
- Xpath 512 " X: 0
-endfunction
-
-function! I()
- try
- execute "try | return 2048 | finally | return 4096 | endtry"
- Xpath 1024 " X: 0
- finally
- Xpath 2048 " X: 2048
- execute "try | return 8192 | finally | return 16384 | endtry"
- Xpath 4096 " X: 0
- endtry
- Xpath 8192 " X: 0
-endfunction
-
-function! J()
- try
- RETURN 32768
- Xpath 16384 " X: 0
- finally
- Xpath 32768 " X: 32768
- return
- Xpath 65536 " X: 0
- endtry
- Xpath 131072 " X: 0
-endfunction
-
-function! K()
- try
- execute "try | return 131072 | finally | return 262144 | endtry"
- Xpath 262144 " X: 0
- finally
- Xpath 524288 " X: 524288
- execute "try | return 524288 | finally | return | endtry"
- Xpath 1048576 " X: 0
- endtry
- Xpath 2097152 " X: 0
-endfunction
-
-function! L()
- try
- return
- Xpath 4194304 " X: 0
- finally
- Xpath 8388608 " X: 8388608
- RETURN 1048576
- Xpath 16777216 " X: 0
- endtry
- Xpath 33554432 " X: 0
-endfunction
-
-function! M()
- try
- return
- Xpath 67108864 " X: 0
- finally
- Xpath 134217728 " X: 134217728
- execute "try | return 4194304 | finally | return 8388608 | endtry"
- Xpath 268435456 " X: 0
- endtry
- Xpath 536870912 " X: 0
-endfunction
-
-function! N()
- RETURN 16777216
-endfunction
-
-function! O()
- execute "try | return 67108864 | finally | return 134217728 | endtry"
-endfunction
-
-let sum = F() + G() + H() + I() + J() + K() + L() + M()
-let expected = 16 + 256 + 1024 + 16384 + 0 + 0 + 2097152 + 8388608
-let sum = sum + N() + O()
-let expected = expected + 33554432 + 134217728
-
-if sum == expected
- Xout "sum = " . sum . " (ok)"
-else
- Xout "sum = " . sum . ", expected: " . expected
-endif
-
-Xpath 1073741824 " X: 1073741824
-
-if sum != expected
- " The Xpath command does not accept 2^31 (negative); add explicitly:
- let Xpath = Xpath + 2147483648 " X: 0
-endif
-
-unlet sum expected
-delfunction F
-delfunction G
-delfunction H
-delfunction I
-delfunction J
-delfunction K
-delfunction L
-delfunction M
-delfunction N
-delfunction O
-
-Xcheck 1216907538
-
-
-"-------------------------------------------------------------------------------
-" Test 34: :finally reason discarded by :continue {{{1
-"
-" When a :finally clause is executed due to a :continue, :break,
-" :return, :finish, error, interrupt or :throw, the jump reason is
-" discarded by a :continue in the finally clause.
-"-------------------------------------------------------------------------------
-
-XpathINIT
-
-if ExtraVim()
-
- XloopINIT! 1 8
-
- function! C(jump)
- XloopNEXT
- let loop = 0
- while loop < 2
- let loop = loop + 1
- if loop == 1
- try
- if a:jump == "continue"
- continue
- elseif a:jump == "break"
- break
- elseif a:jump == "return" || a:jump == "finish"
- return
- elseif a:jump == "error"
- asdf
- elseif a:jump == "interrupt"
- "INTERRUPT
- let dummy = 0
- elseif a:jump == "throw"
- throw "abc"
- endif
- finally
- continue " discards jump that caused the :finally
- Xloop 1 " X: 0
- endtry
- Xloop 2 " X: 0
- elseif loop == 2
- Xloop 4 " X: 4*(1+8+64+512+4096+32768+262144)
- endif
- endwhile
- endfunction
-
- call C("continue")
- Xpath 2097152 " X: 2097152
- call C("break")
- Xpath 4194304 " X: 4194304
- call C("return")
- Xpath 8388608 " X: 8388608
- let g:jump = "finish"
- ExecAsScript C
- unlet g:jump
- Xpath 16777216 " X: 16777216
- try
- call C("error")
- Xpath 33554432 " X: 33554432
- finally
- Xpath 67108864 " X: 67108864
- try
- call C("interrupt")
- Xpath 134217728 " X: 134217728
- finally
- Xpath 268435456 " X: 268435456
- call C("throw")
- Xpath 536870912 " X: 536870912
+ Xpath 268435456 " X: 268435456
+ call C("throw")
+ Xpath 536870912 " X: 536870912
endtry
endtry
Xpath 1073741824 " X: 1073741824
Xcheck 357908480
+" Tests 41 to 48 were moved to test_trycatch.vim
+let Xtest = 49
+
"-------------------------------------------------------------------------------
-" Test 41: Skipped :throw finding next command {{{1
+" Test 49: Throwing exceptions across functions {{{1
"
-" A :throw in an inactive conditional must not hide a following
-" command.
+" When an exception is thrown but not caught inside a function, the
+" caller is checked for a matching :catch clause.
"-------------------------------------------------------------------------------
XpathINIT
-function! F()
- Xpath 1 " X: 1
- if 0 | throw "never" | endif | Xpath 2 " X: 2
- Xpath 4 " X: 4
-endfunction
-
-function! G()
- Xpath 8 " X: 8
- while 0 | throw "never" | endwhile | Xpath 16 " X: 16
- Xpath 32 " X: 32
-endfunction
-
-function H()
- Xpath 64 " X: 64
- if 0 | try | throw "never" | endtry | endif | Xpath 128 " X: 128
- Xpath 256 " X: 256
+function! C()
+ try
+ Xpath 1 " X: 1
+ throw "arrgh"
+ Xpath 2 " X: 0
+ catch /arrgh/
+ Xpath 4 " X: 4
+ endtry
+ Xpath 8 " X: 8
endfunction
-Xpath 512 " X: 512
+XloopINIT! 16 16
-try
- Xpath 1024 " X: 1024
- call F()
- Xpath 2048 " X: 2048
-catch /.*/
- Xpath 4096 " X: 0
- Xout v:exception "in" v:throwpoint
-endtry
+function! T1()
+ XloopNEXT
+ try
+ Xloop 1 " X: 16 + 16*16
+ throw "arrgh"
+ Xloop 2 " X: 0
+ finally
+ Xloop 4 " X: 64 + 64*16
+ endtry
+ Xloop 8 " X: 0
+endfunction
-Xpath 8192 " X: 8192
+function! T2()
+ try
+ Xpath 4096 " X: 4096
+ call T1()
+ Xpath 8192 " X: 0
+ finally
+ Xpath 16384 " X: 16384
+ endtry
+ Xpath 32768 " X: 0
+endfunction
try
- Xpath 16384 " X: 16384
- call G()
- Xpath 32768 " X: 32768
+ Xpath 65536 " X: 65536
+ call C() " throw and catch
+ Xpath 131072 " X: 131072
catch /.*/
- Xpath 65536 " X: 0
+ Xpath 262144 " X: 0
Xout v:exception "in" v:throwpoint
endtry
-Xpath 131072 " X: 131072
-
try
- Xpath 262144 " X: 262144
- call H()
Xpath 524288 " X: 524288
-catch /.*/
+ call T1() " throw, one level
Xpath 1048576 " X: 0
+catch /arrgh/
+ Xpath 2097152 " X: 2097152
+catch /.*/
+ Xpath 4194304 " X: 0
Xout v:exception "in" v:throwpoint
endtry
-Xpath 2097152 " X: 2097152
+try
+ Xpath 8388608 " X: 8388608
+ call T2() " throw, two levels
+ Xpath 16777216 " X: 0
+catch /arrgh/
+ Xpath 33554432 " X: 33554432
+catch /.*/
+ Xpath 67108864 " X: 0
+ Xout v:exception "in" v:throwpoint
+endtry
+Xpath 134217728 " X: 134217728
-delfunction F
-delfunction G
-delfunction H
+Xcheck 179000669
-Xcheck 3076095
+" Leave C, T1, and T2 for execution as scripts in the next test.
"-------------------------------------------------------------------------------
-" Test 42: Catching number and string exceptions {{{1
+" Test 50: Throwing exceptions across script files {{{1
+"
+" When an exception is thrown but not caught inside a script file,
+" the sourcing script or function is checked for a matching :catch
+" clause.
"
-" When a number is thrown, it is converted to a string exception.
-" Numbers and strings may be caught by specifying a regular exception
-" as argument to the :catch command.
+" This test executes the bodies of the functions C, T1, and T2 from
+" the previous test as script files (:return replaced by :finish).
"-------------------------------------------------------------------------------
XpathINIT
-try
-
- try
- Xpath 1 " X: 1
- throw 4711
- Xpath 2 " X: 0
- catch /4711/
- Xpath 4 " X: 4
- endtry
-
- try
- Xpath 8 " X: 8
- throw 4711
- Xpath 16 " X: 0
- catch /^4711$/
- Xpath 32 " X: 32
- endtry
+let scriptC = MakeScript("C") " X: 1 + 4 + 8
+delfunction C
- try
- Xpath 64 " X: 64
- throw 4711
- Xpath 128 " X: 0
- catch /\d/
- Xpath 256 " X: 256
- endtry
+XloopINIT! 16 16
- try
- Xpath 512 " X: 512
- throw 4711
- Xpath 1024 " X: 0
- catch /^\d\+$/
- Xpath 2048 " X: 2048
- endtry
+let scriptT1 = MakeScript("T1") " X: 16 + 64 + 16*16 + 64*16
+delfunction T1
- try
- Xpath 4096 " X: 4096
- throw "arrgh"
- Xpath 8192 " X: 0
- catch /arrgh/
- Xpath 16384 " X: 16384
- endtry
+let scriptT2 = MakeScript("T2", scriptT1) " X: 4096 + 16384
+delfunction T2
+function! F()
try
- Xpath 32768 " X: 32768
- throw "arrgh"
- Xpath 65536 " X: 0
- catch /^arrgh$/
+ Xpath 65536 " X: 65536
+ exec "source" g:scriptC
Xpath 131072 " X: 131072
+ catch /.*/
+ Xpath 262144 " X: 0
+ Xout v:exception "in" v:throwpoint
endtry
try
- Xpath 262144 " X: 262144
- throw "arrgh"
- Xpath 524288 " X: 0
- catch /\l/
- Xpath 1048576 " X: 1048576
- endtry
-
- try
+ Xpath 524288 " X: 524288
+ exec "source" g:scriptT1
+ Xpath 1048576 " X: 0
+ catch /arrgh/
Xpath 2097152 " X: 2097152
- throw "arrgh"
+ catch /.*/
Xpath 4194304 " X: 0
- catch /^\l\+$/
- Xpath 8388608 " X: 8388608
- endtry
-
- try
- try
- Xpath 16777216 " X: 16777216
- throw "ARRGH"
- Xpath 33554432 " X: 0
- catch /^arrgh$/
- Xpath 67108864 " X: 0
- endtry
- catch /^\carrgh$/
- Xpath 134217728 " X: 134217728
- endtry
-
- try
- Xpath 268435456 " X: 268435456
- throw ""
- Xpath 536870912 " X: 0
- catch /^$/
- Xpath 1073741824 " X: 1073741824
+ Xout v:exception "in" v:throwpoint
endtry
+endfunction
+try
+ Xpath 8388608 " X: 8388608
+ call F()
+ Xpath 16777216 " X: 16777216
+ exec "source" scriptT2
+ Xpath 33554432 " X: 0
+catch /arrgh/
+ Xpath 67108864 " X: 67108864
catch /.*/
- " The Xpath command does not accept 2^31 (negative); add explicitly:
- let Xpath = Xpath + 2147483648 " X: 0
+ Xpath 134217728 " X: 0
Xout v:exception "in" v:throwpoint
endtry
+Xpath 268435456 " X: 268435456
+
+call delete(scriptC)
+call delete(scriptT1)
+call delete(scriptT2)
+unlet scriptC scriptT1 scriptT2
+delfunction F
+
+Xcheck 363550045
-Xcheck 1505155949
+" Test 51 was moved to test_trycatch.vim
+let Xtest = 52
"-------------------------------------------------------------------------------
-" Test 43: Selecting the correct :catch clause {{{1
+" Test 52: Uncaught exceptions {{{1
"
-" When an exception is thrown and there are multiple :catch clauses,
-" the first matching one is taken.
+" When an exception is thrown but not caught, an error message is
+" displayed when the script is terminated. In case of an interrupt
+" or error exception, the normal interrupt or error message(s) are
+" displayed.
"-------------------------------------------------------------------------------
XpathINIT
-XloopINIT 1 1024
-let loops = 3
-while loops > 0
+let msgfile = tempname()
+
+function! MESSAGES(...)
try
- if loops == 3
- Xloop 1 " X: 1
- throw "a"
- Xloop 2 " X: 0
- elseif loops == 2
- Xloop 4 " X: 4*1024
- throw "ab"
- Xloop 8 " X: 0
- elseif loops == 1
- Xloop 16 " X: 16*1024*1024
- throw "abc"
- Xloop 32 " X: 0
- endif
- catch /abc/
- Xloop 64 " X: 64*1024*1024
- catch /ab/
- Xloop 128 " X: 128*1024
- catch /.*/
- Xloop 256 " X: 256
- catch /a/
- Xloop 512 " X: 0
+ exec "edit" g:msgfile
+ catch /^Vim(edit):/
+ return 0
endtry
- let loops = loops - 1
- XloopNEXT
-endwhile
-Xpath 1073741824 " X: 1073741824
-
-unlet loops
+ let english = v:lang == "C" || v:lang =~ '^[Ee]n'
+ let match = 1
+ norm gg
-Xcheck 1157763329
+ let num = a:0 / 2
+ let cnt = 1
+ while cnt <= num
+ let enr = a:{2*cnt - 1}
+ let emsg= a:{2*cnt}
+ let cnt = cnt + 1
+ if enr == ""
+ Xout "TODO: Add message number for:" emsg
+ elseif enr == "INT"
+ let enr = ""
+ endif
+ if enr == "" && !english
+ continue
+ endif
+ let pattern = (enr != "") ? enr . ':.*' : ''
+ if english
+ let pattern = pattern . emsg
+ endif
+ if !search(pattern, "W")
+ let match = 0
+ Xout "No match for:" pattern
+ endif
+ norm $
+ endwhile
-"-------------------------------------------------------------------------------
-" Test 44: Missing or empty :catch patterns {{{1
-"
-" A missing or empty :catch pattern means the same as /.*/, that is,
-" catches everything. To catch only empty exceptions, /^$/ must be
-" used. A :catch with missing, empty, or /.*/ argument also works
-" when followed by another command separated by a bar on the same
-" line. :catch patterns cannot be specified between ||. But other
-" pattern separators can be used instead of //.
-"-------------------------------------------------------------------------------
+ bwipeout!
+ return match
+endfunction
-XpathINIT
+if ExtraVim(msgfile)
+ Xpath 1 " X: 1
+ throw "arrgh"
+endif
-try
- try
- Xpath 1 " X: 1
- throw ""
- catch /^$/
- Xpath 2 " X: 2
- endtry
+Xpath 2 " X: 2
+if !MESSAGES('E605', "Exception not caught")
+ Xpath 4 " X: 0
+endif
+if ExtraVim(msgfile)
try
- Xpath 4 " X: 4
- throw ""
- catch /.*/
Xpath 8 " X: 8
+ throw "oops"
+ catch /arrgh/
+ Xpath 16 " X: 0
endtry
+ Xpath 32 " X: 0
+endif
- try
- Xpath 16 " X: 16
- throw ""
- catch //
- Xpath 32 " X: 32
- endtry
+Xpath 64 " X: 64
+if !MESSAGES('E605', "Exception not caught")
+ Xpath 128 " X: 0
+endif
- try
- Xpath 64 " X: 64
- throw ""
- catch
- Xpath 128 " X: 128
- endtry
+if ExtraVim(msgfile)
+ function! T()
+ throw "brrr"
+ endfunction
try
Xpath 256 " X: 256
- throw "oops"
- catch /^$/
- Xpath 512 " X: 0
+ throw "arrgh"
catch /.*/
- Xpath 1024 " X: 1024
+ Xpath 512 " X: 512
+ call T()
endtry
+ Xpath 1024 " X: 0
+endif
- try
- Xpath 2048 " X: 2048
- throw "arrgh"
- catch /^$/
- Xpath 4096 " X: 0
- catch //
- Xpath 8192 " X: 8192
- endtry
+Xpath 2048 " X: 2048
+if !MESSAGES('E605', "Exception not caught")
+ Xpath 4096 " X: 0
+endif
+if ExtraVim(msgfile)
try
+ Xpath 8192 " X: 8192
+ throw "arrgh"
+ finally
Xpath 16384 " X: 16384
throw "brrr"
- catch /^$/
- Xpath 32768 " X: 0
- catch
- Xpath 65536 " X: 65536
endtry
+ Xpath 32768 " X: 0
+endif
- try | Xpath 131072 | throw "x" | catch /.*/ | Xpath 262144 | endtry
- " X: 131072 + 262144
+Xpath 65536 " X: 65536
+if !MESSAGES('E605', "Exception not caught")
+ Xpath 131072 " X: 0
+endif
- try | Xpath 524288 | throw "y" | catch // | Xpath 1048576 | endtry
- " X: 524288 + 1048576
+if ExtraVim(msgfile)
+ try
+ Xpath 262144 " X: 262144
+ "INTERRUPT
+ endtry
+ Xpath 524288 " X: 0
+endif
- while 1
- try
- let caught = 0
- let v:errmsg = ""
- " Extra try level: if ":catch" without arguments below raises
- " a syntax error because it misinterprets the "Xpath" as a pattern,
- " let it be caught by the ":catch /.*/" below.
- try
- try | Xpath 2097152 | throw "z" | catch | Xpath 4194304 | :
- endtry " X: 2097152 + 4194304
- endtry
- catch /.*/
- let caught = 1
- Xout v:exception "in" v:throwpoint
- finally
- if $VIMNOERRTHROW && v:errmsg != ""
- Xout v:errmsg
- endif
- if caught || $VIMNOERRTHROW && v:errmsg != ""
- Xpath 8388608 " X: 0
- endif
- break " discard error for $VIMNOERRTHROW
- endtry
- endwhile
+Xpath 1048576 " X: 1048576
+if !MESSAGES('INT', "Interrupted")
+ Xpath 2097152 " X: 0
+endif
- let cologne = 4711
+if ExtraVim(msgfile)
try
- try
- Xpath 16777216 " X: 16777216
- throw "throw cologne"
- " Next lines catches all and throws 4711:
- catch |throw cologne|
- Xpath 33554432 " X: 0
- endtry
- catch /4711/
- Xpath 67108864 " X: 67108864
+ Xpath 4194304 " X: 4194304
+ let x = novar " error E121; exception: E121
+ catch /E15:/ " should not catch
+ Xpath 8388608 " X: 0
endtry
+ Xpath 16777216 " X: 0
+endif
+
+Xpath 33554432 " X: 33554432
+if !MESSAGES('E121', "Undefined variable")
+ Xpath 67108864 " X: 0
+endif
+if ExtraVim(msgfile)
try
Xpath 134217728 " X: 134217728
- throw "plus"
- catch +plus+
- Xpath 268435456 " X: 268435456
+" unlet novar # " error E108/E488; exception: E488
+ catch /E108:/ " should not catch
+ Xpath 268435456 " X: 0
endtry
+ Xpath 536870912 " X: 0
+endif
- Xpath 536870912 " X: 536870912
-catch /.*/
- Xpath 1073741824 " X: 0
- Xout v:exception "in" v:throwpoint
-endtry
+Xpath 1073741824 " X: 1073741824
+if !MESSAGES('E108', "No such variable", 'E488', "Trailing characters")
+ " The Xpath command does not accept 2^31 (negative); add explicitly:
+ let Xpath = Xpath + 2147483648 " X: 0
+endif
-unlet! caught cologne
+call delete(msgfile)
+unlet msgfile
+
+Xcheck 1247112011
-Xcheck 1031761407
+" Leave MESSAGES() for the next tests.
"-------------------------------------------------------------------------------
-" Test 45: Catching exceptions from nested :try blocks {{{1
+" Test 53: Nesting errors: :endif/:else/:elseif {{{1
+"
+" For nesting errors of :if conditionals the correct error messages
+" should be given.
"
-" When :try blocks are nested, an exception is caught by the innermost
-" try conditional that has a matching :catch clause.
+" This test reuses the function MESSAGES() from the previous test.
+" This functions checks the messages in g:msgfile.
"-------------------------------------------------------------------------------
XpathINIT
-XloopINIT 1 1024
-let loops = 3
-while loops > 0
- try
- try
- try
- try
- if loops == 3
- Xloop 1 " X: 1
- throw "a"
- Xloop 2 " X: 0
- elseif loops == 2
- Xloop 4 " X: 4*1024
- throw "ab"
- Xloop 8 " X: 0
- elseif loops == 1
- Xloop 16 " X: 16*1024*1024
- throw "abc"
- Xloop 32 " X: 0
- endif
- catch /abc/
- Xloop 64 " X: 64*1024*1024
- endtry
- catch /ab/
- Xloop 128 " X: 128*1024
- endtry
- catch /.*/
- Xloop 256 " X: 256
- endtry
- catch /a/
- Xloop 512 " X: 0
- endtry
-
- let loops = loops - 1
- XloopNEXT
-endwhile
-Xpath 1073741824 " X: 1073741824
+let msgfile = tempname()
-unlet loops
+if ExtraVim(msgfile)
+" endif
+endif
+if MESSAGES('E580', ":endif without :if")
+ Xpath 1 " X: 1
+endif
-Xcheck 1157763329
+if ExtraVim(msgfile)
+" while 1
+" endif
+" endwhile
+endif
+if MESSAGES('E580', ":endif without :if")
+ Xpath 2 " X: 2
+endif
+if ExtraVim(msgfile)
+" try
+" finally
+" endif
+" endtry
+endif
+if MESSAGES('E580', ":endif without :if")
+ Xpath 4 " X: 4
+endif
-"-------------------------------------------------------------------------------
-" Test 46: Executing :finally after a :throw in nested :try {{{1
-"
-" When an exception is thrown from within nested :try blocks, the
-" :finally clauses of the non-catching try conditionals should be
-" executed before the matching :catch of the next surrounding :try
-" gets the control. If this also has a :finally clause, it is
-" executed afterwards.
-"-------------------------------------------------------------------------------
+if ExtraVim(msgfile)
+" try
+" endif
+" endtry
+endif
+if MESSAGES('E580', ":endif without :if")
+ Xpath 8 " X: 8
+endif
-XpathINIT
+if ExtraVim(msgfile)
+" try
+" throw "a"
+" catch /a/
+" endif
+" endtry
+endif
+if MESSAGES('E580', ":endif without :if")
+ Xpath 16 " X: 16
+endif
-let sum = 0
+if ExtraVim(msgfile)
+" else
+endif
+if MESSAGES('E581', ":else without :if")
+ Xpath 32 " X: 32
+endif
-try
- Xpath 1 " X: 1
- try
- Xpath 2 " X: 2
- try
- Xpath 4 " X: 4
- try
- Xpath 8 " X: 8
- throw "ABC"
- Xpath 16 " X: 0
- catch /xyz/
- Xpath 32 " X: 0
- finally
- Xpath 64 " X: 64
- if sum != 0
- Xpath 128 " X: 0
- endif
- let sum = sum + 1
- endtry
- Xpath 256 " X: 0
- catch /123/
- Xpath 512 " X: 0
- catch /321/
- Xpath 1024 " X: 0
- finally
- Xpath 2048 " X: 2048
- if sum != 1
- Xpath 4096 " X: 0
- endif
- let sum = sum + 2
- endtry
- Xpath 8192 " X: 0
- finally
- Xpath 16384 " X: 16384
- if sum != 3
- Xpath 32768 " X: 0
- endif
- let sum = sum + 4
- endtry
- Xpath 65536 " X: 0
-catch /ABC/
- Xpath 131072 " X: 131072
- if sum != 7
- Xpath 262144 " X: 0
- endif
- let sum = sum + 8
-finally
- Xpath 524288 " X: 524288
- if sum != 15
- Xpath 1048576 " X: 0
- endif
- let sum = sum + 16
-endtry
-Xpath 65536 " X: 65536
-if sum != 31
- Xpath 131072 " X: 0
+if ExtraVim(msgfile)
+" while 1
+" else
+" endwhile
+endif
+if MESSAGES('E581', ":else without :if")
+ Xpath 64 " X: 64
endif
-unlet sum
+if ExtraVim(msgfile)
+" try
+" finally
+" else
+" endtry
+endif
+if MESSAGES('E581', ":else without :if")
+ Xpath 128 " X: 128
+endif
-Xcheck 739407
+if ExtraVim(msgfile)
+" try
+" else
+" endtry
+endif
+if MESSAGES('E581', ":else without :if")
+ Xpath 256 " X: 256
+endif
+if ExtraVim(msgfile)
+" try
+" throw "a"
+" catch /a/
+" else
+" endtry
+endif
+if MESSAGES('E581', ":else without :if")
+ Xpath 512 " X: 512
+endif
-"-------------------------------------------------------------------------------
-" Test 47: Throwing exceptions from a :catch clause {{{1
-"
-" When an exception is thrown from a :catch clause, it should not be
-" caught by a :catch of the same :try conditional. After executing
-" the :finally clause (if present), surrounding try conditionals
-" should be checked for a matching :catch.
-"-------------------------------------------------------------------------------
+if ExtraVim(msgfile)
+" elseif
+endif
+if MESSAGES('E582', ":elseif without :if")
+ Xpath 1024 " X: 1024
+endif
-XpathINIT
+if ExtraVim(msgfile)
+" while 1
+" elseif
+" endwhile
+endif
+if MESSAGES('E582', ":elseif without :if")
+ Xpath 2048 " X: 2048
+endif
-Xpath 1 " X: 1
-try
- Xpath 2 " X: 2
- try
- Xpath 4 " X: 4
- try
- Xpath 8 " X: 8
- throw "x1"
- Xpath 16 " X: 0
- catch /x1/
- Xpath 32 " X: 32
- try
- Xpath 64 " X: 64
- throw "x2"
- Xpath 128 " X: 0
- catch /x1/
- Xpath 256 " X: 0
- catch /x2/
- Xpath 512 " X: 512
- try
- Xpath 1024 " X: 1024
- throw "x3"
- Xpath 2048 " X: 0
- catch /x1/
- Xpath 4096 " X: 0
- catch /x2/
- Xpath 8192 " X: 0
- finally
- Xpath 16384 " X: 16384
- endtry
- Xpath 32768 " X: 0
- catch /x3/
- Xpath 65536 " X: 0
- endtry
- Xpath 131072 " X: 0
- catch /x1/
- Xpath 262144 " X: 0
- catch /x2/
- Xpath 524288 " X: 0
- catch /x3/
- Xpath 1048576 " X: 0
- finally
- Xpath 2097152 " X: 2097152
- endtry
- Xpath 4194304 " X: 0
- catch /x1/
- Xpath 8388608 " X: 0
- catch /x2/
- Xpath 16777216 " X: 0
- catch /x3/
- Xpath 33554432 " X: 33554432
- endtry
- Xpath 67108864 " X: 67108864
-catch /.*/
- Xpath 134217728 " X: 0
- Xout v:exception "in" v:throwpoint
-endtry
-Xpath 268435456 " X: 268435456
-
-Xcheck 371213935
-
-
-"-------------------------------------------------------------------------------
-" Test 48: Throwing exceptions from a :finally clause {{{1
-"
-" When an exception is thrown from a :finally clause, it should not be
-" caught by a :catch of the same :try conditional. Surrounding try
-" conditionals should be checked for a matching :catch. A previously
-" thrown exception is discarded.
-"-------------------------------------------------------------------------------
+if ExtraVim(msgfile)
+" try
+" finally
+" elseif
+" endtry
+endif
+if MESSAGES('E582', ":elseif without :if")
+ Xpath 4096 " X: 4096
+endif
-XpathINIT
+if ExtraVim(msgfile)
+" try
+" elseif
+" endtry
+endif
+if MESSAGES('E582', ":elseif without :if")
+ Xpath 8192 " X: 8192
+endif
-try
+if ExtraVim(msgfile)
+" try
+" throw "a"
+" catch /a/
+" elseif
+" endtry
+endif
+if MESSAGES('E582', ":elseif without :if")
+ Xpath 16384 " X: 16384
+endif
- try
- try
- Xpath 1 " X: 1
- catch /x1/
- Xpath 2 " X: 0
- finally
- Xpath 4 " X: 4
- throw "x1"
- Xpath 8 " X: 0
- endtry
- Xpath 16 " X: 0
- catch /x1/
- Xpath 32 " X: 32
- endtry
- Xpath 64 " X: 64
+if ExtraVim(msgfile)
+" if 1
+" else
+" else
+" endif
+endif
+if MESSAGES('E583', "multiple :else")
+ Xpath 32768 " X: 32768
+endif
- try
- try
- Xpath 128 " X: 128
- throw "x2"
- Xpath 256 " X: 0
- catch /x2/
- Xpath 512 " X: 512
- catch /x3/
- Xpath 1024 " X: 0
- finally
- Xpath 2048 " X: 2048
- throw "x3"
- Xpath 4096 " X: 0
- endtry
- Xpath 8192 " X: 0
- catch /x2/
- Xpath 16384 " X: 0
- catch /x3/
- Xpath 32768 " X: 32768
- endtry
+if ExtraVim(msgfile)
+" if 1
+" else
+" elseif 1
+" endif
+endif
+if MESSAGES('E584', ":elseif after :else")
Xpath 65536 " X: 65536
+endif
- try
- try
- try
- Xpath 131072 " X: 131072
- throw "x4"
- Xpath 262144 " X: 0
- catch /x5/
- Xpath 524288 " X: 0
- finally
- Xpath 1048576 " X: 1048576
- throw "x5" " discards "x4"
- Xpath 2097152 " X: 0
- endtry
- Xpath 4194304 " X: 0
- catch /x4/
- Xpath 8388608 " X: 0
- finally
- Xpath 16777216 " X: 16777216
- endtry
- Xpath 33554432 " X: 0
- catch /x5/
- Xpath 67108864 " X: 67108864
- endtry
- Xpath 134217728 " X: 134217728
+call delete(msgfile)
+unlet msgfile
-catch /.*/
- Xpath 268435456 " X: 0
- Xout v:exception "in" v:throwpoint
-endtry
-Xpath 536870912 " X: 536870912
+Xcheck 131071
-Xcheck 756255461
+" Leave MESSAGES() for the next test.
"-------------------------------------------------------------------------------
-" Test 49: Throwing exceptions across functions {{{1
+" Test 54: Nesting errors: :while/:endwhile {{{1
"
-" When an exception is thrown but not caught inside a function, the
-" caller is checked for a matching :catch clause.
+" For nesting errors of :while conditionals the correct error messages
+" should be given.
+"
+" This test reuses the function MESSAGES() from the previous test.
+" This functions checks the messages in g:msgfile.
"-------------------------------------------------------------------------------
XpathINIT
-function! C()
- try
- Xpath 1 " X: 1
- throw "arrgh"
- Xpath 2 " X: 0
- catch /arrgh/
- Xpath 4 " X: 4
- endtry
- Xpath 8 " X: 8
-endfunction
-
-XloopINIT! 16 16
+let msgfile = tempname()
-function! T1()
- XloopNEXT
- try
- Xloop 1 " X: 16 + 16*16
- throw "arrgh"
- Xloop 2 " X: 0
- finally
- Xloop 4 " X: 64 + 64*16
- endtry
- Xloop 8 " X: 0
-endfunction
+if ExtraVim(msgfile)
+" endwhile
+endif
+if MESSAGES('E588', ":endwhile without :while")
+ Xpath 1 " X: 1
+endif
-function! T2()
- try
- Xpath 4096 " X: 4096
- call T1()
- Xpath 8192 " X: 0
- finally
- Xpath 16384 " X: 16384
- endtry
- Xpath 32768 " X: 0
-endfunction
+if ExtraVim(msgfile)
+" if 1
+" endwhile
+" endif
+endif
+if MESSAGES('E588', ":endwhile without :while")
+ Xpath 2 " X: 2
+endif
-try
- Xpath 65536 " X: 65536
- call C() " throw and catch
- Xpath 131072 " X: 131072
-catch /.*/
- Xpath 262144 " X: 0
- Xout v:exception "in" v:throwpoint
-endtry
+if ExtraVim(msgfile)
+" while 1
+" if 1
+" endwhile
+endif
+if MESSAGES('E171', "Missing :endif")
+ Xpath 4 " X: 4
+endif
-try
- Xpath 524288 " X: 524288
- call T1() " throw, one level
- Xpath 1048576 " X: 0
-catch /arrgh/
- Xpath 2097152 " X: 2097152
-catch /.*/
- Xpath 4194304 " X: 0
- Xout v:exception "in" v:throwpoint
-endtry
+if ExtraVim(msgfile)
+" try
+" finally
+" endwhile
+" endtry
+endif
+if MESSAGES('E588', ":endwhile without :while")
+ Xpath 8 " X: 8
+endif
-try
- Xpath 8388608 " X: 8388608
- call T2() " throw, two levels
- Xpath 16777216 " X: 0
-catch /arrgh/
- Xpath 33554432 " X: 33554432
-catch /.*/
- Xpath 67108864 " X: 0
- Xout v:exception "in" v:throwpoint
-endtry
-Xpath 134217728 " X: 134217728
+if ExtraVim(msgfile)
+" while 1
+" try
+" finally
+" endwhile
+endif
+if MESSAGES('E600', "Missing :endtry")
+ Xpath 16 " X: 16
+endif
-Xcheck 179000669
+if ExtraVim(msgfile)
+" while 1
+" if 1
+" try
+" finally
+" endwhile
+endif
+if MESSAGES('E600', "Missing :endtry")
+ Xpath 32 " X: 32
+endif
-" Leave C, T1, and T2 for execution as scripts in the next test.
+if ExtraVim(msgfile)
+" while 1
+" try
+" finally
+" if 1
+" endwhile
+endif
+if MESSAGES('E171', "Missing :endif")
+ Xpath 64 " X: 64
+endif
+
+if ExtraVim(msgfile)
+" try
+" endwhile
+" endtry
+endif
+if MESSAGES('E588', ":endwhile without :while")
+ Xpath 128 " X: 128
+endif
+
+if ExtraVim(msgfile)
+" while 1
+" try
+" endwhile
+" endtry
+" endwhile
+endif
+if MESSAGES('E588', ":endwhile without :while")
+ Xpath 256 " X: 256
+endif
+
+if ExtraVim(msgfile)
+" try
+" throw "a"
+" catch /a/
+" endwhile
+" endtry
+endif
+if MESSAGES('E588', ":endwhile without :while")
+ Xpath 512 " X: 512
+endif
+
+if ExtraVim(msgfile)
+" while 1
+" try
+" throw "a"
+" catch /a/
+" endwhile
+" endtry
+" endwhile
+endif
+if MESSAGES('E588', ":endwhile without :while")
+ Xpath 1024 " X: 1024
+endif
+
+
+call delete(msgfile)
+unlet msgfile
+
+Xcheck 2047
+
+" Leave MESSAGES() for the next test.
"-------------------------------------------------------------------------------
-" Test 50: Throwing exceptions across script files {{{1
+" Test 55: Nesting errors: :continue/:break {{{1
"
-" When an exception is thrown but not caught inside a script file,
-" the sourcing script or function is checked for a matching :catch
-" clause.
+" For nesting errors of :continue and :break commands the correct
+" error messages should be given.
"
-" This test executes the bodies of the functions C, T1, and T2 from
-" the previous test as script files (:return replaced by :finish).
+" This test reuses the function MESSAGES() from the previous test.
+" This functions checks the messages in g:msgfile.
"-------------------------------------------------------------------------------
XpathINIT
-let scriptC = MakeScript("C") " X: 1 + 4 + 8
-delfunction C
+let msgfile = tempname()
-XloopINIT! 16 16
+if ExtraVim(msgfile)
+" continue
+endif
+if MESSAGES('E586', ":continue without :while")
+ Xpath 1 " X: 1
+endif
-let scriptT1 = MakeScript("T1") " X: 16 + 64 + 16*16 + 64*16
-delfunction T1
+if ExtraVim(msgfile)
+" if 1
+" continue
+" endif
+endif
+if MESSAGES('E586', ":continue without :while")
+ Xpath 2 " X: 2
+endif
-let scriptT2 = MakeScript("T2", scriptT1) " X: 4096 + 16384
-delfunction T2
+if ExtraVim(msgfile)
+" try
+" finally
+" continue
+" endtry
+endif
+if MESSAGES('E586', ":continue without :while")
+ Xpath 4 " X: 4
+endif
-function! F()
- try
- Xpath 65536 " X: 65536
- exec "source" g:scriptC
- Xpath 131072 " X: 131072
- catch /.*/
- Xpath 262144 " X: 0
- Xout v:exception "in" v:throwpoint
- endtry
+if ExtraVim(msgfile)
+" try
+" continue
+" endtry
+endif
+if MESSAGES('E586', ":continue without :while")
+ Xpath 8 " X: 8
+endif
- try
- Xpath 524288 " X: 524288
- exec "source" g:scriptT1
- Xpath 1048576 " X: 0
- catch /arrgh/
- Xpath 2097152 " X: 2097152
- catch /.*/
- Xpath 4194304 " X: 0
- Xout v:exception "in" v:throwpoint
- endtry
-endfunction
+if ExtraVim(msgfile)
+" try
+" throw "a"
+" catch /a/
+" continue
+" endtry
+endif
+if MESSAGES('E586', ":continue without :while")
+ Xpath 16 " X: 16
+endif
-try
- Xpath 8388608 " X: 8388608
- call F()
- Xpath 16777216 " X: 16777216
- exec "source" scriptT2
- Xpath 33554432 " X: 0
-catch /arrgh/
- Xpath 67108864 " X: 67108864
-catch /.*/
- Xpath 134217728 " X: 0
- Xout v:exception "in" v:throwpoint
-endtry
-Xpath 268435456 " X: 268435456
+if ExtraVim(msgfile)
+" break
+endif
+if MESSAGES('E587', ":break without :while")
+ Xpath 32 " X: 32
+endif
-call delete(scriptC)
-call delete(scriptT1)
-call delete(scriptT2)
-unlet scriptC scriptT1 scriptT2
-delfunction F
+if ExtraVim(msgfile)
+" if 1
+" break
+" endif
+endif
+if MESSAGES('E587', ":break without :while")
+ Xpath 64 " X: 64
+endif
-Xcheck 363550045
+if ExtraVim(msgfile)
+" try
+" finally
+" break
+" endtry
+endif
+if MESSAGES('E587', ":break without :while")
+ Xpath 128 " X: 128
+endif
+
+if ExtraVim(msgfile)
+" try
+" break
+" endtry
+endif
+if MESSAGES('E587', ":break without :while")
+ Xpath 256 " X: 256
+endif
+
+if ExtraVim(msgfile)
+" try
+" throw "a"
+" catch /a/
+" break
+" endtry
+endif
+if MESSAGES('E587', ":break without :while")
+ Xpath 512 " X: 512
+endif
+
+call delete(msgfile)
+unlet msgfile
+
+Xcheck 1023
+
+" Leave MESSAGES() for the next test.
"-------------------------------------------------------------------------------
-" Test 51: Throwing exceptions across :execute and user commands {{{1
+" Test 56: Nesting errors: :endtry {{{1
+"
+" For nesting errors of :try conditionals the correct error messages
+" should be given.
"
-" A :throw command may be executed under an ":execute" or from
-" a user command.
+" This test reuses the function MESSAGES() from the previous test.
+" This functions checks the messages in g:msgfile.
"-------------------------------------------------------------------------------
XpathINIT
-command! -nargs=? THROW1 throw <args> | throw 1
-command! -nargs=? THROW2 try | throw <args> | endtry | throw 2
-command! -nargs=? THROW3 try | throw 3 | catch /3/ | throw <args> | endtry
-command! -nargs=? THROW4 try | throw 4 | finally | throw <args> | endtry
+let msgfile = tempname()
-try
+if ExtraVim(msgfile)
+" endtry
+endif
+if MESSAGES('E602', ":endtry without :try")
+ Xpath 1 " X: 1
+endif
- try
- try
- Xpath 1 " X: 1
- THROW1 "A"
- catch /A/
- Xpath 2 " X: 2
- endtry
- catch /1/
- Xpath 4 " X: 0
- endtry
-
- try
- try
- Xpath 8 " X: 8
- THROW2 "B"
- catch /B/
- Xpath 16 " X: 16
- endtry
- catch /2/
- Xpath 32 " X: 0
- endtry
-
- try
- try
- Xpath 64 " X: 64
- THROW3 "C"
- catch /C/
- Xpath 128 " X: 128
- endtry
- catch /3/
- Xpath 256 " X: 0
- endtry
-
- try
- try
- Xpath 512 " X: 512
- THROW4 "D"
- catch /D/
- Xpath 1024 " X: 1024
- endtry
- catch /4/
- Xpath 2048 " X: 0
- endtry
-
- try
- try
- Xpath 4096 " X: 4096
- execute 'throw "E" | throw 5'
- catch /E/
- Xpath 8192 " X: 8192
- endtry
- catch /5/
- Xpath 16384 " X: 0
- endtry
-
- try
- try
- Xpath 32768 " X: 32768
- execute 'try | throw "F" | endtry | throw 6'
- catch /F/
- Xpath 65536 " X: 65536
- endtry
- catch /6/
- Xpath 131072 " X: 0
- endtry
-
- try
- try
- Xpath 262144 " X: 262144
- execute'try | throw 7 | catch /7/ | throw "G" | endtry'
- catch /G/
- Xpath 524288 " X: 524288
- endtry
- catch /7/
- Xpath 1048576 " X: 0
- endtry
-
- try
- try
- Xpath 2097152 " X: 2097152
- execute 'try | throw 8 | finally | throw "H" | endtry'
- catch /H/
- Xpath 4194304 " X: 4194304
- endtry
- catch /8/
- Xpath 8388608 " X: 0
- endtry
-
-catch /.*/
- Xpath 16777216 " X: 0
- Xout v:exception "in" v:throwpoint
-endtry
-
-Xpath 33554432 " X: 33554432
-
-delcommand THROW1
-delcommand THROW2
-delcommand THROW3
-delcommand THROW4
-
-Xcheck 40744667
-
-
-"-------------------------------------------------------------------------------
-" Test 52: Uncaught exceptions {{{1
-"
-" When an exception is thrown but not caught, an error message is
-" displayed when the script is terminated. In case of an interrupt
-" or error exception, the normal interrupt or error message(s) are
-" displayed.
-"-------------------------------------------------------------------------------
-
-XpathINIT
-
-let msgfile = tempname()
-
-function! MESSAGES(...)
- try
- exec "edit" g:msgfile
- catch /^Vim(edit):/
- return 0
- endtry
-
- let english = v:lang == "C" || v:lang =~ '^[Ee]n'
- let match = 1
- norm gg
-
- let num = a:0 / 2
- let cnt = 1
- while cnt <= num
- let enr = a:{2*cnt - 1}
- let emsg= a:{2*cnt}
- let cnt = cnt + 1
-
- if enr == ""
- Xout "TODO: Add message number for:" emsg
- elseif enr == "INT"
- let enr = ""
- endif
- if enr == "" && !english
- continue
- endif
- let pattern = (enr != "") ? enr . ':.*' : ''
- if english
- let pattern = pattern . emsg
- endif
- if !search(pattern, "W")
- let match = 0
- Xout "No match for:" pattern
- endif
- norm $
- endwhile
-
- bwipeout!
- return match
-endfunction
+if ExtraVim(msgfile)
+" if 1
+" endtry
+" endif
+endif
+if MESSAGES('E602', ":endtry without :try")
+ Xpath 2 " X: 2
+endif
if ExtraVim(msgfile)
- Xpath 1 " X: 1
- throw "arrgh"
+" while 1
+" endtry
+" endwhile
endif
-
-Xpath 2 " X: 2
-if !MESSAGES('E605', "Exception not caught")
- Xpath 4 " X: 0
+if MESSAGES('E602', ":endtry without :try")
+ Xpath 4 " X: 4
endif
if ExtraVim(msgfile)
- try
- Xpath 8 " X: 8
- throw "oops"
- catch /arrgh/
- Xpath 16 " X: 0
- endtry
- Xpath 32 " X: 0
+" try
+" if 1
+" endtry
endif
-
-Xpath 64 " X: 64
-if !MESSAGES('E605', "Exception not caught")
- Xpath 128 " X: 0
+if MESSAGES('E171', "Missing :endif")
+ Xpath 8 " X: 8
endif
if ExtraVim(msgfile)
- function! T()
- throw "brrr"
- endfunction
-
- try
- Xpath 256 " X: 256
- throw "arrgh"
- catch /.*/
- Xpath 512 " X: 512
- call T()
- endtry
- Xpath 1024 " X: 0
+" try
+" while 1
+" endtry
endif
-
-Xpath 2048 " X: 2048
-if !MESSAGES('E605', "Exception not caught")
- Xpath 4096 " X: 0
+if MESSAGES('E170', "Missing :endwhile")
+ Xpath 16 " X: 16
endif
if ExtraVim(msgfile)
- try
- Xpath 8192 " X: 8192
- throw "arrgh"
- finally
- Xpath 16384 " X: 16384
- throw "brrr"
- endtry
- Xpath 32768 " X: 0
+" try
+" finally
+" if 1
+" endtry
endif
-
-Xpath 65536 " X: 65536
-if !MESSAGES('E605', "Exception not caught")
- Xpath 131072 " X: 0
+if MESSAGES('E171', "Missing :endif")
+ Xpath 32 " X: 32
endif
if ExtraVim(msgfile)
- try
- Xpath 262144 " X: 262144
- "INTERRUPT
- endtry
- Xpath 524288 " X: 0
+" try
+" finally
+" while 1
+" endtry
endif
-
-Xpath 1048576 " X: 1048576
-if !MESSAGES('INT', "Interrupted")
- Xpath 2097152 " X: 0
+if MESSAGES('E170', "Missing :endwhile")
+ Xpath 64 " X: 64
endif
if ExtraVim(msgfile)
- try
- Xpath 4194304 " X: 4194304
- let x = novar " error E121; exception: E121
- catch /E15:/ " should not catch
- Xpath 8388608 " X: 0
- endtry
- Xpath 16777216 " X: 0
+" try
+" throw "a"
+" catch /a/
+" if 1
+" endtry
endif
-
-Xpath 33554432 " X: 33554432
-if !MESSAGES('E121', "Undefined variable")
- Xpath 67108864 " X: 0
+if MESSAGES('E171', "Missing :endif")
+ Xpath 128 " X: 128
endif
if ExtraVim(msgfile)
- try
- Xpath 134217728 " X: 134217728
-" unlet novar # " error E108/E488; exception: E488
- catch /E108:/ " should not catch
- Xpath 268435456 " X: 0
- endtry
- Xpath 536870912 " X: 0
+" try
+" throw "a"
+" catch /a/
+" while 1
+" endtry
endif
-
-Xpath 1073741824 " X: 1073741824
-if !MESSAGES('E108', "No such variable", 'E488', "Trailing characters")
- " The Xpath command does not accept 2^31 (negative); add explicitly:
- let Xpath = Xpath + 2147483648 " X: 0
+if MESSAGES('E170', "Missing :endwhile")
+ Xpath 256 " X: 256
endif
call delete(msgfile)
unlet msgfile
-Xcheck 1247112011
+delfunction MESSAGES
-" Leave MESSAGES() for the next tests.
+Xcheck 511
"-------------------------------------------------------------------------------
-" Test 53: Nesting errors: :endif/:else/:elseif {{{1
-"
-" For nesting errors of :if conditionals the correct error messages
-" should be given.
+" Test 57: v:exception and v:throwpoint for user exceptions {{{1
"
-" This test reuses the function MESSAGES() from the previous test.
-" This functions checks the messages in g:msgfile.
+" v:exception evaluates to the value of the exception that was caught
+" most recently and is not finished. (A caught exception is finished
+" when the next ":catch", ":finally", or ":endtry" is reached.)
+" v:throwpoint evaluates to the script/function name and line number
+" where that exception has been thrown.
"-------------------------------------------------------------------------------
XpathINIT
-let msgfile = tempname()
+function! FuncException()
+ let g:exception = v:exception
+endfunction
-if ExtraVim(msgfile)
-" endif
-endif
-if MESSAGES('E580', ":endif without :if")
- Xpath 1 " X: 1
-endif
-
-if ExtraVim(msgfile)
-" while 1
-" endif
-" endwhile
-endif
-if MESSAGES('E580', ":endif without :if")
- Xpath 2 " X: 2
-endif
-
-if ExtraVim(msgfile)
-" try
-" finally
-" endif
-" endtry
-endif
-if MESSAGES('E580', ":endif without :if")
- Xpath 4 " X: 4
-endif
-
-if ExtraVim(msgfile)
-" try
-" endif
-" endtry
-endif
-if MESSAGES('E580', ":endif without :if")
- Xpath 8 " X: 8
-endif
-
-if ExtraVim(msgfile)
-" try
-" throw "a"
-" catch /a/
-" endif
-" endtry
-endif
-if MESSAGES('E580', ":endif without :if")
- Xpath 16 " X: 16
-endif
-
-if ExtraVim(msgfile)
-" else
-endif
-if MESSAGES('E581', ":else without :if")
- Xpath 32 " X: 32
-endif
-
-if ExtraVim(msgfile)
-" while 1
-" else
-" endwhile
-endif
-if MESSAGES('E581', ":else without :if")
- Xpath 64 " X: 64
-endif
-
-if ExtraVim(msgfile)
-" try
-" finally
-" else
-" endtry
-endif
-if MESSAGES('E581', ":else without :if")
- Xpath 128 " X: 128
-endif
-
-if ExtraVim(msgfile)
-" try
-" else
-" endtry
-endif
-if MESSAGES('E581', ":else without :if")
- Xpath 256 " X: 256
-endif
-
-if ExtraVim(msgfile)
-" try
-" throw "a"
-" catch /a/
-" else
-" endtry
-endif
-if MESSAGES('E581', ":else without :if")
- Xpath 512 " X: 512
-endif
-
-if ExtraVim(msgfile)
-" elseif
-endif
-if MESSAGES('E582', ":elseif without :if")
- Xpath 1024 " X: 1024
-endif
-
-if ExtraVim(msgfile)
-" while 1
-" elseif
-" endwhile
-endif
-if MESSAGES('E582', ":elseif without :if")
- Xpath 2048 " X: 2048
-endif
-
-if ExtraVim(msgfile)
-" try
-" finally
-" elseif
-" endtry
-endif
-if MESSAGES('E582', ":elseif without :if")
- Xpath 4096 " X: 4096
-endif
-
-if ExtraVim(msgfile)
-" try
-" elseif
-" endtry
-endif
-if MESSAGES('E582', ":elseif without :if")
- Xpath 8192 " X: 8192
-endif
-
-if ExtraVim(msgfile)
-" try
-" throw "a"
-" catch /a/
-" elseif
-" endtry
-endif
-if MESSAGES('E582', ":elseif without :if")
- Xpath 16384 " X: 16384
-endif
-
-if ExtraVim(msgfile)
-" if 1
-" else
-" else
-" endif
-endif
-if MESSAGES('E583', "multiple :else")
- Xpath 32768 " X: 32768
-endif
-
-if ExtraVim(msgfile)
-" if 1
-" else
-" elseif 1
-" endif
-endif
-if MESSAGES('E584', ":elseif after :else")
- Xpath 65536 " X: 65536
-endif
-
-call delete(msgfile)
-unlet msgfile
-
-Xcheck 131071
-
-" Leave MESSAGES() for the next test.
-
-
-"-------------------------------------------------------------------------------
-" Test 54: Nesting errors: :while/:endwhile {{{1
-"
-" For nesting errors of :while conditionals the correct error messages
-" should be given.
-"
-" This test reuses the function MESSAGES() from the previous test.
-" This functions checks the messages in g:msgfile.
-"-------------------------------------------------------------------------------
-
-XpathINIT
-
-let msgfile = tempname()
-
-if ExtraVim(msgfile)
-" endwhile
-endif
-if MESSAGES('E588', ":endwhile without :while")
- Xpath 1 " X: 1
-endif
-
-if ExtraVim(msgfile)
-" if 1
-" endwhile
-" endif
-endif
-if MESSAGES('E588', ":endwhile without :while")
- Xpath 2 " X: 2
-endif
-
-if ExtraVim(msgfile)
-" while 1
-" if 1
-" endwhile
-endif
-if MESSAGES('E171', "Missing :endif")
- Xpath 4 " X: 4
-endif
-
-if ExtraVim(msgfile)
-" try
-" finally
-" endwhile
-" endtry
-endif
-if MESSAGES('E588', ":endwhile without :while")
- Xpath 8 " X: 8
-endif
-
-if ExtraVim(msgfile)
-" while 1
-" try
-" finally
-" endwhile
-endif
-if MESSAGES('E600', "Missing :endtry")
- Xpath 16 " X: 16
-endif
-
-if ExtraVim(msgfile)
-" while 1
-" if 1
-" try
-" finally
-" endwhile
-endif
-if MESSAGES('E600', "Missing :endtry")
- Xpath 32 " X: 32
-endif
-
-if ExtraVim(msgfile)
-" while 1
-" try
-" finally
-" if 1
-" endwhile
-endif
-if MESSAGES('E171', "Missing :endif")
- Xpath 64 " X: 64
-endif
-
-if ExtraVim(msgfile)
-" try
-" endwhile
-" endtry
-endif
-if MESSAGES('E588', ":endwhile without :while")
- Xpath 128 " X: 128
-endif
-
-if ExtraVim(msgfile)
-" while 1
-" try
-" endwhile
-" endtry
-" endwhile
-endif
-if MESSAGES('E588', ":endwhile without :while")
- Xpath 256 " X: 256
-endif
-
-if ExtraVim(msgfile)
-" try
-" throw "a"
-" catch /a/
-" endwhile
-" endtry
-endif
-if MESSAGES('E588', ":endwhile without :while")
- Xpath 512 " X: 512
-endif
-
-if ExtraVim(msgfile)
-" while 1
-" try
-" throw "a"
-" catch /a/
-" endwhile
-" endtry
-" endwhile
-endif
-if MESSAGES('E588', ":endwhile without :while")
- Xpath 1024 " X: 1024
-endif
-
-
-call delete(msgfile)
-unlet msgfile
-
-Xcheck 2047
-
-" Leave MESSAGES() for the next test.
-
-
-"-------------------------------------------------------------------------------
-" Test 55: Nesting errors: :continue/:break {{{1
-"
-" For nesting errors of :continue and :break commands the correct
-" error messages should be given.
-"
-" This test reuses the function MESSAGES() from the previous test.
-" This functions checks the messages in g:msgfile.
-"-------------------------------------------------------------------------------
-
-XpathINIT
-
-let msgfile = tempname()
-
-if ExtraVim(msgfile)
-" continue
-endif
-if MESSAGES('E586', ":continue without :while")
- Xpath 1 " X: 1
-endif
-
-if ExtraVim(msgfile)
-" if 1
-" continue
-" endif
-endif
-if MESSAGES('E586', ":continue without :while")
- Xpath 2 " X: 2
-endif
-
-if ExtraVim(msgfile)
-" try
-" finally
-" continue
-" endtry
-endif
-if MESSAGES('E586', ":continue without :while")
- Xpath 4 " X: 4
-endif
-
-if ExtraVim(msgfile)
-" try
-" continue
-" endtry
-endif
-if MESSAGES('E586', ":continue without :while")
- Xpath 8 " X: 8
-endif
-
-if ExtraVim(msgfile)
-" try
-" throw "a"
-" catch /a/
-" continue
-" endtry
-endif
-if MESSAGES('E586', ":continue without :while")
- Xpath 16 " X: 16
-endif
-
-if ExtraVim(msgfile)
-" break
-endif
-if MESSAGES('E587', ":break without :while")
- Xpath 32 " X: 32
-endif
-
-if ExtraVim(msgfile)
-" if 1
-" break
-" endif
-endif
-if MESSAGES('E587', ":break without :while")
- Xpath 64 " X: 64
-endif
-
-if ExtraVim(msgfile)
-" try
-" finally
-" break
-" endtry
-endif
-if MESSAGES('E587', ":break without :while")
- Xpath 128 " X: 128
-endif
-
-if ExtraVim(msgfile)
-" try
-" break
-" endtry
-endif
-if MESSAGES('E587', ":break without :while")
- Xpath 256 " X: 256
-endif
-
-if ExtraVim(msgfile)
-" try
-" throw "a"
-" catch /a/
-" break
-" endtry
-endif
-if MESSAGES('E587', ":break without :while")
- Xpath 512 " X: 512
-endif
-
-call delete(msgfile)
-unlet msgfile
-
-Xcheck 1023
-
-" Leave MESSAGES() for the next test.
-
-
-"-------------------------------------------------------------------------------
-" Test 56: Nesting errors: :endtry {{{1
-"
-" For nesting errors of :try conditionals the correct error messages
-" should be given.
-"
-" This test reuses the function MESSAGES() from the previous test.
-" This functions checks the messages in g:msgfile.
-"-------------------------------------------------------------------------------
-
-XpathINIT
-
-let msgfile = tempname()
-
-if ExtraVim(msgfile)
-" endtry
-endif
-if MESSAGES('E602', ":endtry without :try")
- Xpath 1 " X: 1
-endif
-
-if ExtraVim(msgfile)
-" if 1
-" endtry
-" endif
-endif
-if MESSAGES('E602', ":endtry without :try")
- Xpath 2 " X: 2
-endif
-
-if ExtraVim(msgfile)
-" while 1
-" endtry
-" endwhile
-endif
-if MESSAGES('E602', ":endtry without :try")
- Xpath 4 " X: 4
-endif
-
-if ExtraVim(msgfile)
-" try
-" if 1
-" endtry
-endif
-if MESSAGES('E171', "Missing :endif")
- Xpath 8 " X: 8
-endif
-
-if ExtraVim(msgfile)
-" try
-" while 1
-" endtry
-endif
-if MESSAGES('E170', "Missing :endwhile")
- Xpath 16 " X: 16
-endif
-
-if ExtraVim(msgfile)
-" try
-" finally
-" if 1
-" endtry
-endif
-if MESSAGES('E171', "Missing :endif")
- Xpath 32 " X: 32
-endif
-
-if ExtraVim(msgfile)
-" try
-" finally
-" while 1
-" endtry
-endif
-if MESSAGES('E170', "Missing :endwhile")
- Xpath 64 " X: 64
-endif
-
-if ExtraVim(msgfile)
-" try
-" throw "a"
-" catch /a/
-" if 1
-" endtry
-endif
-if MESSAGES('E171', "Missing :endif")
- Xpath 128 " X: 128
-endif
-
-if ExtraVim(msgfile)
-" try
-" throw "a"
-" catch /a/
-" while 1
-" endtry
-endif
-if MESSAGES('E170', "Missing :endwhile")
- Xpath 256 " X: 256
-endif
-
-call delete(msgfile)
-unlet msgfile
-
-delfunction MESSAGES
-
-Xcheck 511
-
-
-"-------------------------------------------------------------------------------
-" Test 57: v:exception and v:throwpoint for user exceptions {{{1
-"
-" v:exception evaluates to the value of the exception that was caught
-" most recently and is not finished. (A caught exception is finished
-" when the next ":catch", ":finally", or ":endtry" is reached.)
-" v:throwpoint evaluates to the script/function name and line number
-" where that exception has been thrown.
-"-------------------------------------------------------------------------------
-
-XpathINIT
-
-function! FuncException()
- let g:exception = v:exception
-endfunction
-
-function! FuncThrowpoint()
- let g:throwpoint = v:throwpoint
-endfunction
-
-let scriptException = MakeScript("FuncException")
-let scriptThrowPoint = MakeScript("FuncThrowpoint")
-
-command! CmdException let g:exception = v:exception
-command! CmdThrowpoint let g:throwpoint = v:throwpoint
-
-XloopINIT! 1 2
-
-function! CHECK(n, exception, throwname, throwline)
- XloopNEXT
- let error = 0
- if v:exception != a:exception
- Xout a:n.": v:exception is" v:exception "instead of" a:exception
- let error = 1
- endif
- if v:throwpoint !~ a:throwname
- let name = escape(a:throwname, '\')
- Xout a:n.": v:throwpoint (".v:throwpoint.") does not match" name
- let error = 1
- endif
- if v:throwpoint !~ a:throwline
- let line = escape(a:throwline, '\')
- Xout a:n.": v:throwpoint (".v:throwpoint.") does not match" line
- let error = 1
- endif
- if error
- Xloop 1 " X: 0
- endif
-endfunction
-
-function! T(arg, line)
- if a:line == 2
- throw a:arg " in line 2
- elseif a:line == 4
- throw a:arg " in line 4
- elseif a:line == 6
- throw a:arg " in line 6
- elseif a:line == 8
- throw a:arg " in line 8
- endif
-endfunction
-
-function! G(arg, line)
- call T(a:arg, a:line)
-endfunction
-
-function! F(arg, line)
- call G(a:arg, a:line)
-endfunction
-
-let scriptT = MakeScript("T")
-let scriptG = MakeScript("G", scriptT)
-let scriptF = MakeScript("F", scriptG)
-
-try
- Xpath 32768 " X: 32768
- call F("oops", 2)
-catch /.*/
- Xpath 65536 " X: 65536
- let exception = v:exception
- let throwpoint = v:throwpoint
- call CHECK(1, "oops", '\<F\[1]\.\.G\[1]\.\.T\>', '\<2\>')
- exec "let exception = v:exception"
- exec "let throwpoint = v:throwpoint"
- call CHECK(2, "oops", '\<F\[1]\.\.G\[1]\.\.T\>', '\<2\>')
- CmdException
- CmdThrowpoint
- call CHECK(3, "oops", '\<F\[1]\.\.G\[1]\.\.T\>', '\<2\>')
- call FuncException()
- call FuncThrowpoint()
- call CHECK(4, "oops", '\<F\[1]\.\.G\[1]\.\.T\>', '\<2\>')
- exec "source" scriptException
- exec "source" scriptThrowPoint
- call CHECK(5, "oops", '\<F\[1]\.\.G\[1]\.\.T\>', '\<2\>')
- try
- Xpath 131072 " X: 131072
- call G("arrgh", 4)
- catch /.*/
- Xpath 262144 " X: 262144
- let exception = v:exception
- let throwpoint = v:throwpoint
- call CHECK(6, "arrgh", '\<G\[1]\.\.T\>', '\<4\>')
- try
- Xpath 524288 " X: 524288
- let g:arg = "autsch"
- let g:line = 6
- exec "source" scriptF
- catch /.*/
- Xpath 1048576 " X: 1048576
- let exception = v:exception
- let throwpoint = v:throwpoint
- " Symbolic links in tempname()s are not resolved, whereas resolving
- " is done for v:throwpoint. Resolve the temporary file name for
- " scriptT, so that it can be matched against v:throwpoint.
- call CHECK(7, "autsch", resolve(scriptT), '\<6\>')
- finally
- Xpath 2097152 " X: 2097152
- let exception = v:exception
- let throwpoint = v:throwpoint
- call CHECK(8, "arrgh", '\<G\[1]\.\.T\>', '\<4\>')
- try
- Xpath 4194304 " X: 4194304
- let g:arg = "brrrr"
- let g:line = 8
- exec "source" scriptG
- catch /.*/
- Xpath 8388608 " X: 8388608
- let exception = v:exception
- let throwpoint = v:throwpoint
- " Resolve scriptT for matching it against v:throwpoint.
- call CHECK(9, "brrrr", resolve(scriptT), '\<8\>')
- finally
- Xpath 16777216 " X: 16777216
- let exception = v:exception
- let throwpoint = v:throwpoint
- call CHECK(10, "arrgh", '\<G\[1]\.\.T\>', '\<4\>')
- endtry
- Xpath 33554432 " X: 33554432
- let exception = v:exception
- let throwpoint = v:throwpoint
- call CHECK(11, "arrgh", '\<G\[1]\.\.T\>', '\<4\>')
- endtry
- Xpath 67108864 " X: 67108864
- let exception = v:exception
- let throwpoint = v:throwpoint
- call CHECK(12, "arrgh", '\<G\[1]\.\.T\>', '\<4\>')
- finally
- Xpath 134217728 " X: 134217728
- let exception = v:exception
- let throwpoint = v:throwpoint
- call CHECK(13, "oops", '\<F\[1]\.\.G\[1]\.\.T\>', '\<2\>')
- endtry
- Xpath 268435456 " X: 268435456
- let exception = v:exception
- let throwpoint = v:throwpoint
- call CHECK(14, "oops", '\<F\[1]\.\.G\[1]\.\.T\>', '\<2\>')
-finally
- Xpath 536870912 " X: 536870912
- let exception = v:exception
- let throwpoint = v:throwpoint
- call CHECK(15, "", '^$', '^$')
-endtry
-
-Xpath 1073741824 " X: 1073741824
-
-unlet exception throwpoint
-delfunction FuncException
-delfunction FuncThrowpoint
-call delete(scriptException)
-call delete(scriptThrowPoint)
-unlet scriptException scriptThrowPoint
-delcommand CmdException
-delcommand CmdThrowpoint
-delfunction T
-delfunction G
-delfunction F
-call delete(scriptT)
-call delete(scriptG)
-call delete(scriptF)
-unlet scriptT scriptG scriptF
-
-Xcheck 2147450880
-
-
-"-------------------------------------------------------------------------------
-"
-" Test 58: v:exception and v:throwpoint for error/interrupt exceptions {{{1
-"
-" v:exception and v:throwpoint work also for error and interrupt
-" exceptions.
-"-------------------------------------------------------------------------------
-
-XpathINIT
-
-if ExtraVim()
-
- function! T(line)
- if a:line == 2
- delfunction T " error (function in use) in line 2
- elseif a:line == 4
- let dummy = 0 " INTERRUPT1 - interrupt in line 4
- endif
- endfunction
-
- while 1
- try
- Xpath 1 " X: 1
- let caught = 0
- call T(2)
- catch /.*/
- let caught = 1
- if v:exception !~ 'Vim(delfunction):'
- Xpath 2 " X: 0
- endif
- if v:throwpoint !~ '\<T\>'
- Xpath 4 " X: 0
- endif
- if v:throwpoint !~ '\<2\>'
- Xpath 8 " X: 0
- endif
- finally
- Xpath 16 " X: 16
- if caught || $VIMNOERRTHROW
- Xpath 32 " X: 32
- endif
- if v:exception != ""
- Xpath 64 " X: 0
- endif
- if v:throwpoint != ""
- Xpath 128 " X: 0
- endif
- break " discard error for $VIMNOERRTHROW
- endtry
- endwhile
+function! FuncThrowpoint()
+ let g:throwpoint = v:throwpoint
+endfunction
- Xpath 256 " X: 256
- if v:exception != ""
- Xpath 512 " X: 0
- endif
- if v:throwpoint != ""
- Xpath 1024 " X: 0
- endif
+let scriptException = MakeScript("FuncException")
+let scriptThrowPoint = MakeScript("FuncThrowpoint")
- while 1
- try
- Xpath 2048 " X: 2048
- let caught = 0
- call T(4)
- catch /.*/
- let caught = 1
- if v:exception != 'Vim:Interrupt'
- Xpath 4096 " X: 0
- endif
- if v:throwpoint !~ '\<T\>'
- Xpath 8192 " X: 0
- endif
- if v:throwpoint !~ '\<4\>'
- Xpath 16384 " X: 0
- endif
- finally
- Xpath 32768 " X: 32768
- if caught || $VIMNOINTTHROW
- Xpath 65536 " X: 65536
- endif
- if v:exception != ""
- Xpath 131072 " X: 0
- endif
- if v:throwpoint != ""
- Xpath 262144 " X: 0
- endif
- break " discard error for $VIMNOERRTHROW
- endtry
- endwhile
+command! CmdException let g:exception = v:exception
+command! CmdThrowpoint let g:throwpoint = v:throwpoint
- Xpath 524288 " X: 524288
- if v:exception != ""
- Xpath 1048576 " X: 0
+XloopINIT! 1 2
+
+function! CHECK(n, exception, throwname, throwline)
+ XloopNEXT
+ let error = 0
+ if v:exception != a:exception
+ Xout a:n.": v:exception is" v:exception "instead of" a:exception
+ let error = 1
endif
- if v:throwpoint != ""
- Xpath 2097152 " X: 0
+ if v:throwpoint !~ a:throwname
+ let name = escape(a:throwname, '\')
+ Xout a:n.": v:throwpoint (".v:throwpoint.") does not match" name
+ let error = 1
endif
+ if v:throwpoint !~ a:throwline
+ let line = escape(a:throwline, '\')
+ Xout a:n.": v:throwpoint (".v:throwpoint.") does not match" line
+ let error = 1
+ endif
+ if error
+ Xloop 1 " X: 0
+ endif
+endfunction
-endif
-
-Xcheck 624945
-
-
-"-------------------------------------------------------------------------------
-"
-" Test 59: v:exception and v:throwpoint when discarding exceptions {{{1
-"
-" When a :catch clause is left by a ":break" etc or an error or
-" interrupt exception, v:exception and v:throwpoint are reset. They
-" are not affected by an exception that is discarded before being
-" caught.
-"-------------------------------------------------------------------------------
-
-XpathINIT
-
-if ExtraVim()
-
- XloopINIT! 1 2
-
- let sfile = expand("<sfile>")
-
- function! LineNumber()
- return substitute(substitute(v:throwpoint, g:sfile, '', ""),
- \ '\D*\(\d*\).*', '\1', "")
- endfunction
-
- command! -nargs=1 SetLineNumber
- \ try | throw "line" | catch /.*/ | let <args> = LineNumber() | endtry
-
- " Check v:exception/v:throwpoint against second/fourth parameter if
- " specified, check for being empty else.
- function! CHECK(n, ...)
- XloopNEXT
- let exception = a:0 != 0 ? a:1 : "" " second parameter (optional)
- let emsg = a:0 != 0 ? a:2 : "" " third parameter (optional)
- let line = a:0 != 0 ? a:3 : 0 " fourth parameter (optional)
- let error = 0
- if emsg != ""
- " exception is the error number, emsg the English error message text
- if exception !~ '^E\d\+$'
- Xout "TODO: Add message number for:" emsg
- elseif v:lang == "C" || v:lang =~ '^[Ee]n'
- if exception == "E492" && emsg == "Not an editor command"
- let exception = '^Vim:' . exception . ': ' . emsg
- else
- let exception = '^Vim(\a\+):' . exception . ': ' . emsg
- endif
- else
- if exception == "E492"
- let exception = '^Vim:' . exception
- else
- let exception = '^Vim(\a\+):' . exception
- endif
- endif
- endif
- if exception == "" && v:exception != ""
- Xout a:n.": v:exception is set:" v:exception
- let error = 1
- elseif exception != "" && v:exception !~ exception
- Xout a:n.": v:exception (".v:exception.") does not match" exception
- let error = 1
- endif
- if line == 0 && v:throwpoint != ""
- Xout a:n.": v:throwpoint is set:" v:throwpoint
- let error = 1
- elseif line != 0 && v:throwpoint !~ '\<' . line . '\>'
- Xout a:n.": v:throwpoint (".v:throwpoint.") does not match" line
- let error = 1
- endif
- if !error
- Xloop 1 " X: 2097151
- endif
- endfunction
-
- while 1
- try
- throw "x1"
- catch /.*/
- break
- endtry
- endwhile
- call CHECK(1)
-
- while 1
- try
- throw "x2"
- catch /.*/
- break
- finally
- call CHECK(2)
- endtry
- break
- endwhile
- call CHECK(3)
-
- while 1
- try
- let errcaught = 0
- try
- try
- throw "x3"
- catch /.*/
- SetLineNumber line_before_error
- asdf
- endtry
- catch /.*/
- let errcaught = 1
- call CHECK(4, 'E492', "Not an editor command",
- \ line_before_error + 1)
- endtry
- finally
- if !errcaught && $VIMNOERRTHROW
- call CHECK(4)
- endif
- break " discard error for $VIMNOERRTHROW
- endtry
- endwhile
- call CHECK(5)
-
- Xpath 2097152 " X: 2097152
-
- while 1
- try
- let intcaught = 0
- try
- try
- throw "x4"
- catch /.*/
- SetLineNumber two_lines_before_interrupt
- "INTERRUPT
- let dummy = 0
- endtry
- catch /.*/
- let intcaught = 1
- call CHECK(6, "Vim:Interrupt", '',
- \ two_lines_before_interrupt + 2)
- endtry
- finally
- if !intcaught && $VIMNOINTTHROW
- call CHECK(6)
- endif
- break " discard interrupt for $VIMNOINTTHROW
- endtry
- endwhile
- call CHECK(7)
-
- Xpath 4194304 " X: 4194304
-
- while 1
- try
- let errcaught = 0
- try
- try
-" if 1
- SetLineNumber line_before_throw
- throw "x5"
- " missing endif
- catch /.*/
- Xpath 8388608 " X: 0
- endtry
- catch /.*/
- let errcaught = 1
- call CHECK(8, 'E171', "Missing :endif", line_before_throw + 3)
- endtry
- finally
- if !errcaught && $VIMNOERRTHROW
- call CHECK(8)
- endif
- break " discard error for $VIMNOERRTHROW
- endtry
- endwhile
- call CHECK(9)
-
- Xpath 16777216 " X: 16777216
+function! T(arg, line)
+ if a:line == 2
+ throw a:arg " in line 2
+ elseif a:line == 4
+ throw a:arg " in line 4
+ elseif a:line == 6
+ throw a:arg " in line 6
+ elseif a:line == 8
+ throw a:arg " in line 8
+ endif
+endfunction
- try
- while 1
- try
- throw "x6"
- finally
- break
- endtry
- break
- endwhile
- catch /.*/
- Xpath 33554432 " X: 0
- endtry
- call CHECK(10)
+function! G(arg, line)
+ call T(a:arg, a:line)
+endfunction
+
+function! F(arg, line)
+ call G(a:arg, a:line)
+endfunction
+
+let scriptT = MakeScript("T")
+let scriptG = MakeScript("G", scriptT)
+let scriptF = MakeScript("F", scriptG)
+try
+ Xpath 32768 " X: 32768
+ call F("oops", 2)
+catch /.*/
+ Xpath 65536 " X: 65536
+ let exception = v:exception
+ let throwpoint = v:throwpoint
+ call CHECK(1, "oops", '\<F\[1]\.\.G\[1]\.\.T\>', '\<2\>')
+ exec "let exception = v:exception"
+ exec "let throwpoint = v:throwpoint"
+ call CHECK(2, "oops", '\<F\[1]\.\.G\[1]\.\.T\>', '\<2\>')
+ CmdException
+ CmdThrowpoint
+ call CHECK(3, "oops", '\<F\[1]\.\.G\[1]\.\.T\>', '\<2\>')
+ call FuncException()
+ call FuncThrowpoint()
+ call CHECK(4, "oops", '\<F\[1]\.\.G\[1]\.\.T\>', '\<2\>')
+ exec "source" scriptException
+ exec "source" scriptThrowPoint
+ call CHECK(5, "oops", '\<F\[1]\.\.G\[1]\.\.T\>', '\<2\>')
try
- while 1
- try
- throw "x7"
- finally
- break
- endtry
- break
- endwhile
+ Xpath 131072 " X: 131072
+ call G("arrgh", 4)
catch /.*/
- Xpath 67108864 " X: 0
- finally
- call CHECK(11)
- endtry
- call CHECK(12)
-
- while 1
+ Xpath 262144 " X: 262144
+ let exception = v:exception
+ let throwpoint = v:throwpoint
+ call CHECK(6, "arrgh", '\<G\[1]\.\.T\>', '\<4\>')
try
- let errcaught = 0
+ Xpath 524288 " X: 524288
+ let g:arg = "autsch"
+ let g:line = 6
+ exec "source" scriptF
+ catch /.*/
+ Xpath 1048576 " X: 1048576
+ let exception = v:exception
+ let throwpoint = v:throwpoint
+ " Symbolic links in tempname()s are not resolved, whereas resolving
+ " is done for v:throwpoint. Resolve the temporary file name for
+ " scriptT, so that it can be matched against v:throwpoint.
+ call CHECK(7, "autsch", resolve(scriptT), '\<6\>')
+ finally
+ Xpath 2097152 " X: 2097152
+ let exception = v:exception
+ let throwpoint = v:throwpoint
+ call CHECK(8, "arrgh", '\<G\[1]\.\.T\>', '\<4\>')
try
- try
- throw "x8"
- finally
- SetLineNumber line_before_error
- asdf
- endtry
+ Xpath 4194304 " X: 4194304
+ let g:arg = "brrrr"
+ let g:line = 8
+ exec "source" scriptG
catch /.*/
- let errcaught = 1
- call CHECK(13, 'E492', "Not an editor command",
- \ line_before_error + 1)
+ Xpath 8388608 " X: 8388608
+ let exception = v:exception
+ let throwpoint = v:throwpoint
+ " Resolve scriptT for matching it against v:throwpoint.
+ call CHECK(9, "brrrr", resolve(scriptT), '\<8\>')
+ finally
+ Xpath 16777216 " X: 16777216
+ let exception = v:exception
+ let throwpoint = v:throwpoint
+ call CHECK(10, "arrgh", '\<G\[1]\.\.T\>', '\<4\>')
endtry
- finally
- if !errcaught && $VIMNOERRTHROW
- call CHECK(13)
- endif
- break " discard error for $VIMNOERRTHROW
+ Xpath 33554432 " X: 33554432
+ let exception = v:exception
+ let throwpoint = v:throwpoint
+ call CHECK(11, "arrgh", '\<G\[1]\.\.T\>', '\<4\>')
endtry
- endwhile
- call CHECK(14)
+ Xpath 67108864 " X: 67108864
+ let exception = v:exception
+ let throwpoint = v:throwpoint
+ call CHECK(12, "arrgh", '\<G\[1]\.\.T\>', '\<4\>')
+ finally
+ Xpath 134217728 " X: 134217728
+ let exception = v:exception
+ let throwpoint = v:throwpoint
+ call CHECK(13, "oops", '\<F\[1]\.\.G\[1]\.\.T\>', '\<2\>')
+ endtry
+ Xpath 268435456 " X: 268435456
+ let exception = v:exception
+ let throwpoint = v:throwpoint
+ call CHECK(14, "oops", '\<F\[1]\.\.G\[1]\.\.T\>', '\<2\>')
+finally
+ Xpath 536870912 " X: 536870912
+ let exception = v:exception
+ let throwpoint = v:throwpoint
+ call CHECK(15, "", '^$', '^$')
+endtry
- Xpath 134217728 " X: 134217728
+Xpath 1073741824 " X: 1073741824
- while 1
- try
- let intcaught = 0
- try
- try
- throw "x9"
- finally
- SetLineNumber two_lines_before_interrupt
- "INTERRUPT
- endtry
- catch /.*/
- let intcaught = 1
- call CHECK(15, "Vim:Interrupt", '',
- \ two_lines_before_interrupt + 2)
- endtry
- finally
- if !intcaught && $VIMNOINTTHROW
- call CHECK(15)
- endif
- break " discard interrupt for $VIMNOINTTHROW
- endtry
- endwhile
- call CHECK(16)
+unlet exception throwpoint
+delfunction FuncException
+delfunction FuncThrowpoint
+call delete(scriptException)
+call delete(scriptThrowPoint)
+unlet scriptException scriptThrowPoint
+delcommand CmdException
+delcommand CmdThrowpoint
+delfunction T
+delfunction G
+delfunction F
+call delete(scriptT)
+call delete(scriptG)
+call delete(scriptF)
+unlet scriptT scriptG scriptF
- Xpath 268435456 " X: 268435456
+Xcheck 2147450880
+
+
+"-------------------------------------------------------------------------------
+"
+" Test 58: v:exception and v:throwpoint for error/interrupt exceptions {{{1
+"
+" v:exception and v:throwpoint work also for error and interrupt
+" exceptions.
+"-------------------------------------------------------------------------------
+
+XpathINIT
+
+if ExtraVim()
+
+ function! T(line)
+ if a:line == 2
+ delfunction T " error (function in use) in line 2
+ elseif a:line == 4
+ let dummy = 0 " INTERRUPT1 - interrupt in line 4
+ endif
+ endfunction
while 1
try
- let errcaught = 0
- try
- try
-" if 1
- SetLineNumber line_before_throw
- throw "x10"
- " missing endif
- finally
- call CHECK(17)
- endtry
- catch /.*/
- let errcaught = 1
- call CHECK(18, 'E171', "Missing :endif", line_before_throw + 3)
- endtry
+ Xpath 1 " X: 1
+ let caught = 0
+ call T(2)
+ catch /.*/
+ let caught = 1
+ if v:exception !~ 'Vim(delfunction):'
+ Xpath 2 " X: 0
+ endif
+ if v:throwpoint !~ '\<T\>'
+ Xpath 4 " X: 0
+ endif
+ if v:throwpoint !~ '\<2\>'
+ Xpath 8 " X: 0
+ endif
finally
- if !errcaught && $VIMNOERRTHROW
- call CHECK(18)
+ Xpath 16 " X: 16
+ if caught || $VIMNOERRTHROW
+ Xpath 32 " X: 32
+ endif
+ if v:exception != ""
+ Xpath 64 " X: 0
+ endif
+ if v:throwpoint != ""
+ Xpath 128 " X: 0
endif
break " discard error for $VIMNOERRTHROW
endtry
endwhile
- call CHECK(19)
- Xpath 536870912 " X: 536870912
+ Xpath 256 " X: 256
+ if v:exception != ""
+ Xpath 512 " X: 0
+ endif
+ if v:throwpoint != ""
+ Xpath 1024 " X: 0
+ endif
while 1
try
- let errcaught = 0
- try
- try
-" if 1
- SetLineNumber line_before_throw
- throw "x11"
- " missing endif
- endtry
- catch /.*/
- let errcaught = 1
- call CHECK(20, 'E171', "Missing :endif", line_before_throw + 3)
- endtry
+ Xpath 2048 " X: 2048
+ let caught = 0
+ call T(4)
+ catch /.*/
+ let caught = 1
+ if v:exception != 'Vim:Interrupt'
+ Xpath 4096 " X: 0
+ endif
+ if v:throwpoint !~ '\<T\>'
+ Xpath 8192 " X: 0
+ endif
+ if v:throwpoint !~ '\<4\>'
+ Xpath 16384 " X: 0
+ endif
finally
- if !errcaught && $VIMNOERRTHROW
- call CHECK(20)
+ Xpath 32768 " X: 32768
+ if caught || $VIMNOINTTHROW
+ Xpath 65536 " X: 65536
+ endif
+ if v:exception != ""
+ Xpath 131072 " X: 0
+ endif
+ if v:throwpoint != ""
+ Xpath 262144 " X: 0
endif
break " discard error for $VIMNOERRTHROW
endtry
endwhile
- call CHECK(21)
- Xpath 1073741824 " X: 1073741824
+ Xpath 524288 " X: 524288
+ if v:exception != ""
+ Xpath 1048576 " X: 0
+ endif
+ if v:throwpoint != ""
+ Xpath 2097152 " X: 0
+ endif
endif
-Xcheck 2038431743
+Xcheck 624945
"-------------------------------------------------------------------------------
"
-" Test 60: (Re)throwing v:exception; :echoerr. {{{1
+" Test 59: v:exception and v:throwpoint when discarding exceptions {{{1
"
-" A user exception can be rethrown after catching by throwing
-" v:exception. An error or interrupt exception cannot be rethrown
-" because Vim exceptions cannot be faked. A Vim exception using the
-" value of v:exception can, however, be triggered by the :echoerr
-" command.
+" When a :catch clause is left by a ":break" etc or an error or
+" interrupt exception, v:exception and v:throwpoint are reset. They
+" are not affected by an exception that is discarded before being
+" caught.
"-------------------------------------------------------------------------------
XpathINIT
-try
- try
- Xpath 1 " X: 1
- throw "oops"
- catch /oops/
- Xpath 2 " X: 2
- throw v:exception " rethrow user exception
- catch /.*/
- Xpath 4 " X: 0
- endtry
-catch /^oops$/ " catches rethrown user exception
- Xpath 8 " X: 8
-catch /.*/
- Xpath 16 " X: 0
-endtry
-
-function! F()
- try
- let caught = 0
- try
- Xpath 32 " X: 32
- write /n/o/n/w/r/i/t/a/b/l/e/_/f/i/l/e
- Xpath 64 " X: 0
- Xout "did_emsg was reset before executing " .
- \ "BufWritePost autocommands."
- catch /^Vim(write):/
- let caught = 1
- throw v:exception " throw error: cannot fake Vim exception
- catch /.*/
- Xpath 128 " X: 0
- finally
- Xpath 256 " X: 256
- if !caught && !$VIMNOERRTHROW
- Xpath 512 " X: 0
- endif
- endtry
- catch /^Vim(throw):/ " catches throw error
- let caught = caught + 1
- catch /.*/
- Xpath 1024 " X: 0
- finally
- Xpath 2048 " X: 2048
- if caught != 2
- if !caught && !$VIMNOERRTHROW
- Xpath 4096 " X: 0
- elseif caught
- Xpath 8192 " X: 0
- endif
- return | " discard error for $VIMNOERRTHROW
- endif
- endtry
-endfunction
+if ExtraVim()
-call F()
-delfunction F
+ XloopINIT! 1 2
-function! G()
- try
- let caught = 0
- try
- Xpath 16384 " X: 16384
- asdf
- catch /^Vim/ " catch error exception
- let caught = 1
- " Trigger Vim error exception with value specified after :echoerr
- let value = substitute(v:exception, '^Vim\((.*)\)\=:', '', "")
- echoerr value
- catch /.*/
- Xpath 32768 " X: 0
- finally
- Xpath 65536 " X: 65536
- if !caught
- if !$VIMNOERRTHROW
- Xpath 131072 " X: 0
- else
- let value = "Error"
- echoerr value
- endif
- endif
- endtry
- catch /^Vim(echoerr):/
- let caught = caught + 1
- if v:exception !~ value
- Xpath 262144 " X: 0
- endif
- catch /.*/
- Xpath 524288 " X: 0
- finally
- Xpath 1048576 " X: 1048576
- if caught != 2
- if !caught && !$VIMNOERRTHROW
- Xpath 2097152 " X: 0
- elseif caught
- Xpath 4194304 " X: 0
- endif
- return | " discard error for $VIMNOERRTHROW
- endif
- endtry
-endfunction
+ let sfile = expand("<sfile>")
-call G()
-delfunction G
+ function! LineNumber()
+ return substitute(substitute(v:throwpoint, g:sfile, '', ""),
+ \ '\D*\(\d*\).*', '\1', "")
+ endfunction
-unlet! value caught
+ command! -nargs=1 SetLineNumber
+ \ try | throw "line" | catch /.*/ | let <args> = LineNumber() | endtry
-if ExtraVim()
- try
- let errcaught = 0
- try
- Xpath 8388608 " X: 8388608
- let intcaught = 0
- "INTERRUPT
- catch /^Vim:/ " catch interrupt exception
- let intcaught = 1
- " Trigger Vim error exception with value specified after :echoerr
- echoerr substitute(v:exception, '^Vim\((.*)\)\=:', '', "")
- catch /.*/
- Xpath 16777216 " X: 0
- finally
- Xpath 33554432 " X: 33554432
- if !intcaught
- if !$VIMNOINTTHROW
- Xpath 67108864 " X: 0
+ " Check v:exception/v:throwpoint against second/fourth parameter if
+ " specified, check for being empty else.
+ function! CHECK(n, ...)
+ XloopNEXT
+ let exception = a:0 != 0 ? a:1 : "" " second parameter (optional)
+ let emsg = a:0 != 0 ? a:2 : "" " third parameter (optional)
+ let line = a:0 != 0 ? a:3 : 0 " fourth parameter (optional)
+ let error = 0
+ if emsg != ""
+ " exception is the error number, emsg the English error message text
+ if exception !~ '^E\d\+$'
+ Xout "TODO: Add message number for:" emsg
+ elseif v:lang == "C" || v:lang =~ '^[Ee]n'
+ if exception == "E492" && emsg == "Not an editor command"
+ let exception = '^Vim:' . exception . ': ' . emsg
else
- echoerr "Interrupt"
+ let exception = '^Vim(\a\+):' . exception . ': ' . emsg
+ endif
+ else
+ if exception == "E492"
+ let exception = '^Vim:' . exception
+ else
+ let exception = '^Vim(\a\+):' . exception
endif
endif
- endtry
- catch /^Vim(echoerr):/
- let errcaught = 1
- if v:exception !~ "Interrupt"
- Xpath 134217728 " X: 0
endif
- finally
- Xpath 268435456 " X: 268435456
- if !errcaught && !$VIMNOERRTHROW
- Xpath 536870912 " X: 0
+ if exception == "" && v:exception != ""
+ Xout a:n.": v:exception is set:" v:exception
+ let error = 1
+ elseif exception != "" && v:exception !~ exception
+ Xout a:n.": v:exception (".v:exception.") does not match" exception
+ let error = 1
endif
- endtry
-endif
-
-Xcheck 311511339
-
-
-"-------------------------------------------------------------------------------
-" Test 61: Catching interrupt exceptions {{{1
-"
-" When an interrupt occurs inside a :try/:endtry region, an
-" interrupt exception is thrown and can be caught. Its value is
-" "Vim:Interrupt". If the interrupt occurs after an error or a :throw
-" but before a matching :catch is reached, all following :catches of
-" that try block are ignored, but the interrupt exception can be
-" caught by the next surrounding try conditional. An interrupt is
-" ignored when there is a previous interrupt that has not been caught
-" or causes a :finally clause to be executed.
-"-------------------------------------------------------------------------------
-
-XpathINIT
-
-if ExtraVim()
+ if line == 0 && v:throwpoint != ""
+ Xout a:n.": v:throwpoint is set:" v:throwpoint
+ let error = 1
+ elseif line != 0 && v:throwpoint !~ '\<' . line . '\>'
+ Xout a:n.": v:throwpoint (".v:throwpoint.") does not match" line
+ let error = 1
+ endif
+ if !error
+ Xloop 1 " X: 2097151
+ endif
+ endfunction
while 1
try
- try
- Xpath 1 " X: 1
- let caught = 0
- "INTERRUPT
- Xpath 2 " X: 0
- catch /^Vim:Interrupt$/
- let caught = 1
- finally
- Xpath 4 " X: 4
- if caught || $VIMNOINTTHROW
- Xpath 8 " X: 8
- endif
- endtry
+ throw "x1"
catch /.*/
- Xpath 16 " X: 0
- Xout v:exception "in" v:throwpoint
- finally
- break " discard interrupt for $VIMNOINTTHROW
+ break
endtry
endwhile
+ call CHECK(1)
while 1
try
- try
- let caught = 0
- try
- Xpath 32 " X: 32
- asdf
- Xpath 64 " X: 0
- catch /do_not_catch/
- Xpath 128 " X: 0
- catch /.*/ "INTERRUPT - throw interrupt if !$VIMNOERRTHROW
- Xpath 256 " X: 0
- catch /.*/
- Xpath 512 " X: 0
- finally "INTERRUPT - throw interrupt if $VIMNOERRTHROW
- Xpath 1024 " X: 1024
- endtry
- catch /^Vim:Interrupt$/
- let caught = 1
- finally
- Xpath 2048 " X: 2048
- if caught || $VIMNOINTTHROW
- Xpath 4096 " X: 4096
- endif
- endtry
+ throw "x2"
catch /.*/
- Xpath 8192 " X: 0
- Xout v:exception "in" v:throwpoint
+ break
finally
- break " discard interrupt for $VIMNOINTTHROW
+ call CHECK(2)
endtry
+ break
endwhile
+ call CHECK(3)
while 1
try
+ let errcaught = 0
try
- let caught = 0
try
- Xpath 16384 " X: 16384
- throw "x"
- Xpath 32768 " X: 0
- catch /do_not_catch/
- Xpath 65536 " X: 0
- catch /x/ "INTERRUPT
- Xpath 131072 " X: 0
+ throw "x3"
catch /.*/
- Xpath 262144 " X: 0
+ SetLineNumber line_before_error
+ asdf
endtry
- catch /^Vim:Interrupt$/
- let caught = 1
- finally
- Xpath 524288 " X: 524288
- if caught || $VIMNOINTTHROW
- Xpath 1048576 " X: 1048576
- endif
+ catch /.*/
+ let errcaught = 1
+ call CHECK(4, 'E492', "Not an editor command",
+ \ line_before_error + 1)
endtry
- catch /.*/
- Xpath 2097152 " X: 0
- Xout v:exception "in" v:throwpoint
finally
- break " discard interrupt for $VIMNOINTTHROW
+ if !errcaught && $VIMNOERRTHROW
+ call CHECK(4)
+ endif
+ break " discard error for $VIMNOERRTHROW
endtry
endwhile
+ call CHECK(5)
+
+ Xpath 2097152 " X: 2097152
while 1
try
- let caught = 0
+ let intcaught = 0
try
- Xpath 4194304 " X: 4194304
- "INTERRUPT
- Xpath 8388608 " X: 0
- catch /do_not_catch/ "INTERRUPT
- Xpath 16777216 " X: 0
- catch /^Vim:Interrupt$/
- let caught = 1
- finally
- Xpath 33554432 " X: 33554432
- if caught || $VIMNOINTTHROW
- Xpath 67108864 " X: 67108864
- endif
+ try
+ throw "x4"
+ catch /.*/
+ SetLineNumber two_lines_before_interrupt
+ "INTERRUPT
+ let dummy = 0
+ endtry
+ catch /.*/
+ let intcaught = 1
+ call CHECK(6, "Vim:Interrupt", '',
+ \ two_lines_before_interrupt + 2)
endtry
- catch /.*/
- Xpath 134217728 " X: 0
- Xout v:exception "in" v:throwpoint
finally
+ if !intcaught && $VIMNOINTTHROW
+ call CHECK(6)
+ endif
break " discard interrupt for $VIMNOINTTHROW
endtry
endwhile
+ call CHECK(7)
- Xpath 268435456 " X: 268435456
-
-endif
-
-Xcheck 374889517
-
-
-"-------------------------------------------------------------------------------
-" Test 62: Catching error exceptions {{{1
-"
-" An error inside a :try/:endtry region is converted to an exception
-" and can be caught. The error exception has a "Vim(cmdname):" prefix
-" where cmdname is the name of the failing command, or a "Vim:" prefix
-" if no command name is known. The "Vim" prefixes cannot be faked.
-"-------------------------------------------------------------------------------
-
-XpathINIT
-
-function! MSG(enr, emsg)
- let english = v:lang == "C" || v:lang =~ '^[Ee]n'
- if a:enr == ""
- Xout "TODO: Add message number for:" a:emsg
- let v:errmsg = ":" . v:errmsg
- endif
- let match = 1
- if v:errmsg !~ '^'.a:enr.':' || (english && v:errmsg !~ a:emsg)
- let match = 0
- if v:errmsg == ""
- Xout "Message missing."
- else
- let v:errmsg = escape(v:errmsg, '"')
- Xout "Unexpected message:" v:errmsg
- endif
- endif
- return match
-endfunction
+ Xpath 4194304 " X: 4194304
-while 1
- try
+ while 1
try
- let caught = 0
- unlet novar
- catch /^Vim(unlet):/
- let caught = 1
- let v:errmsg = substitute(v:exception, '^Vim(unlet):', '', "")
+ let errcaught = 0
+ try
+ try
+" if 1
+ SetLineNumber line_before_throw
+ throw "x5"
+ " missing endif
+ catch /.*/
+ Xpath 8388608 " X: 0
+ endtry
+ catch /.*/
+ let errcaught = 1
+ call CHECK(8, 'E171', "Missing :endif", line_before_throw + 3)
+ endtry
finally
- Xpath 1 " X: 1
- if !caught && !$VIMNOERRTHROW
- Xpath 2 " X: 0
- endif
- if !MSG('E108', "No such variable")
- Xpath 4 " X: 0
+ if !errcaught && $VIMNOERRTHROW
+ call CHECK(8)
endif
+ break " discard error for $VIMNOERRTHROW
endtry
- catch /.*/
- Xpath 8 " X: 0
- Xout v:exception "in" v:throwpoint
- finally
- break " discard error for $VIMNOERRTHROW
- endtry
-endwhile
+ endwhile
+ call CHECK(9)
-while 1
- try
- try
- let caught = 0
- throw novar " error in :throw
- catch /^Vim(throw):/
- let caught = 1
- let v:errmsg = substitute(v:exception, '^Vim(throw):', '', "")
- finally
- Xpath 16 " X: 16
- if !caught && !$VIMNOERRTHROW
- Xpath 32 " X: 0
- endif
- if caught ? !MSG('E121', "Undefined variable")
- \ : !MSG('E15', "Invalid expression")
- Xpath 64 " X: 0
- endif
- endtry
- catch /.*/
- Xpath 128 " X: 0
- Xout v:exception "in" v:throwpoint
- finally
- break " discard error for $VIMNOERRTHROW
- endtry
-endwhile
+ Xpath 16777216 " X: 16777216
-while 1
try
- try
- let caught = 0
- throw "Vim:faked" " error: cannot fake Vim exception
- catch /^Vim(throw):/
- let caught = 1
- let v:errmsg = substitute(v:exception, '^Vim(throw):', '', "")
- finally
- Xpath 256 " X: 256
- if !caught && !$VIMNOERRTHROW
- Xpath 512 " X: 0
- endif
- if !MSG('E608', "Cannot :throw exceptions with 'Vim' prefix")
- Xpath 1024 " X: 0
- endif
- endtry
- catch /.*/
- Xpath 2048 " X: 0
- Xout v:exception "in" v:throwpoint
- finally
- break " discard error for $VIMNOERRTHROW
+ while 1
+ try
+ throw "x6"
+ finally
+ break
+ endtry
+ break
+ endwhile
+ catch /.*/
+ Xpath 33554432 " X: 0
endtry
-endwhile
-
-function! F()
- while 1
- " Missing :endwhile
-endfunction
+ call CHECK(10)
-while 1
try
- try
- let caught = 0
- call F()
- catch /^Vim(endfunction):/
- let caught = 1
- let v:errmsg = substitute(v:exception, '^Vim(endfunction):', '', "")
- finally
- Xpath 4096 " X: 4096
- if !caught && !$VIMNOERRTHROW
- Xpath 8192 " X: 0
- endif
- if !MSG('E170', "Missing :endwhile")
- Xpath 16384 " X: 0
- endif
- endtry
+ while 1
+ try
+ throw "x7"
+ finally
+ break
+ endtry
+ break
+ endwhile
catch /.*/
- Xpath 32768 " X: 0
- Xout v:exception "in" v:throwpoint
+ Xpath 67108864 " X: 0
finally
- break " discard error for $VIMNOERRTHROW
+ call CHECK(11)
endtry
-endwhile
+ call CHECK(12)
-while 1
- try
+ while 1
try
- let caught = 0
- ExecAsScript F
- catch /^Vim:/
- let caught = 1
- let v:errmsg = substitute(v:exception, '^Vim:', '', "")
+ let errcaught = 0
+ try
+ try
+ throw "x8"
+ finally
+ SetLineNumber line_before_error
+ asdf
+ endtry
+ catch /.*/
+ let errcaught = 1
+ call CHECK(13, 'E492', "Not an editor command",
+ \ line_before_error + 1)
+ endtry
finally
- Xpath 65536 " X: 65536
- if !caught && !$VIMNOERRTHROW
- Xpath 131072 " X: 0
- endif
- if !MSG('E170', "Missing :endwhile")
- Xpath 262144 " X: 0
+ if !errcaught && $VIMNOERRTHROW
+ call CHECK(13)
endif
+ break " discard error for $VIMNOERRTHROW
endtry
- catch /.*/
- Xpath 524288 " X: 0
- Xout v:exception "in" v:throwpoint
- finally
- break " discard error for $VIMNOERRTHROW
- endtry
-endwhile
+ endwhile
+ call CHECK(14)
-function! G()
- call G()
-endfunction
+ Xpath 134217728 " X: 134217728
-while 1
- try
- let mfd_save = &mfd
- set mfd=3
+ while 1
try
- let caught = 0
- call G()
- catch /^Vim(call):/
- let caught = 1
- let v:errmsg = substitute(v:exception, '^Vim(call):', '', "")
+ let intcaught = 0
+ try
+ try
+ throw "x9"
+ finally
+ SetLineNumber two_lines_before_interrupt
+ "INTERRUPT
+ endtry
+ catch /.*/
+ let intcaught = 1
+ call CHECK(15, "Vim:Interrupt", '',
+ \ two_lines_before_interrupt + 2)
+ endtry
finally
- Xpath 1048576 " X: 1048576
- if !caught && !$VIMNOERRTHROW
- Xpath 2097152 " X: 0
- endif
- if !MSG('E132', "Function call depth is higher than 'maxfuncdepth'")
- Xpath 4194304 " X: 0
+ if !intcaught && $VIMNOINTTHROW
+ call CHECK(15)
endif
+ break " discard interrupt for $VIMNOINTTHROW
endtry
- catch /.*/
- Xpath 8388608 " X: 0
- Xout v:exception "in" v:throwpoint
- finally
- let &mfd = mfd_save
- break " discard error for $VIMNOERRTHROW
- endtry
-endwhile
+ endwhile
+ call CHECK(16)
-function! H()
- return H()
-endfunction
+ Xpath 268435456 " X: 268435456
-while 1
- try
- let mfd_save = &mfd
- set mfd=3
+ while 1
try
- let caught = 0
- call H()
- catch /^Vim(return):/
- let caught = 1
- let v:errmsg = substitute(v:exception, '^Vim(return):', '', "")
+ let errcaught = 0
+ try
+ try
+" if 1
+ SetLineNumber line_before_throw
+ throw "x10"
+ " missing endif
+ finally
+ call CHECK(17)
+ endtry
+ catch /.*/
+ let errcaught = 1
+ call CHECK(18, 'E171', "Missing :endif", line_before_throw + 3)
+ endtry
finally
- Xpath 16777216 " X: 16777216
- if !caught && !$VIMNOERRTHROW
- Xpath 33554432 " X: 0
- endif
- if !MSG('E132', "Function call depth is higher than 'maxfuncdepth'")
- Xpath 67108864 " X: 0
+ if !errcaught && $VIMNOERRTHROW
+ call CHECK(18)
endif
+ break " discard error for $VIMNOERRTHROW
endtry
- catch /.*/
- Xpath 134217728 " X: 0
- Xout v:exception "in" v:throwpoint
- finally
- let &mfd = mfd_save
- break " discard error for $VIMNOERRTHROW
- endtry
-endwhile
-
-unlet! caught mfd_save
-delfunction F
-delfunction G
-delfunction H
-Xpath 268435456 " X: 268435456
-
-Xcheck 286331153
-
-" Leave MSG() for the next test.
-
-
-"-------------------------------------------------------------------------------
-" Test 63: Suppressing error exceptions by :silent!. {{{1
-"
-" A :silent! command inside a :try/:endtry region suppresses the
-" conversion of errors to an exception and the immediate abortion on
-" error. When the commands executed by the :silent! themselves open
-" a new :try/:endtry region, conversion of errors to exception and
-" immediate abortion is switched on again - until the next :silent!
-" etc. The :silent! has the effect of setting v:errmsg to the error
-" message text (without displaying it) and continuing with the next
-" script line.
-"
-" When a command triggering autocommands is executed by :silent!
-" inside a :try/:endtry, the autocommand execution is not suppressed
-" on error.
-"
-" This test reuses the function MSG() from the previous test.
-"-------------------------------------------------------------------------------
-
-XpathINIT
-
-XloopINIT! 1 4
-
-let taken = ""
-
-function! S(n) abort
- XloopNEXT
- let g:taken = g:taken . "E" . a:n
- let v:errmsg = ""
- exec "asdf" . a:n
-
- " Check that ":silent!" continues:
- Xloop 1
+ endwhile
+ call CHECK(19)
- " Check that ":silent!" sets "v:errmsg":
- if MSG('E492', "Not an editor command")
- Xloop 2
- endif
-endfunction
+ Xpath 536870912 " X: 536870912
-function! Foo()
while 1
try
+ let errcaught = 0
try
- let caught = 0
- " This is not silent:
- call S(3) " X: 0 * 16
- catch /^Vim:/
- let caught = 1
- let errmsg3 = substitute(v:exception, '^Vim:', '', "")
- silent! call S(4) " X: 3 * 64
- finally
- if !caught
- let errmsg3 = v:errmsg
- " Do call S(4) here if not executed in :catch.
- silent! call S(4)
- endif
- Xpath 1048576 " X: 1048576
- if !caught && !$VIMNOERRTHROW
- Xpath 2097152 " X: 0
- endif
- let v:errmsg = errmsg3
- if !MSG('E492', "Not an editor command")
- Xpath 4194304 " X: 0
- endif
- silent! call S(5) " X: 3 * 256
- " Break out of try conditionals that cover ":silent!". This also
- " discards the aborting error when $VIMNOERRTHROW is non-zero.
- break
+ try
+" if 1
+ SetLineNumber line_before_throw
+ throw "x11"
+ " missing endif
+ endtry
+ catch /.*/
+ let errcaught = 1
+ call CHECK(20, 'E171', "Missing :endif", line_before_throw + 3)
endtry
- catch /.*/
- Xpath 8388608 " X: 0
- Xout v:exception "in" v:throwpoint
+ finally
+ if !errcaught && $VIMNOERRTHROW
+ call CHECK(20)
+ endif
+ break " discard error for $VIMNOERRTHROW
endtry
endwhile
- " This is a double ":silent!" (see caller).
- silent! call S(6) " X: 3 * 1024
-endfunction
-
-function! Bar()
- try
- silent! call S(2) " X: 3 * 4
- " X: 3 * 4096
- silent! execute "call Foo() | call S(7)"
- silent! call S(8) " X: 3 * 16384
- endtry " normal end of try cond that covers ":silent!"
- " This has a ":silent!" from the caller:
- call S(9) " X: 3 * 65536
-endfunction
+ call CHECK(21)
-silent! call S(1) " X: 3 * 1
-silent! call Bar()
-silent! call S(10) " X: 3 * 262144
+ Xpath 1073741824 " X: 1073741824
-let expected = "E1E2E3E4E5E6E7E8E9E10"
-if taken != expected
- Xpath 16777216 " X: 0
- Xout "'taken' is" taken "instead of" expected
endif
-augroup TMP
- autocmd BufWritePost * Xpath 33554432 " X: 33554432
-augroup END
-
-Xpath 67108864 " X: 67108864
-write /i/m/p/o/s/s/i/b/l/e
-Xpath 134217728 " X: 134217728
-
-autocmd! TMP
-unlet! caught errmsg3 taken expected
-delfunction S
-delfunction Foo
-delfunction Bar
-delfunction MSG
-
-Xcheck 236978127
+Xcheck 2038431743
"-------------------------------------------------------------------------------
-" Test 64: Error exceptions after error, interrupt or :throw {{{1
"
-" When an error occurs after an interrupt or a :throw but before
-" a matching :catch is reached, all following :catches of that try
-" block are ignored, but the error exception can be caught by the next
-" surrounding try conditional. Any previous error exception is
-" discarded. An error is ignored when there is a previous error that
-" has not been caught.
+" Test 60: (Re)throwing v:exception; :echoerr. {{{1
+"
+" A user exception can be rethrown after catching by throwing
+" v:exception. An error or interrupt exception cannot be rethrown
+" because Vim exceptions cannot be faked. A Vim exception using the
+" value of v:exception can, however, be triggered by the :echoerr
+" command.
"-------------------------------------------------------------------------------
XpathINIT
-if ExtraVim()
+try
+ try
+ Xpath 1 " X: 1
+ throw "oops"
+ catch /oops/
+ Xpath 2 " X: 2
+ throw v:exception " rethrow user exception
+ catch /.*/
+ Xpath 4 " X: 0
+ endtry
+catch /^oops$/ " catches rethrown user exception
+ Xpath 8 " X: 8
+catch /.*/
+ Xpath 16 " X: 0
+endtry
- while 1
+function! F()
+ try
+ let caught = 0
try
- try
- Xpath 1 " X: 1
- let caught = 0
- while 1
-" if 1
- " Missing :endif
- endwhile " throw error exception
- catch /^Vim(/
- let caught = 1
- finally
- Xpath 2 " X: 2
- if caught || $VIMNOERRTHROW
- Xpath 4 " X: 4
- endif
- endtry
+ Xpath 32 " X: 32
+ write /n/o/n/w/r/i/t/a/b/l/e/_/f/i/l/e
+ Xpath 64 " X: 0
+ Xout "did_emsg was reset before executing " .
+ \ "BufWritePost autocommands."
+ catch /^Vim(write):/
+ let caught = 1
+ throw v:exception " throw error: cannot fake Vim exception
catch /.*/
- Xpath 8 " X: 0
- Xout v:exception "in" v:throwpoint
+ Xpath 128 " X: 0
finally
- break " discard error for $VIMNOERRTHROW
+ Xpath 256 " X: 256
+ if !caught && !$VIMNOERRTHROW
+ Xpath 512 " X: 0
+ endif
endtry
- endwhile
+ catch /^Vim(throw):/ " catches throw error
+ let caught = caught + 1
+ catch /.*/
+ Xpath 1024 " X: 0
+ finally
+ Xpath 2048 " X: 2048
+ if caught != 2
+ if !caught && !$VIMNOERRTHROW
+ Xpath 4096 " X: 0
+ elseif caught
+ Xpath 8192 " X: 0
+ endif
+ return | " discard error for $VIMNOERRTHROW
+ endif
+ endtry
+endfunction
- while 1
+call F()
+delfunction F
+
+function! G()
+ try
+ let caught = 0
try
- try
- Xpath 16 " X: 16
- let caught = 0
- try
-" if 1
- " Missing :endif
- catch /.*/ " throw error exception
- Xpath 32 " X: 0
- catch /.*/
- Xpath 64 " X: 0
- endtry
- catch /^Vim(/
- let caught = 1
- finally
- Xpath 128 " X: 128
- if caught || $VIMNOERRTHROW
- Xpath 256 " X: 256
+ Xpath 16384 " X: 16384
+ asdf
+ catch /^Vim/ " catch error exception
+ let caught = 1
+ " Trigger Vim error exception with value specified after :echoerr
+ let value = substitute(v:exception, '^Vim\((.*)\)\=:', '', "")
+ echoerr value
+ catch /.*/
+ Xpath 32768 " X: 0
+ finally
+ Xpath 65536 " X: 65536
+ if !caught
+ if !$VIMNOERRTHROW
+ Xpath 131072 " X: 0
+ else
+ let value = "Error"
+ echoerr value
endif
- endtry
+ endif
+ endtry
+ catch /^Vim(echoerr):/
+ let caught = caught + 1
+ if v:exception !~ value
+ Xpath 262144 " X: 0
+ endif
+ catch /.*/
+ Xpath 524288 " X: 0
+ finally
+ Xpath 1048576 " X: 1048576
+ if caught != 2
+ if !caught && !$VIMNOERRTHROW
+ Xpath 2097152 " X: 0
+ elseif caught
+ Xpath 4194304 " X: 0
+ endif
+ return | " discard error for $VIMNOERRTHROW
+ endif
+ endtry
+endfunction
+
+call G()
+delfunction G
+
+unlet! value caught
+
+if ExtraVim()
+ try
+ let errcaught = 0
+ try
+ Xpath 8388608 " X: 8388608
+ let intcaught = 0
+ "INTERRUPT
+ catch /^Vim:/ " catch interrupt exception
+ let intcaught = 1
+ " Trigger Vim error exception with value specified after :echoerr
+ echoerr substitute(v:exception, '^Vim\((.*)\)\=:', '', "")
catch /.*/
- Xpath 512 " X: 0
- Xout v:exception "in" v:throwpoint
+ Xpath 16777216 " X: 0
finally
- break " discard error for $VIMNOERRTHROW
+ Xpath 33554432 " X: 33554432
+ if !intcaught
+ if !$VIMNOINTTHROW
+ Xpath 67108864 " X: 0
+ else
+ echoerr "Interrupt"
+ endif
+ endif
endtry
- endwhile
+ catch /^Vim(echoerr):/
+ let errcaught = 1
+ if v:exception !~ "Interrupt"
+ Xpath 134217728 " X: 0
+ endif
+ finally
+ Xpath 268435456 " X: 268435456
+ if !errcaught && !$VIMNOERRTHROW
+ Xpath 536870912 " X: 0
+ endif
+ endtry
+endif
+
+Xcheck 311511339
+
+
+"-------------------------------------------------------------------------------
+" Test 61: Catching interrupt exceptions {{{1
+"
+" When an interrupt occurs inside a :try/:endtry region, an
+" interrupt exception is thrown and can be caught. Its value is
+" "Vim:Interrupt". If the interrupt occurs after an error or a :throw
+" but before a matching :catch is reached, all following :catches of
+" that try block are ignored, but the interrupt exception can be
+" caught by the next surrounding try conditional. An interrupt is
+" ignored when there is a previous interrupt that has not been caught
+" or causes a :finally clause to be executed.
+"-------------------------------------------------------------------------------
+
+XpathINIT
+
+if ExtraVim()
while 1
try
try
+ Xpath 1 " X: 1
let caught = 0
- try
- Xpath 1024 " X: 1024
- "INTERRUPT
- catch /do_not_catch/
- Xpath 2048 " X: 0
-" if 1
- " Missing :endif
- catch /.*/ " throw error exception
- Xpath 4096 " X: 0
- catch /.*/
- Xpath 8192 " X: 0
- endtry
- catch /^Vim(/
+ "INTERRUPT
+ Xpath 2 " X: 0
+ catch /^Vim:Interrupt$/
let caught = 1
finally
- Xpath 16384 " X: 16384
- if caught || $VIMNOERRTHROW
- Xpath 32768 " X: 32768
+ Xpath 4 " X: 4
+ if caught || $VIMNOINTTHROW
+ Xpath 8 " X: 8
endif
endtry
catch /.*/
- Xpath 65536 " X: 0
+ Xpath 16 " X: 0
Xout v:exception "in" v:throwpoint
finally
- break " discard error for $VIMNOERRTHROW
+ break " discard interrupt for $VIMNOINTTHROW
endtry
endwhile
try
let caught = 0
try
- Xpath 131072 " X: 131072
- throw "x"
+ Xpath 32 " X: 32
+ asdf
+ Xpath 64 " X: 0
catch /do_not_catch/
- Xpath 262144 " X: 0
-" if 1
- " Missing :endif
- catch /x/ " throw error exception
- Xpath 524288 " X: 0
+ Xpath 128 " X: 0
+ catch /.*/ "INTERRUPT - throw interrupt if !$VIMNOERRTHROW
+ Xpath 256 " X: 0
catch /.*/
- Xpath 1048576 " X: 0
+ Xpath 512 " X: 0
+ finally "INTERRUPT - throw interrupt if $VIMNOERRTHROW
+ Xpath 1024 " X: 1024
endtry
- catch /^Vim(/
+ catch /^Vim:Interrupt$/
let caught = 1
finally
- Xpath 2097152 " X: 2097152
- if caught || $VIMNOERRTHROW
- Xpath 4194304 " X: 4194304
+ Xpath 2048 " X: 2048
+ if caught || $VIMNOINTTHROW
+ Xpath 4096 " X: 4096
endif
endtry
catch /.*/
- Xpath 8388608 " X: 0
+ Xpath 8192 " X: 0
Xout v:exception "in" v:throwpoint
finally
- break " discard error for $VIMNOERRTHROW
+ break " discard interrupt for $VIMNOINTTHROW
endtry
endwhile
try
try
let caught = 0
- Xpath 16777216 " X: 16777216
-" endif " :endif without :if; throw error exception
-" if 1
- " Missing :endif
- catch /do_not_catch/ " ignore new error
- Xpath 33554432 " X: 0
- catch /^Vim(endif):/
+ try
+ Xpath 16384 " X: 16384
+ throw "x"
+ Xpath 32768 " X: 0
+ catch /do_not_catch/
+ Xpath 65536 " X: 0
+ catch /x/ "INTERRUPT
+ Xpath 131072 " X: 0
+ catch /.*/
+ Xpath 262144 " X: 0
+ endtry
+ catch /^Vim:Interrupt$/
let caught = 1
- catch /^Vim(/
- Xpath 67108864 " X: 0
finally
- Xpath 134217728 " X: 134217728
- if caught || $VIMNOERRTHROW
- Xpath 268435456 " X: 268435456
+ Xpath 524288 " X: 524288
+ if caught || $VIMNOINTTHROW
+ Xpath 1048576 " X: 1048576
endif
endtry
catch /.*/
- Xpath 536870912 " X: 0
+ Xpath 2097152 " X: 0
Xout v:exception "in" v:throwpoint
- finally
- break " discard error for $VIMNOERRTHROW
- endtry
- endwhile
-
- Xpath 1073741824 " X: 1073741824
-
-endif
-
-Xcheck 1499645335
-
-
-"-------------------------------------------------------------------------------
-" Test 65: Errors in the /pattern/ argument of a :catch {{{1
-"
-" On an error in the /pattern/ argument of a :catch, the :catch does
-" not match. Any following :catches of the same :try/:endtry don't
-" match either. Finally clauses are executed.
-"-------------------------------------------------------------------------------
-
-XpathINIT
-
-function! MSG(enr, emsg)
- let english = v:lang == "C" || v:lang =~ '^[Ee]n'
- if a:enr == ""
- Xout "TODO: Add message number for:" a:emsg
- let v:errmsg = ":" . v:errmsg
- endif
- let match = 1
- if v:errmsg !~ '^'.a:enr.':' || (english && v:errmsg !~ a:emsg)
- let match = 0
- if v:errmsg == ""
- Xout "Message missing."
- else
- let v:errmsg = escape(v:errmsg, '"')
- Xout "Unexpected message:" v:errmsg
- endif
- endif
- return match
-endfunction
-
-try
- try
- Xpath 1 " X: 1
- throw "oops"
- catch /^oops$/
- Xpath 2 " X: 2
- catch /\)/ " not checked; exception has already been caught
- Xpath 4 " X: 0
- endtry
- Xpath 8 " X: 8
-catch /.*/
- Xpath 16 " X: 0
- Xout v:exception "in" v:throwpoint
-endtry
-
-function! F()
- try
- let caught = 0
- try
- try
- Xpath 32 " X: 32
- throw "ab"
- catch /abc/ " does not catch
- Xpath 64 " X: 0
- catch /\)/ " error; discards exception
- Xpath 128 " X: 0
- catch /.*/ " not checked
- Xpath 256 " X: 0
- finally
- Xpath 512 " X: 512
- endtry
- Xpath 1024 " X: 0
- catch /^ab$/ " checked, but original exception is discarded
- Xpath 2048 " X: 0
- catch /^Vim(catch):/
- let caught = 1
- let v:errmsg = substitute(v:exception, '^Vim(catch):', '', "")
- finally
- Xpath 4096 " X: 4096
- if !caught && !$VIMNOERRTHROW
- Xpath 8192 " X: 0
- endif
- if !MSG('E475', "Invalid argument")
- Xpath 16384 " X: 0
- endif
- if !caught
- return | " discard error
- endif
- endtry
- catch /.*/
- Xpath 32768 " X: 0
- Xout v:exception "in" v:throwpoint
- endtry
-endfunction
-
-call F()
-Xpath 65536 " X: 65536
-
-delfunction MSG
-delfunction F
-unlet! caught
-
-Xcheck 70187
-
-
-"-------------------------------------------------------------------------------
-" Test 66: Stop range :call on error, interrupt, or :throw {{{1
-"
-" When a function which is multiply called for a range since it
-" doesn't handle the range itself has an error in a command
-" dynamically enclosed by :try/:endtry or gets an interrupt or
-" executes a :throw, no more calls for the remaining lines in the
-" range are made. On an error in a command not dynamically enclosed
-" by :try/:endtry, the function is executed again for the remaining
-" lines in the range.
-"-------------------------------------------------------------------------------
-
-XpathINIT
-
-if ExtraVim()
-
- let file = tempname()
- exec "edit" file
-
- insert
-line 1
-line 2
-line 3
-.
-
- XloopINIT! 1 2
-
- let taken = ""
- let expected = "G1EF1E(1)F1E(2)F1E(3)G2EF2E(1)G3IF3I(1)G4TF4T(1)G5AF5A(1)"
-
- function! F(reason, n) abort
- let g:taken = g:taken . "F" . a:n .
- \ substitute(a:reason, '\(\l\).*', '\u\1', "") .
- \ "(" . line(".") . ")"
-
- if a:reason == "error"
- asdf
- elseif a:reason == "interrupt"
- "INTERRUPT
- let dummy = 0
- elseif a:reason == "throw"
- throw "xyz"
- elseif a:reason == "aborting error"
- XloopNEXT
- if g:taken != g:expected
- Xloop 1 " X: 0
- Xout "'taken' is" g:taken "instead of" g:expected
- endif
- try
- bwipeout!
- call delete(file)
- asdf
- endtry
- endif
- endfunction
-
- function! G(reason, n)
- let g:taken = g:taken . "G" . a:n .
- \ substitute(a:reason, '\(\l\).*', '\u\1', "")
- 1,3call F(a:reason, a:n)
- endfunction
+ finally
+ break " discard interrupt for $VIMNOINTTHROW
+ endtry
+ endwhile
- Xpath 8 " X: 8
- call G("error", 1)
- try
- Xpath 16 " X: 16
+ while 1
try
- call G("error", 2)
- Xpath 32 " X: 0
- finally
- Xpath 64 " X: 64
+ let caught = 0
try
- call G("interrupt", 3)
- Xpath 128 " X: 0
+ Xpath 4194304 " X: 4194304
+ "INTERRUPT
+ Xpath 8388608 " X: 0
+ catch /do_not_catch/ "INTERRUPT
+ Xpath 16777216 " X: 0
+ catch /^Vim:Interrupt$/
+ let caught = 1
finally
- Xpath 256 " X: 256
- try
- call G("throw", 4)
- Xpath 512 " X: 0
- endtry
+ Xpath 33554432 " X: 33554432
+ if caught || $VIMNOINTTHROW
+ Xpath 67108864 " X: 67108864
+ endif
endtry
+ catch /.*/
+ Xpath 134217728 " X: 0
+ Xout v:exception "in" v:throwpoint
+ finally
+ break " discard interrupt for $VIMNOINTTHROW
endtry
- catch /xyz/
- Xpath 1024 " X: 1024
- catch /.*/
- Xpath 2048 " X: 0
- Xout v:exception "in" ExtraVimThrowpoint()
- endtry
- Xpath 4096 " X: 4096
- call G("aborting error", 5)
- Xpath 8192 " X: 0
- Xout "'taken' is" taken "instead of" expected
+ endwhile
+
+ Xpath 268435456 " X: 268435456
endif
-Xcheck 5464
+Xcheck 374889517
"-------------------------------------------------------------------------------
-" Test 67: :throw across :call command {{{1
+" Test 62: Catching error exceptions {{{1
"
-" On a call command, an exception might be thrown when evaluating the
-" function name, during evaluation of the arguments, or when the
-" function is being executed. The exception can be caught by the
-" caller.
+" An error inside a :try/:endtry region is converted to an exception
+" and can be caught. The error exception has a "Vim(cmdname):" prefix
+" where cmdname is the name of the failing command, or a "Vim:" prefix
+" if no command name is known. The "Vim" prefixes cannot be faked.
"-------------------------------------------------------------------------------
XpathINIT
-function! THROW(x, n)
- if a:n == 1
- Xpath 1 " X: 1
- elseif a:n == 2
- Xpath 2 " X: 2
- elseif a:n == 3
- Xpath 4 " X: 4
- endif
- throw a:x
-endfunction
-
-function! NAME(x, n)
- if a:n == 1
- Xpath 8 " X: 0
- elseif a:n == 2
- Xpath 16 " X: 16
- elseif a:n == 3
- Xpath 32 " X: 32
- elseif a:n == 4
- Xpath 64 " X: 64
- endif
- return a:x
-endfunction
-
-function! ARG(x, n)
- if a:n == 1
- Xpath 128 " X: 0
- elseif a:n == 2
- Xpath 256 " X: 0
- elseif a:n == 3
- Xpath 512 " X: 512
- elseif a:n == 4
- Xpath 1024 " X: 1024
+function! MSG(enr, emsg)
+ let english = v:lang == "C" || v:lang =~ '^[Ee]n'
+ if a:enr == ""
+ Xout "TODO: Add message number for:" a:emsg
+ let v:errmsg = ":" . v:errmsg
endif
- return a:x
-endfunction
-
-function! F(x, n)
- if a:n == 2
- Xpath 2048 " X: 0
- elseif a:n == 4
- Xpath 4096 " X: 4096
+ let match = 1
+ if v:errmsg !~ '^'.a:enr.':' || (english && v:errmsg !~ a:emsg)
+ let match = 0
+ if v:errmsg == ""
+ Xout "Message missing."
+ else
+ let v:errmsg = escape(v:errmsg, '"')
+ Xout "Unexpected message:" v:errmsg
+ endif
endif
+ return match
endfunction
while 1
try
- let error = 0
- let v:errmsg = ""
-
- while 1
- try
- Xpath 8192 " X: 8192
- call {NAME(THROW("name", 1), 1)}(ARG(4711, 1), 1)
- Xpath 16384 " X: 0
- catch /^name$/
- Xpath 32768 " X: 32768
- catch /.*/
- let error = 1
- Xout "1:" v:exception "in" v:throwpoint
- finally
- if !error && $VIMNOERRTHROW && v:errmsg != ""
- let error = 1
- Xout "1:" v:errmsg
- endif
- if error
- Xpath 65536 " X: 0
- endif
- let error = 0
- let v:errmsg = ""
- break " discard error for $VIMNOERRTHROW
- endtry
- endwhile
-
- while 1
- try
- Xpath 131072 " X: 131072
- call {NAME("F", 2)}(ARG(THROW("arg", 2), 2), 2)
- Xpath 262144 " X: 0
- catch /^arg$/
- Xpath 524288 " X: 524288
- catch /.*/
- let error = 1
- Xout "2:" v:exception "in" v:throwpoint
- finally
- if !error && $VIMNOERRTHROW && v:errmsg != ""
- let error = 1
- Xout "2:" v:errmsg
- endif
- if error
- Xpath 1048576 " X: 0
- endif
- let error = 0
- let v:errmsg = ""
- break " discard error for $VIMNOERRTHROW
- endtry
- endwhile
-
- while 1
- try
- Xpath 2097152 " X: 2097152
- call {NAME("THROW", 3)}(ARG("call", 3), 3)
- Xpath 4194304 " X: 0
- catch /^call$/
- Xpath 8388608 " X: 8388608
- catch /^0$/ " default return value
- Xpath 16777216 " X: 0
- Xout "3:" v:throwpoint
- catch /.*/
- let error = 1
- Xout "3:" v:exception "in" v:throwpoint
- finally
- if !error && $VIMNOERRTHROW && v:errmsg != ""
- let error = 1
- Xout "3:" v:errmsg
- endif
- if error
- Xpath 33554432 " X: 0
- endif
- let error = 0
- let v:errmsg = ""
- break " discard error for $VIMNOERRTHROW
- endtry
- endwhile
-
- while 1
- try
- Xpath 67108864 " X: 67108864
- call {NAME("F", 4)}(ARG(4711, 4), 4)
- Xpath 134217728 " X: 134217728
- catch /.*/
- let error = 1
- Xout "4:" v:exception "in" v:throwpoint
- finally
- if !error && $VIMNOERRTHROW && v:errmsg != ""
- let error = 1
- Xout "4:" v:errmsg
- endif
- if error
- Xpath 268435456 " X: 0
- endif
- let error = 0
- let v:errmsg = ""
- break " discard error for $VIMNOERRTHROW
- endtry
- endwhile
+ try
+ let caught = 0
+ unlet novar
+ catch /^Vim(unlet):/
+ let caught = 1
+ let v:errmsg = substitute(v:exception, '^Vim(unlet):', '', "")
+ finally
+ Xpath 1 " X: 1
+ if !caught && !$VIMNOERRTHROW
+ Xpath 2 " X: 0
+ endif
+ if !MSG('E108', "No such variable")
+ Xpath 4 " X: 0
+ endif
+ endtry
+ catch /.*/
+ Xpath 8 " X: 0
+ Xout v:exception "in" v:throwpoint
+ finally
+ break " discard error for $VIMNOERRTHROW
+ endtry
+endwhile
- catch /^0$/ " default return value
- Xpath 536870912 " X: 0
- Xout v:throwpoint
+while 1
+ try
+ try
+ let caught = 0
+ throw novar " error in :throw
+ catch /^Vim(throw):/
+ let caught = 1
+ let v:errmsg = substitute(v:exception, '^Vim(throw):', '', "")
+ finally
+ Xpath 16 " X: 16
+ if !caught && !$VIMNOERRTHROW
+ Xpath 32 " X: 0
+ endif
+ if caught ? !MSG('E121', "Undefined variable")
+ \ : !MSG('E15', "Invalid expression")
+ Xpath 64 " X: 0
+ endif
+ endtry
catch /.*/
- let error = 1
+ Xpath 128 " X: 0
Xout v:exception "in" v:throwpoint
finally
- if !error && $VIMNOERRTHROW && v:errmsg != ""
- let error = 1
- Xout v:errmsg
- endif
- if error
- Xpath 1073741824 " X: 0
- endif
break " discard error for $VIMNOERRTHROW
endtry
endwhile
-unlet error
-delfunction F
-
-Xcheck 212514423
-
-" Leave THROW(), NAME(), and ARG() for the next test.
-
-
-"-------------------------------------------------------------------------------
-" Test 68: :throw across function calls in expressions {{{1
-"
-" On a function call within an expression, an exception might be
-" thrown when evaluating the function name, during evaluation of the
-" arguments, or when the function is being executed. The exception
-" can be caught by the caller.
-"
-" This test reuses the functions THROW(), NAME(), and ARG() from the
-" previous test.
-"-------------------------------------------------------------------------------
-
-XpathINIT
+while 1
+ try
+ try
+ let caught = 0
+ throw "Vim:faked" " error: cannot fake Vim exception
+ catch /^Vim(throw):/
+ let caught = 1
+ let v:errmsg = substitute(v:exception, '^Vim(throw):', '', "")
+ finally
+ Xpath 256 " X: 256
+ if !caught && !$VIMNOERRTHROW
+ Xpath 512 " X: 0
+ endif
+ if !MSG('E608', "Cannot :throw exceptions with 'Vim' prefix")
+ Xpath 1024 " X: 0
+ endif
+ endtry
+ catch /.*/
+ Xpath 2048 " X: 0
+ Xout v:exception "in" v:throwpoint
+ finally
+ break " discard error for $VIMNOERRTHROW
+ endtry
+endwhile
-function! F(x, n)
- if a:n == 2
- Xpath 2048 " X: 0
- elseif a:n == 4
- Xpath 4096 " X: 4096
- endif
- return a:x
+function! F()
+ while 1
+ " Missing :endwhile
endfunction
-unlet! var1 var2 var3 var4
-
while 1
try
- let error = 0
- let v:errmsg = ""
+ try
+ let caught = 0
+ call F()
+ catch /^Vim(endfunction):/
+ let caught = 1
+ let v:errmsg = substitute(v:exception, '^Vim(endfunction):', '', "")
+ finally
+ Xpath 4096 " X: 4096
+ if !caught && !$VIMNOERRTHROW
+ Xpath 8192 " X: 0
+ endif
+ if !MSG('E170', "Missing :endwhile")
+ Xpath 16384 " X: 0
+ endif
+ endtry
+ catch /.*/
+ Xpath 32768 " X: 0
+ Xout v:exception "in" v:throwpoint
+ finally
+ break " discard error for $VIMNOERRTHROW
+ endtry
+endwhile
- while 1
- try
- Xpath 8192 " X: 8192
- let var1 = {NAME(THROW("name", 1), 1)}(ARG(4711, 1), 1)
- Xpath 16384 " X: 0
- catch /^name$/
- Xpath 32768 " X: 32768
- catch /.*/
- let error = 1
- Xout "1:" v:exception "in" v:throwpoint
- finally
- if !error && $VIMNOERRTHROW && v:errmsg != ""
- let error = 1
- Xout "1:" v:errmsg
- endif
- if error
- Xpath 65536 " X: 0
- endif
- let error = 0
- let v:errmsg = ""
- break " discard error for $VIMNOERRTHROW
- endtry
- endwhile
+while 1
+ try
+ try
+ let caught = 0
+ ExecAsScript F
+ catch /^Vim:/
+ let caught = 1
+ let v:errmsg = substitute(v:exception, '^Vim:', '', "")
+ finally
+ Xpath 65536 " X: 65536
+ if !caught && !$VIMNOERRTHROW
+ Xpath 131072 " X: 0
+ endif
+ if !MSG('E170', "Missing :endwhile")
+ Xpath 262144 " X: 0
+ endif
+ endtry
+ catch /.*/
+ Xpath 524288 " X: 0
+ Xout v:exception "in" v:throwpoint
+ finally
+ break " discard error for $VIMNOERRTHROW
+ endtry
+endwhile
- while 1
- try
- Xpath 131072 " X: 131072
- let var2 = {NAME("F", 2)}(ARG(THROW("arg", 2), 2), 2)
- Xpath 262144 " X: 0
- catch /^arg$/
- Xpath 524288 " X: 524288
- catch /.*/
- let error = 1
- Xout "2:" v:exception "in" v:throwpoint
- finally
- if !error && $VIMNOERRTHROW && v:errmsg != ""
- let error = 1
- Xout "2:" v:errmsg
- endif
- if error
- Xpath 1048576 " X: 0
- endif
- let error = 0
- let v:errmsg = ""
- break " discard error for $VIMNOERRTHROW
- endtry
- endwhile
+function! G()
+ call G()
+endfunction
- while 1
- try
- Xpath 2097152 " X: 2097152
- let var3 = {NAME("THROW", 3)}(ARG("call", 3), 3)
- Xpath 4194304 " X: 0
- catch /^call$/
- Xpath 8388608 " X: 8388608
- catch /^0$/ " default return value
- Xpath 16777216 " X: 0
- Xout "3:" v:throwpoint
- catch /.*/
- let error = 1
- Xout "3:" v:exception "in" v:throwpoint
- finally
- if !error && $VIMNOERRTHROW && v:errmsg != ""
- let error = 1
- Xout "3:" v:errmsg
- endif
- if error
- Xpath 33554432 " X: 0
- endif
- let error = 0
- let v:errmsg = ""
- break " discard error for $VIMNOERRTHROW
- endtry
- endwhile
+while 1
+ try
+ let mfd_save = &mfd
+ set mfd=3
+ try
+ let caught = 0
+ call G()
+ catch /^Vim(call):/
+ let caught = 1
+ let v:errmsg = substitute(v:exception, '^Vim(call):', '', "")
+ finally
+ Xpath 1048576 " X: 1048576
+ if !caught && !$VIMNOERRTHROW
+ Xpath 2097152 " X: 0
+ endif
+ if !MSG('E132', "Function call depth is higher than 'maxfuncdepth'")
+ Xpath 4194304 " X: 0
+ endif
+ endtry
+ catch /.*/
+ Xpath 8388608 " X: 0
+ Xout v:exception "in" v:throwpoint
+ finally
+ let &mfd = mfd_save
+ break " discard error for $VIMNOERRTHROW
+ endtry
+endwhile
- while 1
- try
- Xpath 67108864 " X: 67108864
- let var4 = {NAME("F", 4)}(ARG(4711, 4), 4)
- Xpath 134217728 " X: 134217728
- catch /.*/
- let error = 1
- Xout "4:" v:exception "in" v:throwpoint
- finally
- if !error && $VIMNOERRTHROW && v:errmsg != ""
- let error = 1
- Xout "4:" v:errmsg
- endif
- if error
- Xpath 268435456 " X: 0
- endif
- let error = 0
- let v:errmsg = ""
- break " discard error for $VIMNOERRTHROW
- endtry
- endwhile
+function! H()
+ return H()
+endfunction
- catch /^0$/ " default return value
- Xpath 536870912 " X: 0
- Xout v:throwpoint
+while 1
+ try
+ let mfd_save = &mfd
+ set mfd=3
+ try
+ let caught = 0
+ call H()
+ catch /^Vim(return):/
+ let caught = 1
+ let v:errmsg = substitute(v:exception, '^Vim(return):', '', "")
+ finally
+ Xpath 16777216 " X: 16777216
+ if !caught && !$VIMNOERRTHROW
+ Xpath 33554432 " X: 0
+ endif
+ if !MSG('E132', "Function call depth is higher than 'maxfuncdepth'")
+ Xpath 67108864 " X: 0
+ endif
+ endtry
catch /.*/
- let error = 1
+ Xpath 134217728 " X: 0
Xout v:exception "in" v:throwpoint
finally
- if !error && $VIMNOERRTHROW && v:errmsg != ""
- let error = 1
- Xout v:errmsg
- endif
- if error
- Xpath 1073741824 " X: 0
- endif
+ let &mfd = mfd_save
break " discard error for $VIMNOERRTHROW
endtry
endwhile
-if exists("var1") || exists("var2") || exists("var3") ||
- \ !exists("var4") || var4 != 4711
- " The Xpath command does not accept 2^31 (negative); add explicitly:
- let Xpath = Xpath + 2147483648 " X: 0
- if exists("var1")
- Xout "var1 =" var1
- endif
- if exists("var2")
- Xout "var2 =" var2
- endif
- if exists("var3")
- Xout "var3 =" var3
- endif
- if !exists("var4")
- Xout "var4 unset"
- elseif var4 != 4711
- Xout "var4 =" var4
- endif
-endif
-
-unlet! error var1 var2 var3 var4
-delfunction THROW
-delfunction NAME
-delfunction ARG
+unlet! caught mfd_save
delfunction F
+delfunction G
+delfunction H
+Xpath 268435456 " X: 268435456
-Xcheck 212514423
+Xcheck 286331153
+
+" Leave MSG() for the next test.
"-------------------------------------------------------------------------------
-" Test 69: :throw across :if, :elseif, :while {{{1
+" Test 63: Suppressing error exceptions by :silent!. {{{1
+"
+" A :silent! command inside a :try/:endtry region suppresses the
+" conversion of errors to an exception and the immediate abortion on
+" error. When the commands executed by the :silent! themselves open
+" a new :try/:endtry region, conversion of errors to exception and
+" immediate abortion is switched on again - until the next :silent!
+" etc. The :silent! has the effect of setting v:errmsg to the error
+" message text (without displaying it) and continuing with the next
+" script line.
+"
+" When a command triggering autocommands is executed by :silent!
+" inside a :try/:endtry, the autocommand execution is not suppressed
+" on error.
"
-" On an :if, :elseif, or :while command, an exception might be thrown
-" during evaluation of the expression to test. The exception can be
-" caught by the script.
+" This test reuses the function MSG() from the previous test.
"-------------------------------------------------------------------------------
XpathINIT
-XloopINIT! 1 2
+XloopINIT! 1 4
+
+let taken = ""
-function! THROW(x)
+function! S(n) abort
XloopNEXT
- Xloop 1 " X: 1 + 2 + 4
- throw a:x
+ let g:taken = g:taken . "E" . a:n
+ let v:errmsg = ""
+ exec "asdf" . a:n
+
+ " Check that ":silent!" continues:
+ Xloop 1
+
+ " Check that ":silent!" sets "v:errmsg":
+ if MSG('E492', "Not an editor command")
+ Xloop 2
+ endif
endfunction
-try
+function! Foo()
+ while 1
+ try
+ try
+ let caught = 0
+ " This is not silent:
+ call S(3) " X: 0 * 16
+ catch /^Vim:/
+ let caught = 1
+ let errmsg3 = substitute(v:exception, '^Vim:', '', "")
+ silent! call S(4) " X: 3 * 64
+ finally
+ if !caught
+ let errmsg3 = v:errmsg
+ " Do call S(4) here if not executed in :catch.
+ silent! call S(4)
+ endif
+ Xpath 1048576 " X: 1048576
+ if !caught && !$VIMNOERRTHROW
+ Xpath 2097152 " X: 0
+ endif
+ let v:errmsg = errmsg3
+ if !MSG('E492', "Not an editor command")
+ Xpath 4194304 " X: 0
+ endif
+ silent! call S(5) " X: 3 * 256
+ " Break out of try conditionals that cover ":silent!". This also
+ " discards the aborting error when $VIMNOERRTHROW is non-zero.
+ break
+ endtry
+ catch /.*/
+ Xpath 8388608 " X: 0
+ Xout v:exception "in" v:throwpoint
+ endtry
+ endwhile
+ " This is a double ":silent!" (see caller).
+ silent! call S(6) " X: 3 * 1024
+endfunction
+function! Bar()
try
- Xpath 8 " X: 8
- if 4711 == THROW("if") + 111
- Xpath 16 " X: 0
- else
- Xpath 32 " X: 0
- endif
- Xpath 64 " X: 0
- catch /^if$/
- Xpath 128 " X: 128
- catch /.*/
- Xpath 256 " X: 0
- Xout "if:" v:exception "in" v:throwpoint
- endtry
+ silent! call S(2) " X: 3 * 4
+ " X: 3 * 4096
+ silent! execute "call Foo() | call S(7)"
+ silent! call S(8) " X: 3 * 16384
+ endtry " normal end of try cond that covers ":silent!"
+ " This has a ":silent!" from the caller:
+ call S(9) " X: 3 * 65536
+endfunction
- try
- Xpath 512 " X: 512
- if 4711 == 4 + 7 + 1 + 1
- Xpath 1024 " X: 0
- elseif 4711 == THROW("elseif") + 222
- Xpath 2048 " X: 0
- else
- Xpath 4096 " X: 0
- endif
- Xpath 8192 " X: 0
- catch /^elseif$/
- Xpath 16384 " X: 16384
- catch /.*/
- Xpath 32768 " X: 0
- Xout "elseif:" v:exception "in" v:throwpoint
- endtry
+silent! call S(1) " X: 3 * 1
+silent! call Bar()
+silent! call S(10) " X: 3 * 262144
- try
- Xpath 65536 " X: 65536
- while 4711 == THROW("while") + 4711
- Xpath 131072 " X: 0
- break
- endwhile
- Xpath 262144 " X: 0
- catch /^while$/
- Xpath 524288 " X: 524288
- catch /.*/
- Xpath 1048576 " X: 0
- Xout "while:" v:exception "in" v:throwpoint
- endtry
+let expected = "E1E2E3E4E5E6E7E8E9E10"
+if taken != expected
+ Xpath 16777216 " X: 0
+ Xout "'taken' is" taken "instead of" expected
+endif
-catch /^0$/ " default return value
- Xpath 2097152 " X: 0
- Xout v:throwpoint
-catch /.*/
- Xout v:exception "in" v:throwpoint
- Xpath 4194304 " X: 0
-endtry
+augroup TMP
+ autocmd BufWritePost * Xpath 33554432 " X: 33554432
+augroup END
-Xpath 8388608 " X: 8388608
+Xpath 67108864 " X: 67108864
+write /i/m/p/o/s/s/i/b/l/e
+Xpath 134217728 " X: 134217728
-delfunction THROW
+autocmd! TMP
+unlet! caught errmsg3 taken expected
+delfunction S
+delfunction Foo
+delfunction Bar
+delfunction MSG
-Xcheck 8995471
+Xcheck 236978127
"-------------------------------------------------------------------------------
-" Test 70: :throw across :return or :throw {{{1
+" Test 64: Error exceptions after error, interrupt or :throw {{{1
"
-" On a :return or :throw command, an exception might be thrown during
-" evaluation of the expression to return or throw, respectively. The
-" exception can be caught by the script.
+" When an error occurs after an interrupt or a :throw but before
+" a matching :catch is reached, all following :catches of that try
+" block are ignored, but the error exception can be caught by the next
+" surrounding try conditional. Any previous error exception is
+" discarded. An error is ignored when there is a previous error that
+" has not been caught.
"-------------------------------------------------------------------------------
XpathINIT
-let taken = ""
-
-function! THROW(x, n)
- let g:taken = g:taken . "T" . a:n
- throw a:x
-endfunction
-
-function! F(x, y, n)
- let g:taken = g:taken . "F" . a:n
- return a:x + THROW(a:y, a:n)
-endfunction
-
-function! G(x, y, n)
- let g:taken = g:taken . "G" . a:n
- throw a:x . THROW(a:y, a:n)
- return a:x
-endfunction
-
-try
- try
- Xpath 1 " X: 1
- call F(4711, "return", 1)
- Xpath 2 " X: 0
- catch /^return$/
- Xpath 4 " X: 4
- catch /.*/
- Xpath 8 " X: 0
- Xout "return:" v:exception "in" v:throwpoint
- endtry
-
- try
- Xpath 16 " X: 16
- let var = F(4712, "return-var", 2)
- Xpath 32 " X: 0
- catch /^return-var$/
- Xpath 64 " X: 64
- catch /.*/
- Xpath 128 " X: 0
- Xout "return-var:" v:exception "in" v:throwpoint
- finally
- unlet! var
- endtry
+if ExtraVim()
- try
- Xpath 256 " X: 256
- throw "except1" . THROW("throw1", 3)
- Xpath 512 " X: 0
- catch /^except1/
- Xpath 1024 " X: 0
- catch /^throw1$/
- Xpath 2048 " X: 2048
- catch /.*/
- Xpath 4096 " X: 0
- Xout "throw1:" v:exception "in" v:throwpoint
- endtry
+ while 1
+ try
+ try
+ Xpath 1 " X: 1
+ let caught = 0
+ while 1
+" if 1
+ " Missing :endif
+ endwhile " throw error exception
+ catch /^Vim(/
+ let caught = 1
+ finally
+ Xpath 2 " X: 2
+ if caught || $VIMNOERRTHROW
+ Xpath 4 " X: 4
+ endif
+ endtry
+ catch /.*/
+ Xpath 8 " X: 0
+ Xout v:exception "in" v:throwpoint
+ finally
+ break " discard error for $VIMNOERRTHROW
+ endtry
+ endwhile
- try
- Xpath 8192 " X: 8192
- call G("except2", "throw2", 4)
- Xpath 16384 " X: 0
- catch /^except2/
- Xpath 32768 " X: 0
- catch /^throw2$/
- Xpath 65536 " X: 65536
- catch /.*/
- Xpath 131072 " X: 0
- Xout "throw2:" v:exception "in" v:throwpoint
- endtry
+ while 1
+ try
+ try
+ Xpath 16 " X: 16
+ let caught = 0
+ try
+" if 1
+ " Missing :endif
+ catch /.*/ " throw error exception
+ Xpath 32 " X: 0
+ catch /.*/
+ Xpath 64 " X: 0
+ endtry
+ catch /^Vim(/
+ let caught = 1
+ finally
+ Xpath 128 " X: 128
+ if caught || $VIMNOERRTHROW
+ Xpath 256 " X: 256
+ endif
+ endtry
+ catch /.*/
+ Xpath 512 " X: 0
+ Xout v:exception "in" v:throwpoint
+ finally
+ break " discard error for $VIMNOERRTHROW
+ endtry
+ endwhile
- try
- Xpath 262144 " X: 262144
- let var = G("except3", "throw3", 5)
- Xpath 524288 " X: 0
- catch /^except3/
- Xpath 1048576 " X: 0
- catch /^throw3$/
- Xpath 2097152 " X: 2097152
- catch /.*/
- Xpath 4194304 " X: 0
- Xout "throw3:" v:exception "in" v:throwpoint
- finally
- unlet! var
- endtry
+ while 1
+ try
+ try
+ let caught = 0
+ try
+ Xpath 1024 " X: 1024
+ "INTERRUPT
+ catch /do_not_catch/
+ Xpath 2048 " X: 0
+" if 1
+ " Missing :endif
+ catch /.*/ " throw error exception
+ Xpath 4096 " X: 0
+ catch /.*/
+ Xpath 8192 " X: 0
+ endtry
+ catch /^Vim(/
+ let caught = 1
+ finally
+ Xpath 16384 " X: 16384
+ if caught || $VIMNOERRTHROW
+ Xpath 32768 " X: 32768
+ endif
+ endtry
+ catch /.*/
+ Xpath 65536 " X: 0
+ Xout v:exception "in" v:throwpoint
+ finally
+ break " discard error for $VIMNOERRTHROW
+ endtry
+ endwhile
- let expected = "F1T1F2T2T3G4T4G5T5"
- if taken != expected
- Xpath 8388608 " X: 0
- Xout "'taken' is" taken "instead of" expected
- endif
+ while 1
+ try
+ try
+ let caught = 0
+ try
+ Xpath 131072 " X: 131072
+ throw "x"
+ catch /do_not_catch/
+ Xpath 262144 " X: 0
+" if 1
+ " Missing :endif
+ catch /x/ " throw error exception
+ Xpath 524288 " X: 0
+ catch /.*/
+ Xpath 1048576 " X: 0
+ endtry
+ catch /^Vim(/
+ let caught = 1
+ finally
+ Xpath 2097152 " X: 2097152
+ if caught || $VIMNOERRTHROW
+ Xpath 4194304 " X: 4194304
+ endif
+ endtry
+ catch /.*/
+ Xpath 8388608 " X: 0
+ Xout v:exception "in" v:throwpoint
+ finally
+ break " discard error for $VIMNOERRTHROW
+ endtry
+ endwhile
-catch /^0$/ " default return value
- Xpath 16777216 " X: 0
- Xout v:throwpoint
-catch /.*/
- Xpath 33554432 " X: 0
- Xout v:exception "in" v:throwpoint
-endtry
+ while 1
+ try
+ try
+ let caught = 0
+ Xpath 16777216 " X: 16777216
+" endif " :endif without :if; throw error exception
+" if 1
+ " Missing :endif
+ catch /do_not_catch/ " ignore new error
+ Xpath 33554432 " X: 0
+ catch /^Vim(endif):/
+ let caught = 1
+ catch /^Vim(/
+ Xpath 67108864 " X: 0
+ finally
+ Xpath 134217728 " X: 134217728
+ if caught || $VIMNOERRTHROW
+ Xpath 268435456 " X: 268435456
+ endif
+ endtry
+ catch /.*/
+ Xpath 536870912 " X: 0
+ Xout v:exception "in" v:throwpoint
+ finally
+ break " discard error for $VIMNOERRTHROW
+ endtry
+ endwhile
-Xpath 67108864 " X: 67108864
+ Xpath 1073741824 " X: 1073741824
-unlet taken expected
-delfunction THROW
-delfunction F
-delfunction G
+endif
-Xcheck 69544277
+Xcheck 1499645335
"-------------------------------------------------------------------------------
-" Test 71: :throw across :echo variants and :execute {{{1
+" Test 65: Errors in the /pattern/ argument of a :catch {{{1
"
-" On an :echo, :echon, :echomsg, :echoerr, or :execute command, an
-" exception might be thrown during evaluation of the arguments to
-" be displayed or executed as a command, respectively. Any following
-" arguments are not evaluated, then. The exception can be caught by
-" the script.
+" On an error in the /pattern/ argument of a :catch, the :catch does
+" not match. Any following :catches of the same :try/:endtry don't
+" match either. Finally clauses are executed.
"-------------------------------------------------------------------------------
XpathINIT
-let taken = ""
-
-function! THROW(x, n)
- let g:taken = g:taken . "T" . a:n
- throw a:x
-endfunction
-
-function! F(n)
- let g:taken = g:taken . "F" . a:n
- return "F" . a:n
+function! MSG(enr, emsg)
+ let english = v:lang == "C" || v:lang =~ '^[Ee]n'
+ if a:enr == ""
+ Xout "TODO: Add message number for:" a:emsg
+ let v:errmsg = ":" . v:errmsg
+ endif
+ let match = 1
+ if v:errmsg !~ '^'.a:enr.':' || (english && v:errmsg !~ a:emsg)
+ let match = 0
+ if v:errmsg == ""
+ Xout "Message missing."
+ else
+ let v:errmsg = escape(v:errmsg, '"')
+ Xout "Unexpected message:" v:errmsg
+ endif
+ endif
+ return match
endfunction
try
try
Xpath 1 " X: 1
- echo "echo" . THROW("echo-except", 1) F(1)
- Xpath 2 " X: 0
- catch /^echo-except$/
- Xpath 4 " X: 4
- catch /.*/
- Xpath 8 " X: 0
- Xout "echo:" v:exception "in" v:throwpoint
- endtry
-
- try
- Xpath 16 " X: 16
- echon "echon" . THROW("echon-except", 2) F(2)
- Xpath 32 " X: 0
- catch /^echon-except$/
- Xpath 64 " X: 64
- catch /.*/
- Xpath 128 " X: 0
- Xout "echon:" v:exception "in" v:throwpoint
- endtry
-
- try
- Xpath 256 " X: 256
- echomsg "echomsg" . THROW("echomsg-except", 3) F(3)
- Xpath 512 " X: 0
- catch /^echomsg-except$/
- Xpath 1024 " X: 1024
- catch /.*/
- Xpath 2048 " X: 0
- Xout "echomsg:" v:exception "in" v:throwpoint
- endtry
-
- try
- Xpath 4096 " X: 4096
- echoerr "echoerr" . THROW("echoerr-except", 4) F(4)
- Xpath 8192 " X: 0
- catch /^echoerr-except$/
- Xpath 16384 " X: 16384
- catch /Vim/
- Xpath 32768 " X: 0
- catch /echoerr/
- Xpath 65536 " X: 0
- catch /.*/
- Xpath 131072 " X: 0
- Xout "echoerr:" v:exception "in" v:throwpoint
+ throw "oops"
+ catch /^oops$/
+ Xpath 2 " X: 2
+ catch /\)/ " not checked; exception has already been caught
+ Xpath 4 " X: 0
endtry
+ Xpath 8 " X: 8
+catch /.*/
+ Xpath 16 " X: 0
+ Xout v:exception "in" v:throwpoint
+endtry
+function! F()
try
- Xpath 262144 " X: 262144
- execute "echo 'execute" . THROW("execute-except", 5) F(5) "'"
- Xpath 524288 " X: 0
- catch /^execute-except$/
- Xpath 1048576 " X: 1048576
+ let caught = 0
+ try
+ try
+ Xpath 32 " X: 32
+ throw "ab"
+ catch /abc/ " does not catch
+ Xpath 64 " X: 0
+ catch /\)/ " error; discards exception
+ Xpath 128 " X: 0
+ catch /.*/ " not checked
+ Xpath 256 " X: 0
+ finally
+ Xpath 512 " X: 512
+ endtry
+ Xpath 1024 " X: 0
+ catch /^ab$/ " checked, but original exception is discarded
+ Xpath 2048 " X: 0
+ catch /^Vim(catch):/
+ let caught = 1
+ let v:errmsg = substitute(v:exception, '^Vim(catch):', '', "")
+ finally
+ Xpath 4096 " X: 4096
+ if !caught && !$VIMNOERRTHROW
+ Xpath 8192 " X: 0
+ endif
+ if !MSG('E475', "Invalid argument")
+ Xpath 16384 " X: 0
+ endif
+ if !caught
+ return | " discard error
+ endif
+ endtry
catch /.*/
- Xpath 2097152 " X: 0
- Xout "execute:" v:exception "in" v:throwpoint
+ Xpath 32768 " X: 0
+ Xout v:exception "in" v:throwpoint
endtry
+endfunction
- let expected = "T1T2T3T4T5"
- if taken != expected
- Xpath 4194304 " X: 0
- Xout "'taken' is" taken "instead of" expected
- endif
-
-catch /^0$/ " default return value
- Xpath 8388608 " X: 0
- Xout v:throwpoint
-catch /.*/
- Xpath 16777216 " X: 0
- Xout v:exception "in" v:throwpoint
-endtry
-
-Xpath 33554432 " X: 33554432
+call F()
+Xpath 65536 " X: 65536
-unlet taken expected
-delfunction THROW
+delfunction MSG
delfunction F
+unlet! caught
-Xcheck 34886997
+Xcheck 70187
"-------------------------------------------------------------------------------
-" Test 72: :throw across :let or :unlet {{{1
+" Test 66: Stop range :call on error, interrupt, or :throw {{{1
"
-" On a :let command, an exception might be thrown during evaluation
-" of the expression to assign. On an :let or :unlet command, the
-" evaluation of the name of the variable to be assigned or list or
-" deleted, respectively, may throw an exception. Any following
-" arguments are not evaluated, then. The exception can be caught by
-" the script.
+" When a function which is multiply called for a range since it
+" doesn't handle the range itself has an error in a command
+" dynamically enclosed by :try/:endtry or gets an interrupt or
+" executes a :throw, no more calls for the remaining lines in the
+" range are made. On an error in a command not dynamically enclosed
+" by :try/:endtry, the function is executed again for the remaining
+" lines in the range.
"-------------------------------------------------------------------------------
XpathINIT
-let throwcount = 0
+if ExtraVim()
-function! THROW(x)
- let g:throwcount = g:throwcount + 1
- throw a:x
-endfunction
+ let file = tempname()
+ exec "edit" file
-try
- try
- let $VAR = "old_value"
- Xpath 1 " X: 1
- let $VAR = "let(" . THROW("var") . ")"
- Xpath 2 " X: 0
- catch /^var$/
- Xpath 4 " X: 4
- finally
- if $VAR != "old_value"
- Xpath 8 " X: 0
+ insert
+line 1
+line 2
+line 3
+.
+
+ XloopINIT! 1 2
+
+ let taken = ""
+ let expected = "G1EF1E(1)F1E(2)F1E(3)G2EF2E(1)G3IF3I(1)G4TF4T(1)G5AF5A(1)"
+
+ function! F(reason, n) abort
+ let g:taken = g:taken . "F" . a:n .
+ \ substitute(a:reason, '\(\l\).*', '\u\1', "") .
+ \ "(" . line(".") . ")"
+
+ if a:reason == "error"
+ asdf
+ elseif a:reason == "interrupt"
+ "INTERRUPT
+ let dummy = 0
+ elseif a:reason == "throw"
+ throw "xyz"
+ elseif a:reason == "aborting error"
+ XloopNEXT
+ if g:taken != g:expected
+ Xloop 1 " X: 0
+ Xout "'taken' is" g:taken "instead of" g:expected
+ endif
+ try
+ bwipeout!
+ call delete(file)
+ asdf
+ endtry
endif
- endtry
+ endfunction
+
+ function! G(reason, n)
+ let g:taken = g:taken . "G" . a:n .
+ \ substitute(a:reason, '\(\l\).*', '\u\1', "")
+ 1,3call F(a:reason, a:n)
+ endfunction
+ Xpath 8 " X: 8
+ call G("error", 1)
try
- let @a = "old_value"
Xpath 16 " X: 16
- let @a = "let(" . THROW("reg") . ")"
- Xpath 32 " X: 0
- catch /^reg$/
try
+ call G("error", 2)
+ Xpath 32 " X: 0
+ finally
Xpath 64 " X: 64
- let @A = "let(" . THROW("REG") . ")"
- Xpath 128 " X: 0
- catch /^REG$/
- Xpath 256 " X: 256
+ try
+ call G("interrupt", 3)
+ Xpath 128 " X: 0
+ finally
+ Xpath 256 " X: 256
+ try
+ call G("throw", 4)
+ Xpath 512 " X: 0
+ endtry
+ endtry
endtry
- finally
- if @a != "old_value"
- Xpath 512 " X: 0
- endif
- if @A != "old_value"
- Xpath 1024 " X: 0
- endif
+ catch /xyz/
+ Xpath 1024 " X: 1024
+ catch /.*/
+ Xpath 2048 " X: 0
+ Xout v:exception "in" ExtraVimThrowpoint()
endtry
+ Xpath 4096 " X: 4096
+ call G("aborting error", 5)
+ Xpath 8192 " X: 0
+ Xout "'taken' is" taken "instead of" expected
+
+endif
+
+Xcheck 5464
+
+
+"-------------------------------------------------------------------------------
+" Test 67: :throw across :call command {{{1
+"
+" On a call command, an exception might be thrown when evaluating the
+" function name, during evaluation of the arguments, or when the
+" function is being executed. The exception can be caught by the
+" caller.
+"-------------------------------------------------------------------------------
+XpathINIT
+
+function! THROW(x, n)
+ if a:n == 1
+ Xpath 1 " X: 1
+ elseif a:n == 2
+ Xpath 2 " X: 2
+ elseif a:n == 3
+ Xpath 4 " X: 4
+ endif
+ throw a:x
+endfunction
+
+function! NAME(x, n)
+ if a:n == 1
+ Xpath 8 " X: 0
+ elseif a:n == 2
+ Xpath 16 " X: 16
+ elseif a:n == 3
+ Xpath 32 " X: 32
+ elseif a:n == 4
+ Xpath 64 " X: 64
+ endif
+ return a:x
+endfunction
+
+function! ARG(x, n)
+ if a:n == 1
+ Xpath 128 " X: 0
+ elseif a:n == 2
+ Xpath 256 " X: 0
+ elseif a:n == 3
+ Xpath 512 " X: 512
+ elseif a:n == 4
+ Xpath 1024 " X: 1024
+ endif
+ return a:x
+endfunction
+
+function! F(x, n)
+ if a:n == 2
+ Xpath 2048 " X: 0
+ elseif a:n == 4
+ Xpath 4096 " X: 4096
+ endif
+endfunction
+
+while 1
try
- let saved_gpath = &g:path
- let saved_lpath = &l:path
- Xpath 2048 " X: 2048
- let &path = "let(" . THROW("opt") . ")"
- Xpath 4096 " X: 0
- catch /^opt$/
- try
- Xpath 8192 " X: 8192
- let &g:path = "let(" . THROW("gopt") . ")"
- Xpath 16384 " X: 0
- catch /^gopt$/
+ let error = 0
+ let v:errmsg = ""
+
+ while 1
try
- Xpath 32768 " X: 32768
- let &l:path = "let(" . THROW("lopt") . ")"
- Xpath 65536 " X: 0
- catch /^lopt$/
- Xpath 131072 " X: 131072
+ Xpath 8192 " X: 8192
+ call {NAME(THROW("name", 1), 1)}(ARG(4711, 1), 1)
+ Xpath 16384 " X: 0
+ catch /^name$/
+ Xpath 32768 " X: 32768
+ catch /.*/
+ let error = 1
+ Xout "1:" v:exception "in" v:throwpoint
+ finally
+ if !error && $VIMNOERRTHROW && v:errmsg != ""
+ let error = 1
+ Xout "1:" v:errmsg
+ endif
+ if error
+ Xpath 65536 " X: 0
+ endif
+ let error = 0
+ let v:errmsg = ""
+ break " discard error for $VIMNOERRTHROW
+ endtry
+ endwhile
+
+ while 1
+ try
+ Xpath 131072 " X: 131072
+ call {NAME("F", 2)}(ARG(THROW("arg", 2), 2), 2)
+ Xpath 262144 " X: 0
+ catch /^arg$/
+ Xpath 524288 " X: 524288
+ catch /.*/
+ let error = 1
+ Xout "2:" v:exception "in" v:throwpoint
+ finally
+ if !error && $VIMNOERRTHROW && v:errmsg != ""
+ let error = 1
+ Xout "2:" v:errmsg
+ endif
+ if error
+ Xpath 1048576 " X: 0
+ endif
+ let error = 0
+ let v:errmsg = ""
+ break " discard error for $VIMNOERRTHROW
+ endtry
+ endwhile
+
+ while 1
+ try
+ Xpath 2097152 " X: 2097152
+ call {NAME("THROW", 3)}(ARG("call", 3), 3)
+ Xpath 4194304 " X: 0
+ catch /^call$/
+ Xpath 8388608 " X: 8388608
+ catch /^0$/ " default return value
+ Xpath 16777216 " X: 0
+ Xout "3:" v:throwpoint
+ catch /.*/
+ let error = 1
+ Xout "3:" v:exception "in" v:throwpoint
+ finally
+ if !error && $VIMNOERRTHROW && v:errmsg != ""
+ let error = 1
+ Xout "3:" v:errmsg
+ endif
+ if error
+ Xpath 33554432 " X: 0
+ endif
+ let error = 0
+ let v:errmsg = ""
+ break " discard error for $VIMNOERRTHROW
endtry
- endtry
- finally
- if &g:path != saved_gpath || &l:path != saved_lpath
- Xpath 262144 " X: 0
- endif
- let &g:path = saved_gpath
- let &l:path = saved_lpath
- endtry
+ endwhile
- unlet! var1 var2 var3
+ while 1
+ try
+ Xpath 67108864 " X: 67108864
+ call {NAME("F", 4)}(ARG(4711, 4), 4)
+ Xpath 134217728 " X: 134217728
+ catch /.*/
+ let error = 1
+ Xout "4:" v:exception "in" v:throwpoint
+ finally
+ if !error && $VIMNOERRTHROW && v:errmsg != ""
+ let error = 1
+ Xout "4:" v:errmsg
+ endif
+ if error
+ Xpath 268435456 " X: 0
+ endif
+ let error = 0
+ let v:errmsg = ""
+ break " discard error for $VIMNOERRTHROW
+ endtry
+ endwhile
- try
- Xpath 524288 " X: 524288
- let var1 = "let(" . THROW("var1") . ")"
- Xpath 1048576 " X: 0
- catch /^var1$/
- Xpath 2097152 " X: 2097152
+ catch /^0$/ " default return value
+ Xpath 536870912 " X: 0
+ Xout v:throwpoint
+ catch /.*/
+ let error = 1
+ Xout v:exception "in" v:throwpoint
finally
- if exists("var1")
- Xpath 4194304 " X: 0
+ if !error && $VIMNOERRTHROW && v:errmsg != ""
+ let error = 1
+ Xout v:errmsg
endif
- endtry
-
- try
- let var2 = "old_value"
- Xpath 8388608 " X: 8388608
- let var2 = "let(" . THROW("var2"). ")"
- Xpath 16777216 " X: 0
- catch /^var2$/
- Xpath 33554432 " X: 33554432
- finally
- if var2 != "old_value"
- Xpath 67108864 " X: 0
+ if error
+ Xpath 1073741824 " X: 0
endif
+ break " discard error for $VIMNOERRTHROW
endtry
+endwhile
- try
- Xpath 134217728 " X: 134217728
- let var{THROW("var3")} = 4711
- Xpath 268435456 " X: 0
- catch /^var3$/
- Xpath 536870912 " X: 536870912
- endtry
-
- let addpath = ""
-
- function ADDPATH(p)
- let g:addpath = g:addpath . a:p
- endfunction
-
- try
- call ADDPATH("T1")
- let var{THROW("var4")} var{ADDPATH("T2")} | call ADDPATH("T3")
- call ADDPATH("T4")
- catch /^var4$/
- call ADDPATH("T5")
- endtry
-
- try
- call ADDPATH("T6")
- unlet var{THROW("var5")} var{ADDPATH("T7")} | call ADDPATH("T8")
- call ADDPATH("T9")
- catch /^var5$/
- call ADDPATH("T10")
- endtry
-
- if addpath != "T1T5T6T10" || throwcount != 11
- throw "addpath: " . addpath . ", throwcount: " . throwcount
- endif
-
- Xpath 1073741824 " X: 1073741824
-
-catch /.*/
- " The Xpath command does not accept 2^31 (negative); add explicitly:
- let Xpath = Xpath + 2147483648 " X: 0
- Xout v:exception "in" v:throwpoint
-endtry
+unlet error
+delfunction F
-unlet! var1 var2 var3 addpath throwcount
-delfunction THROW
+Xcheck 212514423
-Xcheck 1789569365
+" Leave THROW(), NAME(), and ARG() for the next test.
"-------------------------------------------------------------------------------
-" Test 73: :throw across :function, :delfunction {{{1
+" Test 68: :throw across function calls in expressions {{{1
+"
+" On a function call within an expression, an exception might be
+" thrown when evaluating the function name, during evaluation of the
+" arguments, or when the function is being executed. The exception
+" can be caught by the caller.
"
-" The :function and :delfunction commands may cause an expression
-" specified in braces to be evaluated. During evaluation, an
-" exception might be thrown. The exception can be caught by the
-" script.
+" This test reuses the functions THROW(), NAME(), and ARG() from the
+" previous test.
"-------------------------------------------------------------------------------
XpathINIT
-let taken = ""
-
-function! THROW(x, n)
- let g:taken = g:taken . "T" . a:n
- throw a:x
-endfunction
-
-function! EXPR(x, n)
- let g:taken = g:taken . "E" . a:n
- if a:n % 2 == 0
- call THROW(a:x, a:n)
+function! F(x, n)
+ if a:n == 2
+ Xpath 2048 " X: 0
+ elseif a:n == 4
+ Xpath 4096 " X: 4096
endif
- return 2 - a:n % 2
+ return a:x
endfunction
-try
- try
- " Define function.
- Xpath 1 " X: 1
- function! F0()
- endfunction
- Xpath 2 " X: 2
- function! F{EXPR("function-def-ok", 1)}()
- endfunction
- Xpath 4 " X: 4
- function! F{EXPR("function-def", 2)}()
- endfunction
- Xpath 8 " X: 0
- catch /^function-def-ok$/
- Xpath 16 " X: 0
- catch /^function-def$/
- Xpath 32 " X: 32
- catch /.*/
- Xpath 64 " X: 0
- Xout "def:" v:exception "in" v:throwpoint
- endtry
-
- try
- " List function.
- Xpath 128 " X: 128
- function F0
- Xpath 256 " X: 256
- function F{EXPR("function-lst-ok", 3)}
- Xpath 512 " X: 512
- function F{EXPR("function-lst", 4)}
- Xpath 1024 " X: 0
- catch /^function-lst-ok$/
- Xpath 2048 " X: 0
- catch /^function-lst$/
- Xpath 4096 " X: 4096
- catch /.*/
- Xpath 8192 " X: 0
- Xout "lst:" v:exception "in" v:throwpoint
- endtry
+unlet! var1 var2 var3 var4
+while 1
try
- " Delete function
- Xpath 16384 " X: 16384
- delfunction F0
- Xpath 32768 " X: 32768
- delfunction F{EXPR("function-del-ok", 5)}
- Xpath 65536 " X: 65536
- delfunction F{EXPR("function-del", 6)}
- Xpath 131072 " X: 0
- catch /^function-del-ok$/
- Xpath 262144 " X: 0
- catch /^function-del$/
- Xpath 524288 " X: 524288
- catch /.*/
- Xpath 1048576 " X: 0
- Xout "del:" v:exception "in" v:throwpoint
- endtry
-
- let expected = "E1E2T2E3E4T4E5E6T6"
- if taken != expected
- Xpath 2097152 " X: 0
- Xout "'taken' is" taken "instead of" expected
- endif
-
-catch /.*/
- Xpath 4194304 " X: 0
- Xout v:exception "in" v:throwpoint
-endtry
-
-Xpath 8388608 " X: 8388608
-
-unlet taken expected
-delfunction THROW
-delfunction EXPR
-
-Xcheck 9032615
-
-
-"-------------------------------------------------------------------------------
-" Test 74: :throw across builtin functions and commands {{{1
-"
-" Some functions like exists(), searchpair() take expression
-" arguments, other functions or commands like substitute() or
-" :substitute cause an expression (specified in the regular
-" expression) to be evaluated. During evaluation an exception
-" might be thrown. The exception can be caught by the script.
-"-------------------------------------------------------------------------------
-
-XpathINIT
-
-let taken = ""
-
-function! THROW(x, n)
- let g:taken = g:taken . "T" . a:n
- throw a:x
-endfunction
-
-function! EXPR(x, n)
- let g:taken = g:taken . "E" . a:n
- call THROW(a:x . a:n, a:n)
- return "EXPR"
-endfunction
-
-function! SKIP(x, n)
- let g:taken = g:taken . "S" . a:n . "(" . line(".")
- let theline = getline(".")
- if theline =~ "skip"
- let g:taken = g:taken . "s)"
- return 1
- elseif theline =~ "throw"
- let g:taken = g:taken . "t)"
- call THROW(a:x . a:n, a:n)
- else
- let g:taken = g:taken . ")"
- return 0
- endif
-endfunction
+ let error = 0
+ let v:errmsg = ""
-function! SUBST(x, n)
- let g:taken = g:taken . "U" . a:n . "(" . line(".")
- let theline = getline(".")
- if theline =~ "not" " SUBST() should not be called for this line
- let g:taken = g:taken . "n)"
- call THROW(a:x . a:n, a:n)
- elseif theline =~ "throw"
- let g:taken = g:taken . "t)"
- call THROW(a:x . a:n, a:n)
- else
- let g:taken = g:taken . ")"
- return "replaced"
- endif
-endfunction
+ while 1
+ try
+ Xpath 8192 " X: 8192
+ let var1 = {NAME(THROW("name", 1), 1)}(ARG(4711, 1), 1)
+ Xpath 16384 " X: 0
+ catch /^name$/
+ Xpath 32768 " X: 32768
+ catch /.*/
+ let error = 1
+ Xout "1:" v:exception "in" v:throwpoint
+ finally
+ if !error && $VIMNOERRTHROW && v:errmsg != ""
+ let error = 1
+ Xout "1:" v:errmsg
+ endif
+ if error
+ Xpath 65536 " X: 0
+ endif
+ let error = 0
+ let v:errmsg = ""
+ break " discard error for $VIMNOERRTHROW
+ endtry
+ endwhile
-try
- try
- Xpath 1 " X: 1
- let result = exists('*{EXPR("exists", 1)}')
- Xpath 2 " X: 0
- catch /^exists1$/
- Xpath 4 " X: 4
- try
- let result = exists('{EXPR("exists", 2)}')
- Xpath 8 " X: 0
- catch /^exists2$/
- Xpath 16 " X: 16
- catch /.*/
- Xpath 32 " X: 0
- Xout "exists2:" v:exception "in" v:throwpoint
- endtry
- catch /.*/
- Xpath 64 " X: 0
- Xout "exists1:" v:exception "in" v:throwpoint
- endtry
+ while 1
+ try
+ Xpath 131072 " X: 131072
+ let var2 = {NAME("F", 2)}(ARG(THROW("arg", 2), 2), 2)
+ Xpath 262144 " X: 0
+ catch /^arg$/
+ Xpath 524288 " X: 524288
+ catch /.*/
+ let error = 1
+ Xout "2:" v:exception "in" v:throwpoint
+ finally
+ if !error && $VIMNOERRTHROW && v:errmsg != ""
+ let error = 1
+ Xout "2:" v:errmsg
+ endif
+ if error
+ Xpath 1048576 " X: 0
+ endif
+ let error = 0
+ let v:errmsg = ""
+ break " discard error for $VIMNOERRTHROW
+ endtry
+ endwhile
- try
- let file = tempname()
- exec "edit" file
- insert
-begin
- xx
-middle 3
- xx
-middle 5 skip
- xx
-middle 7 throw
- xx
-end
-.
- normal! gg
- Xpath 128 " X: 128
- let result =
- \ searchpair("begin", "middle", "end", '', 'SKIP("searchpair", 3)')
- Xpath 256 " X: 256
- let result =
- \ searchpair("begin", "middle", "end", '', 'SKIP("searchpair", 4)')
- Xpath 512 " X: 0
- let result =
- \ searchpair("begin", "middle", "end", '', 'SKIP("searchpair", 5)')
- Xpath 1024 " X: 0
- catch /^searchpair[35]$/
- Xpath 2048 " X: 0
- catch /^searchpair4$/
- Xpath 4096 " X: 4096
- catch /.*/
- Xpath 8192 " X: 0
- Xout "searchpair:" v:exception "in" v:throwpoint
- finally
- bwipeout!
- call delete(file)
- endtry
+ while 1
+ try
+ Xpath 2097152 " X: 2097152
+ let var3 = {NAME("THROW", 3)}(ARG("call", 3), 3)
+ Xpath 4194304 " X: 0
+ catch /^call$/
+ Xpath 8388608 " X: 8388608
+ catch /^0$/ " default return value
+ Xpath 16777216 " X: 0
+ Xout "3:" v:throwpoint
+ catch /.*/
+ let error = 1
+ Xout "3:" v:exception "in" v:throwpoint
+ finally
+ if !error && $VIMNOERRTHROW && v:errmsg != ""
+ let error = 1
+ Xout "3:" v:errmsg
+ endif
+ if error
+ Xpath 33554432 " X: 0
+ endif
+ let error = 0
+ let v:errmsg = ""
+ break " discard error for $VIMNOERRTHROW
+ endtry
+ endwhile
- try
- let file = tempname()
- exec "edit" file
- insert
-subst 1
-subst 2
-not
-subst 4
-subst throw
-subst 6
-.
- normal! gg
- Xpath 16384 " X: 16384
- 1,2substitute/subst/\=SUBST("substitute", 6)/
- try
- Xpath 32768 " X: 32768
+ while 1
try
- let v:errmsg = ""
- 3substitute/subst/\=SUBST("substitute", 7)/
+ Xpath 67108864 " X: 67108864
+ let var4 = {NAME("F", 4)}(ARG(4711, 4), 4)
+ Xpath 134217728 " X: 134217728
+ catch /.*/
+ let error = 1
+ Xout "4:" v:exception "in" v:throwpoint
finally
- if v:errmsg != ""
- " If exceptions are not thrown on errors, fake the error
- " exception in order to get the same execution path.
- throw "faked Vim(substitute)"
+ if !error && $VIMNOERRTHROW && v:errmsg != ""
+ let error = 1
+ Xout "4:" v:errmsg
+ endif
+ if error
+ Xpath 268435456 " X: 0
endif
+ let error = 0
+ let v:errmsg = ""
+ break " discard error for $VIMNOERRTHROW
endtry
- catch /Vim(substitute)/ " Pattern not found ('e' flag missing)
- Xpath 65536 " X: 65536
- 3substitute/subst/\=SUBST("substitute", 8)/e
- Xpath 131072 " X: 131072
- endtry
- Xpath 262144 " X: 262144
- 4,6substitute/subst/\=SUBST("substitute", 9)/
- Xpath 524288 " X: 0
- catch /^substitute[678]/
- Xpath 1048576 " X: 0
- catch /^substitute9/
- Xpath 2097152 " X: 2097152
- finally
- bwipeout!
- call delete(file)
- endtry
-
- try
- Xpath 4194304 " X: 4194304
- let var = substitute("sub", "sub", '\=THROW("substitute()y", 10)', '')
- Xpath 8388608 " X: 0
- catch /substitute()y/
- Xpath 16777216 " X: 16777216
- catch /.*/
- Xpath 33554432 " X: 0
- Xout "substitute()y:" v:exception "in" v:throwpoint
- endtry
+ endwhile
- try
- Xpath 67108864 " X: 67108864
- let var = substitute("not", "sub", '\=THROW("substitute()n", 11)', '')
- Xpath 134217728 " X: 134217728
- catch /substitute()n/
- Xpath 268435456 " X: 0
+ catch /^0$/ " default return value
+ Xpath 536870912 " X: 0
+ Xout v:throwpoint
catch /.*/
- Xpath 536870912 " X: 0
- Xout "substitute()n:" v:exception "in" v:throwpoint
+ let error = 1
+ Xout v:exception "in" v:throwpoint
+ finally
+ if !error && $VIMNOERRTHROW && v:errmsg != ""
+ let error = 1
+ Xout v:errmsg
+ endif
+ if error
+ Xpath 1073741824 " X: 0
+ endif
+ break " discard error for $VIMNOERRTHROW
endtry
+endwhile
- let expected = "E1T1E2T2S3(3)S4(5s)S4(7t)T4U6(1)U6(2)U9(4)U9(5t)T9T10"
- if taken != expected
- Xpath 1073741824 " X: 0
- Xout "'taken' is" taken "instead of" expected
- endif
-
-catch /.*/
+if exists("var1") || exists("var2") || exists("var3") ||
+ \ !exists("var4") || var4 != 4711
" The Xpath command does not accept 2^31 (negative); add explicitly:
- let Xpath = Xpath + 2147483648 " X: 0
- Xout v:exception "in" v:throwpoint
-endtry
+ let Xpath = Xpath + 2147483648 " X: 0
+ if exists("var1")
+ Xout "var1 =" var1
+ endif
+ if exists("var2")
+ Xout "var2 =" var2
+ endif
+ if exists("var3")
+ Xout "var3 =" var3
+ endif
+ if !exists("var4")
+ Xout "var4 unset"
+ elseif var4 != 4711
+ Xout "var4 =" var4
+ endif
+endif
-unlet result var taken expected
+unlet! error var1 var2 var3 var4
delfunction THROW
-delfunction EXPR
-delfunction SKIP
-delfunction SUBST
-
-Xcheck 224907669
-
-
-"-------------------------------------------------------------------------------
-" Test 75: Errors in builtin functions. {{{1
-"
-" On an error in a builtin function called inside a :try/:endtry
-" region, the evaluation of the expression calling that function and
-" the command containing that expression are abandoned. The error can
-" be caught as an exception.
-"
-" A simple :call of the builtin function is a trivial case. If the
-" builtin function is called in the argument list of another function,
-" no further arguments are evaluated, and the other function is not
-" executed. If the builtin function is called from the argument of
-" a :return command, the :return command is not executed. If the
-" builtin function is called from the argument of a :throw command,
-" the :throw command is not executed. The evaluation of the
-" expression calling the builtin function is abandoned.
-"-------------------------------------------------------------------------------
-
-XpathINIT
-
-function! F1(arg1)
- Xpath 1 " X: 0
-endfunction
-
-function! F2(arg1, arg2)
- Xpath 2 " X: 0
-endfunction
-
-function! G()
- Xpath 4 " X: 0
-endfunction
-
-function! H()
- Xpath 8 " X: 0
-endfunction
-
-function! R()
- while 1
- try
- let caught = 0
- let v:errmsg = ""
- Xpath 16 " X: 16
- return append(1, "s")
- catch /E21/
- let caught = 1
- catch /.*/
- Xpath 32 " X: 0
- finally
- Xpath 64 " X: 64
- if caught || $VIMNOERRTHROW && v:errmsg =~ 'E21'
- Xpath 128 " X: 128
- endif
- break " discard error for $VIMNOERRTHROW
- endtry
- endwhile
- Xpath 256 " X: 256
-endfunction
-
-try
- set noma " let append() fail with "E21"
-
- while 1
- try
- let caught = 0
- let v:errmsg = ""
- Xpath 512 " X: 512
- call append(1, "s")
- catch /E21/
- let caught = 1
- catch /.*/
- Xpath 1024 " X: 0
- finally
- Xpath 2048 " X: 2048
- if caught || $VIMNOERRTHROW && v:errmsg =~ 'E21'
- Xpath 4096 " X: 4096
- endif
- break " discard error for $VIMNOERRTHROW
- endtry
- endwhile
-
- while 1
- try
- let caught = 0
- let v:errmsg = ""
- Xpath 8192 " X: 8192
- call F1('x' . append(1, "s"))
- catch /E21/
- let caught = 1
- catch /.*/
- Xpath 16384 " X: 0
- finally
- Xpath 32768 " X: 32768
- if caught || $VIMNOERRTHROW && v:errmsg =~ 'E21'
- Xpath 65536 " X: 65536
- endif
- break " discard error for $VIMNOERRTHROW
- endtry
- endwhile
-
- while 1
- try
- let caught = 0
- let v:errmsg = ""
- Xpath 131072 " X: 131072
- call F2('x' . append(1, "s"), G())
- catch /E21/
- let caught = 1
- catch /.*/
- Xpath 262144 " X: 0
- finally
- Xpath 524288 " X: 524288
- if caught || $VIMNOERRTHROW && v:errmsg =~ 'E21'
- Xpath 1048576 " X: 1048576
- endif
- break " discard error for $VIMNOERRTHROW
- endtry
- endwhile
-
- call R()
-
- while 1
- try
- let caught = 0
- let v:errmsg = ""
- Xpath 2097152 " X: 2097152
- throw "T" . append(1, "s")
- catch /E21/
- let caught = 1
- catch /^T.*/
- Xpath 4194304 " X: 0
- catch /.*/
- Xpath 8388608 " X: 0
- finally
- Xpath 16777216 " X: 16777216
- if caught || $VIMNOERRTHROW && v:errmsg =~ 'E21'
- Xpath 33554432 " X: 33554432
- endif
- break " discard error for $VIMNOERRTHROW
- endtry
- endwhile
-
- while 1
- try
- let caught = 0
- let v:errmsg = ""
- Xpath 67108864 " X: 67108864
- let x = "a"
- let x = x . "b" . append(1, "s") . H()
- catch /E21/
- let caught = 1
- catch /.*/
- Xpath 134217728 " X: 0
- finally
- Xpath 268435456 " X: 268435456
- if caught || $VIMNOERRTHROW && v:errmsg =~ 'E21'
- Xpath 536870912 " X: 536870912
- endif
- if x == "a"
- Xpath 1073741824 " X: 1073741824
- endif
- break " discard error for $VIMNOERRTHROW
- endtry
- endwhile
-catch /.*/
- " The Xpath command does not accept 2^31 (negative); add explicitly:
- let Xpath = Xpath + 2147483648 " X: 0
- Xout v:exception "in" v:throwpoint
-finally
- set ma&
-endtry
+delfunction NAME
+delfunction ARG
+delfunction F
-unlet! caught x
-delfunction F1
-delfunction F2
-delfunction G
-delfunction H
-delfunction R
+Xcheck 212514423
-Xcheck 2000403408
+" Tests 69 to 75 were moved to test_trycatch.vim
+let Xtest = 76
"-------------------------------------------------------------------------------
Xout "No Crash for vimgrep on BufUnload"
Xcheck 0
-"-------------------------------------------------------------------------------
-" Test 87 using (expr) ? funcref : funcref {{{1
-"
-" Vim needs to correctly parse the funcref and even when it does
-" not execute the funcref, it needs to consume the trailing ()
-"-------------------------------------------------------------------------------
-
-XpathINIT
-
-func Add2(x1, x2)
- return a:x1 + a:x2
-endfu
-
-func GetStr()
- return "abcdefghijklmnopqrstuvwxyp"
-endfu
-
-echo function('Add2')(2,3)
+" Test 87 was moved to test_vimscript.vim
+let Xtest = 88
-Xout 1 ? function('Add2')(1,2) : function('Add2')(2,3)
-Xout 0 ? function('Add2')(1,2) : function('Add2')(2,3)
-" Make sure, GetStr() still works.
-Xout GetStr()[0:10]
-
-
-delfunction GetStr
-delfunction Add2
-Xout "Successfully executed funcref Add2"
-
-Xcheck 0
"-------------------------------------------------------------------------------
" Test 88: $VIMNOERRTHROW and $VIMNOINTTHROW support {{{1
--- /dev/null
+" Test try-catch-finally exception handling
+" Most of this was formerly in test49.
+
+source check.vim
+source shared.vim
+
+"-------------------------------------------------------------------------------
+" Test environment {{{1
+"-------------------------------------------------------------------------------
+
+com! XpathINIT let g:Xpath = ''
+com! -nargs=1 -bar Xpath let g:Xpath = g:Xpath . <args>
+
+" Test 25: Executing :finally clauses on normal control flow {{{1
+"
+" Control flow in a :try conditional should always fall through to its
+" :finally clause. A :finally clause of a :try conditional inside an
+" inactive conditional should never be executed.
+"-------------------------------------------------------------------------------
+
+func T25_F()
+ let loops = 3
+ while loops > 0
+ Xpath 'a' . loops
+ if loops >= 2
+ try
+ Xpath 'b' . loops
+ if loops == 2
+ try
+ Xpath 'c' . loops
+ finally
+ Xpath 'd' . loops
+ endtry
+ endif
+ finally
+ Xpath 'e' . loops
+ if loops == 2
+ try
+ Xpath 'f' . loops
+ finally
+ Xpath 'g' . loops
+ endtry
+ endif
+ endtry
+ endif
+ Xpath 'h' . loops
+ let loops = loops - 1
+ endwhile
+ Xpath 'i'
+endfunc
+
+func T25_G()
+ if 1
+ try
+ Xpath 'A'
+ call T25_F()
+ Xpath 'B'
+ finally
+ Xpath 'C'
+ endtry
+ else
+ try
+ Xpath 'D'
+ finally
+ Xpath 'E'
+ endtry
+ endif
+endfunc
+
+func Test_finally()
+ XpathINIT
+ call T25_G()
+ call assert_equal('Aa3b3e3h3a2b2c2d2e2f2g2h2a1h1iBC', g:Xpath)
+endfunc
+
+
+"-------------------------------------------------------------------------------
+" Test 26: Executing :finally clauses after :continue or :break {{{1
+"
+" For a :continue or :break dynamically enclosed in a :try/:endtry
+" region inside the next surrounding :while/:endwhile, if the
+" :continue/:break is before the :finally, the :finally clause is
+" executed first. If the :continue/:break is after the :finally, the
+" :finally clause is broken (like an :if/:endif region).
+"-------------------------------------------------------------------------------
+
+func T26_F()
+ try
+ let loops = 3
+ while loops > 0
+ try
+ try
+ if loops == 2
+ Xpath 'a' . loops
+ let loops = loops - 1
+ continue
+ elseif loops == 1
+ Xpath 'b' . loops
+ break
+ finish
+ endif
+ Xpath 'c' . loops
+ endtry
+ finally
+ Xpath 'd' . loops
+ endtry
+ Xpath 'e' . loops
+ let loops = loops - 1
+ endwhile
+ Xpath 'f'
+ finally
+ Xpath 'g'
+ let loops = 3
+ while loops > 0
+ try
+ finally
+ try
+ if loops == 2
+ Xpath 'h' . loops
+ let loops = loops - 1
+ continue
+ elseif loops == 1
+ Xpath 'i' . loops
+ break
+ finish
+ endif
+ endtry
+ Xpath 'j' . loops
+ endtry
+ Xpath 'k' . loops
+ let loops = loops - 1
+ endwhile
+ Xpath 'l'
+ endtry
+ Xpath 'm'
+endfunc
+
+func Test_finally_after_continue()
+ XpathINIT
+ call T26_F()
+ call assert_equal('c3d3e3a2d1b1d1fgj3k3h2i1lm', g:Xpath)
+endfunc
+
+
+"-------------------------------------------------------------------------------
+" Test 32: Remembering the :return value on :finally {{{1
+"
+" If a :finally clause is executed due to a :return specifying
+" a value, this is the value visible to the caller if not overwritten
+" by a new :return in the :finally clause. A :return without a value
+" in the :finally clause overwrites with value 0.
+"-------------------------------------------------------------------------------
+
+func T32_F()
+ try
+ Xpath 'a'
+ try
+ Xpath 'b'
+ return "ABCD"
+ Xpath 'c'
+ finally
+ Xpath 'd'
+ endtry
+ Xpath 'e'
+ finally
+ Xpath 'f'
+ endtry
+ Xpath 'g'
+endfunc
+
+func T32_G()
+ try
+ Xpath 'h'
+ return 8
+ Xpath 'i'
+ finally
+ Xpath 'j'
+ return 16 + strlen(T32_F())
+ Xpath 'k'
+ endtry
+ Xpath 'l'
+endfunc
+
+func T32_H()
+ try
+ Xpath 'm'
+ return 32
+ Xpath 'n'
+ finally
+ Xpath 'o'
+ return
+ Xpath 'p'
+ endtry
+ Xpath 'q'
+endfunc
+
+func T32_I()
+ try
+ Xpath 'r'
+ finally
+ Xpath 's'
+ return T32_G() + T32_H() + 64
+ Xpath 't'
+ endtry
+ Xpath 'u'
+endfunc
+
+func Test_finally_return()
+ XpathINIT
+ call assert_equal(84, T32_I())
+ call assert_equal('rshjabdfmo', g:Xpath)
+endfunc
+
+"-------------------------------------------------------------------------------
+" Test 33: :return under :execute or user command and :finally {{{1
+"
+" A :return command may be executed under an ":execute" or from
+" a user command. Executing of :finally clauses and passing through
+" the return code works also then.
+"-------------------------------------------------------------------------------
+
+func T33_F()
+ try
+ RETURN 10
+ Xpath 'a'
+ finally
+ Xpath 'b'
+ endtry
+ Xpath 'c'
+endfunc
+
+func T33_G()
+ try
+ RETURN 20
+ Xpath 'd'
+ finally
+ Xpath 'e'
+ RETURN 30
+ Xpath 'f'
+ endtry
+ Xpath 'g'
+endfunc
+
+func T33_H()
+ try
+ execute "try | return 40 | finally | return 50 | endtry"
+ Xpath 'h'
+ finally
+ Xpath 'i'
+ endtry
+ Xpath 'j'
+endfunc
+
+func T33_I()
+ try
+ execute "try | return 60 | finally | return 70 | endtry"
+ Xpath 'k'
+ finally
+ Xpath 'l'
+ execute "try | return 80 | finally | return 90 | endtry"
+ Xpath 'm'
+ endtry
+ Xpath 'n'
+endfunc
+
+func T33_J()
+ try
+ RETURN 100
+ Xpath 'o'
+ finally
+ Xpath 'p'
+ return
+ Xpath 'q'
+ endtry
+ Xpath 'r'
+endfunc
+
+func T33_K()
+ try
+ execute "try | return 110 | finally | return 120 | endtry"
+ Xpath 's'
+ finally
+ Xpath 't'
+ execute "try | return 130 | finally | return | endtry"
+ Xpath 'u'
+ endtry
+ Xpath 'v'
+endfunc
+
+func T33_L()
+ try
+ return
+ Xpath 'w'
+ finally
+ Xpath 'x'
+ RETURN 140
+ Xpath 'y'
+ endtry
+ Xpath 'z'
+endfunc
+
+func T33_M()
+ try
+ return
+ Xpath 'A'
+ finally
+ Xpath 'B'
+ execute "try | return 150 | finally | return 160 | endtry"
+ Xpath 'C'
+ endtry
+ Xpath 'D'
+endfunc
+
+func T33_N()
+ RETURN 170
+endfunc
+
+func T33_O()
+ execute "try | return 180 | finally | return 190 | endtry"
+endfunc
+
+func Test_finally_cmd_return()
+ command! -nargs=? RETURN
+ \ try | return <args> | finally | return <args> * 2 | endtry
+ XpathINIT
+ call assert_equal(20, T33_F())
+ call assert_equal(60, T33_G())
+ call assert_equal(50, T33_H())
+ call assert_equal(90, T33_I())
+ call assert_equal(0, T33_J())
+ call assert_equal(0, T33_K())
+ call assert_equal(280, T33_L())
+ call assert_equal(160, T33_M())
+ call assert_equal(340, T33_N())
+ call assert_equal(190, T33_O())
+ call assert_equal('beilptxB', g:Xpath)
+ delcommand RETURN
+endfunc
+
+
+"-------------------------------------------------------------------------------
+" Test 41: Skipped :throw finding next command {{{1
+"
+" A :throw in an inactive conditional must not hide a following
+" command.
+"-------------------------------------------------------------------------------
+
+func T41_F()
+ Xpath 'a'
+ if 0 | throw 'never' | endif | Xpath 'b'
+ Xpath 'c'
+endfunc
+
+func T41_G()
+ Xpath 'd'
+ while 0 | throw 'never' | endwhile | Xpath 'e'
+ Xpath 'f'
+endfunc
+
+func T41_H()
+ Xpath 'g'
+ if 0 | try | throw 'never' | endtry | endif | Xpath 'h'
+ Xpath 'i'
+endfunc
+
+func Test_throw_inactive_cond()
+ XpathINIT
+ try
+ Xpath 'j'
+ call T41_F()
+ Xpath 'k'
+ catch /.*/
+ Xpath 'l'
+ call assert_report('Caught ' . v:exception . ' in ' . v:throwpoint)
+ endtry
+
+ try
+ Xpath 'm'
+ call T41_G()
+ Xpath 'n'
+ catch /.*/
+ Xpath 'o'
+ call assert_report('Caught ' . v:exception . ' in ' . v:throwpoint)
+ endtry
+
+ try
+ Xpath 'p'
+ call T41_H()
+ Xpath 'q'
+ catch /.*/
+ Xpath 'r'
+ call assert_report('Caught ' . v:exception . ' in ' . v:throwpoint)
+ endtry
+
+ call assert_equal('jabckmdefnpghiq', g:Xpath)
+endfunc
+
+
+"-------------------------------------------------------------------------------
+" Test 42: Catching number and string exceptions {{{1
+"
+" When a number is thrown, it is converted to a string exception.
+" Numbers and strings may be caught by specifying a regular exception
+" as argument to the :catch command.
+"-------------------------------------------------------------------------------
+
+
+func T42_F()
+ try
+
+ try
+ Xpath 'a'
+ throw 4711
+ Xpath 'b'
+ catch /4711/
+ Xpath 'c'
+ endtry
+
+ try
+ Xpath 'd'
+ throw 4711
+ Xpath 'e'
+ catch /^4711$/
+ Xpath 'f'
+ endtry
+
+ try
+ Xpath 'g'
+ throw 4711
+ Xpath 'h'
+ catch /\d/
+ Xpath 'i'
+ endtry
+
+ try
+ Xpath 'j'
+ throw 4711
+ Xpath 'k'
+ catch /^\d\+$/
+ Xpath 'l'
+ endtry
+
+ try
+ Xpath 'm'
+ throw "arrgh"
+ Xpath 'n'
+ catch /arrgh/
+ Xpath 'o'
+ endtry
+
+ try
+ Xpath 'p'
+ throw "arrgh"
+ Xpath 'q'
+ catch /^arrgh$/
+ Xpath 'r'
+ endtry
+
+ try
+ Xpath 's'
+ throw "arrgh"
+ Xpath 't'
+ catch /\l/
+ Xpath 'u'
+ endtry
+
+ try
+ Xpath 'v'
+ throw "arrgh"
+ Xpath 'w'
+ catch /^\l\+$/
+ Xpath 'x'
+ endtry
+
+ try
+ try
+ Xpath 'y'
+ throw "ARRGH"
+ Xpath 'z'
+ catch /^arrgh$/
+ Xpath 'A'
+ endtry
+ catch /^\carrgh$/
+ Xpath 'B'
+ endtry
+
+ try
+ Xpath 'C'
+ throw ""
+ Xpath 'D'
+ catch /^$/
+ Xpath 'E'
+ endtry
+
+ catch /.*/
+ Xpath 'F'
+ call assert_report('Caught ' . v:exception . ' in ' . v:throwpoint)
+ endtry
+endfunc
+
+func Test_catch_number_string()
+ XpathINIT
+ call T42_F()
+ call assert_equal('acdfgijlmoprsuvxyBCE', g:Xpath)
+endfunc
+
+
+"-------------------------------------------------------------------------------
+" Test 43: Selecting the correct :catch clause {{{1
+"
+" When an exception is thrown and there are multiple :catch clauses,
+" the first matching one is taken.
+"-------------------------------------------------------------------------------
+
+func T43_F()
+ let loops = 3
+ while loops > 0
+ try
+ if loops == 3
+ Xpath 'a' . loops
+ throw "a"
+ Xpath 'b' . loops
+ elseif loops == 2
+ Xpath 'c' . loops
+ throw "ab"
+ Xpath 'd' . loops
+ elseif loops == 1
+ Xpath 'e' . loops
+ throw "abc"
+ Xpath 'f' . loops
+ endif
+ catch /abc/
+ Xpath 'g' . loops
+ catch /ab/
+ Xpath 'h' . loops
+ catch /.*/
+ Xpath 'i' . loops
+ catch /a/
+ Xpath 'j' . loops
+ endtry
+
+ let loops = loops - 1
+ endwhile
+ Xpath 'k'
+endfunc
+
+func Test_multi_catch()
+ XpathINIT
+ call T43_F()
+ call assert_equal('a3i3c2h2e1g1k', g:Xpath)
+endfunc
+
+
+"-------------------------------------------------------------------------------
+" Test 44: Missing or empty :catch patterns {{{1
+"
+" A missing or empty :catch pattern means the same as /.*/, that is,
+" catches everything. To catch only empty exceptions, /^$/ must be
+" used. A :catch with missing, empty, or /.*/ argument also works
+" when followed by another command separated by a bar on the same
+" line. :catch patterns cannot be specified between ||. But other
+" pattern separators can be used instead of //.
+"-------------------------------------------------------------------------------
+
+func T44_F()
+ try
+ try
+ Xpath 'a'
+ throw ""
+ catch /^$/
+ Xpath 'b'
+ endtry
+
+ try
+ Xpath 'c'
+ throw ""
+ catch /.*/
+ Xpath 'd'
+ endtry
+
+ try
+ Xpath 'e'
+ throw ""
+ catch //
+ Xpath 'f'
+ endtry
+
+ try
+ Xpath 'g'
+ throw ""
+ catch
+ Xpath 'h'
+ endtry
+
+ try
+ Xpath 'i'
+ throw "oops"
+ catch /^$/
+ Xpath 'j'
+ catch /.*/
+ Xpath 'k'
+ endtry
+
+ try
+ Xpath 'l'
+ throw "arrgh"
+ catch /^$/
+ Xpath 'm'
+ catch //
+ Xpath 'n'
+ endtry
+
+ try
+ Xpath 'o'
+ throw "brrr"
+ catch /^$/
+ Xpath 'p'
+ catch
+ Xpath 'q'
+ endtry
+
+ try | Xpath 'r' | throw "x" | catch /.*/ | Xpath 's' | endtry
+
+ try | Xpath 't' | throw "y" | catch // | Xpath 'u' | endtry
+
+ while 1
+ try
+ let caught = 0
+ let v:errmsg = ""
+ " Extra try level: if ":catch" without arguments below raises
+ " a syntax error because it misinterprets the "Xpath" as a pattern,
+ " let it be caught by the ":catch /.*/" below.
+ try
+ try | Xpath 'v' | throw "z" | catch | Xpath 'w' | :
+ endtry
+ endtry
+ catch /.*/
+ let caught = 1
+ call assert_report('Caught ' . v:exception . ' in ' . v:throwpoint)
+ finally
+ if $VIMNOERRTHROW && v:errmsg != ""
+ call assert_report(v:errmsg)
+ endif
+ if caught || $VIMNOERRTHROW && v:errmsg != ""
+ Xpath 'x'
+ endif
+ break " discard error for $VIMNOERRTHROW
+ endtry
+ endwhile
+
+ let cologne = 4711
+ try
+ try
+ Xpath 'y'
+ throw "throw cologne"
+ " Next lines catches all and throws 4711:
+ catch |throw cologne|
+ Xpath 'z'
+ endtry
+ catch /4711/
+ Xpath 'A'
+ endtry
+
+ try
+ Xpath 'B'
+ throw "plus"
+ catch +plus+
+ Xpath 'C'
+ endtry
+
+ Xpath 'D'
+ catch /.*/
+ Xpath 'E'
+ call assert_report('Caught ' . v:exception . ' in ' . v:throwpoint)
+ endtry
+endfunc
+
+func Test_empty_catch()
+ XpathINIT
+ call T44_F()
+ call assert_equal('abcdefghiklnoqrstuvwyABCD', g:Xpath)
+endfunc
+
+
+"-------------------------------------------------------------------------------
+" Test 45: Catching exceptions from nested :try blocks {{{1
+"
+" When :try blocks are nested, an exception is caught by the innermost
+" try conditional that has a matching :catch clause.
+"-------------------------------------------------------------------------------
+
+func T45_F()
+ let loops = 3
+ while loops > 0
+ try
+ try
+ try
+ try
+ if loops == 3
+ Xpath 'a' . loops
+ throw "a"
+ Xpath 'b' . loops
+ elseif loops == 2
+ Xpath 'c' . loops
+ throw "ab"
+ Xpath 'd' . loops
+ elseif loops == 1
+ Xpath 'e' . loops
+ throw "abc"
+ Xpath 'f' . loops
+ endif
+ catch /abc/
+ Xpath 'g' . loops
+ endtry
+ catch /ab/
+ Xpath 'h' . loops
+ endtry
+ catch /.*/
+ Xpath 'i' . loops
+ endtry
+ catch /a/
+ Xpath 'j' . loops
+ endtry
+
+ let loops = loops - 1
+ endwhile
+ Xpath 'k'
+endfunc
+
+func Test_catch_from_nested_try()
+ XpathINIT
+ call T45_F()
+ call assert_equal('a3i3c2h2e1g1k', g:Xpath)
+endfunc
+
+
+"-------------------------------------------------------------------------------
+" Test 46: Executing :finally after a :throw in nested :try {{{1
+"
+" When an exception is thrown from within nested :try blocks, the
+" :finally clauses of the non-catching try conditionals should be
+" executed before the matching :catch of the next surrounding :try
+" gets the control. If this also has a :finally clause, it is
+" executed afterwards.
+"-------------------------------------------------------------------------------
+
+func T46_F()
+ let sum = 0
+
+ try
+ Xpath 'a'
+ try
+ Xpath 'b'
+ try
+ Xpath 'c'
+ try
+ Xpath 'd'
+ throw "ABC"
+ Xpath 'e'
+ catch /xyz/
+ Xpath 'f'
+ finally
+ Xpath 'g'
+ if sum != 0
+ Xpath 'h'
+ endif
+ let sum = sum + 1
+ endtry
+ Xpath 'i'
+ catch /123/
+ Xpath 'j'
+ catch /321/
+ Xpath 'k'
+ finally
+ Xpath 'l'
+ if sum != 1
+ Xpath 'm'
+ endif
+ let sum = sum + 2
+ endtry
+ Xpath 'n'
+ finally
+ Xpath 'o'
+ if sum != 3
+ Xpath 'p'
+ endif
+ let sum = sum + 4
+ endtry
+ Xpath 'q'
+ catch /ABC/
+ Xpath 'r'
+ if sum != 7
+ Xpath 's'
+ endif
+ let sum = sum + 8
+ finally
+ Xpath 't'
+ if sum != 15
+ Xpath 'u'
+ endif
+ let sum = sum + 16
+ endtry
+ Xpath 'v'
+ if sum != 31
+ Xpath 'w'
+ endif
+endfunc
+
+func Test_finally_after_throw()
+ XpathINIT
+ call T46_F()
+ call assert_equal('abcdglortv', g:Xpath)
+endfunc
+
+
+"-------------------------------------------------------------------------------
+" Test 47: Throwing exceptions from a :catch clause {{{1
+"
+" When an exception is thrown from a :catch clause, it should not be
+" caught by a :catch of the same :try conditional. After executing
+" the :finally clause (if present), surrounding try conditionals
+" should be checked for a matching :catch.
+"-------------------------------------------------------------------------------
+
+func T47_F()
+ Xpath 'a'
+ try
+ Xpath 'b'
+ try
+ Xpath 'c'
+ try
+ Xpath 'd'
+ throw "x1"
+ Xpath 'e'
+ catch /x1/
+ Xpath 'f'
+ try
+ Xpath 'g'
+ throw "x2"
+ Xpath 'h'
+ catch /x1/
+ Xpath 'i'
+ catch /x2/
+ Xpath 'j'
+ try
+ Xpath 'k'
+ throw "x3"
+ Xpath 'l'
+ catch /x1/
+ Xpath 'm'
+ catch /x2/
+ Xpath 'n'
+ finally
+ Xpath 'o'
+ endtry
+ Xpath 'p'
+ catch /x3/
+ Xpath 'q'
+ endtry
+ Xpath 'r'
+ catch /x1/
+ Xpath 's'
+ catch /x2/
+ Xpath 't'
+ catch /x3/
+ Xpath 'u'
+ finally
+ Xpath 'v'
+ endtry
+ Xpath 'w'
+ catch /x1/
+ Xpath 'x'
+ catch /x2/
+ Xpath 'y'
+ catch /x3/
+ Xpath 'z'
+ endtry
+ Xpath 'A'
+ catch /.*/
+ Xpath 'B'
+ call assert_report('Caught ' . v:exception . ' in ' . v:throwpoint)
+ endtry
+ Xpath 'C'
+endfunc
+
+func Test_throw_from_catch()
+ XpathINIT
+ call T47_F()
+ call assert_equal('abcdfgjkovzAC', g:Xpath)
+endfunc
+
+
+"-------------------------------------------------------------------------------
+" Test 48: Throwing exceptions from a :finally clause {{{1
+"
+" When an exception is thrown from a :finally clause, it should not be
+" caught by a :catch of the same :try conditional. Surrounding try
+" conditionals should be checked for a matching :catch. A previously
+" thrown exception is discarded.
+"-------------------------------------------------------------------------------
+
+func T48_F()
+ try
+
+ try
+ try
+ Xpath 'a'
+ catch /x1/
+ Xpath 'b'
+ finally
+ Xpath 'c'
+ throw "x1"
+ Xpath 'd'
+ endtry
+ Xpath 'e'
+ catch /x1/
+ Xpath 'f'
+ endtry
+ Xpath 'g'
+
+ try
+ try
+ Xpath 'h'
+ throw "x2"
+ Xpath 'i'
+ catch /x2/
+ Xpath 'j'
+ catch /x3/
+ Xpath 'k'
+ finally
+ Xpath 'l'
+ throw "x3"
+ Xpath 'm'
+ endtry
+ Xpath 'n'
+ catch /x2/
+ Xpath 'o'
+ catch /x3/
+ Xpath 'p'
+ endtry
+ Xpath 'q'
+
+ try
+ try
+ try
+ Xpath 'r'
+ throw "x4"
+ Xpath 's'
+ catch /x5/
+ Xpath 't'
+ finally
+ Xpath 'u'
+ throw "x5" " discards 'x4'
+ Xpath 'v'
+ endtry
+ Xpath 'w'
+ catch /x4/
+ Xpath 'x'
+ finally
+ Xpath 'y'
+ endtry
+ Xpath 'z'
+ catch /x5/
+ Xpath 'A'
+ endtry
+ Xpath 'B'
+
+ catch /.*/
+ Xpath 'C'
+ call assert_report('Caught ' . v:exception . ' in ' . v:throwpoint)
+ endtry
+ Xpath 'D'
+endfunc
+
+func Test_throw_from_finally()
+ XpathINIT
+ call T48_F()
+ call assert_equal('acfghjlpqruyABD', g:Xpath)
+endfunc
+
+
+"-------------------------------------------------------------------------------
+" Test 51: Throwing exceptions across :execute and user commands {{{1
+"
+" A :throw command may be executed under an ":execute" or from
+" a user command.
+"-------------------------------------------------------------------------------
+
+func T51_F()
+ command! -nargs=? THROW1 throw <args> | throw 1
+ command! -nargs=? THROW2 try | throw <args> | endtry | throw 2
+ command! -nargs=? THROW3 try | throw 3 | catch /3/ | throw <args> | endtry
+ command! -nargs=? THROW4 try | throw 4 | finally | throw <args> | endtry
+
+ try
+
+ try
+ try
+ Xpath 'a'
+ THROW1 "A"
+ catch /A/
+ Xpath 'b'
+ endtry
+ catch /1/
+ Xpath 'c'
+ endtry
+
+ try
+ try
+ Xpath 'd'
+ THROW2 "B"
+ catch /B/
+ Xpath 'e'
+ endtry
+ catch /2/
+ Xpath 'f'
+ endtry
+
+ try
+ try
+ Xpath 'g'
+ THROW3 "C"
+ catch /C/
+ Xpath 'h'
+ endtry
+ catch /3/
+ Xpath 'i'
+ endtry
+
+ try
+ try
+ Xpath 'j'
+ THROW4 "D"
+ catch /D/
+ Xpath 'k'
+ endtry
+ catch /4/
+ Xpath 'l'
+ endtry
+
+ try
+ try
+ Xpath 'm'
+ execute 'throw "E" | throw 5'
+ catch /E/
+ Xpath 'n'
+ endtry
+ catch /5/
+ Xpath 'o'
+ endtry
+
+ try
+ try
+ Xpath 'p'
+ execute 'try | throw "F" | endtry | throw 6'
+ catch /F/
+ Xpath 'q'
+ endtry
+ catch /6/
+ Xpath 'r'
+ endtry
+
+ try
+ try
+ Xpath 's'
+ execute'try | throw 7 | catch /7/ | throw "G" | endtry'
+ catch /G/
+ Xpath 't'
+ endtry
+ catch /7/
+ Xpath 'u'
+ endtry
+
+ try
+ try
+ Xpath 'v'
+ execute 'try | throw 8 | finally | throw "H" | endtry'
+ catch /H/
+ Xpath 'w'
+ endtry
+ catch /8/
+ Xpath 'x'
+ endtry
+
+ catch /.*/
+ Xpath 'y'
+ call assert_report('Caught ' . v:exception . ' in ' . v:throwpoint)
+ endtry
+
+ Xpath 'z'
+
+ delcommand THROW1
+ delcommand THROW2
+ delcommand THROW3
+ delcommand THROW4
+endfunc
+
+func Test_throw_across_commands()
+ XpathINIT
+ call T51_F()
+ call assert_equal('abdeghjkmnpqstvwz', g:Xpath)
+endfunc
+
+
+
+"-------------------------------------------------------------------------------
+" Test 69: :throw across :if, :elseif, :while {{{1
+"
+" On an :if, :elseif, or :while command, an exception might be thrown
+" during evaluation of the expression to test. The exception can be
+" caught by the script.
+"-------------------------------------------------------------------------------
+
+func T69_throw(x)
+ Xpath 'x'
+ throw a:x
+endfunc
+
+func Test_throw_ifelsewhile()
+ XpathINIT
+
+ try
+ try
+ Xpath 'a'
+ if 111 == T69_throw("if") + 111
+ Xpath 'b'
+ else
+ Xpath 'c'
+ endif
+ Xpath 'd'
+ catch /^if$/
+ Xpath 'e'
+ catch /.*/
+ Xpath 'f'
+ call assert_report("if: " . v:exception . " in " . v:throwpoint)
+ endtry
+
+ try
+ Xpath 'g'
+ if v:false
+ Xpath 'h'
+ elseif 222 == T69_throw("elseif") + 222
+ Xpath 'i'
+ else
+ Xpath 'j'
+ endif
+ Xpath 'k'
+ catch /^elseif$/
+ Xpath 'l'
+ catch /.*/
+ Xpath 'm'
+ call assert_report("elseif: " . v:exception . " in " . v:throwpoint)
+ endtry
+
+ try
+ Xpath 'n'
+ while 333 == T69_throw("while") + 333
+ Xpath 'o'
+ break
+ endwhile
+ Xpath 'p'
+ catch /^while$/
+ Xpath 'q'
+ catch /.*/
+ Xpath 'r'
+ call assert_report("while: " .. v:exception .. " in " .. v:throwpoint)
+ endtry
+ catch /^0$/ " default return value
+ Xpath 's'
+ call assert_report(v:throwpoint)
+ catch /.*/
+ call assert_report(v:exception .. " in " .. v:throwpoint)
+ Xpath 't'
+ endtry
+
+ call assert_equal('axegxlnxq', g:Xpath)
+endfunc
+
+
+"-------------------------------------------------------------------------------
+" Test 70: :throw across :return or :throw {{{1
+"
+" On a :return or :throw command, an exception might be thrown during
+" evaluation of the expression to return or throw, respectively. The
+" exception can be caught by the script.
+"-------------------------------------------------------------------------------
+
+let T70_taken = ""
+
+func T70_throw(x, n)
+ let g:T70_taken = g:T70_taken . "T" . a:n
+ throw a:x
+endfunc
+
+func T70_F(x, y, n)
+ let g:T70_taken = g:T70_taken . "F" . a:n
+ return a:x + T70_throw(a:y, a:n)
+endfunc
+
+func T70_G(x, y, n)
+ let g:T70_taken = g:T70_taken . "G" . a:n
+ throw a:x . T70_throw(a:y, a:n)
+ return a:x
+endfunc
+
+func Test_throwreturn()
+ XpathINIT
+
+ try
+ try
+ Xpath 'a'
+ call T70_F(4711, "return", 1)
+ Xpath 'b'
+ catch /^return$/
+ Xpath 'c'
+ catch /.*/
+ Xpath 'd'
+ call assert_report("return: " .. v:exception .. " in " .. v:throwpoint)
+ endtry
+
+ try
+ Xpath 'e'
+ let var = T70_F(4712, "return-var", 2)
+ Xpath 'f'
+ catch /^return-var$/
+ Xpath 'g'
+ catch /.*/
+ Xpath 'h'
+ call assert_report("return-var: " . v:exception . " in " . v:throwpoint)
+ finally
+ unlet! var
+ endtry
+
+ try
+ Xpath 'i'
+ throw "except1" . T70_throw("throw1", 3)
+ Xpath 'j'
+ catch /^except1/
+ Xpath 'k'
+ catch /^throw1$/
+ Xpath 'l'
+ catch /.*/
+ Xpath 'm'
+ call assert_report("throw1: " .. v:exception .. " in " .. v:throwpoint)
+ endtry
+
+ try
+ Xpath 'n'
+ call T70_G("except2", "throw2", 4)
+ Xpath 'o'
+ catch /^except2/
+ Xpath 'p'
+ catch /^throw2$/
+ Xpath 'q'
+ catch /.*/
+ Xpath 'r'
+ call assert_report("throw2: " .. v:exception .. " in " .. v:throwpoint)
+ endtry
+
+ try
+ Xpath 's'
+ let var = T70_G("except3", "throw3", 5)
+ Xpath 't'
+ catch /^except3/
+ Xpath 'u'
+ catch /^throw3$/
+ Xpath 'v'
+ catch /.*/
+ Xpath 'w'
+ call assert_report("throw3: " .. v:exception .. " in " .. v:throwpoint)
+ finally
+ unlet! var
+ endtry
+
+ call assert_equal('F1T1F2T2T3G4T4G5T5', g:T70_taken)
+ Xpath 'x'
+ catch /^0$/ " default return value
+ Xpath 'y'
+ call assert_report(v:throwpoint)
+ catch /.*/
+ Xpath 'z'
+ call assert_report('Caught' .. v:exception .. ' in ' .. v:throwpoint)
+ endtry
+
+ call assert_equal('acegilnqsvx', g:Xpath)
+endfunc
+
+"-------------------------------------------------------------------------------
+" Test 71: :throw across :echo variants and :execute {{{1
+"
+" On an :echo, :echon, :echomsg, :echoerr, or :execute command, an
+" exception might be thrown during evaluation of the arguments to
+" be displayed or executed as a command, respectively. Any following
+" arguments are not evaluated, then. The exception can be caught by
+" the script.
+"-------------------------------------------------------------------------------
+
+let T71_taken = ""
+
+func T71_throw(x, n)
+ let g:T71_taken = g:T71_taken . "T" . a:n
+ throw a:x
+endfunc
+
+func T71_F(n)
+ let g:T71_taken = g:T71_taken . "F" . a:n
+ return "F" . a:n
+endfunc
+
+func Test_throw_echo()
+ XpathINIT
+
+ try
+ try
+ Xpath 'a'
+ echo 'echo ' . T71_throw("echo-except", 1) . T71_F(1)
+ Xpath 'b'
+ catch /^echo-except$/
+ Xpath 'c'
+ catch /.*/
+ Xpath 'd'
+ call assert_report("echo: " .. v:exception .. " in " .. v:throwpoint)
+ endtry
+
+ try
+ Xpath 'e'
+ echon "echon " . T71_throw("echon-except", 2) . T71_F(2)
+ Xpath 'f'
+ catch /^echon-except$/
+ Xpath 'g'
+ catch /.*/
+ Xpath 'h'
+ call assert_report('echon: ' . v:exception . ' in ' . v:throwpoint)
+ endtry
+
+ try
+ Xpath 'i'
+ echomsg "echomsg " . T71_throw("echomsg-except", 3) . T71_F(3)
+ Xpath 'j'
+ catch /^echomsg-except$/
+ Xpath 'k'
+ catch /.*/
+ Xpath 'l'
+ call assert_report('echomsg: ' . v:exception . ' in ' . v:throwpoint)
+ endtry
+
+ try
+ Xpath 'm'
+ echoerr "echoerr " . T71_throw("echoerr-except", 4) . T71_F(4)
+ Xpath 'n'
+ catch /^echoerr-except$/
+ Xpath 'o'
+ catch /Vim/
+ Xpath 'p'
+ catch /echoerr/
+ Xpath 'q'
+ catch /.*/
+ Xpath 'r'
+ call assert_report('echoerr: ' . v:exception . ' in ' . v:throwpoint)
+ endtry
+
+ try
+ Xpath 's'
+ execute "echo 'execute " . T71_throw("execute-except", 5) . T71_F(5) "'"
+ Xpath 't'
+ catch /^execute-except$/
+ Xpath 'u'
+ catch /.*/
+ Xpath 'v'
+ call assert_report('execute: ' . v:exception . ' in ' . v:throwpoint)
+ endtry
+
+ call assert_equal('T1T2T3T4T5', g:T71_taken)
+ Xpath 'w'
+ catch /^0$/ " default return value
+ Xpath 'x'
+ call assert_report(v:throwpoint)
+ catch /.*/
+ Xpath 'y'
+ call assert_report('Caught ' . v:exception . ' in ' . v:throwpoint)
+ endtry
+
+ call assert_equal('acegikmosuw', g:Xpath)
+endfunc
+
+
+"-------------------------------------------------------------------------------
+" Test 72: :throw across :let or :unlet {{{1
+"
+" On a :let command, an exception might be thrown during evaluation
+" of the expression to assign. On an :let or :unlet command, the
+" evaluation of the name of the variable to be assigned or list or
+" deleted, respectively, may throw an exception. Any following
+" arguments are not evaluated, then. The exception can be caught by
+" the script.
+"-------------------------------------------------------------------------------
+
+let throwcount = 0
+
+func T72_throw(x)
+ let g:throwcount = g:throwcount + 1
+ throw a:x
+endfunc
+
+let T72_addpath = ''
+
+func T72_addpath(p)
+ let g:T72_addpath = g:T72_addpath . a:p
+endfunc
+
+func Test_throw_let()
+ XpathINIT
+
+ try
+ try
+ let $VAR = 'old_value'
+ Xpath 'a'
+ let $VAR = 'let(' . T72_throw('var') . ')'
+ Xpath 'b'
+ catch /^var$/
+ Xpath 'c'
+ finally
+ call assert_equal('old_value', $VAR)
+ endtry
+
+ try
+ let @a = 'old_value'
+ Xpath 'd'
+ let @a = 'let(' . T72_throw('reg') . ')'
+ Xpath 'e'
+ catch /^reg$/
+ try
+ Xpath 'f'
+ let @A = 'let(' . T72_throw('REG') . ')'
+ Xpath 'g'
+ catch /^REG$/
+ Xpath 'h'
+ endtry
+ finally
+ call assert_equal('old_value', @a)
+ call assert_equal('old_value', @A)
+ endtry
+
+ try
+ let saved_gpath = &g:path
+ let saved_lpath = &l:path
+ Xpath 'i'
+ let &path = 'let(' . T72_throw('opt') . ')'
+ Xpath 'j'
+ catch /^opt$/
+ try
+ Xpath 'k'
+ let &g:path = 'let(' . T72_throw('gopt') . ')'
+ Xpath 'l'
+ catch /^gopt$/
+ try
+ Xpath 'm'
+ let &l:path = 'let(' . T72_throw('lopt') . ')'
+ Xpath 'n'
+ catch /^lopt$/
+ Xpath 'o'
+ endtry
+ endtry
+ finally
+ call assert_equal(saved_gpath, &g:path)
+ call assert_equal(saved_lpath, &l:path)
+ let &g:path = saved_gpath
+ let &l:path = saved_lpath
+ endtry
+
+ unlet! var1 var2 var3
+
+ try
+ Xpath 'p'
+ let var1 = 'let(' . T72_throw('var1') . ')'
+ Xpath 'q'
+ catch /^var1$/
+ Xpath 'r'
+ finally
+ call assert_true(!exists('var1'))
+ endtry
+
+ try
+ let var2 = 'old_value'
+ Xpath 's'
+ let var2 = 'let(' . T72_throw('var2'). ')'
+ Xpath 't'
+ catch /^var2$/
+ Xpath 'u'
+ finally
+ call assert_equal('old_value', var2)
+ endtry
+
+ try
+ Xpath 'v'
+ let var{T72_throw('var3')} = 4711
+ Xpath 'w'
+ catch /^var3$/
+ Xpath 'x'
+ endtry
+
+ try
+ call T72_addpath('T1')
+ let var{T72_throw('var4')} var{T72_addpath('T2')} | call T72_addpath('T3')
+ call T72_addpath('T4')
+ catch /^var4$/
+ call T72_addpath('T5')
+ endtry
+
+ try
+ call T72_addpath('T6')
+ unlet var{T72_throw('var5')} var{T72_addpath('T7')}
+ \ | call T72_addpath('T8')
+ call T72_addpath('T9')
+ catch /^var5$/
+ call T72_addpath('T10')
+ endtry
+
+ call assert_equal('T1T5T6T10', g:T72_addpath)
+ call assert_equal(11, g:throwcount)
+ catch /.*/
+ call assert_report('Caught ' . v:exception . ' in ' . v:throwpoint)
+ endtry
+
+ call assert_equal('acdfhikmoprsuvx', g:Xpath)
+endfunc
+
+
+"-------------------------------------------------------------------------------
+" Test 73: :throw across :function, :delfunction {{{1
+"
+" The :function and :delfunction commands may cause an expression
+" specified in braces to be evaluated. During evaluation, an
+" exception might be thrown. The exception can be caught by the
+" script.
+"-------------------------------------------------------------------------------
+
+let T73_taken = ''
+
+func T73_throw(x, n)
+ let g:T73_taken = g:T73_taken . 'T' . a:n
+ throw a:x
+endfunc
+
+func T73_expr(x, n)
+ let g:T73_taken = g:T73_taken . 'E' . a:n
+ if a:n % 2 == 0
+ call T73_throw(a:x, a:n)
+ endif
+ return 2 - a:n % 2
+endfunc
+
+func Test_throw_func()
+ XpathINIT
+
+ try
+ try
+ " Define function.
+ Xpath 'a'
+ function! F0()
+ endfunction
+ Xpath 'b'
+ function! F{T73_expr('function-def-ok', 1)}()
+ endfunction
+ Xpath 'c'
+ function! F{T73_expr('function-def', 2)}()
+ endfunction
+ Xpath 'd'
+ catch /^function-def-ok$/
+ Xpath 'e'
+ catch /^function-def$/
+ Xpath 'f'
+ catch /.*/
+ call assert_report('def: ' . v:exception . ' in ' . v:throwpoint)
+ endtry
+
+ try
+ " List function.
+ Xpath 'g'
+ function F0
+ Xpath 'h'
+ function F{T73_expr('function-lst-ok', 3)}
+ Xpath 'i'
+ function F{T73_expr('function-lst', 4)}
+ Xpath 'j'
+ catch /^function-lst-ok$/
+ Xpath 'k'
+ catch /^function-lst$/
+ Xpath 'l'
+ catch /.*/
+ call assert_report('lst: ' . v:exception . ' in ' . v:throwpoint)
+ endtry
+
+ try
+ " Delete function
+ Xpath 'm'
+ delfunction F0
+ Xpath 'n'
+ delfunction F{T73_expr('function-del-ok', 5)}
+ Xpath 'o'
+ delfunction F{T73_expr('function-del', 6)}
+ Xpath 'p'
+ catch /^function-del-ok$/
+ Xpath 'q'
+ catch /^function-del$/
+ Xpath 'r'
+ catch /.*/
+ call assert_report('del: ' . v:exception . ' in ' . v:throwpoint)
+ endtry
+ call assert_equal('E1E2T2E3E4T4E5E6T6', g:T73_taken)
+ catch /.*/
+ call assert_report('Caught ' . v:exception . ' in ' . v:throwpoint)
+ endtry
+
+ call assert_equal('abcfghilmnor', g:Xpath)
+endfunc
+
+
+"-------------------------------------------------------------------------------
+" Test 74: :throw across builtin functions and commands {{{1
+"
+" Some functions like exists(), searchpair() take expression
+" arguments, other functions or commands like substitute() or
+" :substitute cause an expression (specified in the regular
+" expression) to be evaluated. During evaluation an exception
+" might be thrown. The exception can be caught by the script.
+"-------------------------------------------------------------------------------
+
+let T74_taken = ""
+
+func T74_throw(x, n)
+ let g:T74_taken = g:T74_taken . "T" . a:n
+ throw a:x
+endfunc
+
+func T74_expr(x, n)
+ let g:T74_taken = g:T74_taken . "E" . a:n
+ call T74_throw(a:x . a:n, a:n)
+ return "EXPR"
+endfunc
+
+func T74_skip(x, n)
+ let g:T74_taken = g:T74_taken . "S" . a:n . "(" . line(".")
+ let theline = getline(".")
+ if theline =~ "skip"
+ let g:T74_taken = g:T74_taken . "s)"
+ return 1
+ elseif theline =~ "throw"
+ let g:T74_taken = g:T74_taken . "t)"
+ call T74_throw(a:x . a:n, a:n)
+ else
+ let g:T74_taken = g:T74_taken . ")"
+ return 0
+ endif
+endfunc
+
+func T74_subst(x, n)
+ let g:T74_taken = g:T74_taken . "U" . a:n . "(" . line(".")
+ let theline = getline(".")
+ if theline =~ "not" " T74_subst() should not be called for this line
+ let g:T74_taken = g:T74_taken . "n)"
+ call T74_throw(a:x . a:n, a:n)
+ elseif theline =~ "throw"
+ let g:T74_taken = g:T74_taken . "t)"
+ call T74_throw(a:x . a:n, a:n)
+ else
+ let g:T74_taken = g:T74_taken . ")"
+ return "replaced"
+ endif
+endfunc
+
+func Test_throw_builtin_func()
+ XpathINIT
+
+ try
+ try
+ Xpath 'a'
+ let result = exists('*{T74_expr("exists", 1)}')
+ Xpath 'b'
+ catch /^exists1$/
+ Xpath 'c'
+ try
+ let result = exists('{T74_expr("exists", 2)}')
+ Xpath 'd'
+ catch /^exists2$/
+ Xpath 'e'
+ catch /.*/
+ call assert_report('exists2: ' . v:exception . ' in ' . v:throwpoint)
+ endtry
+ catch /.*/
+ call assert_report('exists1: ' . v:exception . ' in ' . v:throwpoint)
+ endtry
+
+ try
+ let file = tempname()
+ exec "edit" file
+ call append(0, [
+ \ 'begin',
+ \ 'xx',
+ \ 'middle 3',
+ \ 'xx',
+ \ 'middle 5 skip',
+ \ 'xx',
+ \ 'middle 7 throw',
+ \ 'xx',
+ \ 'end'])
+ normal! gg
+ Xpath 'f'
+ let result = searchpair("begin", "middle", "end", '',
+ \ 'T74_skip("searchpair", 3)')
+ Xpath 'g'
+ let result = searchpair("begin", "middle", "end", '',
+ \ 'T74_skip("searchpair", 4)')
+ Xpath 'h'
+ let result = searchpair("begin", "middle", "end", '',
+ \ 'T74_skip("searchpair", 5)')
+ Xpath 'i'
+ catch /^searchpair[35]$/
+ Xpath 'j'
+ catch /^searchpair4$/
+ Xpath 'k'
+ catch /.*/
+ call assert_report('searchpair: ' . v:exception . ' in ' . v:throwpoint)
+ finally
+ bwipeout!
+ call delete(file)
+ endtry
+
+ try
+ let file = tempname()
+ exec "edit" file
+ call append(0, [
+ \ 'subst 1',
+ \ 'subst 2',
+ \ 'not',
+ \ 'subst 4',
+ \ 'subst throw',
+ \ 'subst 6'])
+ normal! gg
+ Xpath 'l'
+ 1,2substitute/subst/\=T74_subst("substitute", 6)/
+ try
+ Xpath 'm'
+ try
+ let v:errmsg = ""
+ 3substitute/subst/\=T74_subst("substitute", 7)/
+ finally
+ if v:errmsg != ""
+ " If exceptions are not thrown on errors, fake the error
+ " exception in order to get the same execution path.
+ throw "faked Vim(substitute)"
+ endif
+ endtry
+ catch /Vim(substitute)/ " Pattern not found ('e' flag missing)
+ Xpath 'n'
+ 3substitute/subst/\=T74_subst("substitute", 8)/e
+ Xpath 'o'
+ endtry
+ Xpath 'p'
+ 4,6substitute/subst/\=T74_subst("substitute", 9)/
+ Xpath 'q'
+ catch /^substitute[678]/
+ Xpath 'r'
+ catch /^substitute9/
+ Xpath 's'
+ finally
+ bwipeout!
+ call delete(file)
+ endtry
+
+ try
+ Xpath 't'
+ let var = substitute("sub", "sub", '\=T74_throw("substitute()y", 10)', '')
+ Xpath 'u'
+ catch /substitute()y/
+ Xpath 'v'
+ catch /.*/
+ call assert_report('substitute()y: ' . v:exception . ' in '
+ \ . v:throwpoint)
+ endtry
+
+ try
+ Xpath 'w'
+ let var = substitute("not", "sub", '\=T74_throw("substitute()n", 11)', '')
+ Xpath 'x'
+ catch /substitute()n/
+ Xpath 'y'
+ catch /.*/
+ call assert_report('substitute()n: ' . v:exception . ' in '
+ \ . v:throwpoint)
+ endtry
+
+ call assert_equal('E1T1E2T2S3(3)S4(5s)S4(7t)T4U6(1)U6(2)U9(4)U9(5t)T9T10',
+ \ g:T74_taken)
+
+ catch /.*/
+ call assert_report('Caught ' . v:exception . ' in ' . v:throwpoint)
+ endtry
+
+ call assert_equal('acefgklmnopstvwx', g:Xpath)
+endfunc
+
+
+"-------------------------------------------------------------------------------
+" Test 75: Errors in builtin functions. {{{1
+"
+" On an error in a builtin function called inside a :try/:endtry
+" region, the evaluation of the expression calling that function and
+" the command containing that expression are abandoned. The error can
+" be caught as an exception.
+"
+" A simple :call of the builtin function is a trivial case. If the
+" builtin function is called in the argument list of another function,
+" no further arguments are evaluated, and the other function is not
+" executed. If the builtin function is called from the argument of
+" a :return command, the :return command is not executed. If the
+" builtin function is called from the argument of a :throw command,
+" the :throw command is not executed. The evaluation of the
+" expression calling the builtin function is abandoned.
+"-------------------------------------------------------------------------------
+
+func T75_F1(arg1)
+ Xpath 'a'
+endfunc
+
+func T75_F2(arg1, arg2)
+ Xpath 'b'
+endfunc
+
+func T75_G()
+ Xpath 'c'
+endfunc
+
+func T75_H()
+ Xpath 'd'
+endfunc
+
+func T75_R()
+ while 1
+ try
+ let caught = 0
+ let v:errmsg = ""
+ Xpath 'e'
+ return append(1, "s")
+ catch /E21/
+ let caught = 1
+ catch /.*/
+ Xpath 'f'
+ finally
+ Xpath 'g'
+ if caught || $VIMNOERRTHROW && v:errmsg =~ 'E21'
+ Xpath 'h'
+ endif
+ break " discard error for $VIMNOERRTHROW
+ endtry
+ endwhile
+ Xpath 'i'
+endfunc
+
+func Test_builtin_func_error()
+ XpathINIT
+
+ try
+ set noma " let append() fail with "E21"
+
+ while 1
+ try
+ let caught = 0
+ let v:errmsg = ""
+ Xpath 'j'
+ call append(1, "s")
+ catch /E21/
+ let caught = 1
+ catch /.*/
+ Xpath 'k'
+ finally
+ Xpath 'l'
+ if caught || $VIMNOERRTHROW && v:errmsg =~ 'E21'
+ Xpath 'm'
+ endif
+ break " discard error for $VIMNOERRTHROW
+ endtry
+ endwhile
+
+ while 1
+ try
+ let caught = 0
+ let v:errmsg = ""
+ Xpath 'n'
+ call T75_F1('x' . append(1, "s"))
+ catch /E21/
+ let caught = 1
+ catch /.*/
+ Xpath 'o'
+ finally
+ Xpath 'p'
+ if caught || $VIMNOERRTHROW && v:errmsg =~ 'E21'
+ Xpath 'q'
+ endif
+ break " discard error for $VIMNOERRTHROW
+ endtry
+ endwhile
+
+ while 1
+ try
+ let caught = 0
+ let v:errmsg = ""
+ Xpath 'r'
+ call T75_F2('x' . append(1, "s"), T75_G())
+ catch /E21/
+ let caught = 1
+ catch /.*/
+ Xpath 's'
+ finally
+ Xpath 't'
+ if caught || $VIMNOERRTHROW && v:errmsg =~ 'E21'
+ Xpath 'u'
+ endif
+ break " discard error for $VIMNOERRTHROW
+ endtry
+ endwhile
+
+ call T75_R()
+
+ while 1
+ try
+ let caught = 0
+ let v:errmsg = ""
+ Xpath 'v'
+ throw "T" . append(1, "s")
+ catch /E21/
+ let caught = 1
+ catch /^T.*/
+ Xpath 'w'
+ catch /.*/
+ Xpath 'x'
+ finally
+ Xpath 'y'
+ if caught || $VIMNOERRTHROW && v:errmsg =~ 'E21'
+ Xpath 'z'
+ endif
+ break " discard error for $VIMNOERRTHROW
+ endtry
+ endwhile
+
+ while 1
+ try
+ let caught = 0
+ let v:errmsg = ""
+ Xpath 'A'
+ let x = "a"
+ let x = x . "b" . append(1, "s") . T75_H()
+ catch /E21/
+ let caught = 1
+ catch /.*/
+ Xpath 'B'
+ finally
+ Xpath 'C'
+ if caught || $VIMNOERRTHROW && v:errmsg =~ 'E21'
+ Xpath 'D'
+ endif
+ call assert_equal('a', x)
+ break " discard error for $VIMNOERRTHROW
+ endtry
+ endwhile
+ catch /.*/
+ call assert_report('Caught ' . v:exception . ' in ' . v:throwpoint)
+ finally
+ set ma&
+ endtry
+
+ call assert_equal('jlmnpqrtueghivyzACD', g:Xpath)
+endfunc
+
+" Modelines {{{1
+" vim: ts=8 sw=2 sts=2 expandtab tw=80 fdm=marker
+"-------------------------------------------------------------------------------