Esempio n. 1
0
static double gain_interp(double gain, boost::array<double, 17> db_vector, boost::array<double, 17> volts_vector) {
    double volts;
    gain = uhd::clip<double>(gain, db_vector.front(), db_vector.back()); //let's not get carried away here

    boost::uint8_t gain_step = 0;
    //find which bin we're in
    for(size_t i = 0; i < db_vector.size()-1; i++) {
        if(gain >= db_vector[i] && gain <= db_vector[i+1]) gain_step = i;
    }

    //find the current slope for linear interpolation
    double slope = (volts_vector[gain_step + 1] - volts_vector[gain_step])
                / (db_vector[gain_step + 1] - db_vector[gain_step]);

    //the problem here is that for gains approaching the maximum, the voltage slope becomes infinite
    //i.e., a small change in gain requires an infinite change in voltage
    //to cope, we limit the slope

    if(slope == std::numeric_limits<double>::infinity())
        return volts_vector[gain_step];

    //use the volts per dB slope to find the final interpolated voltage
    volts = volts_vector[gain_step] + (slope * (gain - db_vector[gain_step]));

    UHD_LOGV(often) << "Gain interp: gain: " << gain << ", gain_step: " << int(gain_step) << ", slope: " << slope << ", volts: " << volts << std::endl;

    return volts;
}
Esempio n. 2
0
static uhd::dict<std::string, gain_range_t> get_tvrx_gain_ranges(void) {
    double rfmax = 0.0, rfmin = FLT_MAX;
    BOOST_FOREACH(const std::string range, tvrx_rf_gains_db.keys()) {
        double my_max = tvrx_rf_gains_db[range].back(); //we're assuming it's monotonic
        double my_min = tvrx_rf_gains_db[range].front(); //if it's not this is wrong wrong wrong
        if(my_max > rfmax) rfmax = my_max;
        if(my_min < rfmin) rfmin = my_min;
    }

    double ifmin = tvrx_if_gains_db.front();
    double ifmax = tvrx_if_gains_db.back();

    return map_list_of
        ("RF", gain_range_t(rfmin, rfmax, (rfmax-rfmin)/4096.0))
        ("IF", gain_range_t(ifmin, ifmax, (ifmax-ifmin)/4096.0))
    ;
}