I prepared an example for a friend and thought I'd drop a copy here.
I will try to answer questions more specific than "how does it work?" with more details than "read the code".
This uses an LCSOFT SD adapter wired direct to an UNO. It will work fine with a home-rolled SD too.
I can't say for any shield but differences should not be much beyond connections and CS pin number.
The "big deal" is in addressing the struct with a byte pointer and writing/reading sizeof() the struct bytes.
You can transfer many variables (settings, SRAM image, etc) with very little code this way.
// Testing SD Module connected to Arduino UNO
// This UNO is running IDE version 1.03
// Arduino SPI library and SD library are imported using the
// Sketch->Import Library pop-down menu. Both are standard.
// SD Lib reference: http://arduino.cc/en/Reference/SD
// This sketch demonstrates writing a struct to file as a block and
// reading it back to a struct.
// Connections:
// SD Module pin --- UNO pin
// GND --- GND
// 3.3V --- 3.3V
// 5V --- 5V
// CS --- 10
// MOSI --- 11
// SCK --- 13
// MISO --- 12
// GND --- GND
#include <avr/io.h>
#include <avr/pgmspace.h>
#include <SPI.h>
#include <SD.h>
#define CARD_CS 10
struct myVars
{
byte b0;
byte b1;
int i2;
int i3;
char s4[ 20 ];
};
// ====================================================================
void setup(void)
{
pinMode( CARD_CS, OUTPUT );
digitalWrite( CARD_CS, LOW );
Serial.begin( 9600 );
byte count;
struct myVars example; // creates space for struct example in SRAM
struct myVars copyto; // creates space for struct example in SRAM
byte *buff = (byte *) &example; // to access example as bytes
example.b0 = 1; // fill example with test data, copyto stays empty
example.b1 = 20;
example.i2 = 3000;
example.i3 = 4000;
strcpy( example.s4, "file is test.txt" );
File sdfile; // File object
char fname[ 14 ]; // even # of bytes big enough to hold 8.3 filename and terminator
strcpy( fname, "test.txt" );
// ========== SD begin ====================================
byte flag = SD.begin( ); // test if card is recognized
Serial.print( F("SD card status " ));
Serial.print( flag, DEC ); // show success as 1, fail as 0
if ( !flag )
{
Serial.println( F( " Failed to recognize SD card. Goodbye." ));
while( 1 ); // if fail then sketch ends
}
else
{
Serial.println( F( " is good to go." ));
}
// ========== SD open/create file to write ============================
strcpy( fname, "test.txt" );
sdfile = SD.open( fname, FILE_WRITE );
if ( !sdfile )
{
Serial.print( F( "Unable to open for write: " ));
Serial.println( fname );
while( 1 ); // sketch stops if reach here
}
// ========== SD write struct to file =================================
// this file will only contain 1 struct although it could hold many
// since opening a file that already exists for write will start at the end
// we will set the read/write pointer at the start so as not to grow the file
if ( !sdfile.seek( 0 ))
{
Serial.print( F( "Unable to set seek: " ));
Serial.println( fname );
while( 1 ); // sketch stops if reach here
}
count = sdfile.write( buff, sizeof( myVars ));
if ( count != sizeof( myVars ))
{
Serial.print( F( "Unable to write the example block to " ));
Serial.println( fname );
Serial.print( count, DEC );
Serial.println( F( " bytes written." ));
while( 1 ); // sketch stops if reach here
}
// ========== SD close file ===========================================
sdfile.close(); // I could error check this. If it fails the next open will too.
// ========== SD open file to read ====================================
sdfile = SD.open( fname, FILE_READ ); // try to open text.txt
if ( !sdfile ) // if test.txt not found, notify and change state
{
Serial.print( "Unable to open for read: " );
Serial.println( fname );
while( 1 );
}
// ========== SD read file to struct ==================================
buff = (byte *) ©to; // to access copyto as bytes
for ( count = 0; count < sizeof( myVars ); count++ )
{
if ( sdfile.available())
{
*( buff + count ) = sdfile.read();
}
else
{
Serial.print( F( "Unable to read the example block in " ));
Serial.println( fname );
Serial.print( count, DEC );
Serial.println( F( " bytes read." ));
while( 1 ); // sketch stops if reach here
}
}
// ========== SD close file ===========================================
sdfile.close(); // I could error check this too.
// ========== print retrieved data ====================================
Serial.print( F( "\n Data in copyto block from " ));
Serial.println( fname );
Serial.print( F( "\ncopyto byte b0 " ));
Serial.println( copyto.b0, DEC );
Serial.print( F( "copyto byte b1 " ));
Serial.println( copyto.b1, DEC );
Serial.print( F( "copyto byte i2 " ));
Serial.println( copyto.i2, DEC );
Serial.print( F( "copyto byte i3 " ));
Serial.println( copyto.i3, DEC );
Serial.print( F( "copyto string s4 " ));
Serial.println( copyto.s4 );
// ========== finished ================================================
}
void loop(void)
{
}