1 /* -*- c++ -*- */
2 /*
3  * Copyright 2015 Free Software Foundation, Inc.
4  *
5  * This file is part of GNU Radio
6  *
7  * GNU Radio is free software; you can redistribute it and/or modify
8  * it under the terms of the GNU General Public License as published by
9  * the Free Software Foundation; either version 3, or (at your option)
10  * any later version.
11  *
12  * GNU Radio is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15  * GNU General Public License for more details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with GNU Radio; see the file COPYING.  If not, write to
19  * the Free Software Foundation, Inc., 51 Franklin Street,
20  * Boston, MA 02110-1301, USA.
21  */
22 
23 #ifdef HAVE_CONFIG_H
24 #include "config.h"
25 #endif
26 
27 #include "scl_list.h"
28 #include <gnuradio/fec/polar_decoder_sc_list.h>
29 #include <gnuradio/io_signature.h>
30 #include <volk/volk.h>
31 
32 #include <algorithm>
33 #include <cmath>
34 
35 namespace gr {
36 namespace fec {
37 namespace code {
38 
make(int max_list_size,int block_size,int num_info_bits,std::vector<int> frozen_bit_positions,std::vector<char> frozen_bit_values)39 generic_decoder::sptr polar_decoder_sc_list::make(int max_list_size,
40                                                   int block_size,
41                                                   int num_info_bits,
42                                                   std::vector<int> frozen_bit_positions,
43                                                   std::vector<char> frozen_bit_values)
44 {
45     return generic_decoder::sptr(new polar_decoder_sc_list(max_list_size,
46                                                            block_size,
47                                                            num_info_bits,
48                                                            frozen_bit_positions,
49                                                            frozen_bit_values));
50 }
51 
polar_decoder_sc_list(int max_list_size,int block_size,int num_info_bits,std::vector<int> frozen_bit_positions,std::vector<char> frozen_bit_values)52 polar_decoder_sc_list::polar_decoder_sc_list(int max_list_size,
53                                              int block_size,
54                                              int num_info_bits,
55                                              std::vector<int> frozen_bit_positions,
56                                              std::vector<char> frozen_bit_values)
57     : polar_decoder_common(
58           block_size, num_info_bits, frozen_bit_positions, frozen_bit_values)
59 {
60     d_scl = new polar::scl_list(max_list_size, block_size, block_power());
61 }
62 
~polar_decoder_sc_list()63 polar_decoder_sc_list::~polar_decoder_sc_list() { delete d_scl; }
64 
generic_work(void * in_buffer,void * out_buffer)65 void polar_decoder_sc_list::generic_work(void* in_buffer, void* out_buffer)
66 {
67     const float* in = (const float*)in_buffer;
68     unsigned char* out = (unsigned char*)out_buffer;
69 
70     initialize_list(in);
71     const unsigned char* temp = decode_list();
72     extract_info_bits(out, temp);
73 }
74 
initialize_list(const float * in_buf)75 void polar_decoder_sc_list::initialize_list(const float* in_buf)
76 {
77     polar::path* init_path = d_scl->initial_path();
78     initialize_decoder(init_path->u_vec, init_path->llr_vec, in_buf);
79 }
80 
decode_list()81 const unsigned char* polar_decoder_sc_list::decode_list()
82 {
83     for (int u_num = 0; u_num < block_size(); u_num++) {
84         decode_bit(u_num);
85     }
86     return d_scl->optimal_path()->u_vec;
87 }
88 
decode_bit(const int u_num)89 void polar_decoder_sc_list::decode_bit(const int u_num)
90 {
91     calculate_llrs_for_list(u_num);
92     set_bit_in_list(u_num);
93 }
94 
calculate_llrs_for_list(const int u_num)95 void polar_decoder_sc_list::calculate_llrs_for_list(const int u_num)
96 {
97     for (unsigned int i = 0; i < d_scl->active_size(); i++) {
98         polar::path* current_path = d_scl->next_active_path();
99         butterfly(current_path->llr_vec, current_path->u_vec, 0, u_num, u_num);
100     }
101 }
102 
set_bit_in_list(const int u_num)103 void polar_decoder_sc_list::set_bit_in_list(const int u_num)
104 {
105     // 1. if frozen bit, update with known value
106     if (is_frozen_bit(u_num)) {
107         const unsigned char frozen_bit = next_frozen_bit();
108         d_scl->set_frozen_bit(frozen_bit, u_num);
109     }
110     // 2. info bit
111     else {
112         d_scl->set_info_bit(u_num);
113     }
114 }
115 
116 } /* namespace code */
117 } /* namespace fec */
118 } /* namespace gr */
119