diff options
author | Daniel Hahler <git@thequod.de> | 2019-11-29 09:42:58 +0100 |
---|---|---|
committer | Jan Edmund Lazo <jan.lazo@mail.utoronto.ca> | 2021-03-30 21:55:50 -0400 |
commit | 7268d49c50d01a841a32856cfc5713ae8de2fc96 (patch) | |
tree | c5aebe1c4c71e8158c44845c168b66e1c62ba1ee | |
parent | 36caafeb281bf872f11d475e594eb212636daa4d (diff) | |
download | rneovim-7268d49c50d01a841a32856cfc5713ae8de2fc96.tar.gz rneovim-7268d49c50d01a841a32856cfc5713ae8de2fc96.tar.bz2 rneovim-7268d49c50d01a841a32856cfc5713ae8de2fc96.zip |
tv_dict_watcher_remove: delay freeing with busy queue
-rw-r--r-- | src/nvim/eval/typval.c | 18 |
1 files changed, 13 insertions, 5 deletions
diff --git a/src/nvim/eval/typval.c b/src/nvim/eval/typval.c index 5b3e31b324..726619eb43 100644 --- a/src/nvim/eval/typval.c +++ b/src/nvim/eval/typval.c @@ -1183,8 +1183,12 @@ bool tv_dict_watcher_remove(dict_T *const dict, const char *const key_pattern, QUEUE *w = NULL; DictWatcher *watcher = NULL; bool matched = false; + bool queue_is_busy = false; QUEUE_FOREACH(w, &dict->watchers, { watcher = tv_dict_watcher_node_data(w); + if (watcher->busy) { + queue_is_busy = true; + } if (tv_callback_equal(&watcher->callback, &callback) && watcher->key_pattern_len == key_pattern_len && memcmp(watcher->key_pattern, key_pattern, key_pattern_len) == 0) { @@ -1197,10 +1201,10 @@ bool tv_dict_watcher_remove(dict_T *const dict, const char *const key_pattern, return false; } - QUEUE_REMOVE(w); - if (watcher->busy) { + if (queue_is_busy) { watcher->needs_free = true; } else { + QUEUE_REMOVE(w); tv_dict_watcher_free(watcher); } return true; @@ -1273,9 +1277,13 @@ void tv_dict_watcher_notify(dict_T *const dict, const char *const key, callback_call(&watcher->callback, 3, argv, &rettv); watcher->busy = false; tv_clear(&rettv); - if (watcher->needs_free) { - tv_dict_watcher_free(watcher); - } + } + }) + QUEUE_FOREACH(w, &dict->watchers, { + DictWatcher *watcher = tv_dict_watcher_node_data(w); + if (watcher->needs_free) { + QUEUE_REMOVE(w); + tv_dict_watcher_free(watcher); } }) tv_dict_unref(dict); |