various bugs in IO::Poll (from Lincoln D. Stein <lstein@cshl.org>)
[p5sagit/p5-mst-13.2.git] / ext / IO / lib / IO / Poll.pm
1
2 # IO::Poll.pm
3 #
4 # Copyright (c) 1997-8 Graham Barr <gbarr@pobox.com>. All rights reserved.
5 # This program is free software; you can redistribute it and/or
6 # modify it under the same terms as Perl itself.
7
8 package IO::Poll;
9
10 use strict;
11 use IO::Handle;
12 use Exporter ();
13 our(@ISA, @EXPORT_OK, @EXPORT, $VERSION);
14
15 @ISA = qw(Exporter);
16 $VERSION = "0.04";
17
18 @EXPORT = qw( POLLIN
19               POLLOUT
20               POLLERR
21               POLLHUP
22               POLLNVAL
23             );
24
25 @EXPORT_OK = qw(
26  POLLPRI   
27  POLLRDNORM
28  POLLWRNORM
29  POLLRDBAND
30  POLLWRBAND
31  POLLNORM  
32 );
33
34 # [0] maps fd's to requested masks
35 # [1] maps fd's to returned  masks
36 # [2] maps fd's to handles
37 sub new {
38     my $class = shift;
39
40     my $self = bless [{},{},{}], $class;
41
42     $self;
43 }
44
45 sub mask {
46     my $self = shift;
47     my $io = shift;
48     my $fd = fileno($io);
49     if(@_) {
50         my $mask = shift;
51         if($mask) {
52           $self->[0]{$fd} = $mask;
53           $self->[1]{$fd} = 0;     # no returned mask until poll() called
54           $self->[2]{$fd} = $io;
55         } else {
56           delete $self->[0]{$fd};
57           delete $self->[1]{$fd};
58           delete $self->[2]{$fd};
59         }
60     }
61
62     return unless exists $self->[1]{$fd};
63     return $self->[1]{$fd};
64 }
65
66
67 sub poll {
68     my($self,$timeout) = @_;
69
70     $self->[1] = {};
71
72     my($fd,$mask);
73     my @poll = ();
74
75     while(($fd,$mask) = each %{$self->[0]}) {
76         push(@poll,$fd => $mask);
77     }
78
79     my $ret = @poll ? _poll(defined($timeout) ? $timeout * 1000 : -1,@poll) : 0;
80
81     return $ret
82         unless $ret > 0;
83
84     while(@poll) {
85         my($fd,$got) = splice(@poll,0,2);
86         $self->[1]{$fd} = $got if $got;
87     }
88
89     return $ret;  
90 }
91
92 sub events {
93     my $self = shift;
94     my $io = shift;
95     my $fd = fileno($io);
96     exists $self->[1]{$fd} ? $self->[1]{$fd} : 0;
97 }
98
99 sub remove {
100     my $self = shift;
101     my $io = shift;
102     $self->mask($io,0);
103 }
104
105 sub handles {
106     my $self = shift;
107     return values %{$self->[2]} unless @_;
108
109     my $events = shift || 0;
110     my($fd,$ev,$io,$mask);
111     my @handles = ();
112
113     while(($fd,$ev) = each %{$self->[1]}) {
114       push @handles,$self->[2]{$fd} if $ev & $events;
115     }
116     return @handles;
117 }
118
119 1;
120
121 __END__
122
123 =head1 NAME
124
125 IO::Poll - Object interface to system poll call
126
127 =head1 SYNOPSIS
128
129     use IO::Poll qw(POLLRDNORM POLLWRNORM POLLIN POLLHUP);
130
131     $poll = new IO::Poll;
132
133     $poll->mask($input_handle => POLLIN);
134     $poll->mask($output_handle => POLLOUT);
135
136     $poll->poll($timeout);
137
138     $ev = $poll->events($input);
139
140 =head1 DESCRIPTION
141
142 C<IO::Poll> is a simple interface to the system level poll routine.
143
144 =head1 METHODS
145
146 =over 4
147
148 =item mask ( IO [, EVENT_MASK ] )
149
150 If EVENT_MASK is given, then, if EVENT_MASK is non-zero, IO is added to the
151 list of file descriptors and the next call to poll will check for
152 any event specified in EVENT_MASK. If EVENT_MASK is zero then IO will be
153 removed from the list of file descriptors.
154
155 If EVENT_MASK is not given then the return value will be the current
156 event mask value for IO.
157
158 =item poll ( [ TIMEOUT ] )
159
160 Call the system level poll routine. If TIMEOUT is not specified then the
161 call will block. Returns the number of handles which had events
162 happen, or -1 on error.
163
164 =item events ( IO )
165
166 Returns the event mask which represents the events that happend on IO
167 during the last call to C<poll>.
168
169 =item remove ( IO )
170
171 Remove IO from the list of file descriptors for the next poll.
172
173 =item handles( [ EVENT_MASK ] )
174
175 Returns a list of handles. If EVENT_MASK is not given then a list of all
176 handles known will be returned. If EVENT_MASK is given then a list
177 of handles will be returned which had one of the events specified by
178 EVENT_MASK happen during the last call ti C<poll>
179
180 =back
181
182 =head1 SEE ALSO
183
184 L<poll(2)>, L<IO::Handle>, L<IO::Select>
185
186 =head1 AUTHOR
187
188 Graham Barr. Currently maintained by the Perl Porters.  Please report all
189 bugs to <perl5-porters@perl.org>.
190
191 =head1 COPYRIGHT
192
193 Copyright (c) 1997-8 Graham Barr <gbarr@pobox.com>. All rights reserved.
194 This program is free software; you can redistribute it and/or
195 modify it under the same terms as Perl itself.
196
197 =cut