1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93
|
# All possible one- and two-way fh types:
# - pipe
# - fifo
# - socket pair
# - tcp socket
# - unix socket
use warnings;
use strict;
use lib 't';
use share;
@CheckPoint = (
[ 'client', SENT ], 'client: SENT',
[ 'server', EOF ], 'server: EOF',
[ 'server', 'sockpair' ], ' got "sockpair"',
[ 'server', SENT ], 'server: SENT',
[ 'client', EOF ], 'client: EOF',
[ 'client', 'echo: sockpair'], ' got "echo: sockpair"',
[ 'client', SENT ], 'client: SENT',
[ 'server', EOF ], 'server: EOF',
[ 'server', 'socket' ], ' got "socket"',
[ 'server', SENT ], 'server: SENT',
[ 'client', EOF ], 'client: EOF',
[ 'client', 'echo: socket' ], ' got "echo: socket"',
);
plan tests => @CheckPoint/2;
socketpair my $server, my $client, AF_UNIX, SOCK_STREAM, PF_UNSPEC or die "socketpair: $!";
nonblocking($server);
nonblocking($client);
stream2('sockpair', $server, $client);
my $lst_sock = tcp_server('127.0.0.1', 0);
my $cln_sock = tcp_client('127.0.0.1', sockport($lst_sock));
my $srv_sock;
use Errno qw( EBADF );
until (accept $srv_sock, $lst_sock) {
$! == EAGAIN or (WIN32 && $! == EBADF) or die "accept: $!";
sleep 1;
}
close $lst_sock or die "close: $!";
stream2('socket', $srv_sock, $cln_sock);
sub stream2 {
my ($name, $srv_fh, $cln_fh) = @_;
IO::Stream->new({
fh => $srv_fh,
cb => \&server,
wait_for => EOF,
in_buf_limit=> 1024,
});
IO::Stream->new({
fh => $cln_fh,
cb => \&client,
wait_for => SENT,
out_buf => $name,
in_buf_limit=> 1024,
});
EV::loop;
}
sub server {
my ($io, $e, $err) = @_;
die $err if $err;
checkpoint($e);
if ($e & EOF) {
checkpoint($io->{in_buf});
$io->{wait_for} = SENT;
$io->write("echo: $io->{in_buf}");
}
if ($e & SENT) {
$io->close();
}
}
sub client {
my ($io, $e, $err) = @_;
die $err if $err;
checkpoint($e);
if ($e & SENT) {
$io->{wait_for} = EOF;
shutdown $io->{fh}, 1;
}
if ($e & EOF) {
checkpoint($io->{in_buf});
$io->close();
EV::unloop;
}
}
|