2012-08-06 14 views
14

Nie mogę znaleźć niczego, co podpowie mi, czy port w routerze jest otwarty, czy nie. Czy to możliwe?Sprawdź, czy port jest otwarty.

kod mam teraz tak naprawdę nie wydają się działać ...

private void ScanPort() 
{ 
    string hostname = "localhost"; 
    int portno = 9081; 
    IPAddress ipa = (IPAddress) Dns.GetHostAddresses(hostname)[0]; 
    try 
    { 
     System.Net.Sockets.Socket sock = 
       new System.Net.Sockets.Socket(System.Net.Sockets.AddressFamily.InterNetwork, 
               System.Net.Sockets.SocketType.Stream, 
               System.Net.Sockets.ProtocolType.Tcp); 
     sock.Connect(ipa, portno); 
     if (sock.Connected == true) // Port is in use and connection is successful 
      MessageBox.Show("Port is Closed"); 
     sock.Close(); 
    } 
    catch (System.Net.Sockets.SocketException ex) 
    { 
     if (ex.ErrorCode == 10061) // Port is unused and could not establish connection 
      MessageBox.Show("Port is Open!"); 
     else 
      MessageBox.Show(ex.Message); 
    } 
} 
+0

Jak to się nie udaje? Czy wyniki nie są zgodne z oczekiwaniami, czy otrzymujesz wyjątek? – TheEvilPenguin

+0

także, jeśli twój kod łączy się z portem, to znaczy, że port jest otwarty, nie jest zamknięty –

+0

@TheEvilPenguin Chcę, aby powiedział, że mój port jest otwarty, ponieważ przekazałem go w moim routerze, ale nie udało się połączyć ... –

Odpowiedz

23

Spróbuj tego:

using(TcpClient tcpClient = new TcpClient()) 
{ 
    try { 
     tcpClient.Connect("127.0.0.1", 9081); 
     Console.WriteLine("Port open"); 
    } catch (Exception) { 
     Console.WriteLine("Port closed"); 
    } 
} 

Powinieneś raczej zmienić coś podobnego do 127.0.0.1 192.168.0.1 lub jakikolwiek jest twój adres IP routera.

+0

To nadal nie działa działa, jeśli używam 192.168.1.1 –

+0

, co się stanie, gdy spróbujesz użyć kodu? –

+0

Mówi, że nie może się połączyć, nawet jeśli port jest otwarty. –

2

Jeśli łączysz się z loopback adapterlocalhost lub 127.0.0.1 (there's no place like 127.0.0.1!), jesteś mało prawdopodobne, aby kiedykolwiek wychodzić do routera. System operacyjny jest wystarczająco inteligentny, aby rozpoznać, że jest to specjalny adres. Dunno, jeśli to również jest prawdą, jeśli rzeczywiście określasz "prawdziwy" adres IP swojego komputera.

Zobacz też to pytanie: What is the purpose of the Microsoft Loopback Adapter?

Należy również zauważyć, że działa traceroute localhost (tracert localhost w systemie Windows) pokazuje, że jedynym węzłem sieci zaangażowany jest własne maszyny. Router nigdy nie jest zaangażowany.

1

Port do przodu routera nie może być testowany z poziomu sieci LAN, należy połączyć się ze strony WAN (internet), aby sprawdzić, czy port działa poprawnie.

Kilka stron internetowych oferują usługi, aby sprawdzić, czy port jest otwarty:

What's My IP Port Scanner

GRC | ShieldsUP!

Jeśli chcesz skontaktować się z własnym kodem, to trzeba upewnić się, że TCP/Połączenie IP jest przekierowywane przez zewnętrzny serwer proxy lub konfigurowanie tunelu. To nie ma nic wspólnego z kodem, to podstawową obsługą sieci 101.

12

Lepszym rozwiązaniem, gdzie można nawet określić timeout:

bool IsPortOpen(string host, int port, TimeSpan timeout) 
{ 
    try 
    { 
     using(var client = new TcpClient()) 
     { 
      var result = client.BeginConnect(host, port, null, null); 
      var success = result.AsyncWaitHandle.WaitOne(timeout); 
      if (!success) 
      { 
       return false; 
      } 

      client.EndConnect(result); 
     } 

    } 
    catch 
    { 
     return false; 
    } 
    return true; 
} 

A w F #:

let IsPortOpen (host: string, port: int, timeout: TimeSpan): bool = 
    let canConnect = 
     try 
      use client = new TcpClient() 
      let result = client.BeginConnect(host, port, null, null) 
      let success = result.AsyncWaitHandle.WaitOne(timeout) 
      match success with 
      | false -> false 
      | true -> 
        client.EndConnect(result) 
        true 
     with 
     | _ ->(); false 
    canConnect 
+0

Jak wydajna jest ta metoda? Zwłaszcza w F #? Pracuję nad tezą dotyczącą protokołu sieciowego, a częścią (wstępnego) procesu jest skomponowanie listy dostępnych portów. – czifro

+0

powinno być tak wydajne jak C# jeden ... ale zmierzyć go na wszelki wypadek? – ympostor

+0

czy ten sam wzór może być użyty dla System.Net.Sockets.UdpClient? – tatmanblue

2

Jest nie wiadomo, czy port zostanie przekazany na routerze, chyba że w tym porcie jest program nasłuchujący.

Jak można zauważyć w odpowiedzi Clinton, używaną klasą .Net jest TcpClient, a to dlatego, że do połączenia używasz gniazda TCP. W ten sposób systemy operacyjne tworzą połączenia: za pomocą gniazd. Jednak router tylko przekazuje pakiety (warstwa 3 modelu OSI) do lub z zewnątrz. W twoim przypadku to, co ruter wykonuje, nazywa się: NAT. Jest to jeden publiczny adres IP współużytkowany przez jedno lub więcej prywatnych adresów IP. Właśnie dlatego robisz przekierowanie portu.

Na ścieżce pakietów może znajdować się wiele routerów i nigdy nie wiadomo, co się stało.

Wyobraźmy sobie, że wysyłasz list w tradycyjny sposób. Być może możesz napisać w liście, że odbiorca musi ci odpowiedzieć, abyś mógł sprawdzić, czy on tam jest (ty i odbiornik są gniazdami).Jeśli otrzymasz odpowiedź, będziesz pewny, że on/ona tam jest, ale jeśli nie otrzymasz niczego, czego nie wiesz, jeśli listonosz (w twoim przypadku router) zapomniał dostarczyć list, lub odbiornik nie był odpowiedział. Nigdy też nie dowiedziałbyś się, czy listonosz poprosił znajomego o dostarczenie tego listu. Ponadto listonosz nie otworzy listu, aby wiedzieć, że może odpowiedzieć, ponieważ czekasz na odpowiedź. Wszystko, co możesz zrobić, to trochę poczekać, aby otrzymać odpowiedź. Jeśli nie otrzymasz niczego w tym okresie, założysz, że odbiorcą nie jest to, że wysłałeś list. To jest "timeout".

Widziałem odpowiedź, w której wymieniono oprogramowanie nmap. Jest naprawdę bardzo dobry i złożony miękki, ale myślę, że będzie działał w ten sam sposób. Jeśli nie ma aplikacji nasłuchującej w tym porcie, nie ma możliwości sprawdzenia, czy jest otwarta, czy nie.

Proszę, daj mi znać, gdybym był jasny.