Пример #1
0
        ///  <summary>
        ///  ///  Constructor. Sets the class GUID, product & vendor id.
        ///  Predefined values are in DeviceManagerProp.cs.
        ///  </summary>
        public EPdeviceManager(UInt16 vendor_id, UInt16 product_id)
        {
            UsbNotifications = new UsbDevice();
            WinUsbNotifications = new WinUsbDevice();
            EPdevicesVM = new ObservableCollection<GENdeviceVM>();
            _EPdevices = new Collection<GENdevice>();

            if (vendor_id != 0)
                VENDOR_ID = vendor_id;

            if (product_id != 0)
                PRODUCT_ID = product_id;
        }
Пример #2
0
        ///  <summary>
        ///  Reads data from the ADS1298 device and produces data frames to be sent live to clients.
        ///  </summary>
        internal void ReadDataLive()
        {
            const UInt32 maxBufferSize = 62208;				// Optimal buffer value
            const UInt32 maxBufferDelay = 15;               // Maximum buffer delay in milliseconds

            UInt32 bufferSize;
            UInt32 bytesRead = 0;
            UInt32 sampleFreq;

            UInt32 frameCounter = 0;                      // frame sequence number relative to the beginning of the data acquisition
            UInt32 frameDiff;                             // Difference to calculate the frames in the current package
            UInt32 nPackets = 0;                          //Debug variable to show the numbers of frames generated

            Byte[] readBuffer;
            Byte[] writeBuffer = new Byte[USB_PACKET_SIZE];
            Boolean success = false, sendSuccess = true;

            // Select a optimal buffer size (not extending the consts above)
            WinUsbDevice myWinUsb = new WinUsbDevice();
            Stopwatch myStopwatch = new Stopwatch();
            long ticksBegin, ticksEnd;
            double timeStamp, timeDelta;

            sampleFreq = (UInt32)(HR ? DR_VALUE_HR : DR_VALUE_LP);

            //bufferSize = (UInt32)((sampleFreq * DATALENGTH * (UInt32)((myWinUsb.pipeTimeout<maxBufferDelay) ? myWinUsb.pipeTimeout : maxBufferDelay )* 0.75) / 1000);

            //The buffer size is solely determined by the maximum buffer delay that we choose to allow.
            bufferSize = (UInt32) (DATALENGTH * sampleFreq * maxBufferDelay / 1000);
            bufferSize = bufferSize > maxBufferSize ? maxBufferSize : bufferSize;

            readBuffer = new Byte[bufferSize];
            _packetQueue = new System.Collections.Concurrent.ConcurrentQueue<RawDataPacket>();
            RawDataPacket finalPacket;

            try
            {
                winUsbDev.FlushPipe(PIPE_DATA_IN);

                // Send start-command to ADS device.
                writeBuffer[0] = CMD_START;
                success = winUsbDev.SendBulkData(PIPE_COMMAND_OUT, ref writeBuffer, (UInt32)writeBuffer.Length);       // Send start-command to ADS device.

                if (success)
                {
                    myStopwatch.Reset();
                    myStopwatch.Start();
                    do
                    {
                        // Read some data.
                        ticksBegin = myStopwatch.ElapsedTicks;
                        winUsbDev.ReadBulkData(PIPE_DATA_IN, bufferSize, ref readBuffer, ref bytesRead, ref success);
                        ticksEnd = myStopwatch.ElapsedTicks;

                        timeStamp = (double)ticksBegin / (double)Stopwatch.Frequency;
                        timeDelta = (double)(ticksEnd - ticksBegin) / (double)Stopwatch.Frequency;

                        // Get a proper frame index for our newly read frames
                        // This frame index is 24-bit wide, so at 2000 samples/sec it will
                        // overflow and get back to 0 every 8388 seconds

                        frameDiff=0;

                        for (UInt32 i = 0; i < bytesRead; i += DATALENGTH)
                        {
                            frameCounter = frameCounter & 0x00ffffff;
                            readBuffer[i] = (Byte) ((frameCounter & 0x00ff0000) >> 16);
                            readBuffer[i+1] = (Byte) ((frameCounter & 0x0000ff00) >> 8);
                            readBuffer[i+2] = (Byte) (frameCounter & 0x000000ff);
                            frameCounter++;
                            frameDiff++;
                        }

                            //Here we can create a packet and add it to the frame collection
                            _packetQueue.Enqueue(new RawDataPacket(readBuffer, (Int32)bytesRead, sampleFreq, NumberOfChannels, DATALENGTH, frameDiff, timeStamp, timeDelta));

                        nPackets++;

                        //We have read a new packet, so we make our listeners aware of it
                        OnNewPacket(EventArgs.Empty);

                        sendSuccess &= success;
                    }
                    while (processingData && bytesRead != 0);

                    //Now we send a special duplicate packet indicating there will be no more packets coming
                    finalPacket=new RawDataPacket(readBuffer, (Int32)bytesRead, sampleFreq, NumberOfChannels, DATALENGTH, frameDiff,timeStamp,timeDelta);
                    finalPacket.lastPacket = true;
                    _packetQueue.Enqueue(finalPacket);

                    OnNewPacket(EventArgs.Empty);

                    //DEBUG
                    Console.Out.WriteLine("{0} packets processed.", nPackets);
                    //DEBUG/
                }
                if (sendSuccess)
                {
                    writeBuffer[0] = CMD_STOP;
                    success = winUsbDev.SendBulkData(PIPE_COMMAND_OUT, ref writeBuffer, (UInt32)writeBuffer.Length);   // Send stop-command to ADS device.
                }
            }
            catch (ThreadAbortException)
            {
                throw;
            }

            finally
            {
                writeBuffer[0] = CMD_STOP;
                winUsbDev.SendBulkData(PIPE_COMMAND_OUT, ref writeBuffer, (UInt32)writeBuffer.Length);					// Send stop-command to ADS device.
                winUsbDev.ReadBulkData(PIPE_DATA_IN, bufferSize, ref readBuffer, ref bytesRead, ref success);		// Read the samples after we stopped the reading process.
            }
        }
Пример #3
0
        /*
        ///  <summary>
        ///  Save data from EP device.
        ///  </summary>
        internal override void SaveData(HDF5group hdf5device)
        {
            Int32 rec, data;
            float[] fWriteBuffer;
            byte[] readBuffer = new byte[DATALENGTH];

            Int32[] iWriteBuffer;

            UInt64 counter = 0;
            UInt64[] counterBuffer = new UInt64[1];

            // Write raw data to file.
            if (hdf5device != null) rec = hdf5device.addRecord("EMG RAW", NumberOfChannels, SamplesPerSecond, HDF5group.DataType.INT32, HDF5group.CompressionType.GZIP, 9);
            else rec = 0;

            if (memStream != null)
            {
                memStream.Position = 0;
                while (memStream.Read(readBuffer, 0, DATALENGTH) == DATALENGTH)
                {
                    iWriteBuffer = new Int32[8];
                    for (UInt32 i = SampleLength, j = 0; i < DATALENGTH; i += SampleLength, j++)
                    {
                        iWriteBuffer[j] = readBuffer[i] << 24 | readBuffer[i + 1] << 16 | readBuffer[i + 2] << 8;
                        iWriteBuffer[j] /= 256;
                    }
                    if (hdf5device != null) hdf5device.getRecord(rec).writeData<Int32>(iWriteBuffer);
                }
            }

            // Write attributes
            if (hdf5device != null)
            {
                hdf5device.getRecord(rec).writeAttribute("Manufacturer", winUsbDev.GetUsbStringDescriptor(winUsbDev.usbDevDescriptor.iManufacturer));
                hdf5device.getRecord(rec).writeAttribute("Device name", winUsbDev.GetUsbStringDescriptor(winUsbDev.usbDevDescriptor.iProduct));
                hdf5device.getRecord(rec).writeAttribute("Serial number", winUsbDev.GetUsbStringDescriptor(winUsbDev.usbDevDescriptor.iSerialNumber));
                hdf5device.getRecord(rec).writeAttribute("Number of channels", NumberOfChannels);
                hdf5device.getRecord(rec).writeAttribute("Samples / second", SamplesPerSecond);
                hdf5device.getRecord(rec).writeAttribute("Resolution [Bit]", ResolutionBits);
                hdf5device.getRecord(rec).writeAttribute("+Vref [mV]", (InputDifferantialVoltagePositive).ToString("R"));
                hdf5device.getRecord(rec).writeAttribute("-Vref [mV]", (InputDifferantialVoltageNegative).ToString("R"));
            }
            // Write data + time to file
            counter = 0;
            if (hdf5device != null)  rec = hdf5device.addRecord("EMG + timing", NumberOfChannels + 1, SamplesPerSecond, HDF5group.DataType.FLOAT, HDF5group.CompressionType.GZIP, 9);

            if (memStream != null)
            {
                memStream.Position = 0;
                while (memStream.Read(readBuffer, 0, DATALENGTH) == DATALENGTH)
                {
                    fWriteBuffer = new float[9];
                    fWriteBuffer[0] = counter / (float)SamplesPerSecond;
                    for (UInt32 i = SampleLength, j = 1; i < DATALENGTH; i += SampleLength, j++)
                    {
                        data = readBuffer[i] << 24 | readBuffer[i + 1] << 16 | readBuffer[i + 2] << 8;
                        data /= 256;
                        // Analog inputs are full differential
                        if (data > 0)
                            fWriteBuffer[j] = (data * (InputDifferantialVoltagePositive - InputDifferantialVoltageNegative))
                                                    / (float)Math.Pow(2, ResolutionBits-1);
                        else if (data < 0)
                            fWriteBuffer[j] = (data * (InputDifferantialVoltagePositive - InputDifferantialVoltageNegative))
                                                    / (float)Math.Pow(2, ResolutionBits-1);
                        else
                            fWriteBuffer[j] = 0;
                        switch (j)
                        {
                            case 0: fWriteBuffer[j] /= CH1_GAIN_VALUE; break;
                            case 1: fWriteBuffer[j] /= CH2_GAIN_VALUE; break;
                            case 2: fWriteBuffer[j] /= CH3_GAIN_VALUE; break;
                            case 3: fWriteBuffer[j] /= CH4_GAIN_VALUE; break;
                            case 4: fWriteBuffer[j] /= CH5_GAIN_VALUE; break;
                            case 5: fWriteBuffer[j] /= CH6_GAIN_VALUE; break;
                            case 6: fWriteBuffer[j] /= CH7_GAIN_VALUE; break;
                            case 7: fWriteBuffer[j] /= CH8_GAIN_VALUE; break;
                            default: break;
                        }
                    }
                    if (hdf5device != null) hdf5device.getRecord(rec).writeData<float>(fWriteBuffer);
                    counter++;
                }
            }

            // Write attributes
            if (hdf5device != null)
            {
                hdf5device.getRecord(rec).writeAttribute("Manufacturer", winUsbDev.GetUsbStringDescriptor(winUsbDev.usbDevDescriptor.iManufacturer));
                hdf5device.getRecord(rec).writeAttribute("Device name", winUsbDev.GetUsbStringDescriptor(winUsbDev.usbDevDescriptor.iProduct));
                hdf5device.getRecord(rec).writeAttribute("Serial number", winUsbDev.GetUsbStringDescriptor(winUsbDev.usbDevDescriptor.iSerialNumber));
                hdf5device.getRecord(rec).writeAttribute("Number of channels", NumberOfChannels);
                hdf5device.getRecord(rec).writeAttribute("Samples / second", SamplesPerSecond);
                hdf5device.getRecord(rec).writeAttribute("Resolution [Bit]", ResolutionBits);
                hdf5device.getRecord(rec).writeAttribute("+Vref [mV]", (InputDifferantialVoltagePositive).ToString("R"));
                hdf5device.getRecord(rec).writeAttribute("-Vref [mV]", (InputDifferantialVoltageNegative).ToString("R"));
            }

            // Write sample counter to extra hdf5 record
            counter = 0;
            if (hdf5device != null) rec = hdf5device.addRecord("Sample counter", 1, SamplesPerSecond, HDF5group.DataType.UINT64, HDF5group.CompressionType.GZIP, 9);

            if (memStream != null)
            {
                memStream.Position = 0;
                while (memStream.Read(readBuffer, 0, DATALENGTH) == DATALENGTH)
                {
                    counterBuffer[0] = (UInt64)(readBuffer[1] << 8 | readBuffer[2]);

                    for (UInt32 i=0; i<(UInt32)(counter/(256*256)); i++)	// overflows
                        counterBuffer[0] += (256*256);

                    if (hdf5device != null) hdf5device.getRecord(rec).writeData<UInt64>(counterBuffer);

                    counter++;
                }
            }
        }
        */
        ///  <summary>
        ///  Reads data from the ADS1298 device.
        ///  </summary>
        internal void ReadData()
        {
            const UInt32 maxBufferSize = 62208;				// Optimal buffer value

            UInt32 bufferSize;
            UInt32 bytesRead = 0;

            Byte[] readBuffer;
            Byte[] writeBuffer = new Byte[USB_PACKET_SIZE];
            Boolean success = false, sendSuccess = true;

            // Select a optimal buffer size (not extending the consts above)
            WinUsbDevice myWinUsb = new WinUsbDevice();

            bufferSize = (UInt32)((HR ? DR_VALUE_HR : DR_VALUE_LP) * DATALENGTH * (UInt32)(myWinUsb.pipeTimeout * 0.75) / 1000);
            bufferSize = bufferSize > maxBufferSize ? maxBufferSize : bufferSize;

            readBuffer = new Byte[bufferSize];
            memStream = new MemoryStream();

            try
            {
                winUsbDev.FlushPipe(PIPE_DATA_IN);

                // Send start-command to ADS device.
                writeBuffer[0] = CMD_START;
                success = winUsbDev.SendBulkData(PIPE_COMMAND_OUT, ref writeBuffer, (UInt32)writeBuffer.Length);       // Send start-command to ADS device.

                if (success)
                {
                    do
                    {
                        // Read some data.
                        winUsbDev.ReadBulkData(PIPE_DATA_IN, bufferSize, ref readBuffer, ref bytesRead, ref success);
                        memStream.Write(readBuffer, 0, (Int32)bytesRead);
                        sendSuccess &= success;
                    }
                    while (processingData && bytesRead != 0);
                }
                if (sendSuccess)
                {
                    writeBuffer[0] = CMD_STOP;
                    success = winUsbDev.SendBulkData(PIPE_COMMAND_OUT, ref writeBuffer, (UInt32)writeBuffer.Length);   // Send stop-command to ADS device.
                }
            }
            catch (ThreadAbortException)
            {
                throw;
            }

            finally
            {
                writeBuffer[0] = CMD_STOP;
                winUsbDev.SendBulkData(PIPE_COMMAND_OUT, ref writeBuffer, (UInt32)writeBuffer.Length);					// Send stop-command to ADS device.
                winUsbDev.ReadBulkData(PIPE_DATA_IN, bufferSize, ref readBuffer, ref bytesRead, ref success);		// Read the samples after we stopped the reading process.
            }
        }