summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAndrej Rode <mail@andrejro.de>2018-02-06 01:21:02 +0100
committerAndrej Rode <mail@andrejro.de>2018-02-07 18:55:45 +0100
commit81858b8677c3746d1bbf04e3e9bc3369cd5d6636 (patch)
tree3ae2ed2a0b856a0a6aa2fe705ab5a1228bbcfb76
parentdfc6dd7f0c878f4550c38fd7ef44e7dc0caadebe (diff)
fec: convert viterbi sub-library to valid C++ in correct namespace
-rw-r--r--gnuradio-runtime/include/gnuradio/math.h3
-rw-r--r--gr-fec/include/gnuradio/fec/viterbi.h52
-rw-r--r--gr-fec/lib/ccsds_encoder_impl.cc2
-rw-r--r--gr-fec/lib/decode_ccsds_27_fb_impl.h3
-rw-r--r--gr-fec/lib/encode_ccsds_27_bb_impl.cc2
-rw-r--r--gr-fec/lib/viterbi/CMakeLists.txt1
-rw-r--r--gr-fec/lib/viterbi/decode.cc12
-rw-r--r--gr-fec/lib/viterbi/encode.cc4
-rw-r--r--gr-fec/lib/viterbi/metrics.c127
-rw-r--r--gr-fec/lib/viterbi/viterbi.c487
10 files changed, 354 insertions, 339 deletions
diff --git a/gnuradio-runtime/include/gnuradio/math.h b/gnuradio-runtime/include/gnuradio/math.h
index e60f56b594..ff41006912 100644
--- a/gnuradio-runtime/include/gnuradio/math.h
+++ b/gnuradio-runtime/include/gnuradio/math.h
@@ -31,6 +31,9 @@
#include <gnuradio/api.h>
#include <gnuradio/gr_complex.h>
+#define M_SQRT2 1.41421356237309504880 /* sqrt(2) */
+#define M_LOG2E 1.4426950408889634074 /* log_2 e */
+
namespace gr {
static inline bool
diff --git a/gr-fec/include/gnuradio/fec/viterbi.h b/gr-fec/include/gnuradio/fec/viterbi.h
index 5827f1e9b6..4ba64ed1ed 100644
--- a/gr-fec/include/gnuradio/fec/viterbi.h
+++ b/gr-fec/include/gnuradio/fec/viterbi.h
@@ -1,5 +1,5 @@
/*
- * Copyright 2008 Free Software Foundation, Inc.
+ * Copyright 2008,2018 Free Software Foundation, Inc.
*
* This file is part of GNU Radio
*
@@ -24,30 +24,40 @@
* But it fits so nicely into a 32-bit machine word...
*/
+#ifndef INCLUDED_VITERBI_H
+#define INCLUDED_VITERBI_H
+
#include <gnuradio/fec/api.h>
-struct viterbi_state {
- unsigned long path; /* Decoded path to this state */
- long metric; /* Cumulative metric to this state */
-};
+namespace gr {
+ namespace fec {
+
+ struct FEC_API viterbi_state {
+ unsigned long path; /* Decoded path to this state */
+ long metric; /* Cumulative metric to this state */
+ };
+
+ FEC_API
+ void gen_met(int mettab[2][256], /* Metric table */
+ int amp, /* Signal amplitude */
+ double esn0, /* Es/N0 ratio in dB */
+ double bias, /* Metric bias */
+ int scale); /* Scale factor */
-FEC_API
-int gen_met(int mettab[2][256], /* Metric table */
- int amp, /* Signal amplitude */
- double esn0, /* Es/N0 ratio in dB */
- double bias, /* Metric bias */
- int scale); /* Scale factor */
+ FEC_API unsigned char
+ encode(unsigned char *symbols, unsigned char *data,
+ unsigned int nbytes,unsigned char encstate);
-FEC_API unsigned char
-encode(unsigned char *symbols, unsigned char *data,
- unsigned int nbytes,unsigned char encstate);
+ FEC_API void
+ viterbi_chunks_init(struct viterbi_state* state);
-FEC_API void
-viterbi_chunks_init(struct viterbi_state* state);
+ FEC_API void
+ viterbi_butterfly2(unsigned char *symbols, int mettab[2][256],
+ struct viterbi_state *state0, struct viterbi_state *state1);
- FEC_API void
-viterbi_butterfly2(unsigned char *symbols, int mettab[2][256],
- struct viterbi_state *state0, struct viterbi_state *state1);
+ FEC_API unsigned char
+ viterbi_get_output(struct viterbi_state *state, unsigned char *outbuf);
+ }
+}
-FEC_API unsigned char
-viterbi_get_output(struct viterbi_state *state, unsigned char *outbuf);
+#endif /* INCLUDED_VITERBI_H */
diff --git a/gr-fec/lib/ccsds_encoder_impl.cc b/gr-fec/lib/ccsds_encoder_impl.cc
index 2a2228a8ed..4c873a5288 100644
--- a/gr-fec/lib/ccsds_encoder_impl.cc
+++ b/gr-fec/lib/ccsds_encoder_impl.cc
@@ -28,9 +28,7 @@
#include <gnuradio/fec/generic_encoder.h>
#include <cstdio>
-extern "C" {
#include <gnuradio/fec/viterbi.h>
-}
namespace gr {
namespace fec {
diff --git a/gr-fec/lib/decode_ccsds_27_fb_impl.h b/gr-fec/lib/decode_ccsds_27_fb_impl.h
index 83fed604d4..fff01d2374 100644
--- a/gr-fec/lib/decode_ccsds_27_fb_impl.h
+++ b/gr-fec/lib/decode_ccsds_27_fb_impl.h
@@ -24,10 +24,7 @@
#define INCLUDED_FEC_DECODE_CCSDS_27_FB_IMPL_H
#include <gnuradio/fec/decode_ccsds_27_fb.h>
-
-extern "C" {
#include <gnuradio/fec/viterbi.h>
-}
namespace gr {
namespace fec {
diff --git a/gr-fec/lib/encode_ccsds_27_bb_impl.cc b/gr-fec/lib/encode_ccsds_27_bb_impl.cc
index 56518777c7..e81cfaa75e 100644
--- a/gr-fec/lib/encode_ccsds_27_bb_impl.cc
+++ b/gr-fec/lib/encode_ccsds_27_bb_impl.cc
@@ -27,9 +27,7 @@
#include "encode_ccsds_27_bb_impl.h"
#include <gnuradio/io_signature.h>
-extern "C" {
#include <gnuradio/fec/viterbi.h>
-}
namespace gr {
namespace fec {
diff --git a/gr-fec/lib/viterbi/CMakeLists.txt b/gr-fec/lib/viterbi/CMakeLists.txt
index 10c5940246..5bbbc24ebf 100644
--- a/gr-fec/lib/viterbi/CMakeLists.txt
+++ b/gr-fec/lib/viterbi/CMakeLists.txt
@@ -43,6 +43,7 @@ endif(MSVC)
########################################################################
# Append gnuradio-runtime library sources
########################################################################
+SET_SOURCE_FILES_PROPERTIES( ${viterbi_sources} PROPERTIES LANGUAGE CXX )
list(APPEND gnuradio_fec_sources ${viterbi_sources})
########################################################################
diff --git a/gr-fec/lib/viterbi/decode.cc b/gr-fec/lib/viterbi/decode.cc
index 0af0b34483..3b948818fe 100644
--- a/gr-fec/lib/viterbi/decode.cc
+++ b/gr-fec/lib/viterbi/decode.cc
@@ -27,9 +27,7 @@
*
*/
-extern "C" {
#include <gnuradio/fec/viterbi.h>
-}
#include <cstdio>
#include <cmath>
@@ -52,10 +50,10 @@ int main()
gen_met(mettab, amp, esn0, 0.0, 4);
// Initialize decoder state
- struct viterbi_state state0[64];
- struct viterbi_state state1[64];
+ struct gr::fec::viterbi_state state0[64];
+ struct gr::fec::viterbi_state state1[64];
unsigned char viterbi_in[16];
- viterbi_chunks_init(state0);
+ gr::fec::viterbi_chunks_init(state0);
while (!feof(stdin)) {
unsigned int n = fread(syms, 1, MAXENCSIZE, stdin);
@@ -71,11 +69,11 @@ int main()
// Every four symbols, perform the butterfly2 operation
if ((count % 4) == 3) {
- viterbi_butterfly2(viterbi_in, mettab, state0, state1);
+ gr::fec::viterbi_butterfly2(viterbi_in, mettab, state0, state1);
// Every sixteen symbols, perform the readback operation
if ((count > 64) && (count % 16) == 11) {
- viterbi_get_output(state0, out);
+ gr::fec::viterbi_get_output(state0, out);
fwrite(out++, 1, 1, stdout);
}
}
diff --git a/gr-fec/lib/viterbi/encode.cc b/gr-fec/lib/viterbi/encode.cc
index 4e152781f0..bf857ff7b8 100644
--- a/gr-fec/lib/viterbi/encode.cc
+++ b/gr-fec/lib/viterbi/encode.cc
@@ -29,9 +29,7 @@
*
*/
-extern "C" {
#include <gnuradio/fec/viterbi.h>
-}
#include <cstdio>
@@ -46,7 +44,7 @@ int main()
while (!feof(stdin)) {
unsigned int n = fread(data, 1, MAXCHUNKSIZE, stdin);
- encoder_state = encode(syms, data, n, encoder_state);
+ encoder_state = gr::fec::encode(syms, data, n, encoder_state);
fwrite(syms, 1, n*16, stdout);
}
diff --git a/gr-fec/lib/viterbi/metrics.c b/gr-fec/lib/viterbi/metrics.c
index 0d91c301ff..c4aa7a07ed 100644
--- a/gr-fec/lib/viterbi/metrics.c
+++ b/gr-fec/lib/viterbi/metrics.c
@@ -39,6 +39,8 @@
*/
#define OFFSET 128
+#include<gnuradio/math.h>
+
#include <stdlib.h>
#include <math.h>
@@ -51,76 +53,81 @@ extern double erf(double x);
/* Logarithm base 2 */
#define gr_log2(x) (log(x)*M_LOG2E)
+namespace gr{
+ namespace fec{
+
/* Generate log-likelihood metrics for 8-bit soft quantized channel
* assuming AWGN and BPSK
*/
-void
-gen_met(int mettab[2][256], /* Metric table, [sent sym][rx symbol] */
- int amp, /* Signal amplitude, units */
- double esn0, /* Es/N0 ratio in dB */
- double bias, /* Metric bias; 0 for viterbi, rate for sequential */
- int scale) /* Scale factor */
-{
- double noise;
- int s,bit;
- double metrics[2][256];
- double p0,p1;
-
- /* Es/N0 as power ratio */
- esn0 = pow(10.,esn0/10);
-
- noise = 0.5/esn0; /* only half the noise for BPSK */
- noise = sqrt(noise); /* noise/signal Voltage ratio */
-
- /* Zero is a special value, since this sample includes all
- * lower samples that were clipped to this value, i.e., it
- * takes the whole lower tail of the curve
- */
- p1 = normal(((0-OFFSET+0.5)/amp - 1)/noise); /* P(s|1) */
-
- /* Prob of this value occurring for a 0-bit */ /* P(s|0) */
- p0 = normal(((0-OFFSET+0.5)/amp + 1)/noise);
- metrics[0][0] = gr_log2(2*p0/(p1+p0)) - bias;
- metrics[1][0] = gr_log2(2*p1/(p1+p0)) - bias;
-
- for(s=1;s<255;s++){
- /* P(s|1), prob of receiving s given 1 transmitted */
- p1 = normal(((s-OFFSET+0.5)/amp - 1)/noise) -
- normal(((s-OFFSET-0.5)/amp - 1)/noise);
-
- /* P(s|0), prob of receiving s given 0 transmitted */
- p0 = normal(((s-OFFSET+0.5)/amp + 1)/noise) -
- normal(((s-OFFSET-0.5)/amp + 1)/noise);
+ void
+ gen_met(int mettab[2][256], /* Metric table, [sent sym][rx symbol] */
+ int amp, /* Signal amplitude, units */
+ double esn0, /* Es/N0 ratio in dB */
+ double bias, /* Metric bias; 0 for viterbi, rate for sequential */
+ int scale) /* Scale factor */
+ {
+ double noise;
+ int s,bit;
+ double metrics[2][256];
+ double p0,p1;
+
+ /* Es/N0 as power ratio */
+ esn0 = pow(10.,esn0/10);
+
+ noise = 0.5/esn0; /* only half the noise for BPSK */
+ noise = sqrt(noise); /* noise/signal Voltage ratio */
+
+ /* Zero is a special value, since this sample includes all
+ * lower samples that were clipped to this value, i.e., it
+ * takes the whole lower tail of the curve
+ */
+ p1 = normal(((0-OFFSET+0.5)/amp - 1)/noise); /* P(s|1) */
+
+ /* Prob of this value occurring for a 0-bit */ /* P(s|0) */
+ p0 = normal(((0-OFFSET+0.5)/amp + 1)/noise);
+ metrics[0][0] = gr_log2(2*p0/(p1+p0)) - bias;
+ metrics[1][0] = gr_log2(2*p1/(p1+p0)) - bias;
+
+ for(s=1;s<255;s++){
+ /* P(s|1), prob of receiving s given 1 transmitted */
+ p1 = normal(((s-OFFSET+0.5)/amp - 1)/noise) -
+ normal(((s-OFFSET-0.5)/amp - 1)/noise);
+
+ /* P(s|0), prob of receiving s given 0 transmitted */
+ p0 = normal(((s-OFFSET+0.5)/amp + 1)/noise) -
+ normal(((s-OFFSET-0.5)/amp + 1)/noise);
#ifdef notdef
- printf("P(%d|1) = %lg, P(%d|0) = %lg\n",s,p1,s,p0);
+ printf("P(%d|1) = %lg, P(%d|0) = %lg\n",s,p1,s,p0);
#endif
- metrics[0][s] = gr_log2(2*p0/(p1+p0)) - bias;
- metrics[1][s] = gr_log2(2*p1/(p1+p0)) - bias;
- }
- /* 255 is also a special value */
- /* P(s|1) */
- p1 = 1 - normal(((255-OFFSET-0.5)/amp - 1)/noise);
- /* P(s|0) */
- p0 = 1 - normal(((255-OFFSET-0.5)/amp + 1)/noise);
-
- metrics[0][255] = gr_log2(2*p0/(p1+p0)) - bias;
- metrics[1][255] = gr_log2(2*p1/(p1+p0)) - bias;
+ metrics[0][s] = gr_log2(2*p0/(p1+p0)) - bias;
+ metrics[1][s] = gr_log2(2*p1/(p1+p0)) - bias;
+ }
+ /* 255 is also a special value */
+ /* P(s|1) */
+ p1 = 1 - normal(((255-OFFSET-0.5)/amp - 1)/noise);
+ /* P(s|0) */
+ p0 = 1 - normal(((255-OFFSET-0.5)/amp + 1)/noise);
+
+ metrics[0][255] = gr_log2(2*p0/(p1+p0)) - bias;
+ metrics[1][255] = gr_log2(2*p1/(p1+p0)) - bias;
#ifdef notdef
- /* The probability of a raw symbol error is the probability
- * that a 1-bit would be received as a sample with value
- * 0-128. This is the offset normal curve integrated from -Inf to 0.
- */
- printf("symbol Pe = %lg\n",normal(-1/noise));
+ /* The probability of a raw symbol error is the probability
+ * that a 1-bit would be received as a sample with value
+ * 0-128. This is the offset normal curve integrated from -Inf to 0.
+ */
+ printf("symbol Pe = %lg\n",normal(-1/noise));
#endif
- for(bit=0;bit<2;bit++){
- for(s=0;s<256;s++){
- /* Scale and round to nearest integer */
- mettab[bit][s] = floor(metrics[bit][s] * scale + 0.5);
+ for(bit=0;bit<2;bit++){
+ for(s=0;s<256;s++){
+ /* Scale and round to nearest integer */
+ mettab[bit][s] = floor(metrics[bit][s] * scale + 0.5);
#ifdef notdef
- printf("metrics[%d][%d] = %lg, mettab = %d\n",
- bit,s,metrics[bit][s],mettab[bit][s]);
+ printf("metrics[%d][%d] = %lg, mettab = %d\n",
+ bit,s,metrics[bit][s],mettab[bit][s]);
#endif
+ }
+ }
}
}
}
diff --git a/gr-fec/lib/viterbi/viterbi.c b/gr-fec/lib/viterbi/viterbi.c
index 3c247a3868..11b9f79b9a 100644
--- a/gr-fec/lib/viterbi/viterbi.c
+++ b/gr-fec/lib/viterbi/viterbi.c
@@ -1,6 +1,6 @@
/*
* Copyright 1995 Phil Karn, KA9Q
- * Copyright 2008 Free Software Foundation, Inc.
+ * Copyright 2008,2018 Free Software Foundation, Inc.
*
* This file is part of GNU Radio
*
@@ -86,270 +86,275 @@
extern unsigned char Partab[]; /* Parity lookup table */
-/* Convolutionally encode data into binary symbols */
-unsigned char
-encode(unsigned char *symbols,
- unsigned char *data,
- unsigned int nbytes,
- unsigned char encstate)
-{
- int i;
-
- while(nbytes-- != 0){
- for(i=7;i>=0;i--){
- encstate = (encstate << 1) | ((*data >> i) & 1);
- *symbols++ = Partab[encstate & POLYA];
- *symbols++ = Partab[encstate & POLYB];
+namespace gr {
+ namespace fec {
+
+ /* Convolutionally encode data into binary symbols */
+ unsigned char
+ encode(unsigned char *symbols,
+ unsigned char *data,
+ unsigned int nbytes,
+ unsigned char encstate)
+ {
+ int i;
+
+ while(nbytes-- != 0){
+ for(i=7;i>=0;i--){
+ encstate = (encstate << 1) | ((*data >> i) & 1);
+ *symbols++ = Partab[encstate & POLYA];
+ *symbols++ = Partab[encstate & POLYB];
+ }
+ data++;
+ }
+
+ return encstate;
}
- data++;
- }
- return encstate;
-}
+ /* Viterbi decoder */
+ int
+ viterbi(unsigned long *metric, /* Final path metric (returned value) */
+ unsigned char *data, /* Decoded output data */
+ unsigned char *symbols, /* Raw deinterleaved input symbols */
+ unsigned int nbits, /* Number of output bits */
+ int mettab[2][256] /* Metric table, [sent sym][rx symbol] */
+ ){
+ unsigned int bitcnt = 0;
+ int mets[4];
+ long bestmetric;
+ int beststate,i;
+ struct viterbi_state state0[64],state1[64],*state,*next;
-/* Viterbi decoder */
-int
-viterbi(unsigned long *metric, /* Final path metric (returned value) */
- unsigned char *data, /* Decoded output data */
- unsigned char *symbols, /* Raw deinterleaved input symbols */
- unsigned int nbits, /* Number of output bits */
- int mettab[2][256] /* Metric table, [sent sym][rx symbol] */
- ){
- unsigned int bitcnt = 0;
- int mets[4];
- long bestmetric;
- int beststate,i;
- struct viterbi_state state0[64],state1[64],*state,*next;
-
- state = state0;
- next = state1;
-
- /* Initialize starting metrics to prefer 0 state */
- state[0].metric = 0;
- for(i=1;i<64;i++)
- state[i].metric = -999999;
- state[0].path = 0;
-
- for(bitcnt = 0;bitcnt < nbits;bitcnt++){
- /* Read input symbol pair and compute all possible branch
- * metrics
- */
- mets[0] = mettab[0][symbols[0]] + mettab[0][symbols[1]];
- mets[1] = mettab[0][symbols[0]] + mettab[1][symbols[1]];
- mets[2] = mettab[1][symbols[0]] + mettab[0][symbols[1]];
- mets[3] = mettab[1][symbols[0]] + mettab[1][symbols[1]];
- symbols += 2;
-
- /* These macro calls were generated by genbut.c */
- BUTTERFLY(0,0);
- BUTTERFLY(1,1);
- BUTTERFLY(2,3);
- BUTTERFLY(3,2);
- BUTTERFLY(4,3);
- BUTTERFLY(5,2);
- BUTTERFLY(6,0);
- BUTTERFLY(7,1);
- BUTTERFLY(8,0);
- BUTTERFLY(9,1);
- BUTTERFLY(10,3);
- BUTTERFLY(11,2);
- BUTTERFLY(12,3);
- BUTTERFLY(13,2);
- BUTTERFLY(14,0);
- BUTTERFLY(15,1);
- BUTTERFLY(16,2);
- BUTTERFLY(17,3);
- BUTTERFLY(18,1);
- BUTTERFLY(19,0);
- BUTTERFLY(20,1);
- BUTTERFLY(21,0);
- BUTTERFLY(22,2);
- BUTTERFLY(23,3);
- BUTTERFLY(24,2);
- BUTTERFLY(25,3);
- BUTTERFLY(26,1);
- BUTTERFLY(27,0);
- BUTTERFLY(28,1);
- BUTTERFLY(29,0);
- BUTTERFLY(30,2);
- BUTTERFLY(31,3);
-
- /* Swap current and next states */
- if(bitcnt & 1){
state = state0;
next = state1;
- } else {
- state = state1;
- next = state0;
- }
- // ETTUS
- //if(bitcnt > nbits-7){
- /* In tail, poison non-zero nodes */
- //for(i=1;i<64;i += 2)
- // state[i].metric = -9999999;
- //}
- /* Produce output every 8 bits once path memory is full */
- if((bitcnt % 8) == 5 && bitcnt > 32){
- /* Find current best path */
+
+ /* Initialize starting metrics to prefer 0 state */
+ state[0].metric = 0;
+ for(i=1;i<64;i++)
+ state[i].metric = -999999;
+ state[0].path = 0;
+
+ for(bitcnt = 0;bitcnt < nbits;bitcnt++){
+ /* Read input symbol pair and compute all possible branch
+ * metrics
+ */
+ mets[0] = mettab[0][symbols[0]] + mettab[0][symbols[1]];
+ mets[1] = mettab[0][symbols[0]] + mettab[1][symbols[1]];
+ mets[2] = mettab[1][symbols[0]] + mettab[0][symbols[1]];
+ mets[3] = mettab[1][symbols[0]] + mettab[1][symbols[1]];
+ symbols += 2;
+
+ /* These macro calls were generated by genbut.c */
+ BUTTERFLY(0,0);
+ BUTTERFLY(1,1);
+ BUTTERFLY(2,3);
+ BUTTERFLY(3,2);
+ BUTTERFLY(4,3);
+ BUTTERFLY(5,2);
+ BUTTERFLY(6,0);
+ BUTTERFLY(7,1);
+ BUTTERFLY(8,0);
+ BUTTERFLY(9,1);
+ BUTTERFLY(10,3);
+ BUTTERFLY(11,2);
+ BUTTERFLY(12,3);
+ BUTTERFLY(13,2);
+ BUTTERFLY(14,0);
+ BUTTERFLY(15,1);
+ BUTTERFLY(16,2);
+ BUTTERFLY(17,3);
+ BUTTERFLY(18,1);
+ BUTTERFLY(19,0);
+ BUTTERFLY(20,1);
+ BUTTERFLY(21,0);
+ BUTTERFLY(22,2);
+ BUTTERFLY(23,3);
+ BUTTERFLY(24,2);
+ BUTTERFLY(25,3);
+ BUTTERFLY(26,1);
+ BUTTERFLY(27,0);
+ BUTTERFLY(28,1);
+ BUTTERFLY(29,0);
+ BUTTERFLY(30,2);
+ BUTTERFLY(31,3);
+
+ /* Swap current and next states */
+ if(bitcnt & 1){
+ state = state0;
+ next = state1;
+ } else {
+ state = state1;
+ next = state0;
+ }
+ // ETTUS
+ //if(bitcnt > nbits-7){
+ /* In tail, poison non-zero nodes */
+ //for(i=1;i<64;i += 2)
+ // state[i].metric = -9999999;
+ //}
+ /* Produce output every 8 bits once path memory is full */
+ if((bitcnt % 8) == 5 && bitcnt > 32){
+ /* Find current best path */
+ bestmetric = state[0].metric;
+ beststate = 0;
+ for(i=1;i<64;i++){
+ if(state[i].metric > bestmetric){
+ bestmetric = state[i].metric;
+ beststate = i;
+ }
+ }
+#ifdef notdef
+ printf("metrics[%d] = %d state = %lx\n",beststate,
+ state[beststate].metric,state[beststate].path);
+#endif
+ *data++ = state[beststate].path >> 24;
+ }
+
+ }
+ /* Output remaining bits from 0 state */
+ // ETTUS Find best state instead
bestmetric = state[0].metric;
beststate = 0;
for(i=1;i<64;i++){
- if(state[i].metric > bestmetric){
- bestmetric = state[i].metric;
- beststate = i;
- }
+ if(state[i].metric > bestmetric){
+ bestmetric = state[i].metric;
+ beststate = i;
+ }
}
-#ifdef notdef
- printf("metrics[%d] = %d state = %lx\n",beststate,
- state[beststate].metric,state[beststate].path);
-#endif
+ if((i = bitcnt % 8) != 6)
+ state[beststate].path <<= 6-i;
+
*data++ = state[beststate].path >> 24;
+ *data++ = state[beststate].path >> 16;
+ *data++ = state[beststate].path >> 8;
+ *data = state[beststate].path;
+ //printf ("BS = %d\tBSM = %d\tM0 = %d\n",beststate,state[beststate].metric,state[0].metric);
+ *metric = state[beststate].metric;
+ return 0;
}
- }
- /* Output remaining bits from 0 state */
- // ETTUS Find best state instead
- bestmetric = state[0].metric;
- beststate = 0;
- for(i=1;i<64;i++){
- if(state[i].metric > bestmetric){
- bestmetric = state[i].metric;
- beststate = i;
+
+ void
+ viterbi_chunks_init(struct viterbi_state* state) {
+ // Initialize starting metrics to prefer 0 state
+ int i;
+ state[0].metric = 0;
+ state[0].path = 0;
+ for(i=1;i<64;i++)
+ state[i].metric = -999999;
}
- }
- if((i = bitcnt % 8) != 6)
- state[beststate].path <<= 6-i;
-
- *data++ = state[beststate].path >> 24;
- *data++ = state[beststate].path >> 16;
- *data++ = state[beststate].path >> 8;
- *data = state[beststate].path;
- //printf ("BS = %d\tBSM = %d\tM0 = %d\n",beststate,state[beststate].metric,state[0].metric);
- *metric = state[beststate].metric;
- return 0;
-}
+ void
+ viterbi_butterfly8(unsigned char *symbols, int mettab[2][256], struct viterbi_state *state0, struct viterbi_state *state1)
+ {
+ unsigned int bitcnt;
+ int mets[4];
-void
-viterbi_chunks_init(struct viterbi_state* state) {
- // Initialize starting metrics to prefer 0 state
- int i;
- state[0].metric = 0;
- state[0].path = 0;
- for(i=1;i<64;i++)
- state[i].metric = -999999;
-}
+ struct viterbi_state *state, *next;
+ state = state0;
+ next = state1;
+ // Operate on 16 symbols (8 bits) at a time
+ for(bitcnt = 0;bitcnt < 8;bitcnt++){
+ // Read input symbol pair and compute all possible branch metrics
+ mets[0] = mettab[0][symbols[0]] + mettab[0][symbols[1]];
+ mets[1] = mettab[0][symbols[0]] + mettab[1][symbols[1]];
+ mets[2] = mettab[1][symbols[0]] + mettab[0][symbols[1]];
+ mets[3] = mettab[1][symbols[0]] + mettab[1][symbols[1]];
+ symbols += 2;
+
+ // These macro calls were generated by genbut.c
+ BUTTERFLY(0,0);BUTTERFLY(1,1);BUTTERFLY(2,3);BUTTERFLY(3,2);
+ BUTTERFLY(4,3);BUTTERFLY(5,2);BUTTERFLY(6,0);BUTTERFLY(7,1);
+ BUTTERFLY(8,0);BUTTERFLY(9,1);BUTTERFLY(10,3);BUTTERFLY(11,2);
+ BUTTERFLY(12,3);BUTTERFLY(13,2);BUTTERFLY(14,0);BUTTERFLY(15,1);
+ BUTTERFLY(16,2);BUTTERFLY(17,3);BUTTERFLY(18,1);BUTTERFLY(19,0);
+ BUTTERFLY(20,1);BUTTERFLY(21,0);BUTTERFLY(22,2);BUTTERFLY(23,3);
+ BUTTERFLY(24,2);BUTTERFLY(25,3);BUTTERFLY(26,1);BUTTERFLY(27,0);
+ BUTTERFLY(28,1);BUTTERFLY(29,0);BUTTERFLY(30,2);BUTTERFLY(31,3);
+
+ // Swap current and next states
+ if(bitcnt & 1){
+ state = state0;
+ next = state1;
+ } else {
+ state = state1;
+ next = state0;
+ }
+ }
+ }
+
+ void
+ viterbi_butterfly2(unsigned char *symbols, int mettab[2][256], struct viterbi_state *state0, struct viterbi_state *state1)
+ {
+ //unsigned int bitcnt;
+ int mets[4];
-void
-viterbi_butterfly8(unsigned char *symbols, int mettab[2][256], struct viterbi_state *state0, struct viterbi_state *state1)
-{
- unsigned int bitcnt;
- int mets[4];
-
- struct viterbi_state *state, *next;
- state = state0;
- next = state1;
- // Operate on 16 symbols (8 bits) at a time
- for(bitcnt = 0;bitcnt < 8;bitcnt++){
- // Read input symbol pair and compute all possible branch metrics
- mets[0] = mettab[0][symbols[0]] + mettab[0][symbols[1]];
- mets[1] = mettab[0][symbols[0]] + mettab[1][symbols[1]];
- mets[2] = mettab[1][symbols[0]] + mettab[0][symbols[1]];
- mets[3] = mettab[1][symbols[0]] + mettab[1][symbols[1]];
- symbols += 2;
-
- // These macro calls were generated by genbut.c
- BUTTERFLY(0,0);BUTTERFLY(1,1);BUTTERFLY(2,3);BUTTERFLY(3,2);
- BUTTERFLY(4,3);BUTTERFLY(5,2);BUTTERFLY(6,0);BUTTERFLY(7,1);
- BUTTERFLY(8,0);BUTTERFLY(9,1);BUTTERFLY(10,3);BUTTERFLY(11,2);
- BUTTERFLY(12,3);BUTTERFLY(13,2);BUTTERFLY(14,0);BUTTERFLY(15,1);
- BUTTERFLY(16,2);BUTTERFLY(17,3);BUTTERFLY(18,1);BUTTERFLY(19,0);
- BUTTERFLY(20,1);BUTTERFLY(21,0);BUTTERFLY(22,2);BUTTERFLY(23,3);
- BUTTERFLY(24,2);BUTTERFLY(25,3);BUTTERFLY(26,1);BUTTERFLY(27,0);
- BUTTERFLY(28,1);BUTTERFLY(29,0);BUTTERFLY(30,2);BUTTERFLY(31,3);
-
- // Swap current and next states
- if(bitcnt & 1){
+ struct viterbi_state *state, *next;
state = state0;
next = state1;
- } else {
+ // Operate on 4 symbols (2 bits) at a time
+
+ // Read input symbol pair and compute all possible branch metrics
+ mets[0] = mettab[0][symbols[0]] + mettab[0][symbols[1]];
+ mets[1] = mettab[0][symbols[0]] + mettab[1][symbols[1]];
+ mets[2] = mettab[1][symbols[0]] + mettab[0][symbols[1]];
+ mets[3] = mettab[1][symbols[0]] + mettab[1][symbols[1]];
+
+ // These macro calls were generated by genbut.c
+ BUTTERFLY(0,0);BUTTERFLY(1,1);BUTTERFLY(2,3);BUTTERFLY(3,2);
+ BUTTERFLY(4,3);BUTTERFLY(5,2);BUTTERFLY(6,0);BUTTERFLY(7,1);
+ BUTTERFLY(8,0);BUTTERFLY(9,1);BUTTERFLY(10,3);BUTTERFLY(11,2);
+ BUTTERFLY(12,3);BUTTERFLY(13,2);BUTTERFLY(14,0);BUTTERFLY(15,1);
+ BUTTERFLY(16,2);BUTTERFLY(17,3);BUTTERFLY(18,1);BUTTERFLY(19,0);
+ BUTTERFLY(20,1);BUTTERFLY(21,0);BUTTERFLY(22,2);BUTTERFLY(23,3);
+ BUTTERFLY(24,2);BUTTERFLY(25,3);BUTTERFLY(26,1);BUTTERFLY(27,0);
+ BUTTERFLY(28,1);BUTTERFLY(29,0);BUTTERFLY(30,2);BUTTERFLY(31,3);
+
state = state1;
next = state0;
+
+ // Read input symbol pair and compute all possible branch metrics
+ mets[0] = mettab[0][symbols[2]] + mettab[0][symbols[3]];
+ mets[1] = mettab[0][symbols[2]] + mettab[1][symbols[3]];
+ mets[2] = mettab[1][symbols[2]] + mettab[0][symbols[3]];
+ mets[3] = mettab[1][symbols[2]] + mettab[1][symbols[3]];
+
+ // These macro calls were generated by genbut.c
+ BUTTERFLY(0,0);BUTTERFLY(1,1);BUTTERFLY(2,3);BUTTERFLY(3,2);
+ BUTTERFLY(4,3);BUTTERFLY(5,2);BUTTERFLY(6,0);BUTTERFLY(7,1);
+ BUTTERFLY(8,0);BUTTERFLY(9,1);BUTTERFLY(10,3);BUTTERFLY(11,2);
+ BUTTERFLY(12,3);BUTTERFLY(13,2);BUTTERFLY(14,0);BUTTERFLY(15,1);
+ BUTTERFLY(16,2);BUTTERFLY(17,3);BUTTERFLY(18,1);BUTTERFLY(19,0);
+ BUTTERFLY(20,1);BUTTERFLY(21,0);BUTTERFLY(22,2);BUTTERFLY(23,3);
+ BUTTERFLY(24,2);BUTTERFLY(25,3);BUTTERFLY(26,1);BUTTERFLY(27,0);
+ BUTTERFLY(28,1);BUTTERFLY(29,0);BUTTERFLY(30,2);BUTTERFLY(31,3);
}
- }
-}
-void
-viterbi_butterfly2(unsigned char *symbols, int mettab[2][256], struct viterbi_state *state0, struct viterbi_state *state1)
-{
- //unsigned int bitcnt;
- int mets[4];
-
- struct viterbi_state *state, *next;
- state = state0;
- next = state1;
- // Operate on 4 symbols (2 bits) at a time
-
- // Read input symbol pair and compute all possible branch metrics
- mets[0] = mettab[0][symbols[0]] + mettab[0][symbols[1]];
- mets[1] = mettab[0][symbols[0]] + mettab[1][symbols[1]];
- mets[2] = mettab[1][symbols[0]] + mettab[0][symbols[1]];
- mets[3] = mettab[1][symbols[0]] + mettab[1][symbols[1]];
-
- // These macro calls were generated by genbut.c
- BUTTERFLY(0,0);BUTTERFLY(1,1);BUTTERFLY(2,3);BUTTERFLY(3,2);
- BUTTERFLY(4,3);BUTTERFLY(5,2);BUTTERFLY(6,0);BUTTERFLY(7,1);
- BUTTERFLY(8,0);BUTTERFLY(9,1);BUTTERFLY(10,3);BUTTERFLY(11,2);
- BUTTERFLY(12,3);BUTTERFLY(13,2);BUTTERFLY(14,0);BUTTERFLY(15,1);
- BUTTERFLY(16,2);BUTTERFLY(17,3);BUTTERFLY(18,1);BUTTERFLY(19,0);
- BUTTERFLY(20,1);BUTTERFLY(21,0);BUTTERFLY(22,2);BUTTERFLY(23,3);
- BUTTERFLY(24,2);BUTTERFLY(25,3);BUTTERFLY(26,1);BUTTERFLY(27,0);
- BUTTERFLY(28,1);BUTTERFLY(29,0);BUTTERFLY(30,2);BUTTERFLY(31,3);
-
- state = state1;
- next = state0;
-
- // Read input symbol pair and compute all possible branch metrics
- mets[0] = mettab[0][symbols[2]] + mettab[0][symbols[3]];
- mets[1] = mettab[0][symbols[2]] + mettab[1][symbols[3]];
- mets[2] = mettab[1][symbols[2]] + mettab[0][symbols[3]];
- mets[3] = mettab[1][symbols[2]] + mettab[1][symbols[3]];
-
- // These macro calls were generated by genbut.c
- BUTTERFLY(0,0);BUTTERFLY(1,1);BUTTERFLY(2,3);BUTTERFLY(3,2);
- BUTTERFLY(4,3);BUTTERFLY(5,2);BUTTERFLY(6,0);BUTTERFLY(7,1);
- BUTTERFLY(8,0);BUTTERFLY(9,1);BUTTERFLY(10,3);BUTTERFLY(11,2);
- BUTTERFLY(12,3);BUTTERFLY(13,2);BUTTERFLY(14,0);BUTTERFLY(15,1);
- BUTTERFLY(16,2);BUTTERFLY(17,3);BUTTERFLY(18,1);BUTTERFLY(19,0);
- BUTTERFLY(20,1);BUTTERFLY(21,0);BUTTERFLY(22,2);BUTTERFLY(23,3);
- BUTTERFLY(24,2);BUTTERFLY(25,3);BUTTERFLY(26,1);BUTTERFLY(27,0);
- BUTTERFLY(28,1);BUTTERFLY(29,0);BUTTERFLY(30,2);BUTTERFLY(31,3);
-}
+ unsigned char
+ viterbi_get_output(struct viterbi_state *state, unsigned char *outbuf) {
+ // Produce output every 8 bits once path memory is full
+ // if((bitcnt % 8) == 5 && bitcnt > 32) {
-unsigned char
-viterbi_get_output(struct viterbi_state *state, unsigned char *outbuf) {
- // Produce output every 8 bits once path memory is full
- // if((bitcnt % 8) == 5 && bitcnt > 32) {
-
- // Find current best path
- unsigned int i,beststate;
- int bestmetric;
-
- bestmetric = state[0].metric;
- beststate = 0;
- for(i=1;i<64;i++)
- if(state[i].metric > bestmetric) {
- bestmetric = state[i].metric;
- beststate = i;
+ // Find current best path
+ unsigned int i,beststate;
+ int bestmetric;
+
+ bestmetric = state[0].metric;
+ beststate = 0;
+ for(i=1;i<64;i++)
+ if(state[i].metric > bestmetric) {
+ bestmetric = state[i].metric;
+ beststate = i;
+ }
+ *outbuf = state[beststate].path >> 24;
+ return bestmetric;
}
- *outbuf = state[beststate].path >> 24;
- return bestmetric;
-}
-//printf ("BS = %d\tBSM = %d\tM0 = %d\n",beststate,state[beststate].metric,state[0].metric);
-// In tail, poison non-zero nodes
-//if(bits_out > packet_size-7)
-// for(i=1;i<64;i += 2)
-// state[i].metric = -9999999;
+ //printf ("BS = %d\tBSM = %d\tM0 = %d\n",beststate,state[beststate].metric,state[0].metric);
+ // In tail, poison non-zero nodes
+ //if(bits_out > packet_size-7)
+ // for(i=1;i<64;i += 2)
+ // state[i].metric = -9999999;
+ }
+}