2017-02-07 123 views
0

我們正在使用Azure IoT Hub實施物聯網遙測解決方案。通過使用項目here,我們能夠在ESP8266上實施成功的基本解決方案。但是我們希望ESP可以在本地WiFi網絡上作爲Web服務器工作,主要用於初始配置目的。Azure ESP8266 IoT客戶端庫與ESP8266 Web服務器不兼容

如果再加上上述項目這一行:

#include <ESP8266WebServer.h>  
ESP8266WebServer server(80); 

項目編譯,但是我們不斷收到「核心轉儲」關於ESP和設備停止工作。

致命異常29(StoreProhibitedCause):EPC1 = 0x4000e1b2, EPC2 = 00000000,EPC3 = 00000000,excvaddr = 0x00000004,DEPC = 00000000

異常(29):EPC1 = 0x4000e1b2 EPC2 = 00000000 EPC3 = 00000000 excvaddr = 0x00000004 DEPC = 00000000

CTX:續SP:3fff4700軟復位WDT

CTX:續SP:3fff4460端:3fff4ce0偏移:01b0

堆>>> 3fff4610:40001da0 00000078 00000000 00000010 3fff4620:40001f46 0000000D 66089700 263a390c 3fff4630:66666633 30303734 88fd4100 5da4cdaf 3fff4640:2395829e 2c6ea747 4f2f4c52 72696e6d
3fff4650:00000000 2e353230 306c7263 5503061d 3fff4660:00000000 3fff4740 3fff4740 3fffa878 3fff4670:00000000 3fff46e0 3fff46e0 3ffec9ba 3fff4680:40002514 3fffdd3c 3fff4ce0 3fff4700 3fff4690: 00000000 00000008 00000008 00000001 3fff46a0:00000000 3fff4700 00000000 3fff4638

¿有沒有人遇到過這個問題,並找到一種方法來解決這個問題?

+0

難道是TCP端口號?你可以嘗試其他端口80以外的網絡服務器? – Jackie

+0

這是一個很好的嘗試,但它沒有奏效。我還添加了核心轉儲的問題。 – faturita

+0

ESP8266具有較低的RAM資源,運行Web Server和Azure IoT Hub,因爲例外情況29表示存儲禁用原因。 鏈接: [ESP8266](https://cdn.sparkfun.com/datasheets/Wireless/WiFi/ESP8266ModuleV1.pdf) ,[ESP8266Arduino](https://github.com/esp8266/Arduino/blob/master/) doc/exception_causes.md) 和[EspExceptionDecoder](https://github.com/me-no-dev/EspExceptionDecoder/releases/tag/1.0.6) – JamesLiu

回答

2

我幾乎完全相同的設置(使用ESP8266來託管WiFi服務器,並定期通過Azure IoT Hub發送消息),對我來說,解決問題的方式是非常小心的內存管理。你的堆棧跟蹤甚至可以匹配我的(epc1和excvaddr是相同的)。

我最小化了對malloc/free的調用,試圖讓我的堆碎片化,並且解決了這個問題。我認爲這對芯片內存來說是一個沉重的負擔。

1

我認爲thisthis問題值得一看。兩位作者都使用帶WiFiClientSecure的ESP8266WebServer,並且遇到同樣的問題。 @ Jeroen88指出了一個可能的解決方案here

讓我引用:

內存泄漏(大約24個字節,取決於主機大小)每 一次我用ESP8266HTTPClient從一個安全的網站獲取數據。

將問題深入到SSLContext :: connect(ClientContext * ctx, const char * hostName,uint32_t timeout_ms)。在這個函數中,內存是 ,使用函數ssl_ext_set_host_name(ext,hostName)分配;但是在我看來,這種記憶是永遠不會釋放的。

剛剛在連接功能結束前添加: ssl_ext_set_host_name(ext,nullptr);現在沒有更多的內存在泄漏。

功能齊全:

void connect(ClientContext* ctx, const char* hostName, uint32_t timeout_ms) 
{ 
    SSL_EXTENSIONS* ext = ssl_ext_new(); 
    ssl_ext_set_host_name(ext, hostName); 
    ssl_ext_set_max_fragment_size(ext, 4096); 
    if (_ssl) { 
     /* Creating a new TLS session on top of a new TCP connection. 
      ssl_free will want to send a close notify alert, but the old TCP connection 
      is already gone at this point, so reset s_io_ctx. */ 
     s_io_ctx = nullptr; 
     ssl_free(_ssl); 
     _available = 0; 
     _read_ptr = nullptr; 
    } 
    s_io_ctx = ctx; 
    _ssl = ssl_client_new(_ssl_ctx, 0, nullptr, 0, ext); 
    uint32_t t = millis(); 

    while (millis() - t < timeout_ms && ssl_handshake_status(_ssl) != SSL_OK) { 
     uint8_t* data; 
     int rc = ssl_read(_ssl, &data); 
     if (rc < SSL_OK) { 
      break; 
     } 
    } 
    ssl_ext_set_host_name(ext, nullptr); // THIS FUNCTION FREEs the host_name 
}