STM32F407VE: mpy-cross ValueError with @micropython.native decorator

Discussion and questions about boards that can run MicroPython but don't have a dedicated forum.
Target audience: Everyone interested in running MicroPython on other hardware.
Post Reply
ProudPagan
Posts: 34
Joined: Fri Apr 12, 2019 8:55 am

STM32F407VE: mpy-cross ValueError with @micropython.native decorator

Post by ProudPagan » Thu Jun 06, 2019 4:38 pm

Since my frozen modules did not work (https://github.com/micropython/micropython/issues/4829), I am trying to cross compile my sources into frozen bytecode (.mpy files)

When I do not use the @micropython.native decorator, the .mpy file works OK.

However, when I use the decorator, I see this error:

Code: Select all

ValueError: incompatible .mpy arch
MicroPython v1.11-26-gfaf3d3e9e-dirty on 2019-06-06; BLACK STM32F407VE with STM32F407VE
Anyone else facing this?

User avatar
Roberthh
Posts: 1516
Joined: Sat May 09, 2015 4:13 pm
Location: Rhineland, Europe

Re: STM32F407VE: mpy-cross ValueError with @micropython.native decorator

Post by Roberthh » Thu Jun 06, 2019 7:24 pm

Do you cross-compile the code with the proper arch option, e.g.
mpy-cross -march=armv7m myfile.py

User avatar
jimmo
Posts: 420
Joined: Tue Aug 08, 2017 1:57 am
Location: Sydney, Australia

Re: STM32F407VE: mpy-cross ValueError with @micropython.native decorator

Post by jimmo » Thu Jun 06, 2019 10:19 pm

For some extra background, an .mpy file is platform agnostic -- it just contains MicroPython bytecode that run anywhere. But when you use @native, it has to know which architecture to emit native machine code for. This is the purpose of the march flag. Unfortunately you end up with a platform-specific .mpy but that's kind of to be expected.

Before 1.11 mpy-cross didn't support compiling code with @native. I think there should probably be a proper error if you try and use @native without specifying this flag.

You can see that the makefile passes -march when doing the frozen modules compile.

FYI, as a sort of follow up to your previous question about benefits from @native. Apparently the expected performance gain is about 30% at a 2-3x code size increase. (This is why mpy-cross (or the on-board compiler) doesn't just convert all your code to @native). The reason the bytecode is so competitive is that so much still happens in the python runtime, (i.e. much of the emitted native code is just calls to the python runtime).

@viper is a different story but the semantics of your code change considerably.

ProudPagan
Posts: 34
Joined: Fri Apr 12, 2019 8:55 am

Re: STM32F407VE: mpy-cross ValueError with @micropython.native decorator

Post by ProudPagan » Fri Jun 07, 2019 7:43 am

Thanks for tip.

I have another question on native code execution:

When I enable `MICROPY_DYNAMIC_COMPILER` in py/mpconfig.h

Code: Select all

// Whether the compiler is dynamically configurable (ie at runtime)
// This will disable the ability to execute native/viper code
#ifndef MICROPY_DYNAMIC_COMPILER
#define MICROPY_DYNAMIC_COMPILER (1)
#endif
I get the following linker error:

Code: Select all

LINK build-BLACK_F407VE/firmware.elf
build-BLACK_F407VE/py/compile.o:(.rodata.emit_asm_table+0x24): undefined reference to `emit_inline_xtensa_method_table'
build-BLACK_F407VE/py/compile.o:(.rodata.emit_native_table+0x4): undefined reference to `emit_native_x86_method_table'
build-BLACK_F407VE/py/compile.o:(.rodata.emit_native_table+0x8): undefined reference to `emit_native_x64_method_table'
build-BLACK_F407VE/py/compile.o:(.rodata.emit_native_table+0xc): undefined reference to `emit_native_arm_method_table'
build-BLACK_F407VE/py/compile.o:(.rodata.emit_native_table+0x24): undefined reference to `emit_native_xtensa_method_table'
build-BLACK_F407VE/py/persistentcode.o: In function `load_raw_code':
persistentcode.c:(.text.load_raw_code+0x394): undefined reference to `mp_fun_table'
Makefile:510: recipe for target 'build-BLACK_F407VE/firmware.elf' failed
My py/mpconfig.h:

Code: Select all

// Whether to support loading of persistent code
#ifndef MICROPY_PERSISTENT_CODE_LOAD
#define MICROPY_PERSISTENT_CODE_LOAD (1)
#endif

// Whether to support saving of persistent code
#ifndef MICROPY_PERSISTENT_CODE_SAVE
#define MICROPY_PERSISTENT_CODE_SAVE (0)
#endif

// Whether generated code can persist independently of the VM/runtime instance
// This is enabled automatically when needed by other features
#ifndef MICROPY_PERSISTENT_CODE
#define MICROPY_PERSISTENT_CODE (MICROPY_PERSISTENT_CODE_LOAD || MICROPY_PERSISTENT_CODE_SAVE || MICROPY_MODULE_FROZEN_MPY)
#endif

// Whether to emit x64 native code
#ifndef MICROPY_EMIT_X64
#define MICROPY_EMIT_X64 (0)
#endif

// Whether to emit x86 native code
#ifndef MICROPY_EMIT_X86
#define MICROPY_EMIT_X86 (0)
#endif

// Whether to emit thumb native code
#ifndef MICROPY_EMIT_THUMB
#define MICROPY_EMIT_THUMB (1)
#endif

// Whether to enable the thumb inline assembler
#ifndef MICROPY_EMIT_INLINE_THUMB
#define MICROPY_EMIT_INLINE_THUMB (1)
#endif

// Whether to enable ARMv7-M instruction support in the Thumb2 inline assembler
#ifndef MICROPY_EMIT_INLINE_THUMB_ARMV7M
#define MICROPY_EMIT_INLINE_THUMB_ARMV7M (1)
#endif


// Whether to enable float support in the Thumb2 inline assembler
#ifndef MICROPY_EMIT_INLINE_THUMB_FLOAT
#define MICROPY_EMIT_INLINE_THUMB_FLOAT (1)
#endif

// Whether to emit ARM native code
#ifndef MICROPY_EMIT_ARM
#define MICROPY_EMIT_ARM (0)
#endif

// Whether to emit Xtensa native code
#ifndef MICROPY_EMIT_XTENSA
#define MICROPY_EMIT_XTENSA (0)
#endif

// Whether to enable the Xtensa inline assembler
#ifndef MICROPY_EMIT_INLINE_XTENSA
#define MICROPY_EMIT_INLINE_XTENSA (0)
#endif



In ports/stmp32/mpconfigport.h, I have:

Code: Select all

// emitters
#define MICROPY_PERSISTENT_CODE_LOAD (1)
#ifndef MICROPY_EMIT_THUMB
#define MICROPY_EMIT_THUMB          (1)
#endif
#ifndef MICROPY_EMIT_INLINE_THUMB
#define MICROPY_EMIT_INLINE_THUMB   (1)
#endif

Post Reply