start of AnyEvent conversion
[spider.git] / perl / Msg.pm
index 5ac71b428e44d793bc74f49e1dfb569bc4f04311..5aebab650caac475f3b05600ff2a2e7e3d46f35b 100644 (file)
@@ -5,7 +5,7 @@
 #
 # I have modified it to suit my devious purposes (Dirk Koopman G1TLH)
 #
-# $Id$
+#
 #
 
 package Msg;
@@ -14,15 +14,10 @@ use strict;
 
 use DXUtil;
 
-use vars qw($VERSION $BRANCH);
-($VERSION, $BRANCH) = dxver(q$Revision$);
-
-use IO::Select;
-use IO::Socket;
 use DXDebug;
 use Timer;
 
-use vars qw(%rd_callbacks %wt_callbacks %er_callbacks $rd_handles $wt_handles $er_handles $now %conns $noconns $blocking_supported $cnum $total_in $total_out);
+use vars qw(%rd_callbacks %wt_callbacks %er_callbacks $rd_handles $wt_handles $er_handles $now %conns $noconns $blocking_supported $cnum $total_in $total_out $io_socket);
 
 %rd_callbacks = ();
 %wt_callbacks = ();
@@ -40,10 +35,25 @@ BEGIN {
                local $^W;
         require POSIX; POSIX->import(qw(O_NONBLOCK F_SETFL F_GETFL))
     };
+
+       eval {
+               local $^W;
+               require IO::Socket::INET6;
+       };
+
+       if ($@) {
+               dbg($@);
+               require IO::Socket;
+               $io_socket = 'IO::Socket::INET';
+       } else {
+               $io_socket = 'IO::Socket::INET6';
+       }
+       $io_socket->import;
+
        if ($@ || $main::is_win) {
-               $blocking_supported = IO::Socket->can('blocking') ? 2 : 0;
+               $blocking_supported = $io_socket->can('blocking') ? 2 : 0;
        } else {
-               $blocking_supported = IO::Socket->can('blocking') ? 2 : 1;
+               $blocking_supported = $io_socket->can('blocking') ? 2 : 1;
        }
 
 
@@ -69,12 +79,12 @@ BEGIN {
        # defines EINPROGRESS as 10035.  We provide it here because some
        # Win32 users report POSIX::EINPROGRESS is not vendor-supported.
        if ($^O eq 'MSWin32') { 
-               eval '*EINPROGRESS = sub { 10036 };';
-               eval '*EWOULDBLOCK = *EAGAIN = sub { 10035 };';
-               eval '*F_GETFL     = sub {     0 };';
-               eval '*F_SETFL     = sub {     0 };';
-               eval '*IPPROTO_TCP     = sub {     6 };';
-               eval '*TCP_NODELAY     = sub {     1 };';
+               eval '*EINPROGRESS = sub { 10036 };' unless defined *EINPROGRESS;
+               eval '*EWOULDBLOCK = *EAGAIN = sub { 10035 };' unless defined *EWOULDBLOCK;
+               eval '*F_GETFL     = sub {     0 };' unless defined *F_GETFL;
+               eval '*F_SETFL     = sub {     0 };' unless defined *F_SETFL;
+               eval 'sub IPPROTO_TCP  {     6 };';
+               eval 'sub TCP_NODELAY  {     1 };';
                $blocking_supported = 0;   # it appears that this DOESN'T work :-(
        } 
 }
@@ -182,6 +192,21 @@ sub pid_gone
        }
 }
 
+sub ax25
+{
+       my $conn = shift;
+       return $conn->{csort} eq 'ax25';
+}
+
+sub peerhost
+{
+       my $conn = shift;
+       $conn->{peerhost} ||= 'ax25' if $conn->ax25;
+       $conn->{peerhost} ||= $conn->{sock}->peerhost if $conn->{sock} && $conn->{sock}->isa('IO::Socket::INET');
+       $conn->{peerhost} ||= 'UNKNOWN';
+       return $conn->{peerhost};
+}
+
 #-----------------------------------------------------------------
 # Send side routines
 sub connect {
@@ -196,25 +221,31 @@ sub connect {
        $conn->{peerport} = $to_port;
        $conn->{sort} = 'Outgoing';
        
-    # Create a new internet socket
-    my $sock = IO::Socket::INET->new();
-    return undef unless $sock;
-       
-       my $proto = getprotobyname('tcp');
-       $sock->socket(AF_INET, SOCK_STREAM, $proto) or return undef;
-       
-       blocking($sock, 0);
-       $conn->{blocking} = 0;
+       my $sock;
+       if ($blocking_supported) {
+               $sock = $io_socket->new(PeerAddr => $to_host, PeerPort => $to_port, Proto => 'tcp', Blocking =>0) or return undef;
+       } else {
+               # Create a new internet socket
+               $sock = $io_socket->new();
+               return undef unless $sock;
 
-       # does the host resolve?
-       my $ip = gethostbyname($to_host);
-       return undef unless $ip;
-       
-       my $r = connect($sock, pack_sockaddr_in($to_port, $ip));
-       return undef unless $r || _err_will_block($!);
+               my $proto = getprotobyname('tcp');
+               $sock->socket(AF_INET, SOCK_STREAM, $proto) or return undef;
+
+               blocking($sock, 0);
+               $conn->{blocking} = 0;
+
+               # does the host resolve?
+               my $ip = gethostbyname($to_host);
+               return undef unless $ip;
+
+               my $r = connect($sock, pack_sockaddr_in($to_port, $ip));
+               return undef unless $r || _err_will_block($!);
+       }
        
        $conn->{sock} = $sock;
-    
+       $conn->{peerhost} = $sock->peerhost;    # for consistency
+
     if ($conn->{rproc}) {
         my $callback = sub {$conn->_rcv};
         set_event_handler ($sock, read => $callback);
@@ -228,7 +259,7 @@ sub start_program
        my $pid;
        
        local $^F = 10000;              # make sure it ain't closed on exec
-       my ($a, $b) = IO::Socket->socketpair(AF_UNIX, SOCK_STREAM, PF_UNSPEC);
+       my ($a, $b) = $io_socket->socketpair(AF_UNIX, SOCK_STREAM, PF_UNSPEC);
        if ($a && $b) {
                $a->autoflush(1);
                $b->autoflush(1);
@@ -299,7 +330,7 @@ sub disconnect
 
        if (defined($sock)) {
                set_event_handler ($sock, read => undef, write => undef, error => undef);
-               shutdown($sock, 3);
+               shutdown($sock, 2);
                close($sock);
        }
        
@@ -427,7 +458,7 @@ sub new_server {
     my ($pkg, $my_host, $my_port, $login_proc) = @_;
        my $self = $pkg->new($login_proc);
        
-    $self->{sock} = IO::Socket::INET->new (
+    $self->{sock} = $io_socket->new (
                                           LocalAddr => "$my_host:$my_port",
 #                                          LocalPort => $my_port,
                                           Listen    => SOMAXCONN,
@@ -490,10 +521,10 @@ sub _rcv {                     # Complement to _send
     return unless defined($sock);
 
        my @lines;
-       if ($conn->{blocking}) {
-               blocking($sock, 0);
-               $conn->{blocking} = 0;
-       }
+#      if ($conn->{blocking}) {
+#              blocking($sock, 0);
+#              $conn->{blocking} = 0;
+#      }
        $bytes_read = sysread ($sock, $msg, 1024, 0);
        if (defined ($bytes_read)) {
                if ($bytes_read > 0) {