Mass Storage - switching back and forth between internal file system and USB MSC with SD Card

I am looking at the example code on section 28.7 (Mass Storage) of the beginning ebook (page 80) in order to find ideas on how to switch between an internal file system and USB MSC with my SDCard.

Up to now , my datalogging application is running on FEZ Cobra and stores .csv files using the internal file system (like in section 23.1 example of the ebook).

I now would like to stop datalogging on the SD Card and tell start the USB MSC process on the same SD Card in order for a connected PC to grab those newly created datalog files.

My question is : what sequences of events needs to happen in order to properly switch back and forth between internal file system and USB MSC when they both access the same SD card. Is there also some specific delays to add in for the SDcard to complete files writes and prevent corruption between mode switching?

Cheers,
Jean-Francois

All you need to do is to unmount the media.

I currently do this with a “PC Connect button” on my device using the code below. I change the value of a global State variable to start the USB Mass Storage mode, then it hangs around waiting for the button to be pressed again to detach.


        public static void AttachAsMassStorage()
        {
            // Check debug interface
            if (Configuration.DebugInterface.GetCurrent() == Configuration.DebugInterface.Port.USB1)
            {
                throw new InvalidOperationException("Current debug interface is USB. It must be changed to something else before proceeding. Refer to your platform user manual to change the debug interface.");
            }

            Debug.Print("Starting USB Mass Storage");

            // Start MS
            if (State.MassStorage == null)
            {
                State.MassStorage = USBClientController.StandardDevices.StartMassStorage();
            }

            // Assume SD card is connected

            // Check if the SD card is attached.
            if (State.SD == null)
            {
                try
                {
                    State.SD = new PersistentStorage("SD");
                }
                catch
                {
                    throw new Exception("SD card not detected");
                }
            }

            State.SD.UnmountFileSystem();

            State.MassStorage.AttachLun(0, State.SD, " ", " ");
            // enable host access
            State.MassStorage.EnableLun(0);

            State.SetState(State.USBCONNECTED);

            State.Lcd.ClearDisplay();
            State.Lcd.WriteAt(4, 1, "USB Connected...");

            // Wait for the next state change and disconnect USB.
            // The state will be REQUESTUSBDISCONNECT.
            while (State.CurrentState == State.USBCONNECTED)
            {
                // TODO: USB Animation
                Thread.Sleep(1000);
            }

            State.MassStorage.DisableLun(0);

            USBClientController.Stop();
            
            State.MassStorage = null;

            State.Lcd.ClearDisplay();
            State.Lcd.WriteAt(4, 1, "USB Disconnected...");

            State.SetState(State.STARTING);
        }

Now I also have a question… Is there a better way?

I’d also like to auto detect when USB is connected and disconnected and get rid of the button. Is that possible?

Hi Gus Support and Realiser,

Thanks for your reply. i am now able to switch back and forth between Internal file system and USB MSC.

Realiser, i used the following to auto detect the USB to PC connection:


if (GHIElectronics.NETMF.USBClient.USBClientController.GetState() == GHIElectronics.NETMF.USBClient.USBClientController.State.Running)
                {
                    _log.Unmount(); // disable internal SD card flash file system
                    Thread.Sleep(500);
                    _log.startUSB(); // enable SD card USB client mode emulation for PC transfer
                    Debug.Print("Starting USB Client mode");
                    Thread.Sleep(2500);
                    // Check if connected to PC
                    while (GHIElectronics.NETMF.USBClient.USBClientController.GetState() != GHIElectronics.NETMF.USBClient.USBClientController.State.Running)
                    {
                        Debug.Print("Waiting to connect to PC...");
                    }
                    Debug.Print("Connected to PC...");
                    while (GHIElectronics.NETMF.USBClient.USBClientController.GetState() == GHIElectronics.NETMF.USBClient.USBClientController.State.Running) ;
                    
                    _log.mount(); // enable internal SD card flash file system
                }