Guide to Arduino & Secure Digital (SD) Storage.
Browse through a series of examples on how to read and write to SD cards from an Arduino board.
This article was revised on 2021/11/18 by Karl Söderby.
This guide collects compatible hardware and great code examples that you can use if you want to get started with Secure Digital (SD) cards.
The examples in this guide comes from the SD Library, which originally is based on SdFat by William Greiman.
Hardware & Software Required
*The boards/shields that have an SD card slot are listed below:
- MKR Zero
- MKR IoT Carrier
- MKR MEM Shield
- MKR SD Proto Shield
- MKR ENV Shield
- MKR Ethernet Shield
- Arduino Education Shield
Circuit
Here is an example of how to insert an SD card into the MKR Zero board. None of the examples below requires any additional circuit.
Examples
Below are a series of examples
Read and Write
This example shows how to read and write data to and from an SD card.
- In
, create a new file withsetup()
named "test.txt".SD.open()
enables read and write access to the file, starting at the end. If a fileFILE_WRITE
was already on the card, that file would be opened."test.txt"
- Name the instance of the opened file "myFile".
- Once opened, use
to write a string to the card, followed by a carriage return. Once the content is written, close the file.myFile.println()
- Again, open the file with
. Once opened, ask the Arduino to read the contents of the file withSD.open()
and send them over the serial port. After all the contents of the file are read, close the file withSD.read()
.SD.close()
Note that pin 4 is default Chip Select (CS) pin for most boards. To set CS for MKR Zero, you can use 28 instead of 4, alt. use the SDCARD_SS_PIN definition.
1/*2 SD card read/write3
4 This example shows how to read and write data to and from an SD card file5 The circuit:6 SD card attached to SPI bus as follows:7 ** MOSI - pin 118 ** MISO - pin 129 ** CLK - pin 1310 ** CS - pin 4 (for MKRZero SD: SDCARD_SS_PIN)11
12 created Nov 201013 by David A. Mellis14 modified 9 Apr 201215 by Tom Igoe16
17 This example code is in the public domain.18
19*/20
21#include <SPI.h>22#include <SD.h>23
24File myFile;25
26void setup() {27 // Open serial communications and wait for port to open:28 Serial.begin(9600);29 while (!Serial) {30 ; // wait for serial port to connect. Needed for native USB port only31 }32
33
34 Serial.print("Initializing SD card...");35
36 if (!SD.begin(4)) {37 Serial.println("initialization failed!");38 while (1);39 }40 Serial.println("initialization done.");41
42 // open the file. note that only one file can be open at a time,43 // so you have to close this one before opening another.44 myFile = SD.open("test.txt", FILE_WRITE);45
46 // if the file opened okay, write to it:47 if (myFile) {48 Serial.print("Writing to test.txt...");49 myFile.println("testing 1, 2, 3.");50 // close the file:51 myFile.close();52 Serial.println("done.");53 } else {54 // if the file didn't open, print an error:55 Serial.println("error opening test.txt");56 }57
58 // re-open the file for reading:59 myFile = SD.open("test.txt");60 if (myFile) {61 Serial.println("test.txt:");62
63 // read from the file until there's nothing else in it:64 while (myFile.available()) {65 Serial.write(myFile.read());66 }67 // close the file:68 myFile.close();69 } else {70 // if the file didn't open, print an error:71 Serial.println("error opening test.txt");72 }73}74
75void loop() {76 // nothing happens after setup77}
Card Information
This example shows how to read information about a SD card. The example reports volume type, free space and other information using the SD library, sending it over the serial port.
1/*2
3 SD card test4
5 This example shows how use the utility libraries on which the'6
7 SD library is based in order to get info about your SD card.8
9 Very useful for testing a card when you're not sure whether its working or not.10
11 Pin numbers reflect the default SPI pins for Uno and Nano models12
13 The circuit:14
15 SD card attached to SPI bus as follows:16
17 ** SDO - pin 11 on Arduino Uno/Duemilanove/Diecimila18
19 ** SDI - pin 12 on Arduino Uno/Duemilanove/Diecimila20
21 ** CLK - pin 13 on Arduino Uno/Duemilanove/Diecimila22
23 ** CS - depends on your SD card shield or module.24
25 Pin 10 used here for consistency with other Arduino examples26
27 created 28 Mar 201128
29 by Limor Fried30
31 modified 24 July 202032
33 by Tom Igoe34
35*/36// include the SD library:37#include <SPI.h>38#include <SD.h>39
40// set up variables using the SD utility library functions:41
42Sd2Card card;43
44SdVolume volume;45
46SdFile root;47
48// change this to match your SD shield or module;49// Default SPI on Uno and Nano: pin 1050// Arduino Ethernet shield: pin 451// Adafruit SD shields and modules: pin 1052// Sparkfun SD shield: pin 853// MKRZero SD: SDCARD_SS_PIN54
55const int chipSelect = 10;56
57void setup() {58
59 // Open serial communications and wait for port to open:60
61 Serial.begin(9600);62
63 while (!Serial) {64
65 ; // wait for serial port to connect. Needed for native USB port only66
67 }68
69 Serial.print("\nInitializing SD card...");70
71 // we'll use the initialization code from the utility libraries72
73 // since we're just testing if the card is working!74
75 if (!card.init(SPI_HALF_SPEED, chipSelect)) {76
77 Serial.println("initialization failed. Things to check:");78
79 Serial.println("* is a card inserted?");80
81 Serial.println("* is your wiring correct?");82
83 Serial.println("* did you change the chipSelect pin to match your shield or module?");84
85 while (1);86
87 } else {88
89 Serial.println("Wiring is correct and a card is present.");90
91 }92
93 // print the type of card94
95 Serial.println();96
97 Serial.print("Card type: ");98
99 switch (card.type()) {100
101 case SD_CARD_TYPE_SD1:102
103 Serial.println("SD1");104
105 break;106
107 case SD_CARD_TYPE_SD2:108
109 Serial.println("SD2");110
111 break;112
113 case SD_CARD_TYPE_SDHC:114
115 Serial.println("SDHC");116
117 break;118
119 default:120
121 Serial.println("Unknown");122
123 }124
125 // Now we will try to open the 'volume'/'partition' - it should be FAT16 or FAT32126
127 if (!volume.init(card)) {128
129 Serial.println("Could not find FAT16/FAT32 partition.\nMake sure you've formatted the card");130
131 while (1);132
133 }134
135 Serial.print("Clusters: ");136
137 Serial.println(volume.clusterCount());138
139 Serial.print("Blocks x Cluster: ");140
141 Serial.println(volume.blocksPerCluster());142
143 Serial.print("Total Blocks: ");144
145 Serial.println(volume.blocksPerCluster() * volume.clusterCount());146
147 Serial.println();148
149 // print the type and size of the first FAT-type volume150
151 uint32_t volumesize;152
153 Serial.print("Volume type is: FAT");154
155 Serial.println(volume.fatType(), DEC);156
157 volumesize = volume.blocksPerCluster(); // clusters are collections of blocks158
159 volumesize *= volume.clusterCount(); // we'll have a lot of clusters160
161 volumesize /= 2; // SD card blocks are always 512 bytes (2 blocks are 1KB)162
163 Serial.print("Volume size (Kb): ");164
165 Serial.println(volumesize);166
167 Serial.print("Volume size (Mb): ");168
169 volumesize /= 1024;170
171 Serial.println(volumesize);172
173 Serial.print("Volume size (Gb): ");174
175 Serial.println((float)volumesize / 1024.0);176
177 Serial.println("\nFiles found on the card (name, date and size in bytes): ");178
179 root.openRoot(volume);180
181 // list all files in the card with date and size182
183 root.ls(LS_R | LS_DATE | LS_SIZE);184
185 root.close();186}187
188void loop(void) {189}
Please note: the cluster size is defined at format time by the user and has some default values that can be changed by users following some rules. In the sketch above we are using the default size for a block that is set at 512 bytes by standards. This value is not the cluster size: that is calculated as the number of blocks per cluster. You may find more in depth information about cluster sizes in this article.
Dump File
This example shows how to read a file from a SD card using the SD library and send it over the serial port.
On the SD card, there is a file named "datalog.txt". In the
loop()
, the file is opened when calling SD.open()
. To send the file serially to a computer, use Serial.print()
, reading the contents of the file with SD.read()
.1/*2
3 SD card file dump4
5 This example shows how to read a file from the SD card using the6
7 SD library and send it over the serial port.8
9 Pin numbers reflect the default SPI pins for Uno and Nano models.10
11 The circuit:12
13 SD card attached to SPI bus as follows:14
15 ** SDO - pin 1116
17 ** SDI - pin 1218
19 ** CLK - pin 1320
21 ** CS - depends on your SD card shield or module.22
23 Pin 10 used here for consistency with other Arduino examples24
25 (for MKRZero SD: SDCARD_SS_PIN)26
27 created 22 December 201028
29 by Limor Fried30
31 modified 9 Apr 201232
33 by Tom Igoe34
35 This example code is in the public domain.36
37*/38#include <SD.h>39
40const int chipSelect = 10;41
42void setup() {43
44 // Open serial communications and wait for port to open:45
46 Serial.begin(9600);47
48 // wait for Serial Monitor to connect. Needed for native USB port boards only:49
50 while (!Serial);51
52 Serial.print("Initializing SD card...");53
54 if (!SD.begin(chipSelect)) {55
56 Serial.println("initialization failed. Things to check:");57
58 Serial.println("1. is a card inserted?");59
60 Serial.println("2. is your wiring correct?");61
62 Serial.println("3. did you change the chipSelect pin to match your shield or module?");63
64 Serial.println("Note: press reset or reopen this serial monitor after fixing your issue!");65
66 while (true);67
68 }69
70 Serial.println("initialization done.");71
72 // open the file. note that only one file can be open at a time,73
74 // so you have to close this one before opening another.75
76 File dataFile = SD.open("datalog.txt");77
78 // if the file is available, write to it:79
80 if (dataFile) {81
82 while (dataFile.available()) {83
84 Serial.write(dataFile.read());85
86 }87
88 dataFile.close();89
90 }91
92 // if the file isn't open, pop up an error:93
94 else {95
96 Serial.println("error opening datalog.txt");97
98 }99}100
101void loop() {102}
File Management
This example shows how to create and destroy a file on a SD card.
In the
setup()
, open a new file with SD.open()
named "example.txt". FILE_WRITE
enables read and write access to the file, starting at the end. In this example though, immediately close the file by calling myFile.close()
.After checking to make sure the file exists with
SD.exists()
, delete the file from the card with SD.remove
.1/*2
3 SD card basic file example4
5 This example shows how to create and destroy an SD card file6
7 The circuit. Pin numbers reflect the default8
9 SPI pins for Uno and Nano models:10
11 SD card attached to SPI bus as follows:12
13 ** SDO - pin 1114
15 ** SDI - pin 1216
17 ** CLK - pin 1318
19 ** CS - depends on your SD card shield or module.20
21 Pin 10 used here for consistency with other Arduino examples22
23 (for MKRZero SD: SDCARD_SS_PIN)24
25 created Nov 201026
27 by David A. Mellis28
29 modified 24 July 202030
31 by Tom Igoe32
33 This example code is in the public domain.34
35*/36#include <SD.h>37
38const int chipSelect = 10;39
40File myFile;41
42void setup() {43
44 // Open serial communications and wait for port to open:45
46 Serial.begin(9600);47
48 // wait for Serial Monitor to connect. Needed for native USB port boards only:49while (!Serial);50
51 Serial.print("Initializing SD card...");52
53 if (!SD.begin(10)) {54
55 Serial.println("initialization failed!");56
57 while (1);58
59 }60
61 Serial.println("initialization done.");62
63 if (SD.exists("example.txt")) {64
65 Serial.println("example.txt exists.");66
67 } else {68
69 Serial.println("example.txt doesn't exist.");70
71 }72
73 // open a new file and immediately close it:74
75 Serial.println("Creating example.txt...");76
77 myFile = SD.open("example.txt", FILE_WRITE);78
79 myFile.close();80
81 // Check to see if the file exists:82
83 if (SD.exists("example.txt")) {84
85 Serial.println("example.txt exists.");86
87 } else {88
89 Serial.println("example.txt doesn't exist.");90
91 }92
93 // delete the file:94
95 Serial.println("Removing example.txt...");96
97 SD.remove("example.txt");98
99 if (SD.exists("example.txt")) {100
101 Serial.println("example.txt exists.");102
103 } else {104
105 Serial.println("example.txt doesn't exist.");106
107 }108}109
110void loop() {111
112 // nothing happens after setup finishes.113}
List Files
This example shows how to list the files available in the directory of the SD card.
The main
loop()
does nothing because the function that prints out the file directory of "/" of the SD card is called from the setup()
. This because we need to see it just once.The
printDirectory
function scans through the list of entries and prints on serial every file and directory present. For files the size is printed as well.1/*2
3 Listfiles4
5 This example shows how print out the files in a6
7 directory on a SD card.Pin numbers reflect the default8
9 SPI pins for Uno and Nano models10
11 The circuit:12
13 SD card attached to SPI bus as follows:14
15 ** SDO - pin 1116
17 ** SDI - pin 1218
19 ** CLK - pin 1320
21 ** CS - depends on your SD card shield or module.22
23 Pin 10 used here for consistency with other Arduino examples24
25 (for MKRZero SD: SDCARD_SS_PIN)26
27 created Nov 201028
29 by David A. Mellis30
31 modified 9 Apr 201232
33 by Tom Igoe34
35 modified 2 Feb 201436
37 by Scott Fitzgerald38
39 modified 24 July 202040
41 by Tom Igoe42
43
44
45 This example code is in the public domain.46
47*/48#include <SD.h>49
50const int chipSelect = 10;51
52File root;53
54void setup() {55
56 // Open serial communications and wait for port to open:57
58 Serial.begin(9600);59
60 // wait for Serial Monitor to connect. Needed for native USB port boards only:61
62 while (!Serial);63
64 Serial.print("Initializing SD card...");65
66 if (!SD.begin(chipSelect)) {67
68 Serial.println("initialization failed. Things to check:");69
70 Serial.println("1. is a card inserted?");71
72 Serial.println("2. is your wiring correct?");73
74 Serial.println("3. did you change the chipSelect pin to match your shield or module?");75
76 Serial.println("Note: press reset or reopen this serial monitor after fixing your issue!");77
78 while (true);79
80 }81
82 Serial.println("initialization done.");83
84 root = SD.open("/");85
86 printDirectory(root, 0);87
88 Serial.println("done!");89}90
91void loop() {92
93 // nothing happens after setup finishes.94}95
96void printDirectory(File dir, int numTabs) {97
98 while (true) {99
100 File entry = dir.openNextFile();101
102 if (! entry) {103
104 // no more files105
106 break;107
108 }109
110 for (uint8_t i = 0; i < numTabs; i++) {111
112 Serial.print('\t');113
114 }115
116 Serial.print(entry.name());117
118 if (entry.isDirectory()) {119
120 Serial.println("/");121
122 printDirectory(entry, numTabs + 1);123
124 } else {125
126 // files have sizes, directories do not127
128 Serial.print("\t\t");129
130 Serial.println(entry.size(), DEC);131
132 }133
134 entry.close();135
136 }137}
Suggest changes
The content on docs.arduino.cc is facilitated through a public GitHub repository. If you see anything wrong, you can edit this page here.
License
The Arduino documentation is licensed under the Creative Commons Attribution-Share Alike 4.0 license.