I would like to write to an Micro SD Card. I'm using the Pins 55, 57, 59, 61,63, 65 on the high density connector J1 (see appendix).
The example code TestSDCARD.ino is working well and I can list some directories on the SD Card.
Now I trying to use the FATFileSystem with fopen, fprintf and fclose, but I can't write to the SD Card. The red LED on the Portenta board starts flashing. The Serial output is:
Test
1
Which concludes that there is a error in line fprintf(fs,"test \r\n");
#include "FATFileSystem.h"
#include "mbed.h"
#include <string>
mbed::FATFileSystem fs("fs");
void setup() {
// put your setup code here, to run once:
delay(2000);
Serial.begin(115200);
Serial.println("Test");
FILE *fp = fopen("/fs/test.txt", "w");
Serial.println("1");
fprintf(fp,"test \r\n");
Serial.println("2");
fclose(fp);
}
void loop() {
// put your main code here, to run repeatedly:
}
What is wrong with this code? Is there some example code to write to a SD Card with the Protenta H7?
The SD Card is formatted to FAT32 (32GB, V30, U3)
Ah, ok, i need to mount the filesystem... This is the solution:
#include "SDMMCBlockDevice.h"
#include "FATFileSystem.h"
SDMMCBlockDevice block_device;
mbed::FATFileSystem fs("fs");
void setup() {
// put your setup code here, to run once:
delay(2000);
Serial.begin(115200);
Serial.println("Test");
int err = fs.mount(&block_device);
if (err) {
// Reformat if we can't mount the filesystem
// this should only happen on the first boot
Serial.println("No filesystem found, formatting... ");
fflush(stdout);
err = fs.reformat(&block_device);
}
FILE *fp = fopen("/fs/test.txt", "a");
Serial.println("1");
fprintf(fp,"test \r\n");
Serial.println("2");
fclose(fp);
}
void loop() {
// put your main code here, to run repeatedly:
}
Thanks for this. I was able to write the constant string values to file with this.
The next step is how to write sensor values to sd card file. The fprintf function requires a 'const char' variable as input. I'm getting errors cannot convert convert Arduino::string to const char*.
This seems like a simple problem but I'm an amateur and I have been googling this for hours. Googling "Portenta write to SD card" yields your post first. To save others time I found a solution to write integer values to file.
I'm using the same code as you but removed your fprintf(fp,"test \r\n");
with this into the loop() code.
const int analogInPin0 = A0; // Pin to read analog values from
int sensorValue0=0; // initialize sensor value
char string0[2]; // Array to store the string
sensorValue0 = analogRead(analogInPin0);
itoa(sensorValue0,string0,10); // converts int to char *
fprintf(fp,string0); // write data to file
fprintf(fp,"/r/n"); //new line
delay(500); // Wait 500ms before next loop
I'm able to print integers to file like this. Now to figure out how to do floats. I'll leave that for another day.
@pert does Arduino have a file print procedure that takes a string? The following works fine, but using char arrays is a huge pain. Any Arduino file print procedures that take strings?
#include "SDMMCBlockDevice.h"
#include "FATFileSystem.h"
char myFileName[] = "fs/00000000.json";
char buffer0[30] = "I can be saved";
myFile = fopen(myFileName, "a");
fprintf(myFile, buffer0);
fclose(myFile);
Any other string options?
.
few days later
I made some .json and .csv sd card examples here for edge impulse uploading, but I also made a simple .txt file example
/*
Portenta - TestSDCARD
The sketch shows how to mount an SDCARD and list its content.
then add a file.
Note: SD Card seems finisky, takes a few times to load the filesystem
The circuit:
- Portenta H7 + Vision Shield
or
- Portenta H7 + Portenta Breakout
This example code is in the public domain.
*/
#include "SDMMCBlockDevice.h"
#include "FATFileSystem.h"
SDMMCBlockDevice block_device;
mbed::FATFileSystem fs("fs");
void setup() {
Serial.begin(115200);
pinMode(LED_BUILTIN, OUTPUT);
delay(5000); // time to connect serial
Serial.println("Connect serial if needed");
delay(5000);
//while (!Serial); // blocking call
Serial.println("Mounting SDCARD...");
int err = fs.mount(&block_device);
if (err) {
Serial.println("No SD Card filesystem found, please check SD Card on computer and manually format if needed.");
// int err = fs.reformat(&block_device); // seriously don't want to format your good data
}
}
void loop() {
digitalWrite(LED_BUILTIN, !digitalRead(LED_BUILTIN)); // flips LED on and off
// Make a folder if needed
mkdir("fs/myFolder2",0777); // 0777 full access permissions linux style
char myFileName[] = "fs/myFolder2/test2.txt"; // "fs/" needs to be there, think fileSystem
FILE *myFile = fopen(myFileName, "w"); // "a" for append (add to file), "w" write, "r" read ??
Serial.println(myFileName);
fprintf(myFile,"Test how cool this is \r\n");
fprintf(myFile,"Also this line \r\n");
fclose(myFile);
Serial.println("------------------------- Done Writing file --------------------------------");
delay(10);
unsigned char c;
FILE *fp = fopen(myFileName, "r"); // "r" read only
while (!feof(fp)){ // while not end of file
c=fgetc(fp); // get a character/byte from the file
//printf("Read from file %02x\n\r",c); // and show it in hex format
Serial.print((char)c); // show it as a text character
}
fclose(fp);
Serial.println("------------------------- Done Showing file --------------------------------");
delay(10000); // wait a bit
}
Just occurred to me, if you have the vision shield on the breakout board you have access to 2 SD cards. How do you identify which one is the correct sd card to access?