Сокет Perl как (псевдо) разрыв http сервера с запросом ftp! - PullRequest
1 голос
/ 21 июня 2011

Следующий код является (псевдо!) Http-сервером. Он просто отправляет запрос http.
Неожиданный компортирование происходит с ftp-запросами из браузера, например ftp://localhost:8888/. При этом браузер подключается и остается на связи всегда.

Я не понимаю, что происходит!
Как я могу контролировать это поведение и игнорировать запросы ftp?

#!/usr/bin/perl
use strict;
use Socket; 
use Fcntl qw(F_GETFL F_SETFL O_NONBLOCK);
use IO::Poll;

local *S;
socket      (S, PF_INET   , SOCK_STREAM , getprotobyname('tcp')) || die "socket: $!\n";
setsockopt (S, SOL_SOCKET, SO_REUSEADDR, 1) || die "setsockopt: $!\n";
bind        (S, sockaddr_in(8888, INADDR_ANY)) || die "bind: $!\n";
listen      (S, 10) || die "listen: $!\n";
fcntl(S, F_SETFL, fcntl(S, F_GETFL, 0) | O_NONBLOCK) || die "fcntl: $!\n";

my $poll=IO::Poll->new;
$poll->mask(*S => POLLIN|POLLOUT);


while( 1 ) {
    $poll->poll();
    for my $reader ( $poll->handles(POLLIN ) ) {
        my $remote = accept (my $connection, $reader);
        my $bytes= sysread $connection,my $header,1024;

        if (defined $bytes) {
            if ($bytes == 0 || (index $header,"\r\n\r\n") < 0) {
                close $remote;
                next;
            } 
        } else {
            close $connection;
            next;
        }

        syswrite $connection,"HTTP/1.1 200 OK\r\n\r\n".$header;
        close $connection;
     }
}

1 Ответ

4 голосов
/ 21 июня 2011

В отличие от HTTP, FTP начинается с того, что сервер отправляет приветствие клиенту. В этом случае клиент, думая, что он разговаривает с FTP-сервером, ожидает FTP-приветствия, в то время как сервер, думая, что он разговаривает с HTTP-клиентом, ждет, пока он отправит команду HTTP.

Решение состоит в том, чтобы установить тайм-аут для клиентского сокета ($connection) перед попыткой sysread.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...