Nanopb + Azure MQTT не работает на NodeMCU

Я пытался закодировать строку с помощью библиотеки Nanopb на NodeMCU и опубликовать ее с помощью AzureMQTT.

При индивидуальном тестировании и Nanopb, и Azure работают нормально. Однако интеграция обоих в один скетч дает мне ошибки.

      void loop(){
      uint8_t sMsg[512];
      gestures data;
      char *msg = "aaaaaaaaaaaaaaaaaaaaaaaaa";
      strcpy(data.values,msg);
      Serial.println("done with strcpy");
      pb_ostream_t buffer = pb_ostream_from_buffer(sMsg, sizeof(sMsg));
      if (!(pb_encode(&buffer, gestures_fields, &data))) {
          Serial.println(F("Encoding failed"));
          Serial.println(PB_GET_ERROR(&buffer));
          return;
       }
       else
       {
          Serial.println("enterd else");
          Serial.println((char*)sMsg);
          client.run();
          if (client.connected()) {
         Serial.println("connected");           
         String payload = "{\"DeviceId\":\"" + String(DEVICE_ID) + "\", \"data\":" + (char*)sMsg + "}";
        Serial.println(payload);
        client.sendEvent(payload);
         Serial.println("Published message!");

   }
 }
 Serial.println("Done with loop");
 }

Последовательный выход выглядит следующим образом:

entered if
done with strcpy
enterd else

aaaaaaaaaaaaaaaaaaaaaaaaa?z[@t/⸮?⸮⸮⸮?⸮⸮⸮?⸮⸮⸮?⸮+⸮?⸮⸮⸮?$⸮?
Done with loop

Если наблюдается, client.connected() возвращает false, следовательно, сообщение не публикуется.

Также иногда на client.run() возникает ошибка стека:

Fatal exception 28(LoadProhibitedCause):
epc1=0x401016dc, epc2=0x00000000, epc3=0x00000000, excvaddr=0x02786a4c, 
depc=0x00000000

Exception (28):
epc1=0x401016dc epc2=0x00000000 epc3=0x00000000 excvaddr=0x02786a4c 
depc=0x00000000

ctx: sys 
sp: 3ffffcf0 end: 3fffffb0 offset: 01a0

>>>stack>>>
3ffffe90:  3fff0010 3fff242c 00000000 40216af4  
3ffffea0:  00000000 005e5dbc 40216b4b 3fff242c  
3ffffeb0:  3fff2414 ffffffbc 00000000 ffffffff  
3ffffec0:  02786a30 00000000 4020c087 00000026  
3ffffed0:  ffffffff 00000000 3ffeaf61 00000130  
3ffffee0:  4020c0da 3fff2d2c 3ffef1cc 3ffef4cc  
3ffffef0:  00000000 00000000 4010195b 3fff2d2c  
3fffff00:  000000c0 00000000 00000064 3fff2d94  
3fffff10:  4020b4e0 3fff2d2c 3fff2d6c 401070bc  
3fffff20:  00000009 4021007c 3ffef848 40234b25  
3fffff30:  3fff1f34 3fff1f30 005e5dcb 4010610e  
3fffff40:  402164be 3ffee878 3ffee878 40234d6d  
3fffff50:  401060f4 00000000 00000000 0000001c  
3fffff60:  4021fdb4 3ffeffe8 0000001b 4021fdc1  
3fffff70:  3ffef858 3fff0010 027982a2 60000600  
3fffff80:  4021fe06 3fffdab0 00000000 3fffdcb0  
3fffff90:  3fff0020 3fffdab0 00000000 40208993  
3fffffa0:  40000f49 40000f49 3fffdab0 40000f49  
<<<stack<<<

Расшифровка трассировки стека дает:

Exception 28: LoadProhibited: A load referenced a page mapped with an 
attribute that does not permit loads
Decoding 22 results
0x401016dc: ppEnqueueRxq at ?? line ?
0x401016dc: ppEnqueueRxq at ?? line ?
0x40216af4: ieee80211_parse_wmeparams at ?? line ?
0x40216b4b: ieee80211_parse_wmeparams at ?? line ?
0x4020c087: pp_attach at ?? line ?
0x4020c0da: pp_attach at ?? line ?
0x4010195b: ppCalFrameTimes at ?? line ?
0x4020b4e0: ppCheckTxIdle at ?? line ?
0x401070bc: pvPortMalloc at         

C: \ Users \ Violet \ Documents \ ArduinoData \ packages \ esp8266 \ hardware \ esp8266 \ 2.3.0 \ cores \ esp8266 / heap.c строка 13

0x4021007c: ieee80211_getmgtframe at ?? line ?
0x40234b25: udp_input at 
/Users/igrokhotkov/espressif/arduino/tools/sdk/lwip/src/core/udp.c line 106 
(discriminator 1)
0x4010610e: igmp_timer at 
/Users/igrokhotkov/espressif/arduino/tools/sdk/lwip/src/core/timers.c line 
222
0x402164be: sta_input at ?? line ?
0x40234d6d: udp_bind at 
/Users/igrokhotkov/espressif/arduino/tools/sdk/lwip/src/core/udp.c line 787
0x401060f4: igmp_timer at 
/Users/igrokhotkov/espressif/arduino/tools/sdk/lwip/src/core/timers.c line 217
0x4021fdb4: system_get_os_print at ?? line ?
0x4021fdc1: system_pp_recycle_rx_pkt at ?? line ?
0x4021fe06: system_restart_hook at ?? line ?
0x40208993: std::_Function_base::_Base_manager ::_M_manager(std::_Any_data&, 
std::_Any_data const&, std::_Manager_operation) at 

c:\users\violet\documents\arduinodata\packages\esp8266\tools\xtensa-lx106- 
elf-gcc\1.20.0-26-gb404fb9-2\xtensa-lx106-elf\include\c++\4.8.2/functional 
line 1934
Стоит ли изучать PHP в 2023-2024 годах?
Стоит ли изучать PHP в 2023-2024 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Приемы CSS-макетирования - floats и Flexbox
Приемы CSS-макетирования - floats и Flexbox
Здравствуйте, друзья-студенты! Готовы совершенствовать свои навыки веб-дизайна? Сегодня в нашем путешествии мы рассмотрим приемы CSS-верстки - в...
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
2
0
212
1

Ответы 1

Кажется, вы переполняете свой стек, т.е. не хватает места, выделенного для локальных переменных. Когда одна из библиотек работает отдельно, места достаточно, но при объединении оно заканчивается.

Простой способ исправить это - изменить эту большую переменную на статическое распределение:

uint8_t sMsg[512];        // Allocated on stack area
static uint8_t sMsg[512]; // Allocated separately

Что делает static, так это то, что он резервирует раздел для переменной на все время выполнения программы, вместо того, чтобы пытаться уместить его в небольшой динамической области стека.

Также возможно увеличить размер стека. В Arduino ESP8266 SDK это, похоже, делается путем модификации CONT_STACKSIZE в cores/esp8266/cont.h.

Пытался перейти на статический, сразу при включении питания выдает ошибку стека (9): LoadStoreAlignment Причина: Загрузить или сохранить по невыровненному адресу. Кроме того, попытался изменить размер стека в cont.h на 16384 с 4096. Затем я получаю фатальное исключение 2 (InstructionRetchErrorCause)

Anuroop Shannu 12.05.2018 09:17

Привет, @Anuroop Shannu. Какую библиотеку AzureMQTT вы использовали? Ссылались ли вы на AzureIoTHubMQTTClient или AzureIoTProtocol_MQTT? Вы можете получить образцы с этими двумя библиотеками.

Michael Xu - MSFT 14.05.2018 11:10

Привет, @Michael Xu, MSFT, я использую AzureIoTHubMQTTClient. Как я уже говорил ранее, и Azure, и Nanopb работают нормально по отдельности, то есть я могу опубликовать сообщение и получить его в обозревателе устройства, когда я не использую nanopb.

Anuroop Shannu 14.05.2018 11:21

Другие вопросы по теме