Не могу распарсить / Arduino Pro Mini / GSM SIM900

sbatrov
Offline
Зарегистрирован: 05.12.2016

Здравствуйте!

В программировании я чайник, конкретно Arduino начал заниматься совсем недавно. Появилась проблема в управлении удаленным устройством с помощью DTMF кодов.

Подключаю GSM-модуль SIM900 к компьютеру, открываю терминал и даю в терминале такие команды:

AT+CLIP=1
AT+DDET=1
 
После чего делаю дозвон на модуль с мобильного телефона, поднимаю трубку командой ATA и при нажатии цифровых кнопок на телефоне у меня в терминале отображаются декодированные сигналы в виде +DTMF:1, +DTMF:2 и т.д.
 
После чего подключаю модуль к Arduino, снова делают дозвон. Arduino обнаруживает входящий звонок с помощью такого кода:
 
while (Serial.available() > 0) {
  int inChar = Serial.read();
  inString += (char)inChar;
    if (inChar == '\n') {
      if (inString.startsWith("RING")) {
        Serial.println ("ATA");
        delay (1000);
        Serial.println ("AT+VTS=#");
        bl_blink();
      }
      if (inString.startsWith("+DTMF")) {
        bl_blink();
      }
 
      inString = "";
    }
}
 
После поднятия трубку он пикает мне в ответ командой AT+VTS=#, чтобы я мог убедиться, что система работает. Однако на этом все. Я никак не могу получить строку, содержащую "+DTMF:x", чтобы выполнить какую-либо команду по нажатию кнопки на телефоне.
Подскажите пожалуйста, что не так.

 

okta
Offline
Зарегистрирован: 10.01.2015

Код полностью показали бы. Конкретно в этом куске криминала не вижу.

И да, вот здесь почитайте

sbatrov
Offline
Зарегистрирован: 05.12.2016

Весь код к сожалению привести здесь не могу, т.к. права на него принадлежат работодателю и он используется в коммерческих целях. Да и нет там в принципе ничего больше относящегося к связи.

Когда вывожу строку для отладки на дисплей устройства, то видно все, вплоть до "RING" с номером звонящего абонента. После этого строка остается пустая, несмотря на нажатия кнопок на телефоне. После разрыва соединения в строке появляется "NO CARRIER", т.е. обмен данными между контроллером и GSM-модулем работает нормально.

СМС тоже распарсивается нормально, и заголовок и тело сообщения. Но вот почему я не могу прочитать это несчастное "+DTMF:" - я понять не могу. На компьютере же прекрасно это видно в терминале.

okta
Offline
Зарегистрирован: 10.01.2015

sbatrov пишет:

Весь код к сожалению привести здесь не могу, т.к. права на него принадлежат работодателю и он используется в коммерческих целях.

Тогда вам к экстрасенсам...

sbatrov пишет:

 Да и нет там в принципе ничего больше относящегося к связи.

Эммм... ну как минимум где-то должна быть прописана комманда AT+DDET=1

sbatrov
Offline
Зарегистрирован: 05.12.2016

okta пишет:

Эммм... ну как минимум где-то должна быть прописана комманда AT+DDET=1

В первом посте есть команды инициализации, которые у меня прописаны в SETUP.

А именно:

Serial.begin (19200);

Serial.println ("AT+CLIP=1");

Serial.println ("AT+DDET=1");

Sr.FatCat
Offline
Зарегистрирован: 19.02.2016

Я вижу порочную практику вставлять delay в цикл Serial.aviable()
И не понятно, что происходит когда из этого цикла вываливается. А вывалиться может и посредине строки.
Вообще лучше всего, читать из порта так как это делают во всех библиотеках для текстового общения с устройствами по UART:

byte sendCommand(const char* cmd, const char* expected1, const char* expected2, unsigned int timeout)
{
  if (cmd) {
    purgeSerial();
    SIM_SERIAL.println(cmd);
  }
  uint32_t t = millis();
  byte n = 0;
  do {
    if (SIM_SERIAL.available()) {
      char c = SIM_SERIAL.read();
      if (n >= sizeof(buffer) - 1) {
        // buffer full, discard first half
        n = sizeof(buffer) / 2 - 1;
        memcpy(buffer, buffer + sizeof(buffer) / 2, n);
      }
      buffer[n++] = c;
      buffer[n] = 0;
      if (strstr(buffer, expected1)) {
       return 1;
      }
      if (strstr(buffer, expected2)) {
       return 2;
      }
    }
  } while (millis() - t < timeout);
  return 0;
}

 

valrond
Offline
Зарегистрирован: 30.03.2017

sbatrov пишет:

После поднятия трубку он пикает мне в ответ командой AT+VTS=#, чтобы я мог убедиться, что система работает. Однако на этом все. Я никак не могу получить строку, содержащую "+DTMF:x", чтобы выполнить какую-либо команду по нажатию кнопки на телефоне.
Подскажите пожалуйста, что не так.

Проблема как-то решилась?

valrond
Offline
Зарегистрирован: 30.03.2017

Доброго всем дня. У меня таже проблема. Сериалпорт не выводит строку +DTMF:Х.

Код:

#include <SoftwareSerial.h>

//заводим Serial-соединение с GPRS-Shield на 6 и 7 цифровых входах
SoftwareSerial gprsSerial(6, 7);

void setup()
{
  gprsSerial.begin(19200);
  Serial.begin(9600);
  gprsSerial.println("AT + CLIP=1");
  gprsSerial.println("AT + DDET=1");
}

String currStr = "";
int updateTime = 0;

void loop()
{
  touch();

  if (!gprsSerial.available())
  {
    return;
  }
  

  // Считываем очередной символ с платы
  char currSymb = gprsSerial.read();
  if ('\r' == currSymb) {
    Serial.println();

  }
  else if ('\n' == currSymb)  {
       Serial.println();
  }
  else {
    Serial.print(currSymb);
  }

  if ('\r' == currSymb) {
    if (!currStr.compareTo("RING")) {
      delay(10000);
       gprsSerial.println("ATA");
    }
    currStr = "";
  } else if (currSymb != '\n') {
    currStr += String(currSymb);
  }
}

void touch()
{
  if (millis() >= updateTime) {
    gprsSerial.println("AT");
    updateTime += 5000;
  }
}

Инфа о модеме ("AT + GSV"): http://imgdisk.ru/image/rPXE

Вот что видно в серийнике: http://imgdisk.ru/image/rPXM

Кнопки я естественно нажимал. Проверено в службе поддержки МТС, на офисных АТС

 

Картинки сюда вставить так и не смог...