public IInputData ReadStreamAsyncIO(HekaDAQInputStream stream)
        {
            lock(this)
            {
                var channelData = new ITCMM.ITCChannelDataEx[]
                                      {
                                          new ITCMM.ITCChannelDataEx
                                              {
                                                  ChannelNumber = stream.ChannelNumber,
                                                  ChannelType = (ushort) stream.ChannelType
                                              }
                                      };

                uint err = ItcmmCall(() => ITCMM.ITC_AsyncIO(DevicePtr, 1, channelData));
                if (err != ITCMM.ACQ_SUCCESS)
                {
                    throw new HekaDAQException("Unable to read AsyncIO", err);
                }

                var inData =
                    new InputData(
                        new List<IMeasurement> {new Measurement(channelData[0].Value, 0, HekaDAQInputStream.DAQCountUnits)},
                        new Measurement(0, 0, "Hz"),
                        DateTimeOffset.Now)
                        .DataWithStreamConfiguration(stream, stream.Configuration);

                return inData.DataWithUnits(stream.MeasurementConversionTarget);
            }
        }
        public void PreloadSamples(StreamType channelType, ushort channelNumber, IList<short> samples)
        {
            ITCMM.ITCChannelDataEx[] channelData = new ITCMM.ITCChannelDataEx[1];

            channelData[0].ChannelType = (ushort)channelType;
            channelData[0].ChannelNumber = channelNumber;
            channelData[0].Value = (short)samples.Count;

            channelData[0].Command = ITCMM.PRELOAD_FIFO_COMMAND_EX;

            IntPtr samplesPtr = Marshal.AllocHGlobal(samples.Count * sizeof(short));

            try
            {

                Marshal.Copy(samples.ToArray(), 0, samplesPtr, samples.Count);
                channelData[0].DataPointer = samplesPtr;

                uint err = ItcmmCall(() => ITCMM.ITC_ReadWriteFIFO(DevicePtr, 1, channelData));
                if (err != ITCMM.ACQ_SUCCESS)
                {
                    throw new HekaDAQException("Unable to push data", err);
                }
            }
            finally
            {
                Marshal.FreeHGlobal(samplesPtr);
            }
        }
        public int MaxAvailableSamples(StreamType channelType, ushort channelNumber)
        {
            ITCMM.ITCChannelDataEx info = new ITCMM.ITCChannelDataEx();

            info.ChannelType = (ushort)channelType;
            info.ChannelNumber = channelNumber;

            var infoArr = new ITCMM.ITCChannelDataEx[1];
            infoArr[0] = info;
            uint err = ItcmmCall(() => ITCMM.ITC_GetFIFOInformation(DevicePtr, 1, infoArr));
            if (err != ITCMM.ACQ_SUCCESS)
            {
                throw new HekaDAQException("Unable to get FIFO information", err);
            }

            info = infoArr[0];

            return info.Value;
        }
        public int AvailableSamples(StreamType channelType, ushort channelNumber)
        {
            ItcmmCall(() => ITCMM.ITC_UpdateNow(DevicePtr, System.IntPtr.Zero));

            ITCMM.ITCChannelDataEx[] channelData = new ITCMM.ITCChannelDataEx[1];

            channelData[0].ChannelType = (ushort)channelType;
            channelData[0].ChannelNumber = channelNumber;

            uint err = ItcmmCall(() => ITCMM.ITC_GetDataAvailable(DevicePtr, 1, channelData));
            if (err != ITCMM.ACQ_SUCCESS)
            {
                throw new HekaDAQException("Unable to get available FIFO points", err);
            }

            return channelData[0].Value;
        }
        public void AsyncIORoundTrip()
        {
            HekkaDevice device = HekkaDevice.Zero;

            uint err = ITCMM.ITC_OpenDevice(ITCMM.USB18_ID, 0, ITCMM.SMART_MODE, out device);
            Assert.AreEqual(ITCMM.ACQ_SUCCESS,
                    err,
                    ErrorDescription.ErrorString(err)
                    );

            try
            {
                err = ITCMM.ITC_InitDevice(device, IntPtr.Zero); //ref sHWFunction);
                Assert.AreEqual(ITCMM.ACQ_SUCCESS,
                    err,
                    ErrorDescription.ErrorString(err)
                    );

                uint expectedValue = 8000;

                var channelData = new ITCMM.ITCChannelDataEx[] {
                    new ITCMM.ITCChannelDataEx {
                        ChannelNumber = 0,
                        ChannelType = ITCMM.OUTPUT_GROUP,
                        Value = (short)expectedValue
                    }
                };

                err = ITCMM.ITC_AsyncIO(device, 1, channelData);
                if (err != ITCMM.ACQ_SUCCESS)
                {
                    throw new HekaDAQException("Unable to write AsyncIO", err);
                }

                channelData = new ITCMM.ITCChannelDataEx[] {
                    new ITCMM.ITCChannelDataEx {
                        ChannelNumber = 0,
                        ChannelType = ITCMM.INPUT_GROUP,
                        Value = (short)expectedValue
                    }
                };

                err = ITCMM.ITC_AsyncIO(device, 1, channelData);
                if (err != ITCMM.ACQ_SUCCESS)
                {
                    throw new HekaDAQException("Unable to write AsyncIO", err);
                }

                var actualValue = channelData[0].Value;

                Assert.That(actualValue, Is.InRange(expectedValue - 50, expectedValue + 50));

            }
            finally
            {
                err = ITCMM.ITC_CloseDevice(device);
                Assert.AreEqual(ITCMM.ACQ_SUCCESS,
                    err,
                    ErrorDescription.ErrorString(err)
                    );
            }
        }
        public void ReadAvailableSamples()
        {
            HekkaDevice device = HekkaDevice.Zero;

            uint err = ITCMM.ITC_OpenDevice(ITCMM.USB18_ID, 0, ITCMM.SMART_MODE, out device);
            if (err != ITCMM.ACQ_SUCCESS)
            {
                Assert.Fail(ErrorDescription.ErrorString(err));
            }

            try
            {
                //ITCMM.HWFunction hwf = new ITCMM.HWFunction();

                err = ITCMM.ITC_InitDevice(device, IntPtr.Zero); // ref hwf);

                ITCMM.ITCPublicConfig config = new ITCMM.ITCPublicConfig();
                config.OutputEnable = 1;

                err = ITCMM.ITC_ConfigDevice(device, ref config);
                if (err != ITCMM.ACQ_SUCCESS)
                {
                    Assert.Fail(ErrorDescription.ErrorString(err));
                }

                Assert.NotNull(device);

                ITCMM.ITCChannelInfo channelInfo = new ITCMM.ITCChannelInfo();
                channelInfo.ChannelType = ITCMM.H2D;
                channelInfo.ChannelNumber = 0;
                channelInfo.SamplingRate = 1000.0;
                Assert.AreEqual(System.IntPtr.Zero, channelInfo.FIFOPointer);

                Assert.AreEqual(ITCMM.ACQ_SUCCESS,
                    ITCMM.ITC_SetChannels(device, 1, new ITCMM.ITCChannelInfo[] { channelInfo })
                    );

                Assert.AreEqual(ITCMM.ACQ_SUCCESS,
                    (int)ITCMM.ITC_UpdateChannels(device)
                    );

                ITCMM.ITCChannelDataEx info = new ITCMM.ITCChannelDataEx();

                info.ChannelType = ITCMM.H2D;
                info.ChannelNumber = 0;

                ITCMM.ITCChannelDataEx[] arr = new ITCMM.ITCChannelDataEx[] { info };
                err = ITCMM.ITC_GetDataAvailable(device, 1, arr);
                if (err != ITCMM.ACQ_SUCCESS)
                {
                    Assert.Fail(ErrorDescription.ErrorString(err));
                }

                info = arr[0];

                Assert.That(info.Value, Is.GreaterThanOrEqualTo(0));
            }
            finally
            {
                err = ITCMM.ITC_CloseDevice(device);
                Assert.AreEqual(ITCMM.ACQ_SUCCESS,
                    err,
                    ErrorDescription.ErrorString(err)
                    );
            }
        }