SD card code hanging up on second run

Using the Hydra and SD card module, I can’t get the code to run again without resetting the Hydra. In the debug terminal I just get something like this when I run it the second time:
‘Microsoft.SPOT.Debugger.CorDebug.dll’ (Managed): Loaded ‘C:\Program Files (x86)\GHI Electronics\GHI .NET Gadgeteer SDK\Modules\UsbClientDP\NETMF 4.2\le\GTM.GHIElectronics.UsbClientDP.dll’, Symbols loaded.
‘Microsoft.SPOT.Debugger.CorDebug.dll’ (Managed): Loaded ‘C:\Program Files (x86)\GHI Electronics\GHI .NET Gadgeteer SDK\Mainboards\FEZHydra\NETMF 4.2\le\GHIElectronics.Gadgeteer.FEZHydra.dll’, Symbols loaded.
‘Microsoft.SPOT.Debugger.CorDebug.dll’ (Managed): Loaded ‘c:\users\takushi\documents\visual studio 2012\Projects\sd_card_muddling\sd_card_muddling\bin\Debug\le\sd_card_muddling.exe’, Symbols loaded.
The thread ‘’ (0x2) has exited with code 0 (0x0).
Using mainboard GHI Electronics FEZHydra version 1.2

Here’s my code:

using System;
using System.Text;
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 sd_card_muddling
{
    public partial class Program
    {
        void ProgramStarted()
        {
            int i = 525600;
            byte[] result = Encoding.UTF8.GetBytes(i.ToString());
            Debug.Print("sd_card_stuff........");
                Thread.Sleep(500);
            sdCard.MountSDCard();
                Thread.Sleep(500);
            GT.StorageDevice storage = sdCard.GetStorageDevice();
                Thread.Sleep(500);
            Debug.Print("it's DEAD!!!!");
                Thread.Sleep(500);
            storage.WriteFile("test.txt", result);
                Thread.Sleep(500);
            Debug.Print("It is written");
                Thread.Sleep(500);
            sdCard.UnmountSDCard();
                Thread.Sleep(500);
            Debug.Print(sdCard.IsCardMounted.ToString());
        }
    }
}

Any thoughts on what I can do to fix this?
Thanks in advance,
Danny

Have you tried the official tutorial, from the link below?

https://www.ghielectronics.com/docs/96/sd-card-module

I don’t think that this is a problem with your code as I have seen it on several occasions and with different projects. I did notice the other day that when I looked at the Project Properties,. NET Micro Framework tab the Device name had defaulted back to FEZ Hydra_Gadgeteer which is not the friendly name I gave it. After the reset my FEZ Hydra_01 returns.

@ Architect
That’s where I started, but I wasn’t able to get it running with the Premium namespaces, which threw off the whole pStore stuff. I looked around some more and tried adapting some code from this example (.NET Gadgeteer Camera,Touch Screen, and Storage | Integral Design). It’s a heavy mod though, so I’ll try to confirm that the original works.

@ Sprigo
That’s not good; I wonder if this is a problem on other (non OSHW) boards…

I only noticed the name change for the first time the other day as I had both my Hydra’s attached. One of them still had the default name where as I had given the target device a new ‘Friendly Name’ but found it downloaded the project to the wrong device.

Normally I would see the iteration count and just hit reset. If you let the iteration count top out and then look at the device name is reverted back to the default (which the reset resolves). I cannot say that I’ve noticed this on any of the other (non-OSHW) boards.

@ okinawanspud -

Try this example. It is for Cerberus, but should work on Hydra as well

https://www.ghielectronics.com/community/codeshare/entry/889

So there’s a few questions.

“Premium” is not relevant on a OSHW board. In 4.2 you simply re-map inclusions and references from Premium to the equivalent OSHW ones. In 4.3 that changes; but that’s still in beta so you shouldn’t be assuming that this works and trying something new - you weren’t using 4.3 beta were you ?

Second, have you validated firmware versions match? Are you using Ethernet firmware, and if so do you have the ENC28 module connected on the correct socket?

Third, from your debug output it’s never getting to the first debug.print() statement, so it’s not directly the SD card routines. Can you create a new project that has a timer that just flashes the debug led and show that works on your device with nothing else connected, and then re-connect the SD card module in hardware (not in Gadgeteer designer yet) and prove that continues to run. Then re-add SD card in designer, with no code change, and prove that works, with no SD card inserted. Then prove it all works again but with SD card inserted. If anything halts the expected behaviour, make sure you note what it was.

Then, there’s a codeshare example that you can introduce.
https://www.ghielectronics.com/community/codeshare/entry/643

On a Cerberus I use the following code pattern in ProgramStarted():

            sdCard.SDCardMounted += sdCard_SDCardMounted;
            sdCard.SDCardUnmounted += sdCard_SDCardUnmounted;
   if (sdCard.IsCardMounted)
            {
                try
                {
                    Thread.Sleep(10);
                    VolumeInfo vi = sdCard.GetStorageDevice().Volume;
                    Debug.Print(vi.Name);
                    Debug.Print(vi.IsFormatted.ToString());
                    Debug.Print(vi.FileSystem);
                    Debug.Print(vi.TotalFreeSpace.ToString());

                    string root = sdCard.GetStorageDevice().RootDirectory;
                    Debug.Print("Root: " + root);
                    Debug.Print("Card mounted ok");
                   SD_ready = true;
                }
                catch
                {
                  sdCard.UnmountSDCard();
                    SD_ready = false;
                }
            }
            else
            {
                Debug.Print("SD Card Failed to mount!");
            }

I also have a button (I actually am using joystick pressed) that toggles mount/unmount and track the SD_ready status across the handlers… there’s obviously some duplication here that I could get rid of I guess:


        void sdCard_SDCardUnmounted(SDCard sender)
        {
            Debug.Print("in Unmounted");
            SD_ready = false;
        }

        void sdCard_SDCardMounted(SDCard sender, GT.StorageDevice SDCard)
        {
            Debug.Print("in Mounted");
            SD_ready = true ;
        }

        void joystick_JoystickPressed(Joystick sender, Joystick.JoystickState state)
        {
            if (SD_ready)
            {
                Debug.Print("in Joystick. Unmounting.");
                sdCard.UnmountSDCard();
                SD_ready = false;

            }
            else
            {
                Debug.Print("in Joystick. Trying to mount.");
                try
                {
                    if (!sdCard.IsCardMounted)
                    {
                        Debug.Print("Not mounted");
                        sdCard.MountSDCard();
                    }
                    SD_ready = true;
                    Debug.Print("Mount worked!");
                    VolumeInfo vi = sdCard.GetStorageDevice().Volume;
                    Debug.Print("GetDev worked!");
                    Debug.Print(vi.Name);
                    Debug.Print(vi.IsFormatted.ToString());
                    Debug.Print(vi.FileSystem);
                    Debug.Print(vi.TotalFreeSpace.ToString());

                    string root = sdCard.GetStorageDevice().RootDirectory;
                    Debug.Print("Root: " + root);

              }
                catch
                {
                    Debug.Print("Mount failed");
                    sdCard.UnmountSDCard();
                    SD_ready = false;
             }
            }

One of the big reliability factors I have seen (and has been talked about here) is the SD card, and whether I have it installed when the program boots. Some cards are very sensitive to power conditions on startup and so are better off being left out of the holder until your app has started, and then insert (which is why I use the toggle button - if my app won’t start because the SD card played up when mounted by default, I take the card out and reset and put the card in and hit the button to mount it).