From ad0abe740b4eaa696bec5706d61145e2f4ab2a8a Mon Sep 17 00:00:00 2001 From: Pedro Alvarez Date: Mon, 20 Apr 2020 12:11:02 +0100 Subject: [PATCH] Added support to PDCP SN len of 7. Also added a check for valid configs in pdcp entity. --- lib/include/srslte/upper/pdcp_entity_lte.h | 3 +++ lib/src/asn1/rrc_asn1_utils.cc | 27 ++++++++++++++----- lib/src/upper/pdcp_entity_base.cc | 9 +++++++ lib/src/upper/pdcp_entity_lte.cc | 30 +++++++++++++++++++++- srsenb/src/stack/rrc/rrc.cc | 10 ++------ srsue/src/stack/rrc/rrc.cc | 14 +++------- 6 files changed, 68 insertions(+), 25 deletions(-) diff --git a/lib/include/srslte/upper/pdcp_entity_lte.h b/lib/include/srslte/upper/pdcp_entity_lte.h index fe43efd76..77065df57 100644 --- a/lib/include/srslte/upper/pdcp_entity_lte.h +++ b/lib/include/srslte/upper/pdcp_entity_lte.h @@ -72,6 +72,9 @@ public: last_submitted_pdcp_rx_sn = last_submitted_pdcp_rx_sn_; } + // Config helpers + bool check_valid_config(); + private: srsue::rlc_interface_pdcp* rlc = nullptr; srsue::rrc_interface_pdcp* rrc = nullptr; diff --git a/lib/src/asn1/rrc_asn1_utils.cc b/lib/src/asn1/rrc_asn1_utils.cc index 45ac86c72..33aa1a3ba 100644 --- a/lib/src/asn1/rrc_asn1_utils.cc +++ b/lib/src/asn1/rrc_asn1_utils.cc @@ -214,26 +214,34 @@ srslte::pdcp_config_t make_drb_pdcp_config_t(const uint8_t bearer_id, bool is_ue srslte::pdcp_config_t make_drb_pdcp_config_t(const uint8_t bearer_id, bool is_ue, const asn1::rrc::pdcp_cfg_s& pdcp_cfg) { - pdcp_config_t cfg = make_drb_pdcp_config_t(bearer_id, is_ue); - // TODO: complete config processing + // TODO: complete config processing + pdcp_discard_timer_t discard_timer = pdcp_discard_timer_t::infinity; if (pdcp_cfg.discard_timer_present) { switch (pdcp_cfg.discard_timer.to_number()) { case 10: - cfg.discard_timer = pdcp_discard_timer_t::ms10; + discard_timer = pdcp_discard_timer_t::ms10; break; default: - cfg.discard_timer = pdcp_discard_timer_t::infinity; + discard_timer = pdcp_discard_timer_t::infinity; break; } } + pdcp_t_reordering_t t_reordering = pdcp_t_reordering_t::ms500; if (pdcp_cfg.t_reordering_r12_present) { switch (pdcp_cfg.t_reordering_r12.to_number()) { case 0: - cfg.t_reordering = pdcp_t_reordering_t::ms0; + t_reordering = pdcp_t_reordering_t::ms0; break; default: - cfg.t_reordering = pdcp_t_reordering_t::ms500; + t_reordering = pdcp_t_reordering_t::ms500; + } + } + + uint8_t sn_len = srslte::PDCP_SN_LEN_12; + if (pdcp_cfg.rlc_um_present) { + if (pdcp_cfg.rlc_um.pdcp_sn_size.value == pdcp_cfg_s::rlc_um_s_::pdcp_sn_size_e_::len7bits) { + sn_len = srslte::PDCP_SN_LEN_7; } } @@ -241,6 +249,13 @@ srslte::pdcp_config_t make_drb_pdcp_config_t(const uint8_t bearer_id, bool is_ue // TODO: handle RLC AM config for PDCP } + pdcp_config_t cfg(bearer_id, + PDCP_RB_IS_DRB, + is_ue ? SECURITY_DIRECTION_UPLINK : SECURITY_DIRECTION_DOWNLINK, + is_ue ? SECURITY_DIRECTION_DOWNLINK : SECURITY_DIRECTION_UPLINK, + sn_len, + t_reordering, + discard_timer); return cfg; } diff --git a/lib/src/upper/pdcp_entity_base.cc b/lib/src/upper/pdcp_entity_base.cc index 749b83080..5a910c340 100644 --- a/lib/src/upper/pdcp_entity_base.cc +++ b/lib/src/upper/pdcp_entity_base.cc @@ -234,6 +234,9 @@ uint32_t pdcp_entity_base::read_data_header(const unique_byte_buffer_t& pdu) case PDCP_SN_LEN_5: rcvd_sn_32 = SN(pdu->msg[0]); break; + case PDCP_SN_LEN_7: + rcvd_sn_32 = SN(pdu->msg[0]); + break; case PDCP_SN_LEN_12: srslte::uint8_to_uint16(pdu->msg, &rcvd_sn_16); rcvd_sn_32 = SN(rcvd_sn_16); @@ -270,6 +273,12 @@ void pdcp_entity_base::write_data_header(const srslte::unique_byte_buffer_t& sdu case PDCP_SN_LEN_5: sdu->msg[0] = SN(count); // Data PDU and SN LEN 5 implies SRB, D flag must not be present break; + case PDCP_SN_LEN_7: + sdu->msg[0] = SN(count); + if (is_drb()) { + sdu->msg[0] |= 0x80; // On Data PDUs for DRBs we must set the D flag. + } + break; case PDCP_SN_LEN_12: srslte::uint16_to_uint8(SN(count), sdu->msg); if (is_drb()) { diff --git a/lib/src/upper/pdcp_entity_lte.cc b/lib/src/upper/pdcp_entity_lte.cc index 40ab6d29c..9e77db242 100644 --- a/lib/src/upper/pdcp_entity_lte.cc +++ b/lib/src/upper/pdcp_entity_lte.cc @@ -66,6 +66,11 @@ void pdcp_entity_lte::init(uint32_t lcid_, pdcp_config_t cfg_) cfg.hdr_len_bytes, reordering_window, maximum_pdcp_sn); + + // Check supported config + if (!check_valid_config()) { + log->console("Warning: Invalid PDCP config.\n"); + } } // Reestablishment procedure: 36.323 5.2 @@ -323,7 +328,6 @@ void pdcp_entity_lte::handle_am_drb_pdu(srslte::unique_byte_buffer_t pdu) /**************************************************************************** * Security functions ***************************************************************************/ - void pdcp_entity_lte::get_bearer_status(uint16_t* dlsn, uint16_t* dlhfn, uint16_t* ulsn, uint16_t* ulhfn) { if (cfg.rb_type == PDCP_RB_IS_DRB) { @@ -342,4 +346,28 @@ void pdcp_entity_lte::get_bearer_status(uint16_t* dlsn, uint16_t* dlhfn, uint16_ *ulhfn = (uint16_t)rx_hfn; } +/**************************************************************************** + * Config checking helper + ***************************************************************************/ +bool pdcp_entity_lte::check_valid_config() +{ + if (cfg.sn_len != PDCP_SN_LEN_5 && cfg.sn_len != PDCP_SN_LEN_7 && cfg.sn_len != PDCP_SN_LEN_12) { + log->error("Trying to configure bearer with invalid SN LEN=%d\n", cfg.sn_len); + return false; + } + if (cfg.sn_len == PDCP_SN_LEN_5 && is_drb()) { + log->error("Trying to configure DRB bearer with SN LEN of 5\n"); + return false; + } + if (cfg.sn_len == PDCP_SN_LEN_7 && (is_srb() || !rlc->rb_is_um(lcid))) { + log->error("Trying to configure SRB or RLC AM bearer with SN LEN of 7\n"); + return false; + } + if (cfg.sn_len == PDCP_SN_LEN_12 && is_srb()) { + log->error("Trying to configure SRB with SN LEN of 12.\n"); + return false; + } + return true; +} + } // namespace srslte diff --git a/srsenb/src/stack/rrc/rrc.cc b/srsenb/src/stack/rrc/rrc.cc index 99e9e4fb8..5688c4782 100644 --- a/srsenb/src/stack/rrc/rrc.cc +++ b/srsenb/src/stack/rrc/rrc.cc @@ -1895,20 +1895,14 @@ void rrc::ue::send_connection_reconf(srslte::unique_byte_buffer_t pdu) rnti, lcid, srslte::make_rlc_config_t(conn_reconf->rr_cfg_ded.drb_to_add_mod_list[vec_idx].rlc_cfg)); // Configure DRB1 in PDCP - srslte::pdcp_config_t pdcp_cnfg_drb = srslte::make_drb_pdcp_config_t(drb_id, false); - if (conn_reconf->rr_cfg_ded.drb_to_add_mod_list[vec_idx].pdcp_cfg.rlc_um_present) { - if (conn_reconf->rr_cfg_ded.drb_to_add_mod_list[vec_idx].pdcp_cfg.rlc_um.pdcp_sn_size.value == - pdcp_cfg_s::rlc_um_s_::pdcp_sn_size_e_::len7bits) { - pdcp_cnfg_drb.sn_len = srslte::PDCP_SN_LEN_7; - } - } + srslte::pdcp_config_t pdcp_cnfg_drb = srslte::make_drb_pdcp_config_t(drb_id, false, conn_reconf->rr_cfg_ded.drb_to_add_mod_list[vec_idx].pdcp_cfg); parent->pdcp->add_bearer(rnti, lcid, pdcp_cnfg_drb); parent->pdcp->config_security(rnti, lcid, sec_cfg); parent->pdcp->enable_integrity(rnti, lcid); parent->pdcp->enable_encryption(rnti, lcid); // DRBs have already been configured in GTPU through bearer setup - // Add E-RAB info message for E-RAB 5 (DRB1) + // Add E-RAB info message for the E-RABs std::map::const_iterator it = erab_info_list.find(erab.id); if (it != erab_info_list.end()) { const srslte::unique_byte_buffer_t& erab_info = it->second; diff --git a/srsue/src/stack/rrc/rrc.cc b/srsue/src/stack/rrc/rrc.cc index 21db678dc..748746f0e 100644 --- a/srsue/src/stack/rrc/rrc.cc +++ b/srsue/src/stack/rrc/rrc.cc @@ -2699,21 +2699,15 @@ void rrc::add_drb(drb_to_add_mod_s* drb_cnfg) rrc_log->warning("LCID not present, using %d\n", lcid); } - // Setup PDCP - pdcp_config_t pdcp_cfg = make_drb_pdcp_config_t(drb_cnfg->drb_id, true); + // Setup RLC + rlc->add_bearer(lcid, make_rlc_config_t(drb_cnfg->rlc_cfg)); - if (drb_cnfg->pdcp_cfg.rlc_um_present) { - if (drb_cnfg->pdcp_cfg.rlc_um.pdcp_sn_size == pdcp_cfg_s::rlc_um_s_::pdcp_sn_size_e_::len7bits) { - pdcp_cfg.sn_len = 7; - } - } + // Setup PDCP + pdcp_config_t pdcp_cfg = make_drb_pdcp_config_t(drb_cnfg->drb_id, true, drb_cnfg->pdcp_cfg); pdcp->add_bearer(lcid, pdcp_cfg); pdcp->config_security(lcid, sec_cfg); pdcp->enable_encryption(lcid); - // Setup RLC - rlc->add_bearer(lcid, make_rlc_config_t(drb_cnfg->rlc_cfg)); - // Setup MAC uint8_t log_chan_group = 0; uint8_t priority = 1;