def __init__(self, template, thresh_coeffs, block_len, history_len): self.template = Signal(template) self.template_energy = np.sum(self.template.power) template_len = len(template) self.corr_len = block_len - template_len + 1 self.template_padded = np.concatenate( [self.template, np.zeros(self.corr_len - 1)]) self.template_padded = Signal(self.template_padded) self.template_fft = self.template_padded.fft self.interpolate = gaussian_interpolation self.window = calculate_window(block_len, history_len, template_len) self.thresh_coeffs = thresh_coeffs
def block_reader(stream, size, history): """Read fixed-sized blocks from a stream of raw RTL-SDR samples. Parameters ---------- stream : file-like object Raw 8-bit I/Q interleaved data from RTL-SDR. size : int Size of the blocks that should be generated. history : int Number of samples from the end of the previous block that should be included at the start of a new block. Each block will contain `size` - `history` new samples. Yields ------ timestamp : float Approximate time at which the data was captured. block_idx : int Block index, starting from zero for the first block. data : :class:`numpy.ndarray` Complex-valued array with the block's samples. """ new = size - history # Number of new samples per block data = np.zeros(size) for block_idx, block in enumerate(_raw_block_reader(stream, new * 2)): new_data = raw_to_complex(block) data = np.concatenate([data[-history:], new_data]) yield time.time(), block_idx, Signal(data)
def card_reader(stream): """Read blocks from .card file. A .card ("CARrier Detection") file generally contains blocks of data for which a carrier has been detected. Parameters ---------- stream : file-like object Yields ------ timestamp : float Approximate time at which the data was captured. block_idx : int Block index, starting from zero for the first block that was captured. data : :class:`numpy.ndarray` Complex-valued array with the block's samples. """ while True: line = stream.readline() if len(line) == 0: break if line[0] == '#' or line[0] == '\n': continue if line.startswith('Using Volk machine:') or line.startswith('linux;'): continue timestamp, idx, encoded = line.rstrip('\n').split(' ') raw = np.fromstring(base64.b64decode(encoded), dtype='uint8') data = raw_to_complex(raw) yield float(timestamp), int(idx), Signal(data)
def __init__(self, detection, settings, sample_rate): self.result = detection.result self.unsynced = detection.unsynced self.synced = detection.synced self.corr = detection.corr self.settings = settings self.sample_rate = sample_rate self.template = Signal(self.settings.template) filter_width = int(settings.block_len / settings.carrier_len) * 2 filter_weights = carrier_sync.dirichlet_weights( filter_width, settings.block_len, settings.carrier_len) filtered, delay = carrier_detect._filter(self.unsynced.fft.mag, filter_weights) self.filtered_fft = Signal(filtered[delay:]) self.carrier_interpolator = carrier_sync.make_dirichlet_interpolator( settings.block_len, settings.carrier_len, return_amplitude=True) self.corr_threshold = soa_estimator.calculate_threshold( self.corr, self.result.corr_info.noise, self.settings.corr_thresh)
def test_get_peak(idx, corr_len, window, expected): """Test peak detection with a constant threshold.""" corr = Signal(np.zeros(corr_len)) corr[idx] = 100 peak_idx, peak_mag = soa_estimator.get_peak(corr, window) detected = peak_mag > 99 assert detected == expected if expected: assert peak_idx == idx assert peak_mag == 100
def __init__(self, template, block_len, num=NUM_TEMPLATES): self.corr_len = block_len - len(template) + 1 template_padded = np.concatenate([template, np.zeros(self.corr_len-1)]) template_padded = Signal(template_padded) self.shifts = np.linspace(-0.5, 0.5, num) freqs = np.arange(block_len) * 1. / block_len - 0.5 self.ffts = [] for shift in self.shifts: shift_signal = np.exp(-2j * np.pi * shift * freqs) shifted = template_padded * shift_signal self.ffts.append(shifted.fft.conj) self.num = num
def test_freq_shift(size, freq, shift): """Test freq_shift() with sinusoidal signals.""" signal = np.exp(2j*np.pi*np.arange(size)/size*freq) expected = np.exp(2j*np.pi*np.arange(size)/size*(freq+shift)) expected_fft = np.fft.fft(expected) got = carrier_sync.freq_shift(Signal(signal), shift) # import matplotlib.pyplot as plt # plt.plot(np.abs(signal_fft), label="Signal") # plt.plot(np.abs(expected_fft), label="Expected") # plt.plot(np.abs(got), label="Got") # plt.legend() # plt.show() np.testing.assert_allclose(np.abs(got), np.abs(expected_fft), atol=1e-6, rtol=1e-6)
def _scaled_ook_template(self, signal): ook_template = self.template - np.min(self.template) ook_template = ook_template * signal.rms / Signal(ook_template).rms return ook_template