merging from trondeau/digital-wip for improved dbpsk and dqpsk receivers
authortrondeau <trondeau@221aa14e-8319-0410-a670-987f0aec2ac5>
Sun, 5 Nov 2006 21:14:00 +0000 (21:14 +0000)
committertrondeau <trondeau@221aa14e-8319-0410-a670-987f0aec2ac5>
Sun, 5 Nov 2006 21:14:00 +0000 (21:14 +0000)
git-svn-id: http://gnuradio.org/svn/gnuradio/trunk@3946 221aa14e-8319-0410-a670-987f0aec2ac5

gnuradio-core/src/python/gnuradio/blksimpl/dbpsk.py
gnuradio-core/src/python/gnuradio/blksimpl/dqpsk.py
gnuradio-core/src/python/gnuradio/packet_utils.py

index 7df4f240c5178c131addaffbb2bc361b29cdedce..e0c0054a69297f4739d0b3cc689081c75a6abea1 100644 (file)
@@ -39,7 +39,7 @@ _def_gray_code = True
 _def_verbose = False
 _def_log = False
 
-_def_costas_alpha = 0.05
+_def_costas_alpha = 0.00
 _def_gain_mu = 0.03
 _def_mu = 0.05
 _def_omega_relative_limit = 0.005
@@ -241,10 +241,12 @@ class dbpsk_demod(gr.hier_block):
 
         
         # Costas loop (carrier tracking)
-        # FIXME: need to decide how to handle this more generally; do we pull it from higher layer?
-        costas_order = 2
-        beta = .25 * self._costas_alpha * self._costas_alpha
-        self.costas_loop = gr.costas_loop_cc(self._costas_alpha, beta, 0.002, -0.002, costas_order)
+        # The Costas loop is not needed for BPSK, though it can help. Turn the Costas loop on
+        # by setting an alpha value of something greater than 0 (e.g., 0.1)
+        if self._costas_alpha > 0.0:
+            costas_order = 2
+            beta = .25 * self._costas_alpha * self._costas_alpha
+            self.costas_loop = gr.costas_loop_cc(self._costas_alpha, beta, 0.002, -0.002, costas_order)
 
         # RRC data filter
         ntaps = 11 * self._samples_per_symbol
@@ -289,9 +291,14 @@ class dbpsk_demod(gr.hier_block):
             self._setup_logging()
 
         # Connect and Initialize base class
-        self._fg.connect(self.pre_scaler, self.agc, self.costas_loop,
-                         self.rrc_filter, self.clock_recovery, self.diffdec,
-                         self.slicer, self.symbol_mapper, self.unpack)
+        if self._costas_alpha > 0.0:   # With Costas Loop
+            self._fg.connect(self.pre_scaler, self.agc, self.costas_loop,
+                             self.rrc_filter, self.clock_recovery, self.diffdec,
+                             self.slicer, self.symbol_mapper, self.unpack)
+        else: # Without Costas Loop
+            self._fg.connect(self.pre_scaler, self.agc,
+                             self.rrc_filter, self.clock_recovery, self.diffdec,
+                             self.slicer, self.symbol_mapper, self.unpack)
 
         gr.hier_block.__init__(self, self._fg, self.pre_scaler, self.unpack)
 
@@ -317,10 +324,11 @@ class dbpsk_demod(gr.hier_block):
                          gr.file_sink(gr.sizeof_gr_complex, "prescaler.dat"))
         self._fg.connect(self.agc,
                          gr.file_sink(gr.sizeof_gr_complex, "agc.dat"))
-        self._fg.connect(self.costas_loop,
-                         gr.file_sink(gr.sizeof_gr_complex, "costas_loop.dat"))
-        self._fg.connect((self.costas_loop,1),
-                         gr.file_sink(gr.sizeof_gr_complex, "costas_error.dat"))
+        if self._costas_alpha > 0.0:
+            self._fg.connect(self.costas_loop,
+                             gr.file_sink(gr.sizeof_gr_complex, "costas_loop.dat"))
+            self._fg.connect((self.costas_loop,1),
+                             gr.file_sink(gr.sizeof_gr_complex, "costas_error.dat"))
         self._fg.connect(self.rrc_filter,
                          gr.file_sink(gr.sizeof_gr_complex, "rrc_filter.dat"))
         self._fg.connect(self.clock_recovery,
index 3b60f2242e2fbf69a41aeea4eedb359a6a133a6f..88b3f1e73ce6fb342b29871d90e13fe5e73e3fb6 100644 (file)
@@ -39,7 +39,7 @@ _def_gray_code = True
 _def_verbose = False
 _def_log = False
 
-_def_costas_alpha = 0.10
+_def_costas_alpha = 0.0
 _def_gain_mu = 0.03
 _def_mu = 0.05
 _def_omega_relative_limit = 0.005
@@ -238,11 +238,15 @@ class dqpsk_demod(gr.hier_block):
         self.agc = gr.feedforward_agc_cc(16, 1.0)
        
         # Costas loop (carrier tracking)
-        # FIXME: need to decide how to handle this more generally; do we pull it from higher layer?
-        costas_order = 4
-        beta = .25 * self._costas_alpha * self._costas_alpha
-        #self.costas_loop = gr.costas_loop_cc(self._costas_alpha, beta, 0.1, -0.1, costas_order)
-        self.costas_loop = gr.costas_loop_cc(self._costas_alpha, beta, 0.002, -0.002, costas_order)
+        if self._costas_alpha == 0.0:   # If no alpha value was specified by the user
+            alpha_dir = {2:0.075, 3:0.075, 4:0.105, 5:0.105, 6:0.125, 7:0.130}
+            self._costas_alpha = alpha_dir[self._samples_per_symbol]
+        
+        costas_order = 4        
+        # The value of beta is now set to be overdamped; this value can have a huge impact on the
+        # performance of QPSK. Set to 0.25 for critically damped or higher for underdamped responses.
+        beta = .15 * self._costas_alpha * self._costas_alpha
+        self.costas_loop = gr.costas_loop_cc(self._costas_alpha, beta, 0.02, -0.02, costas_order)
 
         # RRC data filter
         ntaps = 11 * samples_per_symbol
index 1dab48ab426a052c201a41e9cebdf94fe74b7d23..59b1353662086cff8c7e12fe4b642afeb3cca252 100644 (file)
@@ -72,7 +72,7 @@ def conv_1_0_string_to_packed_binary_string(s):
 default_access_code = \
   conv_packed_binary_string_to_1_0_string('\xAC\xDD\xA4\xE2\xF2\x8C\x20\xFC')
 preamble = \
-  conv_packed_binary_string_to_1_0_string('\xAA\xAA\xAA\xAB')
+  conv_packed_binary_string_to_1_0_string('\x6C\xC6\x6C\xC6\x6C\xC6\x6C\xC6')
 
 def is_1_0_string(s):
     if not isinstance(s, str):