srsLTE: AGC only uses boundaries for requesting gain to Radio

This commit is contained in:
Xavier Arteaga 2019-12-19 12:40:26 +01:00 committed by Andre Puschmann
parent 097f492430
commit c92dce71b7
19 changed files with 55 additions and 63 deletions

View File

@ -130,9 +130,9 @@ void sig_int_handler(int signo)
}
}
float srslte_rf_set_rx_gain_wrapper(void* h, float f)
static SRSLTE_AGC_CALLBACK(srslte_rf_set_rx_gain_wrapper)
{
return srslte_rf_set_rx_gain((srslte_rf_t*)h, f);
srslte_rf_set_rx_gain((srslte_rf_t*)h, gain_db);
}
int main(int argc, char** argv)

View File

@ -139,9 +139,9 @@ void sig_int_handler(int signo)
}
}
float srslte_rf_set_rx_gain_wrapper(void* h, float f)
static SRSLTE_AGC_CALLBACK(srslte_rf_set_rx_gain_wrapper)
{
return srslte_rf_set_rx_gain((srslte_rf_t*)h, f);
srslte_rf_set_rx_gain((srslte_rf_t*)h, gain_db);
}
int main(int argc, char** argv)

View File

@ -349,9 +349,9 @@ int srslte_rf_recv_wrapper(void* h, cf_t* data_[SRSLTE_MAX_PORTS], uint32_t nsam
return srslte_rf_recv_with_time_multi(h, ptr, nsamples, true, NULL, NULL);
}
float srslte_rf_set_rx_gain_th_wrapper_(void* h, float f)
static SRSLTE_AGC_CALLBACK(srslte_rf_set_rx_gain_th_wrapper_)
{
return srslte_rf_set_rx_gain_th((srslte_rf_t*)h, f);
srslte_rf_set_rx_gain_th((srslte_rf_t*)h, gain_db);
}
#endif

View File

@ -51,10 +51,10 @@ public:
virtual void set_tx_freq(const uint32_t& radio_idx, const uint32_t& channel_idx, const double& freq) = 0;
virtual void set_rx_freq(const uint32_t& radio_idx, const uint32_t& channel_idx, const double& freq) = 0;
virtual float set_rx_gain_th(const float& gain) = 0;
virtual void set_rx_gain(const uint32_t& radio_idx, const float& gain) = 0;
virtual void set_tx_srate(const uint32_t& radio_idx, const double& srate) = 0;
virtual void set_rx_srate(const uint32_t& radio_idx, const double& srate) = 0;
virtual void set_rx_gain_th(const float& gain) = 0;
virtual void set_rx_gain(const uint32_t& radio_idx, const float& gain) = 0;
virtual void set_tx_srate(const uint32_t& radio_idx, const double& srate) = 0;
virtual void set_rx_srate(const uint32_t& radio_idx, const double& srate) = 0;
// getter
virtual float get_rx_gain(const uint32_t& radio_idx) = 0;

View File

@ -37,6 +37,7 @@
#include "srslte/config.h"
#define SRSLTE_AGC_CALLBACK(NAME) void(NAME)(void* h, float gain_db)
#define SRSLTE_AGC_DEFAULT_TARGET 0.3
#define SRSLTE_AGC_DEFAULT_BW 0.7
@ -47,11 +48,12 @@ typedef struct SRSLTE_API {
float gain;
float min_gain_db;
float max_gain_db;
float default_gain_db;
float y_out;
bool lock;
bool isfirst;
void* uhd_handler;
float (*set_gain_callback)(void*, float);
SRSLTE_AGC_CALLBACK(*set_gain_callback);
srslte_agc_mode_t mode;
float target;
uint32_t nof_frames;
@ -66,7 +68,7 @@ SRSLTE_API int srslte_agc_init_acc(srslte_agc_t* q, srslte_agc_mode_t mode, uint
SRSLTE_API int srslte_agc_init_uhd(srslte_agc_t* q,
srslte_agc_mode_t mode,
uint32_t nof_frames,
float(set_gain_callback)(void*, float),
SRSLTE_AGC_CALLBACK(set_gain_callback),
void* uhd_handler);
SRSLTE_API void srslte_agc_free(srslte_agc_t* q);

View File

@ -200,7 +200,7 @@ SRSLTE_API void srslte_ue_sync_set_nof_find_frames(srslte_ue_sync_t* q, uint32_t
SRSLTE_API srslte_frame_type_t srslte_ue_sync_get_frame_type(srslte_ue_sync_t* q);
SRSLTE_API int srslte_ue_sync_start_agc(srslte_ue_sync_t* q,
float(set_gain_callback)(void*, float),
SRSLTE_AGC_CALLBACK(set_gain_callback),
float min_gain,
float max_gain,
float init_gain_value);

View File

@ -123,7 +123,7 @@ SRSLTE_API void srslte_ue_sync_nbiot_free(srslte_nbiot_ue_sync_t* q);
SRSLTE_API int srslte_ue_sync_nbiot_set_cell(srslte_nbiot_ue_sync_t* q, srslte_nbiot_cell_t cell);
SRSLTE_API int srslte_ue_sync_nbiot_start_agc(srslte_nbiot_ue_sync_t* q,
float(set_gain_callback)(void*, float),
SRSLTE_AGC_CALLBACK(set_gain_callback),
float init_gain_value);
SRSLTE_API uint32_t srslte_ue_sync_nbiot_sf_len(srslte_nbiot_ue_sync_t* q);

View File

@ -96,10 +96,10 @@ public:
bool rx_now(cf_t* buffer[SRSLTE_MAX_PORTS], uint32_t nof_samples, srslte_timestamp_t* rxd_time);
bool rx_at(cf_t* buffer, uint32_t nof_samples, srslte_timestamp_t rx_time);
void set_tx_gain(float gain);
void set_rx_gain(float gain);
void set_tx_rx_gain_offset(float offset);
float set_rx_gain_th(float gain);
void set_tx_gain(float gain);
void set_rx_gain(float gain);
void set_tx_rx_gain_offset(float offset);
void set_rx_gain_th(float gain);
void set_freq_offset(double freq);
void set_tx_freq(uint32_t chan, double freq);

View File

@ -102,7 +102,7 @@ public:
return radios.at(radio_idx)->rx_now(buffer, nof_samples, rxd_time);
}
void set_rx_gain(const uint32_t& radio_idx, const float& gain) override { radios.at(radio_idx)->set_rx_gain(gain); }
float set_rx_gain_th(const float& gain) override { return radios.at(0)->set_rx_gain_th(gain); }
void set_rx_gain_th(const float& gain) override { radios.at(0)->set_rx_gain_th(gain); }
float get_rx_gain(const uint32_t& radio_idx) override { return radios.at(radio_idx)->get_rx_gain(); }
void set_tx_freq(const uint32_t& radio_idx, const uint32_t& channel_idx, const double& freq) override
{

View File

@ -59,7 +59,7 @@ int srslte_agc_init_acc(srslte_agc_t* q, srslte_agc_mode_t mode, uint32_t nof_fr
int srslte_agc_init_uhd(srslte_agc_t* q,
srslte_agc_mode_t mode,
uint32_t nof_frames,
float(set_gain_callback)(void*, float),
SRSLTE_AGC_CALLBACK(set_gain_callback),
void* uhd_handler)
{
if (!srslte_agc_init_acc(q, mode, nof_frames)) {
@ -83,11 +83,11 @@ void srslte_agc_reset(srslte_agc_t* q)
{
q->bandwidth = SRSLTE_AGC_DEFAULT_BW;
q->lock = false;
q->gain = srslte_convert_dB_to_power(50.0f);
q->gain = srslte_convert_dB_to_power(q->default_gain_db);
q->y_out = 1.0;
q->isfirst = true;
if (q->set_gain_callback && q->uhd_handler) {
q->set_gain_callback(q->uhd_handler, srslte_convert_power_to_dB(q->gain));
q->set_gain_callback(q->uhd_handler, q->default_gain_db);
}
}
@ -96,6 +96,7 @@ void srslte_agc_set_gain_range(srslte_agc_t* q, float min_gain_db, float max_gai
if (q) {
q->min_gain_db = min_gain_db;
q->max_gain_db = max_gain_db;
q->default_gain_db = (max_gain_db + min_gain_db) / 2.0f;
}
}
@ -138,7 +139,6 @@ void srslte_agc_process(srslte_agc_t* q, cf_t* signal, uint32_t len)
{
if (!q->lock) {
float gain_db = srslte_convert_power_to_dB(q->gain);
float gain_uhd_db = 50.0f;
float y = 0;
// Apply current gain to input signal
@ -152,13 +152,13 @@ void srslte_agc_process(srslte_agc_t* q, cf_t* signal, uint32_t len)
gain_db = q->max_gain_db;
INFO("Warning: Rx signal strength is too weak. Forcing maximum Rx gain %.2fdB\n", gain_db);
} else if (isinf(gain_db) || isnan(gain_db)) {
gain_db = (q->min_gain_db + q->max_gain_db) / 2.0;
gain_db = q->default_gain_db;
INFO("Warning: AGC went to an unknown state. Setting Rx gain to %.2fdB\n", gain_db);
}
// Set gain
gain_uhd_db = q->set_gain_callback(q->uhd_handler, gain_db);
q->gain = srslte_convert_dB_to_power(gain_uhd_db);
q->set_gain_callback(q->uhd_handler, gain_db);
q->gain = srslte_convert_dB_to_power(gain_db);
}
float* t;
switch (q->mode) {
@ -201,7 +201,7 @@ void srslte_agc_process(srslte_agc_t* q, cf_t* signal, uint32_t len)
if (!q->lock) {
q->gain *= q->target / q->y_out;
}
INFO("AGC gain: %.2f (%.2f) y_out=%.3f, y=%.3f target=%.1f\n", gain_db, gain_uhd_db, q->y_out, y, q->target);
INFO("AGC gain: %.2f y_out=%.3f, y=%.3f target=%.1f\n", gain_db, q->y_out, y, q->target);
}
}
}

View File

@ -141,7 +141,7 @@ void srslte_ue_sync_reset(srslte_ue_sync_t* q)
}
int srslte_ue_sync_start_agc(srslte_ue_sync_t* q,
float(set_gain_callback)(void*, float),
SRSLTE_AGC_CALLBACK(set_gain_callback),
float min_gain_db,
float max_gain_db,
float init_gain_value_db)

View File

@ -127,7 +127,7 @@ clean_exit:
}
int srslte_ue_sync_nbiot_start_agc(srslte_nbiot_ue_sync_t* q,
float(set_gain_callback)(void*, float),
SRSLTE_AGC_CALLBACK(set_gain_callback),
float init_gain_value)
{
uint32_t nframes;

View File

@ -280,9 +280,9 @@ void radio::set_rx_gain(float gain)
srslte_rf_set_rx_gain(&rf_device, gain);
}
float radio::set_rx_gain_th(float gain)
void radio::set_rx_gain_th(float gain)
{
return srslte_rf_set_rx_gain_th(&rf_device, gain);
srslte_rf_set_rx_gain_th(&rf_device, gain);
}
void radio::set_rx_srate(double srate)

View File

@ -151,10 +151,10 @@ void parse_args(int argc, char** argv)
}
}
static float set_gain_callback(void* h, float gain)
static SRSLTE_AGC_CALLBACK(set_gain_callback)
{
auto r = (radio*)h;
return r->set_rx_gain_th(gain);
r->set_rx_gain_th(gain_db);
}
#ifdef ENABLE_GUI

View File

@ -54,31 +54,22 @@ public:
const srslte_cell_t* get_cell() { return &cell; };
// Other functions
const static int MUTEX_X_WORKER = 4;
double set_rx_gain(double gain);
int radio_recv_fnc(cf_t* data[SRSLTE_MAX_PORTS], uint32_t nsamples, srslte_timestamp_t* rx_time);
bool tti_align(uint32_t tti);
void read_sf(cf_t** dst, srslte_timestamp_t* timestamp, int* next_offset);
void set_rx_gain(float gain);
int radio_recv_fnc(cf_t* data[SRSLTE_MAX_PORTS], uint32_t nsamples, srslte_timestamp_t* rx_time);
bool tti_align(uint32_t tti);
void read_sf(cf_t** dst, srslte_timestamp_t* timestamp, int* next_offset);
private:
class phch_scell_recv_buffer
{
private:
uint32_t tti;
srslte_timestamp_t timestamp;
int next_offset;
cf_t* buffer[SRSLTE_MAX_PORTS];
uint32_t tti = 0;
srslte_timestamp_t timestamp = {};
int next_offset = 0;
cf_t* buffer[SRSLTE_MAX_PORTS] = {};
public:
phch_scell_recv_buffer()
{
tti = 0;
next_offset = 0;
bzero(&timestamp, sizeof(timestamp));
for (cf_t*& b : buffer) {
b = nullptr;
}
}
phch_scell_recv_buffer() = default;
~phch_scell_recv_buffer()
{

View File

@ -89,8 +89,8 @@ public:
void force_freq(float dl_freq, float ul_freq);
// Other functions
double set_rx_gain(double gain);
int radio_recv_fnc(cf_t* data[SRSLTE_MAX_PORTS], uint32_t nsamples, srslte_timestamp_t* rx_time);
void set_rx_gain(float gain);
int radio_recv_fnc(cf_t* data[SRSLTE_MAX_PORTS], uint32_t nsamples, srslte_timestamp_t* rx_time);
private:
// Class to run cell search

View File

@ -79,9 +79,9 @@ static int radio_recv_callback(void* obj, cf_t* data[SRSLTE_MAX_PORTS], uint32_t
return ((async_scell_recv*)obj)->radio_recv_fnc(data, nsamples, rx_time);
}
static float callback_set_rx_gain(void* h, float gain)
static SRSLTE_AGC_CALLBACK(callback_set_rx_gain)
{
return (float)((async_scell_recv*)h)->set_rx_gain(gain);
((async_scell_recv*)h)->set_rx_gain(gain_db);
}
void async_scell_recv::init(srslte::radio_interface_phy* _radio_handler, phy_common* _worker_com, srslte::log* _log_h)
@ -198,9 +198,9 @@ void async_scell_recv::set_agc_enable(bool enable)
}
}
double async_scell_recv::set_rx_gain(double gain)
void async_scell_recv::set_rx_gain(float gain)
{
return radio_h->set_rx_gain_th((float)gain);
radio_h->set_rx_gain_th(gain);
}
int async_scell_recv::radio_recv_fnc(cf_t* data[SRSLTE_MAX_PORTS], uint32_t nsamples, srslte_timestamp_t* rx_time)

View File

@ -47,9 +47,9 @@ static int radio_recv_callback(void* obj, cf_t* data[SRSLTE_MAX_PORTS], uint32_t
return ((sync*)obj)->radio_recv_fnc(data, nsamples, rx_time);
}
float callback_set_rx_gain(void* h, float gain)
static SRSLTE_AGC_CALLBACK(callback_set_rx_gain)
{
return ((sync*)h)->set_rx_gain(gain);
((sync*)h)->set_rx_gain(gain_db);
}
void sync::init(srslte::radio_interface_phy* _radio,
@ -963,9 +963,9 @@ int sync::radio_recv_fnc(cf_t* data[SRSLTE_MAX_PORTS], uint32_t nsamples, srslte
}
}
double sync::set_rx_gain(double gain)
void sync::set_rx_gain(float gain)
{
return radio_h->set_rx_gain_th(gain);
radio_h->set_rx_gain_th(gain);
}
/*********

View File

@ -275,12 +275,11 @@ private:
rx_freq = (float)freq;
log_h.info("Set Rx freq to %+.0f MHz.\n", freq * 1.0e-6);
}
float set_rx_gain_th(const float& gain) override
void set_rx_gain_th(const float& gain) override
{
std::unique_lock<std::mutex> lock(mutex);
rx_gain = srslte_convert_dB_to_amplitude(gain);
log_h.info("Set Rx gain-th to %+.1f dB (%.6f).\n", gain, rx_gain);
return srslte_convert_amplitude_to_dB(rx_gain);
}
void set_rx_gain(const uint32_t& radio_idx, const float& gain) override
{