SPI conflict with SD card

SPI conflict with SD card

I could not get two cards communicating using the SPI bus Arduino to work when both were plugged in. Both cards worked when the other card was unplugged.

It turned out that the microSD card was not de-selecting, holding the MISO pin low, so the other card, when selected, was trying unsuccessfully to send pulses to the Arduino. So a hardware conflict.

I fixed this with a mod to the SD card, to remove the tri-state control of the chip select buffer from ground, and wired it to the CS pin. So the hardware of both cards worked the way they should, with both cards accessing the SPI bus.

However the SD.begin changed the SPI bus parameters so that the other card would not then correctly work through the SPI.

I have looked at SD.h and SD.cpp but cannot understand it enough to diagnose what the problem is. Can anyone help please?

The sketch gets ten adc readings of a battery, then starts the SD card, then another ten readings. Below the code are the results, showing the readings obtained.

(I don’t know how to add code, so I have attached a .ino and a .pdf file of the hardware fix of Catalex at catalex.taobao.com MicroSD Card Adapter V1.0 11/01/2013.)

uSDcard.pdf (36.5 KB)

adcsdconflict.ino (1.44 KB)

Where did you get the AD770X library from?

Some notes:

SD.begin should only be needed once (in setup).

Disclaimer: not very familiar with SPI (never really used it).

The normal SPI approach is to first activate one device (CS) and de-activate the others. Once you have read the device, activate one of the other devices (CS) and de-activate the others.
So activate the AD CS line, reset() and init() it, next de-activate the AD CS line and activate the SD card’s CS line and begin() it, next de-activate the SD card’s CS line.

The same applies for reading the AD or SD.

OP’s pdf contains a schematic; @OP, itwould have been better if you would have attached an image that could have been placed in a post
OP’s code

/* test for SPI software conflict between ADC AD7705 and SD card.
*/
#include <AD770X.h>
#include <SD.h>
#include <SPI.h>

AD770X ad7705(4750);
double v;

//const int adcChipSelectPin = 10;
const int sdChipSelectPin = 9;

void setup() {
  Serial.begin(9600);
  
  pinMode(sdChipSelectPin, OUTPUT);
  digitalWrite(sdChipSelectPin, HIGH);
  
  ad7705.reset();
  ad7705.init(AD770X::CHN_AIN1); 
}

void loop() {
  for (int n = 0; n < 10; n++) {
  Serial.println(ad7705.readADResult(AD770X::CHN_AIN1)); 
  }
  
  if (!SD.begin(sdChipSelectPin)) {  // see if the SD card is present and can be initialized:
    Serial.println("Card failed, or not present");
    while (1);                       // don't do anything more:
  }
  Serial.println("card initialized.");
/*
 if (digitalRead(sdChipSelectPin) == LOW) {
    Serial.println(F("SD CS is LOW"));
    digitalWrite(sdChipSelectPin, HIGH);
  } else {
    Serial.println(F("SD SS is HIGH, good!"));
  }
  */
//  SD.end();
//  SPI.end(); SPI.begin();
//  SPI.setDataMode(SPI_MODE0);    // I tried these, but still the same result
//  SPI.setClockDivider(SPI_CLOCK_DIV32);

  for (int n = 0; n < 10; n++) {
  Serial.println(ad7705.readADResult(AD770X::CHN_AIN1)); 
  }
  while(1){}
}
/*
1433.20
1433.13
1433.13
1433.06
1433.06
1432.99
1432.91
1432.99
1433.06
1433.13
card initialized.
1781.18
296.80
296.80
296.80
296.80
296.80
296.80
296.80
296.80
296.80
*/