Minor changes on UE SA PHY

This commit is contained in:
Xavier Arteaga 2022-01-07 11:43:08 +01:00 committed by Xavier Arteaga
parent c494a84738
commit db19941985
7 changed files with 37 additions and 17 deletions

View File

@ -49,7 +49,11 @@ public:
* @brief Describes a cell select result * @brief Describes a cell select result
*/ */
struct cell_select_result_t { struct cell_select_result_t {
bool successful = false; ///< Cell was found and physical layer is synchronised enum {
ERROR = 0, ///< The cell selection procedure failed due a to an invalid configuration
UNSUCCESFUL, ///< The cell selection failed to find and synchronise the SSB
SUCCESFUL, ///< The cell selection was succesful, resulting in a camping state
} status;
}; };
/** /**

View File

@ -32,15 +32,10 @@
namespace srsran { namespace srsran {
/** /**
* Implementation of the radio interface for the PHY * Implementation of radio dummy for the PHY testing
* *
* It uses the rf C library object to access the underlying radio. This implementation uses a flat array to * It uses ringbuffers from srsRAN library to emulate baseband transmission and reception. The current implementation
* transmit/receive samples for all RF channels. The N carriers and P antennas are mapped into M=NP RF channels (M <= * does not support dynamic sampling rates, gains and frequencies.
* SRSRAN_MAX_CHANNELS). Note that all carriers must have the same number of antennas.
*
* The underlying radio receives and transmits M RF channels synchronously from possibly multiple radios using the same
* rf driver object. In the current implementation, the mapping between N carriers and P antennas is sequentially, eg:
* [carrier_0_port_0, carrier_0_port_1, carrier_1_port_0, carrier_1_port_1, ..., carrier_N_port_N]
*/ */
class radio_dummy : public srsran::radio_base, public srsran::radio_interface_phy class radio_dummy : public srsran::radio_base, public srsran::radio_interface_phy
{ {

View File

@ -111,6 +111,7 @@ public:
void add_eps_bearer(uint8_t eps_bearer_id, srsran::srsran_rat_t rat, uint32_t lcid) final {} void add_eps_bearer(uint8_t eps_bearer_id, srsran::srsran_rat_t rat, uint32_t lcid) final {}
void remove_eps_bearer(uint8_t eps_bearer_id) final {} void remove_eps_bearer(uint8_t eps_bearer_id) final {}
void reset_eps_bearers() final {} void reset_eps_bearers() final {}
void cell_select_completed(const cell_select_result_t& result) override;
private: private:
void run_thread() final; void run_thread() final;

View File

@ -104,27 +104,32 @@ int slot_sync::recv_callback(srsran::rf_buffer_t& data, srsran_timestamp_t* rx_t
bool slot_sync::run_sfn_sync() bool slot_sync::run_sfn_sync()
{ {
// Run UE SYNC process using the temporal SFN process buffer
srsran_ue_sync_nr_outcome_t outcome = {}; srsran_ue_sync_nr_outcome_t outcome = {};
if (srsran_ue_sync_nr_zerocopy(&ue_sync_nr, sfn_sync_buff.to_cf_t(), &outcome) < SRSRAN_SUCCESS) { if (srsran_ue_sync_nr_zerocopy(&ue_sync_nr, sfn_sync_buff.to_cf_t(), &outcome) < SRSRAN_SUCCESS) {
logger.error("SYNC: error in zerocopy"); logger.error("SYNC: error in zerocopy");
return false; return false;
} }
// If in sync, update slot index
if (outcome.in_sync) { if (outcome.in_sync) {
slot_cfg.idx = outcome.sfn * SRSRAN_NSLOTS_PER_FRAME_NR(srsran_subcarrier_spacing_15kHz) + outcome.sf_idx; slot_cfg.idx = outcome.sfn * SRSRAN_NSLOTS_PER_FRAME_NR(srsran_subcarrier_spacing_15kHz) + outcome.sf_idx;
} }
// Return true if the PHY in-sync
return outcome.in_sync; return outcome.in_sync;
} }
bool slot_sync::run_camping(srsran::rf_buffer_t& buffer, srsran::rf_timestamp_t& timestamp) bool slot_sync::run_camping(srsran::rf_buffer_t& buffer, srsran::rf_timestamp_t& timestamp)
{ {
// Run UE SYNC process using an external baseband buffer
srsran_ue_sync_nr_outcome_t outcome = {}; srsran_ue_sync_nr_outcome_t outcome = {};
if (srsran_ue_sync_nr_zerocopy(&ue_sync_nr, buffer.to_cf_t(), &outcome) < SRSRAN_SUCCESS) { if (srsran_ue_sync_nr_zerocopy(&ue_sync_nr, buffer.to_cf_t(), &outcome) < SRSRAN_SUCCESS) {
logger.error("SYNC: error in zerocopy"); logger.error("SYNC: error in zerocopy");
return false; return false;
} }
// If in sync, update slot index
if (outcome.in_sync) { if (outcome.in_sync) {
slot_cfg.idx = outcome.sfn * SRSRAN_NSLOTS_PER_FRAME_NR(srsran_subcarrier_spacing_15kHz) + outcome.sf_idx; slot_cfg.idx = outcome.sfn * SRSRAN_NSLOTS_PER_FRAME_NR(srsran_subcarrier_spacing_15kHz) + outcome.sf_idx;
} }
@ -132,6 +137,7 @@ bool slot_sync::run_camping(srsran::rf_buffer_t& buffer, srsran::rf_timestamp_t&
// Set RF timestamp // Set RF timestamp
*timestamp.get_ptr(0) = outcome.timestamp; *timestamp.get_ptr(0) = outcome.timestamp;
// Return true if the PHY in-sync
return outcome.in_sync; return outcome.in_sync;
} }

View File

@ -149,10 +149,16 @@ rrc_interface_phy_nr::cell_select_result_t sync_sa::cell_select_run(const phy_in
{ {
std::unique_lock<std::mutex> ul(rrc_mutex); std::unique_lock<std::mutex> ul(rrc_mutex);
// By default, the result is set to error
rrc_interface_phy_nr::cell_select_result_t result = {};
result.status = rrc_interface_phy_nr::cell_select_result_t::ERROR;
// Wait the FSM to transition to IDLE // Wait the FSM to transition to IDLE
if (!wait_idle()) { if (!wait_idle()) {
logger.error("Cell Search: SYNC thread didn't transition to IDLE after 100 ms\n"); logger.error("Cell Search: SYNC thread didn't transition to IDLE after 100 ms\n");
return {};
// Return default result with error status
return result;
} }
rrc_proc_state = PROC_SELECT_RUNNING; rrc_proc_state = PROC_SELECT_RUNNING;
@ -170,19 +176,21 @@ rrc_interface_phy_nr::cell_select_result_t sync_sa::cell_select_run(const phy_in
cfg.ssb.srate_hz = srate_hz; cfg.ssb.srate_hz = srate_hz;
if (slot_synchronizer.set_sync_cfg(cfg)) { if (slot_synchronizer.set_sync_cfg(cfg)) {
logger.error("Cell Search: Failed setting slot synchronizer configuration"); logger.error("Cell Search: Failed setting slot synchronizer configuration");
return {};
// Return default result with error status
return result;
} }
// SFN synchronization // SFN synchronization
phy_state.run_sfn_sync(); phy_state.run_sfn_sync();
// Determine if the procedure was successful if it is camping // Determine if the procedure was successful if the current state is camping, otherwise it is unsuccessful
rrc_interface_phy_nr::cell_select_result_t result = {}; if (phy_state.is_camping()) {
result.successful = phy_state.is_camping();
if (result.successful) {
logger.info("Cell Select: SFN synchronized. CAMPING..."); logger.info("Cell Select: SFN synchronized. CAMPING...");
result.status = rrc_interface_phy_nr::cell_select_result_t::SUCCESFUL;
} else { } else {
logger.info("Cell Select: Could not synchronize SFN"); logger.info("Cell Select: Could not synchronize SFN");
result.status = rrc_interface_phy_nr::cell_select_result_t::UNSUCCESFUL;
} }
rrc_proc_state = PROC_IDLE; rrc_proc_state = PROC_IDLE;
@ -278,7 +286,7 @@ void sync_sa::run_state_cell_camping()
} }
srsran::phy_common_interface::worker_context_t context; srsran::phy_common_interface::worker_context_t context;
context.sf_idx = tti; context.sf_idx = slot_synchronizer.get_slot_cfg().idx;
context.worker_ptr = nr_worker; context.worker_ptr = nr_worker;
context.last = true; // Set last if standalone context.last = true; // Set last if standalone
last_rx_time.add(FDD_HARQ_DELAY_DL_MS * 1e-3); last_rx_time.add(FDD_HARQ_DELAY_DL_MS * 1e-3);

View File

@ -202,4 +202,9 @@ void ue_stack_nr::set_phy_config_complete(bool status)
sync_task_queue.push([this, status]() { rrc->set_phy_config_complete(status); }); sync_task_queue.push([this, status]() { rrc->set_phy_config_complete(status); });
} }
void ue_stack_nr::cell_select_completed(const rrc_interface_phy_nr::cell_select_result_t& result)
{
sync_task_queue.push([this, result]() { rrc->cell_select_completed(result); });
}
} // namespace srsue } // namespace srsue

View File

@ -230,7 +230,8 @@ int main(int argc, char** argv)
// Start cell selection procedure // Start cell selection procedure
srsue::rrc_interface_phy_nr::cell_select_result_t cs_res = srsue::rrc_interface_phy_nr::cell_select_result_t cs_res =
tb.run_cell_select(args.phy_cfg.carrier, args.phy_cfg.get_ssb_cfg()); tb.run_cell_select(args.phy_cfg.carrier, args.phy_cfg.get_ssb_cfg());
srsran_assert(cs_res.successful, "Failed to perform cell selection"); srsran_assert(cs_res.status == srsue::rrc_interface_phy_nr::cell_select_result_t::SUCCESFUL,
"Failed to perform cell selection");
// Run per TTI basis // Run per TTI basis
while (tb.run_tti()) { while (tb.run_tti()) {