jump to navigation

EMX – SD card reader June 2, 2010

Posted by wesaday in Programming.
Tags: ,
trackback

This is the first real use that I came up with for the EMX board and it would appear that many people have questions regarding the SD card reader capability of the EMX. An SD card would be a quick and easy way to increase the available memory for this primarily embedded system. You might need to save or read text files or log your application to help debug it, updating your application in the field, or other uses.

Create a new project in Visual Studio 2008. Use the Visual C#->Micro Framework->Window Application project template, give the project a meaningful name and click OK.  One thing that I do not like about the template is that the Program.cs file contains the Main method and the window definition. I prefer to separate the functionality but if you want to leave it alone feel free. The only thing that you really need in your Main method is:

Program myApplication = new Program();// Start the application
myApplication.Run(new MainWindow());

I delete the rest of the stuff. Now to the MainWindow. I add a new class called MainWindow to the project. The MainWindow must inherit from Window. Add these using statements:

using System;
using GHIElectronics.NETMF.IO;
using Microsoft.SPOT.Hardware;
using Microsoft.SPOT.Presentation;
using Microsoft.SPOT.Presentation.Media;
using System.IO;
using Microsoft.SPOT;
using Microsoft.SPOT.IO;
We need two private fields; one for the sd card object and one for the SD card insert and removal notification:
private PersistentStorage _sdcard;
private InterruptPort _sdDetect = new InterruptPort(GHIElectronics.NETMF.Hardware.EMX.Pin.IO36, true, Port.ResistorMode.PullDown, Port.InterruptMode.InterruptEdgeBoth);
The first field sets up a PersistentStorage object for out SD card. The second line sets up a port to provide us an interrupt when the SD card is insert and removed. In this case we are going to use IO36, with a glitch filter, using a pull up resistor on the input and finally we want a notification for high and low transitions. If you look closely at the development board, there is a double row of headers down near the lower left side of the board with one side labeled JP1. The sixth pin down from the top is labeled SD Detect and that line is tied to the switch in the SD card connector. By itself it doesn’t do anything, you have to tie that line to an input for the processor. I chose IO36 which is conveniently located right next door to the SD Detect line.  You will need to run a jumper wire from SD Detect to whatever IO line you want to use.  Be very careful!
In the MainWindow constructor we will setup the window Height, Width, Background color and the event handler for the interrupt:

Width = SystemMetrics.ScreenWidth;
Height = SystemMetrics.ScreenHeight;
Background = new SolidColorBrush(0x000000);

_sdDetect.OnInterrupt += OnSdInterrupt;

The interrupt handler is very simple. However it is somewhat counter-intuitive. Because we are using a pull up resistor on the input, the transition values are backwards from what I would think. 0 means that the card was inserted and 1 means that the card was removed. I did try to use a pull down resistor but that wouldn’t work. It works so I didn’t screw with it too much. The handler looks like this:

private void OnSdInterrupt(uint data1, uint data2, DateTime time)
{
     if (data2 == 0)
     {
          _sdcard = new PersistentStorage("SD");
          _sdcard.MountFileSystem();
     }
     else
     {
          if (_sdcard != null)
          {
              _sdcard.UnmountFileSystem();
          }
     }
}

The data2 parameter is the state that the input is transitioning to. When the signal goes low then we know that the SD card has been inserted, we instantiate the PersistentStorage object and then mount the file system. The file system is not mounted by default. When the signal goes back high, we know that the SD card has been removed and we unmount the file system. You can compile and run the program now. You won’t see much of anything though. You can set a break point inside the interrupt handler and see that the input toggles high to low and back to high when you insert and remove an SD card.
The last thing to show is actually using the file system for something. Add the following method to the class:

private void GetFiles()
{
     if (!VolumeInfo.GetVolumes()[0].IsFormatted)
     {
           return;
     }

     string[] files = Directory.GetFiles(VolumeInfo.GetVolumes()[0].RootDirectory);
     foreach (string s in files)
     {
            Debug.Print(s);
     }
}

After the call to MountFileSystem add a call to GetFiles(). All we are doing is simply getting a list of files in the root of the SD card and then printing the file names to the output window. Now you can run the program on your development board and see the SD card doing something when you insert it. That is all there is to it.
Advertisements
%d bloggers like this: