micropython源码分析之c模组注册
本篇文章基于micropython1.18版本分析,1.19版本及之后可能略有差異。
關(guān)于c模組的寫(xiě)法官方文檔有介紹https://docs.micropython.org/en/latest/develop/cmodules.html,也可以參考micropython工程源碼中其他的例子,這里不多介紹。
注冊(cè)c模組
按照c模組構(gòu)造方法寫(xiě)完c程序后,還需要再頭文件中聲明模組注冊(cè),注冊(cè)模組有兩種方式一種手動(dòng)添加到頭文件,另一個(gè)就是采用自動(dòng)注冊(cè)方式,以u(píng)nix端口為例編譯為例子說(shuō)明:
1.手動(dòng)注冊(cè)
找到ports/unix/mpconfigport.h文件,很多外部c模組就在這里面聲明注冊(cè)的。以machine模組為例,需要添加以下語(yǔ)句注冊(cè)聲明
//聲明模組對(duì)象結(jié)構(gòu)體 extern const struct _mp_obj_module_t mp_module_machine;//將模組名-模組指針 加入MICROPY_PORT_BUILTIN_MODULES 宏中,該宏最終會(huì)加入全局模組表中。 #define MICROPY_PORT_BUILTIN_MODULES \ ...{ MP_ROM_QSTR(MP_QSTR_umachine), MP_ROM_PTR(&mp_module_machine) }, \ ...通過(guò)追蹤該宏MICROPY_PORT_BUILTIN_MODULES 可以發(fā)現(xiàn),他被加入到了文件py/objmodule.c中mp_builtin_module_table[]里,代碼如下:
// Global module table and related functionsSTATIC const mp_rom_map_elem_t mp_builtin_module_table[] = {{ MP_ROM_QSTR(MP_QSTR___main__), MP_ROM_PTR(&mp_module___main__) },{ MP_ROM_QSTR(MP_QSTR_builtins), MP_ROM_PTR(&mp_module_builtins) },{ MP_ROM_QSTR(MP_QSTR_micropython), MP_ROM_PTR(&mp_module_micropython) },...省略部分代碼#if MICROPY_PY_BUILTINS_FLOAT#if MICROPY_PY_MATH{ MP_ROM_QSTR(MP_QSTR_math), MP_ROM_PTR(&mp_module_math) },#endif#if MICROPY_PY_BUILTINS_COMPLEX && MICROPY_PY_CMATH{ MP_ROM_QSTR(MP_QSTR_cmath), MP_ROM_PTR(&mp_module_cmath) },#endif#endif#if MICROPY_PY_SYS{ MP_ROM_QSTR(MP_QSTR_usys), MP_ROM_PTR(&mp_module_sys) },#endif#if MICROPY_PY_GC && MICROPY_ENABLE_GC{ MP_ROM_QSTR(MP_QSTR_gc), MP_ROM_PTR(&mp_module_gc) },#endif#if MICROPY_PY_THREAD{ MP_ROM_QSTR(MP_QSTR__thread), MP_ROM_PTR(&mp_module_thread) },#endif// extmod modules#if MICROPY_PY_UASYNCIO{ MP_ROM_QSTR(MP_QSTR__uasyncio), MP_ROM_PTR(&mp_module_uasyncio) },#endif...省略部分代碼// extra builtin modules as defined by a portMICROPY_PORT_BUILTIN_MODULES#ifdef MICROPY_REGISTERED_MODULES// builtin modules declared with MP_REGISTER_MODULE()MICROPY_REGISTERED_MODULES#endif };mp_builtin_module_table[]里就是micropython中注冊(cè)的所有模組了,按宏選擇打開(kāi)。還發(fā)現(xiàn)末尾有一個(gè)MICROPY_REGISTERED_MODULES宏,這個(gè)就關(guān)系到下面要說(shuō)的自動(dòng)注冊(cè)模組方式了。
注:該方式屬于歷史遺留,在1.19版本之后該部分代碼已被移除,mp_builtin_module_table[] 中僅保留MICROPY_REGISTERED_MODULES宏,也就是后續(xù)不管內(nèi)置模組還是外部模組添加都要采用下面的自動(dòng)注冊(cè)方式
2.自動(dòng)注冊(cè)模組
假如我們寫(xiě)好了一個(gè)與具體硬件無(wú)關(guān)的c模組想要發(fā)布分享,或者并不想更改micropython中源代碼部分作為獨(dú)立的工程,那么就可以使用這種方式。源碼中也給出了一個(gè)例子–uarray模組,找到文件py/modarray.c:
#include "py/builtin.h"#if MICROPY_PY_ARRAYSTATIC const mp_rom_map_elem_t mp_module_array_globals_table[] = {{ MP_ROM_QSTR(MP_QSTR___name__), MP_ROM_QSTR(MP_QSTR_uarray) },{ MP_ROM_QSTR(MP_QSTR_array), MP_ROM_PTR(&mp_type_array) }, };STATIC MP_DEFINE_CONST_DICT(mp_module_array_globals, mp_module_array_globals_table);const mp_obj_module_t mp_module_uarray = {.base = { &mp_type_module },.globals = (mp_obj_dict_t *)&mp_module_array_globals, };MP_REGISTER_MODULE(MP_QSTR_uarray, mp_module_uarray, MICROPY_PY_ARRAY);#endif末尾加了一句MP_REGISTER_MODULE(MP_QSTR_uarray, mp_module_uarray, MICROPY_PY_ARRAY);這個(gè)就是用來(lái)聲明自動(dòng)注冊(cè)的宏,該宏用法如下:
// Declare a module as a builtin, processed by makemoduledefs.py // param module_name: MP_QSTR_<module name> // param obj_module: mp_obj_module_t instance // prarm enabled_define: used as `#if (enabled_define) around entry`#define MP_REGISTER_MODULE(module_name, obj_module, enabled_define)3個(gè)參數(shù)為模組名的qstr,模組對(duì)象指針,是否使能,最后加了這句且enabled_define為1那么編譯micropython的時(shí)候就會(huì)自動(dòng)幫你注冊(cè)上。
自動(dòng)注冊(cè)過(guò)程依賴一個(gè)腳本工具py/makemoduledefs.py,通過(guò)這個(gè)腳本會(huì)檢索你的c源碼中含有MP_REGISTER_MODULE的語(yǔ)句提取出信息,然后生成一個(gè)頭文件ports/unix/build-standard/genhdr/moduledefs.h在編譯路徑下。
// Automatically generated by makemoduledefs.py.#if (MICROPY_PY_ARRAY)extern const struct _mp_obj_module_t mp_module_uarray;#define MODULE_DEF_MP_QSTR_UARRAY { MP_ROM_QSTR(MP_QSTR_uarray), MP_ROM_PTR(&mp_module_uarray) }, #else#define MODULE_DEF_MP_QSTR_UARRAY #endif#define MICROPY_REGISTERED_MODULES \MODULE_DEF_MP_QSTR_UARRAY \ // MICROPY_REGISTERED_MODULES像ulab(micropython的類numpy數(shù)組操作庫(kù))這種三方模組就是采用自動(dòng)注冊(cè)方式。
我們自己開(kāi)發(fā)的時(shí)候也盡量采取這種方式,便于模組獨(dú)立維護(hù)管理。
總結(jié)
以上是生活随笔為你收集整理的micropython源码分析之c模组注册的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
- 上一篇: 测试并发应用 (一)监控Lock接口
- 下一篇: Python:file (read,re