0

I am using the following code. I want to timeout and close the connection after 20 seconds, tried with alarms but nothing worked. Here is my code:

my $socket_resp = IO::Socket::INET->new(Blocking => 0, LocalPort => $comm_port, Proto => 'udp', Timeout => 2);
    $socket_resp->setsockopt(SO_RCVTIMEO, SO_RCVTIMEO, 10);
    print "Waiting for Response On Port $comm_port\n";
    while (my $recieved_data = $socket_resp->getline()) {
        chomp($recieved_data);
        print "$recieved_data\n";
        if ($recieved_data =~ m/^done/i) {
            last;
        }
    }

    $socket_resp->close();
  • 1
    Did you try: [How to get IO::Socket::INET timeout after X seconds?](http://stackoverflow.com/questions/3570440/perl-how-to-get-iosocketinet-timeout-after-x-seconds) – matthias krull Jul 17 '12 at 12:28
  • 2
    Do you want a total socket lifespan of at most 20 seconds, or a patience of 20 seconds for *each* `getline()` call? – pilcrow Jul 17 '12 at 13:23
  • You might want to [go back trough your questions](http://stackoverflow.com/users/1065000/user1065000?tab=questions) and [accept answers](http://stackoverflow.com/faq#howtoask) that have helped you. – simbabque Jul 17 '12 at 14:47

1 Answers1

0

Wrapping your entire read loop in an alarm, as suggested in the other question will very likely do what you want. You don't show us code, so we don't know why your previous attempts failed.

That said, SO_RCVTIMEO can be made to work, too, albeit a bit differently.

You want a blocking rather than non-blocking socket in this case. You also want to setsockopt correctly, which requires SOL_SOCKET and pack()ing a struct timeval:

my $s = IO::Socket::INET->new(Proto => 'udp', ...);            # N.B.: blocking
$s->setsockopt(SOL_SOCKET, SO_RCVTIMEO, pack('l!l!', 20, 0));  # N.B.: pack()
while (<$s>) {
  ...
}

Now, the above waits 20 seconds for each underlying call to read(), which may be more than the number of lines returned to your application. That is, if I send your application "foo\n" in one datagram and then nothing, you'll timeout after 20 seconds. However, I might send "f", then wait 19 seconds, "o", then wait 19 seconds, "o", then wait 19 seconds, ... you get the idea.)

Community
  • 1
  • 1
pilcrow
  • 56,591
  • 13
  • 94
  • 135