Skip to content

Interruptions + SPIFFS + std::bind crash #7788

Closed
@Bacto

Description

@Bacto

Platform

  • Hardware: ESP8285
  • Core Version: framework-arduinoespressif8266 3.20704.0 (2.7.4)
  • Development Env: Platformio
  • Operating System: MacOS
  • Module: Wemos D1 mini r2

Problem Description

Hi,

I'm trying to use interruptions in a class and use std::bind(&...::..., this) for this purpose.
Unfortunately, when I try to access to the flash using LittleFS, the ESP crashes:

Exception (0):
epc1=0x40209474 epc2=0x00000000 epc3=0x00000000 excvaddr=0x00000000 depc=0x00000000

Here is the decoded stack trace:

0x401005e9: interrupt_handler at ??:?
0x40100528: interrupt_handler at ??:?
0x401059f8: Cache_Read_Enable_2 at ??:?
0x40105fc1: spi_flash_read at ??:?
0x4010243b: rcReachRetryLimit at ??:?
0x4010261c: rcReachRetryLimit at ??:?
0x40102ade: wDev_ProcessFiq at ??:?
0x40105fbc: spi_flash_read at ??:?
0x40100fa1: __wrap_spi_flash_read at ??:?
0x40208f0d: EspClass::flashRead(unsigned int, unsigned int*, unsigned int) at ??:?
0x402081c4: flash_hal_read(unsigned int, unsigned int, unsigned char*) at ??:?
0x40102b18: wDev_ProcessFiq at ??:?
0x402057be: littlefs_impl::LittleFSImpl::lfs_flash_read(lfs_config const*, unsigned int, unsigned int, void*, unsigned int) at ??:?
0x4020132c: lfs_bd_read$isra$12 at lfs.c:?
0x4020130c: lfs_bd_read$isra$12 at lfs.c:?
0x402014c2: lfs_dir_fetchmatch at lfs.c:?
0x40100601: interrupt_handler at ??:?
0x40201e0a: lfs_dir_find at lfs.c:?
0x40202ae0: lfs_dir_find_match at lfs.c:?
0x40204a18: lfs_file_opencfg at ??:?
0x4020c1b4: _strdup_r at /home/earle/src/esp-quick-toolchain/repo/newlib/newlib/libc/string/strdup_r.c:11
0x40100ce6: malloc at ??:?
0x40100a27: umm_free_core at umm_malloc.cpp:?
0x40204c50: lfs_file_open at ??:?
0x402062ff: littlefs_impl::LittleFSImpl::open(char const*, fs::OpenMode, fs::AccessMode) at ??:?
0x40201c90: lfs_dir_getgstate at lfs.c:?
0x4020530b: std::_Function_base::_Base_manager<std::_Bind<std::_Mem_fn<void (Sandbox::*)()> (Sandbox*)> >::_M_manager(std::_Any_data&, std::_Any_data const&, std::_Manager_operation) at ??:?
0x402069a8: fs::FS::open(char const*, char const*) at ??:?
0x40100100: interruptFunctional(void*) at ??:?
0x40100caf: free at ??:?
0x4020fddd: operator delete(void*) at /workdir/repo/gcc/libstdc++-v3/libsupc++/del_op.cc:48
0x40205401: loop at ??:?
0x40205384: Sandbox::init() at ??:?
0x4010048d: digitalWrite at ??:?
0x402053d8: setup at ??:?
0x4020773c: loop_wrapper() at core_esp8266_main.cpp:?
0x401002e5: cont_wrapper at ??:?

Here is a MCVE:

#include "Arduino.h"
#include <LittleFS.h>
#include <FunctionalInterrupt.h>

// ---------

class Sandbox {
  public:
    void init();

  private:
    void ICACHE_RAM_ATTR interruptHandler();
};

// ---------

void Sandbox::init() {
  // Note: use a pin where there is a lot data (I have 8000 changes/second)
  pinMode(D7, INPUT);
  attachInterrupt(D7, std::bind(&Sandbox::interruptHandler, this), CHANGE);
}

void ICACHE_RAM_ATTR Sandbox::interruptHandler() {
}

// ---------


Sandbox sandbox;

void setup() {
  Serial.begin(74880);
  LittleFS.begin();
  sandbox.init();
}

void loop() {
  // noInterrupts();
  File fd = LittleFS.open("/test", "w");
  fd.close();
  // interrupts();
  delay(1000);
}

Note that it happens when I have some interruptions (8000/seconds in my case but it should crashed with less I suppose).

When I suspend interrupts during the FS access, the ESP doesn't crash.

When I declare interruptHandler as static and don't use std::bind it works too (but I'll have to declare all my variables as static which I would like to avoid).

I tried a lot of things to find a solution but nothing worked and I would like to avoid to use a plain classical function as a callback to attachInterrupt.

If you have any idea... 🙏

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions