Il existe de nombreuses façons d'écrire un protocole série en fonction des fonctionnalités que vous souhaitez et du niveau de vérification des erreurs dont vous avez besoin.
Certaines des choses courantes que vous voyez dans les protocoles point à point sont:
Fin du message
Les protocoles ASCII les plus simples ont juste une séquence de caractères de fin de message, souvent \r
ou \n
comme c'est ce qui est imprimé lorsque la touche Entrée est enfoncée. Les protocoles binaires peuvent utiliser 0x03
ou un autre octet commun.
Début du message
Le problème avec la fin du message est que vous ne savez pas quels autres octets ont déjà été reçus lorsque vous envoyez votre message. Ces octets seraient alors préfixés au message et provoqueraient une mauvaise interprétation. Par exemple, si l'Arduino vient de se réveiller, il peut y avoir des ordures dans le tampon série. Pour contourner cela, vous avez un début de séquence de messages. Dans votre exemple ^
, dans les protocoles binaires, souvent0x02
Vérification des erreurs
Si le message peut être corrompu, nous avons besoin d'une vérification d'erreur. Cela pourrait être une somme de contrôle ou une erreur CRC ou autre chose.
Caractères d'échappement
Il se peut que la somme de contrôle s'ajoute à un caractère de contrôle, tel que l'octet «début de message» ou «fin de message», ou que le message contienne une valeur égale à un caractère de contrôle. La solution est d'introduire un caractère d'échappement. Le caractère d'échappement est placé avant un caractère de contrôle modifié afin que le caractère de contrôle réel ne soit pas présent. Par exemple, si un caractère de début est 0x02, en utilisant le caractère d'échappement 0x10, nous pouvons envoyer la valeur 0x02 dans le message comme paire d'octets 0x10 0x12 (caractère de contrôle XOR octet)
Numéro de paquet
Si un message est corrompu, nous pourrions demander un renvoi avec un message nack ou retry, mais si plusieurs messages ont été envoyés, seul le dernier message peut être renvoyé. Au lieu de cela, le paquet peut recevoir un numéro qui se renouvelle après un certain nombre de messages. Par exemple, si ce nombre est 16, le périphérique émetteur peut stocker les 16 derniers messages envoyés et s'il y en a un endommagé, le périphérique récepteur peut demander un renvoi en utilisant le numéro de paquet.
Longueur
Souvent, dans les protocoles binaires, vous voyez un octet de longueur qui indique au périphérique récepteur le nombre de caractères dans le message. Cela ajoute un autre niveau de vérification d'erreur comme si le nombre correct d'octets n'était pas reçu, il y avait alors une erreur.
Spécifique à l'Arduino
Lors de l'élaboration d'un protocole pour Arduino, la première considération est la fiabilité du canal de communication. Si vous envoyez sur la plupart des supports sans fil, XBee, WiFi, etc., la vérification des erreurs et les tentatives sont déjà intégrées et donc inutile de les mettre dans votre protocole. Si vous envoyez un RS422 sur quelques kilomètres, cela sera nécessaire. Les choses que j'inclurais sont le début du message et la fin des caractères du message, comme vous l'avez fait. Mon implémentation typique ressemble à ceci:
>messageType,data1,data2,…,dataN\n
La délimitation des parties de données par une virgule permet une analyse facile et le message est envoyé en ASCII. Les protocoles ASCII sont excellents car vous pouvez taper des messages dans le moniteur série.
Si vous voulez un protocole binaire, peut-être pour raccourcir la taille des messages, vous devrez implémenter l'échappement si un octet de données peut être le même qu'un octet de contrôle. Les caractères de contrôle binaire sont meilleurs pour les systèmes où le spectre complet de vérification d'erreur et de nouvelles tentatives est souhaité. La charge utile peut toujours être ASCII si vous le souhaitez.