root/ossiedev/branches/0.7.x/components/Interpolator/Interpolator.cpp @ 9211

Revision 9211, 13.1 KB (checked in by mcarrick, 4 years ago)

merging deepan's branch: adding wavedash tool, updating query / configure methods for components

  • Property svn:eol-style set to native
RevLine 
[1468]1/****************************************************************************
2
[3988]3Copyright 2006, 2007 Virginia Polytechnic Institute and State University
[1468]4
[8586]5This file is part of the OSSIE Interpolator.
[1468]6
[8586]7OSSIE Interpolator is free software; you can redistribute it and/or modify
[1468]8it under the terms of the GNU General Public License as published by
9the Free Software Foundation; either version 2 of the License, or
10(at your option) any later version.
11
[8586]12OSSIE Interpolator is distributed in the hope that it will be useful,
[1468]13but WITHOUT ANY WARRANTY; without even the implied warranty of
14MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15GNU General Public License for more details.
16
17You should have received a copy of the GNU General Public License
[8586]18along with OSSIE Interpolator; if not, write to the Free Software
[1468]19Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
20
21****************************************************************************/
22
23
24#include <iostream>
25
[2573]26#include "ossie/debug.h"
27
[8586]28#include "Interpolator.h"
[1468]29
[8586]30Interpolator_i::Interpolator_i(const char *uuid, omni_condition *con) :
[4741]31    Resource_impl(uuid),
32    component_running(con),
33    createDynamicFilter(false),
34    isConfigured_pulseShape(false),
35    isConfigured_k(false),
36    isConfigured_m(false),
37    isConfigured_beta(false)
[1468]38{
[1477]39    previous_length = 0;
[1468]40
[8586]41    dataIn = new standardInterfaces_i::complexShort_p("inData");
42    dataOut = new standardInterfaces_i::complexShort_u("outData");
[1468]43
44    // Start the run_interpolation thread
[2135]45    processing_thread = new omni_thread(do_run_interpolation, (void *) this);
[1468]46    processing_thread->start();
47
[1477]48    // Interpolation factor
49    M = 1;
50
[1476]51    // Filter
52    len_h = 1;
53    h = new float[len_h];
54
55    h[0] = 1.0;
56
[2141]57    i_filter = new SigProc::fir_filter(h, len_h);
58    q_filter = new SigProc::fir_filter(h, len_h);
[1476]59
[1468]60}                                 
61                                 
62
[8586]63Interpolator_i::~Interpolator_i(void)
[1468]64{
[2135]65    delete dataIn;
66    delete dataOut;
[2188]67
[5601]68#ifdef INTERP_LOGGING
[2188]69    delete in_data;
70    delete out_data;
[5601]71#endif
[1468]72}
73
[8586]74CORBA::Object_ptr Interpolator_i::getPort( const char* portName) throw (CORBA::SystemException, CF::PortSupplier::UnknownPort)
[1468]75{
[8586]76    DEBUG(4, Interpolator, "Interpolator getPort() called with: " << portName);
[1468]77
[2135]78    CORBA::Object_var p;
[1468]79
[2135]80    p = dataIn->getPort(portName);
81
82    if (!CORBA::is_nil(p))
[4741]83        return p._retn();
[2135]84
85    p = dataOut->getPort(portName);
86
87    if (!CORBA::is_nil(p))
[4741]88        return p._retn();
[2135]89
90    throw CF::PortSupplier::UnknownPort();
[1468]91}
92
[8586]93void Interpolator_i::start() throw (CORBA::SystemException, CF::Resource::StartError)
[1468]94{
[8586]95    DEBUG(3, Interpolator, "Interpolator start() called")
[1468]96}
97
[8586]98void Interpolator_i::stop() throw (CORBA::SystemException, CF::Resource::StopError)
[1468]99{
[8586]100    DEBUG(3, Interpolator, "Interpolator stop() called")
[1468]101}
102
[8586]103void Interpolator_i::releaseObject() throw (CORBA::SystemException, CF::LifeCycle::ReleaseError)
[1468]104{
[8586]105    DEBUG(3, Interpolator, "In releaseObject.");
[1468]106    component_running->signal();
[8586]107    DEBUG(3, Interpolator, "Leaving releaseObject.");
[4077]108 }
[1468]109
[8586]110void Interpolator_i::initialize() throw (CF::LifeCycle::InitializeError, CORBA::SystemException)
[1468]111{
[5601]112#ifdef INTERP_LOGGING
[2193]113    out_data = new SigProc::dump_data("out_interp.dat", 0, 100000);
[5601]114#endif
[2188]115
[1468]116}
117
[9211]118void
119Interpolator_i::query (CF::Properties & configProperties)
120throw (CORBA::SystemException, CF::UnknownProperties)
121{
122    // for queries of zero length, return all id/value pairs in propertySet
123    if (configProperties.length () == 0)
124    {   
125        configProperties.length (propertySet.length ());
126        for (unsigned int i = 0; i < propertySet.length (); i++)
127        {
128            configProperties[i].id = CORBA::string_dup (propertySet[i].id);
129            configProperties[i].value = propertySet[i].value;
130        }
131
132        return ;
133    }   
134    else {
135        for (unsigned int i = 0; i < configProperties.length(); i++) {
136            for (unsigned int j=0; j < propertySet.length(); j++) {
137                if ( strcmp(configProperties[i].id, propertySet[i].id) == 0 ){
138                    configProperties[i].value = propertySet[i].value;
139               }
140            }
141        }
142    }   
143}
144
145
[8586]146void Interpolator_i::configure(const CF::Properties& props) throw (CORBA::SystemException, CF::PropertySet::InvalidConfiguration, CF::PropertySet::PartialConfiguration)
[1468]147{
[9211]148        static int init = 0;
149
[8586]150    DEBUG(3, Interpolator, "Interpolator configure() called")
[4741]151       
[8586]152    DEBUG(3, Interpolator, "Props length : " << props.length())
[9211]153       
154    std::cout << "Component - Interpolator" << std::endl;
155    if (init == 0){
156        std::cout << "INTERPOLATOR - initial configure call .." << std::endl;
157        if ( props.length() <= 0 ){
158            std::cout << "Interpolator: configure called with invalid \
159                          props.length() - " << props.length() << std::endl;
160            return;
161        }
162        propertySet.length(props.length());
163        for (unsigned int i=0; i < props.length(); i++) {
164            std::cout << "Property Id : " << props[i].id << std::endl;
165            propertySet[i].id = CORBA::string_dup(props[i].id);
166            propertySet[i].value = props[i].value;
167        }
168        init = 1;
169        return;
170    }
171    else {
172                for (unsigned int i = 0; i < props.length(); i++) {
173                    DEBUG(3, Interpolator, "Property id : " << props[i].id)
[1476]174
[9211]175                    if (strcmp(props[i].id, "DCE:e5c1d4aa-4b7f-48b7-b3bf-ed90b7653bec") == 0) {
176                        // InterpFactor property, sets the interpolation factor
177                        CORBA::UShort D;
178                        props[i].value >>= D;
[1476]179
[9211]180                        omni_mutex_lock l(accessPrivateData);
[2199]181
[9211]182                        M = D;
[2199]183
[9211]184                std::cout << "Property id : " << props[i].id << std::endl;
185                // Update value of this property in propertySet also
186                for (unsigned int j=0; j < propertySet.length(); j++ ) {
187                    if ( strcmp(propertySet[j].id, props[i].id) == 0 ) {
188                        propertySet[i].value = props[i].value;
189                        break;
190                    }
191                }
[1476]192
[2199]193
[9211]194                        DEBUG(3, Interpolator, "Interpolation factor set to " << M)
195                        std::cout << std::endl << "INTERP: k = " << M << std::endl;
196                        isConfigured_k = true;
197                    } else if (strcmp(props[i].id, "DCE:9c39de73-54d4-43ad-ab9d-52f5fa526ddf") == 0) {
198                        // filter property, Filter coefficients
199                        CORBA::FloatSeq *coeff_ptr;
200                        props[i].value >>= coeff_ptr;
[1476]201
[9211]202                        omni_mutex_lock l(accessPrivateData);
[1476]203
[9211]204                        len_h = coeff_ptr->length();
205
206                        if ( len_h > 1 ) {
207                            delete []h;
208                            delete i_filter;
209                            delete q_filter;
210
211                            h = new float[len_h];
212                            DEBUG(3, Interpolator, "Interpolator filter length = " << len_h)
213                            for (unsigned int i = 0; i < len_h; i++) {
214                                h[i] = (*coeff_ptr)[i];
215                                //DEBUG(4, Interpolator, "Coeff[" << i << "] = " << h[i])
216                                printf("g(%d) = %f;\n", i+1, h[i]);
217                            }
218                            i_filter = new SigProc::fir_filter(h, len_h);
219                            q_filter = new SigProc::fir_filter(h, len_h);
220
221                        std::cout << "Property id : " << props[i].id << std::endl;
222                        // Update value of this property in propertySet also
223                        for (unsigned int j=0; j < propertySet.length(); j++ ) {
224                            if ( strcmp(propertySet[j].id, props[i].id) == 0 ) {
225                                propertySet[i].value = props[i].value;
226                                break;
227                            }
228                        }
229
230
231                        } else {
232                            // Design filter dynamically
233                            createDynamicFilter = true;
234                        }
235
236                    } else if (strcmp(props[i].id, "DCE:e65ba870-4c11-11dc-9470-00123f63025f") == 0) {
237                        // pulse shape
238                        const char * prop_str;
239                        props[i].value >>= prop_str;
240
241                        // Set appropriate pulse shape
242                        if ( strcmp(prop_str, "rrcos") == 0 ) {
243                            pulseShape = "rrcos";
244                            ///\todo: create function pointer for filter design
245                        } else {
246                            // unknown pulse shape
247                            std::cerr << "ERROR: Interpolator::configure() unknown pulse shape "
248                                      << prop_str << std::endl;
249                            throw CF::PropertySet::InvalidConfiguration();
250                        }
251                        isConfigured_pulseShape = true;
252
253                std::cout << "Property id : " << props[i].id << std::endl;
254                // Update value of this property in propertySet also
255                for (unsigned int j=0; j < propertySet.length(); j++ ) {
256                    if ( strcmp(propertySet[j].id, props[i].id) == 0 ) {
257                        propertySet[i].value = props[i].value;
258                        break;
259                    }
[4741]260                }
261
[9211]262                        std::cout << std::endl << "INTERP: pulse_shape = " << pulseShape << std::endl;
[1476]263
[9211]264                    } else if (strcmp(props[i].id, "DCE:f6843fdc-4c11-11dc-b0be-00123f63025f") == 0) {
265                        // m : symbol delay
266                        CORBA::UShort simple_temp;
267                        props[i].value >>= simple_temp;
268                        m = simple_temp;
269                        isConfigured_m = true;
[4741]270
[9211]271                std::cout << "Property id : " << props[i].id << std::endl;
272                // Update value of this property in propertySet also
273                for (unsigned int j=0; j < propertySet.length(); j++ ) {
274                    if ( strcmp(propertySet[j].id, props[i].id) == 0 ) {
275                        propertySet[i].value = props[i].value;
276                        break;
277                    }
278                }
[4741]279
[9211]280                        std::cout << std::endl << "INTERP: m = " << m << std::endl;
281                    } else if (strcmp(props[i].id, "DCE:fed01972-4c11-11dc-8d59-00123f63025f") == 0) {
282                        // beta : excess bandwidth factor
283                        CORBA::Float simple_temp;
284                        props[i].value >>= simple_temp;
285                        beta = simple_temp;
286                        isConfigured_beta = true;
[1476]287
[9211]288                std::cout << "Property id : " << props[i].id << std::endl;
289                // Update value of this property in propertySet also
290                for (unsigned int j=0; j < propertySet.length(); j++ ) {
291                    if ( strcmp(propertySet[j].id, props[i].id) == 0 ) {
292                        propertySet[i].value = props[i].value;
293                        break;
294                    }
295                }
[1476]296
[9211]297                        std::cout << std::endl << "INTERP: beta = " << beta << std::endl;
298                    } else {
299                        std::cerr << "Interpolator: Unknown property id " << props[i].id << std::endl;
300                        throw CF::PropertySet::InvalidConfiguration();
301                    }
302
303                }
304        }
305
[4741]306    if ( createDynamicFilter        &&
307         isConfigured_pulseShape    &&
308         isConfigured_k             &&
309         isConfigured_m             &&
310         isConfigured_beta )
311    {
312        delete []h;
313        delete i_filter;
314        delete q_filter;
[1476]315
[4741]316        ///\todo do not assume always rrcos filter
[8586]317        std::cout << "Interpolator designing new rrcos filter: "
[4741]318                  << pulseShape << ", k=" << M << ", m=" << m << ", beta=" << beta
319                  << std::endl;
[1476]320
[5057]321        len_h = 2*M*m + 1;
322        h = new float[len_h];
323        SigProc::DesignRRCFilter(M, m, beta, h);
[5287]324        for (unsigned int j=0; j<len_h; j++)
325            printf("h(%d) = %f;\n", j+1, h[j]);
[4741]326
327        i_filter = new SigProc::fir_filter(h, len_h);
328        q_filter = new SigProc::fir_filter(h, len_h);
329    }
330
[1468]331}
332
[8586]333void Interpolator_i::run_interpolation()
[1468]334{
[8586]335    DEBUG(3, Interpolator, "Interpolator run_interpolation() thread started")
[2135]336    PortTypes::ShortSequence *I_in, *Q_in;
337    PortTypes::ShortSequence I_out, Q_out;
[1468]338
[2188]339    unsigned int M_factor(M);
340    unsigned int old_M(0);
[2159]341    unsigned int old_len(0);
[1468]342
343    while (1) {
344
[8586]345        dataIn->getData(I_in, Q_in);//, metadata);
[4741]346        {
347            omni_mutex_lock l(accessPrivateData);
[1713]348
[4741]349            M_factor = M;
350        }
[2193]351
[5057]352        // Adjust MetaData tags
[8586]353/*        if ( createDynamicFilter )
[5057]354            metadata->signal_bandwidth *= (float) ( metadata->sampling_frequency * (1+beta) );
355        else
356            metadata->signal_bandwidth *= metadata->sampling_frequency;
[4741]357
[5057]358        metadata->sampling_frequency *= (float) M;
[8586]359*/
[5057]360
[2135]361        unsigned int len = I_in->length();
[4741]362        unsigned int out_idx(0);
[1468]363
[4741]364        if (len != old_len || M_factor != old_M) {
[8586]365            DEBUG(4, Interpolator, "data len or M changed.");
[4741]366            I_out.length(len * M_factor);
367            Q_out.length(len * M_factor);
368            old_len = len;
369            old_M = M_factor;
[8586]370            DEBUG(4, Interpolator, "New data len: " << len << " M: " << M);
[4741]371        }
[2154]372
[1468]373        for (unsigned int i = 0; i < len; i++) {
374
[8586]375            DEBUG(8, Interpolator, "About to filter data.");
[4741]376            i_filter->do_work(true, (*I_in)[i], I_out[out_idx]);
377            q_filter->do_work(true, (*Q_in)[i], Q_out[out_idx]);
[8586]378            DEBUG(8, Interpolator, "Done filtering data.");
[2188]379
[5601]380#ifdef INTERP_LOGGING
381            out_data->write_data(I_out[out_idx]);
382#endif
[2188]383
[4741]384            out_idx++;
[1713]385
[2135]386            for (unsigned int j = 0; j < M_factor - 1; j++) {
[1468]387
[4741]388                i_filter->do_work(true, 0, I_out[out_idx]);
389                q_filter->do_work(true, 0, Q_out[out_idx]);
[2188]390
[5601]391#ifdef INTERP_LOGGING
392                out_data->write_data(I_out[out_idx]);
393#endif
[2188]394
[1468]395                out_idx++;
396            }
[2193]397        }
[4741]398        dataIn->bufferEmptied();
[8586]399        dataOut->pushPacket(I_out, Q_out);//, *metadata);
[1468]400    }
401}
402
Note: See TracBrowser for help on using the browser.