created a header for all common structs and helper functions

master
Francisco Paisana 5 years ago
parent 02ccb8b32b
commit e9a599857a

@ -50,38 +50,6 @@ inline bool is_in_tti_interval(uint32_t tti, uint32_t tti1, uint32_t tti2)
} // namespace sched_utils
//! structs to bundle together all the sched arguments, and share them with all the sched sub-components
class sched_cell_params_t
{
struct regs_deleter {
void operator()(srslte_regs_t* p)
{
if (p != nullptr) {
srslte_regs_free(p);
delete p;
}
}
};
public:
bool set_cfg(uint32_t enb_cc_idx_,
const sched_interface::cell_cfg_t& cfg_,
const sched_interface::sched_args_t& sched_args);
// convenience getters
uint32_t prb_to_rbg(uint32_t nof_prbs) const { return (nof_prbs + (P - 1)) / P; }
uint32_t nof_prb() const { return cfg.cell.nof_prb; }
uint32_t enb_cc_idx = 0;
sched_interface::cell_cfg_t cfg = {};
const sched_interface::sched_args_t* sched_cfg = nullptr;
std::unique_ptr<srslte_regs_t, regs_deleter> regs;
std::array<sched_dci_cce_t, 3> common_locations = {};
std::array<std::array<sched_dci_cce_t, 10>, 3> rar_locations = {};
std::array<uint32_t, 3> nof_cce_table = {}; ///< map cfix -> nof cces in PDCCH
uint32_t P = 0;
uint32_t nof_rbgs = 0;
};
/* Caution: User addition (ue_cfg) and removal (ue_rem) are not thread-safe
* Rest of operations are thread-safe
*
@ -166,19 +134,6 @@ public:
void tpc_dec(uint16_t rnti);
const ue_cfg_t* get_ue_cfg(uint16_t rnti) final;
// Static Methods
static uint32_t get_rvidx(uint32_t retx_idx)
{
const static int rv_idx[4] = {0, 2, 3, 1};
return rv_idx[retx_idx % 4];
}
static void generate_cce_location(srslte_regs_t* regs,
sched_dci_cce_t* location,
uint32_t cfi,
uint32_t sf_idx = 0,
uint16_t rnti = 0);
static uint32_t aggr_level(uint32_t aggr_idx) { return 1u << aggr_idx; }
class carrier_sched;
protected:

@ -0,0 +1,124 @@
/*
* Copyright 2013-2019 Software Radio Systems Limited
*
* This file is part of srsLTE.
*
* srsLTE is free software: you can redistribute it and/or modify
* it under the terms of the GNU Affero General Public License as
* published by the Free Software Foundation, either version 3 of
* the License, or (at your option) any later version.
*
* srsLTE is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Affero General Public License for more details.
*
* A copy of the GNU Affero General Public License can be found in
* the LICENSE file in the top-level directory of this distribution
* and at http://www.gnu.org/licenses/.
*
*/
#ifndef SRSLTE_SCHEDULER_COMMON_H
#define SRSLTE_SCHEDULER_COMMON_H
#include "srslte/common/bounded_bitset.h"
#include "srslte/interfaces/sched_interface.h"
namespace srsenb {
//! Struct used to store possible CCE locations.
struct sched_dci_cce_t {
uint32_t cce_start[4][6]; ///< Stores starting CCE for each aggr level index and CCE location index
uint32_t nof_loc[4]; ///< Number of possible CCE locations for each aggregation level index
};
//! Params relative to a single TTI
struct tti_params_t {
uint32_t tti_rx;
uint32_t tti_tx_dl;
uint32_t tti_tx_ul;
uint32_t sf_idx_tx_dl;
uint32_t sfn_tx_dl;
explicit tti_params_t(uint32_t tti_rx_);
uint32_t tti_rx_ack_dl() const { return tti_tx_ul; }
};
//! structs to bundle together all the sched arguments, and share them with all the sched sub-components
class sched_cell_params_t
{
struct regs_deleter {
void operator()(srslte_regs_t* p)
{
if (p != nullptr) {
srslte_regs_free(p);
delete p;
}
}
};
public:
bool set_cfg(uint32_t enb_cc_idx_,
const sched_interface::cell_cfg_t& cfg_,
const sched_interface::sched_args_t& sched_args);
// convenience getters
uint32_t prb_to_rbg(uint32_t nof_prbs) const { return (nof_prbs + (P - 1)) / P; }
uint32_t nof_prb() const { return cfg.cell.nof_prb; }
uint32_t enb_cc_idx = 0;
sched_interface::cell_cfg_t cfg = {};
const sched_interface::sched_args_t* sched_cfg = nullptr;
std::unique_ptr<srslte_regs_t, regs_deleter> regs;
std::array<sched_dci_cce_t, 3> common_locations = {};
std::array<std::array<sched_dci_cce_t, 10>, 3> rar_locations = {};
std::array<uint32_t, 3> nof_cce_table = {}; ///< map cfix -> nof cces in PDCCH
uint32_t P = 0;
uint32_t nof_rbgs = 0;
};
//! Bitmask used for CCE allocations
using pdcch_mask_t = srslte::bounded_bitset<sched_interface::max_cce, true>;
//! Bitmask that stores the allocared DL RBGs
using rbgmask_t = srslte::bounded_bitset<25, true>;
//! Bitmask that stores the allocated UL PRBs
using prbmask_t = srslte::bounded_bitset<100, true>;
/***********************
* Helper Functions
**********************/
namespace sched_utils {
uint32_t aggr_level(uint32_t aggr_idx)
{
return 1u << aggr_idx;
}
//! Obtain rvidx from nof retxs. This value is stored in DCI
uint32_t get_rvidx(uint32_t retx_idx)
{
const static uint32_t rv_idx[4] = {0, 2, 3, 1};
return rv_idx[retx_idx % 4];
}
/**
* Generate possible CCE locations a user can use to allocate DCIs
* @param regs Regs data for the given cell configuration
* @param location Result of the CCE location computation.
* @param cfi Number of control symbols used for the PDCCH
* @param sf_idx subframe index specific to the tx TTI (relevant only for data and RAR transmissions)
* @param rnti identity of the user (invalid RNTI for RAR and BC transmissions)
*/
void generate_cce_location(srslte_regs_t* regs,
sched_dci_cce_t* location,
uint32_t cfi,
uint32_t sf_idx = 0,
uint16_t rnti = SRSLTE_INVALID_RNTI);
} // namespace sched_utils
} // namespace srsenb
#endif // SRSLTE_SCHEDULER_COMMON_H

@ -42,18 +42,7 @@ struct alloc_outcome_t {
alloc_outcome_t(result_enum e) : result(e) {}
operator result_enum() { return result; }
operator bool() { return result == SUCCESS; }
const char* to_string() const;
};
//! Params relative to a single TTI
struct tti_params_t {
uint32_t tti_rx;
uint32_t tti_tx_dl;
uint32_t tti_tx_ul;
uint32_t sf_idx;
uint32_t sfn;
explicit tti_params_t(uint32_t tti_rx_);
uint32_t tti_rx_ack_dl() const { return tti_tx_ul; }
const char* to_string() const;
};
//! Result of a Subframe sched computation

@ -29,9 +29,6 @@
namespace srsenb {
// MASK used for CCE allocations
typedef srslte::bounded_bitset<sched_interface::max_cce, true> pdcch_mask_t;
// Range of RBGs
class prb_range_t;
struct rbg_range_t {
@ -93,8 +90,6 @@ protected:
srslte::log_ref log_h;
};
typedef srslte::bounded_bitset<25, true> rbgmask_t;
class dl_harq_proc : public harq_proc
{
public:
@ -147,8 +142,6 @@ private:
ack_t pending_ack;
};
typedef srslte::bounded_bitset<100, true> prbmask_t;
class harq_entity
{
public:

@ -22,8 +22,8 @@
#ifndef SRSENB_SCHEDULER_UE_H
#define SRSENB_SCHEDULER_UE_H
#include "scheduler_common.h"
#include "srslte/common/log.h"
#include "srslte/interfaces/sched_interface.h"
#include <map>
#include <vector>
@ -32,14 +32,6 @@
namespace srsenb {
class sched_cell_params_t;
struct tti_params_t;
struct sched_dci_cce_t {
uint32_t cce_start[4][6];
uint32_t nof_loc[4];
};
struct sched_ue_carrier {
const static int SCHED_MAX_HARQ_PROC = TX_DELAY + FDD_HARQ_DELAY_MS;

@ -89,7 +89,7 @@ bool sched_cell_params_t::set_cfg(uint32_t enb_cc_id
// Compute Common locations for DCI for each CFI
for (uint32_t cfi = 0; cfi < 3; cfi++) {
sched::generate_cce_location(regs.get(), &common_locations[cfi], cfi + 1);
sched_utils::generate_cce_location(regs.get(), &common_locations[cfi], cfi + 1);
}
if (common_locations[sched_cfg->nof_ctrl_symbols - 1].nof_loc[2] == 0) {
Error("SCHED: Current cfi=%d is not valid for broadcast (check scheduler.nof_ctrl_symbols in conf file).\n",
@ -102,7 +102,7 @@ bool sched_cell_params_t::set_cfg(uint32_t enb_cc_id
// Compute UE locations for RA-RNTI
for (uint32_t cfi = 0; cfi < 3; cfi++) {
for (uint32_t sf_idx = 0; sf_idx < 10; sf_idx++) {
sched::generate_cce_location(regs.get(), &rar_locations[cfi][sf_idx], cfi + 1, sf_idx);
sched_utils::generate_cce_location(regs.get(), &rar_locations[cfi][sf_idx], cfi + 1, sf_idx);
}
}
@ -415,15 +415,15 @@ int sched::ul_sched(uint32_t tti, uint32_t cc_idx, srsenb::sched_interface::ul_s
/*******************************************************
*
* Helper functions
* Helper functions and common data types
*
*******************************************************/
void sched::generate_cce_location(srslte_regs_t* regs_,
sched_dci_cce_t* location,
uint32_t cfi,
uint32_t sf_idx,
uint16_t rnti)
void sched_utils::generate_cce_location(srslte_regs_t* regs_,
sched_dci_cce_t* location,
uint32_t cfi,
uint32_t sf_idx,
uint16_t rnti)
{
*location = {};

@ -55,8 +55,8 @@ void bc_sched::dl_sched(sf_sched* tti_sched)
void bc_sched::update_si_windows(sf_sched* tti_sched)
{
uint32_t tti_tx_dl = tti_sched->get_tti_tx_dl();
uint32_t current_sf_idx = tti_sched->get_tti_params().sf_idx;
uint32_t current_sfn = tti_sched->get_tti_params().sfn;
uint32_t current_sf_idx = tti_sched->get_tti_params().sf_idx_tx_dl;
uint32_t current_sfn = tti_sched->get_tti_params().sfn_tx_dl;
for (uint32_t i = 0; i < pending_sibs.size(); ++i) {
// There is SIB data
@ -94,8 +94,8 @@ void bc_sched::update_si_windows(sf_sched* tti_sched)
void bc_sched::alloc_sibs(sf_sched* tti_sched)
{
uint32_t current_sf_idx = tti_sched->get_tti_params().sf_idx;
uint32_t current_sfn = tti_sched->get_tti_params().sfn;
uint32_t current_sf_idx = tti_sched->get_tti_params().sf_idx_tx_dl;
uint32_t current_sfn = tti_sched->get_tti_params().sfn_tx_dl;
for (uint32_t i = 0; i < pending_sibs.size(); i++) {
if (cc_cfg->cfg.sibs[i].len > 0 and pending_sibs[i].is_in_window and pending_sibs[i].n_tx < 4) {

@ -48,10 +48,10 @@ const char* alloc_outcome_t::to_string() const
tti_params_t::tti_params_t(uint32_t tti_rx_) :
tti_rx(tti_rx_),
sf_idx(TTI_ADD(tti_rx, TX_DELAY) % 10),
sf_idx_tx_dl(TTI_ADD(tti_rx, TX_DELAY) % 10),
tti_tx_dl(TTI_ADD(tti_rx, TX_DELAY)),
tti_tx_ul(TTI_ADD(tti_rx, (TX_DELAY + FDD_HARQ_DELAY_MS))),
sfn(TTI_ADD(tti_rx, TX_DELAY) / 10)
sfn_tx_dl(TTI_ADD(tti_rx, TX_DELAY) / 10)
{
}
@ -85,11 +85,11 @@ const sched_dci_cce_t* pdcch_grid_t::get_cce_loc_table(alloc_type_t alloc_type,
case alloc_type_t::DL_PCCH:
return &cc_cfg->common_locations[current_cfix];
case alloc_type_t::DL_RAR:
return &cc_cfg->rar_locations[current_cfix][tti_params->sf_idx];
return &cc_cfg->rar_locations[current_cfix][tti_params->sf_idx_tx_dl];
case alloc_type_t::DL_DATA:
return user->get_locations(cc_cfg->enb_cc_idx, current_cfix + 1, tti_params->sf_idx);
return user->get_locations(cc_cfg->enb_cc_idx, current_cfix + 1, tti_params->sf_idx_tx_dl);
case alloc_type_t::UL_DATA:
return user->get_locations(cc_cfg->enb_cc_idx, current_cfix + 1, tti_params->sf_idx);
return user->get_locations(cc_cfg->enb_cc_idx, current_cfix + 1, tti_params->sf_idx_tx_dl);
default:
break;
}
@ -482,7 +482,7 @@ sf_sched::ctrl_code_t sf_sched::alloc_dl_ctrl(uint32_t aggr_lvl, uint32_t tbs_by
alloc_outcome_t sf_sched::alloc_bc(uint32_t aggr_lvl, uint32_t sib_idx, uint32_t sib_ntx)
{
uint32_t sib_len = cc_cfg->cfg.sibs[sib_idx].len;
uint32_t rv = sched::get_rvidx(sib_ntx);
uint32_t rv = sched_utils::get_rvidx(sib_ntx);
ctrl_code_t ret = alloc_dl_ctrl(aggr_lvl, sib_len, SRSLTE_SIRNTI);
if (not ret.first) {
Warning("SCHED: Could not allocate SIB=%d, L=%d, len=%d, cause=%s\n",

@ -464,7 +464,7 @@ int sched_ue::generate_format1(uint32_t pid,
dci->rnti = rnti;
dci->pid = h->get_id();
dci->tb[0].mcs_idx = (uint32_t)mcs;
dci->tb[0].rv = sched::get_rvidx(h->nof_retx(0));
dci->tb[0].rv = sched_utils::get_rvidx(h->nof_retx(0));
dci->tb[0].ndi = h->get_ndi(0);
dci->tpc_pucch = (uint8_t)next_tpc_pucch;
@ -572,7 +572,7 @@ int sched_ue::generate_format2a_unlocked(uint32_t pid,
/* Fill DCI TB dedicated fields */
if (tbs > 0 && tb_en[tb]) {
dci->tb[tb].mcs_idx = (uint32_t)mcs;
dci->tb[tb].rv = sched::get_rvidx(h->nof_retx(tb));
dci->tb[tb].rv = sched_utils::get_rvidx(h->nof_retx(tb));
if (!SRSLTE_DCI_IS_TB_EN(dci->tb[tb])) {
dci->tb[tb].rv = 2;
}
@ -670,7 +670,7 @@ int sched_ue::generate_format0(sched_interface::ul_sched_data_t* data,
dci->rnti = rnti;
dci->format = SRSLTE_DCI_FORMAT0;
dci->type2_alloc.riv = srslte_ra_type2_to_riv(alloc.L, alloc.RB_start, cell.nof_prb);
dci->tb.rv = sched::get_rvidx(h->nof_retx(0));
dci->tb.rv = sched_utils::get_rvidx(h->nof_retx(0));
if (!is_newtx && h->is_adaptive_retx()) {
dci->tb.mcs_idx = 28 + dci->tb.rv;
} else {
@ -1100,7 +1100,7 @@ sched_ue_carrier::sched_ue_carrier(const sched_interface::ue_cfg_t& cfg_,
// Generate allowed CCE locations
for (int cfi = 0; cfi < 3; cfi++) {
for (int sf_idx = 0; sf_idx < 10; sf_idx++) {
sched::generate_cce_location(cell_params->regs.get(), &dci_locations[cfi][sf_idx], cfi + 1, sf_idx, rnti);
sched_utils::generate_cce_location(cell_params->regs.get(), &dci_locations[cfi][sf_idx], cfi + 1, sf_idx, rnti);
}
}

@ -167,8 +167,8 @@ int output_sched_tester::test_pdsch_collisions(const tti_params_t&
int output_sched_tester::test_sib_scheduling(const tti_params_t& tti_params,
const sched_interface::dl_sched_res_t& dl_result) const
{
uint32_t sfn = tti_params.sfn;
uint32_t sf_idx = tti_params.sf_idx;
uint32_t sfn = tti_params.sfn_tx_dl;
uint32_t sf_idx = tti_params.sf_idx_tx_dl;
bool sib1_present = ((sfn % 2) == 0) and sf_idx == 5;
using bc_elem = const sched_interface::dl_sched_bc_t;

Loading…
Cancel
Save