コード例 #1
0
        /// <summary>
        /// Get fundamental information about the device.
        /// </summary>
        /// <exception cref="RtlSdrLibraryExecutionException"></exception>
        private static DeviceInfo GetDeviceInfo(uint deviceIndex)
        {
            // Create buffers, where the results will be stored.
            var serialBuffer       = new StringBuilder(256);
            var manufacturerBuffer = new StringBuilder(256);
            var productBuffer      = new StringBuilder(256);

            // Get the device name.
            var nameBufferPtr = RtlSdrLibraryWrapper.rtlsdr_get_device_name(deviceIndex);
            var nameBuffer    = Marshal.PtrToStringUTF8(nameBufferPtr);

            // Get the other data of the device.
            var returnCode = RtlSdrLibraryWrapper.rtlsdr_get_device_usb_strings(deviceIndex,
                                                                                manufacturerBuffer, productBuffer, serialBuffer);

            if (returnCode != 0)
            {
                throw new RtlSdrLibraryExecutionException(
                          "Problem happened during reading USB strings of the device. " +
                          $"Error code: {returnCode}, device index: {deviceIndex}.");
            }

            // If everything is good, fill the device info.
            return(new DeviceInfo(deviceIndex, serialBuffer.ToString(), manufacturerBuffer.ToString(),
                                  productBuffer.ToString(), nameBuffer));
        }
コード例 #2
0
        /// <summary>
        /// Stop reading samples from the device.
        /// </summary>
        public void StopReadSamplesAsync()
        {
            // Check the worker thread.
            if (_asyncWorker == null)
            {
                return;
            }

            // Cancel the reading with the native function.
            var returnCode = RtlSdrLibraryWrapper.rtlsdr_cancel_async(_devicePointer);

            // If we did not get 0, there is an error.
            if (returnCode != 0)
            {
                throw new RtlSdrLibraryExecutionException(
                          "Problem happened during stopping asynchronous data reading. " +
                          $"Error code: {returnCode}, device index: {DeviceInfo.Index}.");
            }

            // Stop the worker thread.
            if (_asyncWorker.ThreadState == ThreadState.Running)
            {
                _asyncWorker.Join();
            }

            // Release the worker.
            _asyncWorker = null;

            // Empty the buffer.
            _asyncBuffer = null;
        }
コード例 #3
0
        /// <summary>
        /// Read samples (I/Q) from the device.
        /// </summary>
        /// <param name="requestedSamples">Amount of requested samples.</param>
        /// <returns>I/Q data from the device as an IqData list.</returns>
        /// <exception cref="RtlSdrLibraryExecutionException"></exception>
        public List <IQData> ReadSamples(int requestedSamples)
        {
            // I/Q data means 2 bytes.
            var requestedBytes = requestedSamples * 2;

            // Initialize the buffer.
            var buffer        = new byte[requestedBytes];
            var bufferPinned  = GCHandle.Alloc(buffer, GCHandleType.Pinned);
            var bufferPointer = bufferPinned.AddrOfPinnedObject();

            // Read the ubytes from the device.
            var returnCode = RtlSdrLibraryWrapper.rtlsdr_read_sync(_devicePointer,
                                                                   bufferPointer, requestedBytes, out var receivedBytes);

            // Overflow happened.
            if (returnCode == -8)
            {
                throw new RtlSdrLibraryExecutionException(
                          "Problem happened during reading bytes from the device (overflow, device provided more data). " +
                          $"Error code: {returnCode}, requested bytes: {requestedBytes}, device index: {DeviceInfo.Index}.");
            }

            // Error happened during reading the data.
            if (returnCode != 0)
            {
                throw new RtlSdrLibraryExecutionException(
                          "Problem happened during reading bytes from the device. " +
                          $"Error code: {returnCode}, requested bytes: {requestedBytes}, device index: {DeviceInfo.Index}.");
            }

            // Amount of the received bytes is different than the requested.
            if (receivedBytes != requestedBytes)
            {
                throw new RtlSdrLibraryExecutionException(
                          "Problem happened during reading bytes from the device. " +
                          $"Error code: {returnCode}, requested bytes: {requestedBytes}, " +
                          $"received bytes: {receivedBytes}, device index: {DeviceInfo.Index}.");
            }

            // Release the memory object.
            bufferPinned.Free();

            // Convert byte array to IqData list.
            var iqData = new List <IQData>();

            for (var i = 0; i < buffer.Length; i += 2)
            {
                iqData.Add(new IQData(buffer[i], buffer[i + 1]));
            }

            // Return the IqData list.
            return(iqData);
        }
コード例 #4
0
        /// <summary>
        /// Get fundamental information about all the devices on the system.
        /// </summary>
        /// <returns></returns>
        /// <exception cref="RtlSdrDeviceException"></exception>
        private static Dictionary <uint, DeviceInfo> GetAllDeviceInfo()
        {
            // Check the number of the devices on the system.
            var deviceCount = RtlSdrLibraryWrapper.rtlsdr_get_device_count();

            // If there is no device on the system, throw an exception.
            if (deviceCount == 0)
            {
                throw new RtlSdrDeviceException("There is no supported RTL-SDR device on the system.");
            }

            // Create the list, which will contain the devices.
            var devices = new Dictionary <uint, DeviceInfo>();

            // Iterate the devices.
            for (uint i = 0; i < deviceCount; i++)
            {
                // If everything is good, add the device to the list.
                devices.Add(i, GetDeviceInfo(i));
            }

            // Return the list.
            return(devices);
        }
コード例 #5
0
        /// <summary>
        /// Create an instance of managed RTL-SDR device.
        /// </summary>
        /// <param name="deviceInfo">Fundamental information of the device.</param>
        internal RtlSdrManagedDevice(DeviceInfo deviceInfo)
        {
            // Store the index number of the device.
            _deviceIndex = deviceInfo.Index;

            // Get the other data of the device.
            var returnCode = RtlSdrLibraryWrapper.rtlsdr_open(out _devicePointer, _deviceIndex);

            // The index doesn't exists on the system.
            if (returnCode == -1)
            {
                throw new RtlSdrLibraryExecutionException(
                          "RTL-SDR device cannot be found with the given index. " +
                          $"Error code: {returnCode}, device index: {_deviceIndex}.");
            }

            // The device is already managed.
            if (returnCode == -6)
            {
                throw new RtlSdrLibraryExecutionException(
                          "The RTL-SDR device is already managed (opened). " +
                          $"Error code: {returnCode}, device index: {_deviceIndex}.");
            }

            // Other error was happened.
            if (returnCode != 0)
            {
                throw new RtlSdrLibraryExecutionException(
                          "Problem happened during reading opening the RTL-SDR device. " +
                          $"Error code: {returnCode}, device index: {_deviceIndex}.");
            }

            // Set the device context.
            _deviceContext = GCHandle.Alloc(this);

            // Set the tuner gain mode to automatic.
            // The initialization is necessary, to be sure that it will happen once.
            TunerGainMode = TunerGainModes.AGC;

            // Set the AGC mode to disabled.
            // The initialization is necessary, to be sure that it will happen once.
            AGCMode = AGCModes.Disabled;

            // Set the test mode to disabled.
            // The initialization is necessary, to be sure that it will happen once.
            TestMode = TestModes.Disabled;

            // Set the bandwidth selection mode to automatic.
            // The initialization is necessary, to be sure that it will happen once.
            TunerBandwidthSelectionMode = TunerBandwidthSelectionModes.Automatic;

            // Set the default value of maximum async I/Q buffer.
            // The initialization is necessary, to be sure that it will happen once.
            MaxAsyncBufferSize = AsyncDefaultReadLength * 4;

            // Set the default value of behavior when the buffer is full.
            // The initialization is necessary, to be sure that it will happen once.
            DropSamplesOnFullBuffer = false;

            // Run GetDeviceInfo to put fundamental data of device to the cache.
            DeviceInfo = deviceInfo;
        }
コード例 #6
0
 /// <summary>
 /// Worker method to asynchronously read data from the RTL-SDR device.
 /// </summary>
 /// <exception cref="RtlSdrLibraryExecutionException"></exception>
 private void SamplesAsyncReader(object readLength)
 {
     // Read from device.
     RtlSdrLibraryWrapper.rtlsdr_read_async(_devicePointer, _asyncCallback,
                                            (IntPtr)_deviceContext, 0, (uint)readLength);
 }