Shop OBEX P1 Docs P2 Docs Learn Events
Micropython for P2 - Page 14 — Parallax Forums

Micropython for P2

1111214161723

Comments

  • ersmithersmith Posts: 6,052

    @Rayman said:
    @ersmith Any chance you could post the vgatext.spin file that is the source for the vga driver in your micropython? I attempted to use ansi.spin2 instead, but failed :(. Would like to take baby steps, if possible...

    Unfortunately I forgot to save that away. It's probably similar to the vgatext.spin that's in the original version of my VGA tile driver that I posted to the forums; I've attached a copy.

    Is there a way to do things like this from within REPL?

    Change colors? I'm not sure how to print an escape character from Python, but I'm sure there must be a way. It's been a long time since I looked at it. Other than the escape character everything else is just numbers and letters so those are easy at least.

  • RaymanRayman Posts: 14,633

    pye uses escape characters, so can look at that for example.
    Actually, can sorta fix pye with VGA output by messing with this part of the code:

        def hilite(self, mode):
            if mode == 1: ## used for the status line
                #self.wr("\x1b[1;47m")
            self.wr("\x1b[47m\x1b[30m") ##RJA black on gray
            elif mode == 2: ## used for the marked area
                #self.wr("\x1b[43m")
            self.wr("\x1b[43m\x1b[30m")  ##RJA black on yellow
            else:         ## plain text
                #self.wr("\x1b[0m")
                self.wr("\x1b[37m\x1b[44m") ##RJA white on blue
    

    Might have to look at the Linux version to see what it's actually supposed to look like...

  • RaymanRayman Posts: 14,633
    edited 2024-04-29 21:33

    This version of the text editor, pye, seems to be working well in both FlexProp ansi terminal and VGA monitor.

    Using 24bit RGB color escape sequences works out well because FlexProp ansi terminal ignores them but VGA driver does not, which is just fine. Lets me keep yellow on dark blue text inside the editor and the REPL on VGA monitor.

  • RaymanRayman Posts: 14,633

    @ersmith couple questions if you don’t mind…

    Just reading Wikipedia article and see mention of an inline assembler and also bytecode compiled files with .mpy extension.

    Are these things supported in this version? Does the inline assembler create mpy files or something else?

  • RaymanRayman Posts: 14,633

    Sorry, one more…
    Would including the new littlefs flash drive support be so easy I could do it?
    Or, is this complicated ?

  • ersmithersmith Posts: 6,052

    @Rayman said:
    @ersmith couple questions if you don’t mind…

    Just reading Wikipedia article and see mention of an inline assembler and also bytecode compiled files with .mpy extension.

    Are these things supported in this version? Does the inline assembler create mpy files or something else?

    No, the inline assembler is only for ARM. It puts some inline assembly into the python bytecode; I think there's a special bytecode op to execute machine code on the architectures that support it (ARM, and maybe x86). Adding support for a new architecture is a big undertaking. I'm hoping someone will do it for RISC-V (since the new ESP boards use RISC-V) but so far nobody has.

    Also, python bytecode is really complicated (the opcodes can invoke arbitrary methods, for example), so it's not practical to try to accelerate it with XBYTE, in case that crossed your mind :).

    @Rayman said:
    Sorry, one more…
    Would including the new littlefs flash drive support be so easy I could do it?
    Or, is this complicated ?

    I'm not really sure. Micropython already has littlefs file system support, so in principle it should just be a matter of enabling it. In practice I'm sure we need to provide an SPI driver, and I don't know how hard that would be to do.

  • RaymanRayman Posts: 14,633

    Think found some instructions for creating C modules for micropython that are easily understood:
    https://micropython-usermod.readthedocs.io/en/latest/usermods_05.html

  • RaymanRayman Posts: 14,633

    Not 100% as described above, but was able to twist the pyb module into a new p2 module that I think will make it easier to work with the P2 pins.
    This shows using it to turn P0 high then low. Seems like some of this could go into a script so just have to do, e.g., pinh(1).

    Lots of stuff to add here.
    Would also be nice to add the smartpin constants...

    994 x 654 - 50K
  • RaymanRayman Posts: 14,633
    edited 2024-05-01 20:40

    @ersmith with VGA display and USB keyboard, maybe can use USB serial port for something else?
    Would it be easy to disconnect the interface from the serial port?
    Or, is it very engrained?

    BTW: Not sure I fully understand what is going on here with the C user modules...
    Are these being compiled into RISCVP2 assembly code and the run by the JIT engine?

    Really strange when doing this while remote desktopping into another PC that is running a virtualbox Ubuntu...
    Compiling RISCV for a P2 JIT compiler with micropython on top of it... Hard to keep track of how code is actually being used...

  • roglohrogloh Posts: 5,786
    edited 2024-05-01 23:57

    @Rayman said:
    Really strange when doing this while remote desktopping into another PC that is running a virtualbox Ubuntu...
    Compiling RISCV for a P2 JIT compiler with micropython on top of it... Hard to keep track of how code is actually being used...

    Just think Inception, if you've seen the movie.

    I once did similar - had an older PowerPC based Macbook running a virtual x86 PC environment with a remote desktop into a work PC with xterms to a Solaris machine running a network processor simulator then running my actual code to process real data. Layers upon layers of CPUs/languages although your own case is more nested.

  • RaymanRayman Posts: 14,633

    Would like to be able to load a binary from uSD into hub RAM and have it run from the REPL. So, can have sort of a boot menu. No idea how to do that though…

    Really want littlefs access to flash too. I see the parts are there to do this as @ersmith pointed out…

  • roglohrogloh Posts: 5,786

    LittleFS can be built into uPython with customized config files. I found it takes up quite a bit of space though, from memory something approaching 64kB, and eating into otherwise usable Python heap space. Of course you have a bit more memory to play with with RISC-V variant of uPython to begin with and your executable overhead should be be smaller vs native P2.

  • RaymanRayman Posts: 14,633

    @rogloh that is quite a bit of memory…
    I see mention of code compression in @ersmith docs but don’t really know if that is enabled here or not, or how much that would reduce the overhead.

  • ersmithersmith Posts: 6,052

    @Rayman said:
    Would like to be able to load a binary from uSD into hub RAM and have it run from the REPL. So, can have sort of a boot menu. No idea how to do that though…

    I don't think you can run an arbitrary binary from the Python REPL, but you could certainly run Python code (you're probably already doing this with pye, aren't you?

    @rogloh is right, littlefs is a lot of code, so it will reduce the usable Python heap space. A tricky trade-off.

    @Rayman said:
    I see mention of code compression in @ersmith docs but don’t really know if that is enabled here or not, or how much that would reduce the overhead.

    The code compression is the c in rv32imac. It's on by default, and it does help the code size quite a bit.

  • RaymanRayman Posts: 14,633

    Thanks @ersmith

    Think I'm seeing something that is a bit dissapointing...
    Seems I can make constants like this:

    #define MAGIC_CONSTANT 42
    ...
        { MP_ROM_QSTR(MP_QSTR_magic), MP_ROM_INT(MAGIC_CONSTANT) },
    

    As described in link above.

    But, appears that MP_ROM_INT values are limited to 31 bits? Why would they do this?
    Was trying to make a constant with: #define P_INVERT_A 0x80000000
    not seeing a way to do this...

  • ersmithersmith Posts: 6,052

    @Rayman said:
    Thanks @ersmith

    Think I'm seeing something that is a bit dissapointing...
    Seems I can make constants like this:

    #define MAGIC_CONSTANT 42
    ...
        { MP_ROM_QSTR(MP_QSTR_magic), MP_ROM_INT(MAGIC_CONSTANT) },
    

    As described in link above.

    But, appears that MP_ROM_INT values are limited to 31 bits? Why would they do this?
    Was trying to make a constant with: #define P_INVERT_A 0x80000000
    not seeing a way to do this...

    It's been a while since I looked at it, but if I remember correctly the micropython interpreter uses some bits of values as tags to indicate what kind of value it is. So integers are limited to 31 bits because 1 bit has to say integer/not integer; after that there are additional bits to further determine the type.

  • RaymanRayman Posts: 14,633
    edited 2024-05-02 21:32

    I see how to get the free mem in REPL:

    import gc
     gc.mem_free()
    231728  
    

    Would like to add this as a function in this p2.c as a freemem() function like this:
    STATIC mp_obj_t p2_freemem(void) {

       gc_collect();
       printf("%d Bytes Memory available\r\n",gc_mem_free());
       return mp_const_none;
    }
    STATIC MP_DEFINE_CONST_FUN_OBJ_0(p2_freemem_obj, p2_freemem);
    

    But, can't figure out where the mem_free() function might actually be.
    I see pye.py gets it by importing gc so it must be around somewhere?
    Or, maybe it can't be in C files, only py files?

  • ersmithersmith Posts: 6,052

    @Rayman said:
    I see how to get the free mem in REPL:

    import gc
     gc.mem_free()
    231728  
    

    Would like to add this as a function in this p2.c as a freemem() function like this:
    But, can't figure out where the mem_free() function might actually be.
    I see pye.py gets it by importing gc so it must be around somewhere?

    I'm sure it's somewhere in the micropython source -- you could look for where the garbage collector source code is and probably find it there.

    But I'm unclear what the benefit is: you can already access it from python using the gc module, so why also add it to the p2 module?

  • RaymanRayman Posts: 14,633

    Suppose that's true... Should focus on new features..

  • RaymanRayman Posts: 14,633
    edited 2024-05-02 22:17

    This 31 bit short integer stuff is strange, or maybe I don't understand python..
    I know that bit 31 is the sign bit, but why is the hex() function putting a minus sign in the output when it's set?

    hex(p2.P_PLUS1_A)
    '0x10000000'
    hex(p2.P_OUTBIT_A)
    '-0x40000000'

  • RaymanRayman Posts: 14,633
    edited 2024-05-02 22:37

    Think now have the smartpin constants into p2.c

    With the somewhat annoying exception of P_INVERT_A, as it's 32 bits and can only use 31 bits for some reason...

    c
    c
    9K
    p2.c 8.5K
  • roglohrogloh Posts: 5,786

    @Rayman said:
    Think now have the smartpin constants into p2.c

    With the somewhat annoying exception of P_INVERT_A, as it's 32 bits and can only use 31 bits for some reason...

    Yes there were some limitations there when mapping to IO constants in the P2. By the way if you need integers longer than 31/32 bits for proper calculations etc you can enable support for longer integers. See this setting: MICROPY_LONGINT_IMPL_MPZ for very large numbers. I think there was also some 64 bit integer stuff but that probably doesn't apply to the P2 unless it can fit in with emulated RISC-V somehow.

    Also some of the work we did in our native P2 micropython branch may be of use. I already created a bunch of API functions to control some low level P2 IO stuff and other things in areas that Eric hadn't already put in the RISC-V version.
    https://github.com/team-oz/p2-native-micropython/tree/p2native/ports/p2

  • RaymanRayman Posts: 14,633

    @rogloh Thanks. I see you were able to somehow use 32 bit constants. But, maybe that was not built into the binary?
    I think this version can use very large integers from REPL and from a py file on uSD, but not in the C code...

  • RaymanRayman Posts: 14,633
    edited 2024-05-03 21:59

    Added servo support. Tried to add as submodule, but couldn't figure out how.
    Now, thinking just this regular way is fine...

    Also added a way to show the P2 clock freq.
    Don't do p2.clockfreq() though, that makes it go off the rails :)

    c
    c
    14K
    504 x 207 - 7K
  • RaymanRayman Posts: 14,633
    edited 2024-05-03 22:46

    Had 640x480 VGA working, but somehow broke it... 800x600 still works though..

  • RaymanRayman Posts: 14,633

    When looking at littlefs, see you can easily make a ram drive

    Wondering if a psram drive makes any sense…
    Being able to use psram is nice but does having a file system on it help anything?

  • roglohrogloh Posts: 5,786
    edited 2024-05-03 23:49

    @Rayman said:
    @rogloh Thanks. I see you were able to somehow use 32 bit constants. But, maybe that was not built into the binary?
    I think this version can use very large integers from REPL and from a py file on uSD, but not in the C code...

    I do recall having the same issue you did, and the top bit (or bits?) were not possible to use correctly with this limitation. Our later binary (MP v1.13) includes the machine library with more support for smartpins and these constants. It also had the soft I2C and soft SPI stuff included and a few other goodies for P2s such as COGATN, COGID, reset, native hub memory access and random number generator support etc. Ideally there would be other P2 smartpin capabilities exposed explicitly such as DACs and ADCs as well but that didn't make the cut at the time with the limited resource allocation and it needs more integration with IO pin control. In general I wanted to make it more in line with how MP handled GPIO as the P2 IO right now is not a perfect match with other micro implementations. I believe there would need to be some alternate modes of the pin setup (PIN_ALT) to properly coordinate states and various smartpin modes but again we didn't get that far.

    @Rayman said:
    When looking at littlefs, see you can easily make a ram drive

    Wondering if a psram drive makes any sense…
    Being able to use psram is nice but does having a file system on it help anything?

    It could if you wanted a system that could read/write temporary files for processing data for example. But an SD card could also be used for that anyway and would have more room too. Python code is very slow relative to native PASM2 so any speed advantage of PSRAM will likely be reduced quite a bit.

  • RaymanRayman Posts: 14,633
    edited 2024-05-04 00:46

    Ok, so this is interesting... Without the addition of the p2 module that was just made, 640x480 VGA works just fine.
    But, add p2 module in and VGA is broke... But, the original 800x600 version works... Very strange...
    Thinking the screen buffer address must be hard coded into the binary blob or something...

  • RaymanRayman Posts: 14,633

    Think fixed 640x480 VGA by changing cell size from 8 to 4. Hopefully that problem doesn't come back...

  • RaymanRayman Posts: 14,633
    edited 2024-05-04 14:48

    Added a reboot function to p2 module like this:

    //HUBSET 1<<28 to reboot
    static unsigned char dat[] = {
    0x00, 0x00, 0x88, 0xFF, 0x00, 0x00, 0x64, 0xFD};

    //reboot
    STATIC mp_obj_t p2_reboot() {
       printf("Rebooting...\r\n");
       _waitms(100);
       int params=0;
       int cog=_cognew((int32_t)(((int32_t *)&dat[0])), params) + 1;
       return mp_const_none;
    }
    STATIC MP_DEFINE_CONST_FUN_OBJ_0(p2_reboot_obj, p2_reboot);
    

    Seems that riscvp2 doesn't include access to hubset instruction, so followed the @ersmith instructions to run this .Spin2 assembly code.

Sign In or Register to comment.