This is a live mirror of the Perl 5 development currently hosted at https://github.com/perl/perl5
various pod nits identified by installhtml (all fixed except
[perl5.git] / ext / IO / lib / IO / Socket / INET.pm
CommitLineData
cf7fe8a2
GS
1# IO::Socket::INET.pm
2#
3# Copyright (c) 1997-8 Graham Barr <gbarr@pobox.com>. All rights reserved.
4# This program is free software; you can redistribute it and/or
5# modify it under the same terms as Perl itself.
6
7package IO::Socket::INET;
8
9use strict;
17f410f9 10our(@ISA, $VERSION);
cf7fe8a2
GS
11use IO::Socket;
12use Socket;
13use Carp;
14use Exporter;
15
16@ISA = qw(IO::Socket);
17$VERSION = "1.24";
18
19IO::Socket::INET->register_domain( AF_INET );
20
21my %socket_type = ( tcp => SOCK_STREAM,
22 udp => SOCK_DGRAM,
23 icmp => SOCK_RAW
24 );
25
26sub new {
27 my $class = shift;
28 unshift(@_, "PeerAddr") if @_ == 1;
29 return $class->SUPER::new(@_);
30}
31
32sub _sock_info {
33 my($addr,$port,$proto) = @_;
34 my @proto = ();
35 my @serv = ();
36
37 $port = $1
38 if(defined $addr && $addr =~ s,:([\w\(\)/]+)$,,);
39
40 if(defined $proto) {
41 @proto = $proto =~ m,\D, ? getprotobyname($proto)
42 : getprotobynumber($proto);
43
44 $proto = $proto[2] || undef;
45 }
46
47 if(defined $port) {
48 $port =~ s,\((\d+)\)$,,;
49
50 my $defport = $1 || undef;
51 my $pnum = ($port =~ m,^(\d+)$,)[0];
52
53 @serv= getservbyname($port, $proto[0] || "")
54 if($port =~ m,\D,);
55
56 $port = $pnum || $serv[2] || $defport || undef;
57
58 $proto = (getprotobyname($serv[3]))[2] || undef
59 if @serv && !$proto;
60 }
61
62 return ($addr || undef,
63 $port || undef,
64 $proto || undef
65 );
66}
67
68sub _error {
69 my $sock = shift;
70 local($!);
71 $@ = join("",ref($sock),": ",@_);
72 close($sock)
73 if(defined fileno($sock));
74 return undef;
75}
76
77sub _get_addr {
78 my($sock,$addr_str, $multi) = @_;
79 my @addr;
80 if ($multi && $addr_str !~ /^\d+(?:\.\d+){3}$/) {
81 (undef, undef, undef, undef, @addr) = gethostbyname($addr_str);
82 } else {
83 my $h = inet_aton($addr_str);
84 push(@addr, $h) if defined $h;
85 }
86 @addr;
87}
88
89sub configure {
90 my($sock,$arg) = @_;
91 my($lport,$rport,$laddr,$raddr,$proto,$type);
92
93
94 $arg->{LocalAddr} = $arg->{LocalHost}
95 if exists $arg->{LocalHost} && !exists $arg->{LocalAddr};
96
97 ($laddr,$lport,$proto) = _sock_info($arg->{LocalAddr},
98 $arg->{LocalPort},
99 $arg->{Proto});
100
101 $laddr = defined $laddr ? inet_aton($laddr)
102 : INADDR_ANY;
103
104 return _error($sock,"Bad hostname '",$arg->{LocalAddr},"'")
105 unless(defined $laddr);
106
107 $arg->{PeerAddr} = $arg->{PeerHost}
108 if exists $arg->{PeerHost} && !exists $arg->{PeerAddr};
109
110 unless(exists $arg->{Listen}) {
111 ($raddr,$rport,$proto) = _sock_info($arg->{PeerAddr},
112 $arg->{PeerPort},
113 $proto);
114 }
115
116 $proto ||= (getprotobyname('tcp'))[2];
117
118 my $pname = (getprotobynumber($proto))[0];
119 $type = $arg->{Type} || $socket_type{$pname};
120
121 my @raddr = ();
122
123 if(defined $raddr) {
124 @raddr = $sock->_get_addr($raddr, $arg->{MultiHomed});
125 return _error($sock,"Bad hostname '",$arg->{PeerAddr},"'")
126 unless @raddr;
127 }
128
129 while(1) {
130
131 $sock->socket(AF_INET, $type, $proto) or
132 return _error($sock,"$!");
133
134 if ($arg->{Reuse}) {
135 $sock->sockopt(SO_REUSEADDR,1) or
136 return _error($sock,"$!");
137 }
138
139 if($lport || ($laddr ne INADDR_ANY) || exists $arg->{Listen}) {
140 $sock->bind($lport || 0, $laddr) or
141 return _error($sock,"$!");
142 }
143
144 if(exists $arg->{Listen}) {
145 $sock->listen($arg->{Listen} || 5) or
146 return _error($sock,"$!");
147 last;
148 }
149
23925046
JH
150 # don't try to connect unless we're given a PeerAddr
151 last unless exists($arg->{PeerAddr});
152
cf7fe8a2
GS
153 $raddr = shift @raddr;
154
155 return _error($sock,'Cannot determine remote port')
156 unless($rport || $type == SOCK_DGRAM || $type == SOCK_RAW);
157
158 last
159 unless($type == SOCK_STREAM || defined $raddr);
160
161 return _error($sock,"Bad hostname '",$arg->{PeerAddr},"'")
162 unless defined $raddr;
163
164# my $timeout = ${*$sock}{'io_socket_timeout'};
165# my $before = time() if $timeout;
166
167 if ($sock->connect(pack_sockaddr_in($rport, $raddr))) {
168# ${*$sock}{'io_socket_timeout'} = $timeout;
169 return $sock;
170 }
171
172 return _error($sock,"$!")
173 unless @raddr;
174
175# if ($timeout) {
176# my $new_timeout = $timeout - (time() - $before);
177# return _error($sock, "Timeout") if $new_timeout <= 0;
178# ${*$sock}{'io_socket_timeout'} = $new_timeout;
179# }
180
181 }
182
183 $sock;
184}
185
186sub connect {
187 @_ == 2 || @_ == 3 or
188 croak 'usage: $sock->connect(NAME) or $sock->connect(PORT, ADDR)';
189 my $sock = shift;
190 return $sock->SUPER::connect(@_ == 1 ? shift : pack_sockaddr_in(@_));
191}
192
193sub bind {
194 @_ == 2 || @_ == 3 or
195 croak 'usage: $sock->bind(NAME) or $sock->bind(PORT, ADDR)';
196 my $sock = shift;
197 return $sock->SUPER::bind(@_ == 1 ? shift : pack_sockaddr_in(@_))
198}
199
200sub sockaddr {
201 @_ == 1 or croak 'usage: $sock->sockaddr()';
202 my($sock) = @_;
203 my $name = $sock->sockname;
204 $name ? (sockaddr_in($name))[1] : undef;
205}
206
207sub sockport {
208 @_ == 1 or croak 'usage: $sock->sockport()';
209 my($sock) = @_;
210 my $name = $sock->sockname;
211 $name ? (sockaddr_in($name))[0] : undef;
212}
213
214sub sockhost {
215 @_ == 1 or croak 'usage: $sock->sockhost()';
216 my($sock) = @_;
217 my $addr = $sock->sockaddr;
218 $addr ? inet_ntoa($addr) : undef;
219}
220
221sub peeraddr {
222 @_ == 1 or croak 'usage: $sock->peeraddr()';
223 my($sock) = @_;
224 my $name = $sock->peername;
225 $name ? (sockaddr_in($name))[1] : undef;
226}
227
228sub peerport {
229 @_ == 1 or croak 'usage: $sock->peerport()';
230 my($sock) = @_;
231 my $name = $sock->peername;
232 $name ? (sockaddr_in($name))[0] : undef;
233}
234
235sub peerhost {
236 @_ == 1 or croak 'usage: $sock->peerhost()';
237 my($sock) = @_;
238 my $addr = $sock->peeraddr;
239 $addr ? inet_ntoa($addr) : undef;
240}
241
2421;
243
244__END__
245
246=head1 NAME
247
248IO::Socket::INET - Object interface for AF_INET domain sockets
249
250=head1 SYNOPSIS
251
252 use IO::Socket::INET;
253
254=head1 DESCRIPTION
255
256C<IO::Socket::INET> provides an object interface to creating and using sockets
257in the AF_INET domain. It is built upon the L<IO::Socket> interface and
258inherits all the methods defined by L<IO::Socket>.
259
260=head1 CONSTRUCTOR
261
262=over 4
263
264=item new ( [ARGS] )
265
266Creates an C<IO::Socket::INET> object, which is a reference to a
267newly created symbol (see the C<Symbol> package). C<new>
268optionally takes arguments, these arguments are in key-value pairs.
269
270In addition to the key-value pairs accepted by L<IO::Socket>,
271C<IO::Socket::INET> provides.
272
273
274 PeerAddr Remote host address <hostname>[:<port>]
275 PeerHost Synonym for PeerAddr
276 PeerPort Remote port or service <service>[(<no>)] | <no>
277 LocalAddr Local host bind address hostname[:port]
278 LocalHost Synonym for LocalAddr
279 LocalPort Local host bind port <service>[(<no>)] | <no>
280 Proto Protocol name (or number) "tcp" | "udp" | ...
281 Type Socket type SOCK_STREAM | SOCK_DGRAM | ...
282 Listen Queue size for listen
283 Reuse Set SO_REUSEADDR before binding
284 Timeout Timeout value for various operations
285 MultiHomed Try all adresses for multi-homed hosts
286
287
288If C<Listen> is defined then a listen socket is created, else if the
289socket type, which is derived from the protocol, is SOCK_STREAM then
290connect() is called.
291
292Although it is not illegal, the use of C<MultiHomed> on a socket
293which is in non-blocking mode is of little use. This is because the
294first connect will never fail with a timeout as the connaect call
295will not block.
296
297The C<PeerAddr> can be a hostname or the IP-address on the
298"xx.xx.xx.xx" form. The C<PeerPort> can be a number or a symbolic
299service name. The service name might be followed by a number in
300parenthesis which is used if the service is not known by the system.
301The C<PeerPort> specification can also be embedded in the C<PeerAddr>
302by preceding it with a ":".
303
304If C<Proto> is not given and you specify a symbolic C<PeerPort> port,
305then the constructor will try to derive C<Proto> from the service
306name. As a last resort C<Proto> "tcp" is assumed. The C<Type>
307parameter will be deduced from C<Proto> if not specified.
308
309If the constructor is only passed a single argument, it is assumed to
310be a C<PeerAddr> specification.
311
312Examples:
313
314 $sock = IO::Socket::INET->new(PeerAddr => 'www.perl.org',
315 PeerPort => 'http(80)',
316 Proto => 'tcp');
317
318 $sock = IO::Socket::INET->new(PeerAddr => 'localhost:smtp(25)');
319
320 $sock = IO::Socket::INET->new(Listen => 5,
321 LocalAddr => 'localhost',
322 LocalPort => 9000,
323 Proto => 'tcp');
324
325 $sock = IO::Socket::INET->new('127.0.0.1:25');
326
327
328 NOTE NOTE NOTE NOTE NOTE NOTE NOTE NOTE NOTE NOTE NOTE NOTE
329
330As of VERSION 1.18 all IO::Socket objects have autoflush turned on
331by default. This was not the case with earlier releases.
332
333 NOTE NOTE NOTE NOTE NOTE NOTE NOTE NOTE NOTE NOTE NOTE NOTE
334
a45bd81d
GS
335=back
336
cf7fe8a2
GS
337=head2 METHODS
338
339=over 4
340
341=item sockaddr ()
342
343Return the address part of the sockaddr structure for the socket
344
345=item sockport ()
346
347Return the port number that the socket is using on the local host
348
349=item sockhost ()
350
351Return the address part of the sockaddr structure for the socket in a
352text form xx.xx.xx.xx
353
354=item peeraddr ()
355
356Return the address part of the sockaddr structure for the socket on
357the peer host
358
359=item peerport ()
360
361Return the port number for the socket on the peer host.
362
363=item peerhost ()
364
365Return the address part of the sockaddr structure for the socket on the
366peer host in a text form xx.xx.xx.xx
367
368=back
369
370=head1 SEE ALSO
371
372L<Socket>, L<IO::Socket>
373
374=head1 AUTHOR
375
854822f1
GS
376Graham Barr. Currently maintained by the Perl Porters. Please report all
377bugs to <perl5-porters@perl.org>.
cf7fe8a2
GS
378
379=head1 COPYRIGHT
380
381Copyright (c) 1996-8 Graham Barr <gbarr@pobox.com>. All rights reserved.
382This program is free software; you can redistribute it and/or
383modify it under the same terms as Perl itself.
384
385=cut