Skip to content

Commit 0874a83

Browse files
committed
patch 7.4.2298
Problem: It is not possible to close the "in" part of a channel. Solution: Add ch_close_in().
1 parent d8b5549 commit 0874a83

7 files changed

Lines changed: 66 additions & 10 deletions

File tree

runtime/doc/channel.txt

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
*channel.txt* For Vim version 7.4. Last change: 2016 Aug 31
1+
*channel.txt* For Vim version 7.4. Last change: 2016 Sep 01
22

33

44
VIM REFERENCE MANUAL by Bram Moolenaar
@@ -501,6 +501,10 @@ A special mode is when "in_top" is set to zero and "in_bot" is not set: Every
501501
time a line is added to the buffer, the last-but-one line will be send to the
502502
job stdin. This allows for editing the last line and sending it when pressing
503503
Enter.
504+
*channel-close-in*
505+
When not using the special mode the pipe or socket will be closed after the
506+
last line has been written. This signals the reading end that the input
507+
finished. You can also use |ch_close_in()| to close it sooner.
504508

505509
NUL bytes in the text will be passed to the job (internally Vim stores these
506510
as NL bytes).

runtime/doc/eval.txt

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
*eval.txt* For Vim version 7.4. Last change: 2016 Aug 31
1+
*eval.txt* For Vim version 7.4. Last change: 2016 Sep 01
22

33

44
VIM REFERENCE MANUAL by Bram Moolenaar
@@ -2009,6 +2009,7 @@ call({func}, {arglist} [, {dict}])
20092009
any call {func} with arguments {arglist}
20102010
ceil({expr}) Float round {expr} up
20112011
ch_close({handle}) none close {handle}
2012+
ch_close_in({handle}) none close in part of {handle}
20122013
ch_evalexpr({handle}, {expr} [, {options}])
20132014
any evaluate {expr} on JSON {handle}
20142015
ch_evalraw({handle}, {string} [, {options}])
@@ -2980,6 +2981,14 @@ confirm({msg} [, {choices} [, {default} [, {type}]]])
29802981
ch_close({handle}) *ch_close()*
29812982
Close {handle}. See |channel-close|.
29822983
{handle} can be Channel or a Job that has a Channel.
2984+
A close callback is not invoked.
2985+
2986+
{only available when compiled with the |+channel| feature}
2987+
2988+
ch_close_in({handle}) *ch_close_in()*
2989+
Close the "in" part of {handle}. See |channel-close-in|.
2990+
{handle} can be Channel or a Job that has a Channel.
2991+
A close callback is not invoked.
29832992

29842993
{only available when compiled with the |+channel| feature}
29852994

src/channel.c

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2735,6 +2735,15 @@ channel_close(channel_T *channel, int invoke_close_cb)
27352735
channel->ch_nb_close_cb = NULL;
27362736
}
27372737

2738+
/*
2739+
* Close the "in" part channel "channel".
2740+
*/
2741+
void
2742+
channel_close_in(channel_T *channel)
2743+
{
2744+
may_close_part(&channel->CH_IN_FD);
2745+
}
2746+
27382747
/*
27392748
* Clear the read buffer on "channel"/"part".
27402749
*/

src/evalfunc.c

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -77,6 +77,7 @@ static void f_ceil(typval_T *argvars, typval_T *rettv);
7777
#endif
7878
#ifdef FEAT_JOB_CHANNEL
7979
static void f_ch_close(typval_T *argvars, typval_T *rettv);
80+
static void f_ch_close_in(typval_T *argvars, typval_T *rettv);
8081
static void f_ch_evalexpr(typval_T *argvars, typval_T *rettv);
8182
static void f_ch_evalraw(typval_T *argvars, typval_T *rettv);
8283
static void f_ch_getbufnr(typval_T *argvars, typval_T *rettv);
@@ -499,6 +500,7 @@ static struct fst
499500
#endif
500501
#ifdef FEAT_JOB_CHANNEL
501502
{"ch_close", 1, 1, f_ch_close},
503+
{"ch_close_in", 1, 1, f_ch_close_in},
502504
{"ch_evalexpr", 2, 3, f_ch_evalexpr},
503505
{"ch_evalraw", 2, 3, f_ch_evalraw},
504506
{"ch_getbufnr", 2, 2, f_ch_getbufnr},
@@ -1791,6 +1793,18 @@ f_ch_close(typval_T *argvars, typval_T *rettv UNUSED)
17911793
}
17921794
}
17931795

1796+
/*
1797+
* "ch_close()" function
1798+
*/
1799+
static void
1800+
f_ch_close_in(typval_T *argvars, typval_T *rettv UNUSED)
1801+
{
1802+
channel_T *channel = get_channel_arg(&argvars[0], TRUE, FALSE, 0);
1803+
1804+
if (channel != NULL)
1805+
channel_close_in(channel);
1806+
}
1807+
17941808
/*
17951809
* "ch_getbufnr()" function
17961810
*/

src/proto/channel.pro

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@ int channel_is_open(channel_T *channel);
2727
char *channel_status(channel_T *channel);
2828
void channel_info(channel_T *channel, dict_T *dict);
2929
void channel_close(channel_T *channel, int invoke_close_cb);
30+
void channel_close_in(channel_T *channel);
3031
void channel_clear(channel_T *channel);
3132
void channel_free_all(void);
3233
char_u *channel_read_block(channel_T *channel, int part, int timeout);

src/testdir/test_channel.vim

Lines changed: 25 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -792,22 +792,32 @@ func Test_pipe_from_buffer_nr()
792792
call Run_test_pipe_from_buffer(0)
793793
endfunc
794794

795-
func Run_pipe_through_sort(all)
795+
func Run_pipe_through_sort(all, use_buffer)
796796
if !executable('sort') || !has('job')
797797
return
798798
endif
799-
split sortin
800-
call setline(1, ['ccc', 'aaa', 'ddd', 'bbb', 'eee'])
801-
let options = {'in_io': 'buffer', 'in_name': 'sortin',
802-
\ 'out_io': 'buffer', 'out_name': 'sortout'}
799+
let options = {'out_io': 'buffer', 'out_name': 'sortout'}
800+
if a:use_buffer
801+
split sortin
802+
call setline(1, ['ccc', 'aaa', 'ddd', 'bbb', 'eee'])
803+
let options.in_io = 'buffer'
804+
let options.in_name = 'sortin'
805+
endif
803806
if !a:all
804807
let options.in_top = 2
805808
let options.in_bot = 4
806809
endif
807810
let g:job = job_start('sort', options)
808811
call assert_equal("run", job_status(g:job))
812+
813+
if !a:use_buffer
814+
call ch_sendraw(g:job, "ccc\naaa\nddd\nbbb\neee\n")
815+
call ch_close_in(g:job)
816+
endif
817+
809818
call WaitFor('job_status(g:job) == "dead"')
810819
call assert_equal("dead", job_status(g:job))
820+
811821
sp sortout
812822
call assert_equal('Reading from channel output...', getline(1))
813823
if a:all
@@ -818,18 +828,25 @@ func Run_pipe_through_sort(all)
818828

819829
call job_stop(g:job)
820830
unlet g:job
821-
bwipe! sortin
831+
if a:use_buffer
832+
bwipe! sortin
833+
endif
822834
bwipe! sortout
823835
endfunc
824836

825837
func Test_pipe_through_sort_all()
826838
call ch_log('Test_pipe_through_sort_all()')
827-
call Run_pipe_through_sort(1)
839+
call Run_pipe_through_sort(1, 1)
828840
endfunc
829841

830842
func Test_pipe_through_sort_some()
831843
call ch_log('Test_pipe_through_sort_some()')
832-
call Run_pipe_through_sort(0)
844+
call Run_pipe_through_sort(0, 1)
845+
endfunc
846+
847+
func Test_pipe_through_sort_feed()
848+
call ch_log('Test_pipe_through_sort_feed()')
849+
call Run_pipe_through_sort(1, 0)
833850
endfunc
834851

835852
func Test_pipe_to_nameless_buffer()

src/version.c

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -763,6 +763,8 @@ static char *(features[]) =
763763

764764
static int included_patches[] =
765765
{ /* Add new patch number below this line */
766+
/**/
767+
2298,
766768
/**/
767769
2297,
768770
/**/

0 commit comments

Comments
 (0)