Using Gadgeteer MF4.3 for SD Card throws exceptions

I tried to create a new Gadgeteer project for MF4.3 and Raptor board with an SD Card module. An exception is thrown on this statement in the Designer generated code, program_generated.cs:


 private void InitializeModules() {
            this.sdCard = new GTM.GHIElectronics.SDCard(9);
        }

In my Program.cs, an exception is thrown when I call sdCard.Mount(). A FAT32 formatted card is already inserted. This same card worked using MF4.2 on Raptor. It has files on it that are readable on a PC SD card reader.


using System;
using System.Collections;
using System.Threading;
using Microsoft.SPOT;
using Microsoft.SPOT.Presentation;
using Microsoft.SPOT.Presentation.Controls;
using Microsoft.SPOT.Presentation.Media;
using Microsoft.SPOT.Presentation.Shapes;
using Microsoft.SPOT.Touch;

using Gadgeteer.Networking;
using GT = Gadgeteer;
using GTM = Gadgeteer.Modules;
using Gadgeteer.Modules.GHIElectronics;

namespace SDCardTest
{
    public partial class Program
    {
        // This method is run when the mainboard is powered up or reset.   
        void ProgramStarted()
        {
            /*******************************************************************************************
            Modules added in the Program.gadgeteer designer view are used by typing 
            their name followed by a period, e.g.  button.  or  camera.
            
            Many modules generate useful events. Type +=<tab><tab> to add a handler to an event, e.g.:
                button.ButtonPressed +=<tab><tab>
            
            If you want to do something periodically, use a GT.Timer and handle its Tick event, e.g.:
                GT.Timer timer = new GT.Timer(1000); // every second (1000ms)
                timer.Tick +=<tab><tab>
                timer.Start();
            *******************************************************************************************/


            // Use Debug.Print to show messages in Visual Studio's "Output" window during debugging.

            sdCard.Mounted += sdCard_Mounted;
            sdCard.Unmounted += sdCard_Unmounted;

            Debug.Print("SD Card is inserted = " + sdCard.IsCardInserted.ToString());
            Debug.Print("SD Card is mounted = " + sdCard.IsCardMounted.ToString());

            if (!sdCard.IsCardMounted)
                new Thread(MySDCardMounter).Start();

            Debug.Print("Program Started");
        }

        void MySDCardMounter()
        {
            sdCard.Mount();
        }

        void sdCard_Unmounted(SDCard sender, EventArgs e)
        {
            Debug.Print("SD Card was un-mounted");
        }

        void sdCard_Mounted(SDCard sender, GT.StorageDevice device)
        {
            Debug.Print("SD Card was mounted");
        }
    }
}


These are the exceptions:

Using mainboard GHI Electronics FEZ Raptor version 1.0

Exception System.Exception - 0xffffffff (1)

Message:

GHI.IO.Storage.SDCard::NativeConstructor [IP: 0000]

GHI.IO.Storage.SDCard::.ctor [IP: 0017]

GHIElectronics.Gadgeteer.FEZRaptor::MountStorageDevice [IP: 0019]

Gadgeteer.Modules.GHIElectronics.SDCard::Mount [IP: 0016]

SDCardTest.Program::InitializeModules [IP: 0007]

A first chance exception of type ‘System.Exception’ occurred in GHI.Hardware.dll
SD Card is inserted = True
SD Card is mounted = False

Exception System.Exception - 0xffffffff (4)

Message:

GHI.IO.Storage.SDCard::NativeConstructor [IP: 0000]

GHI.IO.Storage.SDCard::.ctor [IP: 0017]

GHIElectronics.Gadgeteer.FEZRaptor::MountStorageDevice [IP: 0019]

Gadgeteer.Modules.GHIElectronics.SDCard::Mount [IP: 0016]

A first chance exception of type ‘System.Exception’ occurred in GHI.Hardware.dll
The thread ‘’ (0x4) has exited with code 0 (0x0).
Program Started
The thread ‘’ (0x3) has exited with code 0 (0x0).

Ok, I won’t call the mount() function.
But what about, as I said, this Designer-generated code throws an exception:

        this.sdCard = new GTM.GHIElectronics.SDCard(9);

What do I do about that?

“CodeGreen” told me to try this:

https://www.ghielectronics.com/community/forum/topic?id=16569&page=2

mySd = new GHI.IO.Storage.SDCard();

I will try…

I can’t get the SDCard object started.

I call the constructor,


mySd = new GHI.IO.Storage.SDCard();

I get an exception in the SDCard constructor

Using mainboard GHI Electronics FEZ Raptor version 1.0
#### Exception System.Exception - 0xffffffff (1) ####
#### Message:
#### GHI.IO.Storage.SDCard::NativeConstructor [IP: 0000] ####
#### GHI.IO.Storage.SDCard::.ctor [IP: 0017] ####
#### SDCardTest.Program::InitializeModules [IP: 0005] ####
A first chance exception of type ‘System.Exception’ occurred in GHI.Hardware.dll
An unhandled exception of type ‘System.Exception’ occurred in GHI.Hardware.dll

I got it to work by creating sdCard() in a thread


   public partial class Program
    {
        // This method is run when the mainboard is powered up or reset.   
        void ProgramStarted()
        {
            /*******************************************************************************************
            Modules added in the Program.gadgeteer designer view are used by typing 
            their name followed by a period, e.g.  button.  or  camera.
            
            Many modules generate useful events. Type +=<tab><tab> to add a handler to an event, e.g.:
                button.ButtonPressed +=<tab><tab>
            
            If you want to do something periodically, use a GT.Timer and handle its Tick event, e.g.:
                GT.Timer timer = new GT.Timer(1000); // every second (1000ms)
                timer.Tick +=<tab><tab>
                timer.Start();
            *******************************************************************************************/

            new Thread(sdCardTest).Start();

            // Use Debug.Print to show messages in Visual Studio's "Output" window during debugging.
            Debug.Print("Program Started");
        }


        void sdCardTest()
        {

         // if necessary, check that SD is present here...

         SDCard sd_card = new SDCard();
 
         sd_card.Mount();
         bool fs_ready = false;
         RemovableMedia.Insert += (a, b) =>
         {
             fs_ready = true;
         };
         while (! fs_ready ) {
             System.Threading.Thread.Sleep(1);
         }

         // Assume only one storage device is available
          // and that the media is formatted
         string rootDirectory = VolumeInfo.GetVolumes()[0].RootDirectory;
         FileStream FileHandle = new FileStream(rootDirectory +
                                       @ "\hello.txt", FileMode.Create);
         byte[] data =
            Encoding.UTF8.GetBytes("This string will go in the file!");
         FileHandle.Write(data, 0, data.Length);
         FileHandle.Close();

         sd_card.Unmount();
        }
    }

1 Like

How do I create a directory on the SD card? I get this exception. See code below.

2007/01/01 04:24:35.997 Creating directory \SD\testdir
#### Exception System.IO.IOException - CLR_E_INVALID_DRIVER (6) ####
#### Message:
#### Microsoft.SPOT.IO.NativeIO::CreateDirectory [IP: 0000] ####
#### System.IO.Directory::CreateDirectory [IP: 000a] ####
#### SDCardReaders.SDCardReader::SDCardTest [IP: 0036] ####
#### SDCardReaders.SDCardReader::.ctor [IP: 006e] ####
#### SmartTruckRaptor.PrototypeDevice::.ctor [IP: 0072] ####
#### SmartTruckRaptor.Program::ProcessCommandsLoop [IP: 003b] ####
A first chance exception of type ‘System.IO.IOException’ occurred in Microsoft.SPOT.IO.dll


           // example of openread/openwrite usage 
            VolumeInfo vi;
            string dirName;
            string SD_DirName;
            string testfile;
            FileStream FileHandle;
            string[] dirList;
            byte[] data;

            dirName = "testdir";
            testfile = "testdir\\testfile.txt";
            vi = VolumeInfo.GetVolumes()[0];
            SD_DirName = vi.RootDirectory + "\\" + dirName;

            try
            {
                if (!Directory.Exists(SD_DirName))
                {
                    Debug.Print("Creating directory " + SD_DirName);
                    Directory.CreateDirectory(dirName);
                }
            }
            catch (Exception ex3)
            {
                Debug.Print("error creating directory " + dirName + " exception: " + ex3.ToString());
                return;
            }


I think it’s telling you what your problem is (like all exceptions tend to :slight_smile: )

Invalid Driver.

IMHO that means you’re doing it all wrong and the driver you’re invoking is not the one that is meant to leverage the SD card. I suspect that this is an artefact of the way you’ve done things earlier to work around whatever other issue you were having. You probably need the SD Card object to be created outside the thread so it doesn’t get GC’ed

I found the answer - I need to use the full file name path in MF 4.3

SD_DirName = vi.RootDirectory + “\” + dirName;

In 4.2 I was supposed to use only “testdir\testfile.txt” as the path to the file.