2010-05-14 30 views
3

Je dois interroger un serveur, qui exécute un logiciel propriétaire, pour déterminer si ce service est en cours d'exécution. Utilisant wireshark, j'ai été en mesure de réduire le port TCP son utilisation, mais il semble que le trafic est crypté.Déterminez si un serveur écoute sur un port donné

Dans mon cas, il est fort à parier que si le serveur accepte les connexions (c'est-à-dire telnet serverName 1234) le service est en marche et tout est OK. En d'autres termes, je n'ai pas besoin d'effectuer de véritable échange de données, il suffit d'ouvrir une connexion et de la fermer en toute sécurité.

Je me demande comment je peux émuler ceci avec C# et Sockets. Ma programmation réseau se termine essentiellement avec WebClient, donc toute aide est vraiment appréciée.

Répondre

6

Le processus est en fait très simple.

using (var socket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp)) 
{ 
    try 
    { 
     socket.Connect(host, port); 
    } 
    catch (SocketException ex) 
    { 
     if (ex.SocketErrorCode == SocketError.ConnectionRefused) 
     { 
      // ... 
     } 
    } 
} 
+0

Y at-il un moyen d'ajuster le délai de connexion? Il semble échouer, mais seulement après environ une minute ... – Nate

+0

@Nate Je crois que c'est la durée du processus. Il n'y a pas d'option de délai de connexion. – ChaosPandion

+0

J'ai ajouté 'if (ex.SocketErrorCode == SocketError.ConnectionRefused || ex.SocketErrorCode == SocketError.TimedOut)' – Nate

0

Utilisez la classe TcpClient pour connecter le serveur.

3

Utilisez simplement TcpClient essayez de vous connecter au serveur, TcpClient.Connect lèvera une exception si la connexion échoue.

bool IsListening(string server, int port) 
{ 
    using(TcpClient client = new TcpClient()) 
    { 
     try 
     { 
      client.Connect(server, port); 
     } 
     catch(SocketException) 
     { 
      return false; 
     } 
     client.Close(); 
     return true; 
    } 
} 
+0

Y at-il un moyen d'ajuster le délai de connexion? Il semble échouer, mais seulement après environ une minute ... – Nate

2

J'ai utilisé le code suivant. Il y a une mise en garde ... dans un environnement de transaction élevé, les ports disponibles du client peuvent être épuisés car les sockets ne sont pas libérés par le système d'exploitation au même rythme qu'ils sont libérés par le code .NET.

Si quelqu'un a une meilleure idée, s'il vous plaît poster. J'ai vu des problèmes de boule de neige surgir où le serveur ne peut plus faire de connexions sortantes. Je travaille sur une meilleure solution ...

public static bool IsServerUp(string server, int port, int timeout) 
    { 
     bool isUp; 

     try 
     { 
      using (TcpClient tcp = new TcpClient()) 
      { 
       IAsyncResult ar = tcp.BeginConnect(server, port, null, null); 
       WaitHandle wh = ar.AsyncWaitHandle; 

       try 
       { 
        if (!wh.WaitOne(TimeSpan.FromMilliseconds(timeout), false)) 
        { 
         tcp.EndConnect(ar); 
         tcp.Close(); 
         throw new SocketException(); 
        } 

        isUp = true; 
        tcp.EndConnect(ar); 
       } 
       finally 
       { 
        wh.Close(); 
       } 
      } 
     } 
     catch (SocketException e) 
     { 
      LOGGER.Warn(string.Format("TCP connection to server {0} failed.", server), e); 
      isUp = false; 
     } 

     return isUp;