title: SIM900 GSM/GPRS not getting a proper AT+CREG? answer
body: <p>I'm using an Arduino UNO with attached IComsat SIM900 GSM/GPRS shield.
  Using the following tutorial: <a href="http://www.samaria.me.uk/2011/12/arduino-live-gps-tracker-howto.html#!/2011/12/arduino-live-gps-tracker-howto.html" rel="nofollow">Arduino Live GPS Tracker</a> I'm stuck with the AT+CREG? command, which checks if the SIM-card is registered at the provider.</p>
  
  <p>The following logic is used:
  In the GSM_HTTP.INO file within the "void setup()" function, the following line gets executed modem.checkNetwork();</p>
  
  <pre><code>void setup() {           
    Serial.begin(9600); 
    Serial.println("GM862 monitor");
    modem.switchOn();                   // switch the modem on
    delay(4000);                        // wait for the modem to boot
    modem.init();                       // initialize the GSM part of Module
    modem.version();                    // request modem version info
    while (!modem.isRegistered()) {
      delay(1000);
      modem.checkNetwork();             // check the network availability
    }
  }
  </code></pre>
  
  <p>The function "checkNetwork()" is part of the included library GSM862.cpp and looks like this:</p>
  
  <pre><code>void GM862::checkNetwork() {
    char buf[BUF_LENGTH];
    char result;
    requestModem("AT+CREG?", 1000, true, buf);
    result = buf[21];
  
    if (result == '1') {
      state |= STATE_REGISTERED;
    }
    else {
      state &amp;= ~STATE_REGISTERED;
    }
  }
  </code></pre>
  
  <p>Now this is the important part: The value of "result" that gets received by the function "requestModem" returns cryptic values, but no netword status (number 0-5) which is why there is a endless loop trying to register without error or success message.</p>
  
  <p>As this function gets the "buf" variable out of the function "requestModem" in GSM862.cpp, I've had a look at it as well:</p>
  
  <pre><code>byte GM862::requestModem(const char *command, uint16_t timeout, boolean check, char *buf) {
  
    byte count = 0;
  
    *buf = 0;
  
    modem-&gt;flush();
    modem-&gt;println(command);
    count = getsTimeout(buf, timeout);
    return count;
  }
  </code></pre>
  
  <p>In order to have a look into the relevant variables for debugging purposes I've changed the last two functions into the following code:</p>
  
  <p>-->checkNetwork</p>
  
  <pre><code>void GSM862::checkNetwork() {
    char buf[BUF_LENGTH];
    char result;
    requestModem("AT+CREG?", 1000, true, buf);
    result = buf[21];
  
    Serial.print("Debugging buf2:");
    Serial.print(buf[21]);
    Serial.print("Debugging buf2:");
    Serial.print(buf[1]);
    Serial.print("Debugging buf2:");
    Serial.print(buf[0]);
    Serial.print("Debugging result2:");
    Serial.println(result);
  
    if (result == '1') {
      state |= STATE_REGISTERED;
  
      Serial.println("Network registered, home network...");
    }
    else {
      state &amp;= ~STATE_REGISTERED;
  
      if(result == '0'){
        Serial.println("Network not registered, not searching for a new operator to register to...");
      }
      if(result == '2'){
        Serial.println("Still searching for an operators network to register to...");
      }
      if(result == '3'){
        Serial.println("Network registration denied...");
      }
      if(result == '4'){
        Serial.println("Network registration state unknown, probably still starting up...");
      }
      if(result == '5'){
        Serial.println("Network registered, roaming...");
      }
    }
  }
  </code></pre>
  
  <p>--> request Modem</p>
  
  <pre><code>byte GSM862::requestModem(const char *command, uint16_t timeout, boolean check, char *buf) {
  
    byte count = 0;
  
    *buf = 0;
  
    modem-&gt;flush();
    modem-&gt;println(command);
    count = getsTimeout(buf, timeout);
  
    Serial.print("Debugging command1:");
    Serial.println(command);
    Serial.print("Debugging count1:");
    Serial.println(count);
    Serial.print("Debugging buf1:");
    Serial.println(buf);
    Serial.print("Debugging timeout1:");
    Serial.println(timeout);
  
    return count;
  }
  </code></pre>
  
  <p>Like I've mentioned above, it seems that the value out of "result" of the function "checkNetwork" which is actually the value of "buf[21]", displays a cryptic value when displayed on the terminal via Serial.println();</p>
  
  <p>Do you have any idea why or what the exact problem is?</p>