Текст внутри структуры

Тема в разделе "Микроконтроллеры AVR", создана пользователем Tomasina, 22 авг 2017.

Метки:
  1. Tomasina

    Tomasina Сушитель лампочек Модератор

    Есть структура:
    Код (C++):
    struct          // структура пакета данных
    {
      byte thisDeviceID;
      int  status;
    }  Message;
    Вот ее использование:
    Код (C++):
     Message.thisDeviceID = rs485myAddress;
    Message.status = 0;
    Как добавить в структуру текст, чтобы можно было писать так:
    Код (C++):
    Message.text = "Comment";
     
    NikitOS нравится это.
  2. rkit

    rkit Гуру

    Добавляем поле String text
     
  3. Tomasina

    Tomasina Сушитель лампочек Модератор

    Не выходит что-то.
    Master:
    Код (C++):
    #include <RS485_non_blocking.h>
    #include <SoftwareSerial.h>

    #define RS485_RX_PIN          6
    #define RS485_TX_PIN          5
    SoftwareSerial rs485(RS485_RX_PIN, RS485_TX_PIN);  // receive pin, transmit pin

    struct          // структура пакета данных
    {
      byte thisDeviceID;
      byte destinationID;
      int  value;
      String msg;
    } data;

    size_t fWrite(const byte what)
    {
      return rs485.write(what);
    }

    RS485 network(NULL, NULL, fWrite, 0);

    void setup()
    {
      Serial.begin(9600);
      rs485.begin(9600); // software serial for talking to other devices
      network.begin(); // initialize the RS485 library
    }  // end of setup

    void loop()
    {
      //const byte msg[] = "Hello world";  // Этот вариант передается корректно. Только почему "byte"?
      //network.sendMsg(msg, sizeof (msg));

      memset(&data, 0, sizeof(data));

      data.thisDeviceID = 3;
      data.destinationID = 0;
      data.value = 8;
      data.msg = "Test point";

      network.sendMsg((byte *) &data, sizeof data);

      delay (1000);  
    }  // end of loop
     
    Slave:
    Код (C++):
    #include <RS485_non_blocking.h>
    #include <SoftwareSerial.h>
    #define RS485_RX_PIN          6
    #define RS485_TX_PIN          5
    SoftwareSerial rs485(RS485_RX_PIN, RS485_TX_PIN);  // receive pin, transmit pin

    struct          // структура пакета данных
    {
      byte thisDeviceID;
      byte destinationID;
      int  value;
      String msg;
    } data;


    int fAvailable()
    {
      return rs485.available();
    }


    int fRead()
    {
      return rs485.read();
    }

    RS485 network(fRead, fAvailable, NULL, 20);

    void setup()
    {
      Serial.begin(9600);
      rs485.begin(9600); // software serial for talking to other devices
      network.begin(); // initialize the RS485 library
    }  // end of setup

    void loop()
    {
      if (network.update())
      {
        //    Serial.write(network.getData(), network.getLength());  это работает с byte msg[] = "Hello world"
        //  Serial.println();

        memset(&data, 0, sizeof (data));
        int len = network.getLength();
        if (len > sizeof (data)) len = sizeof (data);
        memcpy(&data, network.getData(), len);

        Serial.println(data.thisDeviceID);
        Serial.println(data.destinationID);
        Serial.println(data.value);
        Serial.println(data.msg);
        Serial.println();
      }
    }  // end of loop
     
    Результат:
     
  4. rkit

    rkit Гуру

    Это уже совсем другой вопрос.
    Вот так данные сериализовывать не следует.
    Нужно определить четкий формат, четко его сформировать и переслать.
     
  5. Tomasina

    Tomasina Сушитель лампочек Модератор

    а в чем тут бяка?
     
  6. rkit

    rkit Гуру

    Ну в первую очередь в том, что у строки бывает разная длина, а sizeof data - константа.
     
  7. Tomasina

    Tomasina Сушитель лампочек Модератор

    если String заменить на unsigned char* msg[32]?
     
  8. rkit

    rkit Гуру

    Ну если без указателя. Но это все равно плохая практика и может не работать, если принимающая и отправляющая железка разные.
     
  9. Tomasina

    Tomasina Сушитель лампочек Модератор

    все железки в сети - Uno и Mega2560.
    Как тогда сделать правильно?
     
  10. rkit

    rkit Гуру

    Проще всего взять какой-нибудь существующий формат обмена данными, и воспользоваться готовыми библиотеками. Например вот выглядит прилично, но я не пользовался https://github.com/HEADS-project/arduino_msgpack
    А самостоятельно городить это довольно много возни.
     
    Tomasina нравится это.
  11. ostrov

    ostrov Гуру

    Массив char должен срадобать теоретически. Поле же фиксированной и известной длины, в отличии от String. Я так понимаю так формируете пакеты для передачи данных по RS485?
     
  12. Tomasina

    Tomasina Сушитель лампочек Модератор

    теоретически да, но, похоже, протокол автора исходного скетча не предполагает передачу текстового массива внутри struct. А жаль, ибо это подходящий для меня скетч - он реализует мультимастера в сети (каждое устройство может быть мастером в свой временной слот, в остальное время slave).
    Пришлось отказаться от строк и использовать цифровую замену.
     
  13. ostrov

    ostrov Гуру

    Я делал мультимастера, работало без текста. Но в итоге вернулся к мономастеру, показалось что так надежнее для одноранговой сети. А вот когда сеть двух и более ступенчатая, тогда приходится использовать элементы мультисастера. Но все равно не знаю куда там текст пригодился бы.