diff --git a/RELEASE_NOTES b/RELEASE_NOTES index d33e8c2c9..04e5442b7 100644 --- a/RELEASE_NOTES +++ b/RELEASE_NOTES @@ -57,6 +57,7 @@ Bugs fixed - Bug 2831 - wifi: runtime channel width switch has no effect - Bug 2836 - wifi: Missing VHT information in radiotap header when A-MPDU is used - Bug 2838 - wifi: ht-wifi-network crashes with RTS/CTS enabled and frequency set to 2.4GHz +- Bug 2840 - lte: Wrong configuration of eNBs and UEs - Bug 2843 - spectrum, wifi: Incorrect channel width and center frequency provided for non-HT PPDUs when building SpectralDensity - Bug 2848 - wifi: Association ID not correctly set upon association - Bug 2849 - lte: Received RLC and PDCP PDUs are missing in the stats files diff --git a/src/lte/doc/source/lte-testing.rst b/src/lte/doc/source/lte-testing.rst index 197cc10ad..b361b74cc 100644 --- a/src/lte/doc/source/lte-testing.rst +++ b/src/lte/doc/source/lte-testing.rst @@ -1601,4 +1601,28 @@ are configured to use the secondary carrier and the component carrier manager is split the data uniformly between primary and secondary carrier. The test consists of checking that the throughput obtained over the different carriers are equal considering a given tolerance. For more details about this test, see the section Carrier aggregation usage example. - + + +Carrier aggregation test for eNB and UE configuration +------------------------------------------------------ + +The test suite ``carrier-aggregation-config-test`` is a system test program, which verifies the +following two cases: + + * When carrier aggregation is enabled and UE carriers configuration is different than the default + configuration done in LteHelper, we check that the UE(s) is configured properly once it receives + RRC Connection Reconfiguration message from eNB. + + * A user can configure 2 or more eNBs and UEs with different configuration parameters, i.e., + each eNB and UE can have different EARFCN and Bandwidths and a UE connects to an eNB with similar DL EARFCN. + In this test, we check with CA enabled but the end results will be the same if carrier aggregation is not + enabled and we have more than one eNBs and UEs with different configurations. + +Since, we do not need EPC to test the configuration, this test only simulates the LTE radio access with RLC SM. +There are two test cases, Test 1 tests that the UE is configured properly after receiving RRC Connection Reconfiguration +message from the eNB, which will overwrite UE default configuration done in LteHelper for the sake of +creating PHY and MAC instances equal to the number of component carriers. Test 2 tests that every eNB or UE in a +simulation scenario can be configured with different EARFCNs and Bandwidths. For both test cases, it also counts +the number of times the hooked trace source ``SCarrierConfigured`` get triggered. As, it reflects how many UEs +got attached to their respective eNB. If the count is not equal to the number of UEs in the scenario, the test fails, +which could be the result of improper UE configuration. diff --git a/src/lte/helper/lte-helper.cc b/src/lte/helper/lte-helper.cc index 364421ad3..186305b71 100644 --- a/src/lte/helper/lte-helper.cc +++ b/src/lte/helper/lte-helper.cc @@ -513,31 +513,39 @@ LteHelper::InstallUeDevice (NodeContainer c) Ptr LteHelper::InstallSingleEnbDevice (Ptr n) { + NS_LOG_FUNCTION (this << n); uint16_t cellId = m_cellIdCounter; // \todo Remove, eNB has no cell ID Ptr dev = m_enbNetDeviceFactory.Create (); Ptr handoverAlgorithm = m_handoverAlgorithmFactory.Create (); - if (m_componentCarrierPhyParams.size() == 0) - { - DoComponentCarrierConfigure (dev->GetUlEarfcn (), dev->GetDlEarfcn (), dev->GetUlBandwidth (), dev->GetDlBandwidth ()); - } + NS_ABORT_MSG_IF (m_componentCarrierPhyParams.size() != 0, "CC map is not clean"); + DoComponentCarrierConfigure (dev->GetUlEarfcn (), dev->GetDlEarfcn (), + dev->GetUlBandwidth (), dev->GetDlBandwidth ()); + NS_ABORT_MSG_IF (m_componentCarrierPhyParams.size() != m_noOfCcs, + "CC map size (" << m_componentCarrierPhyParams.size () << + ") must be equal to number of carriers (" << + m_noOfCcs << ")"); - NS_ASSERT_MSG(m_componentCarrierPhyParams.size()!=0, "Cannot create enb ccm map."); // create component carrier map for this eNb device std::map > ccMap; - for (std::map::iterator it = m_componentCarrierPhyParams.begin (); it != m_componentCarrierPhyParams.end (); ++it) + for (std::map::iterator it = m_componentCarrierPhyParams.begin (); + it != m_componentCarrierPhyParams.end (); + ++it) { - Ptr cc = CreateObject (); - cc->SetUlBandwidth(it->second.GetUlBandwidth()); - cc->SetDlBandwidth(it->second.GetDlBandwidth()); - cc->SetDlEarfcn(it->second.GetDlEarfcn()); - cc->SetUlEarfcn(it->second.GetUlEarfcn()); - cc->SetAsPrimary(it->second.IsPrimary()); + Ptr cc = CreateObject (); + cc->SetUlBandwidth (it->second.GetUlBandwidth ()); + cc->SetDlBandwidth (it->second.GetDlBandwidth ()); + cc->SetDlEarfcn (it->second.GetDlEarfcn ()); + cc->SetUlEarfcn (it->second.GetUlEarfcn ()); + cc->SetAsPrimary (it->second.IsPrimary ()); NS_ABORT_MSG_IF (m_cellIdCounter == 65535, "max num cells exceeded"); cc->SetCellId (m_cellIdCounter++); ccMap [it->first] = cc; } + // CC map is not needed anymore + m_componentCarrierPhyParams.clear (); + NS_ABORT_MSG_IF (m_useCa && ccMap.size()<2, "You have to either specify carriers or disable carrier aggregation"); NS_ASSERT (ccMap.size () == m_noOfCcs); @@ -764,24 +772,38 @@ LteHelper::InstallSingleUeDevice (Ptr n) { NS_LOG_FUNCTION (this); - NS_ABORT_MSG_IF (m_componentCarrierPhyParams.size() == 0 && m_useCa, "If CA is enabled, before call this method you need to install Enbs --> InstallEnbDevice()"); - Ptr dev = m_ueNetDeviceFactory.Create (); + + // Initialize the component carriers with default values in order to initialize MACs and PHYs + // of each component carrier. These values must be updated once the UE is attached to the + // eNB and receives RRC Connection Reconfiguration message. In case of primary carrier or + // a single carrier, these values will be updated once the UE will receive SIB2 and MIB. + NS_ABORT_MSG_IF (m_componentCarrierPhyParams.size() != 0, "CC map is not clean"); + DoComponentCarrierConfigure (dev->GetDlEarfcn () + 18000, dev->GetDlEarfcn (), 25, 25); + NS_ABORT_MSG_IF (m_componentCarrierPhyParams.size() != m_noOfCcs, + "CC map size (" << m_componentCarrierPhyParams.size () << + ") must be equal to number of carriers (" << + m_noOfCcs << ")"); + std::map > ueCcMap; - for (std::map< uint8_t, ComponentCarrier >::iterator it = m_componentCarrierPhyParams.begin() ; it != m_componentCarrierPhyParams.end(); ++it) + for (std::map< uint8_t, ComponentCarrier >::iterator it = m_componentCarrierPhyParams.begin(); + it != m_componentCarrierPhyParams.end(); + ++it) { - Ptr cc = CreateObject (); - cc->SetUlBandwidth ( it->second.GetUlBandwidth ()); - cc->SetDlBandwidth ( it->second.GetDlBandwidth ()); - cc->SetDlEarfcn ( it->second.GetDlEarfcn ()); - cc->SetUlEarfcn ( it->second.GetUlEarfcn ()); - cc->SetAsPrimary (it->second.IsPrimary()); + Ptr cc = CreateObject (); + cc->SetUlBandwidth (it->second.GetUlBandwidth ()); + cc->SetDlBandwidth (it->second.GetDlBandwidth ()); + cc->SetDlEarfcn (it->second.GetDlEarfcn ()); + cc->SetUlEarfcn (it->second.GetUlEarfcn ()); + cc->SetAsPrimary (it->second.IsPrimary ()); Ptr mac = CreateObject (); cc->SetMac (mac); // cc->GetPhy ()->Initialize (); // it is initialized within the LteUeNetDevice::DoInitialize () ueCcMap.insert (std::pair > (it->first, cc)); } + // CC map is not needed anymore + m_componentCarrierPhyParams.clear (); for (std::map >::iterator it = ueCcMap.begin (); it != ueCcMap.end (); ++it) { @@ -887,10 +909,9 @@ LteHelper::InstallSingleUeDevice (Ptr n) it->second->GetPhy ()->SetLteUeCphySapUser (rrc->GetLteUeCphySapUser (it->first)); rrc->SetLteUeCphySapProvider (it->second->GetPhy ()->GetLteUeCphySapProvider (), it->first); it->second->GetPhy ()->SetComponentCarrierId (it->first); - it->second->GetPhy ()->SetLteUePhySapUser (it->second->GetMac ()->GetLteUePhySapUser ()); it->second->GetMac ()->SetLteUePhySapProvider (it->second->GetPhy ()->GetLteUePhySapProvider ()); - + bool ccmTest = ccmUe->SetComponentCarrierMacSapProviders (it->first, it->second->GetMac ()->GetLteMacSapProvider()); if (ccmTest == false) @@ -1282,7 +1303,9 @@ LteHelper::DoDeActivateDedicatedEpsBearer (Ptr ueDevice, Ptr ccHelper = CreateObject (); ccHelper->SetNumberOfComponentCarriers (m_noOfCcs); ccHelper->SetUlEarfcn (ulEarfcn); @@ -1290,7 +1313,7 @@ LteHelper::DoComponentCarrierConfigure (uint32_t ulEarfcn, uint32_t dlEarfcn, ui ccHelper->SetDlBandwidth (dlbw); ccHelper->SetUlBandwidth (ulbw); m_componentCarrierPhyParams = ccHelper->EquallySpacedCcs (); - m_componentCarrierPhyParams.at(0).SetAsPrimary(true); + m_componentCarrierPhyParams.at (0).SetAsPrimary (true); } void diff --git a/src/lte/helper/lte-helper.h b/src/lte/helper/lte-helper.h index d10d1d402..9cd0a87bc 100644 --- a/src/lte/helper/lte-helper.h +++ b/src/lte/helper/lte-helper.h @@ -685,12 +685,12 @@ protected: private: /** - * A private function used for component carrier configuration. + * Configure the component carriers * - * \param ulEarfcn uplink EARFCN - not control on the validity at this point - * \param dlEarfcn downlink EARFCN - not control on the validity at this point - * \param ulbw uplink bandwidth for the current CC - * \param dlbw downlink bandwidth for the current CC + * \param ulEarfcn uplink EARFCN + * \param dlEarfcn downlink EARFCN + * \param ulbw uplink bandwidth for each CC + * \param dlbw downlink bandwidth for each CC */ void DoComponentCarrierConfigure (uint32_t ulEarfcn, uint32_t dlEarfcn, uint8_t ulbw, uint8_t dlbw); /** diff --git a/src/lte/model/lte-ue-rrc.cc b/src/lte/model/lte-ue-rrc.cc index 4fe0abdf1..2e535bcff 100644 --- a/src/lte/model/lte-ue-rrc.cc +++ b/src/lte/model/lte-ue-rrc.cc @@ -277,6 +277,10 @@ LteUeRrc::GetTypeId (void) "trace fired upon failure of a handover procedure", MakeTraceSourceAccessor (&LteUeRrc::m_handoverEndErrorTrace), "ns3::LteUeRrc::ImsiCidRntiTracedCallback") + .AddTraceSource ("SCarrierConfigured", + "trace fired after configuring secondary carriers", + MakeTraceSourceAccessor (&LteUeRrc::m_sCarrierConfiguredTrace), + "ns3::LteUeRrc::SCellConfiguredCallback") ; return tid; } @@ -1231,6 +1235,8 @@ LteUeRrc::ApplyRadioResourceConfigDedicatedSecondaryCarrier (LteRrcSap::NonCriti { NS_LOG_FUNCTION (this); + m_sCellToAddModList = nonCec.sCellsToAddModList; + for(std::list::iterator it = nonCec.sCellsToAddModList.begin(); it!=nonCec.sCellsToAddModList.end(); it++) { LteRrcSap::SCellToAddMod scell = *it; @@ -1258,6 +1264,8 @@ LteUeRrc::ApplyRadioResourceConfigDedicatedSecondaryCarrier (LteRrcSap::NonCriti m_cphySapProvider.at (ccId)->SetPa (paDouble); m_cphySapProvider.at (ccId)->SetSrsConfigurationIndex (srsIndex); } + + m_sCarrierConfiguredTrace (this, m_sCellToAddModList); } void diff --git a/src/lte/model/lte-ue-rrc.h b/src/lte/model/lte-ue-rrc.h index 34c8f2634..2e73d1340 100644 --- a/src/lte/model/lte-ue-rrc.h +++ b/src/lte/model/lte-ue-rrc.h @@ -352,6 +352,15 @@ public: (uint64_t imsi, uint16_t cellId, uint16_t rnti, State oldState, State newState); + /** + * TracedCallback signature for secondary carrier configuration events. + * + * \param [in] Pointer to UE RRC + * \param [in] List of LteRrcSap::SCellToAddMod + */ + typedef void (* SCarrierConfiguredCallback) + (Ptr, std::list); + private: @@ -768,6 +777,7 @@ private: uint32_t m_dlEarfcn; /**< Downlink carrier frequency. */ uint32_t m_ulEarfcn; /**< Uplink carrier frequency. */ + std::list m_sCellToAddModList; /**< Secondary carriers. */ /** * The `MibReceived` trace source. Fired upon reception of Master Information @@ -842,6 +852,12 @@ private: * procedure. Exporting IMSI, cell ID, and RNTI. */ TracedCallback m_handoverEndErrorTrace; + /** + * The `SCarrierConfigured` trace source. Fired after the configuration + * of secondary carriers received through RRC Connection Reconfiguration + * message. + */ + TracedCallback, std::list > m_sCarrierConfiguredTrace; /// True if a connection request by upper layers is pending. bool m_connectionPending; diff --git a/src/lte/test/lte-test-carrier-aggregation-configuration.cc b/src/lte/test/lte-test-carrier-aggregation-configuration.cc new file mode 100644 index 000000000..afc456b79 --- /dev/null +++ b/src/lte/test/lte-test-carrier-aggregation-configuration.cc @@ -0,0 +1,374 @@ +/* -*- Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil; -*- */ +/* + * Copyright (c) 2018 Centre Tecnologic de Telecomunicacions de Catalunya (CTTC) + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License version 2 as + * published by the Free Software Foundation; + * + * This program 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 General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + * + * Author: Zoraze Ali + * + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +using namespace ns3; + +/** + * This test suite verifies following two things: + * + * 1. When CA is enabled and UE carriers configuration is different than the default one, + * we check that the UE is configured properly once it receives + * RRC Connection Reconfiguration message from eNB. + * + * 2. A user can configure 2 or more eNBs and UEs with different configuration parameters, + * i.e, each eNB and UE can have different EARFCN and Bandwidths and a UE connects to + * an eNB with similar DL EARFCN. + * Here we check it with CA enabled but the end results will be the same if CA is not + * enabled and we have more than one eNBs and UEs with different configurations. + * + * Since we do not need EPC to test the configuration, this test only simulates + * the LTE radio access with RLC SM. + * + * Test 1 tests that the UE is configured properly after receiving RRC Connection + * Reconfiguration message from the eNB, which will overwrite UE default configuration + * done in LteHelper for the sake of creating PHY and MAC instances equal to the number + * of component carriers. + * + * Test 2 tests that in a simulation scenario every eNB or UE can be configured with + * different EARFCNs and Bandwidths. This will check that the eNBs and UEs configuration + * is not static, as reported in BUG 2840. + */ + +struct ConfigToCheck +{ + uint16_t m_dlBandwidth; + uint16_t m_ulBandwidth; + uint32_t m_dlEarfcn; + uint32_t m_ulEarfcn; +}; + +NS_LOG_COMPONENT_DEFINE ("TestCarrierAggregationConfig"); + +class CarrierAggregationConfigTestCase : public TestCase +{ +public: + /** + * Constructor + * + * \param numberOfNodes, Total Number of eNBs and UEs + * \param configToCheck, Vector containing all the configurations to check + * \param simulationDuration, Duration of the simulation + */ + CarrierAggregationConfigTestCase (uint32_t numberOfNodes, uint16_t numberOfComponentCarriers, std::vector configToCheck, Time simulationDuration) + : TestCase (BuildNameString (numberOfNodes, numberOfComponentCarriers, configToCheck, simulationDuration)), + m_numberOfNodes(numberOfNodes), + m_numberOfComponentCarriers(numberOfComponentCarriers), + m_configToCheck(configToCheck), + m_simulationDuration (simulationDuration) + { + m_connectionCounter = 0.0; + } + +private: + virtual void DoRun (void); + + std::string BuildNameString (uint32_t numberOfNodes, uint16_t numberOfComponentCarriers, std::vector configToCheck, Time simulationDuration); + void Evaluate (std::string context, Ptr ueRrc, std::list sCellToAddModList); + std::vector > EquallySpacedCcs (); + + uint32_t m_numberOfNodes; + uint16_t m_numberOfComponentCarriers; + std::vector m_configToCheck; + uint32_t m_connectionCounter; + Time m_simulationDuration; + std::vector > m_configToCheckContainer; +}; + +std::string +CarrierAggregationConfigTestCase::BuildNameString (uint32_t numberOfNodes, uint16_t numberOfComponentCarriers, std::vector configToCheck, Time simulationDuration) +{ + std::ostringstream oss; + oss << " nodes " << numberOfNodes << " carriers " << numberOfComponentCarriers + << " configurations " << configToCheck.size () + << " duration " << simulationDuration; + return oss.str (); +} + +std::vector > +CarrierAggregationConfigTestCase::EquallySpacedCcs () +{ + std::vector > configToCheckContainer; + + for (auto &it: m_configToCheck) + { + std::map ccmap; + uint32_t ulEarfcn = it.m_ulEarfcn; + uint32_t dlEarfcn = it.m_dlEarfcn; + uint32_t maxBandwidthRb = std::max (it.m_ulBandwidth, it.m_dlBandwidth); + + // Convert bandwidth from RBs to kHz + uint32_t maxBandwidthKhz = LteSpectrumValueHelper::GetChannelBandwidth (maxBandwidthRb) / 1e3; + + for (uint16_t i = 0; i < m_numberOfComponentCarriers; i++) + { + // Make sure we stay within the same band. + if (LteSpectrumValueHelper::GetUplinkCarrierBand (ulEarfcn) != + LteSpectrumValueHelper::GetUplinkCarrierBand (it.m_ulEarfcn) + || LteSpectrumValueHelper::GetDownlinkCarrierBand (dlEarfcn) != + LteSpectrumValueHelper::GetDownlinkCarrierBand (it.m_dlEarfcn)) + { + NS_FATAL_ERROR ("Band is not wide enough to allocate " << m_numberOfComponentCarriers << " CCs"); + } + + ConfigToCheck cc; + cc.m_dlBandwidth = it.m_dlBandwidth; + cc.m_dlEarfcn = dlEarfcn; + cc.m_ulBandwidth = it.m_ulBandwidth; + cc.m_ulEarfcn = ulEarfcn; + + ccmap.insert (std::pair (i, cc)); + + NS_LOG_INFO ("UL BW: " << it.m_ulBandwidth << + ", DL BW: " << it.m_dlBandwidth << + ", UL Earfcn: " << ulEarfcn << + ", DL Earfcn: " << dlEarfcn); + + // The spacing between the center frequencies of two contiguous CCs should be multiple of 300 kHz. + // Round spacing up to 300 kHz. + uint32_t frequencyShift = 300 * (1 + (maxBandwidthKhz - 1) / 300); + + // Unit of EARFCN corresponds to 100kHz. + uint32_t earfcnShift = frequencyShift / 100; + ulEarfcn += earfcnShift; + dlEarfcn += earfcnShift; + } + + configToCheckContainer.push_back (ccmap); + } + + return configToCheckContainer; +} + +void +CarrierAggregationConfigTestCase::Evaluate (std::string context, Ptr ueRrc, std::list sCellToAddModList) +{ + NS_LOG_INFO ("Secondary carriers configured"); + + uint16_t cellId = ueRrc->GetCellId (); + NS_LOG_INFO ("cellId " << cellId); + NS_LOG_INFO ("m_configToCheckContainer size " << m_configToCheckContainer.size ()); + + ++m_connectionCounter; + + std::map configToCheckMap; + + if (cellId == 1) + { + configToCheckMap = m_configToCheckContainer[cellId-1]; + } + else + { + uint16_t n1 = std::max(cellId, m_numberOfComponentCarriers); + uint16_t n2 = std::min(cellId, m_numberOfComponentCarriers); + configToCheckMap = m_configToCheckContainer[n1-n2]; + } + + NS_LOG_INFO ("PCarrier - UL BW: " << static_cast (ueRrc->GetUlBandwidth ()) << + ", DL BW: " << static_cast (ueRrc->GetDlBandwidth ()) << + ", UL Earfcn: " << ueRrc->GetUlEarfcn () << + ", DL Earfcn: " << ueRrc->GetDlEarfcn ()); + + for (auto scell: sCellToAddModList) + { + NS_LOG_INFO ("SCarrier - UL BW: " << static_cast (scell.radioResourceConfigCommonSCell.ulConfiguration.ulFreqInfo.ulBandwidth)<< + ", DL BW: " << static_cast (scell.radioResourceConfigCommonSCell.nonUlConfiguration.dlBandwidth) << + ", UL Earfcn: " << scell.radioResourceConfigCommonSCell.ulConfiguration.ulFreqInfo.ulCarrierFreq << + ", DL Earfcn: " << scell.cellIdentification.dlCarrierFreq); + } + + ConfigToCheck pCConfig = configToCheckMap[0]; // Primary Carrier + ConfigToCheck sCConfig; // Secondary Carriers + + NS_TEST_ASSERT_MSG_EQ (pCConfig.m_dlBandwidth, static_cast (ueRrc->GetDlBandwidth ()), + "Primary Carrier DL bandwidth configuration failed"); + NS_TEST_ASSERT_MSG_EQ (pCConfig.m_ulBandwidth, static_cast (ueRrc->GetUlBandwidth ()), + "Primary Carrier UL bandwidth configuration failed"); + NS_TEST_ASSERT_MSG_EQ (pCConfig.m_dlEarfcn, ueRrc->GetDlEarfcn (), + "Primary Carrier DL EARFCN configuration failed"); + NS_TEST_ASSERT_MSG_EQ (pCConfig.m_ulEarfcn, ueRrc->GetUlEarfcn (), + "Primary Carrier UL EARFCN configuration failed"); + + uint32_t ConfigToCheckMapIndex = 1; + + for (auto scell: sCellToAddModList) + { + sCConfig = configToCheckMap[ConfigToCheckMapIndex]; + + NS_TEST_ASSERT_MSG_EQ (sCConfig.m_dlBandwidth, static_cast (scell.radioResourceConfigCommonSCell.nonUlConfiguration.dlBandwidth), + "Secondary Carrier DL bandwidth configuration failed"); + NS_TEST_ASSERT_MSG_EQ (sCConfig.m_ulBandwidth, static_cast (scell.radioResourceConfigCommonSCell.ulConfiguration.ulFreqInfo.ulBandwidth), + "Secondary Carrier UL bandwidth configuration failed"); + NS_TEST_ASSERT_MSG_EQ (sCConfig.m_dlEarfcn, scell.cellIdentification.dlCarrierFreq, + "Secondary Carrier DL EARFCN configuration failed"); + NS_TEST_ASSERT_MSG_EQ (sCConfig.m_ulEarfcn, scell.radioResourceConfigCommonSCell.ulConfiguration.ulFreqInfo.ulCarrierFreq, + "Secondary Carrier UL EARFCN configuration failed"); + ConfigToCheckMapIndex++; + } +} + +void +CarrierAggregationConfigTestCase::DoRun () +{ + Config::SetDefault ("ns3::LteHelper::UseCa", BooleanValue (true)); + Config::SetDefault ("ns3::LteHelper::NumberOfComponentCarriers", UintegerValue (m_numberOfComponentCarriers)); + Config::SetDefault ("ns3::LteHelper::EnbComponentCarrierManager", StringValue ("ns3::RrComponentCarrierManager")); + + int64_t stream = 1; + + Ptr lteHelper = CreateObject (); + + // Create Nodes: eNodeB and UE + NodeContainer enbNodes; + NodeContainer ueNodes; + enbNodes.Create (m_numberOfNodes); + ueNodes.Create (m_numberOfNodes); + + uint32_t totalNumberOfNodes = enbNodes.GetN () + ueNodes.GetN (); + + // Install Mobility Model + Ptr positionAlloc = CreateObject (); + for (uint16_t i = 0; i < totalNumberOfNodes; i++) + { + positionAlloc->Add (Vector (2 * i, 0, 0)); + } + + MobilityHelper mobility; + mobility.SetMobilityModel ("ns3::ConstantPositionMobilityModel"); + mobility.SetPositionAllocator (positionAlloc); + + for (uint32_t n = 0; n < m_numberOfNodes; ++n) + { + mobility.Install (enbNodes.Get (n)); + mobility.Install (ueNodes.Get (n)); + } + + ConfigToCheck configuration; + NetDeviceContainer enbDevs; + NetDeviceContainer ueDevs; + + // Set bandwidth, EARFCN and install nodes (eNB and UE) + for (uint32_t i = 0; i < m_configToCheck.size (); ++i) + { + configuration = m_configToCheck[i]; + + lteHelper->SetEnbDeviceAttribute ("DlBandwidth", UintegerValue (configuration.m_dlBandwidth)); + lteHelper->SetEnbDeviceAttribute ("UlBandwidth", UintegerValue (configuration.m_ulBandwidth)); + lteHelper->SetEnbDeviceAttribute ("DlEarfcn", UintegerValue (configuration.m_dlEarfcn)); + lteHelper->SetEnbDeviceAttribute ("UlEarfcn", UintegerValue (configuration.m_ulEarfcn)); + lteHelper->SetUeDeviceAttribute ("DlEarfcn", UintegerValue (configuration.m_dlEarfcn)); + enbDevs.Add (lteHelper->InstallEnbDevice (enbNodes.Get (i))); + lteHelper->AssignStreams (enbDevs, stream); + ueDevs.Add (lteHelper->InstallUeDevice (ueNodes.Get (i))); + lteHelper->AssignStreams (ueDevs, stream); + } + + // Calculate the DlBandwidth, UlBandwidth, DlEarfcn and UlEarfcn to which the values from UE RRC would be compared + m_configToCheckContainer = EquallySpacedCcs (); + + // Attach a UE to an eNB + for(uint32_t k = 0; k < m_numberOfNodes; ++k) + { + lteHelper->Attach (ueDevs.Get (k), enbDevs.Get (k)); + } + + // Activate a data radio bearer + enum EpsBearer::Qci q = EpsBearer::GBR_CONV_VOICE; + EpsBearer bearer (q); + lteHelper->ActivateDataRadioBearer (ueDevs, bearer); + + Config::Connect ("/NodeList/*/DeviceList/*/LteUeRrc/SCarrierConfigured", + MakeCallback (&CarrierAggregationConfigTestCase::Evaluate, this)); + + Simulator::Stop (m_simulationDuration); + Simulator::Run (); + + NS_TEST_ASSERT_MSG_EQ (m_connectionCounter, ueNodes.GetN (), "Not all the UEs were connected"); + + Simulator::Destroy (); +} + + +class CarrierAggregationConfigTestSuite : public TestSuite +{ +public: + CarrierAggregationConfigTestSuite (); +}; + +CarrierAggregationConfigTestSuite::CarrierAggregationConfigTestSuite () + : TestSuite ("lte-carrier-aggregation-configuration", SYSTEM) +{ + std::vector configToCheck; + + // Test1 with 1 eNB and 1 UE. + // We put a configuration different than the default configuration done in LteHelper for the sake of + // creating PHY and MAC instances equal to the number of component carriers. + + ConfigToCheck configToCheckTest1; + configToCheckTest1.m_dlBandwidth = 50; + configToCheckTest1.m_ulBandwidth = 50; + configToCheckTest1.m_dlEarfcn = 300; + configToCheckTest1.m_ulEarfcn = 300+18000; + configToCheck.push_back (configToCheckTest1); + uint32_t numberOfNodes = 1; + uint16_t numberOfComponentCarriers = 2; + Time simulationDuration = Seconds (1); + + AddTestCase (new CarrierAggregationConfigTestCase (numberOfNodes, numberOfComponentCarriers, configToCheck, simulationDuration), TestCase::QUICK); + +// configToCheck.erase(configToCheck.begin(), configToCheck.end()); + configToCheck.clear (); + + // Test2 with 2 eNBs and 2 UEs. + // We decrease the bandwidth so not to exceed maximum band bandwidth of 20 MHz + + configToCheckTest1.m_dlBandwidth = 25; + configToCheckTest1.m_ulBandwidth = 25; + configToCheckTest1.m_dlEarfcn = 300; + configToCheckTest1.m_ulEarfcn = 300+18000; + configToCheck.push_back (configToCheckTest1); + + ConfigToCheck configToCheckTest2; + configToCheckTest2.m_dlBandwidth = 25; + configToCheckTest2.m_ulBandwidth = 25; + configToCheckTest2.m_dlEarfcn = 502; + configToCheckTest2.m_ulEarfcn = 502+18000; + configToCheck.push_back (configToCheckTest2); + numberOfNodes = 2; + simulationDuration = Seconds (2); + + AddTestCase (new CarrierAggregationConfigTestCase (numberOfNodes, numberOfComponentCarriers, configToCheck, simulationDuration), TestCase::QUICK); +} + +static CarrierAggregationConfigTestSuite g_carrierAggregationConfigTestSuite; diff --git a/src/lte/wscript b/src/lte/wscript index fe70dccb3..c3f3e229b 100644 --- a/src/lte/wscript +++ b/src/lte/wscript @@ -191,7 +191,8 @@ def build(bld): 'test/lte-simple-spectrum-phy.cc', 'test/lte-test-carrier-aggregation.cc', 'test/lte-test-aggregation-throughput-scale.cc', - 'test/lte-test-ipv6-routing.cc' + 'test/lte-test-ipv6-routing.cc', + 'test/lte-test-carrier-aggregation-configuration.cc' ] headers = bld(features='ns3header')