mirror of
https://github.com/neovim/neovim.git
synced 2025-10-08 10:56:31 +00:00
vim-patch:8.1.0014: qf_init_ext() is too long
Problem: qf_init_ext() is too long.
Solution: Split it into multiple functions. (Yegappan Lakshmanan,
closes vim/vim#2939)
6053f2d29a
This commit is contained in:
@@ -1929,6 +1929,7 @@ int ml_append_buf(
|
|||||||
colnr_T len, // length of new line, including NUL, or 0
|
colnr_T len, // length of new line, including NUL, or 0
|
||||||
bool newfile // flag, see above
|
bool newfile // flag, see above
|
||||||
)
|
)
|
||||||
|
FUNC_ATTR_NONNULL_ARG(1)
|
||||||
{
|
{
|
||||||
if (buf->b_ml.ml_mfp == NULL)
|
if (buf->b_ml.ml_mfp == NULL)
|
||||||
return FAIL;
|
return FAIL;
|
||||||
|
@@ -229,8 +229,9 @@ static char *e_loc_list_changed = N_("E926: Current location list was changed");
|
|||||||
/// @params enc If non-NULL, encoding used to parse errors
|
/// @params enc If non-NULL, encoding used to parse errors
|
||||||
///
|
///
|
||||||
/// @returns -1 for error, number of errors for success.
|
/// @returns -1 for error, number of errors for success.
|
||||||
int qf_init(win_T *wp, char_u *efile, char_u *errorformat, int newlist,
|
int qf_init(win_T *wp, const char_u *restrict efile,
|
||||||
char_u *qf_title, char_u *enc)
|
char_u *restrict errorformat, int newlist,
|
||||||
|
const char_u *restrict qf_title, char_u *restrict enc)
|
||||||
{
|
{
|
||||||
qf_info_T *qi = &ql_info;
|
qf_info_T *qi = &ql_info;
|
||||||
|
|
||||||
@@ -880,6 +881,79 @@ restofline:
|
|||||||
return QF_OK;
|
return QF_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Allocate the fields used for parsing lines and populating a quickfix list.
|
||||||
|
static void qf_alloc_fields(qffields_T *pfields)
|
||||||
|
FUNC_ATTR_NONNULL_ALL
|
||||||
|
{
|
||||||
|
pfields->namebuf = xmalloc(CMDBUFFSIZE + 1);
|
||||||
|
pfields->module = xmalloc(CMDBUFFSIZE + 1);
|
||||||
|
pfields->errmsglen = CMDBUFFSIZE + 1;
|
||||||
|
pfields->errmsg = xmalloc(pfields->errmsglen);
|
||||||
|
pfields->pattern = xmalloc(CMDBUFFSIZE + 1);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Free the fields used for parsing lines and populating a quickfix list.
|
||||||
|
static void qf_free_fields(qffields_T *pfields)
|
||||||
|
FUNC_ATTR_NONNULL_ALL
|
||||||
|
{
|
||||||
|
xfree(pfields->namebuf);
|
||||||
|
xfree(pfields->module);
|
||||||
|
xfree(pfields->errmsg);
|
||||||
|
xfree(pfields->pattern);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Setup the state information used for parsing lines and populating a
|
||||||
|
// quickfix list.
|
||||||
|
static int qf_setup_state(
|
||||||
|
qfstate_T *pstate,
|
||||||
|
char_u *restrict enc,
|
||||||
|
const char_u *restrict efile,
|
||||||
|
typval_T *tv,
|
||||||
|
buf_T *buf,
|
||||||
|
linenr_T lnumfirst,
|
||||||
|
linenr_T lnumlast)
|
||||||
|
FUNC_ATTR_NONNULL_ARG(1)
|
||||||
|
{
|
||||||
|
pstate->vc.vc_type = CONV_NONE;
|
||||||
|
if (enc != NULL && *enc != NUL) {
|
||||||
|
convert_setup(&pstate->vc, enc, p_enc);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (efile != NULL
|
||||||
|
&& (pstate->fd = os_fopen((const char *)efile, "r")) == NULL) {
|
||||||
|
EMSG2(_(e_openerrf), efile);
|
||||||
|
return FAIL;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (tv != NULL) {
|
||||||
|
if (tv->v_type == VAR_STRING) {
|
||||||
|
pstate->p_str = tv->vval.v_string;
|
||||||
|
} else if (tv->v_type == VAR_LIST) {
|
||||||
|
pstate->p_li = tv_list_first(tv->vval.v_list);
|
||||||
|
}
|
||||||
|
pstate->tv = tv;
|
||||||
|
}
|
||||||
|
pstate->buf = buf;
|
||||||
|
pstate->buflnum = lnumfirst;
|
||||||
|
pstate->lnumlast = lnumlast;
|
||||||
|
|
||||||
|
return OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Cleanup the state information used for parsing lines and populating a
|
||||||
|
// quickfix list.
|
||||||
|
static void qf_cleanup_state(qfstate_T *pstate)
|
||||||
|
FUNC_ATTR_NONNULL_ALL
|
||||||
|
{
|
||||||
|
if (pstate->fd != NULL) {
|
||||||
|
fclose(pstate->fd);
|
||||||
|
}
|
||||||
|
xfree(pstate->growbuf);
|
||||||
|
if (pstate->vc.vc_type != CONV_NONE) {
|
||||||
|
convert_setup(&pstate->vc, NULL, NULL);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// Read the errorfile "efile" into memory, line by line, building the error
|
// Read the errorfile "efile" into memory, line by line, building the error
|
||||||
// list.
|
// list.
|
||||||
// Alternative: when "efile" is NULL read errors from buffer "buf".
|
// Alternative: when "efile" is NULL read errors from buffer "buf".
|
||||||
@@ -892,19 +966,20 @@ static int
|
|||||||
qf_init_ext(
|
qf_init_ext(
|
||||||
qf_info_T *qi,
|
qf_info_T *qi,
|
||||||
int qf_idx,
|
int qf_idx,
|
||||||
char_u *efile,
|
const char_u *restrict efile,
|
||||||
buf_T *buf,
|
buf_T *buf,
|
||||||
typval_T *tv,
|
typval_T *tv,
|
||||||
char_u *errorformat,
|
char_u *restrict errorformat,
|
||||||
int newlist, // TRUE: start a new error list
|
bool newlist, // true: start a new error list
|
||||||
linenr_T lnumfirst, // first line number to use
|
linenr_T lnumfirst, // first line number to use
|
||||||
linenr_T lnumlast, // last line number to use
|
linenr_T lnumlast, // last line number to use
|
||||||
char_u *qf_title,
|
const char_u *restrict qf_title,
|
||||||
char_u *enc
|
char_u *restrict enc
|
||||||
)
|
)
|
||||||
|
FUNC_ATTR_NONNULL_ARG(1)
|
||||||
{
|
{
|
||||||
qfstate_T state;
|
qfstate_T state = { 0 };
|
||||||
qffields_T fields;
|
qffields_T fields = { 0 };
|
||||||
qfline_T *old_last = NULL;
|
qfline_T *old_last = NULL;
|
||||||
bool adding = false;
|
bool adding = false;
|
||||||
static efm_T *fmt_first = NULL;
|
static efm_T *fmt_first = NULL;
|
||||||
@@ -916,21 +991,9 @@ qf_init_ext(
|
|||||||
// Do not used the cached buffer, it may have been wiped out.
|
// Do not used the cached buffer, it may have been wiped out.
|
||||||
XFREE_CLEAR(qf_last_bufname);
|
XFREE_CLEAR(qf_last_bufname);
|
||||||
|
|
||||||
memset(&state, 0, sizeof(state));
|
qf_alloc_fields(&fields);
|
||||||
memset(&fields, 0, sizeof(fields));
|
if (qf_setup_state(&state, enc, efile, tv, buf,
|
||||||
state.vc.vc_type = CONV_NONE;
|
lnumfirst, lnumlast) == FAIL) {
|
||||||
if (enc != NULL && *enc != NUL) {
|
|
||||||
convert_setup(&state.vc, enc, p_enc);
|
|
||||||
}
|
|
||||||
|
|
||||||
fields.namebuf = xmalloc(CMDBUFFSIZE + 1);
|
|
||||||
fields.module = xmalloc(CMDBUFFSIZE + 1);
|
|
||||||
fields.errmsglen = CMDBUFFSIZE + 1;
|
|
||||||
fields.errmsg = xmalloc(fields.errmsglen);
|
|
||||||
fields.pattern = xmalloc(CMDBUFFSIZE + 1);
|
|
||||||
|
|
||||||
if (efile != NULL && (state.fd = os_fopen((char *)efile, "r")) == NULL) {
|
|
||||||
EMSG2(_(e_openerrf), efile);
|
|
||||||
goto qf_init_end;
|
goto qf_init_end;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -979,19 +1042,6 @@ qf_init_ext(
|
|||||||
*/
|
*/
|
||||||
got_int = FALSE;
|
got_int = FALSE;
|
||||||
|
|
||||||
if (tv != NULL) {
|
|
||||||
if (tv->v_type == VAR_STRING) {
|
|
||||||
state.p_str = tv->vval.v_string;
|
|
||||||
} else if (tv->v_type == VAR_LIST) {
|
|
||||||
state.p_list = tv->vval.v_list;
|
|
||||||
state.p_li = tv_list_first(tv->vval.v_list);
|
|
||||||
}
|
|
||||||
state.tv = tv;
|
|
||||||
}
|
|
||||||
state.buf = buf;
|
|
||||||
state.buflnum = lnumfirst;
|
|
||||||
state.lnumlast = lnumlast;
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Read the lines in the error file one by one.
|
* Read the lines in the error file one by one.
|
||||||
* Try to recognize one of the error formats in each line.
|
* Try to recognize one of the error formats in each line.
|
||||||
@@ -1059,22 +1109,11 @@ error2:
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
qf_init_end:
|
qf_init_end:
|
||||||
if (state.fd != NULL) {
|
|
||||||
fclose(state.fd);
|
|
||||||
}
|
|
||||||
xfree(fields.namebuf);
|
|
||||||
xfree(fields.module);
|
|
||||||
xfree(fields.errmsg);
|
|
||||||
xfree(fields.pattern);
|
|
||||||
xfree(state.growbuf);
|
|
||||||
|
|
||||||
if (qf_idx == qi->qf_curlist) {
|
if (qf_idx == qi->qf_curlist) {
|
||||||
qf_update_buffer(qi, old_last);
|
qf_update_buffer(qi, old_last);
|
||||||
}
|
}
|
||||||
|
qf_cleanup_state(&state);
|
||||||
if (state.vc.vc_type != CONV_NONE) {
|
qf_free_fields(&fields);
|
||||||
convert_setup(&state.vc, NULL, NULL);
|
|
||||||
}
|
|
||||||
|
|
||||||
return retval;
|
return retval;
|
||||||
}
|
}
|
||||||
@@ -1111,7 +1150,7 @@ static char_u * qf_cmdtitle(char_u *cmd)
|
|||||||
// Prepare for adding a new quickfix list. If the current list is in the
|
// Prepare for adding a new quickfix list. If the current list is in the
|
||||||
// middle of the stack, then all the following lists are freed and then
|
// middle of the stack, then all the following lists are freed and then
|
||||||
// the new list is added.
|
// the new list is added.
|
||||||
static void qf_new_list(qf_info_T *qi, char_u *qf_title)
|
static void qf_new_list(qf_info_T *qi, const char_u *qf_title)
|
||||||
{
|
{
|
||||||
int i;
|
int i;
|
||||||
|
|
||||||
@@ -2760,10 +2799,12 @@ next_entry:
|
|||||||
* Remove newlines and leading whitespace from an error message.
|
* Remove newlines and leading whitespace from an error message.
|
||||||
* Put the result in "buf[bufsize]".
|
* Put the result in "buf[bufsize]".
|
||||||
*/
|
*/
|
||||||
static void qf_fmt_text(char_u *text, char_u *buf, int bufsize)
|
static void qf_fmt_text(const char_u *restrict text, char_u *restrict buf,
|
||||||
|
int bufsize)
|
||||||
|
FUNC_ATTR_NONNULL_ALL
|
||||||
{
|
{
|
||||||
int i;
|
int i;
|
||||||
char_u *p = text;
|
const char_u *p = text;
|
||||||
|
|
||||||
for (i = 0; *p != NUL && i < bufsize - 1; ++i) {
|
for (i = 0; *p != NUL && i < bufsize - 1; ++i) {
|
||||||
if (*p == '\n') {
|
if (*p == '\n') {
|
||||||
@@ -3415,17 +3456,82 @@ static void qf_set_title_var(qf_info_T *qi)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Add an error line to the quickfix buffer.
|
||||||
|
static int qf_buf_add_line(buf_T *buf, linenr_T lnum, const qfline_T *qfp,
|
||||||
|
char_u *dirname)
|
||||||
|
FUNC_ATTR_NONNULL_ALL
|
||||||
|
{
|
||||||
|
int len;
|
||||||
|
buf_T *errbuf;
|
||||||
|
|
||||||
|
if (qfp->qf_module != NULL) {
|
||||||
|
STRCPY(IObuff, qfp->qf_module);
|
||||||
|
len = (int)STRLEN(IObuff);
|
||||||
|
} else if (qfp->qf_fnum != 0
|
||||||
|
&& (errbuf = buflist_findnr(qfp->qf_fnum)) != NULL
|
||||||
|
&& errbuf->b_fname != NULL) {
|
||||||
|
if (qfp->qf_type == 1) { // :helpgrep
|
||||||
|
STRLCPY(IObuff, path_tail(errbuf->b_fname), sizeof(IObuff));
|
||||||
|
} else {
|
||||||
|
// shorten the file name if not done already
|
||||||
|
if (errbuf->b_sfname == NULL
|
||||||
|
|| path_is_absolute(errbuf->b_sfname)) {
|
||||||
|
if (*dirname == NUL) {
|
||||||
|
os_dirname(dirname, MAXPATHL);
|
||||||
|
}
|
||||||
|
shorten_buf_fname(errbuf, dirname, false);
|
||||||
|
}
|
||||||
|
STRLCPY(IObuff, errbuf->b_fname, sizeof(IObuff));
|
||||||
|
}
|
||||||
|
len = (int)STRLEN(IObuff);
|
||||||
|
} else {
|
||||||
|
len = 0;
|
||||||
|
}
|
||||||
|
IObuff[len++] = '|';
|
||||||
|
|
||||||
|
if (qfp->qf_lnum > 0) {
|
||||||
|
snprintf((char *)IObuff + len, sizeof(IObuff), "%" PRId64,
|
||||||
|
(int64_t)qfp->qf_lnum);
|
||||||
|
len += (int)STRLEN(IObuff + len);
|
||||||
|
|
||||||
|
if (qfp->qf_col > 0) {
|
||||||
|
snprintf((char *)IObuff + len, sizeof(IObuff), " col %d", qfp->qf_col);
|
||||||
|
len += (int)STRLEN(IObuff + len);
|
||||||
|
}
|
||||||
|
|
||||||
|
snprintf((char *)IObuff + len, sizeof(IObuff), "%s",
|
||||||
|
(char *)qf_types(qfp->qf_type, qfp->qf_nr));
|
||||||
|
len += (int)STRLEN(IObuff + len);
|
||||||
|
} else if (qfp->qf_pattern != NULL) {
|
||||||
|
qf_fmt_text(qfp->qf_pattern, IObuff + len, IOSIZE - len);
|
||||||
|
len += (int)STRLEN(IObuff + len);
|
||||||
|
}
|
||||||
|
IObuff[len++] = '|';
|
||||||
|
IObuff[len++] = ' ';
|
||||||
|
|
||||||
|
// Remove newlines and leading whitespace from the text.
|
||||||
|
// For an unrecognized line keep the indent, the compiler may
|
||||||
|
// mark a word with ^^^^.
|
||||||
|
qf_fmt_text(len > 3 ? skipwhite(qfp->qf_text) : qfp->qf_text,
|
||||||
|
IObuff + len, IOSIZE - len);
|
||||||
|
|
||||||
|
if (ml_append_buf(buf, lnum, IObuff,
|
||||||
|
(colnr_T)STRLEN(IObuff) + 1, false) == FAIL) {
|
||||||
|
return FAIL;
|
||||||
|
}
|
||||||
|
return OK;
|
||||||
|
}
|
||||||
|
|
||||||
// Fill current buffer with quickfix errors, replacing any previous contents.
|
// Fill current buffer with quickfix errors, replacing any previous contents.
|
||||||
// curbuf must be the quickfix buffer!
|
// curbuf must be the quickfix buffer!
|
||||||
// If "old_last" is not NULL append the items after this one.
|
// If "old_last" is not NULL append the items after this one.
|
||||||
// When "old_last" is NULL then "buf" must equal "curbuf"! Because ml_delete()
|
// When "old_last" is NULL then "buf" must equal "curbuf"! Because ml_delete()
|
||||||
// is used and autocommands will be triggered.
|
// is used and autocommands will be triggered.
|
||||||
static void qf_fill_buffer(qf_info_T *qi, buf_T *buf, qfline_T *old_last)
|
static void qf_fill_buffer(qf_info_T *qi, buf_T *buf, qfline_T *old_last)
|
||||||
|
FUNC_ATTR_NONNULL_ARG(1, 2)
|
||||||
{
|
{
|
||||||
linenr_T lnum;
|
linenr_T lnum;
|
||||||
qfline_T *qfp;
|
qfline_T *qfp;
|
||||||
buf_T *errbuf;
|
|
||||||
int len;
|
|
||||||
const bool old_KeyTyped = KeyTyped;
|
const bool old_KeyTyped = KeyTyped;
|
||||||
|
|
||||||
if (old_last == NULL) {
|
if (old_last == NULL) {
|
||||||
@@ -3455,58 +3561,7 @@ static void qf_fill_buffer(qf_info_T *qi, buf_T *buf, qfline_T *old_last)
|
|||||||
lnum = buf->b_ml.ml_line_count;
|
lnum = buf->b_ml.ml_line_count;
|
||||||
}
|
}
|
||||||
while (lnum < qi->qf_lists[qi->qf_curlist].qf_count) {
|
while (lnum < qi->qf_lists[qi->qf_curlist].qf_count) {
|
||||||
if (qfp->qf_module != NULL) {
|
if (qf_buf_add_line(buf, lnum, qfp, dirname) == FAIL) {
|
||||||
STRCPY(IObuff, qfp->qf_module);
|
|
||||||
len = (int)STRLEN(IObuff);
|
|
||||||
} else if (qfp->qf_fnum != 0
|
|
||||||
&& (errbuf = buflist_findnr(qfp->qf_fnum)) != NULL
|
|
||||||
&& errbuf->b_fname != NULL) {
|
|
||||||
if (qfp->qf_type == 1) { // :helpgrep
|
|
||||||
STRLCPY(IObuff, path_tail(errbuf->b_fname), sizeof(IObuff));
|
|
||||||
} else {
|
|
||||||
// shorten the file name if not done already
|
|
||||||
if (errbuf->b_sfname == NULL
|
|
||||||
|| path_is_absolute(errbuf->b_sfname)) {
|
|
||||||
if (*dirname == NUL) {
|
|
||||||
os_dirname(dirname, MAXPATHL);
|
|
||||||
}
|
|
||||||
shorten_buf_fname(errbuf, dirname, false);
|
|
||||||
}
|
|
||||||
STRLCPY(IObuff, errbuf->b_fname, sizeof(IObuff));
|
|
||||||
}
|
|
||||||
len = (int)STRLEN(IObuff);
|
|
||||||
} else {
|
|
||||||
len = 0;
|
|
||||||
}
|
|
||||||
IObuff[len++] = '|';
|
|
||||||
|
|
||||||
if (qfp->qf_lnum > 0) {
|
|
||||||
sprintf((char *)IObuff + len, "%" PRId64, (int64_t)qfp->qf_lnum);
|
|
||||||
len += (int)STRLEN(IObuff + len);
|
|
||||||
|
|
||||||
if (qfp->qf_col > 0) {
|
|
||||||
sprintf((char *)IObuff + len, " col %d", qfp->qf_col);
|
|
||||||
len += (int)STRLEN(IObuff + len);
|
|
||||||
}
|
|
||||||
|
|
||||||
sprintf((char *)IObuff + len, "%s",
|
|
||||||
(char *)qf_types(qfp->qf_type, qfp->qf_nr));
|
|
||||||
len += (int)STRLEN(IObuff + len);
|
|
||||||
} else if (qfp->qf_pattern != NULL) {
|
|
||||||
qf_fmt_text(qfp->qf_pattern, IObuff + len, IOSIZE - len);
|
|
||||||
len += (int)STRLEN(IObuff + len);
|
|
||||||
}
|
|
||||||
IObuff[len++] = '|';
|
|
||||||
IObuff[len++] = ' ';
|
|
||||||
|
|
||||||
/* Remove newlines and leading whitespace from the text.
|
|
||||||
* For an unrecognized line keep the indent, the compiler may
|
|
||||||
* mark a word with ^^^^. */
|
|
||||||
qf_fmt_text(len > 3 ? skipwhite(qfp->qf_text) : qfp->qf_text,
|
|
||||||
IObuff + len, IOSIZE - len);
|
|
||||||
|
|
||||||
if (ml_append_buf(buf, lnum, IObuff, (colnr_T)STRLEN(IObuff) + 1, false)
|
|
||||||
== FAIL) {
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
lnum++;
|
lnum++;
|
||||||
|
Reference in New Issue
Block a user