Mercurial > vim
comparison src/testdir/test_vimscript.vim @ 10942:e05695e59f6d v8.0.0360
patch 8.0.0360: sometimes VimL is used instead of "Vim script"
commit https://github.com/vim/vim/commit/b544f3c81f1e6a50322855681ac266ffaa8e313c
Author: Bram Moolenaar <Bram@vim.org>
Date: Thu Feb 23 19:03:28 2017 +0100
patch 8.0.0360: sometimes VimL is used instead of "Vim script"
Problem: Sometimes VimL is used, which is confusing.
Solution: Consistently use "Vim script". (Hirohito Higashi)
author | Christian Brabandt <cb@256bit.org> |
---|---|
date | Thu, 23 Feb 2017 19:15:05 +0100 |
parents | |
children | 1c4ebbae41d2 |
comparison
equal
deleted
inserted
replaced
10941:56b3c9414c82 | 10942:e05695e59f6d |
---|---|
1 " Test various aspects of the Vim language. | |
2 " Most of this was formerly in test49. | |
3 | |
4 "------------------------------------------------------------------------------- | |
5 " Test environment {{{1 | |
6 "------------------------------------------------------------------------------- | |
7 | |
8 com! XpathINIT let g:Xpath = '' | |
9 com! -nargs=1 -bar Xpath let g:Xpath = g:Xpath . <args> | |
10 | |
11 " Append a message to the "messages" file | |
12 func! Xout(text) | |
13 split messages | |
14 $put =a:text | |
15 wq | |
16 endfunc | |
17 | |
18 com! -nargs=1 Xout call Xout(<args>) | |
19 | |
20 " MakeScript() - Make a script file from a function. {{{2 | |
21 " | |
22 " Create a script that consists of the body of the function a:funcname. | |
23 " Replace any ":return" by a ":finish", any argument variable by a global | |
24 " variable, and and every ":call" by a ":source" for the next following argument | |
25 " in the variable argument list. This function is useful if similar tests are | |
26 " to be made for a ":return" from a function call or a ":finish" in a script | |
27 " file. | |
28 function! MakeScript(funcname, ...) | |
29 let script = tempname() | |
30 execute "redir! >" . script | |
31 execute "function" a:funcname | |
32 redir END | |
33 execute "edit" script | |
34 " Delete the "function" and the "endfunction" lines. Do not include the | |
35 " word "function" in the pattern since it might be translated if LANG is | |
36 " set. When MakeScript() is being debugged, this deletes also the debugging | |
37 " output of its line 3 and 4. | |
38 exec '1,/.*' . a:funcname . '(.*)/d' | |
39 /^\d*\s*endfunction\>/,$d | |
40 %s/^\d*//e | |
41 %s/return/finish/e | |
42 %s/\<a:\(\h\w*\)/g:\1/ge | |
43 normal gg0 | |
44 let cnt = 0 | |
45 while search('\<call\s*\%(\u\|s:\)\w*\s*(.*)', 'W') > 0 | |
46 let cnt = cnt + 1 | |
47 s/\<call\s*\%(\u\|s:\)\w*\s*(.*)/\='source ' . a:{cnt}/ | |
48 endwhile | |
49 g/^\s*$/d | |
50 write | |
51 bwipeout | |
52 return script | |
53 endfunction | |
54 | |
55 " ExecAsScript - Source a temporary script made from a function. {{{2 | |
56 " | |
57 " Make a temporary script file from the function a:funcname, ":source" it, and | |
58 " delete it afterwards. However, if an exception is thrown the file may remain, | |
59 " the caller should call DeleteTheScript() afterwards. | |
60 let s:script_name = '' | |
61 function! ExecAsScript(funcname) | |
62 " Make a script from the function passed as argument. | |
63 let s:script_name = MakeScript(a:funcname) | |
64 | |
65 " Source and delete the script. | |
66 exec "source" s:script_name | |
67 call delete(s:script_name) | |
68 let s:script_name = '' | |
69 endfunction | |
70 | |
71 function! DeleteTheScript() | |
72 if s:script_name | |
73 call delete(s:script_name) | |
74 let s:script_name = '' | |
75 endif | |
76 endfunc | |
77 | |
78 com! -nargs=1 -bar ExecAsScript call ExecAsScript(<f-args>) | |
79 | |
80 | |
81 "------------------------------------------------------------------------------- | |
82 " Test 1: :endwhile in function {{{1 | |
83 " | |
84 " Detect if a broken loop is (incorrectly) reactivated by the | |
85 " :endwhile. Use a :return to prevent an endless loop, and make | |
86 " this test first to get a meaningful result on an error before other | |
87 " tests will hang. | |
88 "------------------------------------------------------------------------------- | |
89 | |
90 function! T1_F() | |
91 Xpath 'a' | |
92 let first = 1 | |
93 while 1 | |
94 Xpath 'b' | |
95 if first | |
96 Xpath 'c' | |
97 let first = 0 | |
98 break | |
99 else | |
100 Xpath 'd' | |
101 return | |
102 endif | |
103 endwhile | |
104 endfunction | |
105 | |
106 function! T1_G() | |
107 Xpath 'h' | |
108 let first = 1 | |
109 while 1 | |
110 Xpath 'i' | |
111 if first | |
112 Xpath 'j' | |
113 let first = 0 | |
114 break | |
115 else | |
116 Xpath 'k' | |
117 return | |
118 endif | |
119 if 1 " unmatched :if | |
120 endwhile | |
121 endfunction | |
122 | |
123 func Test_endwhile_function() | |
124 XpathINIT | |
125 call T1_F() | |
126 Xpath 'F' | |
127 | |
128 try | |
129 call T1_G() | |
130 catch | |
131 " Catch missing :endif | |
132 call assert_true(v:exception =~ 'E171') | |
133 Xpath 'x' | |
134 endtry | |
135 Xpath 'G' | |
136 | |
137 call assert_equal('abcFhijxG', g:Xpath) | |
138 endfunc | |
139 | |
140 "------------------------------------------------------------------------------- | |
141 " Test 2: :endwhile in script {{{1 | |
142 " | |
143 " Detect if a broken loop is (incorrectly) reactivated by the | |
144 " :endwhile. Use a :finish to prevent an endless loop, and place | |
145 " this test before others that might hang to get a meaningful result | |
146 " on an error. | |
147 " | |
148 " This test executes the bodies of the functions T1_F and T1_G from | |
149 " the previous test as script files (:return replaced by :finish). | |
150 "------------------------------------------------------------------------------- | |
151 | |
152 func Test_endwhile_script() | |
153 XpathINIT | |
154 ExecAsScript T1_F | |
155 Xpath 'F' | |
156 call DeleteTheScript() | |
157 | |
158 try | |
159 ExecAsScript T1_G | |
160 catch | |
161 " Catch missing :endif | |
162 call assert_true(v:exception =~ 'E171') | |
163 Xpath 'x' | |
164 endtry | |
165 Xpath 'G' | |
166 call DeleteTheScript() | |
167 | |
168 call assert_equal('abcFhijxG', g:Xpath) | |
169 endfunc | |
170 | |
171 "------------------------------------------------------------------------------- | |
172 " Test 3: :if, :elseif, :while, :continue, :break {{{1 | |
173 "------------------------------------------------------------------------------- | |
174 | |
175 function Test_if_while() | |
176 XpathINIT | |
177 if 1 | |
178 Xpath 'a' | |
179 let loops = 3 | |
180 while loops > -1 " main loop: loops == 3, 2, 1 (which breaks) | |
181 if loops <= 0 | |
182 let break_err = 1 | |
183 let loops = -1 | |
184 else | |
185 Xpath 'b' . loops | |
186 endif | |
187 if (loops == 2) | |
188 while loops == 2 " dummy loop | |
189 Xpath 'c' . loops | |
190 let loops = loops - 1 | |
191 continue " stop dummy loop | |
192 Xpath 'd' . loops | |
193 endwhile | |
194 continue " continue main loop | |
195 Xpath 'e' . loops | |
196 elseif (loops == 1) | |
197 let p = 1 | |
198 while p " dummy loop | |
199 Xpath 'f' . loops | |
200 let p = 0 | |
201 break " break dummy loop | |
202 Xpath 'g' . loops | |
203 endwhile | |
204 Xpath 'h' . loops | |
205 unlet p | |
206 break " break main loop | |
207 Xpath 'i' . loops | |
208 endif | |
209 if (loops > 0) | |
210 Xpath 'j' . loops | |
211 endif | |
212 while loops == 3 " dummy loop | |
213 let loops = loops - 1 | |
214 endwhile " end dummy loop | |
215 endwhile " end main loop | |
216 Xpath 'k' | |
217 else | |
218 Xpath 'l' | |
219 endif | |
220 Xpath 'm' | |
221 if exists("break_err") | |
222 Xpath 'm' | |
223 unlet break_err | |
224 endif | |
225 | |
226 unlet loops | |
227 | |
228 call assert_equal('ab3j3b2c2b1f1h1km', g:Xpath) | |
229 endfunc | |
230 | |
231 "------------------------------------------------------------------------------- | |
232 " Test 4: :return {{{1 | |
233 "------------------------------------------------------------------------------- | |
234 | |
235 function! T4_F() | |
236 if 1 | |
237 Xpath 'a' | |
238 let loops = 3 | |
239 while loops > 0 " 3: 2: 1: | |
240 Xpath 'b' . loops | |
241 if (loops == 2) | |
242 Xpath 'c' . loops | |
243 return | |
244 Xpath 'd' . loops | |
245 endif | |
246 Xpath 'e' . loops | |
247 let loops = loops - 1 | |
248 endwhile | |
249 Xpath 'f' | |
250 else | |
251 Xpath 'g' | |
252 endif | |
253 endfunction | |
254 | |
255 function Test_return() | |
256 XpathINIT | |
257 call T4_F() | |
258 Xpath '4' | |
259 | |
260 call assert_equal('ab3e3b2c24', g:Xpath) | |
261 endfunction | |
262 | |
263 | |
264 "------------------------------------------------------------------------------- | |
265 " Test 5: :finish {{{1 | |
266 " | |
267 " This test executes the body of the function T4_F from the previous | |
268 " test as a script file (:return replaced by :finish). | |
269 "------------------------------------------------------------------------------- | |
270 | |
271 function Test_finish() | |
272 XpathINIT | |
273 ExecAsScript T4_F | |
274 Xpath '5' | |
275 call DeleteTheScript() | |
276 | |
277 call assert_equal('ab3e3b2c25', g:Xpath) | |
278 endfunction | |
279 | |
280 | |
281 | |
282 "------------------------------------------------------------------------------- | |
283 " Test 6: Defining functions in :while loops {{{1 | |
284 " | |
285 " Functions can be defined inside other functions. An inner function | |
286 " gets defined when the outer function is executed. Functions may | |
287 " also be defined inside while loops. Expressions in braces for | |
288 " defining the function name are allowed. | |
289 " | |
290 " The functions are defined when sourcing the script, only the | |
291 " resulting path is checked in the test function. | |
292 "------------------------------------------------------------------------------- | |
293 | |
294 XpathINIT | |
295 | |
296 " The command CALL collects the argument of all its invocations in "calls" | |
297 " when used from a function (that is, when the global variable "calls" needs | |
298 " the "g:" prefix). This is to check that the function code is skipped when | |
299 " the function is defined. For inner functions, do so only if the outer | |
300 " function is not being executed. | |
301 " | |
302 let calls = "" | |
303 com! -nargs=1 CALL | |
304 \ if !exists("calls") && !exists("outer") | | |
305 \ let g:calls = g:calls . <args> | | |
306 \ endif | |
307 | |
308 let i = 0 | |
309 while i < 3 | |
310 let i = i + 1 | |
311 if i == 1 | |
312 Xpath 'a' | |
313 function! F1(arg) | |
314 CALL a:arg | |
315 let outer = 1 | |
316 | |
317 let j = 0 | |
318 while j < 1 | |
319 Xpath 'b' | |
320 let j = j + 1 | |
321 function! G1(arg) | |
322 CALL a:arg | |
323 endfunction | |
324 Xpath 'c' | |
325 endwhile | |
326 endfunction | |
327 Xpath 'd' | |
328 | |
329 continue | |
330 endif | |
331 | |
332 Xpath 'e' . i | |
333 function! F{i}(i, arg) | |
334 CALL a:arg | |
335 let outer = 1 | |
336 | |
337 if a:i == 3 | |
338 Xpath 'f' | |
339 endif | |
340 let k = 0 | |
341 while k < 3 | |
342 Xpath 'g' . k | |
343 let k = k + 1 | |
344 function! G{a:i}{k}(arg) | |
345 CALL a:arg | |
346 endfunction | |
347 Xpath 'h' . k | |
348 endwhile | |
349 endfunction | |
350 Xpath 'i' | |
351 | |
352 endwhile | |
353 | |
354 if exists("*G1") | |
355 Xpath 'j' | |
356 endif | |
357 if exists("*F1") | |
358 call F1("F1") | |
359 if exists("*G1") | |
360 call G1("G1") | |
361 endif | |
362 endif | |
363 | |
364 if exists("G21") || exists("G22") || exists("G23") | |
365 Xpath 'k' | |
366 endif | |
367 if exists("*F2") | |
368 call F2(2, "F2") | |
369 if exists("*G21") | |
370 call G21("G21") | |
371 endif | |
372 if exists("*G22") | |
373 call G22("G22") | |
374 endif | |
375 if exists("*G23") | |
376 call G23("G23") | |
377 endif | |
378 endif | |
379 | |
380 if exists("G31") || exists("G32") || exists("G33") | |
381 Xpath 'l' | |
382 endif | |
383 if exists("*F3") | |
384 call F3(3, "F3") | |
385 if exists("*G31") | |
386 call G31("G31") | |
387 endif | |
388 if exists("*G32") | |
389 call G32("G32") | |
390 endif | |
391 if exists("*G33") | |
392 call G33("G33") | |
393 endif | |
394 endif | |
395 | |
396 Xpath 'm' | |
397 | |
398 let g:test6_result = g:Xpath | |
399 let g:test6_calls = calls | |
400 | |
401 unlet calls | |
402 delfunction F1 | |
403 delfunction G1 | |
404 delfunction F2 | |
405 delfunction G21 | |
406 delfunction G22 | |
407 delfunction G23 | |
408 delfunction G31 | |
409 delfunction G32 | |
410 delfunction G33 | |
411 | |
412 function Test_defining_functions() | |
413 call assert_equal('ade2ie3ibcg0h1g1h2g2h3fg0h1g1h2g2h3m', g:test6_result) | |
414 call assert_equal('F1G1F2G21G22G23F3G31G32G33', g:test6_calls) | |
415 endfunc | |
416 | |
417 "------------------------------------------------------------------------------- | |
418 " Test 7: Continuing on errors outside functions {{{1 | |
419 " | |
420 " On an error outside a function, the script processing continues | |
421 " at the line following the outermost :endif or :endwhile. When not | |
422 " inside an :if or :while, the script processing continues at the next | |
423 " line. | |
424 "------------------------------------------------------------------------------- | |
425 | |
426 XpathINIT | |
427 | |
428 if 1 | |
429 Xpath 'a' | |
430 while 1 | |
431 Xpath 'b' | |
432 asdf | |
433 Xpath 'c' | |
434 break | |
435 endwhile | Xpath 'd' | |
436 Xpath 'e' | |
437 endif | Xpath 'f' | |
438 Xpath 'g' | |
439 | |
440 while 1 | |
441 Xpath 'h' | |
442 if 1 | |
443 Xpath 'i' | |
444 asdf | |
445 Xpath 'j' | |
446 endif | Xpath 'k' | |
447 Xpath 'l' | |
448 break | |
449 endwhile | Xpath 'm' | |
450 Xpath 'n' | |
451 | |
452 asdf | |
453 Xpath 'o' | |
454 | |
455 asdf | Xpath 'p' | |
456 Xpath 'q' | |
457 | |
458 let g:test7_result = g:Xpath | |
459 | |
460 func Test_error_in_script() | |
461 call assert_equal('abghinoq', g:test7_result) | |
462 endfunc | |
463 | |
464 "------------------------------------------------------------------------------- | |
465 " Test 8: Aborting and continuing on errors inside functions {{{1 | |
466 " | |
467 " On an error inside a function without the "abort" attribute, the | |
468 " script processing continues at the next line (unless the error was | |
469 " in a :return command). On an error inside a function with the | |
470 " "abort" attribute, the function is aborted and the script processing | |
471 " continues after the function call; the value -1 is returned then. | |
472 "------------------------------------------------------------------------------- | |
473 | |
474 XpathINIT | |
475 | |
476 function! T8_F() | |
477 if 1 | |
478 Xpath 'a' | |
479 while 1 | |
480 Xpath 'b' | |
481 asdf | |
482 Xpath 'c' | |
483 asdf | Xpath 'd' | |
484 Xpath 'e' | |
485 break | |
486 endwhile | |
487 Xpath 'f' | |
488 endif | Xpath 'g' | |
489 Xpath 'h' | |
490 | |
491 while 1 | |
492 Xpath 'i' | |
493 if 1 | |
494 Xpath 'j' | |
495 asdf | |
496 Xpath 'k' | |
497 asdf | Xpath 'l' | |
498 Xpath 'm' | |
499 endif | |
500 Xpath 'n' | |
501 break | |
502 endwhile | Xpath 'o' | |
503 Xpath 'p' | |
504 | |
505 return novar " returns (default return value 0) | |
506 Xpath 'q' | |
507 return 1 " not reached | |
508 endfunction | |
509 | |
510 function! T8_G() abort | |
511 if 1 | |
512 Xpath 'r' | |
513 while 1 | |
514 Xpath 's' | |
515 asdf " returns -1 | |
516 Xpath 't' | |
517 break | |
518 endwhile | |
519 Xpath 'v' | |
520 endif | Xpath 'w' | |
521 Xpath 'x' | |
522 | |
523 return -4 " not reached | |
524 endfunction | |
525 | |
526 function! T8_H() abort | |
527 while 1 | |
528 Xpath 'A' | |
529 if 1 | |
530 Xpath 'B' | |
531 asdf " returns -1 | |
532 Xpath 'C' | |
533 endif | |
534 Xpath 'D' | |
535 break | |
536 endwhile | Xpath 'E' | |
537 Xpath 'F' | |
538 | |
539 return -4 " not reached | |
540 endfunction | |
541 | |
542 " Aborted functions (T8_G and T8_H) return -1. | |
543 let g:test8_sum = (T8_F() + 1) - 4 * T8_G() - 8 * T8_H() | |
544 Xpath 'X' | |
545 let g:test8_result = g:Xpath | |
546 | |
547 func Test_error_in_function() | |
548 call assert_equal(13, g:test8_sum) | |
549 call assert_equal('abcefghijkmnoprsABX', g:test8_result) | |
550 | |
551 delfunction T8_F | |
552 delfunction T8_G | |
553 delfunction T8_H | |
554 endfunc | |
555 | |
556 | |
557 "------------------------------------------------------------------------------- | |
558 " Test 9: Continuing after aborted functions {{{1 | |
559 " | |
560 " When a function with the "abort" attribute is aborted due to an | |
561 " error, the next function back in the call hierarchy without an | |
562 " "abort" attribute continues; the value -1 is returned then. | |
563 "------------------------------------------------------------------------------- | |
564 | |
565 XpathINIT | |
566 | |
567 function! F() abort | |
568 Xpath 'a' | |
569 let result = G() " not aborted | |
570 Xpath 'b' | |
571 if result != 2 | |
572 Xpath 'c' | |
573 endif | |
574 return 1 | |
575 endfunction | |
576 | |
577 function! G() " no abort attribute | |
578 Xpath 'd' | |
579 if H() != -1 " aborted | |
580 Xpath 'e' | |
581 endif | |
582 Xpath 'f' | |
583 return 2 | |
584 endfunction | |
585 | |
586 function! H() abort | |
587 Xpath 'g' | |
588 call I() " aborted | |
589 Xpath 'h' | |
590 return 4 | |
591 endfunction | |
592 | |
593 function! I() abort | |
594 Xpath 'i' | |
595 asdf " error | |
596 Xpath 'j' | |
597 return 8 | |
598 endfunction | |
599 | |
600 if F() != 1 | |
601 Xpath 'k' | |
602 endif | |
603 | |
604 let g:test9_result = g:Xpath | |
605 | |
606 delfunction F | |
607 delfunction G | |
608 delfunction H | |
609 delfunction I | |
610 | |
611 func Test_func_abort() | |
612 call assert_equal('adgifb', g:test9_result) | |
613 endfunc | |
614 | |
615 | |
616 "------------------------------------------------------------------------------- | |
617 " Test 10: :if, :elseif, :while argument parsing {{{1 | |
618 " | |
619 " A '"' or '|' in an argument expression must not be mixed up with | |
620 " a comment or a next command after a bar. Parsing errors should | |
621 " be recognized. | |
622 "------------------------------------------------------------------------------- | |
623 | |
624 XpathINIT | |
625 | |
626 function! MSG(enr, emsg) | |
627 let english = v:lang == "C" || v:lang =~ '^[Ee]n' | |
628 if a:enr == "" | |
629 Xout "TODO: Add message number for:" a:emsg | |
630 let v:errmsg = ":" . v:errmsg | |
631 endif | |
632 let match = 1 | |
633 if v:errmsg !~ '^'.a:enr.':' || (english && v:errmsg !~ a:emsg) | |
634 let match = 0 | |
635 if v:errmsg == "" | |
636 Xout "Message missing." | |
637 else | |
638 let v:errmsg = escape(v:errmsg, '"') | |
639 Xout "Unexpected message:" v:errmsg | |
640 endif | |
641 endif | |
642 return match | |
643 endfunction | |
644 | |
645 if 1 || strlen("\"") | Xpath 'a' | |
646 Xpath 'b' | |
647 endif | |
648 Xpath 'c' | |
649 | |
650 if 0 | |
651 elseif 1 || strlen("\"") | Xpath 'd' | |
652 Xpath 'e' | |
653 endif | |
654 Xpath 'f' | |
655 | |
656 while 1 || strlen("\"") | Xpath 'g' | |
657 Xpath 'h' | |
658 break | |
659 endwhile | |
660 Xpath 'i' | |
661 | |
662 let v:errmsg = "" | |
663 if 1 ||| strlen("\"") | Xpath 'j' | |
664 Xpath 'k' | |
665 endif | |
666 Xpath 'l' | |
667 if !MSG('E15', "Invalid expression") | |
668 Xpath 'm' | |
669 endif | |
670 | |
671 let v:errmsg = "" | |
672 if 0 | |
673 elseif 1 ||| strlen("\"") | Xpath 'n' | |
674 Xpath 'o' | |
675 endif | |
676 Xpath 'p' | |
677 if !MSG('E15', "Invalid expression") | |
678 Xpath 'q' | |
679 endif | |
680 | |
681 let v:errmsg = "" | |
682 while 1 ||| strlen("\"") | Xpath 'r' | |
683 Xpath 's' | |
684 break | |
685 endwhile | |
686 Xpath 't' | |
687 if !MSG('E15', "Invalid expression") | |
688 Xpath 'u' | |
689 endif | |
690 | |
691 let g:test10_result = g:Xpath | |
692 delfunction MSG | |
693 | |
694 func Test_expr_parsing() | |
695 call assert_equal('abcdefghilpt', g:test10_result) | |
696 endfunc | |
697 | |
698 | |
699 "------------------------------------------------------------------------------- | |
700 " Test 11: :if, :elseif, :while argument evaluation after abort {{{1 | |
701 " | |
702 " When code is skipped over due to an error, the boolean argument to | |
703 " an :if, :elseif, or :while must not be evaluated. | |
704 "------------------------------------------------------------------------------- | |
705 | |
706 XpathINIT | |
707 | |
708 let calls = 0 | |
709 | |
710 function! P(num) | |
711 let g:calls = g:calls + a:num " side effect on call | |
712 return 0 | |
713 endfunction | |
714 | |
715 if 1 | |
716 Xpath 'a' | |
717 asdf " error | |
718 Xpath 'b' | |
719 if P(1) " should not be called | |
720 Xpath 'c' | |
721 elseif !P(2) " should not be called | |
722 Xpath 'd' | |
723 else | |
724 Xpath 'e' | |
725 endif | |
726 Xpath 'f' | |
727 while P(4) " should not be called | |
728 Xpath 'g' | |
729 endwhile | |
730 Xpath 'h' | |
731 endif | |
732 Xpath 'x' | |
733 | |
734 let g:test11_calls = calls | |
735 let g:test11_result = g:Xpath | |
736 | |
737 unlet calls | |
738 delfunction P | |
739 | |
740 func Test_arg_abort() | |
741 call assert_equal(0, g:test11_calls) | |
742 call assert_equal('ax', g:test11_result) | |
743 endfunc | |
744 | |
745 | |
746 "------------------------------------------------------------------------------- | |
747 " Test 12: Expressions in braces in skipped code {{{1 | |
748 " | |
749 " In code skipped over due to an error or inactive conditional, | |
750 " an expression in braces as part of a variable or function name | |
751 " should not be evaluated. | |
752 "------------------------------------------------------------------------------- | |
753 | |
754 XpathINIT | |
755 | |
756 function! NULL() | |
757 Xpath 'a' | |
758 return 0 | |
759 endfunction | |
760 | |
761 function! ZERO() | |
762 Xpath 'b' | |
763 return 0 | |
764 endfunction | |
765 | |
766 function! F0() | |
767 Xpath 'c' | |
768 endfunction | |
769 | |
770 function! F1(arg) | |
771 Xpath 'e' | |
772 endfunction | |
773 | |
774 let V0 = 1 | |
775 | |
776 Xpath 'f' | |
777 echo 0 ? F{NULL() + V{ZERO()}}() : 1 | |
778 | |
779 Xpath 'g' | |
780 if 0 | |
781 Xpath 'h' | |
782 call F{NULL() + V{ZERO()}}() | |
783 endif | |
784 | |
785 Xpath 'i' | |
786 if 1 | |
787 asdf " error | |
788 Xpath 'j' | |
789 call F1(F{NULL() + V{ZERO()}}()) | |
790 endif | |
791 | |
792 Xpath 'k' | |
793 if 1 | |
794 asdf " error | |
795 Xpath 'l' | |
796 call F{NULL() + V{ZERO()}}() | |
797 endif | |
798 | |
799 let g:test12_result = g:Xpath | |
800 | |
801 func Test_braces_skipped() | |
802 call assert_equal('fgik', g:test12_result) | |
803 endfunc | |
804 | |
805 | |
806 "------------------------------------------------------------------------------- | |
807 " Test 13: Failure in argument evaluation for :while {{{1 | |
808 " | |
809 " A failure in the expression evaluation for the condition of a :while | |
810 " causes the whole :while loop until the matching :endwhile being | |
811 " ignored. Continuation is at the next following line. | |
812 "------------------------------------------------------------------------------- | |
813 | |
814 XpathINIT | |
815 | |
816 Xpath 'a' | |
817 while asdf | |
818 Xpath 'b' | |
819 while 1 | |
820 Xpath 'c' | |
821 break | |
822 endwhile | |
823 Xpath 'd' | |
824 break | |
825 endwhile | |
826 Xpath 'e' | |
827 | |
828 while asdf | Xpath 'f' | endwhile | Xpath 'g' | |
829 Xpath 'h' | |
830 let g:test13_result = g:Xpath | |
831 | |
832 func Test_while_fail() | |
833 call assert_equal('aeh', g:test13_result) | |
834 endfunc | |
835 | |
836 | |
837 "------------------------------------------------------------------------------- | |
838 " Test 14: Failure in argument evaluation for :if {{{1 | |
839 " | |
840 " A failure in the expression evaluation for the condition of an :if | |
841 " does not cause the corresponding :else or :endif being matched to | |
842 " a previous :if/:elseif. Neither of both branches of the failed :if | |
843 " are executed. | |
844 "------------------------------------------------------------------------------- | |
845 | |
846 XpathINIT | |
847 | |
848 function! F() | |
849 Xpath 'a' | |
850 let x = 0 | |
851 if x " false | |
852 Xpath 'b' | |
853 elseif !x " always true | |
854 Xpath 'c' | |
855 let x = 1 | |
856 if g:boolvar " possibly undefined | |
857 Xpath 'd' | |
858 else | |
859 Xpath 'e' | |
860 endif | |
861 Xpath 'f' | |
862 elseif x " never executed | |
863 Xpath 'g' | |
864 endif | |
865 Xpath 'h' | |
866 endfunction | |
867 | |
868 let boolvar = 1 | |
869 call F() | |
870 Xpath '-' | |
871 | |
872 unlet boolvar | |
873 call F() | |
874 let g:test14_result = g:Xpath | |
875 | |
876 delfunction F | |
877 | |
878 func Test_if_fail() | |
879 call assert_equal('acdfh-acfh', g:test14_result) | |
880 endfunc | |
881 | |
882 | |
883 "------------------------------------------------------------------------------- | |
884 " Test 15: Failure in argument evaluation for :if (bar) {{{1 | |
885 " | |
886 " Like previous test, except that the failing :if ... | ... | :endif | |
887 " is in a single line. | |
888 "------------------------------------------------------------------------------- | |
889 | |
890 XpathINIT | |
891 | |
892 function! F() | |
893 Xpath 'a' | |
894 let x = 0 | |
895 if x " false | |
896 Xpath 'b' | |
897 elseif !x " always true | |
898 Xpath 'c' | |
899 let x = 1 | |
900 if g:boolvar | Xpath 'd' | else | Xpath 'e' | endif | |
901 Xpath 'f' | |
902 elseif x " never executed | |
903 Xpath 'g' | |
904 endif | |
905 Xpath 'h' | |
906 endfunction | |
907 | |
908 let boolvar = 1 | |
909 call F() | |
910 Xpath '-' | |
911 | |
912 unlet boolvar | |
913 call F() | |
914 let g:test15_result = g:Xpath | |
915 | |
916 delfunction F | |
917 | |
918 func Test_if_bar_fail() | |
919 call assert_equal('acdfh-acfh', g:test15_result) | |
920 endfunc | |
921 | |
922 "------------------------------------------------------------------------------- | |
923 " Test 90: Recognizing {} in variable name. {{{1 | |
924 "------------------------------------------------------------------------------- | |
925 | |
926 func Test_curlies() | |
927 let s:var = 66 | |
928 let ns = 's' | |
929 call assert_equal(66, {ns}:var) | |
930 | |
931 let g:a = {} | |
932 let g:b = 't' | |
933 let g:a[g:b] = 77 | |
934 call assert_equal(77, g:a['t']) | |
935 endfunc | |
936 | |
937 "------------------------------------------------------------------------------- | |
938 " Test 91: using type(). {{{1 | |
939 "------------------------------------------------------------------------------- | |
940 | |
941 func Test_type() | |
942 call assert_equal(0, type(0)) | |
943 call assert_equal(1, type("")) | |
944 call assert_equal(2, type(function("tr"))) | |
945 call assert_equal(2, type(function("tr", [8]))) | |
946 call assert_equal(3, type([])) | |
947 call assert_equal(4, type({})) | |
948 call assert_equal(5, type(0.0)) | |
949 call assert_equal(6, type(v:false)) | |
950 call assert_equal(6, type(v:true)) | |
951 call assert_equal(7, type(v:none)) | |
952 call assert_equal(7, type(v:null)) | |
953 call assert_equal(8, v:t_job) | |
954 call assert_equal(9, v:t_channel) | |
955 call assert_equal(v:t_number, type(0)) | |
956 call assert_equal(v:t_string, type("")) | |
957 call assert_equal(v:t_func, type(function("tr"))) | |
958 call assert_equal(v:t_func, type(function("tr", [8]))) | |
959 call assert_equal(v:t_list, type([])) | |
960 call assert_equal(v:t_dict, type({})) | |
961 call assert_equal(v:t_float, type(0.0)) | |
962 call assert_equal(v:t_bool, type(v:false)) | |
963 call assert_equal(v:t_bool, type(v:true)) | |
964 call assert_equal(v:t_none, type(v:none)) | |
965 call assert_equal(v:t_none, type(v:null)) | |
966 | |
967 | |
968 call assert_equal(0, 0 + v:false) | |
969 call assert_equal(1, 0 + v:true) | |
970 call assert_equal(0, 0 + v:none) | |
971 call assert_equal(0, 0 + v:null) | |
972 | |
973 call assert_equal('v:false', '' . v:false) | |
974 call assert_equal('v:true', '' . v:true) | |
975 call assert_equal('v:none', '' . v:none) | |
976 call assert_equal('v:null', '' . v:null) | |
977 | |
978 call assert_true(v:false == 0) | |
979 call assert_false(v:false != 0) | |
980 call assert_true(v:true == 1) | |
981 call assert_false(v:true != 1) | |
982 call assert_false(v:true == v:false) | |
983 call assert_true(v:true != v:false) | |
984 | |
985 call assert_true(v:null == 0) | |
986 call assert_false(v:null != 0) | |
987 call assert_true(v:none == 0) | |
988 call assert_false(v:none != 0) | |
989 | |
990 call assert_true(v:false is v:false) | |
991 call assert_true(v:true is v:true) | |
992 call assert_true(v:none is v:none) | |
993 call assert_true(v:null is v:null) | |
994 | |
995 call assert_false(v:false isnot v:false) | |
996 call assert_false(v:true isnot v:true) | |
997 call assert_false(v:none isnot v:none) | |
998 call assert_false(v:null isnot v:null) | |
999 | |
1000 call assert_false(v:false is 0) | |
1001 call assert_false(v:true is 1) | |
1002 call assert_false(v:true is v:false) | |
1003 call assert_false(v:none is 0) | |
1004 call assert_false(v:null is 0) | |
1005 call assert_false(v:null is v:none) | |
1006 | |
1007 call assert_true(v:false isnot 0) | |
1008 call assert_true(v:true isnot 1) | |
1009 call assert_true(v:true isnot v:false) | |
1010 call assert_true(v:none isnot 0) | |
1011 call assert_true(v:null isnot 0) | |
1012 call assert_true(v:null isnot v:none) | |
1013 | |
1014 call assert_equal(v:false, eval(string(v:false))) | |
1015 call assert_equal(v:true, eval(string(v:true))) | |
1016 call assert_equal(v:none, eval(string(v:none))) | |
1017 call assert_equal(v:null, eval(string(v:null))) | |
1018 | |
1019 call assert_equal(v:false, copy(v:false)) | |
1020 call assert_equal(v:true, copy(v:true)) | |
1021 call assert_equal(v:none, copy(v:none)) | |
1022 call assert_equal(v:null, copy(v:null)) | |
1023 | |
1024 call assert_equal([v:false], deepcopy([v:false])) | |
1025 call assert_equal([v:true], deepcopy([v:true])) | |
1026 call assert_equal([v:none], deepcopy([v:none])) | |
1027 call assert_equal([v:null], deepcopy([v:null])) | |
1028 | |
1029 call assert_true(empty(v:false)) | |
1030 call assert_false(empty(v:true)) | |
1031 call assert_true(empty(v:null)) | |
1032 call assert_true(empty(v:none)) | |
1033 | |
1034 func ChangeYourMind() | |
1035 try | |
1036 return v:true | |
1037 finally | |
1038 return 'something else' | |
1039 endtry | |
1040 endfunc | |
1041 | |
1042 call ChangeYourMind() | |
1043 endfunc | |
1044 | |
1045 "------------------------------------------------------------------------------- | |
1046 " Test 92: skipping code {{{1 | |
1047 "------------------------------------------------------------------------------- | |
1048 | |
1049 func Test_skip() | |
1050 let Fn = function('Test_type') | |
1051 call assert_false(0 && Fn[1]) | |
1052 call assert_false(0 && string(Fn)) | |
1053 call assert_false(0 && len(Fn)) | |
1054 let l = [] | |
1055 call assert_false(0 && l[1]) | |
1056 call assert_false(0 && string(l)) | |
1057 call assert_false(0 && len(l)) | |
1058 let f = 1.0 | |
1059 call assert_false(0 && f[1]) | |
1060 call assert_false(0 && string(f)) | |
1061 call assert_false(0 && len(f)) | |
1062 let sp = v:null | |
1063 call assert_false(0 && sp[1]) | |
1064 call assert_false(0 && string(sp)) | |
1065 call assert_false(0 && len(sp)) | |
1066 | |
1067 endfunc | |
1068 | |
1069 "------------------------------------------------------------------------------- | |
1070 " Test 93: :echo and string() {{{1 | |
1071 "------------------------------------------------------------------------------- | |
1072 | |
1073 func Test_echo_and_string() | |
1074 " String | |
1075 let a = 'foo bar' | |
1076 redir => result | |
1077 echo a | |
1078 echo string(a) | |
1079 redir END | |
1080 let l = split(result, "\n") | |
1081 call assert_equal(["foo bar", | |
1082 \ "'foo bar'"], l) | |
1083 | |
1084 " Float | |
1085 if has('float') | |
1086 let a = -1.2e0 | |
1087 redir => result | |
1088 echo a | |
1089 echo string(a) | |
1090 redir END | |
1091 let l = split(result, "\n") | |
1092 call assert_equal(["-1.2", | |
1093 \ "-1.2"], l) | |
1094 endif | |
1095 | |
1096 " Funcref | |
1097 redir => result | |
1098 echo function('string') | |
1099 echo string(function('string')) | |
1100 redir END | |
1101 let l = split(result, "\n") | |
1102 call assert_equal(["string", | |
1103 \ "function('string')"], l) | |
1104 | |
1105 " Recursive dictionary | |
1106 let a = {} | |
1107 let a["a"] = a | |
1108 redir => result | |
1109 echo a | |
1110 echo string(a) | |
1111 redir END | |
1112 let l = split(result, "\n") | |
1113 call assert_equal(["{'a': {...}}", | |
1114 \ "{'a': {...}}"], l) | |
1115 | |
1116 " Recursive list | |
1117 let a = [0] | |
1118 let a[0] = a | |
1119 redir => result | |
1120 echo a | |
1121 echo string(a) | |
1122 redir END | |
1123 let l = split(result, "\n") | |
1124 call assert_equal(["[[...]]", | |
1125 \ "[[...]]"], l) | |
1126 | |
1127 " Empty dictionaries in a list | |
1128 let a = {} | |
1129 redir => result | |
1130 echo [a, a, a] | |
1131 echo string([a, a, a]) | |
1132 redir END | |
1133 let l = split(result, "\n") | |
1134 call assert_equal(["[{}, {}, {}]", | |
1135 \ "[{}, {}, {}]"], l) | |
1136 | |
1137 " Empty dictionaries in a dictionary | |
1138 let a = {} | |
1139 let b = {"a": a, "b": a} | |
1140 redir => result | |
1141 echo b | |
1142 echo string(b) | |
1143 redir END | |
1144 let l = split(result, "\n") | |
1145 call assert_equal(["{'a': {}, 'b': {}}", | |
1146 \ "{'a': {}, 'b': {}}"], l) | |
1147 | |
1148 " Empty lists in a list | |
1149 let a = [] | |
1150 redir => result | |
1151 echo [a, a, a] | |
1152 echo string([a, a, a]) | |
1153 redir END | |
1154 let l = split(result, "\n") | |
1155 call assert_equal(["[[], [], []]", | |
1156 \ "[[], [], []]"], l) | |
1157 | |
1158 " Empty lists in a dictionary | |
1159 let a = [] | |
1160 let b = {"a": a, "b": a} | |
1161 redir => result | |
1162 echo b | |
1163 echo string(b) | |
1164 redir END | |
1165 let l = split(result, "\n") | |
1166 call assert_equal(["{'a': [], 'b': []}", | |
1167 \ "{'a': [], 'b': []}"], l) | |
1168 | |
1169 " Dictionaries in a list | |
1170 let a = {"one": "yes", "two": "yes", "three": "yes"} | |
1171 redir => result | |
1172 echo [a, a, a] | |
1173 echo string([a, a, a]) | |
1174 redir END | |
1175 let l = split(result, "\n") | |
1176 call assert_equal(["[{'one': 'yes', 'two': 'yes', 'three': 'yes'}, {...}, {...}]", | |
1177 \ "[{'one': 'yes', 'two': 'yes', 'three': 'yes'}, {'one': 'yes', 'two': 'yes', 'three': 'yes'}, {'one': 'yes', 'two': 'yes', 'three': 'yes'}]"], l) | |
1178 | |
1179 " Dictionaries in a dictionary | |
1180 let a = {"one": "yes", "two": "yes", "three": "yes"} | |
1181 let b = {"a": a, "b": a} | |
1182 redir => result | |
1183 echo b | |
1184 echo string(b) | |
1185 redir END | |
1186 let l = split(result, "\n") | |
1187 call assert_equal(["{'a': {'one': 'yes', 'two': 'yes', 'three': 'yes'}, 'b': {...}}", | |
1188 \ "{'a': {'one': 'yes', 'two': 'yes', 'three': 'yes'}, 'b': {'one': 'yes', 'two': 'yes', 'three': 'yes'}}"], l) | |
1189 | |
1190 " Lists in a list | |
1191 let a = [1, 2, 3] | |
1192 redir => result | |
1193 echo [a, a, a] | |
1194 echo string([a, a, a]) | |
1195 redir END | |
1196 let l = split(result, "\n") | |
1197 call assert_equal(["[[1, 2, 3], [...], [...]]", | |
1198 \ "[[1, 2, 3], [1, 2, 3], [1, 2, 3]]"], l) | |
1199 | |
1200 " Lists in a dictionary | |
1201 let a = [1, 2, 3] | |
1202 let b = {"a": a, "b": a} | |
1203 redir => result | |
1204 echo b | |
1205 echo string(b) | |
1206 redir END | |
1207 let l = split(result, "\n") | |
1208 call assert_equal(["{'a': [1, 2, 3], 'b': [...]}", | |
1209 \ "{'a': [1, 2, 3], 'b': [1, 2, 3]}"], l) | |
1210 | |
1211 endfunc | |
1212 | |
1213 "------------------------------------------------------------------------------- | |
1214 " Test 94: 64-bit Numbers {{{1 | |
1215 "------------------------------------------------------------------------------- | |
1216 | |
1217 func Test_num64() | |
1218 if !has('num64') | |
1219 return | |
1220 endif | |
1221 | |
1222 call assert_notequal( 4294967296, 0) | |
1223 call assert_notequal(-4294967296, 0) | |
1224 call assert_equal( 4294967296, 0xFFFFffff + 1) | |
1225 call assert_equal(-4294967296, -0xFFFFffff - 1) | |
1226 | |
1227 call assert_equal( 9223372036854775807, 1 / 0) | |
1228 call assert_equal(-9223372036854775807, -1 / 0) | |
1229 call assert_equal(-9223372036854775807 - 1, 0 / 0) | |
1230 | |
1231 call assert_equal( 0x7FFFffffFFFFffff, float2nr( 1.0e150)) | |
1232 call assert_equal(-0x7FFFffffFFFFffff, float2nr(-1.0e150)) | |
1233 | |
1234 let rng = range(0xFFFFffff, 0x100000001) | |
1235 call assert_equal([0xFFFFffff, 0x100000000, 0x100000001], rng) | |
1236 call assert_equal(0x100000001, max(rng)) | |
1237 call assert_equal(0xFFFFffff, min(rng)) | |
1238 call assert_equal(rng, sort(range(0x100000001, 0xFFFFffff, -1), 'N')) | |
1239 endfunc | |
1240 | |
1241 "------------------------------------------------------------------------------- | |
1242 " Test 95: lines of :append, :change, :insert {{{1 | |
1243 "------------------------------------------------------------------------------- | |
1244 | |
1245 function! DefineFunction(name, body) | |
1246 let func = join(['function! ' . a:name . '()'] + a:body + ['endfunction'], "\n") | |
1247 exec func | |
1248 endfunction | |
1249 | |
1250 func Test_script_lines() | |
1251 " :append | |
1252 try | |
1253 call DefineFunction('T_Append', [ | |
1254 \ 'append', | |
1255 \ 'py <<EOS', | |
1256 \ '.', | |
1257 \ ]) | |
1258 catch | |
1259 call assert_false(1, "Can't define function") | |
1260 endtry | |
1261 try | |
1262 call DefineFunction('T_Append', [ | |
1263 \ 'append', | |
1264 \ 'abc', | |
1265 \ ]) | |
1266 call assert_false(1, "Shouldn't be able to define function") | |
1267 catch | |
1268 call assert_exception('Vim(function):E126: Missing :endfunction') | |
1269 endtry | |
1270 | |
1271 " :change | |
1272 try | |
1273 call DefineFunction('T_Change', [ | |
1274 \ 'change', | |
1275 \ 'py <<EOS', | |
1276 \ '.', | |
1277 \ ]) | |
1278 catch | |
1279 call assert_false(1, "Can't define function") | |
1280 endtry | |
1281 try | |
1282 call DefineFunction('T_Change', [ | |
1283 \ 'change', | |
1284 \ 'abc', | |
1285 \ ]) | |
1286 call assert_false(1, "Shouldn't be able to define function") | |
1287 catch | |
1288 call assert_exception('Vim(function):E126: Missing :endfunction') | |
1289 endtry | |
1290 | |
1291 " :insert | |
1292 try | |
1293 call DefineFunction('T_Insert', [ | |
1294 \ 'insert', | |
1295 \ 'py <<EOS', | |
1296 \ '.', | |
1297 \ ]) | |
1298 catch | |
1299 call assert_false(1, "Can't define function") | |
1300 endtry | |
1301 try | |
1302 call DefineFunction('T_Insert', [ | |
1303 \ 'insert', | |
1304 \ 'abc', | |
1305 \ ]) | |
1306 call assert_false(1, "Shouldn't be able to define function") | |
1307 catch | |
1308 call assert_exception('Vim(function):E126: Missing :endfunction') | |
1309 endtry | |
1310 endfunc | |
1311 | |
1312 "------------------------------------------------------------------------------- | |
1313 " Modelines {{{1 | |
1314 " vim: ts=8 sw=4 tw=80 fdm=marker | |
1315 " vim: fdt=substitute(substitute(foldtext(),\ '\\%(^+--\\)\\@<=\\(\\s*\\)\\(.\\{-}\\)\:\ \\%(\"\ \\)\\=\\(Test\ \\d*\\)\:\\s*',\ '\\3\ (\\2)\:\ \\1',\ \"\"),\ '\\(Test\\s*\\)\\(\\d\\)\\D\\@=',\ '\\1\ \\2',\ "") | |
1316 "------------------------------------------------------------------------------- |