Skip to content

Micropython easily gets panic after registering LVGL log print callback function #398

@garywill

Description

@garywill

LVGL doesn't provide feature to change log level during runtime, so I had to use lv.log_register_print_cb() to set a python function as the print callback to control log level. But I encountered memory problem, which always cause MPY system panic.

Microython 1.26.1
LVGL 9.3 (latest lv_binding_micropython commit f33add0)
On ESP32-C3, IDF 5.4.2

A fatal error occurred. The crash dump printed below ....
....
Guru Meditation Error: Core  0 panic'ed (Instruction access fault). Exception was unhandled.

My lv_conf.h

#if LV_USE_LOG 
    /** Set value to one of the following levels of logging detail:
     *  - LV_LOG_LEVEL_TRACE    Log detailed information.
     *  - LV_LOG_LEVEL_INFO     Log important events.
     *  - LV_LOG_LEVEL_WARN     Log if something unwanted happened but didn't cause a problem.
     *  - LV_LOG_LEVEL_ERROR    Log only critical issues, when system may fail.
     *  - LV_LOG_LEVEL_USER     Log only custom log messages added by the user.
     *  - LV_LOG_LEVEL_NONE     Do not log anything. */
    #define LV_LOG_LEVEL LV_LOG_LEVEL_TRACE

    /** - 1: Print log with 'printf';
     *  - 0: User needs to register a callback with `lv_log_register_print_cb()`. */
    #define LV_LOG_PRINTF 0

    /** Set callback to print logs.
     *  E.g `my_print`. The prototype should be `void my_print(lv_log_level_t level, const char * buf)`.
     *  Can be overwritten by `lv_log_register_print_cb`. */

    #define LV_LOG_PRINT_CB mp_lv_log_cb

    /** - 1: Enable printing timestamp;
     *  - 0: Disable printing timestamp. */
    #define LV_LOG_USE_TIMESTAMP 1

    /** - 1: Print file and line number of the log;
     *  - 0: Do not print file and line number of the log. */
    #define LV_LOG_USE_FILE_LINE 1

    /* Enable/disable LV_LOG_TRACE in modules that produces a huge number of logs. */
    #define LV_LOG_TRACE_MEM        1   /**< Enable/disable trace logs in memory operations. */
    #define LV_LOG_TRACE_TIMER      1   /**< Enable/disable trace logs in timer operations. */
    #define LV_LOG_TRACE_INDEV      1   /**< Enable/disable trace logs in input device operations. */
    #define LV_LOG_TRACE_DISP_REFR  1   /**< Enable/disable trace logs in display re-draw operations. */
    #define LV_LOG_TRACE_EVENT      1   /**< Enable/disable trace logs in event dispatch logic. */
    #define LV_LOG_TRACE_OBJ_CREATE 1   /**< Enable/disable trace logs in object creation (core `obj` creation plus every widget). */
    #define LV_LOG_TRACE_LAYOUT     1   /**< Enable/disable trace logs in flex- and grid-layout operations. */
    #define LV_LOG_TRACE_ANIM       1   /**< Enable/disable trace logs in animation logic. */
    #define LV_LOG_TRACE_CACHE      1   /**< Enable/disable trace logs in cache operations. */
#endif  /*LV_USE_LOG*/

My python code:

import lvgl as lv

# {'TRACE': 0, 'INFO': 1, 'WARN': 2, 'ERROR': 3, 'USER': 4, 'NONE': 5}
LV_LOG_LEVEL = lv.LOG_LEVEL.WARN
def lv_log_cb(level, content):
    if level >= LV_LOG_LEVEL:
        print(content)
    # gc.collect() # without this, MPY easily panic. But adding this will make it very slow
lv.log_register_print_cb(lv_log_cb)

disp1 = None
def init_lv():
    global disp1

    lv.init()

    disp1 = lv.display_create(LCD_W, LCD_H)
    disp1.set_color_format(lv.COLOR_FORMAT.I1)

    disp1.set_buffers(lv_disp_bufarr, 
                    None,  
                    len(lv_disp_bufarr),
                    lv.DISPLAY_RENDER_MODE.FULL,
                    )

    disp1.set_flush_cb(flush_cb)

init_lv()


scr = lv.obj()
lv.screen_load(scr)

lv.refr_now(disp1)
# add some widgets
lv.refr_now(disp1)
# add some widgets . Easily MPY system panic !!!

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