Подключение по uart нескольких устройств к arduino uno

dale92

✩✩✩✩✩✩✩
12 Фев 2023
2
0
Добрый день!
Собираю схему удаленного управления резервом питания через gsmмодуль. Для этого приобрел два модуля pzem-004t для отслеживания состояния основной и резервной линии, модем neoway m590, блок промежуточных релюх и ардуинка.
Не могу разобраться со следующим: по отдельности каждый из элементов схемы исправен, в ком порт шлет показания с пземов, модем принимает/отправляет смски. Но как только я пытаюсь заставить их работать в связке, модем отваливается и больше не опрашивается.

C++:
#include <PZEM004Tv30.h>

#include <SoftwareSerial.h>


#define PIN_GEN 13 //пин реле генератора
#define PIN_STOP 11 //пин реле остановки генератора
#define PIN_STRT 10 //пин реле стартера


SoftwareSerial gsmSerial(8, 9);
SoftwareSerial pzemSerialA(3, 4);
SoftwareSerial pzemSerialB(5, 6);
 
PZEM004Tv30 pzem1(pzemSerialA);
PZEM004Tv30 pzem2(pzemSerialB);
 
float voltage1, current1, power1, energy1;
float voltage2, current2, power2, energy2;
float aaa;
unsigned long timing; // Переменная для хранения задержки
 
void setup()
 
  {
 
  Serial.begin(115200);
  gsmSerial.begin(115200);
    
  delay(1000); 
  pinMode(PIN_GEN, OUTPUT);
  pinMode(PIN_STOP, OUTPUT);
  pinMode(PIN_STRT, OUTPUT);
  digitalWrite(PIN_GEN, HIGH);
  digitalWrite(PIN_STOP, HIGH);
  digitalWrite(PIN_STRT, HIGH);
 
 
  Serial.println("GSM NEOWAY");
  Serial.println();
  Serial.println("Turn on AOH:");
  delay(1000);
  gsmSerial.println("AT+CLIP=1");  //включить АОН
  delay(1000);
  Serial.println("Text format sms:");
  delay(1000);
  gsmSerial.println("AT+CMGF=1"); // текстовый формат SMS
  delay(1000);
  Serial.println("Mode GSM:");
  delay(1000);
  gsmSerial.println("AT+CSCS=\"GSM\"");  // кодировка текста - GSM
  delay(1000);
  Serial.println("SMS to terminal:");
  delay(1000);
  gsmSerial.println("AT+CNMI=2,2,0,0,0"); // вывод смс в консоль
  delay(1000); 
  
  }

void loop()

{

//Считываем данные с мониторов сети и генератора один раз в timer

  if(millis() - timing > 15000)
  {           
    voltage1 = pzem1.voltage();
    current1 = pzem1.current();
    power1 = pzem1.power();
    energy1 = pzem1.energy();
    voltage2 = pzem2.voltage();
    current2= pzem2.current();
    power2 = pzem2.power();
    energy2 = pzem2.energy();
    
  
       Serial.println("Город");
       Serial.print("Voltage: ");      Serial.print(voltage1);      Serial.println("V");
       Serial.print("Current: ");      Serial.print(current1);      Serial.println("A");
       Serial.print("Power: ");        Serial.print(power1);        Serial.println("W");
      
       Serial.println("Генератор");
       Serial.print("VoltageG: ");      Serial.print(voltage2);      Serial.println("V");
       Serial.print("CurrentG: ");      Serial.print(current2);      Serial.println("A");
       Serial.print("PowerG: ");        Serial.print(power2);        Serial.println("W");
       Serial.print("EnergyG: ");       Serial.print(energy2);       Serial.println("kWh");
       Serial.println(avr);
       timing = millis();
    }
 
//Управление реле АВР

gsmSerial.println("AT+CMGF=1");

  if(gsmSerial.available()) //если модуль что-то послал
  { 
    char ch = ' ';
    String val = "";
    
     while(gsmSerial.available())
      { 
      ch = gsmSerial.read();
      val += char(ch); //собираем принятые символы в строку
      delay(30);
      }

  Serial.print("Neo send> ");
  Serial.println(val);
    
  if(val.indexOf("+CMT") > -1) //если есть входящее sms
  {
    if(val.indexOf("on") > -1) // смотрим, что за команда
     { 
     Serial.println("On");
     digitalWrite(PIN_STRT, LOW);  //включаем стартер
     delay(30);
     digitalWrite(PIN_STRT, HIGH);
     digitalWrite(PIN_GEN, LOW);    //включаем генератор
     }
    
    if(val.indexOf("off") > -1) // смотрим, что за команда
     {
      digitalWrite(PIN_GEN, HIGH);  //выключаем генератор
     Serial.println("Off");
     }
  }
    
 }


}
Соответственно, стоит мне закоментить часть, где присваиваются значения с пземов, модем на смски реагирую нормально, но стоит один раз считать значения вольт,ампер и тд к модему достучаться больше не могу.
Предполагал, что может проблема в питании модема, т.к. везде пишут, что модуль очень жрущий, подключил от источника на 360 Ватт и развел на разные линии питания модем и остальные элементы, объединив земли. Проблема не ушла.

Не понимаю почему модем отваливается, хотя пземов два и они нормально по очереди опрашиваются?
Может внутрь прерывания опрос модема засунуть?
 

Bruzzer

★★★✩✩✩✩
23 Май 2020
470
134
@dale92,
Не смотрел внимательно ваш код.
SoftwareSerial, даже когда он один, может работать только в полудуплексном режиме, т.е. не может одновременно принимать и отправлять данные.
Когда их несколько, то только один из них работает на прием данных. И вы должны сами переключать на прием нужный в данное время.
Если данные могут прийти в любое время а не только по запросу, то использование SoftwareSerial может принести дополнительные трудности.

Дополнено позже. Посмотрел - библиотека датчиков сама вызывает listen при опросе датчика.
Т.е. вам надо добавить listen только для GSM. Если GSM не шлет данные без запроса, то должно работать.
 
Изменено:
  • Лойс +1
Реакции: Boroda22 и dale92