mirror of
https://github.com/neovim/neovim.git
synced 2025-09-17 00:38:17 +00:00
vim-patch:8.0.1023: it is not easy to identify a quickfix list
Problem: It is not easy to identify a quickfix list.
Solution: Add the "id" field. (Yegappan Lakshmanan)
a539f4f1ae
This commit is contained in:
@@ -4335,6 +4335,9 @@ getqflist([{what}]) *getqflist()*
|
|||||||
returns only the items listed in {what} as a dictionary. The
|
returns only the items listed in {what} as a dictionary. The
|
||||||
following string items are supported in {what}:
|
following string items are supported in {what}:
|
||||||
context get the context stored with |setqflist()|
|
context get the context stored with |setqflist()|
|
||||||
|
id get information for the quickfix list with
|
||||||
|
|quickfix-ID|; zero means the id for the
|
||||||
|
current list or the list specifed by 'nr'
|
||||||
items quickfix list entries
|
items quickfix list entries
|
||||||
nr get information for this quickfix list; zero
|
nr get information for this quickfix list; zero
|
||||||
means the current quickfix list and '$' means
|
means the current quickfix list and '$' means
|
||||||
@@ -4349,6 +4352,8 @@ getqflist([{what}]) *getqflist()*
|
|||||||
all all of the above quickfix properties
|
all all of the above quickfix properties
|
||||||
Non-string items in {what} are ignored.
|
Non-string items in {what} are ignored.
|
||||||
If "nr" is not present then the current quickfix list is used.
|
If "nr" is not present then the current quickfix list is used.
|
||||||
|
If both "nr" and a non-zero "id" are specified, then the list
|
||||||
|
specified by "id" is used.
|
||||||
To get the number of lists in the quickfix stack, set 'nr' to
|
To get the number of lists in the quickfix stack, set 'nr' to
|
||||||
'$' in {what}. The 'nr' value in the returned dictionary
|
'$' in {what}. The 'nr' value in the returned dictionary
|
||||||
contains the quickfix stack size.
|
contains the quickfix stack size.
|
||||||
@@ -4360,6 +4365,7 @@ getqflist([{what}]) *getqflist()*
|
|||||||
|
|
||||||
The returned dictionary contains the following entries:
|
The returned dictionary contains the following entries:
|
||||||
context context information stored with |setqflist()|
|
context context information stored with |setqflist()|
|
||||||
|
id quickfix list ID |quickfix-ID|
|
||||||
items quickfix list entries
|
items quickfix list entries
|
||||||
nr quickfix list number
|
nr quickfix list number
|
||||||
title quickfix list title text
|
title quickfix list title text
|
||||||
@@ -6926,6 +6932,7 @@ setqflist({list} [, {action}[, {what}]]) *setqflist()*
|
|||||||
text and add the resulting entries to the
|
text and add the resulting entries to the
|
||||||
quickfix list {nr}. The value can be a string
|
quickfix list {nr}. The value can be a string
|
||||||
with one line or a list with multiple lines.
|
with one line or a list with multiple lines.
|
||||||
|
id quickfix list identifier |quickfix-ID|
|
||||||
items list of quickfix entries. Same as the {list}
|
items list of quickfix entries. Same as the {list}
|
||||||
argument.
|
argument.
|
||||||
nr list number in the quickfix stack; zero
|
nr list number in the quickfix stack; zero
|
||||||
@@ -6936,6 +6943,9 @@ setqflist({list} [, {action}[, {what}]]) *setqflist()*
|
|||||||
If the "nr" item is not present, then the current quickfix list
|
If the "nr" item is not present, then the current quickfix list
|
||||||
is modified. When creating a new quickfix list, "nr" can be
|
is modified. When creating a new quickfix list, "nr" can be
|
||||||
set to a value one greater than the quickfix stack size.
|
set to a value one greater than the quickfix stack size.
|
||||||
|
When modifying a quickfix list, to guarantee that the correct
|
||||||
|
list is modified, 'id' should be used instead of 'nr' to
|
||||||
|
specify the list.
|
||||||
|
|
||||||
Examples: >
|
Examples: >
|
||||||
:call setqflist([], 'r', {'title': 'My search'})
|
:call setqflist([], 'r', {'title': 'My search'})
|
||||||
|
@@ -82,6 +82,7 @@ struct qfline_S {
|
|||||||
/// created using setqflist()/setloclist() with a title and/or user context
|
/// created using setqflist()/setloclist() with a title and/or user context
|
||||||
/// information and entries can be added later using setqflist()/setloclist().
|
/// information and entries can be added later using setqflist()/setloclist().
|
||||||
typedef struct qf_list_S {
|
typedef struct qf_list_S {
|
||||||
|
unsigned qf_id; ///< Unique identifier for this list
|
||||||
qfline_T *qf_start; ///< pointer to the first error
|
qfline_T *qf_start; ///< pointer to the first error
|
||||||
qfline_T *qf_last; ///< pointer to the last error
|
qfline_T *qf_last; ///< pointer to the last error
|
||||||
qfline_T *qf_ptr; ///< pointer to the current error
|
qfline_T *qf_ptr; ///< pointer to the current error
|
||||||
@@ -117,6 +118,7 @@ struct qf_info_S {
|
|||||||
};
|
};
|
||||||
|
|
||||||
static qf_info_T ql_info; /* global quickfix list */
|
static qf_info_T ql_info; /* global quickfix list */
|
||||||
|
static unsigned last_qf_id = 0; // Last Used quickfix list id
|
||||||
|
|
||||||
#define FMT_PATTERNS 10 /* maximum number of % recognized */
|
#define FMT_PATTERNS 10 /* maximum number of % recognized */
|
||||||
|
|
||||||
@@ -1224,6 +1226,7 @@ static void qf_new_list(qf_info_T *qi, char_u *qf_title)
|
|||||||
qi->qf_curlist = qi->qf_listcount++;
|
qi->qf_curlist = qi->qf_listcount++;
|
||||||
memset(&qi->qf_lists[qi->qf_curlist], 0, (size_t)(sizeof(qf_list_T)));
|
memset(&qi->qf_lists[qi->qf_curlist], 0, (size_t)(sizeof(qf_list_T)));
|
||||||
qf_store_title(qi, qi->qf_curlist, qf_title);
|
qf_store_title(qi, qi->qf_curlist, qf_title);
|
||||||
|
qi->qf_lists[qi->qf_curlist].qf_id = ++last_qf_id;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@@ -1467,6 +1470,9 @@ void copy_loclist(win_T *from, win_T *to)
|
|||||||
|
|
||||||
to_qfl->qf_index = from_qfl->qf_index; /* current index in the list */
|
to_qfl->qf_index = from_qfl->qf_index; /* current index in the list */
|
||||||
|
|
||||||
|
// Assign a new ID for the location list
|
||||||
|
to_qfl->qf_id = ++last_qf_id;
|
||||||
|
|
||||||
/* When no valid entries are present in the list, qf_ptr points to
|
/* When no valid entries are present in the list, qf_ptr points to
|
||||||
* the first item in the list */
|
* the first item in the list */
|
||||||
if (to_qfl->qf_nonevalid) {
|
if (to_qfl->qf_nonevalid) {
|
||||||
@@ -2458,6 +2464,7 @@ static void qf_free(qf_info_T *qi, int idx)
|
|||||||
qfl->qf_title = NULL;
|
qfl->qf_title = NULL;
|
||||||
tv_free(qfl->qf_ctx);
|
tv_free(qfl->qf_ctx);
|
||||||
qfl->qf_ctx = NULL;
|
qfl->qf_ctx = NULL;
|
||||||
|
qfl->qf_id = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@@ -4110,6 +4117,7 @@ enum {
|
|||||||
QF_GETLIST_NR = 0x4,
|
QF_GETLIST_NR = 0x4,
|
||||||
QF_GETLIST_WINID = 0x8,
|
QF_GETLIST_WINID = 0x8,
|
||||||
QF_GETLIST_CONTEXT = 0x10,
|
QF_GETLIST_CONTEXT = 0x10,
|
||||||
|
QF_GETLIST_ID = 0x20,
|
||||||
QF_GETLIST_ALL = 0xFF
|
QF_GETLIST_ALL = 0xFF
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -4155,15 +4163,16 @@ int get_errorlist_properties(win_T *wp, dict_T *what, dict_T *retdict)
|
|||||||
|
|
||||||
if (wp != NULL) {
|
if (wp != NULL) {
|
||||||
qi = GET_LOC_LIST(wp);
|
qi = GET_LOC_LIST(wp);
|
||||||
if (qi == NULL) {
|
}
|
||||||
// If querying for the size of the location list, return 0
|
// List is not present or is empty
|
||||||
if (((di = tv_dict_find(what, S_LEN("nr"))) != NULL)
|
if (qi == NULL || qi->qf_listcount == 0) {
|
||||||
&& (di->di_tv.v_type == VAR_STRING)
|
// If querying for the size of the list, return 0
|
||||||
&& strequal((const char *)di->di_tv.vval.v_string, "$")) {
|
if (((di = tv_dict_find(what, S_LEN("nr"))) != NULL)
|
||||||
return tv_dict_add_nr(retdict, S_LEN("nr"), 0);
|
&& (di->di_tv.v_type == VAR_STRING)
|
||||||
}
|
&& (STRCMP(di->di_tv.vval.v_string, "$") == 0)) {
|
||||||
return FAIL;
|
return tv_dict_add_nr(retdict, S_LEN("nr"), 0);
|
||||||
}
|
}
|
||||||
|
return FAIL;
|
||||||
}
|
}
|
||||||
|
|
||||||
int status = OK;
|
int status = OK;
|
||||||
@@ -4179,44 +4188,51 @@ int get_errorlist_properties(win_T *wp, dict_T *what, dict_T *retdict)
|
|||||||
if (qf_idx < 0 || qf_idx >= qi->qf_listcount) {
|
if (qf_idx < 0 || qf_idx >= qi->qf_listcount) {
|
||||||
return FAIL;
|
return FAIL;
|
||||||
}
|
}
|
||||||
} else if (qi->qf_listcount == 0) { // stack is empty
|
|
||||||
return FAIL;
|
|
||||||
}
|
}
|
||||||
flags |= QF_GETLIST_NR;
|
|
||||||
} else if (di->di_tv.v_type == VAR_STRING
|
} else if (di->di_tv.v_type == VAR_STRING
|
||||||
&& strequal((const char *)di->di_tv.vval.v_string, "$")) {
|
&& strequal((const char *)di->di_tv.vval.v_string, "$")) {
|
||||||
// Get the last quickfix list number
|
// Get the last quickfix list number
|
||||||
if (qi->qf_listcount > 0) {
|
qf_idx = qi->qf_listcount - 1;
|
||||||
qf_idx = qi->qf_listcount - 1;
|
} else {
|
||||||
} else {
|
return FAIL;
|
||||||
qf_idx = -1; // Quickfix stack is empty
|
}
|
||||||
|
flags |= QF_GETLIST_NR;
|
||||||
|
}
|
||||||
|
|
||||||
|
if ((di = tv_dict_find(what, S_LEN("id"))) != NULL) {
|
||||||
|
// Look for a list with the specified id
|
||||||
|
if (di->di_tv.v_type == VAR_NUMBER) {
|
||||||
|
// For zero, use the current list or the list specifed by 'nr'
|
||||||
|
if (di->di_tv.vval.v_number != 0) {
|
||||||
|
for (qf_idx = 0; qf_idx < qi->qf_listcount; qf_idx++) {
|
||||||
|
if (qi->qf_lists[qf_idx].qf_id == di->di_tv.vval.v_number) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (qf_idx == qi->qf_listcount) {
|
||||||
|
return FAIL; // List not found
|
||||||
|
}
|
||||||
}
|
}
|
||||||
flags |= QF_GETLIST_NR;
|
flags |= QF_GETLIST_ID;
|
||||||
} else {
|
} else {
|
||||||
return FAIL;
|
return FAIL;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (qf_idx != -1) {
|
if (tv_dict_find(what, S_LEN("all")) != NULL) {
|
||||||
if (tv_dict_find(what, S_LEN("all")) != NULL) {
|
flags |= QF_GETLIST_ALL;
|
||||||
flags |= QF_GETLIST_ALL;
|
}
|
||||||
}
|
if (tv_dict_find(what, S_LEN("title")) != NULL) {
|
||||||
|
flags |= QF_GETLIST_TITLE;
|
||||||
if (tv_dict_find(what, S_LEN("title")) != NULL) {
|
}
|
||||||
flags |= QF_GETLIST_TITLE;
|
if (tv_dict_find(what, S_LEN("winid")) != NULL) {
|
||||||
}
|
flags |= QF_GETLIST_WINID;
|
||||||
|
}
|
||||||
if (tv_dict_find(what, S_LEN("winid")) != NULL) {
|
if (tv_dict_find(what, S_LEN("context")) != NULL) {
|
||||||
flags |= QF_GETLIST_WINID;
|
flags |= QF_GETLIST_CONTEXT;
|
||||||
}
|
}
|
||||||
|
if (tv_dict_find(what, S_LEN("items")) != NULL) {
|
||||||
if (tv_dict_find(what, S_LEN("context")) != NULL) {
|
flags |= QF_GETLIST_ITEMS;
|
||||||
flags |= QF_GETLIST_CONTEXT;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (tv_dict_find(what, S_LEN("items")) != NULL) {
|
|
||||||
flags |= QF_GETLIST_ITEMS;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (flags & QF_GETLIST_TITLE) {
|
if (flags & QF_GETLIST_TITLE) {
|
||||||
@@ -4254,6 +4270,10 @@ int get_errorlist_properties(win_T *wp, dict_T *what, dict_T *retdict)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if ((status == OK) && (flags & QF_GETLIST_ID)) {
|
||||||
|
status = tv_dict_add_nr(retdict, S_LEN("id"), qi->qf_lists[qf_idx].qf_id);
|
||||||
|
}
|
||||||
|
|
||||||
return status;
|
return status;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -4410,6 +4430,22 @@ static int qf_set_properties(qf_info_T *qi, dict_T *what, int action,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!newlist && (di = tv_dict_find(what, S_LEN("id"))) != NULL) {
|
||||||
|
// Use the quickfix/location list with the specified id
|
||||||
|
if (di->di_tv.v_type == VAR_NUMBER) {
|
||||||
|
for (qf_idx = 0; qf_idx < qi->qf_listcount; qf_idx++) {
|
||||||
|
if (qi->qf_lists[qf_idx].qf_id == di->di_tv.vval.v_number) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (qf_idx == qi->qf_listcount) {
|
||||||
|
return FAIL; // List not found
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
return FAIL;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (newlist) {
|
if (newlist) {
|
||||||
qi->qf_curlist = qf_idx;
|
qi->qf_curlist = qf_idx;
|
||||||
qf_new_list(qi, title);
|
qf_new_list(qi, title);
|
||||||
|
@@ -1879,8 +1879,9 @@ func Xproperty_tests(cchar)
|
|||||||
call g:Xsetlist([], 'r', {'nr':2,'title':'Fruits','context':['Fruits']})
|
call g:Xsetlist([], 'r', {'nr':2,'title':'Fruits','context':['Fruits']})
|
||||||
let l1=g:Xgetlist({'nr':1,'all':1})
|
let l1=g:Xgetlist({'nr':1,'all':1})
|
||||||
let l2=g:Xgetlist({'nr':2,'all':1})
|
let l2=g:Xgetlist({'nr':2,'all':1})
|
||||||
let l1.nr=2
|
let save_id = l1.id
|
||||||
let l2.nr=1
|
let l1.id=l2.id
|
||||||
|
let l2.id=save_id
|
||||||
call g:Xsetlist([], 'r', l1)
|
call g:Xsetlist([], 'r', l1)
|
||||||
call g:Xsetlist([], 'r', l2)
|
call g:Xsetlist([], 'r', l2)
|
||||||
let newl1=g:Xgetlist({'nr':1,'all':1})
|
let newl1=g:Xgetlist({'nr':1,'all':1})
|
||||||
@@ -2527,3 +2528,38 @@ func Test_get_list_from_text()
|
|||||||
call XgetListFromText('c')
|
call XgetListFromText('c')
|
||||||
call XgetListFromText('l')
|
call XgetListFromText('l')
|
||||||
endfunc
|
endfunc
|
||||||
|
|
||||||
|
" Tests for the quickfix list id
|
||||||
|
func Xqfid_tests(cchar)
|
||||||
|
call s:setup_commands(a:cchar)
|
||||||
|
|
||||||
|
call g:Xsetlist([], 'f')
|
||||||
|
call assert_equal({}, g:Xgetlist({'id':0}))
|
||||||
|
Xexpr ''
|
||||||
|
let start_id = g:Xgetlist({'id' : 0}).id
|
||||||
|
Xexpr '' | Xexpr ''
|
||||||
|
Xolder
|
||||||
|
call assert_equal(start_id, g:Xgetlist({'id':0, 'nr':1}).id)
|
||||||
|
call assert_equal(start_id + 1, g:Xgetlist({'id':0, 'nr':0}).id)
|
||||||
|
call assert_equal(start_id + 2, g:Xgetlist({'id':0, 'nr':'$'}).id)
|
||||||
|
call assert_equal({}, g:Xgetlist({'id':0, 'nr':99}))
|
||||||
|
call assert_equal(2, g:Xgetlist({'id':start_id + 1, 'nr':0}).nr)
|
||||||
|
call assert_equal({}, g:Xgetlist({'id':99, 'nr':0}))
|
||||||
|
call assert_equal({}, g:Xgetlist({'id':"abc", 'nr':0}))
|
||||||
|
|
||||||
|
call g:Xsetlist([], 'a', {'id':start_id, 'context':[1,2]})
|
||||||
|
call assert_equal([1,2], g:Xgetlist({'nr':1, 'context':1}).context)
|
||||||
|
call g:Xsetlist([], 'a', {'id':start_id+1, 'text':'F1:10:L10'})
|
||||||
|
call assert_equal('L10', g:Xgetlist({'nr':2, 'items':1}).items[0].text)
|
||||||
|
call assert_equal(-1, g:Xsetlist([], 'a', {'id':999, 'title':'Vim'}))
|
||||||
|
call assert_equal(-1, g:Xsetlist([], 'a', {'id':'abc', 'title':'Vim'}))
|
||||||
|
|
||||||
|
let qfid = g:Xgetlist({'id':0, 'nr':0})
|
||||||
|
call g:Xsetlist([], 'f')
|
||||||
|
call assert_equal({}, g:Xgetlist({'id':qfid, 'nr':0}))
|
||||||
|
endfunc
|
||||||
|
|
||||||
|
func Test_qf_id()
|
||||||
|
call Xqfid_tests('c')
|
||||||
|
call Xqfid_tests('l')
|
||||||
|
endfunc
|
||||||
|
Reference in New Issue
Block a user