On Sa, 26 Mai 2012, Christian Brabandt wrote:
> On Fr, 25 Mai 2012, Alex Efros wrote:
> > Thanks! But, sorry, I just found another simple way to crash 7.3.530
> > without tabs:
> >
> > $ vi -u /dev/null --noplugin
> > :autocmd BufWinLeave * if empty(getbufvar(0+expand('<abuf>'), '&bt')) |
> > lclose | endif
> > :lexpr system('echo :1:some')
> > :lopen
> > :wincmd p
> > :bd
> > Vim: Caught deadly signal SEGV
> > Segmentation fault
>
> I'll look into it.
Here is another patch. I made win_close() return a status, whether it
failed or not.
But although win_close() is called in many places, I made it only in 1
place at do_buffer() evaluate the return value of win_close(), to not
introduce too many other changes.
regards,
Christian
--
--
You received this message from the "vim_dev" maillist.
Do not top-post! Type your reply below the text you are replying to.
For more information, visit http://www.vim.org/maillist.php
diff --git a/src/buffer.c b/src/buffer.c
--- a/src/buffer.c
+++ b/src/buffer.c
@@ -1151,7 +1151,10 @@
*/
while (buf == curbuf
&& (firstwin != lastwin || first_tabpage->tp_next != NULL))
- win_close(curwin, FALSE);
+ {
+ if (win_close(curwin, FALSE) == FAIL);
+ return FAIL;
+ }
#endif
/*
diff --git a/src/proto/window.pro b/src/proto/window.pro
--- a/src/proto/window.pro
+++ b/src/proto/window.pro
@@ -9,7 +9,7 @@
void win_equal __ARGS((win_T *next_curwin, int current, int dir));
void close_windows __ARGS((buf_T *buf, int keep_curwin));
int one_window __ARGS((void));
-void win_close __ARGS((win_T *win, int free_buf));
+int win_close __ARGS((win_T *win, int free_buf));
void win_close_othertab __ARGS((win_T *win, int free_buf, tabpage_T *tp));
void win_free_all __ARGS((void));
win_T *winframe_remove __ARGS((win_T *win, int *dirp, tabpage_T *tp));
diff --git a/src/window.c b/src/window.c
--- a/src/window.c
+++ b/src/window.c
@@ -2147,7 +2147,7 @@
*
* Called by :quit, :close, :xit, :wq and findtag().
*/
- void
+ int
win_close(win, free_buf)
win_T *win;
int free_buf;
@@ -2164,19 +2164,19 @@
if (last_window())
{
EMSG(_("E444: Cannot close last window"));
- return;
+ return FAIL;
}
#ifdef FEAT_AUTOCMD
if (win == aucmd_win)
{
EMSG(_("E813: Cannot close autocmd window"));
- return;
+ return FAIL;
}
if ((firstwin == aucmd_win || lastwin == aucmd_win) && one_window())
{
EMSG(_("E814: Cannot close window, only autocmd window would remain"));
- return;
+ return FAIL;
}
#endif
@@ -2184,7 +2184,7 @@
* and then close the window and the tab page to avoid that curwin and
* curtab are invalid while we are freeing memory. */
if (close_last_window_tabpage(win, free_buf, prev_curtab))
- return;
+ return OK;
/* When closing the help window, try restoring a snapshot after closing
* the window. Otherwise clear the snapshot, it's now invalid. */
@@ -2210,15 +2210,15 @@
other_buffer = TRUE;
apply_autocmds(EVENT_BUFLEAVE, NULL, NULL, FALSE, curbuf);
if (!win_valid(win) || last_window())
- return;
+ return FAIL;
}
apply_autocmds(EVENT_WINLEAVE, NULL, NULL, FALSE, curbuf);
if (!win_valid(win) || last_window())
- return;
+ return FAIL;
# ifdef FEAT_EVAL
/* autocmds may abort script processing */
if (aborting())
- return;
+ return FAIL;
# endif
}
#endif
@@ -2246,7 +2246,7 @@
* other window or moved to another tab page. */
if (!win_valid(win) || last_window() || curtab != prev_curtab
|| close_last_window_tabpage(win, free_buf, prev_curtab))
- return;
+ return FAIL;
/* Free the memory used for the window and get the window that received
* the screen space. */
@@ -2326,6 +2326,7 @@
#endif
redraw_all_later(NOT_VALID);
+ return OK;
}
/*