summaryrefslogtreecommitdiff
path: root/gr-trellis/python
diff options
context:
space:
mode:
Diffstat (limited to 'gr-trellis/python')
-rw-r--r--gr-trellis/python/CMakeLists.txt57
-rw-r--r--gr-trellis/python/__init__.py27
-rw-r--r--gr-trellis/python/awgn1o2_4.fsm15
-rwxr-xr-xgr-trellis/python/qa_trellis.py139
4 files changed, 238 insertions, 0 deletions
diff --git a/gr-trellis/python/CMakeLists.txt b/gr-trellis/python/CMakeLists.txt
new file mode 100644
index 0000000000..a166764fbe
--- /dev/null
+++ b/gr-trellis/python/CMakeLists.txt
@@ -0,0 +1,57 @@
+# Copyright 2011-2012 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 3, 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.
+
+########################################################################
+# Setup python install
+########################################################################
+include(GrPython)
+
+GR_PYTHON_INSTALL(
+ FILES
+ __init__.py
+ DESTINATION ${GR_PYTHON_DIR}/gnuradio/trellis
+ COMPONENT "trellis_python"
+)
+
+########################################################################
+# Handle the unit tests
+########################################################################
+if(ENABLE_TESTING)
+
+list(APPEND GR_TEST_PYTHON_DIRS
+ ${CMAKE_BINARY_DIR}/gr-trellis/python
+ ${CMAKE_BINARY_DIR}/gr-trellis/swig
+ ${CMAKE_BINARY_DIR}/gr-blocks/python
+ ${CMAKE_BINARY_DIR}/gr-blocks/swig
+ ${CMAKE_BINARY_DIR}/gr-filter/python
+ ${CMAKE_BINARY_DIR}/gr-filter/swig
+ ${CMAKE_BINARY_DIR}/gr-analog/python
+ ${CMAKE_BINARY_DIR}/gr-analog/swig
+ ${CMAKE_BINARY_DIR}/gr-digital/python
+ ${CMAKE_BINARY_DIR}/gr-digital/swig
+)
+list(APPEND GR_TEST_TARGET_DEPS gnuradio-trellis gnuradio-digital gnuradio-analog gnuradio-filter)
+
+include(GrTest)
+file(GLOB py_qa_test_files "qa_*.py")
+foreach(py_qa_test_file ${py_qa_test_files})
+ get_filename_component(py_qa_test_name ${py_qa_test_file} NAME_WE)
+ GR_ADD_TEST(${py_qa_test_name} ${PYTHON_EXECUTABLE} ${PYTHON_DASH_B} ${py_qa_test_file})
+endforeach(py_qa_test_file)
+endif(ENABLE_TESTING)
diff --git a/gr-trellis/python/__init__.py b/gr-trellis/python/__init__.py
new file mode 100644
index 0000000000..a1792bc9b4
--- /dev/null
+++ b/gr-trellis/python/__init__.py
@@ -0,0 +1,27 @@
+# Copyright 2012 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 3, 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.
+#
+
+'''
+Blocks and utilities for trellis coding and related.
+'''
+
+# The presence of this file turns this directory into a Python package
+
+from trellis_swig import *
diff --git a/gr-trellis/python/awgn1o2_4.fsm b/gr-trellis/python/awgn1o2_4.fsm
new file mode 100644
index 0000000000..9245c69ac1
--- /dev/null
+++ b/gr-trellis/python/awgn1o2_4.fsm
@@ -0,0 +1,15 @@
+2 4 4
+
+0 2
+0 2
+1 3
+1 3
+
+0 3
+3 0
+1 2
+2 1
+
+AWGN CC from Proakis-Salehi pg 779
+
+
diff --git a/gr-trellis/python/qa_trellis.py b/gr-trellis/python/qa_trellis.py
new file mode 100755
index 0000000000..0e1ddc61b2
--- /dev/null
+++ b/gr-trellis/python/qa_trellis.py
@@ -0,0 +1,139 @@
+#!/usr/bin/env python
+#
+# Copyright 2004,2010,2012 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 3, 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.
+#
+
+import math
+import os
+
+from gnuradio import gr, gr_unittest
+
+import trellis_swig as trellis
+import digital_swig as digital
+import analog_swig as analog
+import blocks_swig as blocks
+
+fsm_args = {"awgn1o2_4": (2, 4, 4,
+ (0, 2, 0, 2, 1, 3, 1, 3),
+ (0, 3, 3, 0, 1, 2, 2, 1),
+ ),
+ "rep2": (2, 1, 4, (0, 0), (0, 3)),
+ "nothing": (2, 1, 2, (0, 0), (0, 1)),
+ }
+
+constells = {2: digital.constellation_bpsk(),
+ 4: digital.constellation_qpsk(),
+ }
+
+class test_trellis (gr_unittest.TestCase):
+
+ def test_001_fsm (self):
+ f = trellis.fsm(*fsm_args["awgn1o2_4"])
+ self.assertEqual(fsm_args["awgn1o2_4"],(f.I(),f.S(),f.O(),f.NS(),f.OS()))
+
+ def test_002_fsm (self):
+ f = trellis.fsm(*fsm_args["awgn1o2_4"])
+ g = trellis.fsm(f)
+ self.assertEqual((g.I(),g.S(),g.O(),g.NS(),g.OS()),(f.I(),f.S(),f.O(),f.NS(),f.OS()))
+
+ def test_003_fsm (self):
+ # FIXME: no file "awgn1o2_4.fsm"
+ #f = trellis.fsm("awgn1o2_4.fsm")
+ #self.assertEqual(fsm_args["awgn1o2_4"],(f.I(),f.S(),f.O(),f.NS(),f.OS()))
+ pass
+
+ def test_004_fsm(self):
+ """ Test to make sure fsm works with a single state fsm."""
+ # Just checking that it initializes properly.
+ f = trellis.fsm(*fsm_args["rep2"])
+
+ def test_001_interleaver (self):
+ K = 5
+ IN = (1,2,3,4,0)
+ DIN = (4,0,1,2,3)
+ i = trellis.interleaver(K,IN)
+ self.assertEqual((K,IN,DIN),(i.K(),i.INTER(),i.DEINTER()))
+
+ def test_001_viterbi(self):
+ """
+ Runs some coding/decoding tests with a few different FSM
+ specs.
+ """
+ for name, args in fsm_args.items():
+ constellation = constells[args[2]]
+ fsms = trellis.fsm(*args)
+ noise = 0.1
+ tb = trellis_tb(constellation, fsms, noise)
+ tb.run()
+ # Make sure all packets succesfully transmitted.
+ self.assertEqual(tb.dst.ntotal(), tb.dst.nright())
+
+
+class trellis_tb(gr.top_block):
+ """
+ A simple top block for use testing gr-trellis.
+ """
+ def __init__(self, constellation, f, N0=0.25, seed=-666L):
+ """
+ constellation - a constellation object used for modulation.
+ f - a finite state machine specification used for coding.
+ N0 - noise level
+ seed - random seed
+ """
+ super(trellis_tb, self).__init__()
+ # packet size in bits (make it multiple of 16 so it can be packed in a short)
+ packet_size = 1024*16
+ # bits per FSM input symbol
+ bitspersymbol = int(round(math.log(f.I())/math.log(2))) # bits per FSM input symbol
+ # packet size in trellis steps
+ K = packet_size/bitspersymbol
+
+ # TX
+ src = gr.lfsr_32k_source_s()
+ # packet size in shorts
+ src_head = gr.head (gr.sizeof_short, packet_size/16)
+ # unpack shorts to symbols compatible with the FSM input cardinality
+ s2fsmi = gr.packed_to_unpacked_ss(bitspersymbol, gr.GR_MSB_FIRST)
+ # initial FSM state = 0
+ enc = trellis.encoder_ss(f, 0)
+ mod = digital.chunks_to_symbols_sc(constellation.points(), 1)
+
+ # CHANNEL
+ add = blocks.add_cc()
+ noise = analog.noise_source_c(analog.GR_GAUSSIAN,math.sqrt(N0/2),seed)
+
+ # RX
+ # data preprocessing to generate metrics for Viterbi
+ metrics = trellis.constellation_metrics_cf(constellation.base(), digital.TRELLIS_EUCLIDEAN)
+ # Put -1 if the Initial/Final states are not set.
+ va = trellis.viterbi_s(f, K, 0, -1)
+ # pack FSM input symbols to shorts
+ fsmi2s = gr.unpacked_to_packed_ss(bitspersymbol, gr.GR_MSB_FIRST)
+ # check the output
+ self.dst = gr.check_lfsr_32k_s()
+
+ self.connect (src, src_head, s2fsmi, enc, mod)
+ self.connect (mod, (add, 0))
+ self.connect (noise, (add, 1))
+ self.connect (add, metrics, va, fsmi2s, self.dst)
+
+
+if __name__ == '__main__':
+ gr_unittest.run(test_trellis, "test_trellis.xml")