Envoi de plusieurs commandes au port série et attente de réponse avant d’en envoyer une autre

la programmation


Salut tout le monde,

demandez de l’aide sur les données du port série reçues.

J’ai un fichier stockant plusieurs commandes.
Je dois envoyer la commande une par une au port série et attendre la réponse et l’affichage pour continuer à envoyer l’autre commande.

J’utilise thread.sleep entre chaque envoi de commande mais ça ne marche pas.

s’il vous plaît, aidez-moi.

Merci

Ce que j’ai essayé :

I'm using thread.sleep between each command send but it does not work. 

Solution 1

Arrêtez de jouer avec Thread.Sleep : cela ne vous aidera probablement pas.
La façon dont je procéderais serait de configurer une file d’attente de commandes et d’utiliser l’événement DataReceived pour obtenir la réponse. Lorsque la réponse est terminée, retirez la commande suivante de la file d’attente, envoyez-la et laissez l’événement DataReceived traiter sa réponse lorsqu’elle arrive.
Lorsque la file d’attente est vide, l’ensemble des commandes est complet.

Solution 2

En général, toutes les opérations d’E/S asynchrones doivent être effectuées dans leurs propres threads pour éviter de bloquer l’application. Sinon, vous aurez des retards dans l’interface graphique ou l’interface graphique sera complètement bloquée dans le pire des cas.

Dans votre cas, vous auriez besoin d’au moins un thread pour recevoir les réponses et transmettre les commandes en file d’attente.

Le thread de réception doit mettre les données en mémoire tampon jusqu’à ce qu’une réponse complète soit reçue. La manière de procéder dépend des données (par exemple saut de ligne avec des données texte ou après réception du nombre d’octets annoncé dans un en-tête de protocole).

Une fois qu’une réponse complète a été reçue, elle est signalée aux autres threads. Dans votre cas, ce sera le thread principal (GUI) pour afficher la réponse et la file d’attente de transmission pour permettre l’envoi de la commande suivante. Notez que la transmission de données d’un thread aux éléments de l’interface graphique nécessite un traitement spécial.

Le thread de transmission peut simplement envoyer en utilisant un appel bloquant car il doit de toute façon attendre. Après l’envoi, il doit attendre le signal de réponse reçu.

Vous pouvez regrouper l’envoi et la réception dans un ou deux threads.

Pseudo-code pour la réception (en supposant des données texte) :

C#
// Check for kill (terminate thread) event (wait with no timeout)
while (!KillEvent)
{
    do 
    {
        // Blocking call until a character is available
        // Should have a timeout and corresponding handling (break here)
        rxChar = ReceiveChar();
        Buffer += rxChar;
    }
    while (rxChar != '\n');
    // Signal other threads that a response has been received
    // Pass a copy of Buffer to the main thread for display
}

Dans le thread de transmission, après avoir envoyé une commande, appelez ce qui précède ou attendez l’événement lorsque la réception est effectuée dans un propre thread.

Utiliser des fils de discussion et des événements que vous évitez d’appeler sleep ce qui doit généralement être évité et garantir qu’aucun temps système n’est perdu.

Solution 3

Mon SerialDevice cours ici :
Communication multithread pour les interfaces GPIB/Visa/Série[^]

implémente exactement le processus décrit dans la Solution2 ci-dessus : avec les commandes asynchrones, les E/S sont effectuées dans un thread séparé qui utilise de simples appels de blocage pour l’écriture/lecture.

Un commentaire sur la solution 1 : l’événement DataReceived est appelé sur un thread non-UI, vous devez donc de toute façon apprendre quelque chose sur le threading si vous souhaitez l’utiliser (par exemple, le gestionnaire DataReceived peut appeler un rappel synchronisé pour éviter les problèmes avec les champs partagés ou composants de l’interface utilisateur).

Solution 4

Entre-temps, j’ai trouvé une solution sans utiliser le gestionnaire DataReceived.
Écrivez simplement la commande sur le port série, puis lisez la réponse du port série après l’écriture.
et cela fonctionne selon ce que je recherche.

Mais je ne sais pas si c’est la bonne façon de procéder.
Exemple:
Écrire();
Lire();

コメント

タイトルとURLをコピーしました