Merged r5033:5116 from developer branch jcorgan/snd, with minor edits. Trunk passes...
[debian/gnuradio] / gr-sounder / src / python / usrp_sounder.py
diff --git a/gr-sounder/src/python/usrp_sounder.py b/gr-sounder/src/python/usrp_sounder.py
new file mode 100755 (executable)
index 0000000..ca722a4
--- /dev/null
@@ -0,0 +1,130 @@
+#!/usr/bin/env python
+#
+# Copyright 2007 Free Software Foundation, Inc.
+# 
+# This file is part of GNU Radio
+# 
+# GNU Radio is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2, or (at your option)
+# any later version.
+# 
+# GNU Radio is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+# 
+# You should have received a copy of the GNU General Public License
+# along with GNU Radio; see the file COPYING.  If not, write to
+# the Free Software Foundation, Inc., 51 Franklin Street,
+# Boston, MA 02110-1301, USA.
+# 
+
+from gnuradio import gr, usrp
+from gnuradio import eng_notation
+from gnuradio.eng_option import eng_option
+from optparse import OptionParser
+import sys, time
+
+n2s = eng_notation.num_to_str
+
+# Set to 0 for 32 MHz tx clock, 1 for 64 MHz tx clock
+# Must match config.vh in FPGA code
+TX_RATE_MAX = 0
+_tx_freq_divisor = 32e6*(TX_RATE_MAX+1)
+
+class sounder_tx:
+    def __init__(self, frequency, degree, loopback):
+       self.trans = usrp.sink_s(fpga_filename='usrp_sounder.rbf')
+        self.subdev_spec = usrp.pick_tx_subdevice(self.trans)
+        self.subdev = usrp.selected_subdev(self.trans, self.subdev_spec)
+        self.trans.tune(0, self.subdev, frequency)
+        self.set_degree(degree);
+        self.set_loopback(loopback)
+            
+    def turn_on(self):
+       self.trans.start()
+       
+    def turn_off(self):
+       self.trans.stop()
+
+    def set_degree(self, value):
+        return self.trans._write_fpga_reg(usrp.FR_USER_0, value);
+
+    def set_loopback(self, value):
+        return self.trans._write_fpga_reg(usrp.FR_USER_1, value==True);
+
+class sounder_rx:
+    def __init__(self, frequency, degree, samples):
+        self.fg = gr.flow_graph()
+       self.rcvr = usrp.source_s(fpga_filename='usrp_sounder.rbf', decim_rate=8)
+        self.subdev_spec = usrp.pick_rx_subdevice(self.rcvr)
+        self.subdev = usrp.selected_subdev(self.rcvr, self.subdev_spec)
+        self.rcvr.tune(0, self.subdev, frequency)
+        self.set_degree(degree);
+       self.sink = gr.file_sink(gr.sizeof_short, "output.dat")
+
+       if samples >= 0:
+           self.head = gr.head(gr.sizeof_short, 2*samples*gr.sizeof_short)
+           self.fg.connect(self.rcvr, self.head, self.sink)
+       else:
+           self.fg.connect(self.rcvr, self.sink)
+
+    def receive(self):
+       self.fg.run()
+       
+    def set_degree(self, value):
+        return self.rcvr._write_fpga_reg(usrp.FR_USER_0, value);
+
+def main():
+    parser = OptionParser(option_class=eng_option)
+    parser.add_option("-f", "--frequency", type="eng_float", default=0.0,
+                      help="set frequency to FREQ in Hz, default is %default", metavar="FREQ")
+
+    parser.add_option("-t", "--transmit", action="store_true", default=False,
+                      help="enable sounding transmitter")
+
+    parser.add_option("-r", "--receive", action="store_true", default=False,
+                      help="enable sounding receiver")
+
+    parser.add_option("-d", "--degree", type="int", default=16,
+                      help="set souding sequence degree (len=2^degree-1), default is %default")
+
+    parser.add_option("-n", "--samples", type="int", default=-1,
+                      help="number of samples to capture on receive, default is infinite")
+
+    parser.add_option("-l", "--loopback", action="store_true", default=False,
+                      help="enable digital loopback, default is disabled")
+
+    (options, args) = parser.parse_args()
+
+    if len(args) != 0 or not (options.transmit | options.receive):
+        parser.print_help()
+        sys.exit(1)
+
+    print "Using PN code degree of", options.degree, "length", 2**options.degree-1
+    print "Sounding frequency range is", n2s(options.frequency-16e6), "to", n2s(options.frequency+16e6)
+    
+    if (options.transmit):
+       print "Enabling sounder transmitter."
+       if (options.loopback):
+           print "Enabling digital loopback."
+        tx = sounder_tx(options.frequency, options.degree, options.loopback)
+       tx.turn_on()
+       
+    try:
+        if (options.receive):
+           print "Enabling sounder receiver."
+           rx = sounder_rx(options.frequency, options.degree, options.samples)
+           rx.receive()
+       else:
+           if (options.transmit):
+               while (True): time.sleep(1.0)
+
+    except KeyboardInterrupt:
+       if (options.transmit):
+           tx.turn_off()
+
+       
+if __name__ == "__main__":
+    main()