diff options
author | Johnathan Corgan <johnathan@corganlabs.com> | 2013-04-09 12:32:11 -0700 |
---|---|---|
committer | Johnathan Corgan <johnathan@corganlabs.com> | 2013-04-09 12:32:11 -0700 |
commit | 8d48040548fcac5e9105fb0e29385dbb3c2c0c19 (patch) | |
tree | 4db793bebbbf3d397b8f22d6e5373cafb2e46644 | |
parent | 0442f56a40c82a67705a108cdbbbedc85a84dc1d (diff) | |
parent | b2c7f058878f7a334fd81bb96d3bd9cd11f27f28 (diff) |
Merge remote-tracking branch 'martin/next-ofdmfix' into next
-rw-r--r-- | gr-digital/include/digital/ofdm_frame_equalizer_vcvc.h | 3 | ||||
-rw-r--r-- | gr-digital/include/digital/packet_header_default.h | 7 | ||||
-rw-r--r-- | gr-digital/include/digital/packet_header_ofdm.h | 39 | ||||
-rw-r--r-- | gr-digital/lib/ofdm_frame_equalizer_vcvc_impl.cc | 40 | ||||
-rw-r--r-- | gr-digital/lib/ofdm_frame_equalizer_vcvc_impl.h | 8 | ||||
-rw-r--r-- | gr-digital/lib/packet_header_ofdm.cc | 18 | ||||
-rw-r--r-- | gr-digital/lib/packet_headerparser_b_impl.cc | 2 | ||||
-rwxr-xr-x | gr-digital/python/qa_ofdm_frame_equalizer_vcvc.py | 33 | ||||
-rwxr-xr-x | gr-digital/python/qa_ofdm_serializer_vcc.py | 3 | ||||
-rwxr-xr-x | gr-digital/python/qa_ofdm_sync_sc_cfb.py | 3 | ||||
-rwxr-xr-x | gr-digital/python/qa_packet_headergenerator_bb.py | 8 | ||||
-rwxr-xr-x | gr-digital/python/qa_packet_headerparser_b.py | 96 |
12 files changed, 203 insertions, 57 deletions
diff --git a/gr-digital/include/digital/ofdm_frame_equalizer_vcvc.h b/gr-digital/include/digital/ofdm_frame_equalizer_vcvc.h index 9cf24034a8..f8e15fb577 100644 --- a/gr-digital/include/digital/ofdm_frame_equalizer_vcvc.h +++ b/gr-digital/include/digital/ofdm_frame_equalizer_vcvc.h @@ -52,7 +52,8 @@ namespace gr { static sptr make( ofdm_equalizer_base::sptr equalizer, const std::string &len_tag_key = "frame_len", - bool propagate_channel_state=false + bool propagate_channel_state=false, + int fixed_frame_len=0 ); }; diff --git a/gr-digital/include/digital/packet_header_default.h b/gr-digital/include/digital/packet_header_default.h index 64804e6d6a..e4c994593f 100644 --- a/gr-digital/include/digital/packet_header_default.h +++ b/gr-digital/include/digital/packet_header_default.h @@ -76,7 +76,7 @@ namespace gr { * If the header length is smaller than 29, bits are simply left out. For this * reason, they always start with the LSB. */ - bool header_formatter( + virtual bool header_formatter( long packet_len, unsigned char *out, const std::vector<gr_tag_t> &tags=std::vector<gr_tag_t>() @@ -85,10 +85,9 @@ namespace gr { /*! * \brief Inverse function to header_formatter(). * - * Reads the bit stream in and writes a corresponding tag into \p tags. - * + * Reads the bit stream in \p header and writes a corresponding tag into \p tags. */ - bool header_parser( + virtual bool header_parser( const unsigned char *header, std::vector<gr_tag_t> &tags); diff --git a/gr-digital/include/digital/packet_header_ofdm.h b/gr-digital/include/digital/packet_header_ofdm.h index 50296a9a50..30d6a953cd 100644 --- a/gr-digital/include/digital/packet_header_ofdm.h +++ b/gr-digital/include/digital/packet_header_ofdm.h @@ -41,10 +41,11 @@ namespace gr { packet_header_ofdm( const std::vector<std::vector<int> > &occupied_carriers, int n_syms, - const std::string &len_tag_key="packet_len", - const std::string &frame_len_tag_key="frame_len", - const std::string &num_tag_key="packet_num", - int bits_per_sym=1); + const std::string &len_tag_key, + const std::string &frame_len_tag_key, + const std::string &num_tag_key, + int bits_per_header_sym, + int bits_per_payload_sym); ~packet_header_ofdm(); /*! @@ -61,19 +62,37 @@ namespace gr { const unsigned char *header, std::vector<gr_tag_t> &tags); + /*! + * \param occupied_carriers See carrier allocator + * \param n_syms The number of OFDM symbols the header should be (usually 1) + * \param len_tag_key The tag key used for the packet length (number of bytes) + * \param frame_len_tag_key The tag key used for the frame length (number of + * OFDM symbols, this is the tag key required for the + * frame equalizer etc.) + * \param bits_per_header_sym Bits per complex symbol in the header, e.g. 1 if + * the header is BPSK modulated, 2 if it's QPSK + * modulated etc. + * \param bits_per_payload_sym Bits per complex symbol in the payload. This is + * required to figure out how many OFDM symbols + * are necessary to encode the given number of + * bytes. + */ static sptr make( - const std::vector<std::vector<int> > &occupied_carriers, - int n_syms, - const std::string &len_tag_key="packet_len", - const std::string &frame_len_tag_key="frame_len", - const std::string &num_tag_key="packet_num", - int bits_per_sym=1); + const std::vector<std::vector<int> > &occupied_carriers, + int n_syms, + const std::string &len_tag_key="packet_len", + const std::string &frame_len_tag_key="frame_len", + const std::string &num_tag_key="packet_num", + int bits_per_header_sym=1, + int bits_per_payload_sym=1 + ); protected: pmt::pmt_t d_frame_len_tag_key; const std::vector<std::vector<int> > d_occupied_carriers; //!< Which carriers/symbols carry data int d_syms_per_set; //!< Helper variable: Total number of elements in d_occupied_carriers + int d_bits_per_payload_sym; }; } // namespace digital diff --git a/gr-digital/lib/ofdm_frame_equalizer_vcvc_impl.cc b/gr-digital/lib/ofdm_frame_equalizer_vcvc_impl.cc index 594b2df838..68050f24b1 100644 --- a/gr-digital/lib/ofdm_frame_equalizer_vcvc_impl.cc +++ b/gr-digital/lib/ofdm_frame_equalizer_vcvc_impl.cc @@ -30,25 +30,39 @@ namespace gr { namespace digital { ofdm_frame_equalizer_vcvc::sptr - ofdm_frame_equalizer_vcvc::make(ofdm_equalizer_base::sptr equalizer, const std::string &len_tag_key, bool propagate_channel_state) + ofdm_frame_equalizer_vcvc::make( + ofdm_equalizer_base::sptr equalizer, + const std::string &len_tag_key, + bool propagate_channel_state, + int fixed_frame_len + ) { return gnuradio::get_initial_sptr ( new ofdm_frame_equalizer_vcvc_impl( - equalizer, len_tag_key, propagate_channel_state + equalizer, len_tag_key, propagate_channel_state, fixed_frame_len ) ); } - ofdm_frame_equalizer_vcvc_impl::ofdm_frame_equalizer_vcvc_impl(ofdm_equalizer_base::sptr equalizer, const std::string &len_tag_key, bool propagate_channel_state) - : gr_tagged_stream_block("ofdm_frame_equalizer_vcvc", + ofdm_frame_equalizer_vcvc_impl::ofdm_frame_equalizer_vcvc_impl( + ofdm_equalizer_base::sptr equalizer, + const std::string &len_tag_key, + bool propagate_channel_state, + int fixed_frame_len + ) : gr_tagged_stream_block("ofdm_frame_equalizer_vcvc", gr_make_io_signature(1, 1, sizeof (gr_complex) * equalizer->fft_len()), gr_make_io_signature(1, 1, sizeof (gr_complex) * equalizer->fft_len()), len_tag_key), d_fft_len(equalizer->fft_len()), d_eq(equalizer), d_propagate_channel_state(propagate_channel_state), + d_fixed_frame_len(len_tag_key.empty() ? fixed_frame_len : 0), d_channel_state(equalizer->fft_len(), gr_complex(1, 0)) - {} + { + if (d_fixed_frame_len) { + set_output_multiple(d_fixed_frame_len); + } + } ofdm_frame_equalizer_vcvc_impl::~ofdm_frame_equalizer_vcvc_impl() { @@ -64,6 +78,12 @@ namespace gr { const gr_complex *in = (const gr_complex *) input_items[0]; gr_complex *out = (gr_complex *) output_items[0]; int carrier_offset = 0; + int frame_len = 0; + if (d_fixed_frame_len) { + frame_len = d_fixed_frame_len; + } else { + frame_len = ninput_items[0]; + } std::vector<gr_tag_t> tags; get_tags_in_range(tags, 0, nitems_read(0), nitems_read(0)+1); @@ -74,10 +94,10 @@ namespace gr { } } - memcpy((void *) out, (void *) in, sizeof(gr_complex) * d_fft_len * ninput_items[0]); + memcpy((void *) out, (void *) in, sizeof(gr_complex) * d_fft_len * frame_len); d_eq->reset(); d_eq->set_carrier_offset(carrier_offset); - d_eq->equalize(out, ninput_items[0], d_channel_state); + d_eq->equalize(out, frame_len, d_channel_state); d_eq->get_channel_state(d_channel_state); if (d_propagate_channel_state) { add_item_tag(0, nitems_written(0), @@ -85,7 +105,11 @@ namespace gr { pmt::init_c32vector(d_fft_len, d_channel_state)); } - return ninput_items[0]; + if (d_fixed_frame_len) { + consume_each(frame_len); + } + + return frame_len; } } /* namespace digital */ diff --git a/gr-digital/lib/ofdm_frame_equalizer_vcvc_impl.h b/gr-digital/lib/ofdm_frame_equalizer_vcvc_impl.h index f86451e839..81789e22c4 100644 --- a/gr-digital/lib/ofdm_frame_equalizer_vcvc_impl.h +++ b/gr-digital/lib/ofdm_frame_equalizer_vcvc_impl.h @@ -33,6 +33,7 @@ namespace gr { const int d_fft_len; ofdm_equalizer_base::sptr d_eq; bool d_propagate_channel_state; + const int d_fixed_frame_len; std::vector<gr_complex> d_channel_state; protected: @@ -41,7 +42,12 @@ namespace gr { void update_length_tags(int n_produced, int n_ports) {}; public: - ofdm_frame_equalizer_vcvc_impl(ofdm_equalizer_base::sptr equalizer, const std::string &len_tag_key, bool propagate_channel_state); + ofdm_frame_equalizer_vcvc_impl( + ofdm_equalizer_base::sptr equalizer, + const std::string &len_tag_key, + bool propagate_channel_state, + int fixed_frame_len + ); ~ofdm_frame_equalizer_vcvc_impl(); int work(int noutput_items, diff --git a/gr-digital/lib/packet_header_ofdm.cc b/gr-digital/lib/packet_header_ofdm.cc index ed3d3586cb..cd42273285 100644 --- a/gr-digital/lib/packet_header_ofdm.cc +++ b/gr-digital/lib/packet_header_ofdm.cc @@ -45,11 +45,12 @@ namespace gr { const std::string &len_tag_key, const std::string &frame_len_tag_key, const std::string &num_tag_key, - int bits_per_sym) + int bits_per_header_sym, + int bits_per_payload_sym) { return packet_header_ofdm::sptr( new packet_header_ofdm( - occupied_carriers, n_syms, len_tag_key, frame_len_tag_key, num_tag_key, bits_per_sym + occupied_carriers, n_syms, len_tag_key, frame_len_tag_key, num_tag_key, bits_per_header_sym, bits_per_payload_sym ) ); } @@ -60,15 +61,17 @@ namespace gr { const std::string &len_tag_key, const std::string &frame_len_tag_key, const std::string &num_tag_key, - int bits_per_sym) + int bits_per_header_sym, + int bits_per_payload_sym) : packet_header_default( _get_header_len_from_occupied_carriers(occupied_carriers, n_syms), len_tag_key, num_tag_key, - bits_per_sym), + bits_per_header_sym), d_frame_len_tag_key(pmt::string_to_symbol(frame_len_tag_key)), d_occupied_carriers(occupied_carriers), - d_syms_per_set(0) + d_syms_per_set(0), + d_bits_per_payload_sym(bits_per_payload_sym) { for (unsigned i = 0; i < d_occupied_carriers.size(); i++) { d_syms_per_set += d_occupied_carriers[i].size(); @@ -87,14 +90,17 @@ namespace gr { if (!packet_header_default::header_parser(in, tags)) { return false; } - int packet_len = 0; // # of OFDM symbols + int packet_len = 0; // # of bytes in this frame for (unsigned i = 0; i < tags.size(); i++) { if (pmt::equal(tags[i].key, d_len_tag_key)) { packet_len = pmt::to_long(tags[i].value); break; } } + // Convert bytes to complex symbols: + packet_len = packet_len * 8 / d_bits_per_payload_sym; + // frame_len == # of OFDM symbols in this frame int frame_len = packet_len / d_syms_per_set; int k = 0; int i = frame_len * d_syms_per_set; diff --git a/gr-digital/lib/packet_headerparser_b_impl.cc b/gr-digital/lib/packet_headerparser_b_impl.cc index 60e1fdef0b..17e5e85091 100644 --- a/gr-digital/lib/packet_headerparser_b_impl.cc +++ b/gr-digital/lib/packet_headerparser_b_impl.cc @@ -79,7 +79,7 @@ namespace gr { } else { pmt::pmt_t dict(pmt::make_dict()); for (unsigned i = 0; i < tags.size(); i++) { - pmt::dict_add(dict, tags[i].key, tags[i].value); + dict = pmt::dict_add(dict, tags[i].key, tags[i].value); } message_port_pub(msg_port_id, dict); } diff --git a/gr-digital/python/qa_ofdm_frame_equalizer_vcvc.py b/gr-digital/python/qa_ofdm_frame_equalizer_vcvc.py index 5a34791650..cb087da2f4 100755 --- a/gr-digital/python/qa_ofdm_frame_equalizer_vcvc.py +++ b/gr-digital/python/qa_ofdm_frame_equalizer_vcvc.py @@ -106,6 +106,39 @@ class qa_ofdm_frame_equalizer_vcvc (gr_unittest.TestCase): if pmt.symbol_to_string(tag.key) == "ofdm_sync_chan_taps": self.assertEqual(list(pmt.c32vector_elements(tag.value)), channel[-fft_len:]) + def test_002_static_wo_tags (self): + fft_len = 8 + # 4 5 6 7 0 1 2 3 + tx_data = [-1, -1, 1, 2, -1, 3, 0, -1, # 0 + -1, -1, 0, 2, -1, 2, 0, -1, # 8 + -1, -1, 3, 0, -1, 1, 0, -1, # 16 (Pilot symbols) + -1, -1, 1, 1, -1, 0, 2, -1] # 24 + cnst = digital.constellation_qpsk() + tx_signal = [cnst.map_to_points_v(x)[0] if x != -1 else 0 for x in tx_data] + occupied_carriers = ((1, 2, 6, 7),) + pilot_carriers = ((), (), (1, 2, 6, 7), ()) + pilot_symbols = ( + [], [], [cnst.map_to_points_v(x)[0] for x in (1, 0, 3, 0)], [] + ) + equalizer = digital.ofdm_equalizer_static(fft_len, occupied_carriers, pilot_carriers, pilot_symbols) + channel = [ + 0, 0, 1, 1, 0, 1, 1, 0, + 0, 0, 1, 1, 0, 1, 1, 0, # These coefficients will be rotated slightly... + 0, 0, 1j, 1j, 0, 1j, 1j, 0, # Go crazy here! + 0, 0, 1j, 1j, 0, 1j, 1j, 0 # ...and again here. + ] + for idx in range(fft_len, 2*fft_len): + channel[idx] = channel[idx-fft_len] * numpy.exp(1j * .1 * numpy.pi * (numpy.random.rand()-.5)) + idx2 = idx+2*fft_len + channel[idx2] = channel[idx2] * numpy.exp(1j * 0 * numpy.pi * (numpy.random.rand()-.5)) + src = blocks.vector_source_c(numpy.multiply(tx_signal, channel), False, fft_len) + eq = digital.ofdm_frame_equalizer_vcvc(equalizer.base(), "", False, 4) + sink = blocks.vector_sink_c(fft_len) + self.tb.connect(src, eq, sink) + self.tb.run () + rx_data = [cnst.decision_maker_v((x,)) if x != 0 else -1 for x in sink.data()] + self.assertEqual(tx_data, rx_data) + def test_002_simpledfe (self): fft_len = 8 # 4 5 6 7 0 1 2 3 diff --git a/gr-digital/python/qa_ofdm_serializer_vcc.py b/gr-digital/python/qa_ofdm_serializer_vcc.py index 0ce6f01348..d0f0bf6449 100755 --- a/gr-digital/python/qa_ofdm_serializer_vcc.py +++ b/gr-digital/python/qa_ofdm_serializer_vcc.py @@ -210,6 +210,5 @@ class qa_ofdm_serializer_vcc (gr_unittest.TestCase): if __name__ == '__main__': - #gr_unittest.run(qa_ofdm_serializer_vcc, "qa_ofdm_serializer_vcc.xml") - gr_unittest.run(qa_ofdm_serializer_vcc) + gr_unittest.run(qa_ofdm_serializer_vcc, "qa_ofdm_serializer_vcc.xml") diff --git a/gr-digital/python/qa_ofdm_sync_sc_cfb.py b/gr-digital/python/qa_ofdm_sync_sc_cfb.py index 8374595d62..06c5a9dc35 100755 --- a/gr-digital/python/qa_ofdm_sync_sc_cfb.py +++ b/gr-digital/python/qa_ofdm_sync_sc_cfb.py @@ -196,6 +196,5 @@ Detection error was: %d """ % (numpy.sum(sink_detect.data()) - n_bursts) if __name__ == '__main__': - #gr_unittest.run(qa_ofdm_sync_sc_cfb, "qa_ofdm_sync_sc_cfb.xml") - gr_unittest.run(qa_ofdm_sync_sc_cfb) + gr_unittest.run(qa_ofdm_sync_sc_cfb, "qa_ofdm_sync_sc_cfb.xml") diff --git a/gr-digital/python/qa_packet_headergenerator_bb.py b/gr-digital/python/qa_packet_headergenerator_bb.py index bb0cfef9f4..03d3af3010 100755 --- a/gr-digital/python/qa_packet_headergenerator_bb.py +++ b/gr-digital/python/qa_packet_headergenerator_bb.py @@ -33,8 +33,8 @@ class qa_packet_headergenerator_bb (gr_unittest.TestCase): self.tb = None def test_001_12bits (self): - # 3 PDUs: | | | | - data = (1, 2, 3, 4, 1, 2, 1, 2, 3, 4) + # 3 PDUs: | | | + data = (1, 2, 3, 4, 1, 2) + tuple(range(25)) tagname = "packet_len" tag1 = gr.gr_tag_t() tag1.offset = 0 @@ -47,7 +47,7 @@ class qa_packet_headergenerator_bb (gr_unittest.TestCase): tag3 = gr.gr_tag_t() tag3.offset = 6 tag3.key = pmt.string_to_symbol(tagname) - tag3.value = pmt.from_long(4) + tag3.value = pmt.from_long(25) src = blocks.vector_source_b(data, False, 1, (tag1, tag2, tag3)) header = digital.packet_headergenerator_bb(12, tagname) sink = blocks.vector_sink_b() @@ -56,7 +56,7 @@ class qa_packet_headergenerator_bb (gr_unittest.TestCase): expected_data = ( 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0 + 1, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0 ) self.assertEqual(sink.data(), expected_data) diff --git a/gr-digital/python/qa_packet_headerparser_b.py b/gr-digital/python/qa_packet_headerparser_b.py index 3c8cd67335..ff74da5657 100755 --- a/gr-digital/python/qa_packet_headerparser_b.py +++ b/gr-digital/python/qa_packet_headerparser_b.py @@ -20,10 +20,12 @@ # import time +import random from gnuradio import gr, gr_unittest import pmt import blocks_swig as blocks import digital_swig as digital +from utils import tagged_streams class qa_packet_headerparser_b (gr_unittest.TestCase): @@ -34,38 +36,96 @@ class qa_packet_headerparser_b (gr_unittest.TestCase): self.tb = None def test_001_t (self): - expected_data = ( - # | Number of symbols | Packet number | Parity + """ + First header: Packet length 4, packet num 0 + Second header: Packet 2, packet num 1 + Third header: Invalid (parity bit does not check) (would be len 4, num 2) + """ + encoded_headers = ( + # | Number of bytes | Packet number | Parity 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0 ) - tagname = "packet_len" + packet_len_tagname = "packet_len" - src = blocks.vector_source_b(expected_data) - parser = digital.packet_headerparser_b(32, tagname) + src = blocks.vector_source_b(encoded_headers) + parser = digital.packet_headerparser_b(32, packet_len_tagname) sink = blocks.message_debug() - self.tb.connect(src, parser) self.tb.msg_connect(parser, "header_data", sink, "store") - self.tb.start () + self.tb.start() time.sleep(1) self.tb.stop() self.tb.wait() - self.assertEqual(sink.num_messages(), 3) - msg = sink.get_message(0) - #try: - #self.assertEqual(4, pmt.pmt_to_long(pmt.pmt_dict_ref(msg, pmt.pmt_string_to_symbol(tagname), pmt.PMT_F))) - #self.assertEqual(0, pmt.pmt_to_long(pmt.pmt_dict_ref(msg, pmt.pmt_string_to_symbol("packet_num"), pmt.PMT_F))) - - #except: - #self.fail() - # msg1: length 4, number 0 - # msg2: length 2, number 1 - # msg3: PMT_F because parity fail + msg1 = pmt.to_python(sink.get_message(0)) + msg2 = pmt.to_python(sink.get_message(1)) + msg3 = pmt.to_python(sink.get_message(2)) + self.assertEqual(msg1, {'packet_len': 4, 'packet_num': 0}) + self.assertEqual(msg2, {'packet_len': 2, 'packet_num': 1}) + self.assertEqual(msg3, False) + def test_002_pipe(self): + """ + Create N packets of random length, pipe them through header generator, + back to header parser, make sure output is the same. + """ + N = 20 + header_len = 32 + packet_len_tagname = "packet_len" + packet_lengths = [random.randint(1, 100) for x in range(N)] + data, tags = tagged_streams.packets_to_vectors([range(packet_lengths[i]) for i in range(N)], packet_len_tagname) + src = blocks.vector_source_b(data, False, 1, tags) + header_gen = digital.packet_headergenerator_bb(header_len, packet_len_tagname) + header_parser = digital.packet_headerparser_b(header_len, packet_len_tagname) + sink = blocks.message_debug() + self.tb.connect(src, header_gen, header_parser) + self.tb.msg_connect(header_parser, "header_data", sink, "store") + self.tb.start() + time.sleep(1) + self.tb.stop() + self.tb.wait() + self.assertEqual(sink.num_messages(), N) + for i in xrange(N): + msg = pmt.to_python(sink.get_message(i)) + self.assertEqual(msg, {'packet_len': packet_lengths[i], 'packet_num': i}) + def test_003_ofdm (self): + """ Header 1: 193 bytes + Header 2: 8 bytes + 2 bits per complex symbol, 32 carriers => 64 bits = 8 bytes per OFDM symbol + """ + encoded_headers = ( + # | Number of bytes | Packet number | Parity + 1, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, + 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + ) + packet_len_tagname = "packet_len" + frame_len_tagname = "frame_len" + src = blocks.vector_source_b(encoded_headers) + header_formatter = digital.packet_header_ofdm( + (range(32),), # 32 carriers are occupied (which doesn't matter here) + 1, # 1 OFDM symbol per header (= 32 bits) + packet_len_tagname, + frame_len_tagname, + "packet_num", + 1, # 1 bit per header symbols (BPSK) + 2 # 2 bits per payload symbol (QPSK) + ) + parser = digital.packet_headerparser_b(header_formatter.base()) + sink = blocks.message_debug() + self.tb.connect(src, parser) + self.tb.msg_connect(parser, "header_data", sink, "store") + self.tb.start() + time.sleep(1) + self.tb.stop() + self.tb.wait() + self.assertEqual(sink.num_messages(), 2) + msg1 = pmt.to_python(sink.get_message(0)) + msg2 = pmt.to_python(sink.get_message(1)) + self.assertEqual(msg1, {'packet_len': 193, 'frame_len': 25, 'packet_num': 0}) + self.assertEqual(msg2, {'packet_len': 8, 'frame_len': 1, 'packet_num': 1}) if __name__ == '__main__': gr_unittest.run(qa_packet_headerparser_b, "qa_packet_headerparser_b.xml") |