3 votes

L'application C# WPF s'est figée au fil du temps

J'ai construit une application C# WPF qui comporte plusieurs threads en arrière-plan effectuant les tâches suivantes :

  1. Plusieurs threads où chacun contient un serveur TCP tournant dans une boucle while et chacun d'eux attend juste un message d'un port spécifique
  2. Un thread surveille constamment un port USB pour un périphérique d'E/S
  3. Un thread acquiert des données à partir d'un périphérique Microsoft Kinect
  4. Un thread répartiteur de timer effectuant des mises à jour basées sur des "drapeaux" (ou variable globale statique) activés par un autre thread.

Un exemple :

    Thread thread = new Thread(new ThreadStart(Server));
    private static void Server()
    {
        try
        {
            IPAddress ipAd = IPAddress.Parse("192.168.1.119");
            // utilisez l'adresse IP locale de la machine,
            // et utilisez la même chose dans le client

            /* Initialise le listener */
            TcpListener myList = new TcpListener(ipAd, 8003);

            /* Commence à écouter sur le port spécifié */
            myList.Start();

            System.Diagnostics.Debug.Write("Le serveur fonctionne sur le port 8003...");
            System.Diagnostics.Debug.Write("Le point de terminaison local est  :" +
                              myList.LocalEndpoint);
            System.Diagnostics.Debug.Write("En attente d'une connexion.....");

            Socket s = myList.AcceptSocket();
            System.Diagnostics.Debug.Write("Connexion acceptée de " + s.RemoteEndPoint);

            byte[] b = new byte[100];
            k = s.Receive(b);
            Console.WriteLine("Reçu...");

            string temp = "";
            for (int i = 0; i < k; i++)
            {
                System.Diagnostics.Debug.Write(Convert.ToChar(b[i]));
                temp += Convert.ToChar(b[i]);
            }

            ASCIIEncoding asen = new ASCIIEncoding();
            s.Send(asen.GetBytes("La chaîne a été reçue par le serveur."));
            System.Diagnostics.Debug.Write("\nEnvoi de l'accusé de réception");
            /* nettoyage */
            s.Close();
            myList.Stop();

            if (k > 0)
            {
                cont = true;
                k = 0;
            }
        }
        catch (Exception e)
        {
            Console.WriteLine("Erreur..... " + e.StackTrace);
        }    
    }

Le problème que j'ai rencontré est que parfois l'application se fige simplement et je ne peux pas y accéder du tout. Le thread principal de l'interface utilisateur se fige également, et je ne peux pas arrêter le programme même à partir du gestionnaire de tâches dans Windows. Normalement, l'application fonctionne parfaitement, mais le problème apparaîtra de façon aléatoire après avoir utilisé l'application pendant de longues heures (par exemple, 4 à 5 heures)

L'ordinateur que j'utilise n'est pas un PC haut de gamme avec seulement 2 Go de RAM et un CPU AMD dual core.

Mon hypothèse sur le problème peut être la suivante :

  1. Mémoire insuffisante (ou fuite de mémoire quelque part, mais Windows fonctionne bien et seul le programme se fige)
  2. Embouteillage réseau (c'est-à-dire un blocage quelque part, mais cela ne semble pas probable avec une application d'envoi et de réception simple)
  3. Échec d'établissement de connexion avec les périphériques USB (y compris Kinect)

Cependant, je ne suis toujours pas sûr de comment résoudre le problème. Je suis peut-être encore assez nouveau dans l'implémentation, donc j'aimerais entendre des commentaires d'experts en C# WPF, en réseau et en applications multithread pour m'aider ici. Merci.

0voto

Zipper Points 1753

La façon la plus facile de déboguer cela est de joindre un débogueur (Visual Studio peut le faire). Ensuite, regardez ce que les threads font. Pour utiliser VS pour déboguer, allez à Déboguer -> Joindre au processus et sélectionnez votre processus. Si cela ne fonctionne pas, vous pouvez essayer de vider le processus en utilisant le gestionnaire de tâches (si vous avez Windows 7 ou supérieur), il suffit de cliquer avec le bouton droit sur le processus et sélectionner Créer un fichier de vidage. Ensuite, vous pouvez faire une analyse hors ligne du fichier en utilisant windbg ou VS. Le plus utile que vous voudrez examiner est ce que les threads font quand il est bloqué. Ce sont normalement les meilleures premières étapes pour ce type de problème.

0voto

Boas Enkler Points 2258

Dans Visual Studio, il existe un visualiseur de concurrence

Je l'utiliserais (je pense que c'est disponible depuis VS 2010. Il peut également être attaché à un processus externe (comme le débogueur Visual Studio).

Vous pourriez également envisager d'utiliser des outils comme le Profiler de performances de redgate

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X