diff --git a/lib/include/srslte/mac/pdu.h b/lib/include/srslte/mac/pdu.h index b5753f2a5..b301e5f4a 100644 --- a/lib/include/srslte/mac/pdu.h +++ b/lib/include/srslte/mac/pdu.h @@ -33,6 +33,22 @@ class subh; namespace srslte { +/* 3GPP 36.321 Table 6.2.1-1 */ +enum class dl_sch_lcid { + CCCH = 0b00000, + //... + SCELL_ACTIVATION_4_OCTET = 0b11000, + SCELL_ACTIVATION = 0b11011, + CON_RES_ID = 0b11100, + TA_CMD = 0b11101, + DRX_CMD = 0b11110, + PADDING = 0b11111 +}; +const char* to_string(dl_sch_lcid v); +uint32_t ce_size(dl_sch_lcid v); +uint32_t ce_subheader_size(dl_sch_lcid v); +uint32_t ce_tot_size(dl_sch_lcid v); + template class pdu { @@ -48,8 +64,7 @@ public: last_sdu_idx(-1), pdu_is_ul(false), buffer_tx(nullptr) - { - } + {} void fprint(FILE* stream) { diff --git a/lib/src/mac/pdu.cc b/lib/src/mac/pdu.cc index 80774a7e2..35c9708a7 100644 --- a/lib/src/mac/pdu.cc +++ b/lib/src/mac/pdu.cc @@ -36,6 +36,64 @@ static uint32_t btable[64] = { namespace srslte { +/************************* + * DL-SCH LCID + *************************/ + +const char* to_string(dl_sch_lcid v) +{ + switch (v) { + case dl_sch_lcid::CCCH: + return "CCCH"; + case dl_sch_lcid::SCELL_ACTIVATION_4_OCTET: + return "Activation/Deactivation (4 octets)"; + case dl_sch_lcid::SCELL_ACTIVATION: + return "Activation/Deactivation (1 octet)"; + case dl_sch_lcid::CON_RES_ID: + return "UE Contention Resolution Identity"; + case dl_sch_lcid::TA_CMD: + return "Timing Advance Command"; + case dl_sch_lcid::DRX_CMD: + return "DRX Command"; + case dl_sch_lcid::PADDING: + return "Padding"; + default: + return "Unrecognized LCID"; + } +} + +uint32_t ce_size(dl_sch_lcid v) +{ + switch (v) { + case dl_sch_lcid::SCELL_ACTIVATION_4_OCTET: + return 4; + case dl_sch_lcid::SCELL_ACTIVATION: + return 1; + case dl_sch_lcid::CON_RES_ID: + return 6; + case dl_sch_lcid::TA_CMD: + return 1; + case dl_sch_lcid::DRX_CMD: + return 0; + default: + return 0; + } +} + +uint32_t ce_subheader_size(dl_sch_lcid v) +{ + return 1; +} + +uint32_t ce_tot_size(dl_sch_lcid v) +{ + return ce_subheader_size(v) + ce_size(v); +} + +/************************* + * SCH PDU + *************************/ + void sch_pdu::fprint(FILE* stream) { fprintf(stream, "MAC SDU for UL/DL-SCH. "); diff --git a/srsenb/hdr/stack/mac/scheduler_ue.h b/srsenb/hdr/stack/mac/scheduler_ue.h index f489ee880..3f6903148 100644 --- a/srsenb/hdr/stack/mac/scheduler_ue.h +++ b/srsenb/hdr/stack/mac/scheduler_ue.h @@ -24,6 +24,7 @@ #include "scheduler_common.h" #include "srslte/common/log.h" +#include "srslte/mac/pdu.h" #include #include @@ -271,15 +272,7 @@ private: std::vector carriers; ///< map of UE CellIndex to carrier configuration // Control Element Command queue - struct ce_cmd { - int cetype = 0; - - explicit ce_cmd(int lcid) : cetype(lcid) {} - int get_sdu_size(const sched_interface::ue_cfg_t& c) const; - // considers both MAC CE and subheader - int get_req_bytes(const sched_interface::ue_cfg_t& c) const; - std::string to_string() const; - }; + using ce_cmd = srslte::dl_sch_lcid; std::deque pending_ces; }; } // namespace srsenb diff --git a/srsenb/src/stack/mac/scheduler_ue.cc b/srsenb/src/stack/mac/scheduler_ue.cc index bebafe580..9349a8294 100644 --- a/srsenb/src/stack/mac/scheduler_ue.cc +++ b/srsenb/src/stack/mac/scheduler_ue.cc @@ -149,7 +149,7 @@ void sched_ue::set_cfg(const sched_interface::ue_cfg_t& cfg_) scell_activation_state_changed |= carriers[ue_idx].is_active() != cc_cfg.active and ue_idx > 0; } if (scell_activation_state_changed) { - pending_ces.emplace_back(srslte::sch_subh::SCELL_ACTIVATION); + pending_ces.emplace_back(srslte::dl_sch_lcid::SCELL_ACTIVATION); log_h->info("SCHED: Enqueueing SCell Activation CMD for rnti=0x%x\n", rnti); } } @@ -224,15 +224,15 @@ void sched_ue::dl_buffer_state(uint8_t lc_id, uint32_t tx_queue, uint32_t retx_q void sched_ue::mac_buffer_state(uint32_t ce_code, uint32_t nof_cmds) { - ce_cmd cmd{(int)ce_code}; + auto cmd = (ce_cmd)ce_code; for (uint32_t i = 0; i < nof_cmds; ++i) { - if (static_cast(cmd.cetype) == srslte::sch_subh::CON_RES_ID) { + if (cmd == ce_cmd::CON_RES_ID) { pending_ces.push_front(cmd); } else { pending_ces.push_back(cmd); } } - Info("SCHED: %s for rnti=0x%x needs to be scheduled\n", cmd.to_string().c_str(), rnti); + Info("SCHED: %s for rnti=0x%x needs to be scheduled\n", to_string(cmd), rnti); } void sched_ue::set_sr() @@ -413,14 +413,14 @@ uint32_t sched_ue::allocate_mac_ces(sched_interface::dl_sched_data_t* data, uint int rem_tbs = total_tbs; while (not pending_ces.empty()) { - int toalloc = pending_ces.front().get_req_bytes(cfg); + int toalloc = srslte::ce_tot_size(pending_ces.front()); if (rem_tbs < toalloc) { break; } - data->pdu[0][data->nof_pdu_elems[0]].lcid = pending_ces.front().cetype; + data->pdu[0][data->nof_pdu_elems[0]].lcid = (uint32_t)pending_ces.front(); data->nof_pdu_elems[0]++; rem_tbs -= toalloc; - Info("SCHED: Added a MAC %s CE for rnti=0x%x\n", pending_ces.front().to_string().c_str(), rnti); + Info("SCHED: Added a MAC %s CE for rnti=0x%x\n", srslte::to_string(pending_ces.front()), rnti); pending_ces.pop_front(); } return total_tbs - rem_tbs; @@ -895,7 +895,7 @@ std::pair sched_ue::get_requested_dl_bytes(uint32_t ue_cc_id // Add pending CEs if (ue_cc_idx == 0) { for (const auto& ce : pending_ces) { - sum_ce_data += ce.get_req_bytes(cfg); + sum_ce_data += srslte::ce_tot_size(ce); } } // Add pending data in remaining RLC buffers @@ -909,12 +909,12 @@ std::pair sched_ue::get_requested_dl_bytes(uint32_t ue_cc_id /* Set Minimum boundary */ min_data = srb0_data; - if (pending_ces.front().cetype == srslte::sch_subh::CON_RES_ID) { - min_data += pending_ces.front().get_req_bytes(cfg); + if (pending_ces.front() == ce_cmd::CON_RES_ID) { + min_data += srslte::ce_tot_size(pending_ces.front()); } if (min_data == 0) { if (sum_ce_data > 0) { - min_data = pending_ces.front().get_req_bytes(cfg); + min_data = srslte::ce_tot_size(pending_ces.front()); } else if (rb_data > 0) { min_data = min_alloc_bytes; } @@ -940,7 +940,7 @@ uint32_t sched_ue::get_pending_dl_new_data() } } for (auto& ce : pending_ces) { - pending_data += ce.get_req_bytes(cfg); + pending_data += srslte::ce_tot_size(ce); } return pending_data; } @@ -1403,48 +1403,4 @@ void sched_ue_carrier::set_dl_cqi(uint32_t tti_tx_dl, uint32_t dl_cqi_) } } -/******************************************************* - * MAC CE Command - ******************************************************/ - -int sched_ue::ce_cmd::get_sdu_size(const sched_interface::ue_cfg_t& c) const -{ - // TS 36.321 Sec. 6.1.3 - MAC Control Elements - switch (cetype) { - case srslte::sch_subh::cetype::TA_CMD: - return 1; - case srslte::sch_subh::cetype::SCELL_ACTIVATION: - // TS 36.321 Sec. 6.1.3.8 - Number of SDU octets is 4 if there are more than 7 Scells (or 8 cells including PCell) - return c.supported_cc_list.size() > 8 ? 4 : 1; - case srslte::sch_subh::cetype::CON_RES_ID: - return 6; - default: - srslte::logmap::get("MAC ")->error("MAC CE not recognized\n"); - return 0; - } -} - -int sched_ue::ce_cmd::get_req_bytes(const sched_interface::ue_cfg_t& c) const -{ - // 36.321 Sec. 6.1.2 - CE subheader format is R/F2/E/LCID (1 octet) for fixed-size MAC CEs. - return get_sdu_size(c) + 1; -} - -std::string sched_ue::ce_cmd::to_string() const -{ - switch (cetype) { - case srslte::sch_subh::cetype::SCELL_ACTIVATION: - return "SCell Activation"; - case srslte::sch_subh::cetype::CON_RES_ID: - return "ContentionResolution"; - case srslte::sch_subh::cetype::TA_CMD: - return "Timing Advance"; - case srslte::sch_subh::cetype::DRX_CMD: - return "DRX"; - default: - srslte::logmap::get("MAC ")->error("MAC CE not recognized\n"); - return ""; - } -} - } // namespace srsenb diff --git a/srsenb/test/mac/CMakeLists.txt b/srsenb/test/mac/CMakeLists.txt index 81bfa3ded..0631c9e91 100644 --- a/srsenb/test/mac/CMakeLists.txt +++ b/srsenb/test/mac/CMakeLists.txt @@ -36,6 +36,7 @@ add_executable(scheduler_test_rand scheduler_test_rand.cc) target_link_libraries(scheduler_test_rand srsenb_mac srsenb_phy srslte_common + srslte_mac scheduler_test_common srslte_phy rrc_asn1 @@ -48,6 +49,7 @@ add_executable(scheduler_ca_test scheduler_ca_test.cc scheduler_test_common.cc) target_link_libraries(scheduler_ca_test srsenb_mac srsenb_phy srslte_common + srslte_mac srslte_phy scheduler_test_common rrc_asn1