Why does listFiles work but this code doesn't?

I am following a github on how to make an accelerometer to measure recoil on firearms (https://github.com/ammolytics/projects/tree/master/accelerometer). I was able to use the example sketches ListFiles and ReadWrite from the SD library, but when I try to run the code from the github with the debugger on, I get "initializing sd card... card failed, or not present." I don't know a lot about coding but I know I have my chip select correct, any help would be appreciated. And of course if there is any information you need to know that I forgot to include please let me know.

  DEBUG_PRINTLN("Initializing SD card...");
  if (!sd.begin(chipSelect, SD_SCK_MHZ(50))) {
    DEBUG_PRINTLN("Card failed, or not present");
    // don't do anything more:
    while (1);
  }
  DEBUG_PRINTLN("Card initialized.");

(Serial Monitor Output)

10:10:11.704 -> VBat: 4.32
10:10:11.704 -> Initializing RTC...
10:10:11.704 -> RTC initialized.
10:10:11.704 -> Filename: 202309291010.csv
10:10:11.704 -> Initializing LIS3DH Sensor...
10:10:11.704 -> LIS3DH initialized.
10:10:11.704 -> Initializing SD card...
10:10:12.015 -> Card failed, or not present

(Full code)

#include <Wire.h>
#include <SPI.h>
#include <Adafruit_LIS3DH.h>
#include <Adafruit_Sensor.h>
#include "RTClib.h"
#include "SdFat.h"


// Battery pin
#define VBATPIN A7

// I2C clock speed
#define I2C_SPEED 1000000
// Set range to 2G, 4G, 8G, 16G
#define ACCEL_RANGE LIS3DH_RANGE_8_G
// 5khz data rate
#define ACCEL_DATARATE LIS3DH_DATARATE_LOWPOWER_5KHZ
// Decimal precision for acceleration
#define ACCEL_PRECISION 3
// Separator character
#define SEP ","

// Enable debug logger.
// Note: Comment out before running in real-world.
#define DEBUG

#ifdef DEBUG
  #define DEBUG_PRINT(x)  Serial.print (x)
  #define DEBUG_PRINTLN(x)  Serial.println (x)
#else
  #define DEBUG_PRINT(x)
  #define DEBUG_PRINTLN(x)
#endif

RTC_PCF8523 rtc;

// change this to match your SD shield or module;
// Adafruit SD shields and modules: pin 10
const int chipSelect = 11;


// Filename format:  YYYYMMDDHHmm.csv
char filename[17];


unsigned long begin_us;
unsigned long begin_epoch;
unsigned long start_us;
unsigned long stop_us;
unsigned long counter = 0;


// software SPI
//Adafruit_LIS3DH lis = Adafruit_LIS3DH(LIS3DH_CS, LIS3DH_MOSI, LIS3DH_MISO, LIS3DH_CLK);
// hardware SPI
//Adafruit_LIS3DH lis = Adafruit_LIS3DH(LIS3DH_CS);
// I2C
Adafruit_LIS3DH lis = Adafruit_LIS3DH();

// set up variables using the SD utility library functions:
// File system object.
SdFat sd;
// Log file.
SdFile dataFile;


/**
 * Setup procedures.
 */
void setup() {
  #ifdef DEBUG
    Serial.begin(115200);
    while (!Serial);     // will pause Zero, Leonardo, etc until serial console opens
  #endif

  #ifdef DEBUG
    float measuredvbat = analogRead(VBATPIN);
    measuredvbat *= 2;    // we divided by 2, so multiply back
    measuredvbat *= 3.3;  // Multiply by 3.3V, our reference voltage
    measuredvbat /= 1024; // convert to voltage
    DEBUG_PRINT("VBat: " ); DEBUG_PRINTLN(measuredvbat);
  #endif

  /**
   * Initialize the Real Time Clock.
   */
  DEBUG_PRINTLN("Initializing RTC...");
  if (! rtc.begin()) {
    DEBUG_PRINTLN("Couldn't find RTC");
    while (1);
  }
  if (! rtc.initialized()) {
    DEBUG_PRINTLN("RTC is NOT running!");
  }
  DEBUG_PRINTLN("RTC initialized.");
  begin_us = micros();
  DateTime now = rtc.now();
  begin_epoch = now.unixtime();

  // Set filename based on timestamp.
  sprintf_P(filename, PSTR("%4d%02d%02d%02d%02d.csv"), now.year(), now.month(), now.day(), now.hour(), now.minute());
  DEBUG_PRINT("Filename: ");
  DEBUG_PRINTLN(filename);

  /**
   * Initialize the accelerometer.
   */
  DEBUG_PRINTLN("Initializing LIS3DH Sensor...");
  if (! lis.begin(LIS3DH_DEFAULT_ADDRESS)) {   // change this to 0x19 for alternative i2c address
    DEBUG_PRINTLN("Couldnt start");
    while (1);
  }
  // Set I2C high speedmode
  Wire.setClock(I2C_SPEED);
  lis.setRange(ACCEL_RANGE);
  lis.setDataRate(ACCEL_DATARATE);
  DEBUG_PRINTLN("LIS3DH initialized.");


  /**
   * Initialize the SD card and log file.
   */
  DEBUG_PRINTLN("Initializing SD card...");
  if (!sd.begin(chipSelect, SD_SCK_MHZ(50))) {
    DEBUG_PRINTLN("Card failed, or not present");
    // don't do anything more:
    while (1);
  }
  DEBUG_PRINTLN("Card initialized.");

  if (! dataFile.open(filename, O_CREAT | O_APPEND | O_WRITE)) {
     DEBUG_PRINTLN("Could not open file...");
     while (1);
  }
  // Write header row to file.
  dataFile.println("timestamp (s), start (µs), accel x (G), accel y (G), accel z (G)");
  dataFile.sync();
  
  // Check to see if the file exists:
  if (! sd.exists(filename)) {
    DEBUG_PRINTLN("Log file doesn't exist.");
    while (1);
  }

  DEBUG_PRINTLN("Ready!");
  DEBUG_PRINTLN("timestamp (s), start (µs), delta (µs), accel x (G), accel y (G), accel z (G)");
}


/**
 * Main Loop
 */
void loop() {
  read_accel();
  log_timers();
  log_accel();
  counter++;

  if (counter >= 1000) {
    write_sd();
    counter = 0;
  }
}


/**
 * Read from the accelerometer sensor and measure how long the op takes.
 */
void read_accel() {
  start_us = micros();
  lis.read();
  stop_us = micros();
}


/**
 * Output the timing info.
 */
void log_timers() {
  DEBUG_PRINT(begin_epoch + ((stop_us - begin_us) / 1000000));
  DEBUG_PRINT(SEP);
  DEBUG_PRINT(stop_us);
  DEBUG_PRINT(SEP);
  // Include time delta in debug output.
  DEBUG_PRINT(stop_us - start_us);
  DEBUG_PRINT(SEP);

  // Write timestamp to file.
  // Roughly equivalent to calling rtc.now().unixtime(), without 1ms latency.
  dataFile.print(begin_epoch + ((stop_us - begin_us) / 1000000));
  dataFile.print(SEP);
  // Write timers to file.
  dataFile.print(stop_us);
  dataFile.print(SEP);
}


/**
 * Output the acceleration info.
 */
void log_accel() {
  #ifdef DEBUG
    Serial.print(lis.x_g, ACCEL_PRECISION);
    Serial.print(SEP);
    Serial.print(lis.y_g, ACCEL_PRECISION);
    Serial.print(SEP);
    Serial.print(lis.z_g, ACCEL_PRECISION);
    Serial.println();
  #endif
  // Write acceleration to file.
  dataFile.print(lis.x_g, ACCEL_PRECISION);
  dataFile.print(SEP);
  dataFile.print(lis.y_g, ACCEL_PRECISION);
  dataFile.print(SEP);
  dataFile.print(lis.z_g, ACCEL_PRECISION);
  // Write newline.
  dataFile.println();
}


/**
 * Sync buffer, actually write to disk.
 * This can take between 9 and 26 milliseconds. Or ~10ms with SDfat.
 */
void write_sd() {
  DEBUG_PRINTLN("Writing to SD card");
  unsigned long pre_write = micros();
  dataFile.sync();
  DEBUG_PRINT("Write ops took: ");
  DEBUG_PRINTLN(micros() - pre_write);
}

Please take a few minutes and read How to get the best out of this forum. Code should always be surrounded by <code>...</code> tags. And please post your complete code; no one has a crystal ball to solve problems in code we can't see.

I apologize for my mistake. That link was very helpful and I will make sure to follow that in future posts. I have updated the post with the code tags, as well as included the full code at the bottom.

Does your listFiles example use the same initialization for the SD card? Depending on the hardware involved, 50MHz is pretty aggressive .

If it's not too much to ask, could you briefly explain what the SD_SCK_MHZ line is doing? and what would you recommend I change the value to?
This is the code I used to test the SD card that worked.

/*
  Listfiles

  This example shows how print out the files in a
  directory on a SD card

  The circuit:
   SD card attached to SPI bus as follows:
 ** MOSI - pin 11
 ** MISO - pin 12
 ** CLK - pin 13
 ** CS - pin 4 (for MKRZero SD: SDCARD_SS_PIN)

  created   Nov 2010
  by David A. Mellis
  modified 9 Apr 2012
  by Tom Igoe
  modified 2 Feb 2014
  by Scott Fitzgerald

  This example code is in the public domain.

*/
#include <SPI.h>
#include <SD.h>

File root;

void setup() {
  // Open serial communications and wait for port to open:
  Serial.begin(9600);
  while (!Serial) {
    ; // wait for serial port to connect. Needed for native USB port only
  }

  Serial.print("Initializing SD card...");

  if (!SD.begin(11)) {
    Serial.println("initialization failed!");
    while (1);
  }
  Serial.println("initialization done.");

  root = SD.open("/");

  printDirectory(root, 0);

  Serial.println("done!");
}

void loop() {
  // nothing happens after setup finishes.
}

void printDirectory(File dir, int numTabs) {
  while (true) {

    File entry =  dir.openNextFile();
    if (! entry) {
      // no more files
      break;
    }
    for (uint8_t i = 0; i < numTabs; i++) {
      Serial.print('\t');
    }
    Serial.print(entry.name());
    if (entry.isDirectory()) {
      Serial.println("/");
      printDirectory(entry, numTabs + 1);
    } else {
      // files have sizes, directories do not
      Serial.print("\t\t");
      Serial.println(entry.size(), DEC);
    }
    entry.close();
  }
}




It's setting the clock frequency for the SPI. Even with Adafruit uSD adapters, I've had troubles with it set that high. You might want to try setting it to 25 or even lower and seeing if it makes any difference.

And I see another potential pitfall. Listfiles is using the SD library. Your code is using the SdFat library. Now, on some hardware, there's not much difference between them (I know with at least one architecture, SD is just shim code around SdFat - or maybe it's the other way around, I'd have to check), but it's possible that with whatever board you're using, that's not the case. If reducing the clock frequency doesn't do the trick, try modding your code to use the SD library rather than SdFat.

I think you are right about the library because changing the clock frequency didnt change anything. Is there a certain line of code that is calling on the SDFat library instead of the SD library? If I were to just uninstall the SDFat library would that change anything at all?

You'd have to change several things, beginning with #include <SD.h> rather than #include <SdFat.h>. SdFile would become File, sd. would become SD.... and it wouldn't surprise me if there's many more.

Another oddity I just noticed is the in both sketches, the chip select line is defined as pin 11. Now, you haven't mentioned anything about the board you're using (and that's another thing you really should do), but, assuming it's an Uno, pin 11 is the MOSI line. That seems odd to me. Of course, that's not knowing what board you're using, so maybe it's a red herring.

Oh of course! I'm so sorry I thought I had mentioned the components but it must've slipped passed me. I am using an adafruit feather M0 Bluefruite LE (nRF52832) as my board, and the adalogger FeatherWing (RTC + SD) to hold the SD card. On the Feather M0 the CS pin is pin 11.

Cross posting wastes everyone's time and is against forum rules.

This topic was automatically closed 180 days after the last reply. New replies are no longer allowed.