当前位置: 首页 > 知识库问答 >
问题:

Esp32:双核任务崩溃,即使同一命令在其他地方也能工作

通安宁
2023-03-14

在这件事上,我已经超出了我的能力。

这个项目是为一些学生提供物联网演示。使用电报,他们可以控制一些照明以及接收一些事件通知。

确认以下各项工作正常:

所有照明和照明电报信息

温度传感器和电报信息

门铃,但不是电报信息

如果bot.sendMessage(聊天id,“有人在门口。”,“”) 被添加到soundDoorbell()函数中,然后发生以下崩溃

CORRUPT HEAP: Bad head at 0x3fff479c. Expected 0xabba1234 got
0x3ffffff8 abort() was called at PC 0x40086cd1 on core 0

ELF file SHA256: 0000000000000000

Backtrace: 0x40088904:0x3ffdc5d0 0x40088b81:0x3ffdc5f0
0x40086cd1:0x3ffdc610 0x40086dfd:0x3ffdc640 0x400f6bcf:0x3ffdc660
0x400f2ebd:0x3ffdc920 0x400f2e4c:0x3ffdc970 0x4008d25d:0x3ffdc9a0
0x40081f1e:0x3ffdc9c0 0x4008208d:0x3ffdc9e0 0x40123ca6:0x3ffdca00
0x4011706a:0x3ffdca20 0x400d3a28:0x3ffdca40 0x400d3629:0x3ffdca60
0x400d37fb:0x3ffdca80 0x400d38f1:0x3ffdcab0 0x400d464d:0x3ffdcad0
0x400d707d:0x3ffdcb00 0x400d15cd:0x3ffdcba0 0x400d16a3:0x3ffdcbc0
0x40089b92:0x3ffdcc00

Rebooting... ets Jun  8 2016 00:22:57

rst:0xc (SW_CPU_RESET),boot:0x17 (SPI_FAST_FLASH_BOOT) configsip: 0,
SPIWP:0xee
clk_drv:0x00,q_drv:0x00,d_drv:0x00,cs0_drv:0x00,hd_drv:0x00,wp_drv:0x00
mode:DIO, clock div:1 load:0x3fff0018,len:4 load:0x3fff001c,len:1044
load:0x40078000,len:10124 load:0x40080400,len:5856 entry 0x400806a8

解码堆栈显示:

0x40088904: invoke_abort at
/home/runner/work/esp32-arduino-lib-builder/esp32-arduino-lib-builder/esp-idf/components/esp32/panic.c
line 156 0x40088b81: abort at
/home/runner/work/esp32-arduino-lib-builder/esp32-arduino-lib-builder/esp-idf/components/esp32/panic.c
line 171 0x40086cd1: lock_acquire_generic at
/home/runner/work/esp32-arduino-lib-builder/esp32-arduino-lib-builder/esp-idf/components/newlib/locks.c
line 143 0x40086dfd: _lock_acquire_recursive at
/home/runner/work/esp32-arduino-lib-builder/esp32-arduino-lib-builder/esp-idf/components/newlib/locks.c
line 171 0x400f6bcf: _vfiprintf_r at
../../../.././newlib/libc/stdio/vfprintf.c line 860 0x400f2ebd:
fiprintf at ../../../.././newlib/libc/stdio/fiprintf.c line 50
0x400f2e4c: __assert_func at ../../../.././newlib/libc/stdlib/assert.c
line 59 0x4008d25d: multi_heap_free at
/home/runner/work/esp32-arduino-lib-builder/esp32-arduino-lib-builder/esp-idf/components/heap/multi_heap_poisoning.c
line 218 0x40081f1e: heap_caps_free at
/home/runner/work/esp32-arduino-lib-builder/esp32-arduino-lib-builder/esp-idf/components/heap/heap_caps.c line 268 0x4008208d: esp_mbedtls_mem_free at
/home/runner/work/esp32-arduino-lib-builder/esp32-arduino-lib-builder/esp-idf/components/mbedtls/port/esp_mem.c
line 35 0x40123ca6: mbedtls_free at
/home/runner/work/esp32-arduino-lib-builder/esp32-arduino-lib-builder/esp-idf/components/mbedtls/mbedtls/library/platform.c
line 98 0x4011706a: mbedtls_ssl_free at
/home/runner/work/esp32-arduino-lib-builder/esp32-arduino-lib-builder/esp-idf/components/mbedtls/mbedtls/library/ssl_tls.c
line 8992 0x400d3a28: stop_ssl_socket(sslclient_context*, char const*,
char const*, char const*) at
C:\Users\abas034\AppData\Local\Arduino15\packages\esp32\hardware\esp32\1.0.6\libraries\WiFiClientSecure\src\ssl_client.cpp
line 272 0x400d3629: WiFiClientSecure::stop() at
C:\Users\abas034\AppData\Local\Arduino15\packages\esp32\hardware\esp32\1.0.6\libraries\WiFiClientSecure\src\WiFiClientSecure.cpp
line 93 0x400d37fb: WiFiClientSecure::connect(char const*, unsigned
short, char const*, char const*, char const*) at
C:\Users\abas034\AppData\Local\Arduino15\packages\esp32\hardware\esp32\1.0.6\libraries\WiFiClientSecure\src\WiFiClientSecure.cpp
line 154 0x400d38f1: WiFiClientSecure::connect(char const*, unsigned
short) at
C:\Users\abas034\AppData\Local\Arduino15\packages\esp32\hardware\esp32\1.0.6\libraries\WiFiClientSecure\src\WiFiClientSecure.cpp
line 112 0x400d464d: UniversalTelegramBot::sendGetToTelegram(String
const&) at C:\Users\abas034\UOA\OneDrive - The University of
Auckland\Documents\Arduino\libraries\UniversalTelegramBot\src\UniversalTelegramBot.cpp
line 73 0x400d707d: UniversalTelegramBot::getUpdates(long) at
C:\Users\ab\UOA\OneDrive - The University of
Auckland\Documents\Arduino\libraries\UniversalTelegramBot\src\UniversalTelegramBot.cpp
line 369 0x400d15cd: checkTelegramBot() at
C:\Users\ab\OneDrive\Documents\Projects\WorkingOn\IoT-Demo\HomeAutomationV3/HomeAutomationV3.ino
line 315 0x400d16a3: nonloopingCode(void*) at
C:\Users\ab\OneDrive\Documents\Projects\WorkingOn\IoT-Demo\HomeAutomationV3/HomeAutomationV3.ino
line 343 0x40089b92: vPortTaskWrapper at
/home/runner/work/esp32-arduino-lib-builder/esp32-arduino-lib-builder/esp-idf/components/freertos/port.c
line 143

考虑到“bot.sendMessage”功能在其他任何地方都可以工作,我无法理解为什么它会在这种情况下失败。

代码



    #include 
    #include 
    #include 
    
    #ifdef ESP32
    #include 
    #else
    #include 
    #endif
    #include 
    #include    
    #include 
    
    #include "DHTesp.h"
    
    //Wifi & Telgram credentials
    #include "config.h"
    
    // Sensors & Control
    
    #define pin_DHT11 4 //
    #define pin_alarmsensor 2 //RCWL-0516
    #define pin_siren 19
    #define pin_led_veranda 26
    #define pin_led_bedroom 25
    #define pin_doorbell 27
    
    DHTesp dht;
    
    #define DATA_PIN    18
    #define LED_TYPE    WS2812 
    #define COLOR_ORDER GRB
    #define NUM_LEDS   12
    CRGB leds[NUM_LEDS];
    
    #define BRIGHTNESS          50
    #define FRAMES_PER_SECOND  120
    
    bool alarmArmed = false;
    bool alarmTriggered = false;
    bool partyledson = false;
    bool livingroomledson = false;
    
    int buttonState;             
    int lastButtonState = LOW;   
    unsigned long lastDebounceTime = 0;  
    unsigned long debounceDelay = 50;    
    
    WiFiClientSecure client;
    UniversalTelegramBot bot(BOTtoken, client);
    
    int botRequestDelay = 50;
    unsigned long lastTimeBotRan;
    
    char textoption;
    
    String chat_id;
    
    TaskHandle_t loopingTasks;
    TaskHandle_t nonloopingTasks;
    
    
    void GetTemperature() { //implemented
      String message = "Temperature: ";
      TempAndHumidity newValues = dht.getTempAndHumidity();
      message.concat(String(newValues.temperature)); message.concat(".");
      bot.sendMessage(chat_id, message, "");
    }
    
    void ToggleAlarm() {
      alarmArmed = !alarmArmed;
    
      if (alarmArmed) {
        bot.sendMessage(chat_id, "Alarm armed.", "");
      }
      else bot.sendMessage(chat_id, "Alarm disarmed.", "");
    
    }
    
    void TogglePartylights() {
      partyledson = !partyledson;
      if (partyledson) {
        livingroomledson = false;
        bot.sendMessage(chat_id, "Party lights switched on.", "");
      }
      else bot.sendMessage(chat_id, "Party lights switched off.", "");
    }
    
    void ToggleVerandaLights() {
      bool LightStatus = digitalRead(pin_led_veranda);
      LightStatus = !LightStatus;
      digitalWrite(pin_led_veranda, LightStatus);
      LightStatus = digitalRead(pin_led_veranda);
      if (LightStatus) {
        bot.sendMessage(chat_id, "Veranda light switched on.", "");
      }
      else bot.sendMessage(chat_id, "Veranda light switched off.", "");
    }
    
    void ToggleLivingRoomLights() {
      partyledson = false;
      bool LightStatus = livingroomledson;
      livingroomledson = !livingroomledson;
      if (livingroomledson) {
        for ( int i = 0; i (leds, NUM_LEDS).setCorrection(TypicalLEDStrip);
      FastLED.setBrightness(BRIGHTNESS);
      FastLED.clear();
      FastLED.show();
      Serial.println("Started");
    
      pinMode(pin_siren, OUTPUT);
      pinMode(pin_led_veranda, OUTPUT);
      pinMode(pin_led_bedroom, OUTPUT);
      pinMode(pin_alarmsensor, INPUT);
      pinMode(pin_doorbell, INPUT_PULLUP);
    
      // Connect to Wi-Fi
      WiFi.mode(WIFI_STA);
      WiFi.begin(ssid, password);
      client.setCACert(TELEGRAM_CERTIFICATE_ROOT);
      while (WiFi.status() != WL_CONNECTED) {
        delay(1000);
        Serial.println("Connecting to WiFi..");
      }
      // Print ESP32 Local IP Address
      Serial.println(WiFi.localIP());
    
      Serial.println("Bot started?");
      bot.sendMessage(CHAT_ID, "System restarted", "");
    
      //create a task that will be executed in the Task1code() function, with priority 1 and executed on core 0
      xTaskCreatePinnedToCore(
        nonloopingCode,   /* Task function. */
        "nonloopingTasks",     /* name of task. */
        16384,       /* Stack size of task */
        NULL,        /* parameter of the task */
        1,           /* priority of the task */
        &nonloopingTasks,      /* Task handle to keep track of created task */
        0);          /* pin task to core 0 */
      delay(500);
    
      xTaskCreatePinnedToCore(
        juggle,   /* Task function. */
        "loopingTasks",     /* name of task. */
        16384,       /* Stack size of task */
        NULL,        /* parameter of the task */
        1,           /* priority of the task */
        &loopingTasks,      /* Task handle to keep track of created task */
        1);          /* pin task to core 1 */
      delay(500);
    
    }
    
    void checkTelegramBot() {
      if (millis() > lastTimeBotRan + botRequestDelay) {
        int numNewMessages = bot.getUpdates(bot.last_message_received + 1);
    
        while (numNewMessages) {
          Serial.println("Got response");
          handleNewMessages(numNewMessages);
          numNewMessages = bot.getUpdates(bot.last_message_received + 1);
        }
        lastTimeBotRan = millis();
      }
    }
    
    void nonloopingCode(void * pvParamters) {
      Serial.print("nonloopingCode running on core ");
      Serial.println(xPortGetCoreID());
      for (;;) {
    
        if ((!partyledson) && (!livingroomledson)) {
          FastLED.clear();
          FastLED.show();
        }
        if (alarmArmed) {
          if (digitalRead(pin_alarmsensor)) {
            bot.sendMessage(chat_id, "Alarm triggered", "");
            partyledson = false;
            alarmTriggered = true;
          }
        }
    
        checkTelegramBot();
      }
    }
    void juggle(void * pvParamters) {
      Serial.print("Juggle running on core ");
      Serial.println(xPortGetCoreID());
      for (;;) {
        checkDoorbell();
        if (alarmTriggered)soundAlarm();
        if (partyledson) {
          fadeToBlackBy( leds, NUM_LEDS, 20);
          byte dothue = 0;
          int i = 0;
          while ((i  debounceDelay) {
       if (reading != buttonState) {
          buttonState = reading;
          if (buttonState == LOW) {
            soundDoorbell();
          }
        }
      }
      lastButtonState = reading;
    }
    
    void loop() {
    }


共有1个答案

嵇丰
2023-03-14

我不认为电报程序是线程安全的。

使用FreeRTOS互斥体(https://microcontrollerslab.com/arduino-freertos-mutex-tutorial-priority-inversion-priority-inheritance/),我设法让它工作起来,虽然有很多滞后,但这是一个更容易解决的问题:)

 类似资料:
  • A task is special because knowing when a task is about to exit is useful in these circumstances: Frameworks know when to render the UI. Measuring enter/leave allows knowing total script/task time. Exi

  • 我有一个从CSV文件读取的: 据我所知,是一个POJO: 我还有一个简单的课程: 但当我尝试使用它时,例如从测试中: 我得到以下错误: 我读过这些问题和答案,但运气不好: 任务不可序列化Flink 无法在scala中序列化任务 任务不可序列化:java。伊奥。仅在类而非对象上调用闭包外函数时NotSerializableException

  • 内核中其他有用的服务 模块   字符串操作   字符串操作     内存操作   内存操作     双向链表   双向链表     单向链表   单向链表   函数 void  rt_show_version (void)   该函数将打印 rt-thread rtos 的版本信息。   rt_device_t  rt_console_get_device (void)   获取控制台设备句柄  

  • 7.15. 其他任务 这里有一些简单的任务,你可以自己解决: 把模板文件存放在tmpl/目录,页面数据存放在data/目录。 增加一个处理函数(handler),将对根目录的请求重定向到/view/FrontPage。 修饰页面模板,使其成为有效的HTML文件。添加CSS规则。 实现页内链接。将[PageName]修改为<a href="/view/PageName">PageName</a>。(

  • 我制作了一个OpenGL应用程序,用于测试Framebuffer Objects,该应用程序适用于我制作的笔记本电脑,我拥有的另一台笔记本电脑和我的台式PC。但是,对于我要求为我测试该应用程序的其他人来说,它似乎崩溃了。 到目前为止,我已经将它缩小到在我调用的第一个扩展(在本例中为glGenBuffers)上崩溃,我100%确定在调用该函数(见下文)之前不会调用该扩展。在浏览了许多答案后,我确定了

  • 问题内容: Erlang(或Joe Armstrong的?)建议 _ 不要使用防御性编程_ ,不要让进程崩溃(而不是用不必要的防护来污染您的代码来跟踪残骸)对我来说是如此有意义,我想知道为什么我要浪费这么多多年来致力于错误处理! 我想知道的是-这种方法仅适用于Erlang等平台吗?Erlang的VM具有对流程监控树的简单本地支持,并且重启流程 确实非常 快。我是否应该将开发工作(而不是在Erlan