Upcoming maintenance
Dear Customers and Partners.
This website will be undergoing scheduled maintenance on June 14, 2023. Please be aware there may be disruption to the developer portal website and associated services during the scheduled maintenance period.
This upgrade is essential to ensure the continued performance, reliability, and security of Developer World.
We apologize for any inconvenience.
Unsolved Run external SPI SD card module on Spresense Main Board
-
Hi there!
I've been working on Spresense Main Board for 3 months. I ran on this issue at the begging of the project, but now I faced it again.I'm using Arduino IDE right now but i'm willing to switch to Nuttx operating system when I will have my first working demo of the project running with Arduino Framework, which I already know enough.
I'm NOT using the Spresense extension board because of the dimension of it. So bought an external SPI SD card module called MH-SD Card module.
I already have it running on a ESP32 dev board, so I'm sure it works fine and the SD Card itself too.When I try to connect the SPI SD and setup the code, it doesn't work. This is my sketch, copied from File > Examples > Examples for Spresense:
/* SD card test This example shows how use the utility libraries on which the' SD library is based in order to get info about your SD card. Very useful for testing a card when you're not sure whether its working or not. The circuit: SD card attached to SPI bus as follows: ** MOSI - pin 11 on Arduino Uno/Duemilanove/Diecimila ** MISO - pin 12 on Arduino Uno/Duemilanove/Diecimila ** CLK - pin 13 on Arduino Uno/Duemilanove/Diecimila ** CS - depends on your SD card shield or module. Pin 4 used here for consistency with other Arduino examples created 28 Mar 2011 by Limor Fried modified 9 Apr 2012 by Tom Igoe */ // include the SD library: #include <SPI.h> #include <SD.h> // set up variables using the SD utility library functions: Sd2Card card; SdVolume volume; SdFile root; // change this to match your SD shield or module; // Arduino Ethernet shield: pin 4 // Adafruit SD shields and modules: pin 10 // Sparkfun SD shield: pin 8 // MKRZero SD: SDCARD_SS_PIN const int chipSelect = 18; //the same used on Spresense LoRa module connectivity. void setup() { // Open serial communications and wait for port to open: Serial.begin(115200); while (!Serial) { ; // wait for serial port to connect. Needed for native USB port only } Serial.print("\nInitializing SD card..."); // we'll use the initialization code from the utility libraries // since we're just testing if the card is working! if (!card.init(SPI_HALF_SPEED, chipSelect)) { Serial.println("initialization failed. Things to check:"); Serial.println("* is a card inserted?"); Serial.println("* is your wiring correct?"); Serial.println("* did you change the chipSelect pin to match your shield or module?"); while (1); } else { Serial.println("Wiring is correct and a card is present."); } // print the type of card Serial.println(); Serial.print("Card type: "); switch (card.type()) { case SD_CARD_TYPE_SD1: Serial.println("SD1"); break; case SD_CARD_TYPE_SD2: Serial.println("SD2"); break; case SD_CARD_TYPE_SDHC: Serial.println("SDHC"); break; default: Serial.println("Unknown"); } // Now we will try to open the 'volume'/'partition' - it should be FAT16 or FAT32 if (!volume.init(card)) { Serial.println("Could not find FAT16/FAT32 partition.\nMake sure you've formatted the card"); while (1); } Serial.print("Clusters: "); Serial.println(volume.clusterCount()); Serial.print("Blocks x Cluster: "); Serial.println(volume.blocksPerCluster()); Serial.print("Total Blocks: "); Serial.println(volume.blocksPerCluster() * volume.clusterCount()); Serial.println(); // print the type and size of the first FAT-type volume uint32_t volumesize; Serial.print("Volume type is: FAT"); Serial.println(volume.fatType(), DEC); volumesize = volume.blocksPerCluster(); // clusters are collections of blocks volumesize *= volume.clusterCount(); // we'll have a lot of clusters volumesize /= 2; // SD card blocks are always 512 bytes (2 blocks are 1KB) Serial.print("Volume size (Kb): "); Serial.println(volumesize); Serial.print("Volume size (Mb): "); volumesize /= 1024; Serial.println(volumesize); Serial.print("Volume size (Gb): "); Serial.println((float)volumesize / 1024.0); Serial.println("\nFiles found on the card (name, date and size in bytes): "); root.openRoot(volume); // list all files in the card with date and size root.ls(LS_R | LS_DATE | LS_SIZE); } void loop(void) { }
I didn't found any other libraries to run an external sd card module and I'm starting to think that Sony Engineers haven't wrote a compatible library for external sd spi modules? (Maybe).
I really hope there's a solution for this, and I end my question telling that, as I said, at the end of my project, I will switch to Nuttx. But when I tried, SPI SD card module didn't work neither. I also followed some tutorials of Nuttx kernel compiling but.. nothing!
I'm sure this is my mistake but I'd really need help.
-
@metafrollo A few thoughts
- I would recommend to switch to the Spresense SDK sooner than later. Especially if you want to do it anyway.
- The Spresense SDK mainly uses the NuttX interfaces. However other implementations could require quite some effort to port to the NuttX API. (You could also include parts of the Spresense Arduino Core inside your NuttX based build and use both worlds)
- Arduino libraries outside of the Spresense Arduino SDK usually create effort because they do not work out of the box, perform poorly or even have bugs. It highly depends on what you use and require.
- If there is a configuration in NuttX, things work out really well and are easy to use. For example the networking just works with the e.g. the MQTT library or AWS IoT library or the webclient library. No need to use incomplete Arduino libraries and tinker around with AT commands.
About the SD card. (I have no experience with external SD Card boards on Spresense)
- The NuttX implementation of SD card access for cxd5602 is based on SDIO, not SPI. So your options are
- Using another extension board that is smaller (e.g. LTE extension board). It is an expensive option. And small 3rd party extension boards are not available at all (sold out). In general any 3rd party hardware is produced in low volume and the support is soso.
- Break out the SDIO pins yourself with a custom board or with this xn--SPRESENSE 100B2B -gj5plczmqb4b8q2fi11fi445f1ggf71g52wa0y0h.
- Configure NuttX SPI SD Card CONFIG_CXD56_SPISD with the SPI channel you use (5 on the main board)
I would give #2 a try.
However I would assume that the library you use should work. I am wondering how you connected the SD card breakout board to the Spresense board? The main board runs on 1.8V. This could be a challenge on its own (except SD cards work with 1.8V which I do not know. At least the extension board uses a dedicated chip between cxd5602 and the SD card slot. See here)
-
@jens6151-0-1-1 Two more comments
- How does the library you use know that you attached your SD Card to SPI5 on the main board? Probably this gets wrong.
- There is also the option "SPI5 pin configuration" in NuttX. Maybe you can change it to CXD56_SPI5_PINMAP_SDIO and use the SDIO implementation?