2012-03-31 17 views
8

Ostatnio pracowałem nad budowaniem serwera TCP za pomocą PHP (wiem, że to zły wybór, ale to jest standard pracy), więc dotarłem do punktu, w którym jest niezawodny prototyp do przeprowadzania testów na nim i pokazał dobre wyniki. na początku użyłem funkcji gniazda do obsługi połączenia dla serwera i działało dobrze, ale jedną z głównych rzeczy w projekcie jest zapewnienie bezpieczeństwa kanału, więc przełączyłem się na stream_socket.Jak sprawdzić, czy połączenie jest resetowane przez peer w php?

to, czego chcę, to odpowiednik socket_last_error w grupie stream_socket, dzięki czemu mogę wiedzieć, kiedy połączenie z klientem jest zamknięte lub nie. bieżąca sytuacja wszystkie procesy będą czekać na timeout timer, aby zwolnić nawet wtedy, gdy klient jest już zamknięty.

Przeszukałem sieć i odkryłem, że nie ma sposobu, aby dowiedzieć się o tym za pośrednictwem PHP i odkryłem, że niektórzy ludzie otworzyli zgłoszenie problemu, prosząc o odpowiednik socket_last_error dla strumienia. https://bugs.php.net/bug.php?id=34380

więc czy jest i tak wiadomo, kiedy sygnał FIN_WAIT zostanie podniesiony, czy nie?

Dziękuję

Odpowiedz

1

Nie sądzę, że to możliwe rodzina stream_socket, wygląda na to, że to zbyt wysoki poziom.

Próbowałem podejmowania bardzo hackish rozwiązanie, nie wiem, czy to będzie działać dla ciebie, to nie jest bardzo wiarygodne:

<?php 
set_error_handler('my_error_handler'); 

function my_error_handler($no,$str,$file,$line) { 
    throw new ErrorException($str,$no,0,$file,$line); 
} 

$socket = stream_socket_server("tcp://0.0.0.0:8000", $errno, $errstr); 
if (!$socket) { 
    echo "$errstr ($errno)\n"; 
} else { 
    while ($conn = stream_socket_accept($socket)) { 
    foreach (str_split('The local time is ' . date('n/j/Y g:i a') . "\n") as $char) { 
     echo $char; 
     try { 
      fwrite($conn,$char); 
     } catch (ErrorException $e) { 
      if (preg_match("/^fwrite\(\): send of 1 bytes failed with errno=([0-9]+) ([A-Za-z \/]+)$/",$e->getMessage(), $matches)) { 
        list($errno,$errstr) = array((int) $matches[1], $matches[2]); 
        if ($errno === 32) { 
          echo "\n[ERROR] $errstr"; // Broken pipe 
        } 
      } 
      echo "\n[ERROR] Couldn't write more on $conn"; 
      break; 
     } 
     fflush($conn); 
    } 
    fclose($conn); 
    } 
    fclose($socket); 
} 
echo "\n"; 
?> 

wprowadzenia: php ./server.php

połączenie: nc localhost 8000 | head -c1

Wyjście serwera:

The loca 
[ERROR] Broken pipe 
[ERROR] Couldn't write more on Resource id #6 
+0

Dziękuję Janus za odpowiedź, ale. jak wiesz, nie jest możliwe, aby hałasować strumieniem, wysyłając dane, aby zobaczyć, kiedy jest on zepsuty, czy też obecna sytuacja jest taka, że ​​serwer czeka na działania klienta, więc z tym co sugerujesz, nie wydaje mi się to możliwe? – user1304594

Powiązane problemy