Statistics
| Branch: | Tag: | Revision:

root / gr-digital / examples / narrowband / receive_path.py @ 6a1e9783

History | View | Annotate | Download (5.9 kB)

1 9be3761d Tom Rondeau
#!/usr/bin/env python
2 9be3761d Tom Rondeau
#
3 aed7404a Tom Rondeau
# Copyright 2005-2007,2011 Free Software Foundation, Inc.
4 9be3761d Tom Rondeau
# 
5 9be3761d Tom Rondeau
# This file is part of GNU Radio
6 9be3761d Tom Rondeau
# 
7 9be3761d Tom Rondeau
# GNU Radio is free software; you can redistribute it and/or modify
8 9be3761d Tom Rondeau
# it under the terms of the GNU General Public License as published by
9 9be3761d Tom Rondeau
# the Free Software Foundation; either version 3, or (at your option)
10 9be3761d Tom Rondeau
# any later version.
11 9be3761d Tom Rondeau
# 
12 9be3761d Tom Rondeau
# GNU Radio is distributed in the hope that it will be useful,
13 9be3761d Tom Rondeau
# but WITHOUT ANY WARRANTY; without even the implied warranty of
14 9be3761d Tom Rondeau
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15 9be3761d Tom Rondeau
# GNU General Public License for more details.
16 9be3761d Tom Rondeau
# 
17 9be3761d Tom Rondeau
# You should have received a copy of the GNU General Public License
18 9be3761d Tom Rondeau
# along with GNU Radio; see the file COPYING.  If not, write to
19 9be3761d Tom Rondeau
# the Free Software Foundation, Inc., 51 Franklin Street,
20 9be3761d Tom Rondeau
# Boston, MA 02110-1301, USA.
21 9be3761d Tom Rondeau
# 
22 9be3761d Tom Rondeau
23 8b3c4ccf Tom Rondeau
from gnuradio import gr, gru
24 9be3761d Tom Rondeau
from gnuradio import eng_notation
25 8b3c4ccf Tom Rondeau
from gnuradio import digital
26 8b3c4ccf Tom Rondeau
27 9be3761d Tom Rondeau
import copy
28 9be3761d Tom Rondeau
import sys
29 9be3761d Tom Rondeau
30 9be3761d Tom Rondeau
# /////////////////////////////////////////////////////////////////////////////
31 9be3761d Tom Rondeau
#                              receive path
32 9be3761d Tom Rondeau
# /////////////////////////////////////////////////////////////////////////////
33 9be3761d Tom Rondeau
34 9be3761d Tom Rondeau
class receive_path(gr.hier_block2):
35 9be3761d Tom Rondeau
    def __init__(self, demod_class, rx_callback, options):
36 9be3761d Tom Rondeau
        gr.hier_block2.__init__(self, "receive_path",
37 19948716 Tom Rondeau
                                gr.io_signature(1, 1, gr.sizeof_gr_complex),
38 19948716 Tom Rondeau
                                gr.io_signature(0, 0, 0))
39 9be3761d Tom Rondeau
        
40 9be3761d Tom Rondeau
        options = copy.copy(options)    # make a copy so we can destructively modify
41 9be3761d Tom Rondeau
42 19948716 Tom Rondeau
        self._verbose     = options.verbose
43 19948716 Tom Rondeau
        self._bitrate     = options.bitrate  # desired bit rate
44 9be3761d Tom Rondeau
45 19948716 Tom Rondeau
        self._rx_callback = rx_callback  # this callback is fired when a packet arrives
46 19948716 Tom Rondeau
        self._demod_class = demod_class  # the demodulator_class we're using
47 9be3761d Tom Rondeau
48 bcf44690 Tom Rondeau
        self._chbw_factor = options.chbw_factor # channel filter bandwidth factor
49 bcf44690 Tom Rondeau
50 9be3761d Tom Rondeau
        # Get demod_kwargs
51 9be3761d Tom Rondeau
        demod_kwargs = self._demod_class.extract_kwargs_from_options(options)
52 9be3761d Tom Rondeau
53 aed7404a Tom Rondeau
        # Build the demodulator
54 57860e01 Tom Rondeau
        self.demodulator = self._demod_class(**demod_kwargs)
55 bcf44690 Tom Rondeau
56 bcf44690 Tom Rondeau
        # Make sure the channel BW factor is between 1 and sps/2
57 bcf44690 Tom Rondeau
        # or the filter won't work.
58 bcf44690 Tom Rondeau
        if(self._chbw_factor < 1.0 or self._chbw_factor > self.samples_per_symbol()/2):
59 bcf44690 Tom Rondeau
            sys.stderr.write("Channel bandwidth factor ({0}) must be within the range [1.0, {1}].\n".format(self._chbw_factor, self.samples_per_symbol()/2))
60 bcf44690 Tom Rondeau
            sys.exit(1)
61 aed7404a Tom Rondeau
        
62 9be3761d Tom Rondeau
        # Design filter to get actual channel we want
63 9be3761d Tom Rondeau
        sw_decim = 1
64 9be3761d Tom Rondeau
        chan_coeffs = gr.firdes.low_pass (1.0,                  # gain
65 57860e01 Tom Rondeau
                                          sw_decim * self.samples_per_symbol(), # sampling rate
66 bcf44690 Tom Rondeau
                                          self._chbw_factor,    # midpoint of trans. band
67 9be3761d Tom Rondeau
                                          0.5,                  # width of trans. band
68 9be3761d Tom Rondeau
                                          gr.firdes.WIN_HANN)   # filter type
69 9be3761d Tom Rondeau
        self.channel_filter = gr.fft_filter_ccc(sw_decim, chan_coeffs)
70 9be3761d Tom Rondeau
        
71 9be3761d Tom Rondeau
        # receiver
72 9be3761d Tom Rondeau
        self.packet_receiver = \
73 57860e01 Tom Rondeau
            digital.demod_pkts(self.demodulator,
74 8b3c4ccf Tom Rondeau
                               access_code=None,
75 8b3c4ccf Tom Rondeau
                               callback=self._rx_callback,
76 8b3c4ccf Tom Rondeau
                               threshold=-1)
77 9be3761d Tom Rondeau
78 9be3761d Tom Rondeau
        # Carrier Sensing Blocks
79 9be3761d Tom Rondeau
        alpha = 0.001
80 9be3761d Tom Rondeau
        thresh = 30   # in dB, will have to adjust
81 9be3761d Tom Rondeau
        self.probe = gr.probe_avg_mag_sqrd_c(thresh,alpha)
82 9be3761d Tom Rondeau
83 9be3761d Tom Rondeau
        # Display some information about the setup
84 9be3761d Tom Rondeau
        if self._verbose:
85 9be3761d Tom Rondeau
            self._print_verbage()
86 9be3761d Tom Rondeau
87 9be3761d Tom Rondeau
        # connect block input to channel filter
88 9be3761d Tom Rondeau
        self.connect(self, self.channel_filter)
89 9be3761d Tom Rondeau
90 9be3761d Tom Rondeau
        # connect the channel input filter to the carrier power detector
91 9be3761d Tom Rondeau
        self.connect(self.channel_filter, self.probe)
92 9be3761d Tom Rondeau
93 9be3761d Tom Rondeau
        # connect channel filter to the packet receiver
94 9be3761d Tom Rondeau
        self.connect(self.channel_filter, self.packet_receiver)
95 9be3761d Tom Rondeau
96 9be3761d Tom Rondeau
    def bitrate(self):
97 9be3761d Tom Rondeau
        return self._bitrate
98 9be3761d Tom Rondeau
99 9be3761d Tom Rondeau
    def samples_per_symbol(self):
100 57860e01 Tom Rondeau
        return self.demodulator._samples_per_symbol
101 57860e01 Tom Rondeau
102 57860e01 Tom Rondeau
    def differential(self):
103 57860e01 Tom Rondeau
        return self.demodulator._differential
104 9be3761d Tom Rondeau
105 9be3761d Tom Rondeau
    def carrier_sensed(self):
106 9be3761d Tom Rondeau
        """
107 9be3761d Tom Rondeau
        Return True if we think carrier is present.
108 9be3761d Tom Rondeau
        """
109 9be3761d Tom Rondeau
        #return self.probe.level() > X
110 9be3761d Tom Rondeau
        return self.probe.unmuted()
111 9be3761d Tom Rondeau
112 9be3761d Tom Rondeau
    def carrier_threshold(self):
113 9be3761d Tom Rondeau
        """
114 9be3761d Tom Rondeau
        Return current setting in dB.
115 9be3761d Tom Rondeau
        """
116 9be3761d Tom Rondeau
        return self.probe.threshold()
117 9be3761d Tom Rondeau
118 9be3761d Tom Rondeau
    def set_carrier_threshold(self, threshold_in_db):
119 9be3761d Tom Rondeau
        """
120 9be3761d Tom Rondeau
        Set carrier threshold.
121 9be3761d Tom Rondeau
122 9be3761d Tom Rondeau
        @param threshold_in_db: set detection threshold
123 9be3761d Tom Rondeau
        @type threshold_in_db:  float (dB)
124 9be3761d Tom Rondeau
        """
125 9be3761d Tom Rondeau
        self.probe.set_threshold(threshold_in_db)
126 9be3761d Tom Rondeau
    
127 9be3761d Tom Rondeau
        
128 9be3761d Tom Rondeau
    def add_options(normal, expert):
129 9be3761d Tom Rondeau
        """
130 9be3761d Tom Rondeau
        Adds receiver-specific options to the Options Parser
131 9be3761d Tom Rondeau
        """
132 a2af88f6 Tom Rondeau
        if not normal.has_option("--bitrate"):
133 a2af88f6 Tom Rondeau
            normal.add_option("-r", "--bitrate", type="eng_float", default=100e3,
134 a2af88f6 Tom Rondeau
                              help="specify bitrate [default=%default].")
135 9be3761d Tom Rondeau
        normal.add_option("-v", "--verbose", action="store_true", default=False)
136 19948716 Tom Rondeau
        expert.add_option("-S", "--samples-per-symbol", type="float", default=2,
137 9be3761d Tom Rondeau
                          help="set samples/symbol [default=%default]")
138 9be3761d Tom Rondeau
        expert.add_option("", "--log", action="store_true", default=False,
139 9be3761d Tom Rondeau
                          help="Log all parts of flow graph to files (CAUTION: lots of data)")
140 bcf44690 Tom Rondeau
        expert.add_option("", "--chbw-factor", type="float", default=1.0,
141 bcf44690 Tom Rondeau
                          help="Channel bandwidth = chbw_factor x signal bandwidth [defaut=%default]")
142 9be3761d Tom Rondeau
143 9be3761d Tom Rondeau
    # Make a static method to call before instantiation
144 9be3761d Tom Rondeau
    add_options = staticmethod(add_options)
145 9be3761d Tom Rondeau
146 9be3761d Tom Rondeau
147 9be3761d Tom Rondeau
    def _print_verbage(self):
148 9be3761d Tom Rondeau
        """
149 9be3761d Tom Rondeau
        Prints information about the receive path
150 9be3761d Tom Rondeau
        """
151 9be3761d Tom Rondeau
        print "\nReceive Path:"
152 9be3761d Tom Rondeau
        print "modulation:      %s"    % (self._demod_class.__name__)
153 9be3761d Tom Rondeau
        print "bitrate:         %sb/s" % (eng_notation.num_to_str(self._bitrate))
154 57860e01 Tom Rondeau
        print "samples/symbol:  %.4f"    % (self.samples_per_symbol())
155 57860e01 Tom Rondeau
        print "Differential:    %s"    % (self.differential())