changeset 27873:d1af65b322d0 v8.2.4462

patch 8.2.4462: not enough testing for quickfix code Commit: https://github.com/vim/vim/commit/9c9be05b17ececb1515a2f41a4dedbf848d3d8b6 Author: Yegappan Lakshmanan <yegappan@yahoo.com> Date: Thu Feb 24 12:33:17 2022 +0000 patch 8.2.4462: not enough testing for quickfix code Problem: Not enough testing for quickfix code. Solution: Add more tests. Fix uncovered problem. (Yegappan Lakshmanan, closes #9839)
author Bram Moolenaar <Bram@vim.org>
date Thu, 24 Feb 2022 13:45:03 +0100
parents 7f09baac337b
children f4a227222e7a
files src/quickfix.c src/testdir/test_makeencoding.vim src/testdir/test_quickfix.vim src/version.c src/window.c
diffstat 5 files changed, 184 insertions(+), 15 deletions(-) [+]
line wrap: on
line diff
--- a/src/quickfix.c
+++ b/src/quickfix.c
@@ -2086,7 +2086,7 @@ check_quickfix_busy(void)
 
 /*
  * Add an entry to the end of the list of errors.
- * Returns QF_OK or QF_FAIL.
+ * Returns QF_OK on success or QF_FAIL on a memory allocation failure.
  */
     static int
 qf_add_entry(
@@ -4051,9 +4051,6 @@ qf_view_result(int split)
 {
     qf_info_T   *qi = &ql_info;
 
-    if (!bt_quickfix(curbuf))
-	return;
-
     if (IS_LL_WINDOW(curwin))
 	qi = GET_LOC_LIST(curwin);
 
@@ -4525,8 +4522,12 @@ qf_update_buffer(qf_info_T *qi, qfline_T
 		win = curwin;
 	    else
 	    {
+		// Find the file window (non-quickfix) with this location list
 		win = qf_find_win_with_loclist(qi);
 		if (win == NULL)
+		    // File window is not found. Find the location list window.
+		    win = qf_find_win(qi);
+		if (win == NULL)
 		    return;
 	    }
 	    qf_winid = win->w_id;
@@ -8343,7 +8344,9 @@ ex_helpgrep(exarg_T *eap)
 	    if (new_qi)
 		ll_free_all(&qi);
 	}
-	else if (curwin->w_llist == NULL)
+	else if (curwin->w_llist == NULL && new_qi)
+	    // current window didn't have a location list associated with it
+	    // before. Associate the new location list now.
 	    curwin->w_llist = qi;
     }
 }
--- a/src/testdir/test_makeencoding.vim
+++ b/src/testdir/test_makeencoding.vim
@@ -103,4 +103,18 @@ func Test_make()
   endfor
 endfunc
 
+" Test for an error file with a long line that needs an encoding conversion
+func Test_longline_conversion()
+  new
+  call setline(1, ['Xfile:10:' .. repeat("\xe0", 2000)])
+  write ++enc=latin1 Xerr.out
+  bw!
+  set errorformat&
+  set makeencoding=latin1
+  cfile Xerr.out
+  call assert_equal(repeat("\u00e0", 2000), getqflist()[0].text)
+  call delete('Xerr.out')
+  set makeencoding&
+endfunc
+
 " vim: shiftwidth=2 sts=2 expandtab
--- a/src/testdir/test_quickfix.vim
+++ b/src/testdir/test_quickfix.vim
@@ -254,6 +254,7 @@ func XwindowTests(cchar)
   " Opening the location list window without any errors should fail
   if a:cchar == 'l'
       call assert_fails('lopen', 'E776:')
+      call assert_fails('lwindow', 'E776:')
   endif
 
   " Create a list with no valid entries
@@ -739,12 +740,14 @@ def Test_helpgrep_vim9_restore_cpo()
   silent helpgrep grail
 
   assert_equal('aABceFs', &cpo)
-  delete(dir, 'rf')
+  delete('Xruntime', 'rf')
   &rtp = rtp_save
   cclose
   helpclose
 enddef
 
+" When running the :helpgrep command, if an autocmd modifies the 'cpoptions'
+" value, then Vim crashes. (issue fixed by 7.2b-004 and 8.2.4453)
 func Test_helpgrep_restore_cpo_aucmd()
   let save_cpo = &cpo
   augroup QF_Test
@@ -1281,8 +1284,14 @@ func Xinvalid_efm_Tests(cchar)
   set efm=
   call assert_fails('Xexpr "abc.txt:1:Hello world"', 'E378:')
 
+  " Empty directory name. When there is an error in parsing new entries, make
+  " sure the previous quickfix list is made the current list.
+  set efm&
+  cexpr ["one", "two"]
+  let qf_id = getqflist(#{id: 0}).id
   set efm=%DEntering\ dir\ abc,%f:%l:%m
   call assert_fails('Xexpr ["Entering dir abc", "abc.txt:1:Hello world"]', 'E379:')
+  call assert_equal(qf_id, getqflist(#{id: 0}).id)
 
   let &efm = save_efm
 endfunc
@@ -1535,7 +1544,7 @@ func XquickfixChangedByAutocmd(cchar)
     endfunc
   endif
 
-  augroup testgroup
+  augroup QF_Test
     au!
     autocmd BufReadCmd test_changed.txt call ReadFunc()
   augroup END
@@ -1549,7 +1558,24 @@ func XquickfixChangedByAutocmd(cchar)
   endfor
   call assert_fails('Xrewind', ErrorNr . ':')
 
-  augroup! testgroup
+  augroup QF_Test
+    au!
+  augroup END
+
+  if a:cchar == 'c'
+    cexpr ["Xtest1:1:Line"]
+    cwindow
+    only
+    augroup QF_Test
+      au!
+      autocmd WinEnter * call setqflist([], 'f')
+    augroup END
+    call assert_fails('exe "normal \<CR>"', 'E925:')
+    augroup QF_Test
+      au!
+    augroup END
+  endif
+  %bw!
 endfunc
 
 func Test_quickfix_was_changed_by_autocmd()
@@ -1688,6 +1714,8 @@ func SetXlistTests(cchar, bnum)
   call g:Xsetlist([[1, 2,3]])
   call assert_equal(0, len(g:Xgetlist()))
   call assert_fails('call g:Xsetlist([], [])', 'E928:')
+  call g:Xsetlist([test_null_dict()])
+  call assert_equal([], g:Xgetlist())
 endfunc
 
 func Test_setqflist()
@@ -2967,6 +2995,19 @@ func XvimgrepTests(cchar)
   call assert_equal(0, getbufinfo('Xtestfile1')[0].loaded)
   call assert_equal([], getbufinfo('Xtestfile2'))
 
+  " Test for opening the dummy buffer used by vimgrep in a window. The new
+  " window should be closed
+  %bw!
+  augroup QF_Test
+    au!
+    autocmd BufReadPre * exe "sb " .. expand("<abuf>")
+  augroup END
+  call assert_fails("Xvimgrep /sublime/ Xtestfile1", 'E480:')
+  call assert_equal(1, winnr('$'))
+  augroup QF_Test
+    au!
+  augroup END
+
   call delete('Xtestfile1')
   call delete('Xtestfile2')
 endfunc
@@ -4133,14 +4174,19 @@ endfunc
 " The following test used to crash Vim
 func Test_lhelpgrep_autocmd()
   lhelpgrep quickfix
-  autocmd QuickFixCmdPost * call setloclist(0, [], 'f')
+  augroup QF_Test
+    au!
+    autocmd QuickFixCmdPost * call setloclist(0, [], 'f')
+  augroup END
   lhelpgrep buffer
   call assert_equal('help', &filetype)
   call assert_equal(0, getloclist(0, {'nr' : '$'}).nr)
   lhelpgrep tabpage
   call assert_equal('help', &filetype)
   call assert_equal(1, getloclist(0, {'nr' : '$'}).nr)
-  au! QuickFixCmdPost
+  augroup QF_Test
+    au!
+  augroup END
 
   new | only
   augroup QF_Test
@@ -4153,7 +4199,7 @@ func Test_lhelpgrep_autocmd()
   wincmd w
   call assert_fails('helpgrep quickfix', 'E925:')
   augroup QF_Test
-    au! BufEnter
+    au!
   augroup END
 
   new | only
@@ -4163,7 +4209,7 @@ func Test_lhelpgrep_autocmd()
   augroup END
   call assert_fails('helpgrep quickfix', 'E925:')
   augroup QF_Test
-    au! BufEnter
+    au!
   augroup END
 
   new | only
@@ -4173,10 +4219,43 @@ func Test_lhelpgrep_autocmd()
   augroup END
   call assert_fails('lhelpgrep quickfix', 'E926:')
   augroup QF_Test
-    au! BufEnter
+    au!
+  augroup END
+
+  " Replace the contents of a help window location list when it is still in
+  " use.
+  new | only
+  lhelpgrep quickfix
+  wincmd w
+  augroup QF_Test
+    au!
+    autocmd WinEnter * call setloclist(0, [], 'r')
+  augroup END
+  call assert_fails('lhelpgrep win_getid', 'E926:')
+  augroup QF_Test
+    au!
   augroup END
 
-  new | only
+  %bw!
+endfunc
+
+" The following test used to crash Vim
+func Test_lhelpgrep_autocmd_free_loclist()
+  %bw!
+  lhelpgrep quickfix
+  wincmd w
+  augroup QF_Test
+    au!
+    autocmd WinEnter * call setloclist(0, [], 'f')
+  augroup END
+  lhelpgrep win_getid
+  wincmd w
+  wincmd w
+  wincmd w
+  augroup QF_Test
+    au!
+  augroup END
+  %bw!
 endfunc
 
 " Test for shortening/simplifying the file name when opening the
@@ -5160,6 +5239,7 @@ func Xtest_getqflist_by_idx(cchar)
   call assert_equal('L20', l[0].text)
   call assert_equal([], g:Xgetlist({'idx' : -1, 'items' : 0}).items)
   call assert_equal([], g:Xgetlist({'idx' : 3, 'items' : 0}).items)
+  call assert_equal({}, g:Xgetlist(#{idx: "abc"}))
   %bwipe!
 endfunc
 
@@ -5217,6 +5297,19 @@ func Xtest_qftextfunc(cchar)
   call assert_equal('F1|10 col 2-7| green', getline(1))
   call assert_equal('F1|20-25 col 4-8| blue', getline(2))
   Xclose
+
+  set efm=%f:%l:%c:%m
+  set quickfixtextfunc=Tqfexpr
+  " Update the list with only the cwindow
+  Xwindow
+  only
+  call g:Xsetlist([
+        \ { 'filename': 'F2', 'lnum': 20, 'col': 2,
+        \   'end_col': 7, 'text': 'red'}
+        \ ])
+  call assert_equal(['F2-L20C2-red'], getline(1, '$'))
+  new
+  Xclose
   set efm&
   set quickfixtextfunc&
 
@@ -5926,5 +6019,62 @@ func Test_lopen_bwipe_all()
   call delete('Xresult')
 endfunc
 
+" Test for calling setqflist() function recursively
+func Test_recursive_setqflist()
+  augroup QF_Test
+    au!
+    autocmd BufWinEnter quickfix call setqflist([], 'r')
+  augroup END
+
+  copen
+  call assert_fails("call setqflist([], 'a')", 'E952:')
+
+  augroup QF_Test
+    au!
+  augroup END
+  %bw!
+endfunc
+
+" Test for failure to create a new window when selecting a file from the
+" quickfix window
+func Test_cwindow_newwin_fails()
+  cgetexpr ["Xfile1:10:L10", "Xfile1:20:L20"]
+  cwindow
+  only
+  let qf_wid = win_getid()
+  " create the maximum number of scratch windows
+  let hor_win_count = (&lines - 1)/2
+  let hor_split_count = hor_win_count - 1
+  for s in range(1, hor_split_count) | new | set buftype=nofile | endfor
+  call win_gotoid(qf_wid)
+  call assert_fails('exe "normal \<CR>"', 'E36:')
+  %bw!
+endfunc
+
+" Test for updating the location list when only the location list window is
+" present and the corresponding file window is closed.
+func Test_loclist_update_with_llwin_only()
+  %bw!
+  new
+  wincmd w
+  lexpr ["Xfile1:1:Line1"]
+  lopen
+  wincmd p
+  close
+  call setloclist(2, [], 'r', {'lines': ["Xtest2:2:Line2"]})
+  call assert_equal(['Xtest2|2| Line2'], getbufline(winbufnr(2), 1, '$'))
+  %bw!
+endfunc
+
+" Test for getting the quickfix list after a buffer with an error is wiped out
+func Test_getqflist_wiped_out_buffer()
+  %bw!
+  cexpr ["Xtest1:34:Wiped out"]
+  let bnum = bufnr('Xtest1')
+  call assert_equal(bnum, getqflist()[0].bufnr)
+  bw Xtest1
+  call assert_equal(0, getqflist()[0].bufnr)
+  %bw!
+endfunc
 
 " vim: shiftwidth=2 sts=2 expandtab
--- a/src/version.c
+++ b/src/version.c
@@ -755,6 +755,8 @@ static char *(features[]) =
 static int included_patches[] =
 {   /* Add new patch number below this line */
 /**/
+    4462,
+/**/
     4461,
 /**/
     4460,
--- a/src/window.c
+++ b/src/window.c
@@ -4959,7 +4959,7 @@ buf_jump_open_win(buf_T *buf)
 
 /*
  * Jump to the first open window in any tab page that contains buffer "buf",
- * if one exists.
+ * if one exists. First search in the windows present in the current tab page.
  * Returns a pointer to the window found, otherwise NULL.
  */
     win_T *