greiman / SdFat

Arduino FAT16/FAT32 exFAT Library
MIT License
1.07k stars 502 forks source link

Two SD card bugs since v1.0.11 #362

Open ChoCho59 opened 2 years ago

ChoCho59 commented 2 years ago

Hi, Recently I use the TwoCards example in SdFat v1.0.7 in my project, it works OK. Here are the codes :

include

include "SdFat.h"

include "FreeStack.h"

// set ENABLE_EXTENDED_TRANSFER_CLASS non-zero to use faster EX classes // Use second SPI port SdFat sd2(2); // SdFatEX sd2(2); const uint8_t SD2_CS = PB12; // chip select for sd2

const uint8_t BUF_DIM = 100; uint8_t buf[BUF_DIM];

const uint32_t FILE_SIZE = 1000000; const uint16_t NWRITE = FILE_SIZE/BUF_DIM; //------------------------------------------------------------------------------ // print error msg, any SD error codes, and halt. // store messages in flash

define errorExit(msg) errorHalt(F(msg))

define initError(msg) initErrorHalt(F(msg))

//------------------------------------------------------------------------------ void setup() { Serial.begin(57600); while (!Serial) { }

// fill buffer with known data for (size_t i = 0; i < sizeof(buf); i++) { buf[i] = i; }

// initialize the second card if (!sd2.begin(SD2_CS, SD_SCK_MHZ(18))) { sd2.initError("sd2:"); } // create Dir2 on sd2 if it does not exist if (!sd2.exists("/Dir2")) { if (!sd2.mkdir("/Dir2")) { sd2.errorExit("sd2.mkdir"); } }

// list root directory Serial.println(F("------sd2 root-------")); sd2.ls(); Serial.println(""); // make /Dir2 the default directory for sd2 if (!sd2.chdir("/Dir2")) { sd2.errorExit("sd2.chdir"); }

// list current directory Serial.println(F("------sd2 Dir2-------")); sd2.ls(); Serial.println(F("---------------------")); Serial.println(F("Done")); }

void loop() {}


I noticed that SdFat has updated to version 2. I download and installed the latest version, change only SdFat sd2(2) to SdFat sd2 in the above example, but found that it complies OK, but does not work and give the following errors :

sd2: begin() failed Do not reformat the SD. No card, wrong chip select pin, or wiring error? SdError: 0X1,0X0

I then downloaded some other older versions to test, and the results :

v1.0.8 ok using SdFat sd2(2)

v1.0.11
SdFat sd2(2) give a "invalid conversion from 'int' to 'SPIClass*' [-fpermissive]" when compiling,

change it to SdFat sd2, compiles with no error, but give running errors : sd2: Can't access SD card. Do not reformat. No card, wrong chip select pin, or SPI problem? SD errorCode: 0X20,0X0

Finally I noticed that version 2 have no example using two SD cards ! Is this a known bugs ?

greiman commented 2 years ago

I tried this old example of TwoCards.

It runs on Uno OK.

On A Mega I needed to change line 143 from: Serial.println(file2.fileSize()); To: Serial.println((uint32_t)file2.fileSize());

On boards with sufficient memory SdFat V2 support FAT and exFAT so fileSize is type uint64_t and Arduino print does not support uint64_t.

The compile output on Mega:

Sketch uses 29882 bytes (11%) of program storage space. Maximum is 253952 bytes.
Global variables use 1623 bytes (19%) of dynamic memory, leaving 6569 bytes for local variables. Maximum is 8192 bytes.

Output from example:

FreeStack: 6278
type any character to start
------sd1 root-------
Dir1/
------sd2 root-------
Dir2/
------sd1 Dir1-------
------sd2 Dir2-------
---------------------
Writing test.bin to sd1
Copying test.bin to copy.bin
File size: 1000000
Copy time: 5707 millis
------sd1 -------
2022-01-01 00:00          0 Dir1/
  2022-01-01 00:00    1000000 test.bin
------sd2 -------
2022-01-01 00:00          0 Dir2/
  2022-01-01 00:00    1000000 copy.bin
---------------------
Renaming copy.bin
------sd1 -------
2022-01-01 00:00          0 Dir1/
  2022-01-01 00:00    1000000 test.bin
------sd2 -------
2022-01-01 00:00          0 Dir2/
  2022-01-01 00:00    1000000 rename.bin
---------------------
Done
greiman commented 2 years ago

Here is the section of SdFatConfig.h where the legacy SdFat and File types are defined:

//------------------------------------------------------------------------------
/**
 * File types for SdFat, File, SdFile, SdBaseFile, fstream,
 * ifstream, and ofstream.
 *
 * Set SDFAT_FILE_TYPE to:
 *
 * 1 for FAT16/FAT32, 2 for exFAT, 3 for FAT16/FAT32 and exFAT.
 */
#ifndef SDFAT_FILE_TYPE
#if defined(__AVR__) && FLASHEND < 0X8000
// 32K AVR boards.
#define SDFAT_FILE_TYPE 1
#else  // defined(__AVR__) && FLASHEND < 0X8000
// All other boards.
#define SDFAT_FILE_TYPE 3
#endif  // defined(__AVR__) && FLASHEND < 0X8000
#endif  // SDFAT_FILE_TYPE
ChoCho59 commented 2 years ago

Sorry, my test is using a STM32F103VCT6 board with Maple core !

greiman commented 2 years ago

If you are using the Roger Clark package go to their forum. I think Steve Strong has a version of SdFat that works with that package.

I test with the STMicroelectronics package:

https://github.com/stm32duino/Arduino_Core_STM32

Here is TwoCards on a Nucleo F446RE with only Chip Select modified, uint64_t is supported in print:

FreeStack: 127248
type any character to start
------sd1 root-------
Dir1/
------sd2 root-------
Dir2/
------sd1 Dir1-------
------sd2 Dir2-------
---------------------
Writing test.bin to sd1
Copying test.bin to copy.bin
File size: 1000000
Copy time: 2501 millis
------sd1 -------
2022-01-01 00:00          0 Dir1/
  2022-01-01 00:00    1000000 test.bin
------sd2 -------
2022-01-01 00:00          0 Dir2/
  2022-01-01 00:00    1000000 copy.bin
---------------------
Renaming copy.bin
------sd1 -------
2022-01-01 00:00          0 Dir1/
  2022-01-01 00:00    1000000 test.bin
------sd2 -------
2022-01-01 00:00          0 Dir2/
  2022-01-01 00:00    1000000 rename.bin
---------------------
Done