mirror of
https://github.com/neovim/neovim.git
synced 2025-09-17 16:58:17 +00:00
vim-patch:8.1.1964: crash when using nested map() and filter() (#35715)
Problem: Crash when using nested map() and filter().
Solution: Do not set the v:key type to string without clearing the pointer.
c36350bca3
Port filter_map() changes from patch 8.1.1939.
Note: v8.1.1964 reverts a redundant change for `filter_map()` (now
within `filter_map_dict()`) from v8.1.1957.
Co-authored-by: Bram Moolenaar <Bram@vim.org>
This commit is contained in:
@@ -5412,8 +5412,6 @@ static void filter_map_dict(dict_T *d, filtermap_T filtermap, const char *func_n
|
|||||||
d_ret = rettv->vval.v_dict;
|
d_ret = rettv->vval.v_dict;
|
||||||
}
|
}
|
||||||
|
|
||||||
vimvars[VV_KEY].vv_type = VAR_STRING;
|
|
||||||
|
|
||||||
const VarLockStatus prev_lock = d->dv_lock;
|
const VarLockStatus prev_lock = d->dv_lock;
|
||||||
if (d->dv_lock == VAR_UNLOCKED) {
|
if (d->dv_lock == VAR_UNLOCKED) {
|
||||||
d->dv_lock = VAR_LOCKED;
|
d->dv_lock = VAR_LOCKED;
|
||||||
@@ -5425,11 +5423,11 @@ static void filter_map_dict(dict_T *d, filtermap_T filtermap, const char *func_n
|
|||||||
|| var_check_ro(di->di_flags, arg_errmsg, TV_TRANSLATE))) {
|
|| var_check_ro(di->di_flags, arg_errmsg, TV_TRANSLATE))) {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
vimvars[VV_KEY].vv_str = xstrdup(di->di_key);
|
set_vim_var_string(VV_KEY, di->di_key, -1);
|
||||||
typval_T newtv;
|
typval_T newtv;
|
||||||
bool rem;
|
bool rem;
|
||||||
int r = filter_map_one(&di->di_tv, expr, filtermap, &newtv, &rem);
|
int r = filter_map_one(&di->di_tv, expr, filtermap, &newtv, &rem);
|
||||||
tv_clear(&vimvars[VV_KEY].vv_tv);
|
tv_clear(get_vim_var_tv(VV_KEY));
|
||||||
if (r == FAIL || did_emsg) {
|
if (r == FAIL || did_emsg) {
|
||||||
tv_clear(&newtv);
|
tv_clear(&newtv);
|
||||||
break;
|
break;
|
||||||
@@ -5496,7 +5494,7 @@ static void filter_map_blob(blob_T *blob_arg, filtermap_T filtermap, typval_T *e
|
|||||||
.v_lock = VAR_UNLOCKED,
|
.v_lock = VAR_UNLOCKED,
|
||||||
.vval.v_number = val,
|
.vval.v_number = val,
|
||||||
};
|
};
|
||||||
vimvars[VV_KEY].vv_nr = idx;
|
set_vim_var_nr(VV_KEY, idx);
|
||||||
typval_T newtv;
|
typval_T newtv;
|
||||||
bool rem;
|
bool rem;
|
||||||
if (filter_map_one(&tv, expr, filtermap, &newtv, &rem) == FAIL
|
if (filter_map_one(&tv, expr, filtermap, &newtv, &rem) == FAIL
|
||||||
@@ -5614,7 +5612,7 @@ static void filter_map_list(list_T *l, filtermap_T filtermap, const char *func_n
|
|||||||
&& value_check_lock(TV_LIST_ITEM_TV(li)->v_lock, arg_errmsg, TV_TRANSLATE)) {
|
&& value_check_lock(TV_LIST_ITEM_TV(li)->v_lock, arg_errmsg, TV_TRANSLATE)) {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
vimvars[VV_KEY].vv_nr = idx;
|
set_vim_var_nr(VV_KEY, idx);
|
||||||
typval_T newtv;
|
typval_T newtv;
|
||||||
bool rem;
|
bool rem;
|
||||||
if (filter_map_one(TV_LIST_ITEM_TV(li), expr, filtermap, &newtv, &rem) == FAIL) {
|
if (filter_map_one(TV_LIST_ITEM_TV(li), expr, filtermap, &newtv, &rem) == FAIL) {
|
||||||
@@ -5684,15 +5682,16 @@ static void filter_map(typval_T *argvars, typval_T *rettv, filtermap_T filtermap
|
|||||||
}
|
}
|
||||||
|
|
||||||
typval_T save_val;
|
typval_T save_val;
|
||||||
|
typval_T save_key;
|
||||||
|
|
||||||
prepare_vimvar(VV_VAL, &save_val);
|
prepare_vimvar(VV_VAL, &save_val);
|
||||||
|
prepare_vimvar(VV_KEY, &save_key);
|
||||||
|
|
||||||
// We reset "did_emsg" to be able to detect whether an error
|
// We reset "did_emsg" to be able to detect whether an error
|
||||||
// occurred during evaluation of the expression.
|
// occurred during evaluation of the expression.
|
||||||
int save_did_emsg = did_emsg;
|
int save_did_emsg = did_emsg;
|
||||||
did_emsg = false;
|
did_emsg = false;
|
||||||
|
|
||||||
typval_T save_key;
|
|
||||||
prepare_vimvar(VV_KEY, &save_key);
|
|
||||||
if (argvars[0].v_type == VAR_DICT) {
|
if (argvars[0].v_type == VAR_DICT) {
|
||||||
filter_map_dict(argvars[0].vval.v_dict, filtermap, func_name,
|
filter_map_dict(argvars[0].vval.v_dict, filtermap, func_name,
|
||||||
arg_errmsg, expr, rettv);
|
arg_errmsg, expr, rettv);
|
||||||
|
Reference in New Issue
Block a user