-
Notifications
You must be signed in to change notification settings - Fork 131
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
spi.write() (in C, in Makecode extension) crashes the Microbit? #465
Comments
Update: The I tested this by removing all of the set-up calls in The LCD screen does not use the MISO pin. Therefore there is no interaction with the screen that could be affected by omitting the set-up calls within |
I have finally discovered what the curious problem is, and it makes no sense to me. Surely this is a bug? When I successfully no longer have SPI write operations in the Javascript part of my extension, having moved them all to C, I find that the thing crashes at the
Even though in the CPP file I have this:
...which clearly inititalises the SPI device in C. Why does it need to be either formatted or frequency-set in the JS too? That makes no sense to me. |
It makes no sense to me either, but I hope this helps... I searched the MakeCode source for spiFrequency. In pins.cpp, pins.spiFrequency() calls allocSPI(), which calls The extension cpp file uses another SPI object defined by I would remove that and use the pins.spiXXX functions instead. I think MOSI, MISO and SCK are 15,14 and 13 by default. |
I can understand that the SPI device is not initialised by default - and therefore isn't visible as any Unfortuntely, executing SPI calls from the Javascript is very time-consuming - I can save 15% of the run-time by using C++ to deliver all 504 bytes of a buffer to the SPI device simply because even a simple FOR loop in JS is not efficiently coded. Therefore I have ported to C++ absoutely everything in my extension for driving the 84x48 pixel Nokia 3310 LCD screen. Earlier I submitted this issue: https://github.com/lancaster-university/microbit-dal/issues/464 while I was trying to get to grips with C++. @mmoskal said he would be adding a I really hope the equivalent function will be available to call from a cpp extension too? |
I may be missing some reason why this is the wrong thing to do, but if you put the declarations below at the top of your CPP file, you can delete the SPI object and use the pins functions. allocSPI() gives a pointer to call SPI::write directly. I can't test if it actually works, but I seem to be able to remove the pins call from the ts file without it crashing. I initially included a declaration for spiPins, but got complaints about DigitalPin. Don't know why.
|
Thank you. It's a bit beyond my understanding of C++ and so by trial and error I found it could just call I then deleted the seemingly unnecessary However, I'm a bit surprised that using this method rather than original SPI object makes my buffer transfer (a FOR loop with For now I will leave your method in as it certainly "looks better". Hopefully we'll see the spiTransfer() function at a later date. |
Where typescript says "declare namespace pins" and "pins.", C++ says "namespace pins" and "pins::". And "using namespace pins" removes the need for "pins::". spiWrite is better than spi->write() for future compatibility. Even better, spiTransfer( bytebuffer, NULL) is now supported in the MakeCode beta. The declaration would be An unexpectedly large jump in the loop time may be due to a small difference in the code causing loop iterations to contain extra regular interrupts. I wonder what happens to the transfer times if the micro:bit screen is disabled (better?), or if Bluetooth is connected (worse?). |
I've tested that on the beta. I think it's a shame that there isn't a more native SPI buffer transfer routine which could eliminate more of the overheads from repeatedly calling spiWrite() through however many layers of abstraction: for a receiving device (eg LCD screen) which is capable of accepting an unbroken stream of bits and which doesn't deliver data back again, it would be lovely to be able to get as close as possible to an unbroken stream of bits delivered by the Microbit. I guess there would be a difference in circumstances when the Microbit needs to read the receive-buffer. |
I have a situation in which a write to SPI seems to crash the Microbit. I’ve been looking at this for an hour or two now but cannot see what is wrong.
My Makecode extension to drive a Nokia 3310 LCD screen (84 x 48 pixels) is in this repository
https://github.com/MTKilpatrick/pxt-nokialcd
The TS file has shims for lots of functions that I have transferred to the .CPP file to speed up all the graphics. I’m transferring all the SPI routines to C as well.
The extension beings by calling
init()
in JS which in turn callsSPIinit()
(in the CPP) to initialise the SPI port.init()
then sets up the LCD display with several commands - these are determine by setting Digital Pin16 to low (LCD_CMD). Data writes to the screen are performed when P16 is high (LCD_DAT). The chip select is performed by P12 and reset by P8.The first set-up call is
writeFunctionSet()
thenlcdExtenedFunctions()
which sets the display into a command mode in order to set up a few parameters.writeFunctionSet()
exists in both the JS and C files.This extension makes the Microbit hang up if I use the
shim=nokialcd::writeFunctionSet
to make it use the C version of the function. If I use the JS version by removing the shim, the whole thing works.If you look at the code in both the TS and CPP files,
writeFunction()
is identical. It merely sets P12 and P16 to the appropriate states, callsspi.write()
with a value and then reverts P12 and P16.Please note that
spi.write()
is also used in the functionwriteSPIBuf()
in the CPP file - this transfers the 504-byte buffer to the screen. This function works and I have tested it.Unless I comment out the
spi.write(0x20 | (v << 1) | (h & 1));
line inwriteFunctionSet,
the init() hangs up and does not exit from the call towriteFunctionSet,
Line 72 of nokialcd.ts.The text was updated successfully, but these errors were encountered: