root/experimental/components/SymbolSyncPoly/autotest_sources/SymbolSyncPoly_testsuite.h @ 3790

Revision 3790, 9.4 KB (checked in by jgaeddert, 6 years ago)

adding new test to SymbolSyncPoly DSP; method to change loop filter bandwidth

Line 
1#ifndef __SYMBOLSYNCPOLYDSPTEST_H
2#define __SYMBOLSYNCPOLYDSPTEST_H
3
4#include <cxxtest/TestSuite.h>
5#include "src/SymbolSyncPolyDSP.h"
6#include "I_in_rrc_qpsk_N512_dT0_dF0_k4_m4_b025_Npfb32.h"
7#include "Q_in_rrc_qpsk_N512_dT0_dF0_k4_m4_b025_Npfb32.h"
8#include "msg_i_rrc_qpsk_N512_dT0_dF0_k4_m4_b025_Npfb32.h"
9#include "msg_q_rrc_qpsk_N512_dT0_dF0_k4_m4_b025_Npfb32.h"
10
11#include "test_02.h"
12#include "test_03.h"
13
14//
15// A simple test suite: Just inherit CxxTest::TestSuite and write tests!
16//
17
18unsigned int CountSymbolErrors( short * msg_in_i,
19        short * msg_in_q,
20        short * msg_out_i,
21        short * msg_out_q,
22        short tol,
23        unsigned int N)
24{
25    unsigned int num_errors(0);
26    for (unsigned int i=0; i<N; i++) {
27        if ( abs(msg_in_i[i]-msg_out_i[i]) > tol && abs(msg_in_q[i]-msg_out_q[i]) > tol )
28            num_errors++;
29    }
30    return num_errors;
31}
32
33
34// NOTE: " : public CxxTest::TestSuite" must be on the same line as the class
35//       definition, otherwise the python script does not recognize it
36//       as a test class
37class SymbolSyncPoly_testsuite1 : public CxxTest::TestSuite,
38    public SymbolSyncPolyDSP
39{
40public:
41
42    void test1() {
43        // initialize variables
44        mf_i  = -10;
45        dmf_i =  10;
46        mf_q  =  10;
47        dmf_q =  10;
48        GenerateTimingErrorSignal();
49        TS_ASSERT_DELTA( q, 0.0f/(Ac*Ac), 1e-6f );
50    }
51
52    void test2() {
53        // initialize variables
54        mf_i  =  30;
55        dmf_i =  5;
56        mf_q  =  20;
57        dmf_q =  1;
58        GenerateTimingErrorSignal();
59        TS_ASSERT_DELTA( q, -85.0f/(Ac*Ac), 1e-12f );
60    }
61
62};
63
64
65class SymbolSyncPoly_testsuite_ComputeFilterBankIndex : public CxxTest::TestSuite,
66    public SymbolSyncPolyDSP
67{
68  public:
69    void testShift() {
70        // Normal operation
71        Npfb = 32;
72        b_soft = 11.0f;
73        ComputeFilterBankIndex();
74        TS_ASSERT_EQUALS( b, 11 );
75        TS_ASSERT_DELTA( b_soft, 11.0f, 0.0001f );
76        TS_ASSERT_EQUALS( lc, SHIFT );
77    }
78
79    void testStuff() {
80        // Filter bank overflow
81        Npfb = 32;
82        b_soft = 32.1f;
83        ComputeFilterBankIndex();
84        TS_ASSERT_EQUALS( b, 0 );
85        TS_ASSERT_DELTA( b_soft, 0.1f, 0.0001f );
86        TS_ASSERT_EQUALS( lc, STUFF );
87    }
88
89    void testSkip() {
90        // Filter bank underflow
91        Npfb = 32;
92        b_soft = -2.1f;
93        ComputeFilterBankIndex();
94        TS_ASSERT_EQUALS( b, 30 );
95        TS_ASSERT_DELTA( b_soft, 29.9f, 0.0001f );
96        TS_ASSERT_EQUALS( lc, SKIP );
97    }
98
99};
100
101/** \brief Test suite for SymbolSyncPolyDSP class
102 *
103 * In here we perform robust testing of the synchonization mechanism
104 * using different configurations and input vectors
105 */
106class SymbolSyncPoly_symboltestsuite: public CxxTest::TestSuite
107{
108public:
109
110    ///\Basic test case for SynchronizeAndDecimate. No symbol offsets or timing errors
111    void xtestBasicSynchronization()
112    {
113        SymbolSyncPolyDSP symbolSync;
114        ///The following input buffers and expected results are defined in header files
115        ///float nominal_test_vector_I, nominal_test_vector_Q;
116        ///short nominal_expected_results_I, nominal_expected_results_Q;
117
118        //float to short conversion
119        //float max_float_value = 3;   //double check this value later if signal is noisy
120        short max_short_value = 10000;//32767;
121        //float tmp_float;
122        unsigned int N_in = 512; //This number must match with the lenght of the input buffer
123        short* nominal_test_vector_I_short = new short[N_in];
124        short* nominal_test_vector_Q_short = new short[N_in];
125        for(unsigned int i =0 ; i < N_in; i++){
126            //tmp_float = nominal_test_vector_I[i];// / max_float_value; //gives a value between 0 and 1
127            nominal_test_vector_I_short[i] = (short) (nominal_test_vector_I[i] * max_short_value);
128
129            //tmp_float = nominal_test_vector_Q[i];// / max_float_value; //gives a value between 0 and 1
130            nominal_test_vector_Q_short[i] = (short) (nominal_test_vector_Q[i] * max_short_value);
131        }
132
133        ///Init variables shall match the values used in MATLAB to get the test vectors and
134        ///expected result
135        char type[] = "rrcos";  ///< filter type
136        unsigned int k = 2;        ///< samples per symbol
137        unsigned int m = 4;        ///< symbol delay
138        float beta = .25;        ///< rolloff factor
139        unsigned int Npfb = 32;    ///< polyphse filter bank size
140
141        unsigned int N_out = N_in/k + 2; //Need some buffer for mismatched samples per symbol
142        short* systemOutputI = new short[N_out];
143        short* systemOutputQ = new short[N_out];
144
145
146        symbolSync.ConfigureFilterBank(type, k, m, beta, Npfb);
147
148        //send test data
149        symbolSync.SynchronizeAndDecimate(  nominal_test_vector_I_short,
150                                            nominal_test_vector_Q_short,
151                                            N_in,
152                                            systemOutputI,
153                                            systemOutputQ,
154                                            N_out);
155
156        std::cout << std::endl << "testBasicSynchronization:" << std::endl;
157        std::cout << N_in << " Input samples and " << N_out << " Output symbols" << std::endl;   
158        //hard decision to see if we recovered the message correctly
159        for(unsigned int i = 0; i<N_out; i++){
160            systemOutputI[i] = (systemOutputI[i] < 0)? -1 : 1;
161            systemOutputQ[i] = (systemOutputQ[i] < 0)? -1 : 1;
162        }
163
164        //verify
165        TS_ASSERT_SAME_DATA(&systemOutputI[m],
166                            nominal_expected_results_I,
167                            (N_out - m)*sizeof(short));
168
169        TS_ASSERT_SAME_DATA(&systemOutputQ[m],
170                            nominal_expected_results_Q,
171                            (N_out - m)*sizeof(short));
172
173        delete [] systemOutputI;
174        delete [] systemOutputQ;
175        delete [] nominal_test_vector_I_short;
176        delete [] nominal_test_vector_Q_short;
177    }
178
179    // test_02
180    void testSymbolSynchronizationTimingOffset_02()
181    {
182        std::cout << std::endl << "testSymbolSynchronizationTimingOffset_02" << std::endl;
183        SymbolSyncPolyDSP symbolSync;
184
185        // Init variables shall match the values used in MATLAB to get the test vectors and
186        // expected result
187        unsigned int N_out_02 = N_in_02;
188
189        //Need some buffer for mismatched samples per symbol
190        short* I_out_02 = new short[N_out_02];
191        short* Q_out_02 = new short[N_out_02];
192        memset( I_out_02, 0, N_out_02*sizeof(short) );
193        memset( Q_out_02, 0, N_out_02*sizeof(short) );
194
195        symbolSync.ConfigureFilterBank(type_02, k_02, m_02, beta_02, Npfb_02);
196        symbolSync.UpdateTimingLoopFilterCoefficients(alpha_s_02, beta_s_02);
197
198        //send test data
199        symbolSync.SynchronizeAndDecimate(
200            I_in_02,
201            Q_in_02,
202            N_in_02,
203            I_out_02,
204            Q_out_02,
205            N_out_02);
206
207        //hard decision to see if we recovered the message correctly
208        unsigned int num_correct_symbols(0);
209        short t_min = short(Ac_02 / sqrtf(2) * 0.5);      // minimum threshold
210        short t_max = short(Ac_02 / sqrtf(2) * 1.5);    // maximum threshold
211        for(unsigned int i = 0; i<N_out_02; i++){
212            if ( abs(I_out_02[i])>t_min && abs(I_out_02[i])<t_max &&
213                 abs(Q_out_02[i])>t_min && abs(Q_out_02[i])<t_max )
214                num_correct_symbols++;
215            //std::cout << "  " << I_out_02[i] << "  " << Q_out_02[i] << std::endl;
216        }
217
218        std::cout << "num_correct_symbols : " << num_correct_symbols << std::endl;
219
220        TS_ASSERT(num_correct_symbols > 200);
221
222        delete [] I_out_02;
223        delete [] Q_out_02;
224    }
225
226
227    // test_03
228    void testSymbolSynchronizationTimingOffset_03()
229    {
230        std::cout << std::endl << "testSymbolSynchronizationTimingOffset_03" << std::endl;
231        SymbolSyncPolyDSP symbolSync;
232
233        // Init variables shall match the values used in MATLAB to get the test vectors and
234        // expected result
235        unsigned int N_out_03 = N_in_03;
236
237        //Need some buffer for mismatched samples per symbol
238        short* I_out_03 = new short[N_out_03];
239        short* Q_out_03 = new short[N_out_03];
240        memset( I_out_03, 0, N_out_03*sizeof(short) );
241        memset( Q_out_03, 0, N_out_03*sizeof(short) );
242
243        symbolSync.ConfigureFilterBank(type_03, k_03, m_03, beta_03, Npfb_03);
244        symbolSync.UpdateTimingLoopFilterCoefficients(alpha_s_03, beta_s_03);
245
246        //send test data
247        symbolSync.SynchronizeAndDecimate(
248            I_in_03,
249            Q_in_03,
250            N_in_03,
251            I_out_03,
252            Q_out_03,
253            N_out_03);
254
255        // hard decision to see if we recovered the message correctly
256        unsigned int num_errors_2_percent;
257        num_errors_2_percent =
258            CountSymbolErrors(I_out_03+m_03-1, Q_out_03+m_03-1, msg_i_03, msg_q_03, Ac_03/50, N_out_03-m_03);
259        std::cout << "  num errors outside 2% tolerance = " << num_errors_2_percent << std::endl;
260        TS_ASSERT(num_errors_2_percent < 50);
261       
262        unsigned int num_errors_5_percent;
263        num_errors_5_percent =
264            CountSymbolErrors(I_out_03+m_03-1, Q_out_03+m_03-1, msg_i_03, msg_q_03, Ac_03/20, N_out_03-m_03);
265        std::cout << "  num errors outside 5% tolerance = " << num_errors_5_percent << std::endl;
266        TS_ASSERT(num_errors_5_percent < 20);
267
268        delete [] I_out_03;
269        delete [] Q_out_03;
270    }
271
272};
273
274#endif
275
Note: See TracBrowser for help on using the browser.