1 /* -*- c++ -*- */
2 /*
3  * Copyright 2015-2017,2019 Free Software Foundation, Inc.
4  *
5  * This is free software; you can redistribute it and/or modify
6  * it under the terms of the GNU General Public License as published by
7  * the Free Software Foundation; either version 3, or (at your option)
8  * any later version.
9  *
10  * This software is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13  * GNU General Public License for more details.
14  *
15  * You should have received a copy of the GNU General Public License
16  * along with this software; see the file COPYING.  If not, write to
17  * the Free Software Foundation, Inc., 51 Franklin Street,
18  * Boston, MA 02110-1301, USA.
19  */
20 
21 #ifdef HAVE_CONFIG_H
22 #include "config.h"
23 #endif
24 
25 #include "dvbt2_framemapper_cc_impl.h"
26 #include <gnuradio/io_signature.h>
27 #include <algorithm>
28 
29 namespace gr {
30 namespace dtv {
31 
32 dvbt2_framemapper_cc::sptr
make(dvb_framesize_t framesize,dvb_code_rate_t rate,dvb_constellation_t constellation,dvbt2_rotation_t rotation,int fecblocks,int tiblocks,dvbt2_extended_carrier_t carriermode,dvbt2_fftsize_t fftsize,dvb_guardinterval_t guardinterval,dvbt2_l1constellation_t l1constellation,dvbt2_pilotpattern_t pilotpattern,int t2frames,int numdatasyms,dvbt2_papr_t paprmode,dvbt2_version_t version,dvbt2_preamble_t preamble,dvbt2_inputmode_t inputmode,dvbt2_reservedbiasbits_t reservedbiasbits,dvbt2_l1scrambled_t l1scrambled,dvbt2_inband_t inband)33 dvbt2_framemapper_cc::make(dvb_framesize_t framesize,
34                            dvb_code_rate_t rate,
35                            dvb_constellation_t constellation,
36                            dvbt2_rotation_t rotation,
37                            int fecblocks,
38                            int tiblocks,
39                            dvbt2_extended_carrier_t carriermode,
40                            dvbt2_fftsize_t fftsize,
41                            dvb_guardinterval_t guardinterval,
42                            dvbt2_l1constellation_t l1constellation,
43                            dvbt2_pilotpattern_t pilotpattern,
44                            int t2frames,
45                            int numdatasyms,
46                            dvbt2_papr_t paprmode,
47                            dvbt2_version_t version,
48                            dvbt2_preamble_t preamble,
49                            dvbt2_inputmode_t inputmode,
50                            dvbt2_reservedbiasbits_t reservedbiasbits,
51                            dvbt2_l1scrambled_t l1scrambled,
52                            dvbt2_inband_t inband)
53 {
54     return gnuradio::get_initial_sptr(new dvbt2_framemapper_cc_impl(framesize,
55                                                                     rate,
56                                                                     constellation,
57                                                                     rotation,
58                                                                     fecblocks,
59                                                                     tiblocks,
60                                                                     carriermode,
61                                                                     fftsize,
62                                                                     guardinterval,
63                                                                     l1constellation,
64                                                                     pilotpattern,
65                                                                     t2frames,
66                                                                     numdatasyms,
67                                                                     paprmode,
68                                                                     version,
69                                                                     preamble,
70                                                                     inputmode,
71                                                                     reservedbiasbits,
72                                                                     l1scrambled,
73                                                                     inband));
74 }
75 
76 /*
77  * The private constructor
78  */
dvbt2_framemapper_cc_impl(dvb_framesize_t framesize,dvb_code_rate_t rate,dvb_constellation_t constellation,dvbt2_rotation_t rotation,int fecblocks,int tiblocks,dvbt2_extended_carrier_t carriermode,dvbt2_fftsize_t fftsize,dvb_guardinterval_t guardinterval,dvbt2_l1constellation_t l1constellation,dvbt2_pilotpattern_t pilotpattern,int t2frames,int numdatasyms,dvbt2_papr_t paprmode,dvbt2_version_t version,dvbt2_preamble_t preamble,dvbt2_inputmode_t inputmode,dvbt2_reservedbiasbits_t reservedbiasbits,dvbt2_l1scrambled_t l1scrambled,dvbt2_inband_t inband)79 dvbt2_framemapper_cc_impl::dvbt2_framemapper_cc_impl(
80     dvb_framesize_t framesize,
81     dvb_code_rate_t rate,
82     dvb_constellation_t constellation,
83     dvbt2_rotation_t rotation,
84     int fecblocks,
85     int tiblocks,
86     dvbt2_extended_carrier_t carriermode,
87     dvbt2_fftsize_t fftsize,
88     dvb_guardinterval_t guardinterval,
89     dvbt2_l1constellation_t l1constellation,
90     dvbt2_pilotpattern_t pilotpattern,
91     int t2frames,
92     int numdatasyms,
93     dvbt2_papr_t paprmode,
94     dvbt2_version_t version,
95     dvbt2_preamble_t preamble,
96     dvbt2_inputmode_t inputmode,
97     dvbt2_reservedbiasbits_t reservedbiasbits,
98     dvbt2_l1scrambled_t l1scrambled,
99     dvbt2_inband_t inband)
100     : gr::block("dvbt2_framemapper_cc",
101                 gr::io_signature::make(1, 1, sizeof(gr_complex)),
102                 gr::io_signature::make(1, 1, sizeof(gr_complex)))
103 {
104     L1Pre* l1preinit = &L1_Signalling[0].l1pre_data;
105     L1Post* l1postinit = &L1_Signalling[0].l1post_data;
106     double normalization;
107     double m_16qam_lookup[4] = { 3.0, 1.0, -3.0, -1.0 };
108     double m_64qam_lookup[8] = { 7.0, 5.0, 1.0, 3.0, -7.0, -5.0, -1.0, -3.0 };
109     int real_index, imag_index;
110     int N_punc_temp, N_post_temp;
111     if (framesize == FECFRAME_NORMAL) {
112         switch (constellation) {
113         case MOD_QPSK:
114             cell_size = 32400;
115             break;
116         case MOD_16QAM:
117             cell_size = 16200;
118             break;
119         case MOD_64QAM:
120             cell_size = 10800;
121             break;
122         case MOD_256QAM:
123             cell_size = 8100;
124             break;
125         default:
126             cell_size = 0;
127             break;
128         }
129     } else {
130         switch (constellation) {
131         case MOD_QPSK:
132             cell_size = 8100;
133             break;
134         case MOD_16QAM:
135             cell_size = 4050;
136             break;
137         case MOD_64QAM:
138             cell_size = 2700;
139             break;
140         case MOD_256QAM:
141             cell_size = 2025;
142             break;
143         default:
144             cell_size = 0;
145             break;
146         }
147     }
148     l1preinit->type = STREAMTYPE_TS;
149     l1preinit->bwt_ext = carriermode;
150     fft_size = fftsize;
151     l1preinit->s1 = preamble;
152     l1preinit->s2 = fft_size & 0x7;
153     l1preinit->l1_repetition_flag = FALSE;
154     l1preinit->guard_interval = guardinterval;
155     l1preinit->papr = paprmode;
156     l1preinit->l1_mod = l1constellation;
157     l1preinit->l1_cod = 0;
158     l1preinit->l1_fec_type = 0;
159     l1preinit->l1_post_info_size = KSIG_POST - 32;
160     l1preinit->pilot_pattern = pilotpattern;
161     l1preinit->tx_id_availability = 0;
162     l1preinit->cell_id = 0;
163     l1preinit->network_id = 0x3085;
164     l1preinit->t2_system_id = 0x8001;
165     l1preinit->num_t2_frames = t2frames;
166     l1preinit->num_data_symbols = numdatasyms;
167     l1preinit->regen_flag = FALSE;
168     l1preinit->l1_post_extension = FALSE;
169     l1preinit->num_rf = 1;
170     l1preinit->current_rf_index = 0;
171     l1preinit->t2_version = version;
172     if (version == VERSION_131) {
173         l1preinit->l1_post_scrambled = l1scrambled;
174     } else {
175         l1preinit->l1_post_scrambled = FALSE;
176     }
177     l1preinit->t2_base_lite = FALSE;
178     if (reservedbiasbits == RESERVED_ON && version == VERSION_131) {
179         l1preinit->reserved = 0xf;
180     } else {
181         l1preinit->reserved = 0x0;
182     }
183 
184     l1postinit->sub_slices_per_frame = 1;
185     l1postinit->num_plp = 1;
186     l1postinit->num_aux = 0;
187     l1postinit->aux_config_rfu = 0;
188     l1postinit->rf_idx = 0;
189     l1postinit->frequency = 729833333;
190     l1postinit->plp_id = 0;
191     l1postinit->plp_type = 1;
192     l1postinit->plp_payload_type = 3;
193     l1postinit->ff_flag = 0;
194     l1postinit->first_rf_idx = 0;
195     l1postinit->first_frame_idx = 0;
196     l1postinit->plp_group_id = 1;
197     switch (rate) {
198     case C1_3:
199         l1postinit->plp_cod = 6;
200         break;
201     case C2_5:
202         l1postinit->plp_cod = 7;
203         break;
204     case C1_2:
205         l1postinit->plp_cod = 0;
206         break;
207     case C3_5:
208         l1postinit->plp_cod = 1;
209         break;
210     case C2_3:
211         l1postinit->plp_cod = 2;
212         break;
213     case C3_4:
214         l1postinit->plp_cod = 3;
215         break;
216     case C4_5:
217         l1postinit->plp_cod = 4;
218         break;
219     case C5_6:
220         l1postinit->plp_cod = 5;
221         break;
222     default:
223         l1postinit->plp_cod = 0;
224         break;
225     }
226     l1postinit->plp_mod = constellation;
227     l1postinit->plp_rotation = rotation;
228     l1postinit->plp_fec_type = framesize;
229     l1postinit->plp_num_blocks_max = fecblocks;
230     l1postinit->frame_interval = 1;
231     l1postinit->time_il_length = tiblocks;
232     l1postinit->time_il_type = 0;
233     l1postinit->in_band_a_flag = 0;
234     if (inband == INBAND_ON && version == VERSION_131) {
235         l1postinit->in_band_b_flag = 1;
236     } else {
237         l1postinit->in_band_b_flag = 0;
238     }
239     if (reservedbiasbits == RESERVED_ON && version == VERSION_131) {
240         l1postinit->reserved_1 = 0x7ff;
241     } else {
242         l1postinit->reserved_1 = 0x0;
243     }
244     if (version == VERSION_111) {
245         l1postinit->plp_mode = 0;
246     } else {
247         l1postinit->plp_mode = inputmode + 1;
248     }
249     l1postinit->static_flag = 0;
250     l1postinit->static_padding_flag = 0;
251     l1postinit->fef_length_msb = 0;
252     if (reservedbiasbits == RESERVED_ON && version == VERSION_131) {
253         l1postinit->reserved_2 = 0x3fffffff;
254     } else {
255         l1postinit->reserved_2 = 0;
256     }
257     l1postinit->frame_idx = 0;
258     l1postinit->sub_slice_interval = 0;
259     l1postinit->type_2_start = 0;
260     l1postinit->l1_change_counter = 0;
261     l1postinit->start_rf_idx = 0;
262     if (reservedbiasbits == RESERVED_ON && version == VERSION_131) {
263         l1postinit->reserved_3 = 0xff;
264     } else {
265         l1postinit->reserved_3 = 0;
266     }
267     l1postinit->plp_id = 0;
268     l1postinit->plp_start = 0;
269     l1postinit->plp_num_blocks = fecblocks;
270     if (reservedbiasbits == RESERVED_ON && version == VERSION_131) {
271         l1postinit->reserved_4 = 0xff;
272         l1postinit->reserved_5 = 0xff;
273     } else {
274         l1postinit->reserved_4 = 0;
275         l1postinit->reserved_5 = 0;
276     }
277 
278     bch_poly_build_tables();
279     l1pre_ldpc_lookup_generate();
280     m_bpsk[0] = gr_complex(1.0, 0.0);
281     m_bpsk[1] = gr_complex(-1.0, 0.0);
282     unmodulated = gr_complex(0.0, 0.0);
283 
284     l1post_ldpc_lookup_generate();
285     switch (l1constellation) {
286     case L1_MOD_BPSK:
287         eta_mod = 1;
288         break;
289     case L1_MOD_QPSK:
290         normalization = sqrt(2);
291         m_qpsk[0] = gr_complex(1.0 / normalization, 1.0 / normalization);
292         m_qpsk[1] = gr_complex(1.0 / normalization, -1.0 / normalization);
293         m_qpsk[2] = gr_complex(-1.0 / normalization, 1.0 / normalization);
294         m_qpsk[3] = gr_complex(-1.0 / normalization, -1.0 / normalization);
295         eta_mod = 2;
296         break;
297     case L1_MOD_16QAM:
298         normalization = sqrt(10);
299         for (int i = 0; i < 16; i++) {
300             real_index = ((i & 0x8) >> 2) | ((i & 0x2) >> 1);
301             imag_index = ((i & 0x4) >> 1) | ((i & 0x1) >> 0);
302             m_16qam[i] = gr_complex(m_16qam_lookup[real_index] / normalization,
303                                     m_16qam_lookup[imag_index] / normalization);
304         }
305         eta_mod = 4;
306         break;
307     case L1_MOD_64QAM:
308         normalization = sqrt(42);
309         for (int i = 0; i < 64; i++) {
310             real_index = ((i & 0x20) >> 3) | ((i & 0x8) >> 2) | ((i & 0x2) >> 1);
311             imag_index = ((i & 0x10) >> 2) | ((i & 0x4) >> 1) | ((i & 0x1) >> 0);
312             m_64qam[i] = gr_complex(m_64qam_lookup[real_index] / normalization,
313                                     m_64qam_lookup[imag_index] / normalization);
314         }
315         eta_mod = 6;
316         break;
317     }
318     N_P2 = 1;
319     C_P2 = 0;
320     N_FC = 0;
321     C_FC = 0;
322     C_DATA = 0;
323     if ((preamble == PREAMBLE_T2_SISO) || (preamble == PREAMBLE_T2_LITE_SISO)) {
324         switch (fft_size) {
325         case FFTSIZE_1K:
326             N_P2 = 16;
327             C_P2 = 558;
328             break;
329         case FFTSIZE_2K:
330             N_P2 = 8;
331             C_P2 = 1118;
332             break;
333         case FFTSIZE_4K:
334             N_P2 = 4;
335             C_P2 = 2236;
336             break;
337         case FFTSIZE_8K:
338         case FFTSIZE_8K_T2GI:
339             N_P2 = 2;
340             C_P2 = 4472;
341             break;
342         case FFTSIZE_16K:
343         case FFTSIZE_16K_T2GI:
344             N_P2 = 1;
345             C_P2 = 8944;
346             break;
347         case FFTSIZE_32K:
348         case FFTSIZE_32K_T2GI:
349             N_P2 = 1;
350             C_P2 = 22432;
351             break;
352         }
353     } else {
354         switch (fft_size) {
355         case FFTSIZE_1K:
356             N_P2 = 16;
357             C_P2 = 546;
358             break;
359         case FFTSIZE_2K:
360             N_P2 = 8;
361             C_P2 = 1098;
362             break;
363         case FFTSIZE_4K:
364             N_P2 = 4;
365             C_P2 = 2198;
366             break;
367         case FFTSIZE_8K:
368         case FFTSIZE_8K_T2GI:
369             N_P2 = 2;
370             C_P2 = 4398;
371             break;
372         case FFTSIZE_16K:
373         case FFTSIZE_16K_T2GI:
374             N_P2 = 1;
375             C_P2 = 8814;
376             break;
377         case FFTSIZE_32K:
378         case FFTSIZE_32K_T2GI:
379             N_P2 = 1;
380             C_P2 = 17612;
381             break;
382         }
383     }
384     switch (fft_size) {
385     case FFTSIZE_1K:
386         switch (pilotpattern) {
387         case PILOT_PP1:
388             C_DATA = 764;
389             N_FC = 568;
390             C_FC = 402;
391             break;
392         case PILOT_PP2:
393             C_DATA = 768;
394             N_FC = 710;
395             C_FC = 654;
396             break;
397         case PILOT_PP3:
398             C_DATA = 798;
399             N_FC = 710;
400             C_FC = 490;
401             break;
402         case PILOT_PP4:
403             C_DATA = 804;
404             N_FC = 780;
405             C_FC = 707;
406             break;
407         case PILOT_PP5:
408             C_DATA = 818;
409             N_FC = 780;
410             C_FC = 544;
411             break;
412         case PILOT_PP6:
413             C_DATA = 0;
414             N_FC = 0;
415             C_FC = 0;
416             break;
417         case PILOT_PP7:
418             C_DATA = 0;
419             N_FC = 0;
420             C_FC = 0;
421             break;
422         case PILOT_PP8:
423             C_DATA = 0;
424             N_FC = 0;
425             C_FC = 0;
426             break;
427         }
428         if (paprmode == PAPR_TR || paprmode == PAPR_BOTH) {
429             if (C_DATA != 0) {
430                 C_DATA -= 10;
431             }
432             if (N_FC != 0) {
433                 N_FC -= 10;
434             }
435             if (C_FC != 0) {
436                 C_FC -= 10;
437             }
438         }
439         break;
440     case FFTSIZE_2K:
441         switch (pilotpattern) {
442         case PILOT_PP1:
443             C_DATA = 1522;
444             N_FC = 1136;
445             C_FC = 804;
446             break;
447         case PILOT_PP2:
448             C_DATA = 1532;
449             N_FC = 1420;
450             C_FC = 1309;
451             break;
452         case PILOT_PP3:
453             C_DATA = 1596;
454             N_FC = 1420;
455             C_FC = 980;
456             break;
457         case PILOT_PP4:
458             C_DATA = 1602;
459             N_FC = 1562;
460             C_FC = 1415;
461             break;
462         case PILOT_PP5:
463             C_DATA = 1632;
464             N_FC = 1562;
465             C_FC = 1088;
466             break;
467         case PILOT_PP6:
468             C_DATA = 0;
469             N_FC = 0;
470             C_FC = 0;
471             break;
472         case PILOT_PP7:
473             C_DATA = 1646;
474             N_FC = 1632;
475             C_FC = 1396;
476             break;
477         case PILOT_PP8:
478             C_DATA = 0;
479             N_FC = 0;
480             C_FC = 0;
481             break;
482         }
483         if (paprmode == PAPR_TR || paprmode == PAPR_BOTH) {
484             if (C_DATA != 0) {
485                 C_DATA -= 18;
486             }
487             if (N_FC != 0) {
488                 N_FC -= 18;
489             }
490             if (C_FC != 0) {
491                 C_FC -= 18;
492             }
493         }
494         break;
495     case FFTSIZE_4K:
496         switch (pilotpattern) {
497         case PILOT_PP1:
498             C_DATA = 3084;
499             N_FC = 2272;
500             C_FC = 1609;
501             break;
502         case PILOT_PP2:
503             C_DATA = 3092;
504             N_FC = 2840;
505             C_FC = 2619;
506             break;
507         case PILOT_PP3:
508             C_DATA = 3228;
509             N_FC = 2840;
510             C_FC = 1961;
511             break;
512         case PILOT_PP4:
513             C_DATA = 3234;
514             N_FC = 3124;
515             C_FC = 2831;
516             break;
517         case PILOT_PP5:
518             C_DATA = 3298;
519             N_FC = 3124;
520             C_FC = 2177;
521             break;
522         case PILOT_PP6:
523             C_DATA = 0;
524             N_FC = 0;
525             C_FC = 0;
526             break;
527         case PILOT_PP7:
528             C_DATA = 3328;
529             N_FC = 3266;
530             C_FC = 2792;
531             break;
532         case PILOT_PP8:
533             C_DATA = 0;
534             N_FC = 0;
535             C_FC = 0;
536             break;
537         }
538         if (paprmode == PAPR_TR || paprmode == PAPR_BOTH) {
539             if (C_DATA != 0) {
540                 C_DATA -= 36;
541             }
542             if (N_FC != 0) {
543                 N_FC -= 36;
544             }
545             if (C_FC != 0) {
546                 C_FC -= 36;
547             }
548         }
549         break;
550     case FFTSIZE_8K:
551     case FFTSIZE_8K_T2GI:
552         if (carriermode == CARRIERS_NORMAL) {
553             switch (pilotpattern) {
554             case PILOT_PP1:
555                 C_DATA = 6208;
556                 N_FC = 4544;
557                 C_FC = 3218;
558                 break;
559             case PILOT_PP2:
560                 C_DATA = 6214;
561                 N_FC = 5680;
562                 C_FC = 5238;
563                 break;
564             case PILOT_PP3:
565                 C_DATA = 6494;
566                 N_FC = 5680;
567                 C_FC = 3922;
568                 break;
569             case PILOT_PP4:
570                 C_DATA = 6498;
571                 N_FC = 6248;
572                 C_FC = 5662;
573                 break;
574             case PILOT_PP5:
575                 C_DATA = 6634;
576                 N_FC = 6248;
577                 C_FC = 4354;
578                 break;
579             case PILOT_PP6:
580                 C_DATA = 0;
581                 N_FC = 0;
582                 C_FC = 0;
583                 break;
584             case PILOT_PP7:
585                 C_DATA = 6698;
586                 N_FC = 6532;
587                 C_FC = 5585;
588                 break;
589             case PILOT_PP8:
590                 C_DATA = 6698;
591                 N_FC = 0;
592                 C_FC = 0;
593                 break;
594             }
595         } else {
596             switch (pilotpattern) {
597             case PILOT_PP1:
598                 C_DATA = 6296;
599                 N_FC = 4608;
600                 C_FC = 3264;
601                 break;
602             case PILOT_PP2:
603                 C_DATA = 6298;
604                 N_FC = 5760;
605                 C_FC = 5312;
606                 break;
607             case PILOT_PP3:
608                 C_DATA = 6584;
609                 N_FC = 5760;
610                 C_FC = 3978;
611                 break;
612             case PILOT_PP4:
613                 C_DATA = 6588;
614                 N_FC = 6336;
615                 C_FC = 5742;
616                 break;
617             case PILOT_PP5:
618                 C_DATA = 6728;
619                 N_FC = 6336;
620                 C_FC = 4416;
621                 break;
622             case PILOT_PP6:
623                 C_DATA = 0;
624                 N_FC = 0;
625                 C_FC = 0;
626                 break;
627             case PILOT_PP7:
628                 C_DATA = 6788;
629                 N_FC = 6624;
630                 C_FC = 5664;
631                 break;
632             case PILOT_PP8:
633                 C_DATA = 6788;
634                 N_FC = 0;
635                 C_FC = 0;
636                 break;
637             }
638         }
639         if (paprmode == PAPR_TR || paprmode == PAPR_BOTH) {
640             if (C_DATA != 0) {
641                 C_DATA -= 72;
642             }
643             if (N_FC != 0) {
644                 N_FC -= 72;
645             }
646             if (C_FC != 0) {
647                 C_FC -= 72;
648             }
649         }
650         break;
651     case FFTSIZE_16K:
652     case FFTSIZE_16K_T2GI:
653         if (carriermode == CARRIERS_NORMAL) {
654             switch (pilotpattern) {
655             case PILOT_PP1:
656                 C_DATA = 12418;
657                 N_FC = 9088;
658                 C_FC = 6437;
659                 break;
660             case PILOT_PP2:
661                 C_DATA = 12436;
662                 N_FC = 11360;
663                 C_FC = 10476;
664                 break;
665             case PILOT_PP3:
666                 C_DATA = 12988;
667                 N_FC = 11360;
668                 C_FC = 7845;
669                 break;
670             case PILOT_PP4:
671                 C_DATA = 13002;
672                 N_FC = 12496;
673                 C_FC = 11324;
674                 break;
675             case PILOT_PP5:
676                 C_DATA = 13272;
677                 N_FC = 12496;
678                 C_FC = 8709;
679                 break;
680             case PILOT_PP6:
681                 C_DATA = 13288;
682                 N_FC = 13064;
683                 C_FC = 11801;
684                 break;
685             case PILOT_PP7:
686                 C_DATA = 13416;
687                 N_FC = 13064;
688                 C_FC = 11170;
689                 break;
690             case PILOT_PP8:
691                 C_DATA = 13406;
692                 N_FC = 0;
693                 C_FC = 0;
694                 break;
695             }
696         } else {
697             switch (pilotpattern) {
698             case PILOT_PP1:
699                 C_DATA = 12678;
700                 N_FC = 9280;
701                 C_FC = 6573;
702                 break;
703             case PILOT_PP2:
704                 C_DATA = 12698;
705                 N_FC = 11600;
706                 C_FC = 10697;
707                 break;
708             case PILOT_PP3:
709                 C_DATA = 13262;
710                 N_FC = 11600;
711                 C_FC = 8011;
712                 break;
713             case PILOT_PP4:
714                 C_DATA = 13276;
715                 N_FC = 12760;
716                 C_FC = 11563;
717                 break;
718             case PILOT_PP5:
719                 C_DATA = 13552;
720                 N_FC = 12760;
721                 C_FC = 8893;
722                 break;
723             case PILOT_PP6:
724                 C_DATA = 13568;
725                 N_FC = 13340;
726                 C_FC = 12051;
727                 break;
728             case PILOT_PP7:
729                 C_DATA = 13698;
730                 N_FC = 13340;
731                 C_FC = 11406;
732                 break;
733             case PILOT_PP8:
734                 C_DATA = 13688;
735                 N_FC = 0;
736                 C_FC = 0;
737                 break;
738             }
739         }
740         if (paprmode == PAPR_TR || paprmode == PAPR_BOTH) {
741             if (C_DATA != 0) {
742                 C_DATA -= 144;
743             }
744             if (N_FC != 0) {
745                 N_FC -= 144;
746             }
747             if (C_FC != 0) {
748                 C_FC -= 144;
749             }
750         }
751         break;
752     case FFTSIZE_32K:
753     case FFTSIZE_32K_T2GI:
754         if (carriermode == CARRIERS_NORMAL) {
755             switch (pilotpattern) {
756             case PILOT_PP1:
757                 C_DATA = 0;
758                 N_FC = 0;
759                 C_FC = 0;
760                 break;
761             case PILOT_PP2:
762                 C_DATA = 24886;
763                 N_FC = 22720;
764                 C_FC = 20952;
765                 break;
766             case PILOT_PP3:
767                 C_DATA = 0;
768                 N_FC = 0;
769                 C_FC = 0;
770                 break;
771             case PILOT_PP4:
772                 C_DATA = 26022;
773                 N_FC = 24992;
774                 C_FC = 22649;
775                 break;
776             case PILOT_PP5:
777                 C_DATA = 0;
778                 N_FC = 0;
779                 C_FC = 0;
780                 break;
781             case PILOT_PP6:
782                 C_DATA = 26592;
783                 N_FC = 26128;
784                 C_FC = 23603;
785                 break;
786             case PILOT_PP7:
787                 C_DATA = 26836;
788                 N_FC = 0;
789                 C_FC = 0;
790                 break;
791             case PILOT_PP8:
792                 C_DATA = 26812;
793                 N_FC = 0;
794                 C_FC = 0;
795                 break;
796             }
797         } else {
798             switch (pilotpattern) {
799             case PILOT_PP1:
800                 C_DATA = 0;
801                 N_FC = 0;
802                 C_FC = 0;
803                 break;
804             case PILOT_PP2:
805                 C_DATA = 25412;
806                 N_FC = 23200;
807                 C_FC = 21395;
808                 break;
809             case PILOT_PP3:
810                 C_DATA = 0;
811                 N_FC = 0;
812                 C_FC = 0;
813                 break;
814             case PILOT_PP4:
815                 C_DATA = 26572;
816                 N_FC = 25520;
817                 C_FC = 23127;
818                 break;
819             case PILOT_PP5:
820                 C_DATA = 0;
821                 N_FC = 0;
822                 C_FC = 0;
823                 break;
824             case PILOT_PP6:
825                 C_DATA = 27152;
826                 N_FC = 26680;
827                 C_FC = 24102;
828                 break;
829             case PILOT_PP7:
830                 C_DATA = 27404;
831                 N_FC = 0;
832                 C_FC = 0;
833                 break;
834             case PILOT_PP8:
835                 C_DATA = 27376;
836                 N_FC = 0;
837                 C_FC = 0;
838                 break;
839             }
840         }
841         if (paprmode == PAPR_TR || paprmode == PAPR_BOTH) {
842             if (C_DATA != 0) {
843                 C_DATA -= 288;
844             }
845             if (N_FC != 0) {
846                 N_FC -= 288;
847             }
848             if (C_FC != 0) {
849                 C_FC -= 288;
850             }
851         }
852         break;
853     }
854     if ((preamble == PREAMBLE_T2_SISO) || (preamble == PREAMBLE_T2_LITE_SISO)) {
855         if (guardinterval == GI_1_128 && pilotpattern == PILOT_PP7) {
856             N_FC = 0;
857             C_FC = 0;
858         }
859         if (guardinterval == GI_1_32 && pilotpattern == PILOT_PP4) {
860             N_FC = 0;
861             C_FC = 0;
862         }
863         if (guardinterval == GI_1_16 && pilotpattern == PILOT_PP2) {
864             N_FC = 0;
865             C_FC = 0;
866         }
867         if (guardinterval == GI_19_256 && pilotpattern == PILOT_PP2) {
868             N_FC = 0;
869             C_FC = 0;
870         }
871     }
872     N_punc_temp = (6 * (KBCH_1_2 - KSIG_POST)) / 5;
873     N_post_temp = KSIG_POST + NBCH_PARITY + 9000 - N_punc_temp;
874     if (N_P2 == 1) {
875         N_post = ceil((float)N_post_temp / (2 * (float)eta_mod)) * 2 * eta_mod;
876     } else {
877         N_post =
878             ceil((float)N_post_temp / ((float)eta_mod * (float)N_P2)) * eta_mod * N_P2;
879     }
880     N_punc = N_punc_temp - (N_post - N_post_temp);
881     l1preinit->l1_post_size = N_post / eta_mod;
882     add_l1pre(&l1pre_cache[0]);
883     l1_constellation = l1constellation;
884     t2_frames = t2frames;
885     t2_frame_num = 0;
886     if (version == VERSION_131) {
887         l1_scrambled = l1scrambled;
888     } else {
889         l1_scrambled = FALSE;
890     }
891     stream_items = cell_size * fecblocks;
892     if (N_FC == 0) {
893         set_output_multiple((N_P2 * C_P2) + (numdatasyms * C_DATA));
894         mapped_items = (N_P2 * C_P2) + (numdatasyms * C_DATA);
895         if (mapped_items < (stream_items + 1840 + (N_post / eta_mod) + (N_FC - C_FC))) {
896             GR_LOG_WARN(d_logger, "Frame Mapper, too many FEC blocks in T2 frame.");
897             mapped_items = stream_items + 1840 + (N_post / eta_mod) +
898                            (N_FC - C_FC); /* avoid segfault */
899         }
900         zigzag_interleave = (gr_complex*)malloc(sizeof(gr_complex) * mapped_items);
901         if (zigzag_interleave == NULL) {
902             GR_LOG_FATAL(d_logger,
903                          "Frame Mapper, cannot allocate memory for zigzag_interleave.");
904             throw std::bad_alloc();
905         }
906     } else {
907         set_output_multiple((N_P2 * C_P2) + ((numdatasyms - 1) * C_DATA) + N_FC);
908         mapped_items = (N_P2 * C_P2) + ((numdatasyms - 1) * C_DATA) + N_FC;
909         if (mapped_items < (stream_items + 1840 + (N_post / eta_mod) + (N_FC - C_FC))) {
910             GR_LOG_WARN(d_logger, "Frame Mapper, too many FEC blocks in T2 frame.");
911             mapped_items = stream_items + 1840 + (N_post / eta_mod) +
912                            (N_FC - C_FC); /* avoid segfault */
913         }
914         zigzag_interleave = (gr_complex*)malloc(sizeof(gr_complex) * mapped_items);
915         if (zigzag_interleave == NULL) {
916             GR_LOG_FATAL(d_logger,
917                          "Frame Mapper, cannot allocate memory for zigzag_interleave.");
918             throw std::bad_alloc();
919         }
920     }
921     dummy_randomize =
922         (gr_complex*)malloc(sizeof(gr_complex) * mapped_items - stream_items - 1840 -
923                             (N_post / eta_mod) - (N_FC - C_FC));
924     if (dummy_randomize == NULL) {
925         free(zigzag_interleave);
926         GR_LOG_FATAL(d_logger,
927                      "Frame Mapper, cannot allocate memory for dummy_randomize.");
928         throw std::bad_alloc();
929     }
930     init_dummy_randomizer();
931     init_l1_randomizer();
932 }
933 
934 /*
935  * Our virtual destructor.
936  */
~dvbt2_framemapper_cc_impl()937 dvbt2_framemapper_cc_impl::~dvbt2_framemapper_cc_impl()
938 {
939     free(dummy_randomize);
940     free(zigzag_interleave);
941 }
942 
forecast(int noutput_items,gr_vector_int & ninput_items_required)943 void dvbt2_framemapper_cc_impl::forecast(int noutput_items,
944                                          gr_vector_int& ninput_items_required)
945 {
946     ninput_items_required[0] = stream_items * (noutput_items / mapped_items);
947 }
948 
949 #define CRC_POLY 0x04C11DB7
950 
add_crc32_bits(unsigned char * in,int length)951 int dvbt2_framemapper_cc_impl::add_crc32_bits(unsigned char* in, int length)
952 {
953     int crc = 0xffffffff;
954     int b;
955     int i = 0;
956 
957     for (int n = 0; n < length; n++) {
958         b = in[i++] ^ ((crc >> 31) & 0x01);
959         crc <<= 1;
960         if (b) {
961             crc ^= CRC_POLY;
962         }
963     }
964 
965     for (int n = 31; n >= 0; n--) {
966         in[i++] = (crc & (1 << n)) ? 1 : 0;
967     }
968     return 32;
969 }
970 
poly_mult(const int * ina,int lena,const int * inb,int lenb,int * out)971 int dvbt2_framemapper_cc_impl::poly_mult(
972     const int* ina, int lena, const int* inb, int lenb, int* out)
973 {
974     memset(out, 0, sizeof(int) * (lena + lenb));
975 
976     for (int i = 0; i < lena; i++) {
977         for (int j = 0; j < lenb; j++) {
978             if (ina[i] * inb[j] > 0) {
979                 out[i + j]++; // count number of terms for this pwr of x
980             }
981         }
982     }
983     int max = 0;
984     for (int i = 0; i < lena + lenb; i++) {
985         out[i] = out[i] & 1; // If even ignore the term
986         if (out[i])
987             max = i;
988     }
989     // return the size of array to house the result.
990     return max + 1;
991 }
992 
poly_pack(const int * pin,unsigned int * pout,int len)993 void dvbt2_framemapper_cc_impl::poly_pack(const int* pin, unsigned int* pout, int len)
994 {
995     int lw = len / 32;
996     int ptr = 0;
997     unsigned int temp;
998     if (len % 32) {
999         lw++;
1000     }
1001 
1002     for (int i = 0; i < lw; i++) {
1003         temp = 0x80000000;
1004         pout[i] = 0;
1005         for (int j = 0; j < 32; j++) {
1006             if (pin[ptr++]) {
1007                 pout[i] |= temp;
1008             }
1009             temp >>= 1;
1010         }
1011     }
1012 }
1013 
bch_poly_build_tables(void)1014 void dvbt2_framemapper_cc_impl::bch_poly_build_tables(void)
1015 {
1016     // Short polynomials
1017     const int polys01[] = { 1, 1, 0, 1, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 1 };
1018     const int polys02[] = { 1, 0, 0, 0, 0, 0, 1, 0, 1, 0, 0, 1, 0, 0, 1 };
1019     const int polys03[] = { 1, 1, 1, 0, 0, 0, 1, 0, 0, 1, 1, 0, 0, 0, 1 };
1020     const int polys04[] = { 1, 0, 0, 0, 1, 0, 0, 1, 1, 0, 1, 0, 1, 0, 1 };
1021     const int polys05[] = { 1, 0, 1, 0, 1, 0, 1, 0, 1, 1, 0, 1, 0, 1, 1 };
1022     const int polys06[] = { 1, 0, 0, 1, 0, 0, 0, 1, 1, 1, 0, 0, 0, 1, 1 };
1023     const int polys07[] = { 1, 0, 1, 0, 0, 1, 1, 1, 0, 0, 1, 1, 0, 1, 1 };
1024     const int polys08[] = { 1, 0, 0, 0, 0, 1, 0, 0, 1, 1, 1, 1, 0, 0, 1 };
1025     const int polys09[] = { 1, 1, 1, 1, 0, 0, 0, 0, 0, 1, 1, 0, 0, 0, 1 };
1026     const int polys10[] = { 1, 0, 0, 1, 0, 0, 1, 0, 0, 1, 0, 1, 1, 0, 1 };
1027     const int polys11[] = { 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 1, 1, 0, 1 };
1028     const int polys12[] = { 1, 1, 1, 1, 0, 1, 1, 1, 1, 0, 1, 0, 0, 1, 1 };
1029 
1030     int len;
1031     int polyout[2][200];
1032 
1033     len = poly_mult(polys01, 15, polys02, 15, polyout[0]);
1034     len = poly_mult(polys03, 15, polyout[0], len, polyout[1]);
1035     len = poly_mult(polys04, 15, polyout[1], len, polyout[0]);
1036     len = poly_mult(polys05, 15, polyout[0], len, polyout[1]);
1037     len = poly_mult(polys06, 15, polyout[1], len, polyout[0]);
1038     len = poly_mult(polys07, 15, polyout[0], len, polyout[1]);
1039     len = poly_mult(polys08, 15, polyout[1], len, polyout[0]);
1040     len = poly_mult(polys09, 15, polyout[0], len, polyout[1]);
1041     len = poly_mult(polys10, 15, polyout[1], len, polyout[0]);
1042     len = poly_mult(polys11, 15, polyout[0], len, polyout[1]);
1043     len = poly_mult(polys12, 15, polyout[1], len, polyout[0]);
1044     poly_pack(polyout[0], m_poly_s_12, 168);
1045 }
1046 
reg_6_shift(unsigned int * sr)1047 inline void dvbt2_framemapper_cc_impl::reg_6_shift(unsigned int* sr)
1048 {
1049     sr[5] = (sr[5] >> 1) | (sr[4] << 31);
1050     sr[4] = (sr[4] >> 1) | (sr[3] << 31);
1051     sr[3] = (sr[3] >> 1) | (sr[2] << 31);
1052     sr[2] = (sr[2] >> 1) | (sr[1] << 31);
1053     sr[1] = (sr[1] >> 1) | (sr[0] << 31);
1054     sr[0] = (sr[0] >> 1);
1055 }
1056 
l1pre_ldpc_lookup_generate(void)1057 void dvbt2_framemapper_cc_impl::l1pre_ldpc_lookup_generate(void)
1058 {
1059     int im;
1060     int index;
1061     int pbits;
1062     int q;
1063     index = 0;
1064     im = 0;
1065 
1066     pbits = FRAME_SIZE_SHORT - NBCH_1_4; // number of parity bits
1067     q = 36;
1068 
1069     for (int row = 0; row < 9; row++) {
1070         for (int n = 0; n < 360; n++) {
1071             for (int col = 1; col <= ldpc_tab_1_4S[row][0]; col++) {
1072                 l1pre_ldpc_encode.p[index] = (ldpc_tab_1_4S[row][col] + (n * q)) % pbits;
1073                 l1pre_ldpc_encode.d[index] = im;
1074                 index++;
1075             }
1076             im++;
1077         }
1078     }
1079     l1pre_ldpc_encode.table_length = index;
1080 }
1081 
l1post_ldpc_lookup_generate(void)1082 void dvbt2_framemapper_cc_impl::l1post_ldpc_lookup_generate(void)
1083 {
1084     int im;
1085     int index;
1086     int pbits;
1087     int q;
1088     index = 0;
1089     im = 0;
1090 
1091     pbits = FRAME_SIZE_SHORT - NBCH_1_2; // number of parity bits
1092     q = 25;
1093 
1094     for (int row = 0; row < 20; row++) {
1095         for (int n = 0; n < 360; n++) {
1096             for (int col = 1; col <= ldpc_tab_1_2S[row][0]; col++) {
1097                 l1post_ldpc_encode.p[index] = (ldpc_tab_1_2S[row][col] + (n * q)) % pbits;
1098                 l1post_ldpc_encode.d[index] = im;
1099                 index++;
1100             }
1101             im++;
1102         }
1103     }
1104     l1post_ldpc_encode.table_length = index;
1105 }
1106 
add_l1pre(gr_complex * out)1107 void dvbt2_framemapper_cc_impl::add_l1pre(gr_complex* out)
1108 {
1109     int temp, offset_bits = 0;
1110     unsigned char b, value;
1111     unsigned int shift[6];
1112     int plen = FRAME_SIZE_SHORT - NBCH_1_4;
1113     const unsigned char* d;
1114     unsigned char* p;
1115     unsigned char* l1pre = l1_temp;
1116     L1Pre* l1preinit = &L1_Signalling[0].l1pre_data;
1117     int g, o, index;
1118 
1119     temp = l1preinit->type;
1120     for (int n = 7; n >= 0; n--) {
1121         l1pre[offset_bits++] = temp & (1 << n) ? 1 : 0;
1122     }
1123     l1pre[offset_bits++] = l1preinit->bwt_ext;
1124     temp = l1preinit->s1;
1125     for (int n = 2; n >= 0; n--) {
1126         l1pre[offset_bits++] = temp & (1 << n) ? 1 : 0;
1127     }
1128     temp = l1preinit->s2;
1129     for (int n = 2; n >= 0; n--) {
1130         l1pre[offset_bits++] = temp & (1 << n) ? 1 : 0;
1131     }
1132     l1pre[offset_bits++] = 0;
1133     l1pre[offset_bits++] = l1preinit->l1_repetition_flag;
1134     temp = l1preinit->guard_interval;
1135     for (int n = 2; n >= 0; n--) {
1136         l1pre[offset_bits++] = temp & (1 << n) ? 1 : 0;
1137     }
1138     temp = l1preinit->papr;
1139     for (int n = 3; n >= 0; n--) {
1140         l1pre[offset_bits++] = temp & (1 << n) ? 1 : 0;
1141     }
1142     temp = l1preinit->l1_mod;
1143     for (int n = 3; n >= 0; n--) {
1144         l1pre[offset_bits++] = temp & (1 << n) ? 1 : 0;
1145     }
1146     temp = l1preinit->l1_cod;
1147     for (int n = 1; n >= 0; n--) {
1148         l1pre[offset_bits++] = temp & (1 << n) ? 1 : 0;
1149     }
1150     temp = l1preinit->l1_fec_type;
1151     for (int n = 1; n >= 0; n--) {
1152         l1pre[offset_bits++] = temp & (1 << n) ? 1 : 0;
1153     }
1154     temp = l1preinit->l1_post_size;
1155     for (int n = 17; n >= 0; n--) {
1156         l1pre[offset_bits++] = temp & (1 << n) ? 1 : 0;
1157     }
1158     temp = l1preinit->l1_post_info_size;
1159     for (int n = 17; n >= 0; n--) {
1160         l1pre[offset_bits++] = temp & (1 << n) ? 1 : 0;
1161     }
1162     temp = l1preinit->pilot_pattern;
1163     for (int n = 3; n >= 0; n--) {
1164         l1pre[offset_bits++] = temp & (1 << n) ? 1 : 0;
1165     }
1166     temp = l1preinit->tx_id_availability;
1167     for (int n = 7; n >= 0; n--) {
1168         l1pre[offset_bits++] = temp & (1 << n) ? 1 : 0;
1169     }
1170     temp = l1preinit->cell_id;
1171     for (int n = 15; n >= 0; n--) {
1172         l1pre[offset_bits++] = temp & (1 << n) ? 1 : 0;
1173     }
1174     temp = l1preinit->network_id;
1175     for (int n = 15; n >= 0; n--) {
1176         l1pre[offset_bits++] = temp & (1 << n) ? 1 : 0;
1177     }
1178     temp = l1preinit->t2_system_id;
1179     for (int n = 15; n >= 0; n--) {
1180         l1pre[offset_bits++] = temp & (1 << n) ? 1 : 0;
1181     }
1182     temp = l1preinit->num_t2_frames;
1183     for (int n = 7; n >= 0; n--) {
1184         l1pre[offset_bits++] = temp & (1 << n) ? 1 : 0;
1185     }
1186     temp = l1preinit->num_data_symbols;
1187     for (int n = 11; n >= 0; n--) {
1188         l1pre[offset_bits++] = temp & (1 << n) ? 1 : 0;
1189     }
1190     temp = l1preinit->regen_flag;
1191     for (int n = 2; n >= 0; n--) {
1192         l1pre[offset_bits++] = temp & (1 << n) ? 1 : 0;
1193     }
1194     l1pre[offset_bits++] = l1preinit->l1_post_extension;
1195     temp = l1preinit->num_rf;
1196     for (int n = 2; n >= 0; n--) {
1197         l1pre[offset_bits++] = temp & (1 << n) ? 1 : 0;
1198     }
1199     temp = l1preinit->current_rf_index;
1200     for (int n = 2; n >= 0; n--) {
1201         l1pre[offset_bits++] = temp & (1 << n) ? 1 : 0;
1202     }
1203     temp = l1preinit->t2_version;
1204     for (int n = 3; n >= 0; n--) {
1205         l1pre[offset_bits++] = temp & (1 << n) ? 1 : 0;
1206     }
1207     l1pre[offset_bits++] = l1preinit->l1_post_scrambled;
1208     l1pre[offset_bits++] = l1preinit->t2_base_lite;
1209     temp = l1preinit->reserved;
1210     for (int n = 3; n >= 0; n--) {
1211         l1pre[offset_bits++] = temp & (1 << n) ? 1 : 0;
1212     }
1213     offset_bits += add_crc32_bits(l1pre, offset_bits);
1214     /* Padding */
1215     for (int n = KBCH_1_4 - offset_bits - 1; n >= 0; n--) {
1216         l1pre[offset_bits++] = 0;
1217     }
1218     /* BCH */
1219     offset_bits = 0;
1220     memset(shift, 0, sizeof(unsigned int) * 6);
1221     for (int j = 0; j < KBCH_1_4; j++) {
1222         value = l1pre[offset_bits++];
1223         b = (value ^ ((shift[5] & 0x01000000) ? 1 : 0));
1224         reg_6_shift(shift);
1225         if (b) {
1226             shift[0] ^= m_poly_s_12[0];
1227             shift[1] ^= m_poly_s_12[1];
1228             shift[2] ^= m_poly_s_12[2];
1229             shift[3] ^= m_poly_s_12[3];
1230             shift[4] ^= m_poly_s_12[4];
1231             shift[5] ^= m_poly_s_12[5];
1232         }
1233     }
1234     for (int n = 0; n < NBCH_PARITY; n++) {
1235         l1pre[offset_bits++] = (shift[5] & 0x01000000) ? 1 : 0;
1236         reg_6_shift(shift);
1237     }
1238     /* LDPC */
1239     d = l1_temp;
1240     p = &l1_temp[NBCH_1_4];
1241     memset(p, 0, sizeof(unsigned char) * plen);
1242     for (int j = 0; j < l1pre_ldpc_encode.table_length; j++) {
1243         p[l1pre_ldpc_encode.p[j]] ^= d[l1pre_ldpc_encode.d[j]];
1244     }
1245     for (int j = 1; j < plen; j++) {
1246         p[j] ^= p[j - 1];
1247     }
1248     /* Puncturing */
1249     for (int c = 0; c < 31; c++) {
1250         g = pre_puncture[c];
1251         for (int c2 = 0; c2 < 360; c2++) {
1252             o = (c2 * 36) + g + NBCH_1_4;
1253             l1_temp[o] = 0x55;
1254         }
1255     }
1256     g = pre_puncture[31];
1257     for (int c2 = 0; c2 < 328; c2++) {
1258         o = (c2 * 36) + g + NBCH_1_4;
1259         l1_temp[o] = 0x55;
1260     }
1261     /* remove padding and punctured bits, BPSK modulate */
1262     index = 0;
1263     for (int w = 0; w < KSIG_PRE; w++) {
1264         out[index++] = m_bpsk[l1_temp[w]];
1265     }
1266     for (int w = 0; w < NBCH_PARITY; w++) {
1267         out[index++] = m_bpsk[l1_temp[w + KBCH_1_4]];
1268     }
1269     for (int w = 0; w < FRAME_SIZE_SHORT - NBCH_1_4; w++) {
1270         if (l1_temp[w + NBCH_1_4] != 0x55) {
1271             out[index++] = m_bpsk[l1_temp[w + NBCH_1_4]];
1272         }
1273     }
1274 }
1275 
add_l1post(gr_complex * out,int t2_frame_num)1276 void dvbt2_framemapper_cc_impl::add_l1post(gr_complex* out, int t2_frame_num)
1277 {
1278     int temp, offset_bits = 0;
1279     unsigned char b, value;
1280     unsigned int shift[6];
1281     int plen = FRAME_SIZE_SHORT - NBCH_1_2;
1282     const unsigned char* d;
1283     unsigned char* p;
1284     unsigned char* l1post = l1_interleave;
1285     L1Post* l1postinit = &L1_Signalling[0].l1post_data;
1286     int m, g, o, last, index;
1287     const int* post_padding;
1288     const int* post_puncture;
1289     int rows, numCols, mod, offset, pack, produced;
1290     unsigned char* cols[12];
1291 
1292     temp = l1postinit->sub_slices_per_frame;
1293     for (int n = 14; n >= 0; n--) {
1294         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1295     }
1296     temp = l1postinit->num_plp;
1297     for (int n = 7; n >= 0; n--) {
1298         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1299     }
1300     temp = l1postinit->num_aux;
1301     for (int n = 3; n >= 0; n--) {
1302         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1303     }
1304     temp = l1postinit->aux_config_rfu;
1305     for (int n = 7; n >= 0; n--) {
1306         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1307     }
1308     temp = l1postinit->rf_idx;
1309     for (int n = 2; n >= 0; n--) {
1310         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1311     }
1312     temp = l1postinit->frequency;
1313     for (int n = 31; n >= 0; n--) {
1314         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1315     }
1316     temp = l1postinit->plp_id;
1317     for (int n = 7; n >= 0; n--) {
1318         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1319     }
1320     temp = l1postinit->plp_type;
1321     for (int n = 2; n >= 0; n--) {
1322         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1323     }
1324     temp = l1postinit->plp_payload_type;
1325     for (int n = 4; n >= 0; n--) {
1326         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1327     }
1328     l1post[offset_bits++] = l1postinit->ff_flag;
1329     temp = l1postinit->first_rf_idx;
1330     for (int n = 2; n >= 0; n--) {
1331         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1332     }
1333     temp = l1postinit->first_frame_idx;
1334     for (int n = 7; n >= 0; n--) {
1335         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1336     }
1337     temp = l1postinit->plp_group_id;
1338     for (int n = 7; n >= 0; n--) {
1339         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1340     }
1341     temp = l1postinit->plp_cod;
1342     for (int n = 2; n >= 0; n--) {
1343         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1344     }
1345     temp = l1postinit->plp_mod;
1346     for (int n = 2; n >= 0; n--) {
1347         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1348     }
1349     l1post[offset_bits++] = l1postinit->plp_rotation;
1350     temp = l1postinit->plp_fec_type;
1351     for (int n = 1; n >= 0; n--) {
1352         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1353     }
1354     temp = l1postinit->plp_num_blocks_max;
1355     for (int n = 9; n >= 0; n--) {
1356         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1357     }
1358     temp = l1postinit->frame_interval;
1359     for (int n = 7; n >= 0; n--) {
1360         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1361     }
1362     temp = l1postinit->time_il_length;
1363     for (int n = 7; n >= 0; n--) {
1364         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1365     }
1366     l1post[offset_bits++] = l1postinit->time_il_type;
1367     l1post[offset_bits++] = l1postinit->in_band_a_flag;
1368     l1post[offset_bits++] = l1postinit->in_band_b_flag;
1369     temp = l1postinit->reserved_1;
1370     for (int n = 10; n >= 0; n--) {
1371         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1372     }
1373     temp = l1postinit->plp_mode;
1374     for (int n = 1; n >= 0; n--) {
1375         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1376     }
1377     l1post[offset_bits++] = l1postinit->static_flag;
1378     l1post[offset_bits++] = l1postinit->static_padding_flag;
1379     temp = l1postinit->fef_length_msb;
1380     for (int n = 1; n >= 0; n--) {
1381         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1382     }
1383     temp = l1postinit->reserved_2;
1384     for (int n = 29; n >= 0; n--) {
1385         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1386     }
1387     temp = t2_frame_num;
1388     for (int n = 7; n >= 0; n--) {
1389         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1390     }
1391     temp = l1postinit->sub_slice_interval;
1392     for (int n = 21; n >= 0; n--) {
1393         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1394     }
1395     temp = l1postinit->type_2_start;
1396     for (int n = 21; n >= 0; n--) {
1397         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1398     }
1399     temp = l1postinit->l1_change_counter;
1400     for (int n = 7; n >= 0; n--) {
1401         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1402     }
1403     temp = l1postinit->start_rf_idx;
1404     for (int n = 2; n >= 0; n--) {
1405         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1406     }
1407     temp = l1postinit->reserved_3;
1408     for (int n = 7; n >= 0; n--) {
1409         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1410     }
1411     temp = l1postinit->plp_id_dynamic;
1412     for (int n = 7; n >= 0; n--) {
1413         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1414     }
1415     temp = l1postinit->plp_start;
1416     for (int n = 21; n >= 0; n--) {
1417         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1418     }
1419     temp = l1postinit->plp_num_blocks;
1420     for (int n = 9; n >= 0; n--) {
1421         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1422     }
1423     temp = l1postinit->reserved_4;
1424     for (int n = 7; n >= 0; n--) {
1425         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1426     }
1427     temp = l1postinit->reserved_5;
1428     for (int n = 7; n >= 0; n--) {
1429         l1post[offset_bits++] = temp & (1 << n) ? 1 : 0;
1430     }
1431     offset_bits += add_crc32_bits(l1post, offset_bits);
1432     if (l1_scrambled == TRUE) {
1433         for (int n = 0; n < offset_bits; n++) {
1434             l1post[n] = l1post[n] ^ l1_randomize[n];
1435         }
1436     }
1437     /* Padding */
1438     switch (l1_constellation) {
1439     case L1_MOD_BPSK:
1440         post_padding = post_padding_bqpsk;
1441         break;
1442     case L1_MOD_QPSK:
1443         post_padding = post_padding_bqpsk;
1444         break;
1445     case L1_MOD_16QAM:
1446         post_padding = post_padding_16qam;
1447         break;
1448     case L1_MOD_64QAM:
1449         post_padding = post_padding_64qam;
1450         break;
1451     default:
1452         post_padding = post_padding_bqpsk;
1453         break;
1454     }
1455     memset(l1_map, 0, KBCH_1_2);
1456     if (offset_bits <= 360) {
1457         m = 20 - 1;
1458         last = 360 - offset_bits;
1459     } else {
1460         m = (KBCH_1_2 - offset_bits) / 360;
1461         last = KBCH_1_2 - offset_bits - (360 * m);
1462     }
1463     for (int n = 0; n < m; n++) {
1464         index = post_padding[n] * 360;
1465         if (post_padding[n] == 19) {
1466             for (int w = 0; w < 192; w++) {
1467                 l1_map[index++] = 0x7;
1468             }
1469         } else {
1470             for (int w = 0; w < 360; w++) {
1471                 l1_map[index++] = 0x7;
1472             }
1473         }
1474     }
1475     if (post_padding[m] == 19) {
1476         index = (post_padding[m] * 360) + 192 - last;
1477     } else {
1478         index = (post_padding[m] * 360) + 360 - last;
1479     }
1480     for (int w = 0; w < last; w++) {
1481         l1_map[index++] = 0x7;
1482     }
1483     index = 0;
1484     l1post = l1_temp;
1485     for (int n = 0; n < KBCH_1_2; n++) {
1486         if (l1_map[n] != 0x7) {
1487             l1post[n] = l1_interleave[index++];
1488         } else {
1489             l1post[n] = 0;
1490         }
1491     }
1492     /* BCH */
1493     offset_bits = 0;
1494     memset(shift, 0, sizeof(unsigned int) * 6);
1495     for (int j = 0; j < KBCH_1_2; j++) {
1496         value = l1post[offset_bits++];
1497         b = (value ^ ((shift[5] & 0x01000000) ? 1 : 0));
1498         reg_6_shift(shift);
1499         if (b) {
1500             shift[0] ^= m_poly_s_12[0];
1501             shift[1] ^= m_poly_s_12[1];
1502             shift[2] ^= m_poly_s_12[2];
1503             shift[3] ^= m_poly_s_12[3];
1504             shift[4] ^= m_poly_s_12[4];
1505             shift[5] ^= m_poly_s_12[5];
1506         }
1507     }
1508     for (int n = 0; n < NBCH_PARITY; n++) {
1509         l1post[offset_bits++] = (shift[5] & 0x01000000) ? 1 : 0;
1510         reg_6_shift(shift);
1511     }
1512     /* LDPC */
1513     d = l1_temp;
1514     p = &l1_temp[NBCH_1_2];
1515     memset(p, 0, sizeof(unsigned char) * plen);
1516     for (int j = 0; j < l1post_ldpc_encode.table_length; j++) {
1517         p[l1post_ldpc_encode.p[j]] ^= d[l1post_ldpc_encode.d[j]];
1518     }
1519     for (int j = 1; j < plen; j++) {
1520         p[j] ^= p[j - 1];
1521     }
1522     /* Puncturing */
1523     switch (l1_constellation) {
1524     case L1_MOD_BPSK:
1525         post_puncture = post_puncture_bqpsk;
1526         break;
1527     case L1_MOD_QPSK:
1528         post_puncture = post_puncture_bqpsk;
1529         break;
1530     case L1_MOD_16QAM:
1531         post_puncture = post_puncture_16qam;
1532         break;
1533     case L1_MOD_64QAM:
1534         post_puncture = post_puncture_64qam;
1535         break;
1536     default:
1537         post_puncture = post_puncture_bqpsk;
1538         break;
1539     }
1540     for (int c = 0; c < (N_punc / 360); c++) {
1541         g = post_puncture[c];
1542         for (int c2 = 0; c2 < 360; c2++) {
1543             o = (c2 * 25) + g + NBCH_1_2;
1544             l1_temp[o] = 0x55;
1545         }
1546     }
1547     g = post_puncture[(N_punc / 360)];
1548     for (int c2 = 0; c2 < (N_punc - ((N_punc / 360) * 360)); c2++) {
1549         o = (c2 * 25) + g + NBCH_1_2;
1550         l1_temp[o] = 0x55;
1551     }
1552     /* remove padding and punctured bits */
1553     index = 0;
1554     for (int w = 0; w < KBCH_1_2; w++) {
1555         if (l1_map[w] != 0x7) {
1556             l1_interleave[index++] = l1_temp[w];
1557         }
1558     }
1559     for (int w = 0; w < NBCH_PARITY; w++) {
1560         l1_interleave[index++] = l1_temp[w + KBCH_1_2];
1561     }
1562     for (int w = 0; w < FRAME_SIZE_SHORT - NBCH_1_2; w++) {
1563         if (l1_temp[w + NBCH_1_2] != 0x55) {
1564             l1_interleave[index++] = l1_temp[w + NBCH_1_2];
1565         }
1566     }
1567     /* Bit interleave for 16QAM and 64QAM */
1568     if (l1_constellation == L1_MOD_16QAM || l1_constellation == L1_MOD_64QAM) {
1569         if (l1_constellation == L1_MOD_16QAM) {
1570             numCols = 8;
1571             rows = N_post / 8;
1572         } else {
1573             numCols = 12;
1574             rows = N_post / 12;
1575         }
1576         for (int j = 0; j < numCols; j++) {
1577             cols[j] = &l1_interleave[rows * j];
1578         }
1579         index = 0;
1580         for (int k = 0; k < rows; k++) {
1581             for (int w = 0; w < numCols; w++) {
1582                 *l1post++ = *(cols[w] + index);
1583             }
1584             index++;
1585         }
1586     }
1587     switch (l1_constellation) {
1588     case L1_MOD_BPSK:
1589         index = 0;
1590         produced = 0;
1591         for (int d = 0; d < N_post; d++) {
1592             out[produced++] = m_bpsk[l1_interleave[index++]];
1593         }
1594         break;
1595     case L1_MOD_QPSK:
1596         mod = 2;
1597         index = 0;
1598         produced = 0;
1599         for (int d = 0; d < N_post / mod; d++) {
1600             pack = 0;
1601             for (int e = 0; e < mod; e++) {
1602                 pack |= l1_interleave[index++];
1603                 pack <<= 1;
1604             }
1605             pack >>= 1;
1606             out[produced++] = m_qpsk[pack];
1607         }
1608         break;
1609     case L1_MOD_16QAM:
1610         mod = 4;
1611         index = 0;
1612         produced = 0;
1613         for (int d = 0; d < N_post / (mod * 2); d++) {
1614             pack = 0;
1615             for (int e = 0; e < (mod * 2); e++) {
1616                 offset = mux16[e];
1617                 pack |= l1_temp[index + offset];
1618                 pack <<= 1;
1619             }
1620             pack >>= 1;
1621             out[produced++] = m_16qam[pack >> 4];
1622             out[produced++] = m_16qam[pack & 0xf];
1623             index += (mod * 2);
1624         }
1625         break;
1626     case L1_MOD_64QAM:
1627         mod = 6;
1628         index = 0;
1629         produced = 0;
1630         for (int d = 0; d < N_post / (mod * 2); d++) {
1631             pack = 0;
1632             for (int e = 0; e < (mod * 2); e++) {
1633                 offset = mux64[e];
1634                 pack |= l1_temp[index + offset];
1635                 pack <<= 1;
1636             }
1637             pack >>= 1;
1638             out[produced++] = m_64qam[pack >> 6];
1639             out[produced++] = m_64qam[pack & 0x3f];
1640             index += (mod * 2);
1641         }
1642         break;
1643     }
1644 }
1645 
init_dummy_randomizer(void)1646 void dvbt2_framemapper_cc_impl::init_dummy_randomizer(void)
1647 {
1648     int sr = 0x4A80;
1649     int num = mapped_items - stream_items - 1840 - (N_post / eta_mod) - (N_FC - C_FC);
1650     std::fill_n(&dummy_randomize[0], num, 0);
1651     for (int i = 0; i < num; i++) {
1652         int b = ((sr) ^ (sr >> 1)) & 1;
1653         dummy_randomize[i] = (b ? -1.0 : 1.0);
1654         sr >>= 1;
1655         if (b) {
1656             sr |= 0x4000;
1657         }
1658     }
1659 }
1660 
init_l1_randomizer(void)1661 void dvbt2_framemapper_cc_impl::init_l1_randomizer(void)
1662 {
1663     int sr = 0x4A80;
1664     for (int i = 0; i < KBCH_1_2; i++) {
1665         int b = ((sr) ^ (sr >> 1)) & 1;
1666         l1_randomize[i] = b;
1667         sr >>= 1;
1668         if (b) {
1669             sr |= 0x4000;
1670         }
1671     }
1672 }
1673 
general_work(int noutput_items,gr_vector_int & ninput_items,gr_vector_const_void_star & input_items,gr_vector_void_star & output_items)1674 int dvbt2_framemapper_cc_impl::general_work(int noutput_items,
1675                                             gr_vector_int& ninput_items,
1676                                             gr_vector_const_void_star& input_items,
1677                                             gr_vector_void_star& output_items)
1678 {
1679     const gr_complex* in = (const gr_complex*)input_items[0];
1680     gr_complex* out = (gr_complex*)output_items[0];
1681     int index = 0;
1682     int read, save, count = 0;
1683     gr_complex* interleave = zigzag_interleave;
1684 
1685     for (int i = 0; i < noutput_items; i += mapped_items) {
1686         if (N_P2 == 1) {
1687             for (int j = 0; j < 1840; j++) {
1688                 *out++ = l1pre_cache[index++];
1689             }
1690             add_l1post(out, t2_frame_num);
1691             t2_frame_num = (t2_frame_num + 1) % t2_frames;
1692             out += N_post / eta_mod;
1693             for (int j = 0; j < stream_items; j++) {
1694                 *out++ = *in++;
1695             }
1696             index = 0;
1697             for (int j = 0; j < mapped_items - stream_items - 1840 - (N_post / eta_mod) -
1698                                     (N_FC - C_FC);
1699                  j++) {
1700                 *out++ = dummy_randomize[index++];
1701             }
1702             for (int j = 0; j < N_FC - C_FC; j++) {
1703                 *out++ = unmodulated;
1704             }
1705         } else {
1706             for (int j = 0; j < 1840; j++) {
1707                 *interleave++ = l1pre_cache[index++];
1708             }
1709             add_l1post(interleave, t2_frame_num);
1710             t2_frame_num = (t2_frame_num + 1) % t2_frames;
1711             interleave += N_post / eta_mod;
1712             for (int j = 0; j < stream_items; j++) {
1713                 *interleave++ = *in++;
1714             }
1715             index = 0;
1716             for (int j = 0; j < mapped_items - stream_items - 1840 - (N_post / eta_mod) -
1717                                     (N_FC - C_FC);
1718                  j++) {
1719                 *interleave++ = dummy_randomize[index++];
1720             }
1721             for (int j = 0; j < N_FC - C_FC; j++) {
1722                 *interleave++ = unmodulated;
1723             }
1724             interleave = zigzag_interleave;
1725             read = 0;
1726             index = 0;
1727             for (int n = 0; n < N_P2; n++) {
1728                 save = read;
1729                 for (int j = 0; j < 1840 / N_P2; j++) {
1730                     out[index++] = interleave[read];
1731                     count++;
1732                     read += N_P2;
1733                 }
1734                 read = save + 1;
1735                 index += C_P2 - (1840 / N_P2);
1736             }
1737             read = 1840;
1738             index = 1840 / N_P2;
1739             for (int n = 0; n < N_P2; n++) {
1740                 save = read;
1741                 for (int j = 0; j < (N_post / eta_mod) / N_P2; j++) {
1742                     out[index++] = interleave[read];
1743                     count++;
1744                     read += N_P2;
1745                 }
1746                 read = save + 1;
1747                 index += C_P2 - ((N_post / eta_mod) / N_P2);
1748             }
1749             read = 1840 + (N_post / eta_mod);
1750             index = (1840 / N_P2) + ((N_post / eta_mod) / N_P2);
1751             for (int n = 0; n < N_P2; n++) {
1752                 for (int j = 0; j < C_P2 - (1840 / N_P2) - ((N_post / eta_mod) / N_P2);
1753                      j++) {
1754                     out[index++] = interleave[read++];
1755                     count++;
1756                 }
1757                 index += C_P2 - (C_P2 - (1840 / N_P2) - ((N_post / eta_mod) / N_P2));
1758             }
1759             index -= C_P2 - (C_P2 - (1840 / N_P2) - ((N_post / eta_mod) / N_P2));
1760             for (int j = 0; j < mapped_items - count; j++) {
1761                 out[index++] = interleave[read++];
1762             }
1763             out += mapped_items;
1764         }
1765     }
1766 
1767     // Tell runtime system how many input items we consumed on
1768     // each input stream.
1769     consume_each(stream_items);
1770 
1771     // Tell runtime system how many output items we produced.
1772     return noutput_items;
1773 }
1774 
1775 const int dvbt2_framemapper_cc_impl::ldpc_tab_1_4S[9][13] = {
1776     { 12, 6295, 9626, 304, 7695, 4839, 4936, 1660, 144, 11203, 5567, 6347, 12557 },
1777     { 12, 10691, 4988, 3859, 3734, 3071, 3494, 7687, 10313, 5964, 8069, 8296, 11090 },
1778     { 12, 10774, 3613, 5208, 11177, 7676, 3549, 8746, 6583, 7239, 12265, 2674, 4292 },
1779     { 12, 11869, 3708, 5981, 8718, 4908, 10650, 6805, 3334, 2627, 10461, 9285, 11120 },
1780     { 3, 7844, 3079, 10773, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
1781     { 3, 3385, 10854, 5747, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
1782     { 3, 1360, 12010, 12202, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
1783     { 3, 6189, 4241, 2343, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
1784     { 3, 9840, 12726, 4977, 0, 0, 0, 0, 0, 0, 0, 0, 0 }
1785 };
1786 
1787 const int dvbt2_framemapper_cc_impl::ldpc_tab_1_2S[20][9] = {
1788     { 8, 20, 712, 2386, 6354, 4061, 1062, 5045, 5158 },
1789     { 8, 21, 2543, 5748, 4822, 2348, 3089, 6328, 5876 },
1790     { 8, 22, 926, 5701, 269, 3693, 2438, 3190, 3507 },
1791     { 8, 23, 2802, 4520, 3577, 5324, 1091, 4667, 4449 },
1792     { 8, 24, 5140, 2003, 1263, 4742, 6497, 1185, 6202 },
1793     { 3, 0, 4046, 6934, 0, 0, 0, 0, 0 },
1794     { 3, 1, 2855, 66, 0, 0, 0, 0, 0 },
1795     { 3, 2, 6694, 212, 0, 0, 0, 0, 0 },
1796     { 3, 3, 3439, 1158, 0, 0, 0, 0, 0 },
1797     { 3, 4, 3850, 4422, 0, 0, 0, 0, 0 },
1798     { 3, 5, 5924, 290, 0, 0, 0, 0, 0 },
1799     { 3, 6, 1467, 4049, 0, 0, 0, 0, 0 },
1800     { 3, 7, 7820, 2242, 0, 0, 0, 0, 0 },
1801     { 3, 8, 4606, 3080, 0, 0, 0, 0, 0 },
1802     { 3, 9, 4633, 7877, 0, 0, 0, 0, 0 },
1803     { 3, 10, 3884, 6868, 0, 0, 0, 0, 0 },
1804     { 3, 11, 8935, 4996, 0, 0, 0, 0, 0 },
1805     { 3, 12, 3028, 764, 0, 0, 0, 0, 0 },
1806     { 3, 13, 5988, 1057, 0, 0, 0, 0, 0 },
1807     { 3, 14, 7411, 3450, 0, 0, 0, 0, 0 }
1808 };
1809 
1810 const int dvbt2_framemapper_cc_impl::pre_puncture[36] = {
1811     27, 13, 29, 32, 5,  0, 11, 21, 33, 20, 25, 28, 18, 35, 8, 3, 9,  31,
1812     22, 24, 7,  14, 17, 4, 2,  26, 16, 34, 19, 10, 12, 23, 1, 6, 30, 15
1813 };
1814 
1815 const int dvbt2_framemapper_cc_impl::post_padding_bqpsk[20] = {
1816     18, 17, 16, 15, 14, 13, 12, 11, 4, 10, 9, 8, 3, 2, 7, 6, 5, 1, 19, 0
1817 };
1818 
1819 const int dvbt2_framemapper_cc_impl::post_padding_16qam[20] = {
1820     18, 17, 16, 15, 14, 13, 12, 11, 4, 10, 9, 8, 7, 3, 2, 1, 6, 5, 19, 0
1821 };
1822 
1823 const int dvbt2_framemapper_cc_impl::post_padding_64qam[20] = {
1824     18, 17, 16, 4, 15, 14, 13, 12, 3, 11, 10, 9, 2, 8, 7, 1, 6, 5, 19, 0
1825 };
1826 
1827 const int dvbt2_framemapper_cc_impl::post_puncture_bqpsk[25] = {
1828     6,  4,  18, 9,  13, 8, 15, 20, 5,  17, 2, 24, 10,
1829     22, 12, 3,  16, 23, 1, 14, 0,  21, 19, 7, 11
1830 };
1831 
1832 const int dvbt2_framemapper_cc_impl::post_puncture_16qam[25] = {
1833     6, 4,  13, 9,  18, 8,  15, 20, 5,  17, 2,  22, 24,
1834     7, 12, 1,  16, 23, 14, 0,  21, 10, 19, 11, 3
1835 };
1836 
1837 const int dvbt2_framemapper_cc_impl::post_puncture_64qam[25] = {
1838     6,  15, 13, 10, 3,  17, 21, 8, 5,  19, 2,  23, 16,
1839     24, 7,  18, 1,  12, 20, 0,  4, 14, 9,  11, 22
1840 };
1841 
1842 const int dvbt2_framemapper_cc_impl::mux16[8] = { 7, 1, 3, 5, 2, 4, 6, 0 };
1843 
1844 const int dvbt2_framemapper_cc_impl::mux64[12] = { 11, 8, 5, 2, 10, 7, 4, 1, 9, 6, 3, 0 };
1845 
1846 } /* namespace dtv */
1847 } /* namespace gr */
1848