summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorBram Moolenaar <Bram@vim.org>2020-03-28 18:06:31 +0100
committerBram Moolenaar <Bram@vim.org>2020-03-28 18:06:31 +0100
commit09c569038c42dcbdaa5c9b35fc9d1afbe5072cb4 (patch)
treea727453135a63e143ce899a9eb86ecdfa2b64a0f
parent599c89c82fe3c85378e8077b4e589f0ee4218da2 (diff)
downloadvim-git-09c569038c42dcbdaa5c9b35fc9d1afbe5072cb4.tar.gz
patch 8.2.0466: not parsing messages recursively breaks the govim pluginv8.2.0466
Problem: Not parsing messages recursively breaks the govim plugin. Solution: When called recursively do handle messages but do not close channels.
-rw-r--r--src/channel.c62
-rw-r--r--src/version.c2
2 files changed, 34 insertions, 30 deletions
diff --git a/src/channel.c b/src/channel.c
index d3be7ecd3..4db40c9dd 100644
--- a/src/channel.c
+++ b/src/channel.c
@@ -4428,16 +4428,14 @@ channel_parse_messages(void)
int ret = FALSE;
int r;
ch_part_T part = PART_SOCK;
- static int recursive = FALSE;
+ static int recursive = 0;
#ifdef ELAPSED_FUNC
elapsed_T start_tv;
#endif
// The code below may invoke callbacks, which might call us back.
- // That doesn't work well, just return without doing anything.
- if (recursive)
- return FALSE;
- recursive = TRUE;
+ // In a recursive call channels will not be closed.
+ ++recursive;
++safe_to_invoke_callback;
#ifdef ELAPSED_FUNC
@@ -4454,33 +4452,37 @@ channel_parse_messages(void)
}
while (channel != NULL)
{
- if (channel_can_close(channel))
- {
- channel->ch_to_be_closed = (1U << PART_COUNT);
- channel_close_now(channel);
- // channel may have been freed, start over
- channel = first_channel;
- continue;
- }
- if (channel->ch_to_be_freed || channel->ch_killing)
+ if (recursive == 1)
{
- channel_free_contents(channel);
- if (channel->ch_job != NULL)
- channel->ch_job->jv_channel = NULL;
+ if (channel_can_close(channel))
+ {
+ channel->ch_to_be_closed = (1U << PART_COUNT);
+ channel_close_now(channel);
+ // channel may have been freed, start over
+ channel = first_channel;
+ continue;
+ }
+ if (channel->ch_to_be_freed || channel->ch_killing)
+ {
+ channel_free_contents(channel);
+ if (channel->ch_job != NULL)
+ channel->ch_job->jv_channel = NULL;
- // free the channel and then start over
- channel_free_channel(channel);
- channel = first_channel;
- continue;
- }
- if (channel->ch_refcount == 0 && !channel_still_useful(channel))
- {
- // channel is no longer useful, free it
- channel_free(channel);
- channel = first_channel;
- part = PART_SOCK;
- continue;
+ // free the channel and then start over
+ channel_free_channel(channel);
+ channel = first_channel;
+ continue;
+ }
+ if (channel->ch_refcount == 0 && !channel_still_useful(channel))
+ {
+ // channel is no longer useful, free it
+ channel_free(channel);
+ channel = first_channel;
+ part = PART_SOCK;
+ continue;
+ }
}
+
if (channel->ch_part[part].ch_fd != INVALID_FD
|| channel_has_readahead(channel, part))
{
@@ -4521,7 +4523,7 @@ channel_parse_messages(void)
}
--safe_to_invoke_callback;
- recursive = FALSE;
+ --recursive;
return ret;
}
diff --git a/src/version.c b/src/version.c
index c33bf2c56..1630b5e70 100644
--- a/src/version.c
+++ b/src/version.c
@@ -739,6 +739,8 @@ static char *(features[]) =
static int included_patches[] =
{ /* Add new patch number below this line */
/**/
+ 466,
+/**/
465,
/**/
464,