@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.
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...
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.
@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.
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...
@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...
@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.
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…
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.
@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.
@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.
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...
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.
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?
@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?
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?
@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
@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...
@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.
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...
Comments
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.
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.
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:
Might have to look at the Linux version to see what it's actually supposed to look like...
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.
@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?
Sorry, one more…
Would including the new littlefs flash drive support be so easy I could do it?
Or, is this complicated ?
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 .
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.
Think found some instructions for creating C modules for micropython that are easily understood:
https://micropython-usermod.readthedocs.io/en/latest/usermods_05.html
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...
@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...
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.
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…
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.
@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.
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.
The code compression is the
c
inrv32imac
. It's on by default, and it does help the code size quite a bit.Thanks @ersmith
Think I'm seeing something that is a bit dissapointing...
Seems I can make constants like this:
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.
I see how to get the free mem in REPL:
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) {
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?
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 thep2
module?Suppose that's true... Should focus on new features..
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'
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
@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...
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
Had 640x480 VGA working, but somehow broke it... 800x600 still works though..
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?
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.
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.
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...
Think fixed 640x480 VGA by changing cell size from 8 to 4. Hopefully that problem doesn't come back...
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};
Seems that riscvp2 doesn't include access to hubset instruction, so followed the @ersmith instructions to run this .Spin2 assembly code.