www.mikrocontroller.net

Forum: Mikrocontroller und Digitale Elektronik Antwort auf AT Befehl. Wie das Ende erkennen?


Autor: 0Fh (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo Forum,

nach langem googlen, weiß ich momentan nicht mehr weiter.
Ich schreibe gerade eine kleine Applikation, die mit verschiedenen 
Modems Verbindungen aufbauen soll. Dazu sende ich AT Befehle an das 
Modem. Nun habe ich folgendes Problem:

Bisher habe ich das Ende der Antwort auf einen AT Befehl daran erkannt, 
dass ich auf ein
<CR><LF>OK<CR><LF>, bzw. ein
<CR><LF>ERROR<CR><LF> gewartet habe.

Das Ganze ging bisher auch nur, weil ich mit +CMEE=0 dem Modem 
mitgeteilt habe, dass es mir keine Fehlercodes, sondern einfach nur 
"ERROR" ausgeben soll.

Nun gibt es jedoch noch weitere AT Befehle, die wiederum 
unterschiedliche Antworten liefern können. Auf einen Anruf (ATD<Nummer>) 
kann u. a. ein
<CR><LF>CONNECT<CR><LF> oder ein
<CR><LF>NO CARRIER<CR><LF> geliefert werden.

Ich denke das es hier noch viel mehr Antwortmöglichkeiten gibt, die ich 
noch nicht abdecken konnte, daher die Frage:

Hat jemand Erfahrung mit AT Befehlen und weiß evtl. wo es eine 
verlässliche Übersicht (am besten eine Spec.) gibt. In der alle 
Antwortmöglichkeiten abgedeckt werden, bzw. eine Idee wie ich das Ende 
einer Antwort auf einen AT Befehl erkennen kann?

Vielen Dank schon einmal!

Autor: Peter (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
im wiki zu AT-Befelssatz ist

http://www.iclinks.com/public_ftp/DocRelease/icl43...

verlinkt.

Autor: Ollz (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Allgemein (Ausnahme siehe unten) variieren AT-Befehle und die Antworten 
stark von Gerät zu Gerät. Deine beste Hoffnung ist es, genau für dein 
Gerät eine Befehlsliste zu bekommen.

Für einige Geräteklassen, zum Beispiel Mobiltelefone, hat sich die 
Industrie die Mühe gemacht, detailliertere Standards festzulegen und 
viele Hersteller halten sich sogar an die Standards. Solche Standards 
wären mein zweiter Ansatz um an Informationen zu kommen.

Mein dritter Ansatz wäre den Protokoll-Parser flexibel zu schreiben, so 
dass er zum Beispiel Antworten wie "CONNECT" <beliebige Zeichen> 
<CR><LF> versteht.

Autor: Arne (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Ich denke, dass der AT befehlssatz (soweit ich mich an mein Zyxel 1496E+ 
erinnern kann) auch herstellerspezifische Erweiterungen beinhaltet.
Warum empfängst Du nicht solange bis das zweite <LF> vom Modem 
eintrudelt?

Autor: 0Fh (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
@ Peter:
Werde mir den Link gleich anschauen. Vielen Dank schon Mal!

@ Ollz:
1. Das Problem ist, dass ich gerne mehrere Geräte unterstützen möchte 
:(. Für mein Gerät hier habe ich sogar eine Spec. ergattern können!

2. Auf solche einen Standard hoffe ich. Zumindest kann ich dann sagen 
das ich nach Standard X gearbeitet habe und ich nichts für kann, wenn 
die anderen sich nicht dran halten ;). Kennst du einen solchen Standard 
zufälligerweise, bzw. hast einen Ansatz wie und wo man ihn finden 
könnte?

3. Oh das mit dem dynamischen erkennnen kann irgendwie schwierig werden 
fürchte ich...
Ich hatte aber bereits die Vermutung, dass die Antwort immer an einem 
Stück erfolgt. Daher habe ich kurz darüber nachgedacht nach dem Empfang 
des ersten Antwortbytes einfach einen Timeout zu starten. Sobald ich 
dann X ms/s kein Byte mehr erhalten habe könnte ich davon ausgehen, dass 
die Antowrt komplett ist. Ist das vielleicht eine Möglichkeit?

@ Arne:
Das zweite <LF> geht leider nicht :(. Spontan fallen mir zwei Beispiele 
dazu ein:
1. AT+CSQ? liefert zum Beispiel die Empfangsstärke bei einer GSM 
Karte/Handy und hat folgendes Antwortformat:
<CR><LF>%s<CR><LF><CR><LF>OK<CR><LF> (e.g. "AT+CSQ")
2. Es kann sein dass die Karte ein Echo macht. Sendet man dann 
AT<CR><LF>
antwortet sie:
AT<CR><LF><CR><LF>OK<CR><LF> :(

Wer hat den Kram eigentlich erfunden *grrr.
Habe noch Hoffnung dass es irgewendwie geht, da es dieser Felder für 
benutzerspezifische Initialisierungskommandos in Widows gibt...

Autor: Stefan Rauße (srausse)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
zwei Anmerkungen bzw. Vorschläge von mir:

1. Ein Befehl zum Modem fängt immer mit "AT" (Ausnahme "A/") an und hört 
mit <CR> auf. Ein <LF> muss nicht mitgeschickt werden.

2. Empfangene Daten beginnen mit <CR> <LF> und werden mit <CR> <LF> 
abgeschlossen. Bei einem AT+CSQ? gibt es halt zwei Antworten, nämlich:

a.) <CR><LF>%s<CR><LF> und
b.) <CR><LF>OK<CR><LF>

Deine Software muss dann nur die korrekte Start- und Stopbedingung 
erkennen. In meinem Fall verwende ich dafür eine Statemachine:
  void gsm_rx_frame (void) {
  u8 byte;
  
  while ((gsm.uart->rx_rd!=gsm.uart->rx_wr)&&(!(gsm.flag&(1<<GSM_RX_TGR)))) {  // Solange Auswerten wie was im Empfangspuffer liegt      
    byte = gsm.uart->rx_buf[gsm.uart->rx_rd];
    gsm.uart->rx_rd = (gsm.uart->rx_rd+1) % RX_BUF;              // Pointer hochzählen (Ringpuffer!)

    switch (gsm.uart->rx_state) {
      case GSM_WAIT:   {if (byte==CR)   {gsm.uart->rx_state++;}  break;}    // Kein Telegramm angefangen, Abfrage des ersten Startbyte
      case GSM_START: {                          // Empfang des zweiten Startbytes bewerten
        if (byte==LF) {
          gsm.uart->rx_bytes = 0;                    // Zähler für empfangene Bytes zurücksetzen
          gsm.uart->rx_state++;                     // -> in den nächsten State
          }                                                      
        else {gsm.uart->rx_state--;}                  // ansonsten zurück!
        break;
        }
      case GSM_DATEN: {                          // Abspeichern der empfangenen Daten
        gsm.uart->rx_daten[gsm.uart->rx_bytes++] = byte;
        if (byte==CR) {gsm.uart->rx_state++;}              // CR ist der erste Teil vom Ende -> daher auf LF prüfen
        if (gsm.uart->rx_bytes>=RX_DATEN) {                // Zuviele Daten empfangen? -> Wieder auf die Startbedingung warten
          gsm.uart->rx_state=GSM_WAIT;
          }
        break;
        }      
      case GSM_END: {                            // Überprüfung auf das Ende
        gsm.uart->rx_daten[gsm.uart->rx_bytes++] = byte;
        if (byte==LF) {                          // LF ist der zeite Teil vom Ende -> daher 
          gsm.flag       |= (1<<GSM_RX_TGR);            // komplette Antwort erhalten
          gsm.uart->rx_timeout = GSM_RX_TIMEOUT;            // Timeout zurücksetzen  
          gsm.uart->rx_state   = GSM_WAIT;              // wieder auf Anfang stellen
          }
        else {gsm.uart->rx_state--;}                  // ansonsten in vorherigen State zurückgehen
        if (gsm.uart->rx_bytes>=RX_DATEN) {                // Zuviele Daten empfangen? -> Wieder auf die Startbedingung warten
          gsm.uart->rx_state=GSM_WAIT;
          }
        break;
        }      
      }
    }      
  }

Durch das gesetze Flag kann ich in meinem weiteren Routinen die 
empfangenen Daten schön sauber auf ihre Nutzdaten hin bewerten...

Bezogen auf AT+CSQ? würde die Routine natürlich zweimal das Flag setzen, 
aber nach dem ersten Telegramm erstmal aufhören weiter zu bewerten!

Gruß
Stefan

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel
  • Verweis auf anderen Beitrag einfügen: Rechtsklick auf Beitragstitel,
    "Adresse kopieren", und in den Text einfügen




Bild automatisch verkleinern, falls nötig
Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder
GIF-Format hochladen. Siehe Bildformate.
Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt.
Bitte hier nur auf die ursprüngliche Frage antworten,
für neue Fragen einen neuen Beitrag erstellen.

Mit dem Abschicken bestätigst du, die Nutzungsbedingungen anzuerkennen.