Perl IO::Socket::INET сбивает с толку Ошибка недопустимого аргумента

Рассмотрим следующий фрагмент Perl-скрипта:

use IO::Socket;
# ...
my $sock = IO::Socket::INET->new(
    PeerAddr => $host, # e.g. "google.com"
    PeerPort => $port, # e.g. 80
    Proto => 'tcp'
);
die("no socket: $!") unless $sock;
# ...

В нормальных условиях все работает, как и ожидалось, но когда интернет-соединение хост-системы неактивно, переменная «sock» пуста, а $! имеет сообщение «Недопустимый аргумент».

Я неправильно использую конструктор INET или это ожидаемое поведение? Если последнее, есть ли способ отличить ошибку «неактивный сетевой интерфейс» от подлинного недопустимого аргумента метода конструктора?


person maerics    schedule 23.05.2011    source источник
comment
@ikegami: к сожалению, ни Perl 5.8.9 в Mac OS 10.6.7, ни Perl 5.10.1 в Linux 2.6.35 (Ubuntu 10.10) не имеют $^E отличного от $! для этой ошибки.   -  person maerics    schedule 23.05.2011
comment
Тогда извините, это вся информация, которую предоставляет система. А может где-то не хватает проверки ошибок, а реальная ошибка заменяется бесполезной.   -  person ikegami    schedule 23.05.2011


Ответы (1)


Вы видите «Недопустимый аргумент», потому что конструктор пытается разрешить имя хоста, получает ошибку и возвращает EINVAL в $!. Если бы вы использовали IP-адрес в $host, вы бы увидели настоящую ошибку «Сеть недоступна».

Кроме того, IO::Socket::INET устанавливает $@ для уточнения ошибки, возвращенной в $!, поэтому, если вы напечатаете $@, а также $!, вы увидите "Неверное имя хоста 'google.com'", что, вероятно, является даже лучшей диагностикой, чем "Сеть недоступна". get с IP-адресом вместо имени хоста. В обоих случаях должно быть сразу понятно, что происходит.

person Grrrr    schedule 23.05.2011