diff options
author | Bram Moolenaar <Bram@vim.org> | 2019-02-03 14:53:10 +0100 |
---|---|---|
committer | Bram Moolenaar <Bram@vim.org> | 2019-02-03 14:53:10 +0100 |
commit | aa5df7e3127dff6b7336df0903f5c569a40eb174 (patch) | |
tree | 491988c562057debdd52dc8198958e4099fd9452 /src/channel.c | |
parent | 01a6c21691631ee55744a1799a9725e5d6521cf4 (diff) | |
download | vim-git-aa5df7e3127dff6b7336df0903f5c569a40eb174.tar.gz |
patch 8.1.0870: Vim doesn't use the new ConPTY support in Windows 10v8.1.0870
Problem: Vim doesn't use the new ConPTY support in Windows 10.
Solution: Use ConPTY support, if available. (Nobuhiro Takasaki, closes #3794)
Diffstat (limited to 'src/channel.c')
-rw-r--r-- | src/channel.c | 73 |
1 files changed, 61 insertions, 12 deletions
diff --git a/src/channel.c b/src/channel.c index 20cf46238..484d0139b 100644 --- a/src/channel.c +++ b/src/channel.c @@ -1720,11 +1720,7 @@ channel_get_all(channel_T *channel, ch_part_T part, int *outlen) char_u *res; char_u *p; - /* If there is only one buffer just get that one. */ - if (head->rq_next == NULL || head->rq_next->rq_next == NULL) - return channel_get(channel, part, outlen); - - /* Concatenate everything into one buffer. */ + // Concatenate everything into one buffer. for (node = head->rq_next; node != NULL; node = node->rq_next) len += node->rq_buflen; res = lalloc(len + 1, TRUE); @@ -1738,7 +1734,7 @@ channel_get_all(channel_T *channel, ch_part_T part, int *outlen) } *p = NUL; - /* Free all buffers */ + // Free all buffers do { p = channel_get(channel, part, NULL); @@ -1747,16 +1743,37 @@ channel_get_all(channel_T *channel, ch_part_T part, int *outlen) if (outlen != NULL) { + // Returning the length, keep NUL characters. *outlen += len; return res; } - /* turn all NUL into NL */ - while (len > 0) + // Turn all NUL into NL, so that the result can be used as a string. + p = res; + while (p < res + len) { - --len; - if (res[len] == NUL) - res[len] = NL; + if (*p == NUL) + *p = NL; +#ifdef WIN32 + else if (*p == 0x1b) + { + // crush the escape sequence OSC 0/1/2: ESC ]0; + if (p + 3 < res + len + && p[1] == ']' + && (p[2] == '0' || p[2] == '1' || p[2] == '2') + && p[3] == ';') + { + // '\a' becomes a NL + while (p < res + (len - 1) && *p != '\a') + ++p; + // BEL is zero width characters, suppress display mistake + // ConPTY (after 10.0.18317) requires advance checking + if (p[-1] == NUL) + p[-1] = 0x07; + } + } +#endif + ++p; } return res; @@ -4330,7 +4347,7 @@ channel_parse_messages(void) channel = first_channel; continue; } - if (channel->ch_to_be_freed) + if (channel->ch_to_be_freed || channel->ch_killing) { channel_free(channel); /* channel has been freed, start over */ @@ -4930,6 +4947,28 @@ get_job_options(typval_T *tv, jobopt_T *opt, int supported, int supported2) opt->jo_set2 |= JO2_TERM_KILL; opt->jo_term_kill = tv_get_string_chk(item); } + else if (STRCMP(hi->hi_key, "term_mode") == 0) + { + char_u *p; + + if (!(supported2 & JO2_TERM_MODE)) + break; + opt->jo_set2 |= JO2_TERM_MODE; + p = tv_get_string_chk(item); + if (p == NULL) + { + semsg(_(e_invargval), "term_mode"); + return FAIL; + } + // Allow empty string, "winpty", "conpty". + if (!(*p == NUL || STRCMP(p, "winpty") == 0 + || STRCMP(p, "conpty") == 0)) + { + semsg(_(e_invargval), "term_mode"); + return FAIL; + } + opt->jo_term_mode = p[0]; + } # if defined(FEAT_GUI) || defined(FEAT_TERMGUICOLORS) else if (STRCMP(hi->hi_key, "ansi_colors") == 0) { @@ -5440,6 +5479,16 @@ job_cleanup(job_T *job) channel_need_redraw = TRUE; } + if (job->jv_channel != NULL + && job->jv_channel->ch_anonymous_pipe && !job->jv_channel->ch_killing) + { + ++safe_to_invoke_callback; + channel_free_contents(job->jv_channel); + job->jv_channel->ch_job = NULL; + job->jv_channel = NULL; + --safe_to_invoke_callback; + } + // Do not free the job in case the close callback of the associated channel // isn't invoked yet and may get information by job_info(). if (job->jv_refcount == 0 && !job_channel_still_useful(job)) |