diff options
Diffstat (limited to '')
-rw-r--r-- | src/quickfix.c | 79 |
1 files changed, 71 insertions, 8 deletions
diff --git a/src/quickfix.c b/src/quickfix.c index dd681ca..0bf4cfe 100644 --- a/src/quickfix.c +++ b/src/quickfix.c @@ -780,9 +780,9 @@ qf_get_next_buf_line(qfstate_T *state) return QF_END_OF_INPUT; p_buf = ml_get_buf(state->buf, state->buflnum, FALSE); + len = ml_get_buf_len(state->buf, state->buflnum); state->buflnum += 1; - len = (int)STRLEN(p_buf); if (len > IOSIZE - 2) { state->linebuf = qf_grow_linebuf(state, len); @@ -3146,7 +3146,8 @@ qf_goto_win_with_qfl_file(int qf_fnum) // Didn't find it, go to the window before the quickfix // window, unless 'switchbuf' contains 'uselast': in this case we // try to jump to the previously used window first. - if ((swb_flags & SWB_USELAST) && win_valid(prevwin)) + if ((swb_flags & SWB_USELAST) && win_valid(prevwin) && + !prevwin->w_p_wfb) win = prevwin; else if (altwin != NULL) win = altwin; @@ -3158,7 +3159,8 @@ qf_goto_win_with_qfl_file(int qf_fnum) } // Remember a usable window. - if (altwin == NULL && !win->w_p_pvw && bt_normal(win->w_buffer)) + if (altwin == NULL && !win->w_p_pvw && !win->w_p_wfb && + bt_normal(win->w_buffer)) altwin = win; } @@ -3261,8 +3263,51 @@ qf_jump_edit_buffer( prev_winid == curwin->w_id ? curwin : NULL); } else - retval = buflist_getfile(qf_ptr->qf_fnum, - (linenr_T)1, GETF_SETMARK | GETF_SWITCH, forceit); + { + int fnum = qf_ptr->qf_fnum; + + if (!forceit && curwin->w_p_wfb && curbuf->b_fnum != fnum) + { + if (qi->qfl_type == QFLT_LOCATION) + { + // Location lists cannot split or reassign their window + // so 'winfixbuf' windows must fail + emsg(_(e_winfixbuf_cannot_go_to_buffer)); + return FAIL; + } + + if (win_valid(prevwin) && !prevwin->w_p_wfb && + !bt_quickfix(prevwin->w_buffer)) + { + // 'winfixbuf' is set; attempt to change to a window without it + // that isn't a quickfix/location list window. + win_goto(prevwin); + } + if (curwin->w_p_wfb) + { + // Split the window, which will be 'nowinfixbuf', and set curwin + // to that + if (win_split(0, 0) == OK) + *opened_window = TRUE; + + if (curwin->w_p_wfb) + { + // Autocommands set 'winfixbuf' or sent us to another window + // with it set, or we failed to split the window. Give up, + // but don't return immediately, as they may have messed + // with the list. + emsg(_(e_winfixbuf_cannot_go_to_buffer)); + retval = FAIL; + } + } + } + + if (retval == OK) + { + retval = buflist_getfile(fnum, + (linenr_T)1, GETF_SETMARK | GETF_SWITCH, forceit); + } + } // If a location list, check whether the associated window is still // present. @@ -4829,8 +4874,17 @@ qf_fill_buffer(qf_list_T *qfl, buf_T *buf, qfline_T *old_last, int qf_winid) } // delete all existing lines + // + // Note: we cannot store undo information, because + // qf buffer is usually not allowed to be modified. + // + // So we need to clean up undo information + // otherwise autocommands may invalidate the undo stack while ((curbuf->b_ml.ml_flags & ML_EMPTY) == 0) (void)ml_delete((linenr_T)1); + + // Remove all undo information + u_clearallandblockfree(curbuf); } // Check if there is anything to display @@ -4982,6 +5036,11 @@ qf_jump_first(qf_info_T *qi, int_u save_qfid, int forceit) if (qf_restore_list(qi, save_qfid) == FAIL) return; + + if (!check_can_set_curbuf_forceit(forceit)) + return; + + // Autocommands might have cleared the list, check for that. if (!qf_list_empty(qf_get_curlist(qi))) qf_jump(qi, 0, 0, forceit); @@ -5898,7 +5957,7 @@ ex_cfile(exarg_T *eap) // This function is used by the :cfile, :cgetfile and :caddfile // commands. - // :cfile always creates a new quickfix list and jumps to the + // :cfile always creates a new quickfix list and may jump to the // first error. // :cgetfile creates a new quickfix list but doesn't jump to the // first error. @@ -6137,13 +6196,14 @@ vgr_match_buflines( break; col = regmatch->endpos[0].col + (col == regmatch->endpos[0].col); - if (col > (colnr_T)STRLEN(ml_get_buf(buf, lnum, FALSE))) + if (col > ml_get_buf_len(buf, lnum)) break; } } else { char_u *str = ml_get_buf(buf, lnum, FALSE); + colnr_T linelen = ml_get_buf_len(buf, lnum); int score; int_u matches[MAX_FUZZY_MATCHES]; int_u sz = ARRAY_LENGTH(matches); @@ -6182,7 +6242,7 @@ vgr_match_buflines( if ((flags & VGR_GLOBAL) == 0) break; col = matches[pat_len - 1] + col + 1; - if (col > (colnr_T)STRLEN(str)) + if (col > linelen) break; } } @@ -6488,6 +6548,9 @@ ex_vimgrep(exarg_T *eap) char_u *au_name = NULL; int status; + if (!check_can_set_curbuf_forceit(eap->forceit)) + return; + au_name = vgr_get_auname(eap->cmdidx); if (au_name != NULL && apply_autocmds(EVENT_QUICKFIXCMDPRE, au_name, curbuf->b_fname, TRUE, curbuf)) |