Problème pour décoder la réponse d'une commande AT

Bonjour à tous
Pourriez-vous m'aider à terminer mon projet qui consiste en un petit modem GPRS qui permet d'envoyer de alarmes provenant une petit contrôleur genre Zélio, et de commander l'arrêt et le redémarrage des alarmes à distance

Matériel utilisé: UNO sur 1.0.5+ shield GPRS Geek-on fire acheté chez Mc Hobby
Coté matériel, rien à reprocher, très fiable , j'en ai un qui fonctionne avec le même genre de programme qui celui qui est joint, et pas de problème . Par contre, il me reste un problème important à régler qui est la gestion de réseau. smiley-kiss

En effet, le sketch proposé par GOF ne permet pas de détecter la perte de réseau, et donc si le GPRS décroche deu réseau, on perd le contact, et aucun possibilité de se rebrancher , sauf de se rendre sur place pour rebooter le système.

C'est pourquoi j'ai essayé de faire la même application avec la librairie GOGPRS, mais j'ai du abandonner , car elle n'est pas stable, et , il n'y à pas de réelle gestion du réseau contrairement à ce qu pourrait laisser croire le titre des exemples.

C'est ici que je demanderai l'aide des spécialistes.

La commande AT+CREG permet de savoir si le module est enregistré sur le réseau ou non .
Si le message retourné est ( +creg 0 , 1), réseau OK
si ( +creg 0 , 2), pas de réseau .

Je lance donc toutes les X heures la commande " AT+CREG" qui selon la librairie sotwaresérial devrait retourner ( +creg 0 , 1) dans la variable "msg " .

Seulement je n'arrive pas à décoder le retour du message, et la variable "msg" reste vide

j'ai aussi le même problème avec le retour du module pour confirmer que le message est bien parti, que je n'arrive pas à décoder

Pourriez-vous m'aider pour cette partie ?

voici le code en fichier joint car sinon , trop de caractères (je sais, je suis bavard)

un grand merci d'avance

modem_21_oct_2013.ino (14.3 KB)

Salut,

Je comprend pas ton code, je pense que la partie qui nous interesse c'est celle ci :

  if ((MillisSeconde - TempSeconde) > 40)
  {
  ClearGprsMsg();
  modemSerial.println("AT+CMGD=0,4");
  modemSerial.println("AT+CREG?");
  delay(1000);
  Serial.print("\tmessage\t");
  Serial.println(msg);
   if( msg==("+CREG: 0,1"))
   //if( msg==("OK"))
   {
          ReseauOk=1;
   }
   else
   {
     ReseauOk=0;
   }
   countSmS8=0;  
   delay(100);
    temps = millis(); //on stocke la nouvelle heure
  }

Et la question à 1000$ est : comment veux-tu lire quelque chose avec un Serial.println() ??! En plus Software Serial n'a pas de buffer, il faut écouter en permanence sinon tout bit est perdu ! Donc pendant ton delay(1000) tout le monde s'est barré ...

Bonjour

Merci B@tto pour ta réponse

Oups la gaffe !!! je suppose que c'est sérial;read au lieu de Serial.println() . J'ai déjà tellement chipoté avec ce truc que j'ai du me tromper

J'ai aussi déjà fait des essais avec sérial read, mais ça ne marchait pas non plus , mais évidemment, si tout se sauve pendant le delay,
moi qui pensais bien faire en laissant le temps au module pour écrire
Et donc
si je supprime le delay, et mettant sérial read ça devrait fonctionner ?

J'ai aussi fait un essai avec le bout de programme ci-dessous , mais qu'il y ai du réseau ou pas, le moniteur me retourne 255 dans tous les cas ( ce bout de programme provient de " Capteur d’alerte par SMS | Téléfab)

merci de ton aide

 void reseauIndisponible() // Gère le réseau mobile
 
{
   modemSerial.print("AT+CREG=?"); // Demande de l'enregistrement sur le réseau
   while (!modemSerial.available());
   for (int i=0; i<21; i++) 
   {
   modemSerial.read();
 }
   //veille = modemSerial.read() != 49 and modemSerial.read() != 49; // Analyse du résultat
   while (modemSerial.read() != 44); // Jusqu'à la virgule ','
   
   reseau = modemSerial.read() != 49; // Analyse du résultat 
   if (reseau)
   {
     Serial.println("*** Reseau disponible ***");
     ReseauOk=1;
   }
   else
   {
     ReseauOk=0;
   }
   
}

Je comprend pas pourquoi tu veux réinventer la roue alors que le code d'origine de telefab.fr est bon :

void reseauIndisponible() // Gère le réseau mobile {
GPRS.print("AT+CREG?\r\n"); // Demande de l'enregistrement sur le réseau
while (!GPRS.available());
while (GPRS.read() != 44); // Jusqu'à la virgule ','
veille = GPRS.read() != 49; // Analyse du résultat : ‘1’ ou pas
}
for (int i=0; i<21; i++) 
   {
   modemSerial.read();
 }

pourquoi une boucle à 21 itérations ??! :

le programme de Telefab ne fonctionne pas au niveau de la détection de réseau

lorsque on lit le contenu de la variable veille, ell renvoie 255

Au niveau de la boucle , j'ai repris une version non terminée du prg téléfab , et il ne faut donc pas tenir compte de la boucle à 21 itérations

Reposte alors le code exact ...

Voila le code en annexe

lorsque je lance le void reseau disponible, le programme s'arrete

merci d'avance

modem_sinsin_21_oct_2013.ino (13.5 KB)

Déjà ça : modemSerial.print("AT+CREG?");

c'est pas ça : modemSerial.print("AT+CREG?\r\n");

O k, mais quand on lance modemSerial.print("AT+CREG?\r\n"); la commande ne part pas , tandis que l'autre part

casper22:
lorsque on lit le contenu de la variable veille, ell renvoie 255

justement... veille est dans ce cas un boolean. et pour un boolean, si false vaut 0, true vaut 255.

du coup, après la ligne

veille = GPRS.read() != 49; // Analyse du résultat : ‘1’ ou pas

veille contient le résultat du test GPRS.read() != 49, si elle est à 255, c'est que le test est vrai, c-à-d que GPRS.read() est différent de 49, et 49 est le code du caractère "1".