A first chance exception of type 'System.InvalidOperationException'

Hi Gents,

I am using Cerbuino Bee, and VS2010 and 4.2 QFE2 Firmware…

My code basically is trying to read from 3 inputs: SPI, UART and Analog, and then it writes the data in SD card…

but sometimes I have this exception:
A first chance exception of type ‘System.InvalidOperationException’ occurred in Microsoft.SPOT.Hardware.dll

Sometimes the program is terminated, and sometimes it proceeds

Do you have any idea why I have this?

Regards :slight_smile:

May be a sample code to reproduce your experiment will be a good starting point.

Thanks guys, and here is my code:

BTW: the full exception was:
[em]A first chance exception of type ‘System.InvalidOperationException’ occurred in Microsoft.SPOT.Hardware.dll
Exception performing Timer operation[/em]


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.Touch;

using Gadgeteer.Networking;
using GT = Gadgeteer;
using GTM = Gadgeteer.Modules;
using GTI = Gadgeteer.Interfaces;
using Gadgeteer.Modules.GHIElectronics;
using System.IO;
using Microsoft.SPOT.IO;

namespace Final
{

    public partial class Program
    {

        //GPS
        private GT.Timer _timer;
        private string _root;
        
        //SPI
        static GT.Socket _socket;
        static GTI.SPI.Configuration _config;
        static GTI.SPI _spi;

        // This method is run when the mainboard is powered up or reset.   
        public void ProgramStarted()
        {

            // Serial Config.
            usbSerial.Configure(9600,
                    GT.Interfaces.Serial.SerialParity.None,
                    GT.Interfaces.Serial.SerialStopBits.One, 8);

            usbSerial.SerialLine.Open();

            usbSerial.SerialLine.DataReceived += new
            GT.Interfaces.Serial.DataReceivedEventHandler(SerialLine_DataReceived);

            // SPI Config
            _socket = GT.Socket.GetSocket(1, true, null, null);
            _config = new GTI.SPI.Configuration(false, 0, 0, false, true, 2000);
            _spi = new GTI.SPI(_socket, _config, GTI.SPI.Sharing.Exclusive, _socket, GT.Socket.Pin.Five, null);

            // SD Card Config.
            GHI.OSHW.Hardware.StorageDev.MountSD();
            if (VolumeInfo.GetVolumes()[0].IsFormatted)
            {
                _root = VolumeInfo.GetVolumes()[0].RootDirectory;
                _timer = new GT.Timer(1000);
                _timer.Tick += new GT.Timer.TickEventHandler(TimerTick);
                _timer.Start();
            }
        }

        void TimerTick(GT.Timer timer)
        {
            //  *******************************
            string fileName = Path.Combine(_root, "FinalDONE.txt");
            Stream stream;

            // GPS Reading
            int NumberOfBytesToRead = usbSerial.SerialLine.BytesToRead;
            byte[] SerialBuffer = new byte[NumberOfBytesToRead];
            usbSerial.SerialLine.Read(SerialBuffer, 0, NumberOfBytesToRead);

            // SPI Reading
            byte[] BytesWrite = new byte[] { 0, 1, 2, 3, 4 };
            byte[] SPIBuffer = new byte[5];
            _spi.WriteRead(BytesWrite, SPIBuffer);

            // Pressure Config. & Reading
            var analogInput = new Microsoft.SPOT.Hardware.AnalogInput(GHI.OSHW.Hardware.FEZCerbuino.Pin.AnalogIn.A1);
            var analogValue = analogInput.Read();

            // SD Logging
            if (File.Exists(fileName))
            {
                stream = File.OpenWrite(fileName);
                stream.Position = stream.Length; //FM Not To Overwrite
            }
            else
            {
                stream = File.Create(fileName);
            }
            using (var writer = new StreamWriter(stream))
            {
                // GPS writing to SD
                writer.Write("GPS Message: ");
                for (int g = 0; g < NumberOfBytesToRead; g++)
                {
                    char GPSchar = (char)SerialBuffer[g];
                    Debug.Print(GPSchar.ToString());
                    Debug.Print("#");
                    writer.Write(GPSchar.ToString());
                }
                
                writer.WriteLine("");
                writer.WriteLine("");

                // SPI writing to SD
                writer.Write("IMU Message: ");
                for (int s = 0; s < 5; s++)
                {
                    char SPIchar = (char)SPIBuffer[s];
                    Debug.Print(SPIchar.ToString());
                    Debug.Print("#");
                    writer.Write(SPIchar.ToString());
                }

                writer.WriteLine("");
                writer.WriteLine("");

                // Pressure writing to SD
                writer.WriteLine("Analog Value: " + analogValue);

                writer.WriteLine("");
                writer.WriteLine("");

                Debug.Print(analogValue.ToString());
            }
            stream.Dispose();
        }

        void SerialLine_DataReceived(GT.Interfaces.Serial sender, System.IO.Ports.SerialData data)
        {

        }
    }
}

It seems the Exception was when it reach this for the second time:


var analogInput = new Microsoft.SPOT.Hardware.AnalogInput(GHI.OSHW.Hardware.FEZCerbuino.Pin.AnalogIn.A0);

Dear PetaByte,

Could this be occuring as the timer is trying to repeatedly re-declare the Cerbuino Analogue Pin? Perhaps finding a way to take this part of the code outside of the timer (Event Handler?) may avoid the Exception.

@ IanW - Good catch!

I would move allocation of the fixed size buffers outside of the tick handler as well.

Thnx Gents,

That what I thought and what I tried actually, but it seems that (analogInput ) has to be defined “inside” the timer, otherwise there will be an error and it will be as if it is not declared!!

However, I’ll keep trying …

Regards…

What kind of error?

I would try with

analogInput.Dispose()

after analog reading is done. It I also think it is much better to define analogInput as global variable.

Hello Guys :slight_smile:

@ Architect:
When I defined:

var analogInput = new Microsoft.SPOT.Hardware.AnalogInput(GHI.OSHW.Hardware.FEZCerbuino.Pin.AnalogIn.A0);

as a global variable I got this error:
[em]Error 1 The type or namespace name ‘var’ could not be found (are you missing a using directive or an assembly reference?)[/em]

@ jernejk:
Thaaaaaanx dude :slight_smile: :slight_smile: :slight_smile:
You were alright, “analogInput.Dispose()” killed the exception :slight_smile:

Thanx for all of you gents…

But I still recommend you to define global variable, but you can’t use var. Just change var with the correct type like this:

Microsoft.SPOT.Hardware.AnalogInput analogInput = new Microsoft.SPOT.Hardware.AnalogInput(GHI.OSHW.Hardware.FEZCerbuino.Pin.AnalogIn.A0);