Class: PWN::SDR::Decoder::RFID::DetectorIQ

Inherits:
Object
  • Object
show all
Defined in:
lib/pwn/sdr/decoder/rfid.rb

Overview

Streaming I/Q energy/burst demod for Base.run_iq.

Instance Method Summary collapse

Constructor Details

#initialize(rate:, protocol:, modulation:, extra: {}) ⇒ DetectorIQ

Returns a new instance of DetectorIQ.



14
15
16
17
18
19
20
21
22
23
24
25
26
27
# File 'lib/pwn/sdr/decoder/rfid.rb', line 14

def initialize(rate:, protocol:, modulation:, extra: {})
  @rate = rate.to_f
  @protocol = protocol
  @modulation = modulation
  @extra = extra
  @floor = nil
  @in_burst = false
  @burst_t0 = nil
  @magnitudes = []
  @sample_count = 0
  @peak = -200.0
  @burst_n = 0
  @threshold = (extra[:threshold] || 8.0).to_f
end

Instance Method Details

#feed_iq(samples, rate: nil) ⇒ Object



29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
# File 'lib/pwn/sdr/decoder/rfid.rb', line 29

def feed_iq(samples, rate: nil, &)
  @rate = rate.to_f if rate
  @magnitudes.concat(PWN::SDR::Decoder::DSP.mag_sq(iq: samples))
  m2 = @magnitudes
  hop = [(@rate / 1000.0).round, 1].max
  i = 0
  while i + hop <= m2.length
    win = m2[i, hop]
    break if win.nil? || win.empty?

    ms = win.sum / win.length
    lvl = ms.positive? ? (10.0 * Math.log10(ms)) : -120.0
    @floor = @floor.nil? ? lvl : ((@floor * 0.98) + (lvl * 0.02))
    delta = lvl - @floor
    if delta >= @threshold
      unless @in_burst
        @in_burst = true
        @burst_t0 = @sample_count
        @peak = lvl
      end
      @peak = lvl if lvl > @peak
    elsif @in_burst
      emit_burst(&)
    end
    i += hop
    @sample_count += hop
  end
  @magnitudes.shift(i)
end

#flushObject



59
60
61
62
63
# File 'lib/pwn/sdr/decoder/rfid.rb', line 59

def flush(&)
  @sample_count += @magnitudes.length
  @magnitudes.clear
  emit_burst(truncated: true, &) if @in_burst
end