mirror of
https://gitlab.eurecom.fr/oai/openairinterface5g.git
synced 2026-07-18 15:10:29 +00:00
Compare commits
145 Commits
NR_UE_enab
...
NR_SRB_Con
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
a9f7c3f89a | ||
|
|
91d88abbfb | ||
|
|
7772a51c07 | ||
|
|
9bba3c795a | ||
|
|
87c83aaf21 | ||
|
|
483f4b2d1b | ||
|
|
dc288b7bc8 | ||
|
|
8cff73dc39 | ||
|
|
5c49c67f98 | ||
|
|
1956fd3b72 | ||
|
|
4649f0f615 | ||
|
|
5880c1f8c7 | ||
|
|
356a4d83e9 | ||
|
|
a5343618cf | ||
|
|
b67badef1b | ||
|
|
41d3892c64 | ||
|
|
62292f892e | ||
|
|
66bc0bac1e | ||
|
|
08e775559b | ||
|
|
a9b76b5341 | ||
|
|
92ba7dc249 | ||
|
|
1ce1e8f82b | ||
|
|
d5f95c6c79 | ||
|
|
ce85677762 | ||
|
|
a21ba6c7dc | ||
|
|
f3c922b1c1 | ||
|
|
028be9e486 | ||
|
|
a6a39d9951 | ||
|
|
bfd2c35c35 | ||
|
|
72cc6b16bf | ||
|
|
592642cb28 | ||
|
|
e15f0b2813 | ||
|
|
fad30fff8a | ||
|
|
49487217bf | ||
|
|
4766f3a629 | ||
|
|
4421bc5665 | ||
|
|
1605266440 | ||
|
|
6030a75a65 | ||
|
|
dfa50d975b | ||
|
|
5697057f0b | ||
|
|
a76ef07a69 | ||
|
|
43ef53cbcf | ||
|
|
46bbb6a943 | ||
|
|
c4dc689249 | ||
|
|
0312db24b4 | ||
|
|
b2722225ab | ||
|
|
fa8e7d9f71 | ||
|
|
d626d4b27f | ||
|
|
bdc83aaac6 | ||
|
|
af35e37c74 | ||
|
|
1fd1853ce7 | ||
|
|
f00e5deb14 | ||
|
|
b4fad9c589 | ||
|
|
e981df3cd8 | ||
|
|
e6ddb5379c | ||
|
|
878b483746 | ||
|
|
9812545c61 | ||
|
|
38516da2dc | ||
|
|
0f378cf3da | ||
|
|
db410e41a6 | ||
|
|
8c421698c4 | ||
|
|
f9d8c922e4 | ||
|
|
602424f616 | ||
|
|
e344a7bd4a | ||
|
|
f6d5e5f95d | ||
|
|
5db27b9305 | ||
|
|
f4f8db4373 | ||
|
|
994229963b | ||
|
|
ac6262e82b | ||
|
|
3b6f720125 | ||
|
|
fefb6148e6 | ||
|
|
84579c5dc0 | ||
|
|
90dc22aea6 | ||
|
|
aa8e695d59 | ||
|
|
079157eb55 | ||
|
|
6ca5753555 | ||
|
|
c180323de4 | ||
|
|
9e428fe6c2 | ||
|
|
45e5be9c44 | ||
|
|
57b28d0732 | ||
|
|
22ac1b9486 | ||
|
|
55495f68bc | ||
|
|
b84880a1fe | ||
|
|
655b7d64f9 | ||
|
|
fbea1eff2b | ||
|
|
c6d6a42484 | ||
|
|
5217b76448 | ||
|
|
457423fe25 | ||
|
|
ad1f8a372e | ||
|
|
97dd024c1d | ||
|
|
c6aae3140e | ||
|
|
8f2c96e6e2 | ||
|
|
d82d881463 | ||
|
|
b331fc9af6 | ||
|
|
118ac391ad | ||
|
|
685837f8de | ||
|
|
3efc7538ac | ||
|
|
c264b2650d | ||
|
|
c948fefec2 | ||
|
|
67b91fec27 | ||
|
|
d797dacaaa | ||
|
|
f86fb5df56 | ||
|
|
b46abe7bcb | ||
|
|
ad44cbdc94 | ||
|
|
b5f58b7d22 | ||
|
|
9c462934d4 | ||
|
|
1aac22879c | ||
|
|
7dac9ba9a0 | ||
|
|
caff16a6d1 | ||
|
|
966569c119 | ||
|
|
49eb710850 | ||
|
|
06578d2d2b | ||
|
|
79632d2f91 | ||
|
|
58bab3f202 | ||
|
|
bc70da119d | ||
|
|
0f3d53e1b9 | ||
|
|
ec988428ac | ||
|
|
bb73d64186 | ||
|
|
e5216cdba3 | ||
|
|
5689cf906a | ||
|
|
679b6be9be | ||
|
|
b0c79092fa | ||
|
|
a02b0b4054 | ||
|
|
a81b655c3f | ||
|
|
b77ecaf2d8 | ||
|
|
15cd202d5f | ||
|
|
ef508433d2 | ||
|
|
4a7ca735da | ||
|
|
b2f4b9828b | ||
|
|
3f02d18f86 | ||
|
|
3c84c4d887 | ||
|
|
7e327ae84a | ||
|
|
05033b0bf4 | ||
|
|
3b3452dcce | ||
|
|
2b22daa445 | ||
|
|
5dc6712cec | ||
|
|
c8b67cb1a1 | ||
|
|
46f1dc9614 | ||
|
|
bdd31eb852 | ||
|
|
8f3adc8bc8 | ||
|
|
85fe26bd80 | ||
|
|
170a8f1702 | ||
|
|
fe4b3c0a21 | ||
|
|
0a375bc044 | ||
|
|
760acd0856 |
@@ -463,9 +463,9 @@ include_directories ("${RRC_FULL_DIR}")
|
||||
|
||||
#NR RRC
|
||||
#######
|
||||
set (NR_RRC_ASN1_VERSION "NR_Rel15" )
|
||||
make_version(NR_RRC_VERSION 15 6 0)
|
||||
set (NR_RRC_GRAMMAR ${OPENAIR2_DIR}/RRC/NR/MESSAGES/asn1c/ASN1_files/nr-rrc-15.6.0.asn1)
|
||||
set (NR_RRC_ASN1_VERSION "NR_Rel16" )
|
||||
make_version(NR_RRC_VERSION 16 1 0)
|
||||
set (NR_RRC_GRAMMAR ${OPENAIR2_DIR}/RRC/NR/MESSAGES/asn1c/ASN1_files/nr-rrc-16.1.0.asn1)
|
||||
add_definitions(-DNR_RRC_VERSION=${NR_RRC_VERSION})
|
||||
set (NR_RRC_FULL_DIR ${asn1_generated_dir}/RRC_${NR_RRC_ASN1_VERSION})
|
||||
|
||||
@@ -544,6 +544,59 @@ add_library(S1AP_ENB
|
||||
add_dependencies(S1AP_ENB rrc_flag s1ap_flag)
|
||||
|
||||
|
||||
# NGAP
|
||||
# Same limitation as described in RRC: unknown generated file list
|
||||
# so we generate it at cmake time
|
||||
##############
|
||||
set (NGAP_RELEASE R15)
|
||||
|
||||
set(NGAP_DIR ${OPENAIR3_DIR}/NGAP)
|
||||
make_version(NGAP_VERSION 15 8 0)
|
||||
set(NGAP_ASN_FILES "ngap-15.8.0.asn1")
|
||||
|
||||
add_definitions(-DNGAP_VERSION=${NGAP_VERSION})
|
||||
set(NGAP_ASN_DIR ${NGAP_DIR}/MESSAGES/ASN1/ASN1_files)
|
||||
set(NGAP_C_DIR ${asn1_generated_dir}/NGAP_${NGAP_RELEASE})
|
||||
|
||||
# Warning: if you modify ASN.1 source file to generate new C files, cmake should be re-run instead of make
|
||||
execute_process(COMMAND ${OPENAIR_CMAKE}/tools/make_asn1c_includes.sh "${NGAP_C_DIR}" "${NGAP_ASN_DIR}/${NGAP_ASN_FILES}" "NGAP_" -fno-include-deps -findirect-choice
|
||||
RESULT_VARIABLE ret)
|
||||
if (NOT ${ret} STREQUAL 0)
|
||||
message(FATAL_ERROR "${ret}: error")
|
||||
endif (NOT ${ret} STREQUAL 0)
|
||||
file(GLOB NGAP_source ${NGAP_C_DIR}/*.c)
|
||||
|
||||
add_custom_target (
|
||||
ngap_flag ALL
|
||||
${OPENAIR_CMAKE}/tools/make_asn1c_includes.sh "${NGAP_C_DIR}" "${NGAP_ASN_DIR}/${NGAP_ASN_FILES}" "NGAP_" -fno-include-deps
|
||||
DEPENDS "${NGAP_ASN_DIR}/${NGAP_ASN_FILES}"
|
||||
)
|
||||
|
||||
add_library(NGAP_LIB
|
||||
${NGAP_source}
|
||||
# ${NGAP_DIR}/ngap_common.c
|
||||
)
|
||||
add_dependencies(NGAP_LIB rrc_flag ngap_flag)
|
||||
|
||||
include_directories ("${NGAP_C_DIR}")
|
||||
include_directories ("${NGAP_DIR}")
|
||||
|
||||
add_library(NGAP_GNB
|
||||
${NGAP_DIR}/ngap_gNB.c
|
||||
${NGAP_DIR}/ngap_gNB_context_management_procedures.c
|
||||
${NGAP_DIR}/ngap_gNB_decoder.c
|
||||
${NGAP_DIR}/ngap_gNB_encoder.c
|
||||
${NGAP_DIR}/ngap_gNB_handlers.c
|
||||
${NGAP_DIR}/ngap_gNB_itti_messaging.c
|
||||
${NGAP_DIR}/ngap_gNB_management_procedures.c
|
||||
${NGAP_DIR}/ngap_gNB_nas_procedures.c
|
||||
${NGAP_DIR}/ngap_gNB_nnsf.c
|
||||
${NGAP_DIR}/ngap_gNB_overload.c
|
||||
${NGAP_DIR}/ngap_gNB_trace.c
|
||||
${NGAP_DIR}/ngap_gNB_ue_context.c
|
||||
)
|
||||
add_dependencies(NGAP_GNB rrc_flag ngap_flag)
|
||||
|
||||
#M2AP
|
||||
# Same limitation as described in RRC/S1AP: unknown generated file list
|
||||
# so we generate it at cmake time
|
||||
@@ -933,6 +986,8 @@ add_boolean_option(MESSAGE_CHART_GENERATOR_PHY False "trace some PHY exchang
|
||||
add_boolean_option(UE_EXPANSION False "enable UE_EXPANSION with max 256 UE")
|
||||
add_boolean_option(PHY_TX_THREAD False "enable UE_EXPANSION with max 256 UE")
|
||||
add_boolean_option(PRE_SCD_THREAD False "enable UE_EXPANSION with max 256 UE")
|
||||
add_boolean_option(UESIM_EXPANSION False "enable UESIM_EXPANSION with max 256 UE")
|
||||
add_boolean_option(ITTI_SIM False "enable itti simulator")
|
||||
|
||||
########################
|
||||
# Include order
|
||||
@@ -1912,6 +1967,7 @@ set(NR_PDCP_SRC
|
||||
${OPENAIR2_DIR}/LAYER2/nr_pdcp/nr_pdcp_ue_manager.c
|
||||
${OPENAIR2_DIR}/LAYER2/nr_pdcp/nr_pdcp_entity.c
|
||||
${OPENAIR2_DIR}/LAYER2/nr_pdcp/nr_pdcp_entity_drb_am.c
|
||||
${OPENAIR2_DIR}/LAYER2/nr_pdcp/nr_pdcp_entity_srb.c
|
||||
)
|
||||
|
||||
set(L2_SRC
|
||||
@@ -1964,6 +2020,7 @@ set(L2_NR_SRC
|
||||
${NR_RRC_DIR}/rrc_gNB_internode.c
|
||||
${NR_RRC_DIR}/rrc_gNB_reconfig.c
|
||||
${NR_RRC_DIR}/rrc_gNB_UE_context.c
|
||||
${NR_RRC_DIR}/rrc_gNB_NGAP.c
|
||||
)
|
||||
|
||||
set(L2_SRC_UE
|
||||
@@ -2454,6 +2511,124 @@ if(NAS_UE)
|
||||
endif()
|
||||
|
||||
|
||||
if(ITTI_SIM)
|
||||
set(libnas_ue_api_OBJS
|
||||
${NAS_SRC}UE/API/USER/at_command.c
|
||||
${NAS_SRC}UE/API/USER/at_error.c
|
||||
${NAS_SRC}UE/API/USER/at_response.c
|
||||
${NAS_SRC}UE/API/USER/user_api.c
|
||||
${NAS_SRC}UE/API/USER/user_indication.c
|
||||
${NAS_SRC}UE/API/USIM/aka_functions.c
|
||||
${NAS_SRC}UE/API/USIM/usim_api.c
|
||||
)
|
||||
set(libnas_ue_emm_OBJS
|
||||
${NAS_SRC}UE/EMM/Attach.c
|
||||
${NAS_SRC}UE/EMM/Authentication.c
|
||||
${NAS_SRC}UE/EMM/Detach.c
|
||||
${NAS_SRC}UE/EMM/emm_main.c
|
||||
${NAS_SRC}UE/EMM/EmmStatusHdl.c
|
||||
${NAS_SRC}UE/EMM/Identification.c
|
||||
${NAS_SRC}UE/EMM/IdleMode.c
|
||||
${NAS_SRC}UE/EMM/LowerLayer.c
|
||||
${NAS_SRC}UE/EMM/SecurityModeControl.c
|
||||
${NAS_SRC}UE/EMM/ServiceRequestHdl.c
|
||||
${NAS_SRC}UE/EMM/TrackingAreaUpdate.c
|
||||
)
|
||||
set(libnas_ue_emm_sap_OBJS
|
||||
${NAS_SRC}UE/EMM/SAP/emm_as.c
|
||||
${NAS_SRC}UE/EMM/SAP/EmmDeregisteredAttachNeeded.c
|
||||
${NAS_SRC}UE/EMM/SAP/EmmDeregisteredAttemptingToAttach.c
|
||||
${NAS_SRC}UE/EMM/SAP/EmmDeregistered.c
|
||||
${NAS_SRC}UE/EMM/SAP/EmmDeregisteredInitiated.c
|
||||
${NAS_SRC}UE/EMM/SAP/EmmDeregisteredLimitedService.c
|
||||
${NAS_SRC}UE/EMM/SAP/EmmDeregisteredNoCellAvailable.c
|
||||
${NAS_SRC}UE/EMM/SAP/EmmDeregisteredNoImsi.c
|
||||
${NAS_SRC}UE/EMM/SAP/EmmDeregisteredNormalService.c
|
||||
${NAS_SRC}UE/EMM/SAP/EmmDeregisteredPlmnSearch.c
|
||||
${NAS_SRC}UE/EMM/SAP/emm_esm.c
|
||||
${NAS_SRC}UE/EMM/SAP/emm_fsm.c
|
||||
${NAS_SRC}UE/EMM/SAP/EmmNull.c
|
||||
${NAS_SRC}UE/EMM/SAP/emm_recv.c
|
||||
${NAS_SRC}UE/EMM/SAP/emm_reg.c
|
||||
${NAS_SRC}UE/EMM/SAP/EmmRegisteredAttemptingToUpdate.c
|
||||
${NAS_SRC}UE/EMM/SAP/EmmRegistered.c
|
||||
${NAS_SRC}UE/EMM/SAP/EmmRegisteredImsiDetachInitiated.c
|
||||
${NAS_SRC}UE/EMM/SAP/EmmRegisteredInitiated.c
|
||||
${NAS_SRC}UE/EMM/SAP/EmmRegisteredLimitedService.c
|
||||
${NAS_SRC}UE/EMM/SAP/EmmRegisteredNoCellAvailable.c
|
||||
${NAS_SRC}UE/EMM/SAP/EmmRegisteredNormalService.c
|
||||
${NAS_SRC}UE/EMM/SAP/EmmRegisteredPlmnSearch.c
|
||||
${NAS_SRC}UE/EMM/SAP/EmmRegisteredUpdateNeeded.c
|
||||
${NAS_SRC}UE/EMM/SAP/emm_sap.c
|
||||
${NAS_SRC}UE/EMM/SAP/emm_send.c
|
||||
${NAS_SRC}UE/EMM/SAP/EmmServiceRequestInitiated.c
|
||||
${NAS_SRC}UE/EMM/SAP/EmmTrackingAreaUpdatingInitiated.c
|
||||
)
|
||||
set (libnas_ue_esm_OBJS
|
||||
${NAS_SRC}UE/ESM/DedicatedEpsBearerContextActivation.c
|
||||
${NAS_SRC}UE/ESM/DefaultEpsBearerContextActivation.c
|
||||
${NAS_SRC}UE/ESM/EpsBearerContextDeactivation.c
|
||||
${NAS_SRC}UE/ESM/esm_ebr.c
|
||||
${NAS_SRC}UE/ESM/esm_ebr_context.c
|
||||
${NAS_SRC}UE/ESM/esm_ip.c
|
||||
${NAS_SRC}UE/ESM/esm_main.c
|
||||
${NAS_SRC}UE/ESM/esm_pt.c
|
||||
${NAS_SRC}UE/ESM/EsmStatusHdl.c
|
||||
${NAS_SRC}UE/ESM/PdnConnectivity.c
|
||||
${NAS_SRC}UE/ESM/PdnDisconnect.c
|
||||
)
|
||||
set(libnas_ue_esm_sap_OBJS
|
||||
${NAS_SRC}UE/ESM/SAP/esm_recv.c
|
||||
${NAS_SRC}UE/ESM/SAP/esm_send.c
|
||||
${NAS_SRC}UE/ESM/SAP/esm_sap.c
|
||||
)
|
||||
|
||||
set(libnrnas_emm_msg_OBJS
|
||||
${NAS_SRC}COMMON/EMM/MSG/RegistrationRequest.c
|
||||
)
|
||||
|
||||
set(libnrnas_ies_OBJS
|
||||
${NAS_SRC}COMMON/IES/ExtendedProtocolDiscriminator.c
|
||||
${NAS_SRC}COMMON/IES/FGSMobileIdentity.c
|
||||
${NAS_SRC}COMMON/IES/FGSRegistrationType.c
|
||||
${NAS_SRC}COMMON/IES/SpareHalfOctet.c
|
||||
${NAS_SRC}COMMON/IES/FGMMCapability.c
|
||||
${NAS_SRC}COMMON/IES/NrUESecurityCapability.c
|
||||
)
|
||||
|
||||
add_library(LIB_NAS_SIMUE
|
||||
${NAS_SRC}UE/nas_itti_messaging.c
|
||||
${NAS_SRC}UE/nas_network.c
|
||||
${NAS_SRC}UE/nas_parser.c
|
||||
${NAS_SRC}UE/nas_proc.c
|
||||
${NAS_SRC}UE/nas_user.c
|
||||
${NAS_SRC}NR_UE/nr_nas_msg_sim.c
|
||||
${libnas_api_OBJS}
|
||||
${libnas_ue_api_OBJS}
|
||||
${libnas_emm_msg_OBJS}
|
||||
${libnas_esm_msg_OBJS}
|
||||
${libnas_ies_OBJS}
|
||||
${libnas_utils_OBJS}
|
||||
${libnas_ue_emm_OBJS}
|
||||
${libnas_ue_emm_sap_OBJS}
|
||||
${libnas_ue_esm_OBJS}
|
||||
${libnas_ue_esm_sap_OBJS}
|
||||
${libnrnas_emm_msg_OBJS}
|
||||
${libnrnas_ies_OBJS}
|
||||
)
|
||||
add_dependencies(LIB_NAS_SIMUE rrc_flag)
|
||||
set(NAS_SIM_LIB LIB_NAS_SIMUE)
|
||||
|
||||
include_directories(${NAS_SRC}NR_UE)
|
||||
include_directories(${NAS_SRC}UE)
|
||||
include_directories(${NAS_SRC}UE/API/USER)
|
||||
include_directories(${NAS_SRC}UE/API/USIM)
|
||||
include_directories(${NAS_SRC}UE/EMM)
|
||||
include_directories(${NAS_SRC}UE/EMM/SAP)
|
||||
include_directories(${NAS_SRC}UE/ESM)
|
||||
include_directories(${NAS_SRC}UE/ESM/SAP)
|
||||
endif()
|
||||
|
||||
# nbiot
|
||||
add_definitions("-DNUMBER_OF_UE_MAX_NB_IoT=16")
|
||||
set (NBIOT_SOURCES
|
||||
@@ -2852,7 +3027,7 @@ target_link_libraries (nr-softmodem
|
||||
-Wl,--start-group
|
||||
UTIL HASHTABLE SCTP_CLIENT UDP SCHED_LIB SCHED_RU_LIB SCHED_NR_LIB PHY_NR PHY PHY_COMMON PHY_NR_COMMON PHY_RU LFDS NR_GTPV1U SECU_CN SECU_OSA
|
||||
${ITTI_LIB} ${FLPT_MSG_LIB} ${ASYNC_IF_LIB} ${FLEXRAN_AGENT_LIB} LFDS7 ${MSC_LIB} ${RAL_LIB} ${NAS_UE_LIB} RRC_LIB NR_RRC_LIB
|
||||
S1AP_LIB S1AP_ENB L2_LTE_NR L2_NR MAC_NR_COMMON NFAPI_COMMON_LIB NFAPI_LIB NFAPI_VNF_LIB NFAPI_PNF_LIB NFAPI_USER_LIB
|
||||
NGAP_LIB NGAP_GNB S1AP_LIB S1AP_ENB L2_LTE_NR L2_NR MAC_NR_COMMON NFAPI_COMMON_LIB NFAPI_LIB NFAPI_VNF_LIB NFAPI_PNF_LIB NFAPI_USER_LIB
|
||||
X2AP_LIB X2AP_ENB F1AP_LIB F1AP M2AP_LIB M2AP_ENB M3AP_LIB M3AP_ENB ${PROTO_AGENT_LIB} ${FSPT_MSG_LIB}
|
||||
-Wl,--end-group z dl)
|
||||
|
||||
@@ -2934,7 +3109,7 @@ add_executable(nr-uesoftmodem
|
||||
|
||||
target_link_libraries (nr-uesoftmodem
|
||||
-Wl,--start-group
|
||||
RRC_LIB NR_RRC_LIB SECU_CN SECU_OSA UTIL HASHTABLE SCTP_CLIENT UDP SCHED_RU_LIB SCHED_UE_LIB SCHED_NR_UE_LIB
|
||||
RRC_LIB NR_RRC_LIB NGAP_LIB NGAP_GNB SECU_CN SECU_OSA UTIL HASHTABLE SCTP_CLIENT UDP SCHED_RU_LIB SCHED_UE_LIB SCHED_NR_UE_LIB
|
||||
PHY_COMMON PHY_NR_COMMON PHY_UE PHY_NR_UE PHY_RU LFDS NR_L2_UE L2_UE_LTE_NR MAC_NR_COMMON NFAPI_COMMON_LIB NFAPI_LIB NFAPI_PNF_LIB
|
||||
NFAPI_USER_LIB S1AP_LIB S1AP_ENB
|
||||
${MSC_LIB} ${RAL_LIB} ${NAS_UE_LIB} ${ITTI_LIB} ${FLPT_MSG_LIB} ${ASYNC_IF_LIB} LFDS7 ${ATLAS_LIBRARIES} LIB_5GNAS_GNB
|
||||
@@ -3246,7 +3421,7 @@ if (${T_TRACER})
|
||||
foreach(i
|
||||
#all "add_executable" definitions (except tests, rb_tool, updatefw)
|
||||
lte-softmodem lte-uesoftmodem nr-softmodem
|
||||
nr-uesoftmodem dlsim dlsim_tm4 dlsim_tm7
|
||||
nr-uesoftmodem dlsim dlsim_tm4 dlsim_tm7 nr-ittisim
|
||||
ulsim pbchsim scansim mbmssim pdcchsim pucchsim prachsim
|
||||
syncsim nr_ulsim nr_dlsim nr_dlschsim nr_pbchsim nr_pucchsim
|
||||
nr_ulschsim ldpctest polartest smallblocktest cu_test du_test
|
||||
@@ -3333,6 +3508,53 @@ add_executable(rb_tool
|
||||
)
|
||||
target_include_directories(rb_tool PRIVATE ${OPENAIR2_DIR}/NETWORK_DRIVER/MESH/)
|
||||
|
||||
# nr-ittisim
|
||||
###################################################
|
||||
|
||||
add_executable(nr-ittisim
|
||||
${rrc_h}
|
||||
${nr_rrc_h}
|
||||
${OPENAIR2_DIR}/GNB_APP/gnb_app.c
|
||||
${OPENAIR2_DIR}/GNB_APP/gnb_config.c
|
||||
${OPENAIR_DIR}/executables/nr-gnb.c
|
||||
${OPENAIR_DIR}/executables/nr-ru.c
|
||||
${OPENAIR2_DIR}/SIMULATION/NR_RRC/itti_sim.c
|
||||
${OPENAIR_DIR}/executables/softmodem-common.c
|
||||
${OPENAIR1_DIR}/SIMULATION/TOOLS/taus.c
|
||||
${OPENAIR_TARGETS}/ARCH/COMMON/common_lib.c
|
||||
${OPENAIR_TARGETS}/ARCH/COMMON/record_player.c
|
||||
${OPENAIR2_DIR}/RRC/NAS/nas_config.c
|
||||
${OPENAIR2_DIR}/RRC/NAS/rb_config.c
|
||||
${OPENAIR3_DIR}/GTPV1-U/gtpv1u_gNB.c
|
||||
${OPENAIR1_DIR}/SIMULATION/ETH_TRANSPORT/netlink_init.c
|
||||
${OPENAIR3_DIR}/NAS/UE/nas_ue_task.c
|
||||
${OPENAIR_DIR}/common/utils/utils.c
|
||||
${OPENAIR_DIR}/common/utils/system.c
|
||||
${OPENAIR_DIR}/common/utils/nr/nr_common.c
|
||||
${OPENAIR_DIR}/common/utils/threadPool/thread-pool.c
|
||||
${GTPU_need_ITTI}
|
||||
${XFORMSINTERFACE_SOURCE}
|
||||
${T_SOURCE}
|
||||
${CONFIG_SOURCES}
|
||||
${SHLIB_LOADER_SOURCES}
|
||||
)
|
||||
|
||||
target_link_libraries (nr-ittisim
|
||||
-Wl,--start-group
|
||||
UTIL HASHTABLE SCTP_CLIENT UDP SCHED_LIB SCHED_RU_LIB SCHED_NR_LIB PHY_NR PHY PHY_COMMON PHY_NR_COMMON PHY_RU LFDS NR_GTPV1U SECU_CN SECU_OSA
|
||||
${ITTI_LIB} ${FLPT_MSG_LIB} ${ASYNC_IF_LIB} ${FLEXRAN_AGENT_LIB} LFDS7 ${MSC_LIB} ${RAL_LIB} ${NAS_SIM_LIB} RRC_LIB NR_RRC_LIB
|
||||
NGAP_LIB NGAP_GNB S1AP_LIB S1AP_ENB L2_LTE_NR L2_NR MAC_NR_COMMON NFAPI_COMMON_LIB NFAPI_LIB NFAPI_VNF_LIB NFAPI_PNF_LIB NFAPI_USER_LIB
|
||||
X2AP_LIB X2AP_ENB F1AP_LIB F1AP M2AP_LIB M2AP_ENB M3AP_LIB M3AP_ENB ${PROTO_AGENT_LIB} ${FSPT_MSG_LIB}
|
||||
NR_L2_UE
|
||||
-Wl,--end-group z dl)
|
||||
|
||||
target_link_libraries (nr-ittisim ${LIBXML2_LIBRARIES})
|
||||
target_link_libraries (nr-ittisim pthread m ${CONFIG_LIB} rt crypt ${CRYPTO_LIBRARIES} ${OPENSSL_LIBRARIES} ${NETTLE_LIBRARIES} sctp ${XFORMS_LIBRARIES} ${PROTOBUF_LIB} ${CMAKE_DL_LIBS} ${LIBYAML_LIBRARIES} ${ATLAS_LIBRARIES})
|
||||
target_link_libraries (nr-ittisim ${LIB_LMS_LIBRARIES})
|
||||
target_link_libraries (nr-ittisim ${T_LIB})
|
||||
|
||||
add_dependencies( nr-ittisim ldpc_orig ldpc_optim ldpc_optim8seg ldpc )
|
||||
|
||||
# ???
|
||||
####################
|
||||
list(APPEND oai_nw_drv_src device.c common.c ioctl.c classifier.c tool.c)
|
||||
|
||||
@@ -66,6 +66,7 @@ UE_TIMING_TRACE="False"
|
||||
USRP_REC_PLAY="False"
|
||||
BUILD_ECLIPSE=0
|
||||
NR="False"
|
||||
ITTI_SIM="False"
|
||||
OPTIONAL_LIBRARIES="telnetsrv enbscope uescope nrscope msc"
|
||||
trap handle_ctrl_c INT
|
||||
|
||||
@@ -159,6 +160,8 @@ Options
|
||||
Build for I/Q record-playback modes
|
||||
-k | --skip-shared-libraries
|
||||
Skip build for shared libraries to reduce compilation time when building frequently for debugging purposes
|
||||
--ittiSIM
|
||||
Makes the itti simulator
|
||||
-h | --help
|
||||
Print this help
|
||||
|
||||
@@ -413,6 +416,11 @@ function main() {
|
||||
CMAKE_CMD="$CMAKE_CMD -GNinja"
|
||||
MAKE_CMD=ninja
|
||||
shift;;
|
||||
--ittiSIM)
|
||||
ittiSIM=1
|
||||
ITTI_SIM="True"
|
||||
echo_info "Will compile itti simulator"
|
||||
shift;;
|
||||
-h | --help)
|
||||
print_help
|
||||
exit 1;;
|
||||
@@ -571,7 +579,7 @@ function main() {
|
||||
config_libconfig_shlib=params_libconfig
|
||||
|
||||
# first generate the CMakefile in the right directory
|
||||
if [ "$eNB" = "1" -o "$eNBocp" = "1" -o "$UE" = "1" -o "$gNB" = "1" -o "$nrUE" = "1" -o "$HW" = "EXMIMO" ] ; then
|
||||
if [ "$eNB" = "1" -o "$eNBocp" = "1" -o "$UE" = "1" -o "$gNB" = "1" -o "$nrUE" = "1" -o "$HW" = "EXMIMO" -o "$ittiSIM" = "1" ] ; then
|
||||
|
||||
# softmodem compilation
|
||||
|
||||
@@ -595,6 +603,7 @@ function main() {
|
||||
echo "set ( UE_TIMING_TRACE $UE_TIMING_TRACE )" >> $cmake_file
|
||||
echo "set ( USRP_REC_PLAY $USRP_REC_PLAY )" >> $cmake_file
|
||||
echo "set ( SKIP_SHARED_LIB_FLAG $SKIP_SHARED_LIB_FLAG )" >> $cmake_file
|
||||
echo "set ( ITTI_SIM $ITTI_SIM )" >> $cmake_file
|
||||
echo 'include(${CMAKE_CURRENT_SOURCE_DIR}/../CMakeLists.txt)' >> $cmake_file
|
||||
cd $DIR/$build_dir/build
|
||||
eval $CMAKE_CMD
|
||||
@@ -616,6 +625,10 @@ function main() {
|
||||
execlist="$execlist nr-uesoftmodem"
|
||||
fi
|
||||
|
||||
if [ "$ittiSIM" = "1" ] ; then
|
||||
execlist="$execlist nr-ittisim"
|
||||
fi
|
||||
|
||||
for f in $execlist ; do
|
||||
echo_info "Compiling $f..."
|
||||
compilations \
|
||||
|
||||
@@ -16,4 +16,5 @@ set ( UE_DEBUG_TRACE False )
|
||||
set ( UE_TIMING_TRACE False )
|
||||
set ( USRP_REC_PLAY False )
|
||||
set ( SKIP_SHARED_LIB_FLAG False )
|
||||
set ( PHYSIM True)
|
||||
include(${CMAKE_CURRENT_SOURCE_DIR}/../CMakeLists.txt)
|
||||
|
||||
@@ -19,6 +19,10 @@ if [ "$done_flag" -ot $ASN1_SOURCE_DIR ] ; then
|
||||
sed -i 's/18446744073709551615))/18446744073709551615U))/g' "$GENERATED_FULL_DIR"/${ASN1C_PREFIX}E-RABUsageReportItem.c
|
||||
sed -i 's/18446744073709551615 }/18446744073709551615U }/g' "$GENERATED_FULL_DIR"/${ASN1C_PREFIX}E-RABUsageReportItem.c
|
||||
fi
|
||||
if [ "$ASN1C_PREFIX" = "NGAP_" ] ; then
|
||||
sed -i 's/18446744073709551615))/18446744073709551615U))/g' "$GENERATED_FULL_DIR"/${ASN1C_PREFIX}VolumeTimedReport-Item.c
|
||||
sed -i 's/18446744073709551615 }/18446744073709551615U }/g' "$GENERATED_FULL_DIR"/${ASN1C_PREFIX}VolumeTimedReport-Item.c
|
||||
fi
|
||||
|
||||
fi
|
||||
touch $done_flag
|
||||
|
||||
@@ -445,6 +445,7 @@ int logInit (void)
|
||||
register_log_component("NR_RRC","log",NR_RRC);
|
||||
register_log_component("NR_MAC","log",NR_MAC);
|
||||
register_log_component("NR_PHY","log",NR_PHY);
|
||||
register_log_component("NGAP","",NGAP);
|
||||
|
||||
for (int i=0 ; log_level_names[i].name != NULL ; i++)
|
||||
g_log->level2string[i] = toupper(log_level_names[i].name[0]); // uppercased first letter of level name
|
||||
|
||||
@@ -226,6 +226,7 @@ typedef enum {
|
||||
X2AP,
|
||||
M2AP,
|
||||
M3AP,
|
||||
NGAP,
|
||||
GNB_APP,
|
||||
NR_RRC,
|
||||
NR_MAC,
|
||||
|
||||
@@ -400,6 +400,27 @@ ID = LEGACY_S1AP_TRACE
|
||||
GROUP = ALL:LEGACY_S1AP:LEGACY_GROUP_TRACE:LEGACY
|
||||
FORMAT = string,log
|
||||
|
||||
ID = LEGACY_NGAP_INFO
|
||||
DESC = NGAP legacy logs - info level
|
||||
GROUP = ALL:LEGACY_NGAP:LEGACY_GROUP_INFO:LEGACY
|
||||
FORMAT = string,log
|
||||
ID = LEGACY_NGAP_ERROR
|
||||
DESC = NGAP legacy logs - error level
|
||||
GROUP = ALL:LEGACY_NGAP:LEGACY_GROUP_ERROR:LEGACY
|
||||
FORMAT = string,log
|
||||
ID = LEGACY_NGAP_WARNING
|
||||
DESC = NGAP legacy logs - warning level
|
||||
GROUP = ALL:LEGACY_NGAP:LEGACY_GROUP_WARNING:LEGACY
|
||||
FORMAT = string,log
|
||||
ID = LEGACY_NGAP_DEBUG
|
||||
DESC = NGAP legacy logs - debug level
|
||||
GROUP = ALL:LEGACY_NGAP:LEGACY_GROUP_DEBUG:LEGACY
|
||||
FORMAT = string,log
|
||||
ID = LEGACY_NGAP_TRACE
|
||||
DESC = NGAP legacy logs - trace level
|
||||
GROUP = ALL:LEGACY_NGAP:LEGACY_GROUP_TRACE:LEGACY
|
||||
FORMAT = string,log
|
||||
|
||||
ID = LEGACY_X2AP_INFO
|
||||
DESC = X2AP legacy logs - info level
|
||||
GROUP = ALL:LEGACY_X2AP:LEGACY_GROUP_INFO:LEGACY
|
||||
|
||||
@@ -49,11 +49,14 @@ typedef enum {
|
||||
MSC_RLC_ENB,
|
||||
MSC_PDCP_ENB,
|
||||
MSC_RRC_ENB,
|
||||
MSC_RRC_GNB,
|
||||
MSC_IP_ENB,
|
||||
MSC_S1AP_ENB,
|
||||
MSC_NGAP_GNB,
|
||||
MSC_GTPU_ENB,
|
||||
MSC_GTPU_SGW,
|
||||
MSC_S1AP_MME,
|
||||
MSC_NGAP_AMF,
|
||||
MSC_MMEAPP_MME,
|
||||
MSC_NAS_MME,
|
||||
MSC_NAS_EMM_MME,
|
||||
|
||||
@@ -16,3 +16,8 @@
|
||||
#include "openair2/COMMON/gtpv1_u_messages_def.h"
|
||||
#include "openair2/COMMON/flexran_messages_def.h"
|
||||
#include "openair2/COMMON/f1ap_messages_def.h"
|
||||
#include "openair2/COMMON/ngap_messages_def.h"
|
||||
#if ITTI_SIM
|
||||
#include "openair2/COMMON/itti_sim_messages_def.h"
|
||||
#endif
|
||||
|
||||
|
||||
@@ -230,6 +230,7 @@ typedef struct IttiMsgText_s {
|
||||
#include <openair2/COMMON/sctp_messages_types.h>
|
||||
#include <openair2/COMMON/udp_messages_types.h>
|
||||
#include <openair2/COMMON/gtpv1_u_messages_types.h>
|
||||
#include <openair2/COMMON/ngap_messages_types.h>
|
||||
#include <openair3/SCTP/sctp_eNB_task.h>
|
||||
#include <openair3/NAS/UE/nas_proc_defs.h>
|
||||
#include <openair3/NAS/UE/ESM/esmData.h>
|
||||
@@ -260,6 +261,11 @@ typedef struct IttiMsgText_s {
|
||||
void *rrc_enb_process_itti_msg(void *);
|
||||
#include <openair3/SCTP/sctp_eNB_task.h>
|
||||
#include <openair3/S1AP/s1ap_eNB.h>
|
||||
#include <openair3/NGAP/ngap_gNB.h>
|
||||
|
||||
#ifdef ITTI_SIM
|
||||
#include <openair2/COMMON/itti_sim_messages_types.h>
|
||||
#endif
|
||||
|
||||
/*
|
||||
static const char *const messages_definition_xml = {
|
||||
@@ -312,6 +318,7 @@ void * rrc_enb_process_msg(void*);
|
||||
TASK_DEF(TASK_RRC_GNB, TASK_PRIORITY_MED, 200, NULL,NULL)\
|
||||
TASK_DEF(TASK_RAL_ENB, TASK_PRIORITY_MED, 200, NULL, NULL) \
|
||||
TASK_DEF(TASK_S1AP, TASK_PRIORITY_MED, 200, NULL, NULL) \
|
||||
TASK_DEF(TASK_NGAP, TASK_PRIORITY_MED, 200, NULL, NULL) \
|
||||
TASK_DEF(TASK_X2AP, TASK_PRIORITY_MED, 200, NULL, NULL) \
|
||||
TASK_DEF(TASK_M2AP_ENB, TASK_PRIORITY_MED, 200, NULL, NULL) \
|
||||
TASK_DEF(TASK_M2AP_MCE, TASK_PRIORITY_MED, 200, NULL, NULL) \
|
||||
@@ -329,6 +336,7 @@ void * rrc_enb_process_msg(void*);
|
||||
TASK_DEF(TASK_RLC_UE, TASK_PRIORITY_MED, 200, NULL, NULL) \
|
||||
TASK_DEF(TASK_PDCP_UE, TASK_PRIORITY_MED, 200, NULL, NULL) \
|
||||
TASK_DEF(TASK_RRC_UE, TASK_PRIORITY_MED, 200, NULL, NULL) \
|
||||
TASK_DEF(TASK_RRC_NRUE, TASK_PRIORITY_MED, 200, NULL, NULL) \
|
||||
TASK_DEF(TASK_NAS_UE, TASK_PRIORITY_MED, 200, NULL, NULL) \
|
||||
TASK_DEF(TASK_RAL_UE, TASK_PRIORITY_MED, 200, NULL, NULL) \
|
||||
TASK_DEF(TASK_MSC, TASK_PRIORITY_MED, 200, NULL, NULL)\
|
||||
@@ -336,6 +344,8 @@ void * rrc_enb_process_msg(void*);
|
||||
TASK_DEF(TASK_UDP, TASK_PRIORITY_MED, 1000, NULL, NULL)\
|
||||
TASK_DEF(TASK_CU_F1, TASK_PRIORITY_MED, 200, NULL, NULL) \
|
||||
TASK_DEF(TASK_DU_F1, TASK_PRIORITY_MED, 200, NULL, NULL) \
|
||||
TASK_DEF(TASK_RRC_UE_SIM, TASK_PRIORITY_MED, 200, NULL, NULL) \
|
||||
TASK_DEF(TASK_RRC_GNB_SIM, TASK_PRIORITY_MED, 200, NULL, NULL) \
|
||||
TASK_DEF(TASK_MAX, TASK_PRIORITY_MED, 200, NULL, NULL)
|
||||
|
||||
#define TASK_DEF(TaskID, pRIO, qUEUEsIZE, FuNc, ThreadFunc) { pRIO, qUEUEsIZE, #TaskID, FuNc, ThreadFunc },
|
||||
|
||||
@@ -83,6 +83,8 @@ unsigned short config_frames[4] = {2,9,11,13};
|
||||
#include "executables/thread-common.h"
|
||||
#include "NB_IoT_interface.h"
|
||||
#include "x2ap_eNB.h"
|
||||
#include "ngap_gNB.h"
|
||||
#include "gnb_paramdef.h"
|
||||
|
||||
pthread_cond_t nfapi_sync_cond;
|
||||
pthread_mutex_t nfapi_sync_mutex;
|
||||
@@ -387,30 +389,52 @@ int create_gNB_tasks(uint32_t gnb_nb) {
|
||||
return -1;
|
||||
}*/
|
||||
if(itti_create_task(TASK_SCTP, sctp_eNB_task, NULL) < 0){
|
||||
LOG_E(SCTP, "Create task for SCTP failed\n");
|
||||
return -1;
|
||||
LOG_E(SCTP, "Create task for SCTP failed\n");
|
||||
return -1;
|
||||
}
|
||||
if (is_x2ap_enabled()) {
|
||||
if(itti_create_task(TASK_X2AP, x2ap_task, NULL) < 0){
|
||||
LOG_E(X2AP, "Create task for X2AP failed\n");
|
||||
}
|
||||
if(itti_create_task(TASK_X2AP, x2ap_task, NULL) < 0){
|
||||
LOG_E(X2AP, "Create task for X2AP failed\n");
|
||||
}
|
||||
}
|
||||
else {
|
||||
LOG_I(X2AP, "X2AP is disabled.\n");
|
||||
LOG_I(X2AP, "X2AP is disabled.\n");
|
||||
}
|
||||
}
|
||||
|
||||
paramdef_t NETParams[] = GNBNETPARAMS_DESC;
|
||||
char aprefix[MAX_OPTNAME_SIZE*2 + 8];
|
||||
sprintf(aprefix,"%s.[%i].%s",GNB_CONFIG_STRING_GNB_LIST,0,GNB_CONFIG_STRING_NETWORK_INTERFACES_CONFIG);
|
||||
config_get( NETParams,sizeof(NETParams)/sizeof(paramdef_t),aprefix);
|
||||
|
||||
if (EPC_MODE_ENABLED && (get_softmodem_params()->phy_test==0 && get_softmodem_params()->do_ra==0)) {
|
||||
for(int i = GNB_INTERFACE_NAME_FOR_NG_AMF_IDX; i <= GNB_IPV4_ADDRESS_FOR_NG_AMF_IDX; i++){
|
||||
if( NETParams[i].strptr == NULL){
|
||||
LOG_E(NGAP, "No configuration in the file.\n");
|
||||
NGAP_CONF_MODE = 0;
|
||||
}
|
||||
else {
|
||||
LOG_D(NGAP, "Configuration in the file: %s.\n",*NETParams[i].strptr);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
if (AMF_MODE_ENABLED && (get_softmodem_params()->phy_test==0 && get_softmodem_params()->do_ra==0)) {
|
||||
if (gnb_nb > 0) {
|
||||
/*if (itti_create_task (TASK_SCTP, sctp_eNB_task, NULL) < 0) {
|
||||
/*
|
||||
if (itti_create_task (TASK_SCTP, sctp_eNB_task, NULL) < 0) {
|
||||
LOG_E(SCTP, "Create task for SCTP failed\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (itti_create_task (TASK_S1AP, s1ap_eNB_task, NULL) < 0) {
|
||||
LOG_E(S1AP, "Create task for S1AP failed\n");
|
||||
return -1;
|
||||
}*/
|
||||
*/
|
||||
if(NGAP_CONF_MODE){
|
||||
if (itti_create_task (TASK_NGAP, ngap_gNB_task, NULL) < 0) {
|
||||
LOG_E(NGAP, "Create task for NGAP failed\n");
|
||||
return -1;
|
||||
}
|
||||
} else {
|
||||
LOG_E(NGAP, "Ngap task not created\n");
|
||||
}
|
||||
|
||||
|
||||
if(!emulate_rf){
|
||||
@@ -430,9 +454,9 @@ int create_gNB_tasks(uint32_t gnb_nb) {
|
||||
|
||||
if (gnb_nb > 0) {
|
||||
if (itti_create_task (TASK_GNB_APP, gNB_app_task, NULL) < 0) {
|
||||
LOG_E(GNB_APP, "Create task for gNB APP failed\n");
|
||||
return -1;
|
||||
}
|
||||
LOG_E(GNB_APP, "Create task for gNB APP failed\n");
|
||||
return -1;
|
||||
}
|
||||
LOG_I(NR_RRC,"Creating NR RRC gNB Task\n");
|
||||
|
||||
if (itti_create_task (TASK_RRC_GNB, rrc_gnb_task, NULL) < 0) {
|
||||
@@ -821,7 +845,8 @@ int main( int argc, char **argv )
|
||||
}
|
||||
|
||||
openair0_cfg[0].threequarter_fs = threequarter_fs;
|
||||
EPC_MODE_ENABLED = !IS_SOFTMODEM_NOS1; //!get_softmodem_params()->phy_test;
|
||||
AMF_MODE_ENABLED = !IS_SOFTMODEM_NOS1; //!get_softmodem_params()->phy_test;
|
||||
NGAP_CONF_MODE = !IS_SOFTMODEM_NOS1; //!get_softmodem_params()->phy_test;
|
||||
|
||||
if (get_softmodem_params()->do_ra)
|
||||
AssertFatal(get_softmodem_params()->phy_test == 0,"RA and phy_test are mutually exclusive\n");
|
||||
|
||||
@@ -44,7 +44,7 @@
|
||||
#define OPENAIR_THREAD_STACK_SIZE PTHREAD_STACK_MIN //4096 //RTL_PTHREAD_STACK_MIN*6
|
||||
//#define DLC_THREAD_STACK_SIZE 4096 //DLC stack size
|
||||
//#define UE_SLOT_PARALLELISATION
|
||||
#define UE_DLSCH_PARALLELISATION
|
||||
//#define UE_DLSCH_PARALLELISATION
|
||||
|
||||
/*enum openair_SCHED_STATUS {
|
||||
openair_SCHED_STOPPED=1,
|
||||
|
||||
@@ -1124,7 +1124,7 @@ int find_pucch_resource_set(NR_UE_MAC_INST_t *mac, uint8_t gNB_id, int uci_size)
|
||||
break;
|
||||
}
|
||||
else {
|
||||
pucch_resource_set_id = 1;
|
||||
pucch_resource_set_id = 1;
|
||||
return (pucch_resource_set_id);
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -235,8 +235,8 @@ void fill_scc(NR_ServingCellConfigCommon_t *scc,uint64_t *ssb_bitmap,int N_RB_DL
|
||||
|
||||
void fix_scc(NR_ServingCellConfigCommon_t *scc,uint64_t ssbmap);
|
||||
void prepare_scc(NR_ServingCellConfigCommon_t *scc);
|
||||
s1ap_eNB_config_t s1ap_config;
|
||||
uint32_t s1ap_generate_eNB_id(void) {return 0;}
|
||||
ngap_gNB_config_t ngap_config;
|
||||
uint32_t ngap_generate_gNB_id(void) {return 0;}
|
||||
void configure_nfapi_pnf(char *vnf_ip_addr, int vnf_p5_port, char *pnf_ip_addr, int pnf_p7_port, int vnf_p7_port) { return;}
|
||||
void configure_nfapi_vnf(char *vnf_addr, int vnf_p5_port) { return;}
|
||||
|
||||
|
||||
17
openair2/COMMON/itti_sim_messages_def.h
Normal file
17
openair2/COMMON/itti_sim_messages_def.h
Normal file
@@ -0,0 +1,17 @@
|
||||
/*!
|
||||
\file itti_sim_messages_def.h
|
||||
|
||||
\brief itti message for itti simulator
|
||||
\author Yoshio INOUE, Masayuki HARADA
|
||||
\email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com
|
||||
\date 2020
|
||||
\version 0.1
|
||||
*/
|
||||
|
||||
|
||||
|
||||
MESSAGE_DEF(GNB_RRC_BCCH_DATA_IND, MESSAGE_PRIORITY_MED, itti_sim_rrc_ch_t, GNBBCCHind)
|
||||
MESSAGE_DEF(GNB_RRC_CCCH_DATA_IND, MESSAGE_PRIORITY_MED, itti_sim_rrc_ch_t, GNBCCCHind)
|
||||
MESSAGE_DEF(GNB_RRC_DCCH_DATA_IND, MESSAGE_PRIORITY_MED, itti_sim_rrc_ch_t, GNBDCCHind)
|
||||
MESSAGE_DEF(UE_RRC_CCCH_DATA_IND, MESSAGE_PRIORITY_MED, itti_sim_rrc_ch_t, UECCCHind)
|
||||
MESSAGE_DEF(UE_RRC_DCCH_DATA_IND, MESSAGE_PRIORITY_MED, itti_sim_rrc_ch_t, UEDCCHind)
|
||||
32
openair2/COMMON/itti_sim_messages_types.h
Normal file
32
openair2/COMMON/itti_sim_messages_types.h
Normal file
@@ -0,0 +1,32 @@
|
||||
/*!
|
||||
\file itti_sim_messages_types.h
|
||||
|
||||
\brief itti message for itti simulator
|
||||
\author Yoshio INOUE, Masayuki HARADA
|
||||
\email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com
|
||||
\date 2020
|
||||
\version 0.1
|
||||
*/
|
||||
|
||||
#ifndef ITTI_SIM_MESSAGES_TYPES_H_
|
||||
#define ITTI_SIM_MESSAGES_TYPES_H_
|
||||
|
||||
#include "LTE_asn_constant.h"
|
||||
|
||||
|
||||
|
||||
#define GNB_RRC_BCCH_DATA_IND(mSGpTR) (mSGpTR)->ittiMsg.GNBBCCHind
|
||||
#define GNB_RRC_CCCH_DATA_IND(mSGpTR) (mSGpTR)->ittiMsg.GNBCCCHind
|
||||
#define GNB_RRC_DCCH_DATA_IND(mSGpTR) (mSGpTR)->ittiMsg.GNBDCCHind
|
||||
#define UE_RRC_CCCH_DATA_IND(mSGpTR) (mSGpTR)->ittiMsg.UECCCHind
|
||||
#define UE_RRC_DCCH_DATA_IND(mSGpTR) (mSGpTR)->ittiMsg.UEDCCHind
|
||||
|
||||
|
||||
|
||||
typedef struct itti_sim_rrc_ch_s {
|
||||
rb_id_t rbid;
|
||||
uint8_t *sdu;
|
||||
int size;
|
||||
} itti_sim_rrc_ch_t;
|
||||
|
||||
#endif /* ITTI_SIM_MESSAGES_TYPES_H_ */
|
||||
@@ -41,10 +41,16 @@ MESSAGE_DEF(RRC_MAC_CCCH_DATA_REQ, MESSAGE_PRIORITY_MED_PLUS, RrcMacCcchDat
|
||||
MESSAGE_DEF(RRC_MAC_CCCH_DATA_CNF, MESSAGE_PRIORITY_MED_PLUS, RrcMacCcchDataCnf, rrc_mac_ccch_data_cnf)
|
||||
MESSAGE_DEF(RRC_MAC_CCCH_DATA_IND, MESSAGE_PRIORITY_MED_PLUS, RrcMacCcchDataInd, rrc_mac_ccch_data_ind)
|
||||
|
||||
|
||||
MESSAGE_DEF(RRC_MAC_MCCH_DATA_REQ, MESSAGE_PRIORITY_MED_PLUS, RrcMacMcchDataReq, rrc_mac_mcch_data_req)
|
||||
MESSAGE_DEF(RRC_MAC_MCCH_DATA_IND, MESSAGE_PRIORITY_MED_PLUS, RrcMacMcchDataInd, rrc_mac_mcch_data_ind)
|
||||
|
||||
MESSAGE_DEF(RRC_MAC_PCCH_DATA_REQ, MESSAGE_PRIORITY_MED_PLUS, RrcMacPcchDataReq, rrc_mac_pcch_data_req)
|
||||
|
||||
/* RRC configures DRX context (MAC timers) of a UE */
|
||||
MESSAGE_DEF(RRC_MAC_DRX_CONFIG_REQ, MESSAGE_PRIORITY_MED, rrc_mac_drx_config_req_t, rrc_mac_drx_config_req)
|
||||
MESSAGE_DEF(RRC_MAC_DRX_CONFIG_REQ, MESSAGE_PRIORITY_MED, rrc_mac_drx_config_req_t, rrc_mac_drx_config_req)
|
||||
|
||||
// gNB
|
||||
MESSAGE_DEF(NR_RRC_MAC_CCCH_DATA_IND, MESSAGE_PRIORITY_MED_PLUS, NRRrcMacCcchDataInd, nr_rrc_mac_ccch_data_ind)
|
||||
MESSAGE_DEF(NR_RRC_MAC_BCCH_DATA_IND, MESSAGE_PRIORITY_MED_PLUS, NRRrcMacBcchDataInd, nr_rrc_mac_bcch_data_ind)
|
||||
|
||||
|
||||
@@ -38,6 +38,7 @@
|
||||
|
||||
#define RRC_MAC_BCCH_DATA_REQ(mSGpTR) (mSGpTR)->ittiMsg.rrc_mac_bcch_data_req
|
||||
#define RRC_MAC_BCCH_DATA_IND(mSGpTR) (mSGpTR)->ittiMsg.rrc_mac_bcch_data_ind
|
||||
#define NR_RRC_MAC_BCCH_DATA_IND(mSGpTR) (mSGpTR)->ittiMsg.nr_rrc_mac_bcch_data_ind
|
||||
|
||||
#define RRC_MAC_BCCH_MBMS_DATA_REQ(mSGpTR) (mSGpTR)->ittiMsg.rrc_mac_bcch_mbms_data_req
|
||||
#define RRC_MAC_BCCH_MBMS_DATA_IND(mSGpTR) (mSGpTR)->ittiMsg.rrc_mac_bcch_mbms_data_ind
|
||||
@@ -45,6 +46,7 @@
|
||||
#define RRC_MAC_CCCH_DATA_REQ(mSGpTR) (mSGpTR)->ittiMsg.rrc_mac_ccch_data_req
|
||||
#define RRC_MAC_CCCH_DATA_CNF(mSGpTR) (mSGpTR)->ittiMsg.rrc_mac_ccch_data_cnf
|
||||
#define RRC_MAC_CCCH_DATA_IND(mSGpTR) (mSGpTR)->ittiMsg.rrc_mac_ccch_data_ind
|
||||
#define NR_RRC_MAC_CCCH_DATA_IND(mSGpTR) (mSGpTR)->ittiMsg.nr_rrc_mac_ccch_data_ind
|
||||
|
||||
#define RRC_MAC_MCCH_DATA_REQ(mSGpTR) (mSGpTR)->ittiMsg.rrc_mac_mcch_data_req
|
||||
#define RRC_MAC_MCCH_DATA_IND(mSGpTR) (mSGpTR)->ittiMsg.rrc_mac_mcch_data_ind
|
||||
@@ -86,6 +88,15 @@ typedef struct RrcMacBcchDataInd_s {
|
||||
uint8_t rsrp;
|
||||
} RrcMacBcchDataInd;
|
||||
|
||||
typedef struct NRRrcMacBcchDataInd_s {
|
||||
uint32_t frame;
|
||||
uint8_t sub_frame;
|
||||
uint32_t sdu_size;
|
||||
uint8_t sdu[BCCH_SDU_SIZE];
|
||||
uint8_t gnb_index;
|
||||
uint8_t rsrq;
|
||||
uint8_t rsrp;
|
||||
} NRRrcMacBcchDataInd;
|
||||
|
||||
typedef struct RrcMacBcchMbmsDataReq_s {
|
||||
uint32_t frame;
|
||||
@@ -126,6 +137,16 @@ typedef struct RrcMacCcchDataInd_s {
|
||||
int CC_id;
|
||||
} RrcMacCcchDataInd;
|
||||
|
||||
typedef struct NRRrcMacCcchDataInd_s {
|
||||
uint32_t frame;
|
||||
uint8_t sub_frame;
|
||||
uint16_t rnti;
|
||||
uint32_t sdu_size;
|
||||
uint8_t sdu[CCCH_SDU_SIZE];
|
||||
uint8_t gnb_index;
|
||||
int CC_id;
|
||||
} NRRrcMacCcchDataInd;
|
||||
|
||||
typedef struct RrcMacMcchDataReq_s {
|
||||
uint32_t frame;
|
||||
uint32_t sdu_size;
|
||||
|
||||
90
openair2/COMMON/ngap_messages_def.h
Normal file
90
openair2/COMMON/ngap_messages_def.h
Normal file
@@ -0,0 +1,90 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*
|
||||
* ngap_messages_def.h
|
||||
*
|
||||
* Created on: 2020
|
||||
* Author: Yoshio INOUE, Masayuki HARADA
|
||||
* Email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
*/
|
||||
|
||||
/* Messages for NGAP logging */
|
||||
MESSAGE_DEF(NGAP_UPLINK_NAS_LOG , MESSAGE_PRIORITY_MED, IttiMsgText , ngap_uplink_nas_log)
|
||||
MESSAGE_DEF(NGAP_UE_CAPABILITY_IND_LOG , MESSAGE_PRIORITY_MED, IttiMsgText , ngap_ue_capability_ind_log)
|
||||
MESSAGE_DEF(NGAP_INITIAL_CONTEXT_SETUP_LOG , MESSAGE_PRIORITY_MED, IttiMsgText , ngap_initial_context_setup_log)
|
||||
MESSAGE_DEF(NGAP_NAS_NON_DELIVERY_IND_LOG , MESSAGE_PRIORITY_MED, IttiMsgText , ngap_nas_non_delivery_ind_log)
|
||||
MESSAGE_DEF(NGAP_DOWNLINK_NAS_LOG , MESSAGE_PRIORITY_MED, IttiMsgText , ngap_downlink_nas_log)
|
||||
MESSAGE_DEF(NGAP_S1_SETUP_LOG , MESSAGE_PRIORITY_MED, IttiMsgText , ngap_s1_setup_log)
|
||||
MESSAGE_DEF(NGAP_INITIAL_UE_MESSAGE_LOG , MESSAGE_PRIORITY_MED, IttiMsgText , ngap_initial_ue_message_log)
|
||||
MESSAGE_DEF(NGAP_UE_CONTEXT_RELEASE_REQ_LOG, MESSAGE_PRIORITY_MED, IttiMsgText , ngap_ue_context_release_req_log)
|
||||
MESSAGE_DEF(NGAP_UE_CONTEXT_RELEASE_COMMAND_LOG, MESSAGE_PRIORITY_MED, IttiMsgText , ngap_ue_context_release_command_log)
|
||||
MESSAGE_DEF(NGAP_UE_CONTEXT_RELEASE_COMPLETE_LOG, MESSAGE_PRIORITY_MED, IttiMsgText , ngap_ue_context_release_complete_log)
|
||||
MESSAGE_DEF(NGAP_UE_CONTEXT_RELEASE_LOG , MESSAGE_PRIORITY_MED, IttiMsgText , ngap_ue_context_release_log)
|
||||
MESSAGE_DEF(NGAP_PDUSESSION_SETUP_REQUEST_LOG , MESSAGE_PRIORITY_MED, IttiMsgText , ngap_pdusession_setup_request_log)
|
||||
MESSAGE_DEF(NGAP_PDUSESSION_SETUP_RESPONSE_LOG , MESSAGE_PRIORITY_MED, IttiMsgText , ngap_pdusession_setup_response_log)
|
||||
MESSAGE_DEF(NGAP_PDUSESSION_MODIFY_REQUEST_LOG , MESSAGE_PRIORITY_MED, IttiMsgText , ngap_pdusession_modify_request_log)
|
||||
MESSAGE_DEF(NGAP_PDUSESSION_MODIFY_RESPONSE_LOG , MESSAGE_PRIORITY_MED, IttiMsgText , ngap_pdusession_modify_response_log)
|
||||
MESSAGE_DEF(NGAP_PAGING_LOG , MESSAGE_PRIORITY_MED, IttiMsgText , ngap_paging_log)
|
||||
MESSAGE_DEF(NGAP_PDUSESSION_RELEASE_REQUEST_LOG , MESSAGE_PRIORITY_MED, IttiMsgText , ngap_pdusession_release_request_log)
|
||||
MESSAGE_DEF(NGAP_PDUSESSION_RELEASE_RESPONSE_LOG , MESSAGE_PRIORITY_MED, IttiMsgText , ngap_pdusession_release_response_log)
|
||||
MESSAGE_DEF(NGAP_ERROR_INDICATION_LOG , MESSAGE_PRIORITY_MED, IttiMsgText , ngap_error_indication_log)
|
||||
MESSAGE_DEF(NGAP_PATH_SWITCH_REQ_LOG , MESSAGE_PRIORITY_MED, IttiMsgText , ngap_path_switch_req_log)
|
||||
MESSAGE_DEF(NGAP_PATH_SWITCH_REQ_ACK_LOG , MESSAGE_PRIORITY_MED, IttiMsgText , ngap_path_switch_req_ack_log)
|
||||
|
||||
/* gNB application layer -> NGAP messages */
|
||||
MESSAGE_DEF(NGAP_REGISTER_GNB_REQ , MESSAGE_PRIORITY_MED, ngap_register_gnb_req_t , ngap_register_gnb_req)
|
||||
|
||||
/* NGAP -> gNB application layer messages */
|
||||
MESSAGE_DEF(NGAP_REGISTER_GNB_CNF , MESSAGE_PRIORITY_MED, ngap_register_gnb_cnf_t , ngap_register_gnb_cnf)
|
||||
MESSAGE_DEF(NGAP_DEREGISTERED_GNB_IND , MESSAGE_PRIORITY_MED, ngap_deregistered_gnb_ind_t , ngap_deregistered_gnb_ind)
|
||||
|
||||
/* RRC -> NGAP messages */
|
||||
MESSAGE_DEF(NGAP_NAS_FIRST_REQ , MESSAGE_PRIORITY_MED, ngap_nas_first_req_t , ngap_nas_first_req)
|
||||
MESSAGE_DEF(NGAP_UPLINK_NAS , MESSAGE_PRIORITY_MED, ngap_uplink_nas_t , ngap_uplink_nas)
|
||||
MESSAGE_DEF(NGAP_UE_CAPABILITIES_IND , MESSAGE_PRIORITY_MED, ngap_ue_cap_info_ind_t , ngap_ue_cap_info_ind)
|
||||
MESSAGE_DEF(NGAP_INITIAL_CONTEXT_SETUP_RESP, MESSAGE_PRIORITY_MED, ngap_initial_context_setup_resp_t, ngap_initial_context_setup_resp)
|
||||
MESSAGE_DEF(NGAP_INITIAL_CONTEXT_SETUP_FAIL, MESSAGE_PRIORITY_MED, ngap_initial_context_setup_fail_t, ngap_initial_context_setup_fail)
|
||||
MESSAGE_DEF(NGAP_NAS_NON_DELIVERY_IND , MESSAGE_PRIORITY_MED, ngap_nas_non_delivery_ind_t , ngap_nas_non_delivery_ind)
|
||||
MESSAGE_DEF(NGAP_UE_CONTEXT_RELEASE_RESP , MESSAGE_PRIORITY_MED, ngap_ue_release_resp_t , ngap_ue_release_resp)
|
||||
MESSAGE_DEF(NGAP_UE_CONTEXT_RELEASE_COMPLETE, MESSAGE_PRIORITY_MED, ngap_ue_release_complete_t , ngap_ue_release_complete)
|
||||
MESSAGE_DEF(NGAP_UE_CTXT_MODIFICATION_RESP , MESSAGE_PRIORITY_MED, ngap_ue_ctxt_modification_resp_t , ngap_ue_ctxt_modification_resp)
|
||||
MESSAGE_DEF(NGAP_UE_CTXT_MODIFICATION_FAIL , MESSAGE_PRIORITY_MED, ngap_ue_ctxt_modification_fail_t , ngap_ue_ctxt_modification_fail)
|
||||
MESSAGE_DEF(NGAP_PDUSESSION_SETUP_RESP , MESSAGE_PRIORITY_MED, ngap_pdusession_setup_resp_t , ngap_pdusession_setup_resp)
|
||||
MESSAGE_DEF(NGAP_PDUSESSION_SETUP_REQUEST_FAIL , MESSAGE_PRIORITY_MED, ngap_pdusession_setup_req_fail_t , ngap_pdusession_setup_request_fail)
|
||||
MESSAGE_DEF(NGAP_PDUSESSION_MODIFY_RESP , MESSAGE_PRIORITY_MED, ngap_pdusession_modify_resp_t , ngap_pdusession_modify_resp)
|
||||
MESSAGE_DEF(NGAP_PDUSESSION_RELEASE_RESPONSE , MESSAGE_PRIORITY_MED, ngap_pdusession_release_resp_t , ngap_pdusession_release_resp)
|
||||
MESSAGE_DEF(NGAP_PATH_SWITCH_REQ , MESSAGE_PRIORITY_MED, ngap_path_switch_req_t , ngap_path_switch_req)
|
||||
MESSAGE_DEF(NGAP_PATH_SWITCH_REQ_ACK , MESSAGE_PRIORITY_MED, ngap_path_switch_req_ack_t , ngap_path_switch_req_ack)
|
||||
MESSAGE_DEF(NGAP_PDUSESSION_MODIFICATION_IND , MESSAGE_PRIORITY_MED, ngap_pdusession_modification_ind_t , ngap_pdusession_modification_ind)
|
||||
|
||||
/* NGAP -> RRC messages */
|
||||
MESSAGE_DEF(NGAP_DOWNLINK_NAS , MESSAGE_PRIORITY_MED, ngap_downlink_nas_t , ngap_downlink_nas )
|
||||
MESSAGE_DEF(NGAP_INITIAL_CONTEXT_SETUP_REQ , MESSAGE_PRIORITY_MED, ngap_initial_context_setup_req_t , ngap_initial_context_setup_req )
|
||||
MESSAGE_DEF(NGAP_UE_CTXT_MODIFICATION_REQ , MESSAGE_PRIORITY_MED, ngap_ue_ctxt_modification_req_t , ngap_ue_ctxt_modification_req)
|
||||
MESSAGE_DEF(NGAP_PAGING_IND , MESSAGE_PRIORITY_MED, ngap_paging_ind_t , ngap_paging_ind )
|
||||
MESSAGE_DEF(NGAP_PDUSESSION_SETUP_REQ , MESSAGE_PRIORITY_MED, ngap_pdusession_setup_req_t , ngap_pdusession_setup_req )
|
||||
MESSAGE_DEF(NGAP_PDUSESSION_MODIFY_REQ , MESSAGE_PRIORITY_MED, ngap_pdusession_modify_req_t , ngap_pdusession_modify_req )
|
||||
MESSAGE_DEF(NGAP_PDUSESSION_RELEASE_COMMAND , MESSAGE_PRIORITY_MED, ngap_pdusession_release_command_t , ngap_pdusession_release_command)
|
||||
MESSAGE_DEF(NGAP_UE_CONTEXT_RELEASE_COMMAND, MESSAGE_PRIORITY_MED, ngap_ue_release_command_t , ngap_ue_release_command)
|
||||
|
||||
/* NGAP <-> RRC messages (can be initiated either by MME or gNB) */
|
||||
MESSAGE_DEF(NGAP_UE_CONTEXT_RELEASE_REQ , MESSAGE_PRIORITY_MED, ngap_ue_release_req_t , ngap_ue_release_req)
|
||||
821
openair2/COMMON/ngap_messages_types.h
Normal file
821
openair2/COMMON/ngap_messages_types.h
Normal file
@@ -0,0 +1,821 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*
|
||||
* ngap_messages_types.h
|
||||
*
|
||||
* Created on: 2020
|
||||
* Author: Yoshio INOUE, Masayuki HARADA
|
||||
* Email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
*/
|
||||
|
||||
#ifndef NGAP_MESSAGES_TYPES_H_
|
||||
#define NGAP_MESSAGES_TYPES_H_
|
||||
|
||||
#include "LTE_asn_constant.h"
|
||||
//-------------------------------------------------------------------------------------------//
|
||||
// Defines to access message fields.
|
||||
|
||||
#define NGAP_REGISTER_GNB_REQ(mSGpTR) (mSGpTR)->ittiMsg.ngap_register_gnb_req
|
||||
|
||||
#define NGAP_REGISTER_GNB_CNF(mSGpTR) (mSGpTR)->ittiMsg.ngap_register_gnb_cnf
|
||||
#define NGAP_DEREGISTERED_GNB_IND(mSGpTR) (mSGpTR)->ittiMsg.ngap_deregistered_gnb_ind
|
||||
|
||||
#define NGAP_NAS_FIRST_REQ(mSGpTR) (mSGpTR)->ittiMsg.ngap_nas_first_req
|
||||
#define NGAP_UPLINK_NAS(mSGpTR) (mSGpTR)->ittiMsg.ngap_uplink_nas
|
||||
#define NGAP_UE_CAPABILITIES_IND(mSGpTR) (mSGpTR)->ittiMsg.ngap_ue_cap_info_ind
|
||||
#define NGAP_INITIAL_CONTEXT_SETUP_RESP(mSGpTR) (mSGpTR)->ittiMsg.ngap_initial_context_setup_resp
|
||||
#define NGAP_INITIAL_CONTEXT_SETUP_FAIL(mSGpTR) (mSGpTR)->ittiMsg.ngap_initial_context_setup_fail
|
||||
#define NGAP_UE_CONTEXT_RELEASE_RESP(mSGpTR) (mSGpTR)->ittiMsg.ngap_ue_release_resp
|
||||
#define NGAP_NAS_NON_DELIVERY_IND(mSGpTR) (mSGpTR)->ittiMsg.ngap_nas_non_delivery_ind
|
||||
#define NGAP_UE_CTXT_MODIFICATION_RESP(mSGpTR) (mSGpTR)->ittiMsg.ngap_ue_ctxt_modification_resp
|
||||
#define NGAP_UE_CTXT_MODIFICATION_FAIL(mSGpTR) (mSGpTR)->ittiMsg.ngap_ue_ctxt_modification_fail
|
||||
#define NGAP_PDUSESSION_SETUP_RESP(mSGpTR) (mSGpTR)->ittiMsg.ngap_pdusession_setup_resp
|
||||
#define NGAP_PDUSESSION_SETUP_FAIL(mSGpTR) (mSGpTR)->ittiMsg.ngap_pdusession_setup_req_fail
|
||||
#define NGAP_PDUSESSION_MODIFY_RESP(mSGpTR) (mSGpTR)->ittiMsg.ngap_pdusession_modify_resp
|
||||
#define NGAP_PATH_SWITCH_REQ(mSGpTR) (mSGpTR)->ittiMsg.ngap_path_switch_req
|
||||
#define NGAP_PATH_SWITCH_REQ_ACK(mSGpTR) (mSGpTR)->ittiMsg.ngap_path_switch_req_ack
|
||||
#define NGAP_PDUSESSION_MODIFICATION_IND(mSGpTR) (mSGpTR)->ittiMsg.ngap_pdusession_modification_ind
|
||||
|
||||
#define NGAP_DOWNLINK_NAS(mSGpTR) (mSGpTR)->ittiMsg.ngap_downlink_nas
|
||||
#define NGAP_INITIAL_CONTEXT_SETUP_REQ(mSGpTR) (mSGpTR)->ittiMsg.ngap_initial_context_setup_req
|
||||
#define NGAP_UE_CTXT_MODIFICATION_REQ(mSGpTR) (mSGpTR)->ittiMsg.ngap_ue_ctxt_modification_req
|
||||
#define NGAP_UE_CONTEXT_RELEASE_COMMAND(mSGpTR) (mSGpTR)->ittiMsg.ngap_ue_release_command
|
||||
#define NGAP_UE_CONTEXT_RELEASE_COMPLETE(mSGpTR) (mSGpTR)->ittiMsg.ngap_ue_release_complete
|
||||
#define NGAP_PDUSESSION_SETUP_REQ(mSGpTR) (mSGpTR)->ittiMsg.ngap_pdusession_setup_req
|
||||
#define NGAP_PDUSESSION_MODIFY_REQ(mSGpTR) (mSGpTR)->ittiMsg.ngap_pdusession_modify_req
|
||||
#define NGAP_PAGING_IND(mSGpTR) (mSGpTR)->ittiMsg.ngap_paging_ind
|
||||
|
||||
#define NGAP_UE_CONTEXT_RELEASE_REQ(mSGpTR) (mSGpTR)->ittiMsg.ngap_ue_release_req
|
||||
#define NGAP_PDUSESSION_RELEASE_COMMAND(mSGpTR) (mSGpTR)->ittiMsg.ngap_pdusession_release_command
|
||||
#define NGAP_PDUSESSION_RELEASE_RESPONSE(mSGpTR) (mSGpTR)->ittiMsg.ngap_pdusession_release_resp
|
||||
|
||||
//-------------------------------------------------------------------------------------------//
|
||||
/* Maximum number of e-rabs to be setup/deleted in a single message.
|
||||
* Even if only one bearer will be modified by message.
|
||||
*/
|
||||
#define NGAP_MAX_PDUSESSION (LTE_maxDRB + 3)
|
||||
|
||||
/* Length of the transport layer address string
|
||||
* 160 bits / 8 bits by char.
|
||||
*/
|
||||
#define NGAP_TRANSPORT_LAYER_ADDRESS_SIZE (160 / 8)
|
||||
|
||||
#define NGAP_MAX_NB_AMF_IP_ADDRESS 10
|
||||
#define NGAP_IMSI_LENGTH 16
|
||||
|
||||
#define QOSFLOW_MAX_VALUE 64
|
||||
|
||||
/* Security key length used within gNB
|
||||
* Even if only 16 bytes will be effectively used,
|
||||
* the key length is 32 bytes (256 bits)
|
||||
*/
|
||||
#define SECURITY_KEY_LENGTH 32
|
||||
|
||||
typedef enum ngap_paging_drx_e {
|
||||
NGAP_PAGING_DRX_32 = 0x0,
|
||||
NGAP_PAGING_DRX_64 = 0x1,
|
||||
NGAP_PAGING_DRX_128 = 0x2,
|
||||
NGAP_PAGING_DRX_256 = 0x3
|
||||
} ngap_paging_drx_t;
|
||||
|
||||
/* Lower value codepoint
|
||||
* indicates higher priority.
|
||||
*/
|
||||
typedef enum ngap_paging_priority_s {
|
||||
NGAP_PAGING_PRIO_LEVEL1 = 0,
|
||||
NGAP_PAGING_PRIO_LEVEL2 = 1,
|
||||
NGAP_PAGING_PRIO_LEVEL3 = 2,
|
||||
NGAP_PAGING_PRIO_LEVEL4 = 3,
|
||||
NGAP_PAGING_PRIO_LEVEL5 = 4,
|
||||
NGAP_PAGING_PRIO_LEVEL6 = 5,
|
||||
NGAP_PAGING_PRIO_LEVEL7 = 6,
|
||||
NGAP_PAGING_PRIO_LEVEL8 = 7
|
||||
} ngap_paging_priority_t;
|
||||
|
||||
typedef enum ngap_cn_domain_s {
|
||||
NGAP_CN_DOMAIN_PS = 1,
|
||||
NGAP_CN_DOMAIN_CS = 2
|
||||
} ngap_cn_domain_t;
|
||||
|
||||
typedef struct ngap_net_ip_address_s {
|
||||
unsigned ipv4:1;
|
||||
unsigned ipv6:1;
|
||||
char ipv4_address[16];
|
||||
char ipv6_address[46];
|
||||
} ngap_net_ip_address_t;
|
||||
|
||||
typedef uint64_t bitrate_t;
|
||||
|
||||
typedef struct ngap_ambr_s {
|
||||
bitrate_t br_ul;
|
||||
bitrate_t br_dl;
|
||||
} ngap_ambr_t;
|
||||
|
||||
typedef enum ngap_priority_level_s {
|
||||
NGAP_PRIORITY_LEVEL_SPARE = 0,
|
||||
NGAP_PRIORITY_LEVEL_HIGHEST = 1,
|
||||
NGAP_PRIORITY_LEVEL_LOWEST = 14,
|
||||
NGAP_PRIORITY_LEVEL_NO_PRIORITY = 15
|
||||
} ngap_priority_level_t;
|
||||
|
||||
typedef enum ngap_pre_emp_capability_e {
|
||||
NGAP_PRE_EMPTION_CAPABILITY_ENABLED = 0,
|
||||
NGAP_PRE_EMPTION_CAPABILITY_DISABLED = 1,
|
||||
NGAP_PRE_EMPTION_CAPABILITY_MAX,
|
||||
} ngap_pre_emp_capability_t;
|
||||
|
||||
typedef enum ngap_pre_emp_vulnerability_e {
|
||||
NGAP_PRE_EMPTION_VULNERABILITY_ENABLED = 0,
|
||||
NGAP_PRE_EMPTION_VULNERABILITY_DISABLED = 1,
|
||||
NGAP_PRE_EMPTION_VULNERABILITY_MAX,
|
||||
} ngap_pre_emp_vulnerability_t;
|
||||
|
||||
typedef struct ngap_allocation_retention_priority_s {
|
||||
ngap_priority_level_t priority_level;
|
||||
ngap_pre_emp_capability_t pre_emp_capability;
|
||||
ngap_pre_emp_vulnerability_t pre_emp_vulnerability;
|
||||
} ngap_allocation_retention_priority_t;
|
||||
|
||||
typedef struct ngap_security_capabilities_s {
|
||||
uint16_t nRencryption_algorithms;
|
||||
uint16_t nRintegrity_algorithms;
|
||||
uint16_t eUTRAencryption_algorithms;
|
||||
uint16_t eUTRAintegrity_algorithms;
|
||||
} ngap_security_capabilities_t;
|
||||
|
||||
/* Provides the establishment cause for the RRC connection request as provided
|
||||
* by the upper layers. W.r.t. the cause value names: highPriorityAccess
|
||||
* concerns AC11..AC15, ‘mt Estands for ‘Mobile Terminating Eand ‘mo Efor
|
||||
* 'Mobile Originating'. Defined in TS 36.331.
|
||||
*/
|
||||
typedef enum ngap_rrc_establishment_cause_e {
|
||||
NGAP_RRC_CAUSE_EMERGENCY = 0x0,
|
||||
NGAP_RRC_CAUSE_HIGH_PRIO_ACCESS = 0x1,
|
||||
NGAP_RRC_CAUSE_MT_ACCESS = 0x2,
|
||||
NGAP_RRC_CAUSE_MO_SIGNALLING = 0x3,
|
||||
NGAP_RRC_CAUSE_MO_DATA = 0x4,
|
||||
NGAP_RRC_CAUSE_MO_VOICECALL = 0x5,
|
||||
NGAP_RRC_CAUSE_MO_VIDEOCALL = 0x6,
|
||||
NGAP_RRC_CAUSE_MO_SMS = 0x7,
|
||||
NGAP_RRC_CAUSE_MPS_PRIORITY_ACCESS = 0x8,
|
||||
NGAP_RRC_CAUSE_MCS_PRIORITY_ACCESS = 0x9,
|
||||
NGAP_RRC_CAUSE_NOTAVAILABLE = 0x10,
|
||||
NGAP_RRC_CAUSE_LAST
|
||||
} ngap_rrc_establishment_cause_t;
|
||||
|
||||
typedef struct ngap_guami_s {
|
||||
uint16_t mcc;
|
||||
uint16_t mnc;
|
||||
uint8_t mnc_len;
|
||||
uint8_t amf_region_id;
|
||||
uint16_t amf_set_id;
|
||||
uint8_t amf_pointer;
|
||||
} ngap_guami_t;
|
||||
|
||||
typedef struct ngap_allowed_NSSAI_s{
|
||||
uint8_t sST;
|
||||
uint8_t sD_flag;
|
||||
uint8_t sD[3];
|
||||
}ngap_allowed_NSSAI_t;
|
||||
|
||||
typedef struct fiveg_s_tmsi_s {
|
||||
uint16_t amf_set_id;
|
||||
uint8_t amf_pointer;
|
||||
uint32_t m_tmsi;
|
||||
} fiveg_s_tmsi_t;
|
||||
|
||||
typedef struct ngap_tai_plmn_identity_s {
|
||||
uint16_t mcc;
|
||||
uint16_t mnc;
|
||||
uint8_t mnc_digit_length;
|
||||
} ngap_plmn_identity_t;
|
||||
|
||||
typedef struct ngap_ue_paging_identity_s {
|
||||
fiveg_s_tmsi_t s_tmsi;
|
||||
} ngap_ue_paging_identity_t;
|
||||
|
||||
typedef enum ngap_ue_identities_presenceMask_e {
|
||||
NGAP_UE_IDENTITIES_NONE = 0,
|
||||
NGAP_UE_IDENTITIES_FiveG_s_tmsi = 1 << 1,
|
||||
NGAP_UE_IDENTITIES_guami = 1 << 2,
|
||||
} ngap_ue_identities_presenceMask_t;
|
||||
|
||||
typedef struct ngap_ue_identity_s {
|
||||
ngap_ue_identities_presenceMask_t presenceMask;
|
||||
fiveg_s_tmsi_t s_tmsi;
|
||||
ngap_guami_t guami;
|
||||
} ngap_ue_identity_t;
|
||||
|
||||
typedef struct ngap_nas_pdu_s {
|
||||
/* Octet string data */
|
||||
uint8_t *buffer;
|
||||
/* Length of the octet string */
|
||||
uint32_t length;
|
||||
} ngap_nas_pdu_t, ngap_ue_radio_cap_t;
|
||||
|
||||
typedef struct ngap_mobility_restriction_s{
|
||||
ngap_plmn_identity_t serving_plmn;
|
||||
}ngap_mobility_restriction_t;
|
||||
|
||||
typedef enum pdu_session_type_e {
|
||||
PDUSessionType_ipv4 = 0,
|
||||
PDUSessionType_ipv6 = 1,
|
||||
PDUSessionType_ipv4v6 = 2,
|
||||
PDUSessionType_ethernet = 3,
|
||||
PDUSessionType_unstructured = 4
|
||||
}pdu_session_type_t;
|
||||
|
||||
typedef struct ngap_transport_layer_addr_s {
|
||||
/* Length of the transport layer address buffer in bits. NGAP layer received a
|
||||
* bit string<1..160> containing one of the following addresses: ipv4,
|
||||
* ipv6, or ipv4 and ipv6. The layer doesn't interpret the buffer but
|
||||
* silently forward it to NG-U.
|
||||
*/
|
||||
uint8_t pdu_session_type;
|
||||
uint8_t length;
|
||||
uint8_t buffer[20]; // in network byte order
|
||||
} ngap_transport_layer_addr_t;
|
||||
|
||||
#define TRANSPORT_LAYER_ADDR_COPY(dEST,sOURCE) \
|
||||
do { \
|
||||
AssertFatal(sOURCE.len <= 20); \
|
||||
memcpy(dEST.buffer, sOURCE.buffer, sOURCE.len); \
|
||||
dEST.length = sOURCE.length; \
|
||||
} while (0)
|
||||
|
||||
typedef struct pdusession_level_qos_parameter_s {
|
||||
uint8_t qci;
|
||||
|
||||
ngap_allocation_retention_priority_t allocation_retention_priority;
|
||||
} pdusession_level_qos_parameter_t;
|
||||
|
||||
typedef struct pdusession_s {
|
||||
/* Unique pdusession_id for the UE. */
|
||||
uint8_t pdusession_id;
|
||||
|
||||
uint8_t nb_qos;
|
||||
/* Quality of service for this pdusession */
|
||||
pdusession_level_qos_parameter_t qos[QOSFLOW_MAX_VALUE];
|
||||
/* The NAS PDU should be forwarded by the RRC layer to the NAS layer */
|
||||
ngap_nas_pdu_t nas_pdu;
|
||||
/* The transport layer address for the IP packets */
|
||||
ngap_transport_layer_addr_t upf_addr;
|
||||
/* S-GW Tunnel endpoint identifier */
|
||||
uint32_t gtp_teid;
|
||||
} pdusession_t;
|
||||
|
||||
|
||||
typedef enum pdusession_qosflow_mapping_ind_e{
|
||||
QOSFLOW_MAPPING_INDICATION_UL = 0,
|
||||
QOSFLOW_MAPPING_INDICATION_DL = 1,
|
||||
QOSFLOW_MAPPING_INDICATION_NON = 0xFF
|
||||
}pdusession_qosflow_mapping_ind_t;
|
||||
|
||||
typedef struct pdusession_associate_qosflow_s{
|
||||
uint8_t qci;
|
||||
pdusession_qosflow_mapping_ind_t qos_flow_mapping_ind;
|
||||
}pdusession_associate_qosflow_t;
|
||||
|
||||
typedef struct pdusession_setup_s {
|
||||
/* Unique pdusession_id for the UE. */
|
||||
uint8_t pdusession_id;
|
||||
|
||||
/* The transport layer address for the IP packets */
|
||||
ngap_transport_layer_addr_t gNB_addr;
|
||||
|
||||
/* UPF Tunnel endpoint identifier */
|
||||
uint32_t gtp_teid;
|
||||
|
||||
/* qos flow list number */
|
||||
uint8_t nb_of_qos_flow;
|
||||
|
||||
/* qos flow list(1 ~ 64) */
|
||||
pdusession_associate_qosflow_t associated_qos_flows[QOSFLOW_MAX_VALUE];
|
||||
} pdusession_setup_t;
|
||||
|
||||
typedef struct pdusession_tobe_added_s {
|
||||
/* Unique pdusession_id for the UE. */
|
||||
uint8_t pdusession_id;
|
||||
|
||||
/* Unique drb_ID for the UE. */
|
||||
uint8_t drb_ID;
|
||||
|
||||
/* The transport layer address for the IP packets */
|
||||
ngap_transport_layer_addr_t upf_addr;
|
||||
|
||||
/* S-GW Tunnel endpoint identifier */
|
||||
uint32_t gtp_teid;
|
||||
} pdusession_tobe_added_t;
|
||||
|
||||
typedef struct pdusession_admitted_tobe_added_s {
|
||||
/* Unique pdusession_id for the UE. */
|
||||
uint8_t pdusession_id;
|
||||
|
||||
/* Unique drb_ID for the UE. */
|
||||
uint8_t drb_ID;
|
||||
|
||||
/* The transport layer address for the IP packets */
|
||||
ngap_transport_layer_addr_t gnb_addr;
|
||||
|
||||
/* S-GW Tunnel endpoint identifier */
|
||||
uint32_t gtp_teid;
|
||||
} pdusession_admitted_tobe_added_t;
|
||||
|
||||
|
||||
|
||||
typedef struct pdusession_tobeswitched_s {
|
||||
/* Unique pdusession_id for the UE. */
|
||||
uint8_t pdusession_id;
|
||||
|
||||
/* The transport layer address for the IP packets */
|
||||
ngap_transport_layer_addr_t upf_addr;
|
||||
|
||||
/* S-GW Tunnel endpoint identifier */
|
||||
uint32_t gtp_teid;
|
||||
} pdusession_tobeswitched_t;
|
||||
|
||||
typedef struct pdusession_modify_s {
|
||||
/* Unique pdusession_id for the UE. */
|
||||
uint8_t pdusession_id;
|
||||
} pdusession_modify_t;
|
||||
|
||||
typedef enum ngap_Cause_e {
|
||||
NGAP_CAUSE_NOTHING, /* No components present */
|
||||
NGAP_CAUSE_RADIO_NETWORK,
|
||||
NGAP_CAUSE_TRANSPORT,
|
||||
NGAP_CAUSE_NAS,
|
||||
NGAP_CAUSE_PROTOCOL,
|
||||
NGAP_CAUSE_MISC,
|
||||
/* Extensions may appear below */
|
||||
|
||||
} ngap_Cause_t;
|
||||
|
||||
typedef struct pdusession_failed_s {
|
||||
/* Unique pdusession_id for the UE. */
|
||||
uint8_t pdusession_id;
|
||||
/* Cause of the failure */
|
||||
// cause_t cause;
|
||||
ngap_Cause_t cause;
|
||||
uint8_t cause_value;
|
||||
} pdusession_failed_t;
|
||||
|
||||
typedef enum ngap_ue_ctxt_modification_present_s {
|
||||
NGAP_UE_CONTEXT_MODIFICATION_SECURITY_KEY = (1 << 0),
|
||||
NGAP_UE_CONTEXT_MODIFICATION_UE_AMBR = (1 << 1),
|
||||
NGAP_UE_CONTEXT_MODIFICATION_UE_SECU_CAP = (1 << 2),
|
||||
} ngap_ue_ctxt_modification_present_t;
|
||||
|
||||
typedef enum ngap_paging_ind_present_s {
|
||||
NGAP_PAGING_IND_PAGING_DRX = (1 << 0),
|
||||
NGAP_PAGING_IND_PAGING_PRIORITY = (1 << 1),
|
||||
} ngap_paging_ind_present_t;
|
||||
|
||||
//-------------------------------------------------------------------------------------------//
|
||||
// gNB application layer -> NGAP messages
|
||||
typedef struct ngap_register_gnb_req_s {
|
||||
/* Unique gNB_id to identify the gNB within EPC.
|
||||
* For macro gNB ids this field should be 20 bits long.
|
||||
* For home gNB ids this field should be 28 bits long.
|
||||
*/
|
||||
uint32_t gNB_id;
|
||||
/* The type of the cell */
|
||||
enum cell_type_e cell_type;
|
||||
|
||||
/* Optional name for the cell
|
||||
* NOTE: the name can be NULL (i.e no name) and will be cropped to 150
|
||||
* characters.
|
||||
*/
|
||||
char *gNB_name;
|
||||
|
||||
/* Tracking area code */
|
||||
uint32_t tac;
|
||||
|
||||
#define PLMN_LIST_MAX_SIZE 6
|
||||
/* Mobile Country Code
|
||||
* Mobile Network Code
|
||||
*/
|
||||
uint16_t mcc[PLMN_LIST_MAX_SIZE];
|
||||
uint16_t mnc[PLMN_LIST_MAX_SIZE];
|
||||
uint8_t mnc_digit_length[PLMN_LIST_MAX_SIZE];
|
||||
uint8_t num_plmn;
|
||||
|
||||
uint16_t num_nssai[PLMN_LIST_MAX_SIZE];
|
||||
ngap_allowed_NSSAI_t s_nssai[PLMN_LIST_MAX_SIZE][8];
|
||||
|
||||
/* Default Paging DRX of the gNB as defined in TS 38.304 */
|
||||
ngap_paging_drx_t default_drx;
|
||||
|
||||
/* The gNB IP address to bind */
|
||||
net_ip_address_t gnb_ip_address;
|
||||
|
||||
/* Nb of AMF to connect to */
|
||||
uint8_t nb_amf;
|
||||
/* List of AMF to connect to */
|
||||
net_ip_address_t amf_ip_address[NGAP_MAX_NB_AMF_IP_ADDRESS];
|
||||
uint8_t broadcast_plmn_num[NGAP_MAX_NB_AMF_IP_ADDRESS];
|
||||
uint8_t broadcast_plmn_index[NGAP_MAX_NB_AMF_IP_ADDRESS][PLMN_LIST_MAX_SIZE];
|
||||
|
||||
/* Number of SCTP streams used for a amf association */
|
||||
uint16_t sctp_in_streams;
|
||||
uint16_t sctp_out_streams;
|
||||
} ngap_register_gnb_req_t;
|
||||
|
||||
//-------------------------------------------------------------------------------------------//
|
||||
// NGAP -> gNB application layer messages
|
||||
typedef struct ngap_register_gnb_cnf_s {
|
||||
/* Nb of AMF connected */
|
||||
uint8_t nb_amf;
|
||||
} ngap_register_gnb_cnf_t;
|
||||
|
||||
typedef struct ngap_deregistered_gnb_ind_s {
|
||||
/* Nb of AMF connected */
|
||||
uint8_t nb_amf;
|
||||
} ngap_deregistered_gnb_ind_t;
|
||||
|
||||
//-------------------------------------------------------------------------------------------//
|
||||
// RRC -> NGAP messages
|
||||
|
||||
/* The NAS First Req is the first message exchanged between RRC and NGAP
|
||||
* for an UE.
|
||||
* The rnti uniquely identifies an UE within a cell. Later the gnb_ue_ngap_id
|
||||
* will be the unique identifier used between RRC and NGAP.
|
||||
*/
|
||||
typedef struct ngap_nas_first_req_s {
|
||||
/* UE id for initial connection to NGAP */
|
||||
uint16_t ue_initial_id;
|
||||
|
||||
/* the chosen PLMN identity as index, see TS 36.331 6.2.2 RRC Connection
|
||||
* Setup Complete. This index here is zero-based, unlike the standard! */
|
||||
int selected_plmn_identity;
|
||||
|
||||
/* Establishment cause as sent by UE */
|
||||
ngap_rrc_establishment_cause_t establishment_cause;
|
||||
|
||||
/* NAS PDU */
|
||||
ngap_nas_pdu_t nas_pdu;
|
||||
|
||||
/* If this flag is set NGAP layer is expecting the GUAMI. If = 0,
|
||||
* the temporary s-tmsi is used.
|
||||
*/
|
||||
ngap_ue_identity_t ue_identity;
|
||||
} ngap_nas_first_req_t;
|
||||
|
||||
typedef struct ngap_uplink_nas_s {
|
||||
/* Unique UE identifier within an gNB */
|
||||
uint32_t gNB_ue_ngap_id;
|
||||
|
||||
/* NAS pdu */
|
||||
ngap_nas_pdu_t nas_pdu;
|
||||
} ngap_uplink_nas_t;
|
||||
|
||||
typedef struct ngap_ue_cap_info_ind_s {
|
||||
uint32_t gNB_ue_ngap_id;
|
||||
ngap_ue_radio_cap_t ue_radio_cap;
|
||||
} ngap_ue_cap_info_ind_t;
|
||||
|
||||
typedef struct ngap_initial_context_setup_resp_s {
|
||||
uint32_t gNB_ue_ngap_id;
|
||||
|
||||
/* Number of pdusession setup-ed in the list */
|
||||
uint8_t nb_of_pdusessions;
|
||||
/* list of pdusession setup-ed by RRC layers */
|
||||
pdusession_setup_t pdusessions[NGAP_MAX_PDUSESSION];
|
||||
|
||||
/* Number of pdusession failed to be setup in list */
|
||||
uint8_t nb_of_pdusessions_failed;
|
||||
/* list of pdusessions that failed to be setup */
|
||||
pdusession_failed_t pdusessions_failed[NGAP_MAX_PDUSESSION];
|
||||
} ngap_initial_context_setup_resp_t;
|
||||
|
||||
typedef struct ngap_initial_context_setup_fail_s {
|
||||
uint32_t gNB_ue_ngap_id;
|
||||
|
||||
/* TODO add cause */
|
||||
} ngap_initial_context_setup_fail_t, ngap_ue_ctxt_modification_fail_t, ngap_pdusession_setup_req_fail_t;
|
||||
|
||||
typedef struct ngap_nas_non_delivery_ind_s {
|
||||
uint32_t gNB_ue_ngap_id;
|
||||
ngap_nas_pdu_t nas_pdu;
|
||||
/* TODO: add cause */
|
||||
} ngap_nas_non_delivery_ind_t;
|
||||
|
||||
typedef struct ngap_ue_ctxt_modification_req_s {
|
||||
uint32_t gNB_ue_ngap_id;
|
||||
|
||||
/* Bit-mask of possible present parameters */
|
||||
ngap_ue_ctxt_modification_present_t present;
|
||||
|
||||
/* Following fields are optionnaly present */
|
||||
|
||||
/* Security key */
|
||||
uint8_t security_key[SECURITY_KEY_LENGTH];
|
||||
|
||||
/* UE aggregate maximum bitrate */
|
||||
ngap_ambr_t ue_ambr;
|
||||
|
||||
/* NR Security capabilities */
|
||||
ngap_security_capabilities_t security_capabilities;
|
||||
} ngap_ue_ctxt_modification_req_t;
|
||||
|
||||
typedef struct ngap_ue_ctxt_modification_resp_s {
|
||||
uint32_t gNB_ue_ngap_id;
|
||||
} ngap_ue_ctxt_modification_resp_t;
|
||||
|
||||
typedef struct ngap_ue_release_complete_s {
|
||||
|
||||
uint32_t gNB_ue_ngap_id;
|
||||
|
||||
} ngap_ue_release_complete_t;
|
||||
|
||||
//-------------------------------------------------------------------------------------------//
|
||||
// NGAP -> RRC messages
|
||||
typedef struct ngap_downlink_nas_s {
|
||||
/* UE id for initial connection to NGAP */
|
||||
uint16_t ue_initial_id;
|
||||
|
||||
/* Unique UE identifier within an gNB */
|
||||
uint32_t gNB_ue_ngap_id;
|
||||
|
||||
/* NAS pdu */
|
||||
ngap_nas_pdu_t nas_pdu;
|
||||
} ngap_downlink_nas_t;
|
||||
|
||||
|
||||
typedef struct ngap_initial_context_setup_req_s {
|
||||
/* UE id for initial connection to NGAP */
|
||||
uint16_t ue_initial_id;
|
||||
|
||||
/* gNB ue ngap id as initialized by NGAP layer */
|
||||
uint32_t gNB_ue_ngap_id;
|
||||
|
||||
uint64_t amf_ue_ngap_id:40;
|
||||
|
||||
/* UE aggregate maximum bitrate */
|
||||
ngap_ambr_t ue_ambr;
|
||||
|
||||
/* guami */
|
||||
ngap_guami_t guami;
|
||||
|
||||
/* allowed nssai */
|
||||
uint8_t nb_allowed_nssais;
|
||||
ngap_allowed_NSSAI_t allowed_nssai[8];
|
||||
|
||||
/* Security algorithms */
|
||||
ngap_security_capabilities_t security_capabilities;
|
||||
|
||||
/* Security key */
|
||||
uint8_t security_key[SECURITY_KEY_LENGTH];
|
||||
|
||||
/* Number of pdusession to be setup in the list */
|
||||
uint8_t nb_of_pdusessions;
|
||||
/* list of pdusession to be setup by RRC layers */
|
||||
pdusession_t pdusession_param[NGAP_MAX_PDUSESSION];
|
||||
|
||||
/* Mobility Restriction List */
|
||||
uint8_t mobility_restriction_flag;
|
||||
ngap_mobility_restriction_t mobility_restriction;
|
||||
|
||||
/* Nas Pdu */
|
||||
uint8_t nas_pdu_flag;
|
||||
ngap_nas_pdu_t nas_pdu;
|
||||
} ngap_initial_context_setup_req_t;
|
||||
|
||||
|
||||
typedef struct ngap_paging_ind_s {
|
||||
/* UE paging identity */
|
||||
ngap_ue_paging_identity_t ue_paging_identity;
|
||||
|
||||
/* Indicates origin of paging */
|
||||
ngap_cn_domain_t cn_domain;
|
||||
|
||||
/* PLMN_identity in TAI of Paging*/
|
||||
ngap_plmn_identity_t plmn_identity[256];
|
||||
|
||||
/* TAC in TAIList of Paging*/
|
||||
int16_t tac[256];
|
||||
|
||||
/* size of TAIList*/
|
||||
int16_t tai_size;
|
||||
|
||||
/* Optional fields */
|
||||
ngap_paging_drx_t paging_drx;
|
||||
|
||||
ngap_paging_priority_t paging_priority;
|
||||
} ngap_paging_ind_t;
|
||||
|
||||
typedef struct ngap_pdusession_setup_req_s {
|
||||
/* UE id for initial connection to NGAP */
|
||||
uint16_t ue_initial_id;
|
||||
|
||||
/* AMF UE id */
|
||||
uint64_t amf_ue_ngap_id:40;
|
||||
|
||||
/* gNB ue ngap id as initialized by NGAP layer */
|
||||
uint32_t gNB_ue_ngap_id;
|
||||
|
||||
/* Number of pdusession to be setup in the list */
|
||||
uint8_t nb_pdusessions_tosetup;
|
||||
|
||||
/* E RAB setup request */
|
||||
pdusession_t pdusession_setup_params[NGAP_MAX_PDUSESSION];
|
||||
|
||||
} ngap_pdusession_setup_req_t;
|
||||
|
||||
typedef struct ngap_pdusession_setup_resp_s {
|
||||
uint32_t gNB_ue_ngap_id;
|
||||
|
||||
/* Number of pdusession setup-ed in the list */
|
||||
uint8_t nb_of_pdusessions;
|
||||
/* list of pdusession setup-ed by RRC layers */
|
||||
pdusession_setup_t pdusessions[NGAP_MAX_PDUSESSION];
|
||||
|
||||
/* Number of pdusession failed to be setup in list */
|
||||
uint8_t nb_of_pdusessions_failed;
|
||||
/* list of pdusessions that failed to be setup */
|
||||
pdusession_failed_t pdusessions_failed[NGAP_MAX_PDUSESSION];
|
||||
} ngap_pdusession_setup_resp_t;
|
||||
|
||||
typedef struct ngap_path_switch_req_s {
|
||||
|
||||
uint32_t gNB_ue_ngap_id;
|
||||
|
||||
/* Number of pdusession setup-ed in the list */
|
||||
uint8_t nb_of_pdusessions;
|
||||
|
||||
/* list of pdusession setup-ed by RRC layers */
|
||||
pdusession_setup_t pdusessions_tobeswitched[NGAP_MAX_PDUSESSION];
|
||||
|
||||
/* AMF UE id */
|
||||
uint64_t amf_ue_ngap_id:40;
|
||||
|
||||
ngap_guami_t ue_guami;
|
||||
|
||||
uint16_t ue_initial_id;
|
||||
|
||||
/* Security algorithms */
|
||||
ngap_security_capabilities_t security_capabilities;
|
||||
|
||||
} ngap_path_switch_req_t;
|
||||
|
||||
typedef struct ngap_path_switch_req_ack_s {
|
||||
|
||||
/* UE id for initial connection to NGAP */
|
||||
uint16_t ue_initial_id;
|
||||
|
||||
uint32_t gNB_ue_ngap_id;
|
||||
|
||||
/* AMF UE id */
|
||||
uint64_t amf_ue_ngap_id:40;
|
||||
|
||||
/* UE aggregate maximum bitrate */
|
||||
ngap_ambr_t ue_ambr;
|
||||
|
||||
/* Number of pdusession setup-ed in the list */
|
||||
uint8_t nb_pdusessions_tobeswitched;
|
||||
|
||||
/* list of pdusession to be switched by RRC layers */
|
||||
pdusession_tobeswitched_t pdusessions_tobeswitched[NGAP_MAX_PDUSESSION];
|
||||
|
||||
/* Number of pdusessions to be released by RRC */
|
||||
uint8_t nb_pdusessions_tobereleased;
|
||||
|
||||
/* list of pdusessions to be released */
|
||||
pdusession_failed_t pdusessions_tobereleased[NGAP_MAX_PDUSESSION];
|
||||
|
||||
/* Security key */
|
||||
int next_hop_chain_count;
|
||||
uint8_t next_security_key[SECURITY_KEY_LENGTH];
|
||||
|
||||
} ngap_path_switch_req_ack_t;
|
||||
|
||||
typedef struct ngap_pdusession_modification_ind_s {
|
||||
|
||||
uint32_t gNB_ue_ngap_id;
|
||||
|
||||
/* AMF UE id */
|
||||
uint64_t amf_ue_ngap_id:40;
|
||||
|
||||
/* Number of pdusession setup-ed in the list */
|
||||
uint8_t nb_of_pdusessions_tobemodified;
|
||||
|
||||
uint8_t nb_of_pdusessions_nottobemodified;
|
||||
|
||||
/* list of pdusession setup-ed by RRC layers */
|
||||
pdusession_setup_t pdusessions_tobemodified[NGAP_MAX_PDUSESSION];
|
||||
|
||||
pdusession_setup_t pdusessions_nottobemodified[NGAP_MAX_PDUSESSION];
|
||||
|
||||
uint16_t ue_initial_id;
|
||||
|
||||
} ngap_pdusession_modification_ind_t;
|
||||
|
||||
// NGAP --> RRC messages
|
||||
typedef struct ngap_ue_release_command_s {
|
||||
|
||||
uint32_t gNB_ue_ngap_id;
|
||||
|
||||
} ngap_ue_release_command_t;
|
||||
|
||||
|
||||
//-------------------------------------------------------------------------------------------//
|
||||
// NGAP <-- RRC messages
|
||||
typedef struct ngap_ue_release_req_s {
|
||||
uint32_t gNB_ue_ngap_id;
|
||||
ngap_Cause_t cause;
|
||||
long cause_value;
|
||||
} ngap_ue_release_req_t, ngap_ue_release_resp_t;
|
||||
|
||||
typedef struct ngap_pdusession_modify_req_s {
|
||||
/* UE id for initial connection to NGAP */
|
||||
uint16_t ue_initial_id;
|
||||
|
||||
/* AMF UE id */
|
||||
uint64_t amf_ue_ngap_id:40;
|
||||
|
||||
/* gNB ue ngap id as initialized by NGAP layer */
|
||||
uint32_t gNB_ue_ngap_id;
|
||||
|
||||
/* Number of pdusession to be modify in the list */
|
||||
uint8_t nb_pdusessions_tomodify;
|
||||
|
||||
/* E RAB modify request */
|
||||
pdusession_t pdusession_modify_params[NGAP_MAX_PDUSESSION];
|
||||
} ngap_pdusession_modify_req_t;
|
||||
|
||||
typedef struct ngap_pdusession_modify_resp_s {
|
||||
uint32_t gNB_ue_ngap_id;
|
||||
|
||||
/* Number of pdusession modify-ed in the list */
|
||||
uint8_t nb_of_pdusessions;
|
||||
/* list of pdusession modify-ed by RRC layers */
|
||||
pdusession_modify_t pdusessions[NGAP_MAX_PDUSESSION];
|
||||
|
||||
/* Number of pdusession failed to be modify in list */
|
||||
uint8_t nb_of_pdusessions_failed;
|
||||
/* list of pdusessions that failed to be modify */
|
||||
pdusession_failed_t pdusessions_failed[NGAP_MAX_PDUSESSION];
|
||||
} ngap_pdusession_modify_resp_t;
|
||||
|
||||
typedef struct pdusession_release_s {
|
||||
/* Unique pdusession_id for the UE. */
|
||||
uint8_t pdusession_id;
|
||||
} pdusession_release_t;
|
||||
|
||||
typedef struct ngap_pdusession_release_command_s {
|
||||
/* AMF UE id */
|
||||
uint64_t amf_ue_ngap_id:40;
|
||||
|
||||
/* gNB ue ngap id as initialized by NGAP layer */
|
||||
uint32_t gNB_ue_ngap_id;
|
||||
|
||||
/* The NAS PDU should be forwarded by the RRC layer to the NAS layer */
|
||||
ngap_nas_pdu_t nas_pdu;
|
||||
|
||||
/* Number of pdusession to be released in the list */
|
||||
uint8_t nb_pdusessions_torelease;
|
||||
|
||||
/* PDUSession release command */
|
||||
pdusession_release_t pdusession_release_params[NGAP_MAX_PDUSESSION];
|
||||
|
||||
} ngap_pdusession_release_command_t;
|
||||
|
||||
typedef struct ngap_pdusession_release_resp_s {
|
||||
/* AMF UE id */
|
||||
uint64_t amf_ue_ngap_id:40;
|
||||
|
||||
/* gNB ue ngap id as initialized by NGAP layer */
|
||||
uint32_t gNB_ue_ngap_id;
|
||||
|
||||
/* Number of pdusession released in the list */
|
||||
uint8_t nb_of_pdusessions_released;
|
||||
|
||||
/* list of pdusessions released */
|
||||
pdusession_release_t pdusession_release[NGAP_MAX_PDUSESSION];
|
||||
|
||||
/* Number of pdusession failed to be released in list */
|
||||
uint8_t nb_of_pdusessions_failed;
|
||||
/* list of pdusessions that failed to be released */
|
||||
pdusession_failed_t pdusessions_failed[NGAP_MAX_PDUSESSION];
|
||||
|
||||
} ngap_pdusession_release_resp_t;
|
||||
|
||||
#endif /* NGAP_MESSAGES_TYPES_H_ */
|
||||
@@ -31,3 +31,6 @@
|
||||
MESSAGE_DEF(RRC_DCCH_DATA_REQ, MESSAGE_PRIORITY_MED_PLUS, RrcDcchDataReq, rrc_dcch_data_req)
|
||||
MESSAGE_DEF(RRC_DCCH_DATA_IND, MESSAGE_PRIORITY_MED_PLUS, RrcDcchDataInd, rrc_dcch_data_ind)
|
||||
MESSAGE_DEF(RRC_PCCH_DATA_REQ, MESSAGE_PRIORITY_MED_PLUS, RrcPcchDataReq, rrc_pcch_data_req)
|
||||
|
||||
// gNB
|
||||
MESSAGE_DEF(NR_RRC_DCCH_DATA_IND, MESSAGE_PRIORITY_MED_PLUS, NRRrcDcchDataInd, nr_rrc_dcch_data_ind)
|
||||
|
||||
@@ -35,6 +35,9 @@
|
||||
#define RRC_DCCH_DATA_IND(mSGpTR) (mSGpTR)->ittiMsg.rrc_dcch_data_ind
|
||||
#define RRC_PCCH_DATA_REQ(mSGpTR) (mSGpTR)->ittiMsg.rrc_pcch_data_req
|
||||
|
||||
// gNB
|
||||
#define NR_RRC_DCCH_DATA_IND(mSGpTR) (mSGpTR)->ittiMsg.nr_rrc_dcch_data_ind
|
||||
|
||||
//-------------------------------------------------------------------------------------------//
|
||||
// Messages between RRC and PDCP layers
|
||||
typedef struct RrcDcchDataReq_s {
|
||||
@@ -61,6 +64,16 @@ typedef struct RrcDcchDataInd_s {
|
||||
uint8_t eNB_index; // LG: needed in UE
|
||||
} RrcDcchDataInd;
|
||||
|
||||
typedef struct NRRrcDcchDataInd_s {
|
||||
uint32_t frame;
|
||||
uint8_t dcch_index;
|
||||
uint32_t sdu_size;
|
||||
uint8_t *sdu_p;
|
||||
uint16_t rnti;
|
||||
uint8_t module_id;
|
||||
uint8_t gNB_index; // LG: needed in UE
|
||||
} NRRrcDcchDataInd;
|
||||
|
||||
typedef struct RrcPcchDataReq_s {
|
||||
uint32_t sdu_size;
|
||||
uint8_t *sdu_p;
|
||||
|
||||
@@ -299,6 +299,12 @@ typedef struct protocol_ctxt_s {
|
||||
(CTXT_Pp)->module_id, \
|
||||
(CTXT_Pp)->rnti
|
||||
|
||||
#define PROTOCOL_NR_CTXT_ARGS(CTXT_Pp) \
|
||||
(CTXT_Pp)->frame, \
|
||||
((CTXT_Pp)->enb_flag == GNB_FLAG_YES) ? "gNB":" UE", \
|
||||
(CTXT_Pp)->module_id, \
|
||||
(CTXT_Pp)->rnti
|
||||
|
||||
#define CHECK_CTXT_ARGS(CTXT_Pp)
|
||||
|
||||
#define exit_fun(msg) exit_function(__FILE__,__FUNCTION__,__LINE__,msg)
|
||||
|
||||
@@ -74,6 +74,7 @@ TASK_DEF(TASK_PROTO_AGENT, TASK_PRIORITY_MED, 200)
|
||||
|
||||
/// Radio Resource Control task
|
||||
TASK_DEF(TASK_RRC_UE, TASK_PRIORITY_MED, 200)
|
||||
TASK_DEF(TASK_RRC_NRUE, TASK_PRIORITY_MED, 200)
|
||||
/// Non Access Stratum task
|
||||
TASK_DEF(TASK_NAS_UE, TASK_PRIORITY_MED, 200)
|
||||
TASK_DEF(TASK_RAL_UE, TASK_PRIORITY_MED, 200)
|
||||
@@ -81,3 +82,8 @@ TASK_DEF(TASK_RAL_UE, TASK_PRIORITY_MED, 200)
|
||||
//MESSAGE GENERATOR TASK
|
||||
TASK_DEF(TASK_MSC, TASK_PRIORITY_MED, 200)
|
||||
|
||||
#ifdef ITTI_SIM
|
||||
TASK_DEF(TASK_RRC_GNB_SIM, TASK_PRIORITY_MED, 200)
|
||||
TASK_DEF(TASK_RRC_UE_SIM, TASK_PRIORITY_MED, 200)
|
||||
#endif
|
||||
|
||||
|
||||
@@ -39,7 +39,7 @@
|
||||
|
||||
#include "x2ap_eNB.h"
|
||||
#include "intertask_interface.h"
|
||||
#include "s1ap_eNB.h"
|
||||
#include "ngap_gNB.h"
|
||||
#include "sctp_eNB_task.h"
|
||||
#include "gtpv1u_eNB_task.h"
|
||||
#include "PHY/INIT/phy_init.h"
|
||||
@@ -75,26 +75,29 @@ static void configure_nr_rrc(uint32_t gnb_id)
|
||||
static uint32_t gNB_app_register(uint32_t gnb_id_start, uint32_t gnb_id_end)//, const Enb_properties_array_t *enb_properties)
|
||||
{
|
||||
uint32_t gnb_id;
|
||||
//MessageDef *msg_p;
|
||||
MessageDef *msg_p;
|
||||
uint32_t register_gnb_pending = 0;
|
||||
|
||||
for (gnb_id = gnb_id_start; (gnb_id < gnb_id_end) ; gnb_id++) {
|
||||
{
|
||||
//s1ap_register_enb_req_t *s1ap_register_gNB; //Type Temporarily reuse
|
||||
if(NGAP_CONF_MODE){
|
||||
ngap_register_gnb_req_t *ngap_register_gNB; //Type Temporarily reuse
|
||||
|
||||
// note: there is an implicit relationship between the data structure and the message name
|
||||
msg_p = itti_alloc_new_message (TASK_GNB_APP, NGAP_REGISTER_GNB_REQ); //Message Temporarily reuse
|
||||
|
||||
// note: there is an implicit relationship between the data structure and the message name
|
||||
/*msg_p = itti_alloc_new_message (TASK_GNB_APP, S1AP_REGISTER_ENB_REQ); //Message Temporarily reuse
|
||||
RCconfig_NR_NG(msg_p, gnb_id);
|
||||
|
||||
ngap_register_gNB = &NGAP_REGISTER_GNB_REQ(msg_p); //Message Temporarily reuse
|
||||
|
||||
RCconfig_NR_S1(msg_p, gnb_id);*/
|
||||
LOG_I(GNB_APP,"default drx %d\n",ngap_register_gNB->default_drx);
|
||||
|
||||
itti_send_msg_to_task (TASK_NGAP, GNB_MODULE_ID_TO_INSTANCE(gnb_id), msg_p);
|
||||
}
|
||||
|
||||
if (gnb_id == 0) RCconfig_nr_gtpu();
|
||||
|
||||
/*s1ap_register_gNB = &S1AP_REGISTER_ENB_REQ(msg_p); //Message Temporarily reuse
|
||||
LOG_I(GNB_APP,"default drx %d\n",s1ap_register_gNB->default_drx);*/
|
||||
|
||||
LOG_I(GNB_APP,"[gNB %d] gNB_app_register for instance %d\n", gnb_id, GNB_MODULE_ID_TO_INSTANCE(gnb_id));
|
||||
|
||||
//itti_send_msg_to_task (TASK_S1AP, GNB_MODULE_ID_TO_INSTANCE(gnb_id), msg_p);
|
||||
LOG_I(GNB_APP,"[gNB %d] gNB_app_register for instance %d\n", gnb_id, GNB_MODULE_ID_TO_INSTANCE(gnb_id));
|
||||
|
||||
register_gnb_pending++;
|
||||
}
|
||||
@@ -173,7 +176,7 @@ void *gNB_app_task(void *args_p)
|
||||
__attribute__((unused)) uint32_t x2_register_gnb_pending = gNB_app_register_x2 (gnb_id_start, gnb_id_end);
|
||||
}
|
||||
|
||||
if (EPC_MODE_ENABLED) {
|
||||
if (AMF_MODE_ENABLED) {
|
||||
/* Try to register each gNB */
|
||||
//registered_gnb = 0;
|
||||
__attribute__((unused)) uint32_t register_gnb_pending = gNB_app_register (gnb_id_start, gnb_id_end);//, gnb_properties_p);
|
||||
@@ -201,16 +204,16 @@ void *gNB_app_task(void *args_p)
|
||||
break;
|
||||
|
||||
|
||||
/*
|
||||
case S1AP_REGISTER_ENB_CNF:
|
||||
LOG_I(GNB_APP, "[gNB %d] Received %s: associated MME %d\n", instance, msg_name,
|
||||
S1AP_REGISTER_ENB_CNF(msg_p).nb_mme);
|
||||
|
||||
case NGAP_REGISTER_GNB_CNF:
|
||||
LOG_I(GNB_APP, "[gNB %d] Received %s: associated AMF %d\n", instance, msg_name,
|
||||
NGAP_REGISTER_GNB_CNF(msg_p).nb_amf);
|
||||
/*
|
||||
DevAssert(register_gnb_pending > 0);
|
||||
register_gnb_pending--;
|
||||
|
||||
// Check if at least gNB is registered with one MME
|
||||
if (S1AP_REGISTER_ENB_CNF(msg_p).nb_mme > 0) {
|
||||
// Check if at least gNB is registered with one AMF
|
||||
if (NGAP_REGISTER_GNB_CNF(msg_p).nb_amf > 0) {
|
||||
registered_gnb++;
|
||||
}
|
||||
|
||||
@@ -226,7 +229,7 @@ void *gNB_app_task(void *args_p)
|
||||
} else {
|
||||
uint32_t not_associated = gnb_nb - registered_gnb;
|
||||
|
||||
LOG_W(GNB_APP, " %d gNB %s not associated with a MME, retrying registration in %d seconds ...\n",
|
||||
LOG_W(GNB_APP, " %d gNB %s not associated with a AMF, retrying registration in %d seconds ...\n",
|
||||
not_associated, not_associated > 1 ? "are" : "is", GNB_REGISTER_RETRY_DELAY);
|
||||
|
||||
// Restart the gNB registration process in GNB_REGISTER_RETRY_DELAY seconds
|
||||
@@ -241,12 +244,12 @@ void *gNB_app_task(void *args_p)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
break;
|
||||
*/
|
||||
case S1AP_DEREGISTERED_ENB_IND:
|
||||
LOG_W(GNB_APP, "[gNB %d] Received %s: associated MME %d\n", instance, msg_name,
|
||||
S1AP_DEREGISTERED_ENB_IND(msg_p).nb_mme);
|
||||
break;
|
||||
|
||||
case NGAP_DEREGISTERED_GNB_IND:
|
||||
LOG_W(GNB_APP, "[gNB %d] Received %s: associated AMF %d\n", instance, msg_name,
|
||||
NGAP_DEREGISTERED_GNB_IND(msg_p).nb_amf);
|
||||
|
||||
/* TODO handle recovering of registration */
|
||||
break;
|
||||
|
||||
@@ -38,6 +38,7 @@
|
||||
#include "UTIL/OTG/otg_externs.h"
|
||||
#include "intertask_interface.h"
|
||||
#include "s1ap_eNB.h"
|
||||
#include "ngap_gNB.h"
|
||||
#include "sctp_eNB_task.h"
|
||||
#include "sctp_default_values.h"
|
||||
// #include "SystemInformationBlockType2.h"
|
||||
@@ -341,8 +342,8 @@ void RCconfig_nr_flexran()
|
||||
/* gNB ID from configuration, as read in by RCconfig_RRC() */
|
||||
if (!GNBParamList.paramarray[i][GNB_GNB_ID_IDX].uptr) {
|
||||
// Calculate a default gNB ID
|
||||
if (EPC_MODE_ENABLED)
|
||||
gnb_id = i + (s1ap_generate_eNB_id () & 0xFFFF8);
|
||||
if (AMF_MODE_ENABLED)
|
||||
gnb_id = i + (ngap_generate_gNB_id () & 0xFFFFFF8);
|
||||
else
|
||||
gnb_id = i;
|
||||
} else {
|
||||
@@ -535,7 +536,7 @@ void RCconfig_NRRRC(MessageDef *msg_p, uint32_t i, gNB_RRC_INST *rrc) {
|
||||
AssertFatal (i<num_gnbs,"Failed to parse config file no %ith element in %s \n",i, GNB_CONFIG_STRING_ACTIVE_GNBS);
|
||||
|
||||
/*
|
||||
if (EPC_MODE_ENABLED) {
|
||||
if (AMF_MODE_ENABLED) {
|
||||
if (strcasecmp( *(GNBSParams[GNB_ASN1_VERBOSITY_IDX].strptr), GNB_CONFIG_STRING_ASN1_VERBOSITY_NONE) == 0) {
|
||||
asn_debug = 0;
|
||||
asn1_xer_print = 0;
|
||||
@@ -561,10 +562,10 @@ void RCconfig_NRRRC(MessageDef *msg_p, uint32_t i, gNB_RRC_INST *rrc) {
|
||||
|
||||
if (GNBParamList.paramarray[i][GNB_GNB_ID_IDX].uptr == NULL) {
|
||||
// Calculate a default gNB ID
|
||||
if (EPC_MODE_ENABLED) {
|
||||
if (AMF_MODE_ENABLED) {
|
||||
uint32_t hash;
|
||||
hash = s1ap_generate_eNB_id ();
|
||||
gnb_id = i + (hash & 0xFFFF8);
|
||||
hash = ngap_generate_gNB_id ();
|
||||
gnb_id = i + (hash & 0xFFFFFF8);
|
||||
} else {
|
||||
gnb_id = i;
|
||||
}
|
||||
@@ -672,16 +673,19 @@ int RCconfig_nr_gtpu(void ) {
|
||||
|
||||
|
||||
|
||||
char* gnb_interface_name_for_NGU = NULL;
|
||||
char* gnb_ipv4_address_for_NGU = NULL;
|
||||
uint32_t gnb_port_for_NGU = 0;
|
||||
char* gnb_interface_name_for_S1U = NULL;
|
||||
char* gnb_ipv4_address_for_S1U = NULL;
|
||||
uint32_t gnb_port_for_S1U = 0;
|
||||
char *address = NULL;
|
||||
char *cidr = NULL;
|
||||
char gtpupath[MAX_OPTNAME_SIZE*2 + 8];
|
||||
|
||||
uint8_t gnb_mode = 0;
|
||||
|
||||
paramdef_t GNBSParams[] = GNBSPARAMS_DESC;
|
||||
|
||||
paramdef_t NETParams[] = GNBNETPARAMS_DESC;
|
||||
paramdef_t GTPUParams[] = GNBGTPUPARAMS_DESC;
|
||||
LOG_I(GTPU,"Configuring GTPu\n");
|
||||
|
||||
@@ -691,15 +695,23 @@ int RCconfig_nr_gtpu(void ) {
|
||||
AssertFatal (num_gnbs >0,
|
||||
"Failed to parse config file no active gNodeBs in %s \n", GNB_CONFIG_STRING_ACTIVE_GNBS);
|
||||
|
||||
|
||||
sprintf(gtpupath,"%s.[%i].%s",GNB_CONFIG_STRING_GNB_LIST,0,GNB_CONFIG_STRING_NETWORK_INTERFACES_CONFIG);
|
||||
config_get( GTPUParams,sizeof(GTPUParams)/sizeof(paramdef_t),gtpupath);
|
||||
|
||||
config_get(GTPUParams,sizeof(GTPUParams)/sizeof(paramdef_t),gtpupath);
|
||||
|
||||
config_get(NETParams,sizeof(NETParams)/sizeof(paramdef_t),gtpupath);
|
||||
|
||||
if (NETParams[0].strptr != NULL) { // SA
|
||||
LOG_I(GTPU, "SA mode \n");
|
||||
cidr = gnb_ipv4_address_for_NGU;
|
||||
gnb_mode = 0;
|
||||
} else {// NSA
|
||||
LOG_I(GTPU, "NSA mode \n");
|
||||
cidr = gnb_ipv4_address_for_S1U;
|
||||
gnb_mode = 1;
|
||||
}
|
||||
|
||||
address = strtok(cidr, "/");
|
||||
|
||||
|
||||
if (address) {
|
||||
MessageDef *message;
|
||||
AssertFatal((message = itti_alloc_new_message(TASK_GNB_APP, GTPV1U_ENB_S1_REQ))!=NULL,"");
|
||||
@@ -707,18 +719,25 @@ int RCconfig_nr_gtpu(void ) {
|
||||
// LOG_I(GTPU,"Configuring GTPu address : %s -> %x\n",address,RC.gtpv1u_data_g->enb_ip_address_for_S1u_S12_S4_up);
|
||||
|
||||
|
||||
IPV4_STR_ADDR_TO_INT_NWBO ( address, GTPV1U_ENB_S1_REQ(message).enb_ip_address_for_S1u_S12_S4_up, "BAD IP ADDRESS FORMAT FOR eNB S1_U !\n" );
|
||||
LOG_I(GTPU,"Configuring GTPu address : %s -> %x\n",address,GTPV1U_ENB_S1_REQ(message).enb_ip_address_for_S1u_S12_S4_up);
|
||||
GTPV1U_ENB_S1_REQ(message).enb_port_for_S1u_S12_S4_up = gnb_port_for_S1U;
|
||||
if (gnb_mode == 1) { // NSA
|
||||
IPV4_STR_ADDR_TO_INT_NWBO (address, GTPV1U_ENB_S1_REQ(message).enb_ip_address_for_S1u_S12_S4_up, "BAD IP ADDRESS FORMAT FOR eNB S1_U !\n" );
|
||||
LOG_I(GTPU,"Configuring GTPu address : %s -> %x\n",address,GTPV1U_ENB_S1_REQ(message).enb_ip_address_for_S1u_S12_S4_up);
|
||||
GTPV1U_ENB_S1_REQ(message).enb_port_for_S1u_S12_S4_up = gnb_port_for_S1U;
|
||||
} else {// TODO SA
|
||||
IPV4_STR_ADDR_TO_INT_NWBO (address, GTPV1U_ENB_S1_REQ(message).enb_ip_address_for_S1u_S12_S4_up, "BAD IP ADDRESS FORMAT FOR gNB NG_U !\n" );
|
||||
LOG_I(GTPU,"Configuring GTPu address : %s -> %x\n",address,GTPV1U_ENB_S1_REQ(message).enb_ip_address_for_S1u_S12_S4_up);
|
||||
GTPV1U_ENB_S1_REQ(message).enb_port_for_S1u_S12_S4_up = gnb_port_for_NGU;
|
||||
}
|
||||
|
||||
itti_send_msg_to_task (TASK_GTPV1_U, 0, message); // data model is wrong: gtpu doesn't have enb_id (or module_id)
|
||||
} else
|
||||
LOG_E(GTPU,"invalid address for S1U\n");
|
||||
LOG_E(GTPU,"invalid address for NGU\n");
|
||||
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int RCconfig_NR_S1(MessageDef *msg_p, uint32_t i) {
|
||||
int RCconfig_NR_NG(MessageDef *msg_p, uint32_t i) {
|
||||
|
||||
int j,k = 0;
|
||||
int gnb_id;
|
||||
@@ -741,7 +760,7 @@ int RCconfig_NR_S1(MessageDef *msg_p, uint32_t i) {
|
||||
config_get( GNBSParams,sizeof(GNBSParams)/sizeof(paramdef_t),NULL);
|
||||
|
||||
/*
|
||||
if (EPC_MODE_ENABLED) {
|
||||
if (AMF_MODE_ENABLED) {
|
||||
if (strcasecmp( *(GNBSParams[GNB_ASN1_VERBOSITY_IDX].strptr), GNB_CONFIG_STRING_ASN1_VERBOSITY_NONE) == 0) {
|
||||
asn_debug = 0;
|
||||
asn1_xer_print = 0;
|
||||
@@ -766,56 +785,61 @@ int RCconfig_NR_S1(MessageDef *msg_p, uint32_t i) {
|
||||
if (GNBSParams[GNB_ACTIVE_GNBS_IDX].numelt>0) {
|
||||
// Output a list of all gNBs.
|
||||
config_getlist( &GNBParamList,GNBParams,sizeof(GNBParams)/sizeof(paramdef_t),NULL);
|
||||
|
||||
if (GNBParamList.numelt > 0) {
|
||||
for (k = 0; k < GNBParamList.numelt; k++) {
|
||||
if (GNBParamList.paramarray[k][GNB_GNB_ID_IDX].uptr == NULL) {
|
||||
// Calculate a default gNB ID
|
||||
if (EPC_MODE_ENABLED) {
|
||||
uint32_t hash;
|
||||
|
||||
hash = s1ap_generate_eNB_id ();
|
||||
gnb_id = k + (hash & 0xFFFF8);
|
||||
} else {
|
||||
gnb_id = k;
|
||||
}
|
||||
} else {
|
||||
if (GNBParamList.paramarray[k][GNB_GNB_ID_IDX].uptr == NULL) {
|
||||
// Calculate a default gNB ID
|
||||
if (AMF_MODE_ENABLED) {
|
||||
uint32_t hash;
|
||||
|
||||
hash = ngap_generate_gNB_id ();
|
||||
gnb_id = k + (hash & 0xFFFFFF8);
|
||||
} else {
|
||||
gnb_id = k;
|
||||
}
|
||||
} else {
|
||||
gnb_id = *(GNBParamList.paramarray[k][GNB_GNB_ID_IDX].uptr);
|
||||
}
|
||||
|
||||
|
||||
// search if in active list
|
||||
for (j=0; j < GNBSParams[GNB_ACTIVE_GNBS_IDX].numelt; j++) {
|
||||
if (strcmp(GNBSParams[GNB_ACTIVE_GNBS_IDX].strlistptr[j], *(GNBParamList.paramarray[k][GNB_GNB_NAME_IDX].strptr)) == 0) {
|
||||
// search if in active list
|
||||
for (j=0; j < GNBSParams[GNB_ACTIVE_GNBS_IDX].numelt; j++) {
|
||||
if (strcmp(GNBSParams[GNB_ACTIVE_GNBS_IDX].strlistptr[j], *(GNBParamList.paramarray[k][GNB_GNB_NAME_IDX].strptr)) == 0) {
|
||||
paramdef_t PLMNParams[] = GNBPLMNPARAMS_DESC;
|
||||
paramlist_def_t PLMNParamList = {GNB_CONFIG_STRING_PLMN_LIST, NULL, 0};
|
||||
paramdef_t SNSSAIParams[] = GNBSNSSAIPARAMS_DESC;
|
||||
paramlist_def_t SNSSAIParamList = {GNB_CONFIG_STRING_SNSSAI_LIST, NULL, 0};
|
||||
/* map parameter checking array instances to parameter definition array instances */
|
||||
checkedparam_t config_check_PLMNParams [] = PLMNPARAMS_CHECK;
|
||||
checkedparam_t config_check_SNSSAIParams [] = SNSSAIPARAMS_CHECK;
|
||||
|
||||
for (int I = 0; I < sizeof(PLMNParams) / sizeof(paramdef_t); ++I)
|
||||
PLMNParams[I].chkPptr = &(config_check_PLMNParams[I]);
|
||||
for (int J = 0; J < sizeof(SNSSAIParams) / sizeof(paramdef_t); ++J)
|
||||
SNSSAIParams[J].chkPptr = &(config_check_SNSSAIParams[J]);
|
||||
|
||||
paramdef_t S1Params[] = GNBS1PARAMS_DESC;
|
||||
paramlist_def_t S1ParamList = {GNB_CONFIG_STRING_MME_IP_ADDRESS,NULL,0};
|
||||
|
||||
paramdef_t SCTPParams[] = GNBSCTPPARAMS_DESC;
|
||||
paramdef_t NETParams[] = GNBNETPARAMS_DESC;
|
||||
char aprefix[MAX_OPTNAME_SIZE*2 + 8];
|
||||
|
||||
S1AP_REGISTER_ENB_REQ (msg_p).eNB_id = gnb_id;
|
||||
|
||||
if (strcmp(*(GNBParamList.paramarray[k][GNB_CELL_TYPE_IDX].strptr), "CELL_MACRO_GNB") == 0) {
|
||||
S1AP_REGISTER_ENB_REQ (msg_p).cell_type = CELL_MACRO_ENB;
|
||||
} else if (strcmp(*(GNBParamList.paramarray[k][GNB_CELL_TYPE_IDX].strptr), "CELL_HOME_GNB") == 0) {
|
||||
S1AP_REGISTER_ENB_REQ (msg_p).cell_type = CELL_HOME_ENB;
|
||||
} else {
|
||||
AssertFatal (0,
|
||||
"Failed to parse gNB configuration file %s, gnb %d unknown value \"%s\" for cell_type choice: CELL_MACRO_GNB or CELL_HOME_GNB !\n",
|
||||
RC.config_file_name, i, *(GNBParamList.paramarray[k][GNB_CELL_TYPE_IDX].strptr));
|
||||
}
|
||||
|
||||
S1AP_REGISTER_ENB_REQ (msg_p).eNB_name = strdup(*(GNBParamList.paramarray[k][GNB_GNB_NAME_IDX].strptr));
|
||||
S1AP_REGISTER_ENB_REQ (msg_p).tac = *GNBParamList.paramarray[k][GNB_TRACKING_AREA_CODE_IDX].uptr;
|
||||
paramdef_t NGParams[] = GNBNGPARAMS_DESC;
|
||||
paramlist_def_t NGParamList = {GNB_CONFIG_STRING_AMF_IP_ADDRESS,NULL,0};
|
||||
|
||||
paramdef_t SCTPParams[] = GNBSCTPPARAMS_DESC;
|
||||
paramdef_t NETParams[] = GNBNETPARAMS_DESC;
|
||||
char aprefix[MAX_OPTNAME_SIZE*2 + 8];
|
||||
sprintf(aprefix, "%s.[%i]", GNB_CONFIG_STRING_GNB_LIST, k);
|
||||
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).gNB_id = gnb_id;
|
||||
|
||||
if (strcmp(*(GNBParamList.paramarray[k][GNB_CELL_TYPE_IDX].strptr), "CELL_MACRO_GNB") == 0) {
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).cell_type = CELL_MACRO_GNB;
|
||||
} else if (strcmp(*(GNBParamList.paramarray[k][GNB_CELL_TYPE_IDX].strptr), "CELL_HOME_GNB") == 0) {
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).cell_type = CELL_HOME_ENB;
|
||||
} else {
|
||||
AssertFatal (0,
|
||||
"Failed to parse gNB configuration file %s, gnb %d unknown value \"%s\" for cell_type choice: CELL_MACRO_GNB or CELL_HOME_GNB !\n",
|
||||
RC.config_file_name, i, *(GNBParamList.paramarray[k][GNB_CELL_TYPE_IDX].strptr));
|
||||
}
|
||||
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).gNB_name = strdup(*(GNBParamList.paramarray[k][GNB_GNB_NAME_IDX].strptr));
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).tac = *GNBParamList.paramarray[k][GNB_TRACKING_AREA_CODE_IDX].uptr;
|
||||
AssertFatal(!GNBParamList.paramarray[k][GNB_MOBILE_COUNTRY_CODE_IDX_OLD].strptr
|
||||
&& !GNBParamList.paramarray[k][GNB_MOBILE_NETWORK_CODE_IDX_OLD].strptr,
|
||||
"It seems that you use an old configuration file. Please change the existing\n"
|
||||
@@ -831,100 +855,116 @@ int RCconfig_NR_S1(MessageDef *msg_p, uint32_t i) {
|
||||
AssertFatal(0, "The number of PLMN IDs must be in [1,6], but is %d\n",
|
||||
PLMNParamList.numelt);
|
||||
|
||||
S1AP_REGISTER_ENB_REQ(msg_p).num_plmn = PLMNParamList.numelt;
|
||||
NGAP_REGISTER_GNB_REQ(msg_p).num_plmn = PLMNParamList.numelt;
|
||||
|
||||
for (int l = 0; l < PLMNParamList.numelt; ++l) {
|
||||
|
||||
S1AP_REGISTER_ENB_REQ (msg_p).mcc[l] = *PLMNParamList.paramarray[l][GNB_MOBILE_COUNTRY_CODE_IDX].uptr;
|
||||
S1AP_REGISTER_ENB_REQ (msg_p).mnc[l] = *PLMNParamList.paramarray[l][GNB_MOBILE_NETWORK_CODE_IDX].uptr;
|
||||
S1AP_REGISTER_ENB_REQ (msg_p).mnc_digit_length[l] = *PLMNParamList.paramarray[l][GNB_MNC_DIGIT_LENGTH].u8ptr;
|
||||
S1AP_REGISTER_ENB_REQ (msg_p).default_drx = 0;
|
||||
AssertFatal((S1AP_REGISTER_ENB_REQ (msg_p).mnc_digit_length[l] == 2) ||
|
||||
(S1AP_REGISTER_ENB_REQ (msg_p).mnc_digit_length[l] == 3),
|
||||
"BAD MNC DIGIT LENGTH %d",
|
||||
S1AP_REGISTER_ENB_REQ (msg_p).mnc_digit_length[l]);
|
||||
}
|
||||
sprintf(aprefix,"%s.[%i]",GNB_CONFIG_STRING_GNB_LIST,k);
|
||||
config_getlist( &S1ParamList,S1Params,sizeof(S1Params)/sizeof(paramdef_t),aprefix);
|
||||
|
||||
S1AP_REGISTER_ENB_REQ (msg_p).nb_mme = 0;
|
||||
|
||||
for (int l = 0; l < S1ParamList.numelt; l++) {
|
||||
|
||||
S1AP_REGISTER_ENB_REQ (msg_p).nb_mme += 1;
|
||||
|
||||
strcpy(S1AP_REGISTER_ENB_REQ (msg_p).mme_ip_address[l].ipv4_address,*(S1ParamList.paramarray[l][GNB_MME_IPV4_ADDRESS_IDX].strptr));
|
||||
strcpy(S1AP_REGISTER_ENB_REQ (msg_p).mme_ip_address[l].ipv6_address,*(S1ParamList.paramarray[l][GNB_MME_IPV6_ADDRESS_IDX].strptr));
|
||||
char snssaistr[MAX_OPTNAME_SIZE*2 + 8];
|
||||
sprintf(snssaistr, "%s.[%i].%s.[%i]", GNB_CONFIG_STRING_GNB_LIST, k, GNB_CONFIG_STRING_PLMN_LIST, l);
|
||||
config_getlist(&SNSSAIParamList, SNSSAIParams, sizeof(SNSSAIParams)/sizeof(paramdef_t), snssaistr);
|
||||
|
||||
if (strcmp(*(S1ParamList.paramarray[l][GNB_MME_IP_ADDRESS_ACTIVE_IDX].strptr), "yes") == 0) {
|
||||
}
|
||||
if (strcmp(*(S1ParamList.paramarray[l][GNB_MME_IP_ADDRESS_PREFERENCE_IDX].strptr), "ipv4") == 0) {
|
||||
S1AP_REGISTER_ENB_REQ (msg_p).mme_ip_address[j].ipv4 = 1;
|
||||
} else if (strcmp(*(S1ParamList.paramarray[l][GNB_MME_IP_ADDRESS_PREFERENCE_IDX].strptr), "ipv6") == 0) {
|
||||
S1AP_REGISTER_ENB_REQ (msg_p).mme_ip_address[j].ipv6 = 1;
|
||||
} else if (strcmp(*(S1ParamList.paramarray[l][GNB_MME_IP_ADDRESS_PREFERENCE_IDX].strptr), "no") == 0) {
|
||||
S1AP_REGISTER_ENB_REQ (msg_p).mme_ip_address[j].ipv4 = 1;
|
||||
S1AP_REGISTER_ENB_REQ (msg_p).mme_ip_address[j].ipv6 = 1;
|
||||
}
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).mcc[l] = *PLMNParamList.paramarray[l][GNB_MOBILE_COUNTRY_CODE_IDX].uptr;
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).mnc[l] = *PLMNParamList.paramarray[l][GNB_MOBILE_NETWORK_CODE_IDX].uptr;
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).mnc_digit_length[l] = *PLMNParamList.paramarray[l][GNB_MNC_DIGIT_LENGTH].u8ptr;
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).default_drx = 0;
|
||||
AssertFatal((NGAP_REGISTER_GNB_REQ (msg_p).mnc_digit_length[l] == 2) ||
|
||||
(NGAP_REGISTER_GNB_REQ (msg_p).mnc_digit_length[l] == 3),
|
||||
"BAD MNC DIGIT LENGTH %d",
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).mnc_digit_length[l]);
|
||||
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).num_nssai[l] = SNSSAIParamList.numelt;
|
||||
for (int s = 0; s < SNSSAIParamList.numelt; ++s) {
|
||||
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).s_nssai[l][s].sST = *SNSSAIParamList.paramarray[s][GNB_SLICE_SERIVE_TYPE_IDX].uptr;
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).s_nssai[l][s].sD_flag = 0;
|
||||
if(*SNSSAIParamList.paramarray[s][GNB_SLICE_DIFFERENTIATOR_IDX].uptr != 0) {
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).s_nssai[l][s].sD_flag = 1;
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).s_nssai[l][s].sD[0] = (*SNSSAIParamList.paramarray[s][GNB_SLICE_DIFFERENTIATOR_IDX].uptr & 0xFF0000) >> 16;
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).s_nssai[l][s].sD[1] = (*SNSSAIParamList.paramarray[s][GNB_SLICE_DIFFERENTIATOR_IDX].uptr & 0x00FF00) >> 8;
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).s_nssai[l][s].sD[2] = (*SNSSAIParamList.paramarray[s][GNB_SLICE_DIFFERENTIATOR_IDX].uptr & 0x0000FF);
|
||||
}
|
||||
}
|
||||
}
|
||||
sprintf(aprefix,"%s.[%i]",GNB_CONFIG_STRING_GNB_LIST,k);
|
||||
config_getlist( &NGParamList,NGParams,sizeof(NGParams)/sizeof(paramdef_t),aprefix);
|
||||
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).nb_amf = 0;
|
||||
|
||||
for (int l = 0; l < NGParamList.numelt; l++) {
|
||||
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).nb_amf += 1;
|
||||
|
||||
strcpy(NGAP_REGISTER_GNB_REQ (msg_p).amf_ip_address[l].ipv4_address,*(NGParamList.paramarray[l][GNB_AMF_IPV4_ADDRESS_IDX].strptr));
|
||||
strcpy(NGAP_REGISTER_GNB_REQ (msg_p).amf_ip_address[l].ipv6_address,*(NGParamList.paramarray[l][GNB_AMF_IPV6_ADDRESS_IDX].strptr));
|
||||
|
||||
if (S1ParamList.paramarray[l][GNB_MME_BROADCAST_PLMN_INDEX].iptr)
|
||||
S1AP_REGISTER_ENB_REQ(msg_p).broadcast_plmn_num[l] = S1ParamList.paramarray[l][GNB_MME_BROADCAST_PLMN_INDEX].numelt;
|
||||
if (strcmp(*(NGParamList.paramarray[l][GNB_AMF_IP_ADDRESS_ACTIVE_IDX].strptr), "yes") == 0) {
|
||||
}
|
||||
if (strcmp(*(NGParamList.paramarray[l][GNB_AMF_IP_ADDRESS_PREFERENCE_IDX].strptr), "ipv4") == 0) {
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).amf_ip_address[j].ipv4 = 1;
|
||||
} else if (strcmp(*(NGParamList.paramarray[l][GNB_AMF_IP_ADDRESS_PREFERENCE_IDX].strptr), "ipv6") == 0) {
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).amf_ip_address[j].ipv6 = 1;
|
||||
} else if (strcmp(*(NGParamList.paramarray[l][GNB_AMF_IP_ADDRESS_PREFERENCE_IDX].strptr), "no") == 0) {
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).amf_ip_address[j].ipv4 = 1;
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).amf_ip_address[j].ipv6 = 1;
|
||||
}
|
||||
|
||||
if (NGParamList.paramarray[l][GNB_AMF_BROADCAST_PLMN_INDEX].iptr)
|
||||
NGAP_REGISTER_GNB_REQ(msg_p).broadcast_plmn_num[l] = NGParamList.paramarray[l][GNB_AMF_BROADCAST_PLMN_INDEX].numelt;
|
||||
else
|
||||
S1AP_REGISTER_ENB_REQ(msg_p).broadcast_plmn_num[l] = 0;
|
||||
NGAP_REGISTER_GNB_REQ(msg_p).broadcast_plmn_num[l] = 0;
|
||||
|
||||
AssertFatal(S1AP_REGISTER_ENB_REQ(msg_p).broadcast_plmn_num[l] <= S1AP_REGISTER_ENB_REQ(msg_p).num_plmn,
|
||||
"List of broadcast PLMN to be sent to MME can not be longer than actual "
|
||||
AssertFatal(NGAP_REGISTER_GNB_REQ(msg_p).broadcast_plmn_num[l] <= NGAP_REGISTER_GNB_REQ(msg_p).num_plmn,
|
||||
"List of broadcast PLMN to be sent to AMF can not be longer than actual "
|
||||
"PLMN list (max %d, but is %d)\n",
|
||||
S1AP_REGISTER_ENB_REQ(msg_p).num_plmn,
|
||||
S1AP_REGISTER_ENB_REQ(msg_p).broadcast_plmn_num[l]);
|
||||
NGAP_REGISTER_GNB_REQ(msg_p).num_plmn,
|
||||
NGAP_REGISTER_GNB_REQ(msg_p).broadcast_plmn_num[l]);
|
||||
|
||||
for (int el = 0; el < S1AP_REGISTER_ENB_REQ(msg_p).broadcast_plmn_num[l]; ++el) {
|
||||
for (int el = 0; el < NGAP_REGISTER_GNB_REQ(msg_p).broadcast_plmn_num[l]; ++el) {
|
||||
/* UINTARRAY gets mapped to int, see config_libconfig.c:223 */
|
||||
S1AP_REGISTER_ENB_REQ(msg_p).broadcast_plmn_index[l][el] = S1ParamList.paramarray[l][GNB_MME_BROADCAST_PLMN_INDEX].iptr[el];
|
||||
AssertFatal(S1AP_REGISTER_ENB_REQ(msg_p).broadcast_plmn_index[l][el] >= 0
|
||||
&& S1AP_REGISTER_ENB_REQ(msg_p).broadcast_plmn_index[l][el] < S1AP_REGISTER_ENB_REQ(msg_p).num_plmn,
|
||||
"index for MME's MCC/MNC (%d) is an invalid index for the registered PLMN IDs (%d)\n",
|
||||
S1AP_REGISTER_ENB_REQ(msg_p).broadcast_plmn_index[l][el],
|
||||
S1AP_REGISTER_ENB_REQ(msg_p).num_plmn);
|
||||
NGAP_REGISTER_GNB_REQ(msg_p).broadcast_plmn_index[l][el] = NGParamList.paramarray[l][GNB_AMF_BROADCAST_PLMN_INDEX].iptr[el];
|
||||
AssertFatal(NGAP_REGISTER_GNB_REQ(msg_p).broadcast_plmn_index[l][el] >= 0
|
||||
&& NGAP_REGISTER_GNB_REQ(msg_p).broadcast_plmn_index[l][el] < NGAP_REGISTER_GNB_REQ(msg_p).num_plmn,
|
||||
"index for AMF's MCC/MNC (%d) is an invalid index for the registered PLMN IDs (%d)\n",
|
||||
NGAP_REGISTER_GNB_REQ(msg_p).broadcast_plmn_index[l][el],
|
||||
NGAP_REGISTER_GNB_REQ(msg_p).num_plmn);
|
||||
}
|
||||
|
||||
/* if no broadcasst_plmn array is defined, fill default values */
|
||||
if (S1AP_REGISTER_ENB_REQ(msg_p).broadcast_plmn_num[l] == 0) {
|
||||
S1AP_REGISTER_ENB_REQ(msg_p).broadcast_plmn_num[l] = S1AP_REGISTER_ENB_REQ(msg_p).num_plmn;
|
||||
if (NGAP_REGISTER_GNB_REQ(msg_p).broadcast_plmn_num[l] == 0) {
|
||||
NGAP_REGISTER_GNB_REQ(msg_p).broadcast_plmn_num[l] = NGAP_REGISTER_GNB_REQ(msg_p).num_plmn;
|
||||
|
||||
for (int el = 0; el < S1AP_REGISTER_ENB_REQ(msg_p).num_plmn; ++el)
|
||||
S1AP_REGISTER_ENB_REQ(msg_p).broadcast_plmn_index[l][el] = el;
|
||||
for (int el = 0; el < NGAP_REGISTER_GNB_REQ(msg_p).num_plmn; ++el)
|
||||
NGAP_REGISTER_GNB_REQ(msg_p).broadcast_plmn_index[l][el] = el;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
// SCTP SETTING
|
||||
S1AP_REGISTER_ENB_REQ (msg_p).sctp_out_streams = SCTP_OUT_STREAMS;
|
||||
S1AP_REGISTER_ENB_REQ (msg_p).sctp_in_streams = SCTP_IN_STREAMS;
|
||||
if (EPC_MODE_ENABLED) {
|
||||
sprintf(aprefix,"%s.[%i].%s",GNB_CONFIG_STRING_GNB_LIST,k,GNB_CONFIG_STRING_SCTP_CONFIG);
|
||||
config_get( SCTPParams,sizeof(SCTPParams)/sizeof(paramdef_t),aprefix);
|
||||
S1AP_REGISTER_ENB_REQ (msg_p).sctp_in_streams = (uint16_t)*(SCTPParams[GNB_SCTP_INSTREAMS_IDX].uptr);
|
||||
S1AP_REGISTER_ENB_REQ (msg_p).sctp_out_streams = (uint16_t)*(SCTPParams[GNB_SCTP_OUTSTREAMS_IDX].uptr);
|
||||
}
|
||||
|
||||
// SCTP SETTING
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).sctp_out_streams = SCTP_OUT_STREAMS;
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).sctp_in_streams = SCTP_IN_STREAMS;
|
||||
if (AMF_MODE_ENABLED) {
|
||||
sprintf(aprefix,"%s.[%i].%s",GNB_CONFIG_STRING_GNB_LIST,k,GNB_CONFIG_STRING_SCTP_CONFIG);
|
||||
config_get( SCTPParams,sizeof(SCTPParams)/sizeof(paramdef_t),aprefix);
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).sctp_in_streams = (uint16_t)*(SCTPParams[GNB_SCTP_INSTREAMS_IDX].uptr);
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).sctp_out_streams = (uint16_t)*(SCTPParams[GNB_SCTP_OUTSTREAMS_IDX].uptr);
|
||||
}
|
||||
|
||||
sprintf(aprefix,"%s.[%i].%s",GNB_CONFIG_STRING_GNB_LIST,k,GNB_CONFIG_STRING_NETWORK_INTERFACES_CONFIG);
|
||||
// NETWORK_INTERFACES
|
||||
// NETWORK_INTERFACES
|
||||
config_get( NETParams,sizeof(NETParams)/sizeof(paramdef_t),aprefix);
|
||||
|
||||
// S1AP_REGISTER_ENB_REQ (msg_p).enb_interface_name_for_S1U = strdup(enb_interface_name_for_S1U);
|
||||
cidr = *(NETParams[GNB_IPV4_ADDRESS_FOR_S1_MME_IDX].strptr);
|
||||
address = strtok(cidr, "/");
|
||||
|
||||
S1AP_REGISTER_ENB_REQ (msg_p).enb_ip_address.ipv6 = 0;
|
||||
S1AP_REGISTER_ENB_REQ (msg_p).enb_ip_address.ipv4 = 1;
|
||||
|
||||
strcpy(S1AP_REGISTER_ENB_REQ (msg_p).enb_ip_address.ipv4_address, address);
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// NGAP_REGISTER_GNB_REQ (msg_p).enb_interface_name_for_NGU = strdup(enb_interface_name_for_NGU);
|
||||
cidr = *(NETParams[GNB_IPV4_ADDRESS_FOR_NG_AMF_IDX].strptr);
|
||||
address = strtok(cidr, "/");
|
||||
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).gnb_ip_address.ipv6 = 0;
|
||||
NGAP_REGISTER_GNB_REQ (msg_p).gnb_ip_address.ipv4 = 1;
|
||||
|
||||
strcpy(NGAP_REGISTER_GNB_REQ (msg_p).gnb_ip_address.ipv4_address, address);
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1021,10 +1061,10 @@ int RCconfig_NR_X2(MessageDef *msg_p, uint32_t i) {
|
||||
for (k = 0; k < GNBParamList.numelt; k++) {
|
||||
if (GNBParamList.paramarray[k][GNB_GNB_ID_IDX].uptr == NULL) {
|
||||
// Calculate a default eNB ID
|
||||
if (EPC_MODE_ENABLED) {
|
||||
if (AMF_MODE_ENABLED) {
|
||||
uint32_t hash;
|
||||
hash = s1ap_generate_eNB_id ();
|
||||
gnb_id = k + (hash & 0xFFFF8);
|
||||
hash = ngap_generate_gNB_id ();
|
||||
gnb_id = k + (hash & 0xFFFFFF8);
|
||||
} else {
|
||||
gnb_id = k;
|
||||
}
|
||||
@@ -1150,7 +1190,7 @@ int RCconfig_NR_X2(MessageDef *msg_p, uint32_t i) {
|
||||
X2AP_REGISTER_ENB_REQ (msg_p).sctp_out_streams = SCTP_OUT_STREAMS;
|
||||
X2AP_REGISTER_ENB_REQ (msg_p).sctp_in_streams = SCTP_IN_STREAMS;
|
||||
|
||||
if (EPC_MODE_ENABLED) {
|
||||
if (AMF_MODE_ENABLED) {
|
||||
sprintf(aprefix,"%s.[%i].%s",GNB_CONFIG_STRING_GNB_LIST,k,GNB_CONFIG_STRING_SCTP_CONFIG);
|
||||
config_get( SCTPParams,sizeof(SCTPParams)/sizeof(paramdef_t),aprefix);
|
||||
X2AP_REGISTER_ENB_REQ (msg_p).sctp_in_streams = (uint16_t)*(SCTPParams[GNB_SCTP_INSTREAMS_IDX].uptr);
|
||||
|
||||
@@ -39,6 +39,7 @@
|
||||
#include "platform_constants.h"
|
||||
#include "PHY/defs_eNB.h"
|
||||
#include "s1ap_messages_types.h"
|
||||
#include "ngap_messages_types.h"
|
||||
|
||||
#ifdef CMAKER
|
||||
#include "rrc_messages_types.h"
|
||||
@@ -102,7 +103,7 @@ extern void NRRCConfig(void);
|
||||
//void ru_config_display(void);
|
||||
|
||||
void RCconfig_NRRRC(MessageDef *msg_p, uint32_t i, gNB_RRC_INST *rrc);
|
||||
int RCconfig_NR_S1(MessageDef *msg_p, uint32_t i);
|
||||
int RCconfig_NR_NG(MessageDef *msg_p, uint32_t i);
|
||||
int RCconfig_NR_X2(MessageDef *msg_p, uint32_t i);
|
||||
|
||||
#endif /* GNB_CONFIG_H_ */
|
||||
|
||||
@@ -150,7 +150,7 @@ typedef struct ccparams_nr_x2 {
|
||||
{GNB_CONFIG_STRING_GNB_ID, NULL, 0, uptr:NULL, defintval:0, TYPE_UINT, 0}, \
|
||||
{GNB_CONFIG_STRING_CELL_TYPE, NULL, 0, strptr:NULL, defstrval:"CELL_MACRO_GNB", TYPE_STRING, 0}, \
|
||||
{GNB_CONFIG_STRING_GNB_NAME, NULL, 0, strptr:NULL, defstrval:"OAIgNodeB", TYPE_STRING, 0}, \
|
||||
{GNB_CONFIG_STRING_TRACKING_AREA_CODE, NULL, 0, strptr:NULL, defstrval:"0", TYPE_STRING, 0}, \
|
||||
{GNB_CONFIG_STRING_TRACKING_AREA_CODE, NULL, 0, uptr:NULL, defuintval:0, TYPE_UINT, 0}, \
|
||||
{GNB_CONFIG_STRING_MOBILE_COUNTRY_CODE_OLD, NULL, 0, strptr:NULL, defstrval:NULL, TYPE_STRING, 0}, \
|
||||
{GNB_CONFIG_STRING_MOBILE_NETWORK_CODE_OLD, NULL, 0, strptr:NULL, defstrval:NULL, TYPE_STRING, 0}, \
|
||||
{GNB_CONFIG_STRING_TRANSPORT_S_PREFERENCE, NULL, 0, strptr:NULL, defstrval:"local_mac", TYPE_STRING, 0}, \
|
||||
@@ -236,38 +236,58 @@ typedef struct ccparams_nr_x2 {
|
||||
}
|
||||
|
||||
|
||||
/* SNSSAI ID configuration */
|
||||
|
||||
#define GNB_CONFIG_STRING_SNSSAI_LIST "snssaiList"
|
||||
|
||||
#define GNB_CONFIG_STRING_SLICE_SERIVE_TYPE "sst"
|
||||
#define GNB_CONFIG_STRING_SLICE_DIFFERENTIATOR "sd"
|
||||
|
||||
/* MME configuration parameters section name */
|
||||
#define GNB_CONFIG_STRING_MME_IP_ADDRESS "mme_ip_address"
|
||||
#define GNB_SLICE_SERIVE_TYPE_IDX 0
|
||||
#define GNB_SLICE_DIFFERENTIATOR_IDX 1
|
||||
|
||||
#define GNBSNSSAIPARAMS_DESC { \
|
||||
/* optname helpstr paramflags XXXptr def val type numelt */ \
|
||||
{GNB_CONFIG_STRING_SLICE_SERIVE_TYPE, "slice serive type", 0, uptr:NULL, defuintval:1, TYPE_UINT, 0}, \
|
||||
{GNB_CONFIG_STRING_SLICE_DIFFERENTIATOR, "slice differentiator", 0, uptr:NULL, defuintval:0, TYPE_UINT, 0}, \
|
||||
}
|
||||
|
||||
#define SLICE_SERIVE_TYPE_OKRANGES {1,2,3,4}
|
||||
|
||||
#define SNSSAIPARAMS_CHECK { \
|
||||
{ .s1 = { config_check_intval, SLICE_SERIVE_TYPE_OKRANGES, 4 } }, \
|
||||
{ .s5 = { NULL } }, \
|
||||
}
|
||||
|
||||
/* AMF configuration parameters section name */
|
||||
#define GNB_CONFIG_STRING_AMF_IP_ADDRESS "amf_ip_address"
|
||||
|
||||
/* SRB1 configuration parameters names */
|
||||
|
||||
|
||||
#define GNB_CONFIG_STRING_MME_IPV4_ADDRESS "ipv4"
|
||||
#define GNB_CONFIG_STRING_MME_IPV6_ADDRESS "ipv6"
|
||||
#define GNB_CONFIG_STRING_MME_IP_ADDRESS_ACTIVE "active"
|
||||
#define GNB_CONFIG_STRING_MME_IP_ADDRESS_PREFERENCE "preference"
|
||||
#define GNB_CONFIG_STRING_MME_BROADCAST_PLMN_INDEX "broadcast_plmn_index"
|
||||
#define GNB_CONFIG_STRING_AMF_IPV4_ADDRESS "ipv4"
|
||||
#define GNB_CONFIG_STRING_AMF_IPV6_ADDRESS "ipv6"
|
||||
#define GNB_CONFIG_STRING_AMF_IP_ADDRESS_ACTIVE "active"
|
||||
#define GNB_CONFIG_STRING_AMF_IP_ADDRESS_PREFERENCE "preference"
|
||||
#define GNB_CONFIG_STRING_AMF_BROADCAST_PLMN_INDEX "broadcast_plmn_index"
|
||||
|
||||
|
||||
/*-------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
/* MME configuration parameters */
|
||||
/* optname helpstr paramflags XXXptr defXXXval type numelt */
|
||||
/*-------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
#define GNBS1PARAMS_DESC { \
|
||||
{GNB_CONFIG_STRING_MME_IPV4_ADDRESS, NULL, 0, uptr:NULL, defstrval:NULL, TYPE_STRING, 0}, \
|
||||
{GNB_CONFIG_STRING_MME_IPV6_ADDRESS, NULL, 0, uptr:NULL, defstrval:NULL, TYPE_STRING, 0}, \
|
||||
{GNB_CONFIG_STRING_MME_IP_ADDRESS_ACTIVE, NULL, 0, uptr:NULL, defstrval:NULL, TYPE_STRING, 0}, \
|
||||
{GNB_CONFIG_STRING_MME_IP_ADDRESS_PREFERENCE, NULL, 0, uptr:NULL, defstrval:NULL, TYPE_STRING, 0}, \
|
||||
#define GNBNGPARAMS_DESC { \
|
||||
{GNB_CONFIG_STRING_AMF_IPV4_ADDRESS, NULL, 0, uptr:NULL, defstrval:NULL, TYPE_STRING, 0}, \
|
||||
{GNB_CONFIG_STRING_AMF_IPV6_ADDRESS, NULL, 0, uptr:NULL, defstrval:NULL, TYPE_STRING, 0}, \
|
||||
{GNB_CONFIG_STRING_AMF_IP_ADDRESS_ACTIVE, NULL, 0, uptr:NULL, defstrval:NULL, TYPE_STRING, 0}, \
|
||||
{GNB_CONFIG_STRING_AMF_IP_ADDRESS_PREFERENCE, NULL, 0, uptr:NULL, defstrval:NULL, TYPE_STRING, 0}, \
|
||||
}
|
||||
|
||||
#define GNB_MME_IPV4_ADDRESS_IDX 0
|
||||
#define GNB_MME_IPV6_ADDRESS_IDX 1
|
||||
#define GNB_MME_IP_ADDRESS_ACTIVE_IDX 2
|
||||
#define GNB_MME_IP_ADDRESS_PREFERENCE_IDX 3
|
||||
#define GNB_MME_BROADCAST_PLMN_INDEX 4
|
||||
#define GNB_AMF_IPV4_ADDRESS_IDX 0
|
||||
#define GNB_AMF_IPV6_ADDRESS_IDX 1
|
||||
#define GNB_AMF_IP_ADDRESS_ACTIVE_IDX 2
|
||||
#define GNB_AMF_IP_ADDRESS_PREFERENCE_IDX 3
|
||||
#define GNB_AMF_BROADCAST_PLMN_INDEX 4
|
||||
/*---------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
/*---------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
/* SCTP configuration parameters section name */
|
||||
@@ -295,11 +315,11 @@ typedef struct ccparams_nr_x2 {
|
||||
/* S1 interface configuration parameters section name */
|
||||
#define GNB_CONFIG_STRING_NETWORK_INTERFACES_CONFIG "NETWORK_INTERFACES"
|
||||
|
||||
#define GNB_INTERFACE_NAME_FOR_S1_MME_IDX 0
|
||||
#define GNB_IPV4_ADDRESS_FOR_S1_MME_IDX 1
|
||||
#define GNB_INTERFACE_NAME_FOR_S1U_IDX 2
|
||||
#define GNB_IPV4_ADDR_FOR_S1U_IDX 3
|
||||
#define GNB_PORT_FOR_S1U_IDX 4
|
||||
#define GNB_INTERFACE_NAME_FOR_NG_AMF_IDX 0
|
||||
#define GNB_IPV4_ADDRESS_FOR_NG_AMF_IDX 1
|
||||
#define GNB_INTERFACE_NAME_FOR_NGU_IDX 2
|
||||
#define GNB_IPV4_ADDR_FOR_NGU_IDX 3
|
||||
#define GNB_PORT_FOR_NGU_IDX 4
|
||||
#define GNB_IPV4_ADDR_FOR_X2C_IDX 5
|
||||
#define GNB_PORT_FOR_X2C_IDX 6
|
||||
|
||||
@@ -307,9 +327,15 @@ typedef struct ccparams_nr_x2 {
|
||||
#define GNB_CONFIG_STRING_GNB_INTERFACE_NAME_FOR_S1_MME "GNB_INTERFACE_NAME_FOR_S1_MME"
|
||||
#define GNB_CONFIG_STRING_GNB_IPV4_ADDRESS_FOR_S1_MME "GNB_IPV4_ADDRESS_FOR_S1_MME"
|
||||
#define GNB_CONFIG_STRING_GNB_INTERFACE_NAME_FOR_S1U "GNB_INTERFACE_NAME_FOR_S1U"
|
||||
#define GNB_CONFIG_STRING_GNB_IPV4_ADDR_FOR_S1U "GNB_IPV4_ADDRESS_FOR_S1U"
|
||||
#define GNB_CONFIG_STRING_GNB_IPV4_ADDRESS_FOR_S1U "GNB_IPV4_ADDRESS_FOR_S1U"
|
||||
#define GNB_CONFIG_STRING_GNB_PORT_FOR_S1U "GNB_PORT_FOR_S1U"
|
||||
|
||||
#define GNB_CONFIG_STRING_GNB_INTERFACE_NAME_FOR_NG_AMF "GNB_INTERFACE_NAME_FOR_NG_AMF"
|
||||
#define GNB_CONFIG_STRING_GNB_IPV4_ADDRESS_FOR_NG_AMF "GNB_IPV4_ADDRESS_FOR_NG_AMF"
|
||||
#define GNB_CONFIG_STRING_GNB_INTERFACE_NAME_FOR_NGU "GNB_INTERFACE_NAME_FOR_NGU"
|
||||
#define GNB_CONFIG_STRING_GNB_IPV4_ADDR_FOR_NGU "GNB_IPV4_ADDRESS_FOR_NGU"
|
||||
#define GNB_CONFIG_STRING_GNB_PORT_FOR_NGU "GNB_PORT_FOR_NGU"
|
||||
|
||||
/* X2 interface configuration parameters names */
|
||||
#define GNB_CONFIG_STRING_ENB_IPV4_ADDR_FOR_X2C "GNB_IPV4_ADDRESS_FOR_X2C"
|
||||
#define GNB_CONFIG_STRING_ENB_PORT_FOR_X2C "GNB_PORT_FOR_X2C"
|
||||
@@ -319,11 +345,11 @@ typedef struct ccparams_nr_x2 {
|
||||
/* optname helpstr paramflags XXXptr defXXXval type numelt */
|
||||
/*--------------------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
#define GNBNETPARAMS_DESC { \
|
||||
{GNB_CONFIG_STRING_GNB_INTERFACE_NAME_FOR_S1_MME, NULL, 0, strptr:NULL, defstrval:NULL, TYPE_STRING, 0}, \
|
||||
{GNB_CONFIG_STRING_GNB_IPV4_ADDRESS_FOR_S1_MME, NULL, 0, strptr:NULL, defstrval:NULL, TYPE_STRING, 0}, \
|
||||
{GNB_CONFIG_STRING_GNB_INTERFACE_NAME_FOR_S1U, NULL, 0, strptr:NULL, defstrval:NULL, TYPE_STRING, 0}, \
|
||||
{GNB_CONFIG_STRING_GNB_IPV4_ADDR_FOR_S1U, NULL, 0, strptr:NULL, defstrval:NULL, TYPE_STRING, 0}, \
|
||||
{GNB_CONFIG_STRING_GNB_PORT_FOR_S1U, NULL, 0, uptr:NULL, defintval:2152L, TYPE_UINT, 0}, \
|
||||
{GNB_CONFIG_STRING_GNB_INTERFACE_NAME_FOR_NG_AMF, NULL, 0, strptr:NULL, defstrval:NULL, TYPE_STRING, 0}, \
|
||||
{GNB_CONFIG_STRING_GNB_IPV4_ADDRESS_FOR_NG_AMF, NULL, 0, strptr:NULL, defstrval:NULL, TYPE_STRING, 0}, \
|
||||
{GNB_CONFIG_STRING_GNB_INTERFACE_NAME_FOR_NGU, NULL, 0, strptr:NULL, defstrval:NULL, TYPE_STRING, 0}, \
|
||||
{GNB_CONFIG_STRING_GNB_IPV4_ADDR_FOR_NGU, NULL, 0, strptr:NULL, defstrval:NULL, TYPE_STRING, 0}, \
|
||||
{GNB_CONFIG_STRING_GNB_PORT_FOR_NGU, NULL, 0, uptr:NULL, defintval:2152L, TYPE_UINT, 0}, \
|
||||
{GNB_CONFIG_STRING_ENB_IPV4_ADDR_FOR_X2C, NULL, 0, strptr:NULL, defstrval:NULL, TYPE_STRING, 0}, \
|
||||
{GNB_CONFIG_STRING_ENB_PORT_FOR_X2C, NULL, 0, uptr:NULL, defintval:0L, TYPE_UINT, 0} \
|
||||
}
|
||||
@@ -335,8 +361,11 @@ typedef struct ccparams_nr_x2 {
|
||||
/* optname helpstr paramflags XXXptr defXXXval type numelt */
|
||||
/*--------------------------------------------------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
#define GNBGTPUPARAMS_DESC { \
|
||||
{GNB_CONFIG_STRING_GNB_INTERFACE_NAME_FOR_NGU, NULL, 0, strptr:&gnb_interface_name_for_NGU, defstrval:"lo", TYPE_STRING, 0}, \
|
||||
{GNB_CONFIG_STRING_GNB_IPV4_ADDR_FOR_NGU, NULL, 0, strptr:&gnb_ipv4_address_for_NGU, defstrval:"127.0.0.1", TYPE_STRING, 0}, \
|
||||
{GNB_CONFIG_STRING_GNB_PORT_FOR_NGU, NULL, 0, uptr:&gnb_port_for_NGU, defintval:2152, TYPE_UINT, 0}, \
|
||||
{GNB_CONFIG_STRING_GNB_INTERFACE_NAME_FOR_S1U, NULL, 0, strptr:&gnb_interface_name_for_S1U, defstrval:"lo", TYPE_STRING, 0}, \
|
||||
{GNB_CONFIG_STRING_GNB_IPV4_ADDR_FOR_S1U, NULL, 0, strptr:&gnb_ipv4_address_for_S1U, defstrval:"127.0.0.1", TYPE_STRING, 0}, \
|
||||
{GNB_CONFIG_STRING_GNB_IPV4_ADDRESS_FOR_S1U, NULL, 0, strptr:&gnb_ipv4_address_for_S1U, defstrval:"127.0.0.1", TYPE_STRING, 0}, \
|
||||
{GNB_CONFIG_STRING_GNB_PORT_FOR_S1U, NULL, 0, uptr:&gnb_port_for_S1U, defintval:2152, TYPE_UINT, 0} \
|
||||
}
|
||||
/*-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------*/
|
||||
|
||||
@@ -185,6 +185,7 @@ void ue_dci_configuration(NR_UE_MAC_INST_t *mac, fapi_nr_dl_config_request_t *dl
|
||||
|
||||
int ss_id;
|
||||
uint8_t bwp_id = 1, coreset_id = 1;
|
||||
//NR_ServingCellConfig_t *scd = mac->scg->spCellConfig->spCellConfigDedicated;
|
||||
NR_BWP_Downlink_t *bwp = mac->DLbwp[bwp_id - 1];
|
||||
|
||||
#ifdef DEBUG_DCI
|
||||
|
||||
@@ -2065,7 +2065,7 @@ uint16_t nr_dci_format_size (PHY_VARS_NR_UE *ue,
|
||||
(dynamic_prb_BundlingType2==dy_2_n4)||(dynamic_prb_BundlingType2==dy_2_wideband)) prb_BundlingType_size=1;
|
||||
|
||||
// 15 RATE_MATCHING_IND FIXME!!!
|
||||
// according to TS 38.212: Rate matching indicator – 0, 1, or 2 bits according to higher layer parameter rateMatchPattern
|
||||
// according to TS 38.212: Rate matching indicator E0, 1, or 2 bits according to higher layer parameter rateMatchPattern
|
||||
uint8_t rateMatching_bits = pdsch_config.n_rateMatchPatterns;
|
||||
// 16 ZP_CSI_RS_TRIGGER FIXME!!!
|
||||
// 0, 1, or 2 bits as defined in Subclause 5.1.4.2 of [6, TS 38.214].
|
||||
@@ -2208,7 +2208,7 @@ uint16_t nr_dci_format_size (PHY_VARS_NR_UE *ue,
|
||||
// 2 bits otherwise
|
||||
uint8_t ptrs_dmrs_bits=0; //FIXME!!!
|
||||
// 46 BETA_OFFSET_IND
|
||||
// at IE PUSCH-Config, beta_offset indicator – 0 if the higher layer parameter betaOffsets = semiStatic; otherwise 2 bits
|
||||
// at IE PUSCH-Config, beta_offset indicator E0 if the higher layer parameter betaOffsets = semiStatic; otherwise 2 bits
|
||||
// uci-OnPUSCH
|
||||
// Selection between and configuration of dynamic and semi-static beta-offset. If the field is absent or released, the UE applies the value 'semiStatic' and the BetaOffsets
|
||||
uint8_t betaOffsets = 0;
|
||||
@@ -4147,10 +4147,10 @@ int nr_extract_dci_info(NR_UE_MAC_INST_t *mac,
|
||||
|
||||
case NR_RNTI_P:
|
||||
/*
|
||||
// Short Messages Indicator – 2 bits
|
||||
// Short Messages Indicator E2 bits
|
||||
for (int i=0; i<2; i++)
|
||||
dci_pdu |= (((uint64_t)dci_pdu_rel15->short_messages_indicator>>(1-i))&1)<<(dci_size-pos++);
|
||||
// Short Messages – 8 bits
|
||||
// Short Messages E8 bits
|
||||
for (int i=0; i<8; i++)
|
||||
*dci_pdu |= (((uint64_t)dci_pdu_rel15->short_messages>>(7-i))&1)<<(dci_size-pos++);
|
||||
// Freq domain assignment 0-16 bit
|
||||
@@ -4217,13 +4217,13 @@ int nr_extract_dci_info(NR_UE_MAC_INST_t *mac,
|
||||
// HARQ process number 4bit
|
||||
pos+=4;
|
||||
dci_pdu_rel15->harq_pid = (*dci_pdu>>(dci_size-pos))&0xf;
|
||||
// Downlink assignment index – 2 bits
|
||||
// Downlink assignment index E2 bits
|
||||
pos+=2;
|
||||
dci_pdu_rel15->dai[0].val = (*dci_pdu>>(dci_size-pos))&3;
|
||||
// TPC command for scheduled PUCCH – 2 bits
|
||||
// TPC command for scheduled PUCCH E2 bits
|
||||
pos+=2;
|
||||
dci_pdu_rel15->tpc = (*dci_pdu>>(dci_size-pos))&3;
|
||||
// PDSCH-to-HARQ_feedback timing indicator – 3 bits
|
||||
// PDSCH-to-HARQ_feedback timing indicator E3 bits
|
||||
pos+=3;
|
||||
dci_pdu_rel15->pdsch_to_harq_feedback_timing_indicator.val = (*dci_pdu>>(dci_size-pos))&7;
|
||||
|
||||
@@ -4241,10 +4241,9 @@ int nr_extract_dci_info(NR_UE_MAC_INST_t *mac,
|
||||
// Time domain assignment 4bit
|
||||
pos+=4;
|
||||
dci_pdu_rel15->time_domain_assignment.val = (*dci_pdu>>(dci_size-pos))&0xf;
|
||||
// This is not supported yet - Skip for now
|
||||
// Frequency hopping flag – 1 bit
|
||||
//pos++;
|
||||
//dci_pdu_rel15->frequency_hopping_flag.val= (*dci_pdu>>(dci_size-pos))&1;
|
||||
// Frequency hopping flag E1 bit
|
||||
pos++;
|
||||
dci_pdu_rel15->frequency_hopping_flag.val= (*dci_pdu>>(dci_size-pos))&1;
|
||||
// MCS 5 bit
|
||||
pos+=5;
|
||||
dci_pdu_rel15->mcs= (*dci_pdu>>(dci_size-pos))&0x1f;
|
||||
@@ -4257,10 +4256,10 @@ int nr_extract_dci_info(NR_UE_MAC_INST_t *mac,
|
||||
// HARQ process number 4bit
|
||||
pos+=4;
|
||||
dci_pdu_rel15->harq_pid = (*dci_pdu>>(dci_size-pos))&0xf;
|
||||
// TPC command for scheduled PUSCH – 2 bits
|
||||
// TPC command for scheduled PUSCH E2 bits
|
||||
pos+=2;
|
||||
dci_pdu_rel15->tpc = (*dci_pdu>>(dci_size-pos))&3;
|
||||
// UL/SUL indicator – 1 bit
|
||||
// UL/SUL indicator E1 bit
|
||||
/* commented for now (RK): need to get this from BWP descriptor
|
||||
if (cfg->pucch_config.pucch_GroupHopping.value)
|
||||
dci_pdu->= ((uint64_t)*dci_pdu>>(dci_size-pos)ul_sul_indicator&1)<<(dci_size-pos++);
|
||||
@@ -4278,7 +4277,7 @@ int nr_extract_dci_info(NR_UE_MAC_INST_t *mac,
|
||||
// Time domain assignment 4bit
|
||||
for (int i=0; i<4; i++)
|
||||
dci_pdu->= (((uint64_t)*dci_pdu>>(dci_size-pos)time_domain_assignment>>(3-i))&1)<<(dci_size-pos++);
|
||||
// Frequency hopping flag – 1 bit
|
||||
// Frequency hopping flag E1 bit
|
||||
dci_pdu->= ((uint64_t)*dci_pdu>>(dci_size-pos)frequency_hopping_flag&1)<<(dci_size-pos++);
|
||||
// MCS 5 bit
|
||||
for (int i=0; i<5; i++)
|
||||
@@ -4292,11 +4291,11 @@ int nr_extract_dci_info(NR_UE_MAC_INST_t *mac,
|
||||
for (int i=0; i<4; i++)
|
||||
*dci_pdu |= (((uint64_t)*dci_pdu>>(dci_size-pos)harq_pid>>(3-i))&1)<<(dci_size-pos++);
|
||||
|
||||
// TPC command for scheduled PUSCH – 2 bits
|
||||
// TPC command for scheduled PUSCH E2 bits
|
||||
for (int i=0; i<2; i++)
|
||||
dci_pdu->= (((uint64_t)*dci_pdu>>(dci_size-pos)tpc>>(1-i))&1)<<(dci_size-pos++);
|
||||
*/
|
||||
// UL/SUL indicator – 1 bit
|
||||
// UL/SUL indicator E1 bit
|
||||
/*
|
||||
commented for now (RK): need to get this information from BWP descriptor
|
||||
if (cfg->pucch_config.pucch_GroupHopping.value)
|
||||
|
||||
@@ -798,7 +798,11 @@ void nr_configure_pucch(nfapi_nr_pucch_pdu_t* pucch_pdu,
|
||||
AssertFatal(1==0,"Couldn't fine pucch resource indicator %d in PUCCH resource set %d for %d UCI bits",pucch_resource,i,O_uci);
|
||||
}
|
||||
if (pucchresset->pucch_ResourceSetId == 1 && O_uci>2) {
|
||||
#if (NR_RRC_VERSION >= MAKE_VERSION(16, 0, 0))
|
||||
N3 = pucchresset->maxPayloadSize!= NULL ? *pucchresset->maxPayloadSize : 1706;
|
||||
#else
|
||||
N3 = pucchresset->maxPayloadMinus1!= NULL ? *pucchresset->maxPayloadMinus1 : 1706;
|
||||
#endif
|
||||
if (N2<O_uci && N3>O_uci) {
|
||||
if (pucch_resource < n_list)
|
||||
resource_id = pucchresset->resourceList.list.array[pucch_resource];
|
||||
|
||||
@@ -358,16 +358,7 @@ boolean_t pdcp_data_req(
|
||||
LOG_D(PDCP, "pdcp data req on drb %ld, size %d, rnti %x, node_type %d \n",
|
||||
rb_idP, pdcp_pdu_size, ctxt_pP->rnti, RC.rrc ? RC.rrc[ctxt_pP->module_id]->node_type: -1);
|
||||
|
||||
// The check on nos1 is done only for the use case of LTE stack running over 5g-nr PHY. This should be changed
|
||||
// before future merge of develop with develop-nr and instead of a check of IS_SOFTMODEM_NOS1, we should use a check
|
||||
// with a new execution option capturing the nr-ip-over-LTE-stack use case.
|
||||
ngran_node_t node_type;
|
||||
if (IS_SOFTMODEM_NOS1)
|
||||
node_type = ngran_gNB;
|
||||
else
|
||||
node_type = RC.rrc[ctxt_pP->module_id]->node_type;
|
||||
|
||||
if (ctxt_pP->enb_flag == ENB_FLAG_YES && NODE_IS_DU(node_type)) { //RC.rrc[ctxt_pP->module_id]->node_type
|
||||
if (ctxt_pP->enb_flag == ENB_FLAG_YES && NODE_IS_DU(RC.rrc[ctxt_pP->module_id]->node_type)) {
|
||||
LOG_E(PDCP, "Can't be DU, bad node type %d \n", RC.rrc[ctxt_pP->module_id]->node_type);
|
||||
ret=FALSE;
|
||||
} else {
|
||||
|
||||
@@ -22,6 +22,7 @@
|
||||
#include "nr_pdcp_entity.h"
|
||||
|
||||
#include "nr_pdcp_entity_drb_am.h"
|
||||
#include "nr_pdcp_entity_srb.h"
|
||||
|
||||
#include "LOG/log.h"
|
||||
|
||||
@@ -34,7 +35,32 @@ nr_pdcp_entity_t *new_nr_pdcp_entity_srb(
|
||||
char *buf, int size, int sdu_id),
|
||||
void *deliver_pdu_data)
|
||||
{
|
||||
abort();
|
||||
|
||||
nr_pdcp_entity_srb_t *ret;
|
||||
|
||||
ret = calloc(1, sizeof(nr_pdcp_entity_srb_t));
|
||||
if (ret == NULL) {
|
||||
LOG_E(PDCP, "%s:%d:%s: out of memory\n", __FILE__, __LINE__, __FUNCTION__);
|
||||
exit(1);
|
||||
}
|
||||
|
||||
ret->common.recv_pdu = nr_pdcp_entity_srb_recv_pdu;
|
||||
ret->common.recv_sdu = nr_pdcp_entity_srb_recv_sdu;
|
||||
ret->common.set_integrity_key = nr_pdcp_entity_srb_set_integrity_key;
|
||||
|
||||
ret->common.delete = nr_pdcp_entity_srb_delete;
|
||||
|
||||
ret->common.deliver_sdu = deliver_sdu;
|
||||
ret->common.deliver_sdu_data = deliver_sdu_data;
|
||||
|
||||
ret->common.deliver_pdu = deliver_pdu;
|
||||
ret->common.deliver_pdu_data = deliver_pdu_data;
|
||||
|
||||
ret->srb_id = rb_id;
|
||||
|
||||
ret->common.maximum_nr_pdcp_sn = 4095;
|
||||
|
||||
return (nr_pdcp_entity_t *)ret;
|
||||
}
|
||||
|
||||
nr_pdcp_entity_t *new_nr_pdcp_entity_drb_am(
|
||||
|
||||
75
openair2/LAYER2/nr_pdcp/nr_pdcp_entity_srb.c
Normal file
75
openair2/LAYER2/nr_pdcp/nr_pdcp_entity_srb.c
Normal file
@@ -0,0 +1,75 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
#include "nr_pdcp_entity_srb.h"
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
void nr_pdcp_entity_srb_recv_pdu(nr_pdcp_entity_t *_entity, char *buffer, int size)
|
||||
{
|
||||
nr_pdcp_entity_srb_t *entity = (nr_pdcp_entity_srb_t *)_entity;
|
||||
|
||||
if (size < 2) abort();
|
||||
entity->common.deliver_sdu(entity->common.deliver_sdu_data,
|
||||
(nr_pdcp_entity_t *)entity, buffer+2, size-2);
|
||||
}
|
||||
|
||||
void nr_pdcp_entity_srb_recv_sdu(nr_pdcp_entity_t *_entity, char *buffer, int size,
|
||||
int sdu_id)
|
||||
{
|
||||
nr_pdcp_entity_srb_t *entity = (nr_pdcp_entity_srb_t *)_entity;
|
||||
int sn;
|
||||
char buf[size+6];
|
||||
|
||||
sn = entity->common.next_nr_pdcp_tx_sn;
|
||||
|
||||
entity->common.next_nr_pdcp_tx_sn++;
|
||||
if (entity->common.next_nr_pdcp_tx_sn > entity->common.maximum_nr_pdcp_sn) {
|
||||
entity->common.next_nr_pdcp_tx_sn = 0;
|
||||
entity->common.tx_hfn++;
|
||||
}
|
||||
|
||||
buf[0] = (sn >> 8) & 0x0f;
|
||||
buf[1] = sn & 0xff;
|
||||
memcpy(buf+2, buffer, size);
|
||||
|
||||
/* For now use padding for the MAC-I bytes (normally carrying message authentication code)
|
||||
* which come after the data payload bytes (38.323, section 6.2.2.1) */
|
||||
for (int i=size; i<size+4; i++)
|
||||
buf[i] = 0;
|
||||
|
||||
entity->common.deliver_pdu(entity->common.deliver_pdu_data,
|
||||
(nr_pdcp_entity_t *)entity, buf, size+6, sdu_id);
|
||||
}
|
||||
|
||||
void nr_pdcp_entity_srb_set_integrity_key(nr_pdcp_entity_t *_entity, char *key)
|
||||
{
|
||||
/* nothing to do */
|
||||
}
|
||||
|
||||
void nr_pdcp_entity_srb_delete(nr_pdcp_entity_t *_entity)
|
||||
{
|
||||
nr_pdcp_entity_srb_t *entity = (nr_pdcp_entity_srb_t *)_entity;
|
||||
free(entity);
|
||||
}
|
||||
|
||||
38
openair2/LAYER2/nr_pdcp/nr_pdcp_entity_srb.h
Normal file
38
openair2/LAYER2/nr_pdcp/nr_pdcp_entity_srb.h
Normal file
@@ -0,0 +1,38 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
#ifndef _NR_PDCP_ENTITY_SRB_H_
|
||||
#define _NR_PDCP_ENTITY_SRB_H_
|
||||
|
||||
#include "nr_pdcp_entity.h"
|
||||
|
||||
typedef struct {
|
||||
nr_pdcp_entity_t common;
|
||||
int srb_id;
|
||||
} nr_pdcp_entity_srb_t;
|
||||
|
||||
void nr_pdcp_entity_srb_recv_pdu(nr_pdcp_entity_t *_entity, char *buffer, int size);
|
||||
void nr_pdcp_entity_srb_recv_sdu(nr_pdcp_entity_t *_entity, char *buffer, int size, int sdu_id);
|
||||
void nr_pdcp_entity_srb_set_integrity_key(nr_pdcp_entity_t *_entity, char *key);
|
||||
void nr_pdcp_entity_srb_delete(nr_pdcp_entity_t *_entity);
|
||||
|
||||
|
||||
#endif /* _NR_PDCP_ENTITY_SRB_H_ */
|
||||
@@ -486,6 +486,54 @@ rb_found:
|
||||
enqueue_rlc_data_req(&ctxt, 0, MBMS_FLAG_NO, rb_id, sdu_id, 0, size, memblock, NULL, NULL);
|
||||
}
|
||||
|
||||
static void deliver_sdu_srb(void *_ue, nr_pdcp_entity_t *entity,
|
||||
char *buf, int size)
|
||||
{
|
||||
/* Implementation to be added */
|
||||
return;
|
||||
}
|
||||
|
||||
static void deliver_pdu_srb(void *_ue, nr_pdcp_entity_t *entity,
|
||||
char *buf, int size, int sdu_id)
|
||||
{
|
||||
nr_pdcp_ue_t *ue = _ue;
|
||||
int srb_id;
|
||||
protocol_ctxt_t ctxt;
|
||||
int i;
|
||||
mem_block_t *memblock;
|
||||
|
||||
for (i = 0; i < 2; i++) {
|
||||
if (entity == ue->srb[i]) {
|
||||
srb_id = i+1;
|
||||
goto rb_found;
|
||||
}
|
||||
}
|
||||
|
||||
LOG_E(PDCP, "%s:%d:%s: fatal, no RB found for ue %d\n",
|
||||
__FILE__, __LINE__, __FUNCTION__, ue->rnti);
|
||||
exit(1);
|
||||
|
||||
rb_found:
|
||||
ctxt.module_id = 0;
|
||||
ctxt.enb_flag = 1;
|
||||
ctxt.instance = 0;
|
||||
ctxt.frame = 0;
|
||||
ctxt.subframe = 0;
|
||||
ctxt.eNB_index = 0;
|
||||
ctxt.configured = 1;
|
||||
ctxt.brOption = 0;
|
||||
|
||||
ctxt.rnti = ue->rnti;
|
||||
|
||||
memblock = get_free_mem_block(size, __FUNCTION__);
|
||||
memcpy(memblock->data, buf, size);
|
||||
|
||||
printf("!!!!!!! deliver_pdu_srb (srb %d) calling rlc_data_req size %d: ", srb_id, size);
|
||||
//for (i = 0; i < size; i++) printf(" %2.2x", (unsigned char)memblock->data[i]);
|
||||
printf("\n");
|
||||
enqueue_rlc_data_req(&ctxt, 1, MBMS_FLAG_NO, srb_id, sdu_id, 0, size, memblock, NULL, NULL);
|
||||
}
|
||||
|
||||
boolean_t pdcp_data_ind(
|
||||
const protocol_ctxt_t *const ctxt_pP,
|
||||
const srb_flag_t srb_flagP,
|
||||
@@ -586,7 +634,32 @@ void pdcp_run(const protocol_ctxt_t *const ctxt_pP)
|
||||
|
||||
static void add_srb(int rnti, struct NR_SRB_ToAddMod *s)
|
||||
{
|
||||
TODO;
|
||||
nr_pdcp_entity_t *pdcp_srb;
|
||||
nr_pdcp_ue_t *ue;
|
||||
|
||||
int srb_id = s->srb_Identity;
|
||||
|
||||
printf("\n\n################# rnti %d add drb %d\n\n\n", rnti, srb_id);
|
||||
|
||||
if (srb_id != 1) {
|
||||
LOG_E(PDCP, "%s:%d:%s: fatal, bad drb id %d\n",
|
||||
__FILE__, __LINE__, __FUNCTION__, srb_id);
|
||||
exit(1);
|
||||
}
|
||||
|
||||
nr_pdcp_manager_lock(nr_pdcp_ue_manager);
|
||||
ue = nr_pdcp_manager_get_ue(nr_pdcp_ue_manager, rnti);
|
||||
if (ue->srb[srb_id-1] != NULL) {
|
||||
LOG_D(PDCP, "%s:%d:%s: warning DRB %d already exist for ue %d, do nothing\n",
|
||||
__FILE__, __LINE__, __FUNCTION__, srb_id, rnti);
|
||||
} else {
|
||||
pdcp_srb = new_nr_pdcp_entity_srb(srb_id, deliver_sdu_srb, ue, deliver_pdu_srb, ue);
|
||||
nr_pdcp_ue_add_srb_pdcp_entity(ue, srb_id, pdcp_srb);
|
||||
|
||||
LOG_D(PDCP, "%s:%d:%s: added drb %d to ue %d\n",
|
||||
__FILE__, __LINE__, __FUNCTION__, srb_id, rnti);
|
||||
}
|
||||
nr_pdcp_manager_unlock(nr_pdcp_ue_manager);
|
||||
}
|
||||
|
||||
static void add_drb_am(int rnti, struct NR_DRB_ToAddMod *s)
|
||||
@@ -869,10 +942,45 @@ boolean_t pdcp_remove_UE(
|
||||
return 1;
|
||||
}
|
||||
|
||||
void pdcp_config_set_security(const protocol_ctxt_t* const ctxt_pP, pdcp_t *pdcp_pP, rb_id_t rb_id,
|
||||
uint16_t lc_idP, uint8_t security_modeP, uint8_t *kRRCenc_pP, uint8_t *kRRCint_pP, uint8_t *kUPenc_pP)
|
||||
void pdcp_config_set_security(
|
||||
const protocol_ctxt_t* const ctxt_pP,
|
||||
pdcp_t *const pdcp_pP,
|
||||
const rb_id_t rb_id,
|
||||
const uint16_t lc_idP,
|
||||
const uint8_t security_modeP,
|
||||
uint8_t *const kRRCenc_pP,
|
||||
uint8_t *const kRRCint_pP,
|
||||
uint8_t *const kUPenc_pP)
|
||||
{
|
||||
TODO;
|
||||
DevAssert(pdcp_pP != NULL);
|
||||
|
||||
if ((security_modeP >= 0) && (security_modeP <= 0x77)) {
|
||||
pdcp_pP->cipheringAlgorithm = security_modeP & 0x0f;
|
||||
pdcp_pP->integrityProtAlgorithm = (security_modeP>>4) & 0xf;
|
||||
LOG_D(PDCP, PROTOCOL_PDCP_CTXT_FMT" CONFIG_ACTION_SET_SECURITY_MODE: cipheringAlgorithm %d integrityProtAlgorithm %d\n",
|
||||
PROTOCOL_PDCP_CTXT_ARGS(ctxt_pP,pdcp_pP),
|
||||
pdcp_pP->cipheringAlgorithm,
|
||||
pdcp_pP->integrityProtAlgorithm);
|
||||
pdcp_pP->kRRCenc = kRRCenc_pP;
|
||||
pdcp_pP->kRRCint = kRRCint_pP;
|
||||
pdcp_pP->kUPenc = kUPenc_pP;
|
||||
/* Activate security */
|
||||
pdcp_pP->security_activated = 1;
|
||||
MSC_LOG_EVENT(
|
||||
(ctxt_pP->enb_flag == ENB_FLAG_YES) ? MSC_PDCP_ENB:MSC_PDCP_UE,
|
||||
"0 Set security ciph %X integ %x UE %"PRIx16" ",
|
||||
pdcp_pP->cipheringAlgorithm,
|
||||
pdcp_pP->integrityProtAlgorithm,
|
||||
ctxt_pP->rnti);
|
||||
} else {
|
||||
MSC_LOG_EVENT(
|
||||
(ctxt_pP->enb_flag == ENB_FLAG_YES) ? MSC_PDCP_ENB:MSC_PDCP_UE,
|
||||
"0 Set security failed UE %"PRIx16" ",
|
||||
ctxt_pP->rnti);
|
||||
LOG_E(PDCP,PROTOCOL_PDCP_CTXT_FMT" bad security mode %d",
|
||||
PROTOCOL_PDCP_CTXT_ARGS(ctxt_pP,pdcp_pP),
|
||||
security_modeP);
|
||||
}
|
||||
}
|
||||
|
||||
static boolean_t pdcp_data_req_drb(
|
||||
|
||||
@@ -37,6 +37,9 @@
|
||||
|
||||
#include "COMMON/s1ap_messages_types.h"
|
||||
#include "COMMON/rrc_messages_types.h"
|
||||
#if ITTI_SIM
|
||||
#include "COMMON/itti_sim_messages_types.h"
|
||||
#endif
|
||||
|
||||
#include "collection/tree.h"
|
||||
#include "rrc_types_NB_IoT.h"
|
||||
|
||||
@@ -43,6 +43,77 @@
|
||||
|
||||
extern RAN_CONTEXT_t RC;
|
||||
|
||||
int
|
||||
nr_rrc_mac_remove_ue(module_id_t mod_idP,
|
||||
rnti_t rntiP){
|
||||
// todo
|
||||
return 0;
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
uint8_t
|
||||
nr_rrc_data_req(
|
||||
const protocol_ctxt_t *const ctxt_pP,
|
||||
const rb_id_t rb_idP,
|
||||
const mui_t muiP,
|
||||
const confirm_t confirmP,
|
||||
const sdu_size_t sdu_sizeP,
|
||||
uint8_t *const buffer_pP,
|
||||
const pdcp_transmission_mode_t modeP
|
||||
)
|
||||
//------------------------------------------------------------------------------
|
||||
{
|
||||
if(sdu_sizeP == 255) {
|
||||
LOG_I(RRC,"sdu_sizeP == 255");
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
MSC_LOG_TX_MESSAGE(
|
||||
ctxt_pP->enb_flag ? MSC_RRC_ENB : MSC_RRC_UE,
|
||||
ctxt_pP->enb_flag ? MSC_PDCP_ENB : MSC_PDCP_UE,
|
||||
buffer_pP,
|
||||
sdu_sizeP,
|
||||
MSC_AS_TIME_FMT"RRC_DCCH_DATA_REQ UE %x MUI %d size %u",
|
||||
MSC_AS_TIME_ARGS(ctxt_pP),
|
||||
ctxt_pP->rnti,
|
||||
muiP,
|
||||
sdu_sizeP);
|
||||
MessageDef *message_p;
|
||||
// Uses a new buffer to avoid issue with PDCP buffer content that could be changed by PDCP (asynchronous message handling).
|
||||
uint8_t *message_buffer;
|
||||
message_buffer = itti_malloc (
|
||||
ctxt_pP->enb_flag ? TASK_RRC_ENB : TASK_RRC_UE,
|
||||
ctxt_pP->enb_flag ? TASK_PDCP_ENB : TASK_PDCP_UE,
|
||||
sdu_sizeP);
|
||||
memcpy (message_buffer, buffer_pP, sdu_sizeP);
|
||||
message_p = itti_alloc_new_message (ctxt_pP->enb_flag ? TASK_RRC_ENB : TASK_RRC_UE, RRC_DCCH_DATA_REQ);
|
||||
RRC_DCCH_DATA_REQ (message_p).frame = ctxt_pP->frame;
|
||||
RRC_DCCH_DATA_REQ (message_p).enb_flag = ctxt_pP->enb_flag;
|
||||
RRC_DCCH_DATA_REQ (message_p).rb_id = rb_idP;
|
||||
RRC_DCCH_DATA_REQ (message_p).muip = muiP;
|
||||
RRC_DCCH_DATA_REQ (message_p).confirmp = confirmP;
|
||||
RRC_DCCH_DATA_REQ (message_p).sdu_size = sdu_sizeP;
|
||||
RRC_DCCH_DATA_REQ (message_p).sdu_p = message_buffer;
|
||||
//memcpy (RRC_DCCH_DATA_REQ (message_p).sdu_p, buffer_pP, sdu_sizeP);
|
||||
RRC_DCCH_DATA_REQ (message_p).mode = modeP;
|
||||
RRC_DCCH_DATA_REQ (message_p).module_id = ctxt_pP->module_id;
|
||||
RRC_DCCH_DATA_REQ (message_p).rnti = ctxt_pP->rnti;
|
||||
RRC_DCCH_DATA_REQ (message_p).eNB_index = ctxt_pP->eNB_index;
|
||||
itti_send_msg_to_task (
|
||||
ctxt_pP->enb_flag ? TASK_PDCP_ENB : TASK_PDCP_UE,
|
||||
ctxt_pP->instance,
|
||||
message_p);
|
||||
LOG_I(RRC,"sent RRC_DCCH_DATA_REQ to TASK_PDCP_ENB\n");
|
||||
|
||||
/* Hack: only trigger PDCP if in CU, otherwise it is triggered by RU threads
|
||||
* Ideally, PDCP would not neet to be triggered like this but react to ITTI
|
||||
* messages automatically */
|
||||
if (ctxt_pP->enb_flag && NODE_IS_CU(RC.rrc[ctxt_pP->module_id]->node_type))
|
||||
pdcp_run(ctxt_pP);
|
||||
|
||||
return TRUE; // TODO should be changed to a CNF message later, currently RRC lite does not used the returned value anyway.
|
||||
}
|
||||
|
||||
int8_t mac_rrc_nr_data_req(const module_id_t Mod_idP,
|
||||
const int CC_id,
|
||||
const frame_t frameP,
|
||||
|
||||
@@ -41,8 +41,34 @@
|
||||
#include <per_encoder.h>
|
||||
|
||||
#include "asn1_msg.h"
|
||||
#include "../nr_rrc_proto.h"
|
||||
#include "RRC/NR/nr_rrc_extern.h"
|
||||
#if defined(NR_Rel15)
|
||||
#include "NR_DL-CCCH-Message.h"
|
||||
#include "NR_UL-CCCH-Message.h"
|
||||
#include "NR_DL-DCCH-Message.h"
|
||||
#include "NR_RRCReject.h"
|
||||
#include "NR_RejectWaitTime.h"
|
||||
#include "NR_RRCSetup.h"
|
||||
#include "NR_RRCSetup-IEs.h"
|
||||
#include "NR_SRB-ToAddModList.h"
|
||||
#include "NR_CellGroupConfig.h"
|
||||
#include "NR_RLC-BearerConfig.h"
|
||||
#include "NR_RLC-Config.h"
|
||||
#include "NR_LogicalChannelConfig.h"
|
||||
#include "NR_PDCP-Config.h"
|
||||
#include "NR_MAC-CellGroupConfig.h"
|
||||
#include "NR_SecurityModeCommand.h"
|
||||
#include "NR_CipheringAlgorithm.h"
|
||||
#include "NR_RRCReconfiguration-IEs.h"
|
||||
#include "NR_DRB-ToAddMod.h"
|
||||
#include "NR_DRB-ToAddModList.h"
|
||||
#include "NR_SecurityConfig.h"
|
||||
#include "NR_RRCReconfiguration-v1530-IEs.h"
|
||||
#include "NR_UL-DCCH-Message.h"
|
||||
#include "NR_SDAP-Config.h"
|
||||
#include "NR_RRCReconfigurationComplete.h"
|
||||
#include "NR_RRCReconfigurationComplete-IEs.h"
|
||||
#if defined(NR_Rel16)
|
||||
#include "NR_SCS-SpecificCarrier.h"
|
||||
#include "NR_TDD-UL-DL-ConfigCommon.h"
|
||||
#include "NR_FrequencyInfoUL.h"
|
||||
@@ -574,6 +600,656 @@ void do_SpCellConfig(gNB_RRC_INST *rrc,
|
||||
spconfig->reconfigurationWithSync = CALLOC(1,sizeof(struct NR_ReconfigurationWithSync));
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
uint8_t do_RRCReject(uint8_t Mod_id,
|
||||
uint8_t *const buffer)
|
||||
//------------------------------------------------------------------------------
|
||||
{
|
||||
asn_enc_rval_t enc_rval;;
|
||||
NR_DL_CCCH_Message_t dl_ccch_msg;
|
||||
NR_RRCReject_t *rrcReject;
|
||||
NR_RejectWaitTime_t waitTime = 1;
|
||||
|
||||
memset((void *)&dl_ccch_msg, 0, sizeof(NR_DL_CCCH_Message_t));
|
||||
dl_ccch_msg.message.present = NR_DL_CCCH_MessageType_PR_c1;
|
||||
dl_ccch_msg.message.choice.c1 = CALLOC(1, sizeof(struct NR_DL_CCCH_MessageType__c1));
|
||||
dl_ccch_msg.message.choice.c1->present = NR_RRCReject__criticalExtensions_PR_rrcReject;
|
||||
|
||||
dl_ccch_msg.message.choice.c1->choice.rrcReject = CALLOC(1,sizeof(NR_RRCReject_t));
|
||||
rrcReject = dl_ccch_msg.message.choice.c1->choice.rrcReject;
|
||||
|
||||
rrcReject->criticalExtensions.choice.rrcReject = CALLOC(1, sizeof(struct NR_RRCReject_IEs));
|
||||
rrcReject->criticalExtensions.choice.rrcReject->waitTime = CALLOC(1, sizeof(NR_RejectWaitTime_t));
|
||||
|
||||
rrcReject->criticalExtensions.present = NR_RRCReject__criticalExtensions_PR_rrcReject;
|
||||
rrcReject->criticalExtensions.choice.rrcReject->waitTime = &waitTime;
|
||||
|
||||
if ( LOG_DEBUGFLAG(DEBUG_ASN1) ) {
|
||||
xer_fprint(stdout, &asn_DEF_NR_DL_CCCH_Message, (void *)&dl_ccch_msg);
|
||||
}
|
||||
|
||||
enc_rval = uper_encode_to_buffer(&asn_DEF_NR_DL_CCCH_Message,
|
||||
NULL,
|
||||
(void *)&dl_ccch_msg,
|
||||
buffer,
|
||||
100);
|
||||
|
||||
if(enc_rval.encoded == -1) {
|
||||
LOG_E(NR_RRC, "[gNB AssertFatal]ASN1 message encoding failed (%s, %lu)!\n",
|
||||
enc_rval.failed_type->name, enc_rval.encoded);
|
||||
return -1;
|
||||
}
|
||||
|
||||
LOG_D(NR_RRC,"RRCReject Encoded %zd bits (%zd bytes)\n",
|
||||
enc_rval.encoded,(enc_rval.encoded+7)/8);
|
||||
return((enc_rval.encoded+7)/8);
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
uint8_t do_RRCSetup(const protocol_ctxt_t *const ctxt_pP,
|
||||
rrc_gNB_ue_context_t *const ue_context_pP,
|
||||
int CC_id,
|
||||
uint8_t *const buffer,
|
||||
const uint8_t transaction_id,
|
||||
NR_SRB_ToAddModList_t *SRB_configList)
|
||||
//------------------------------------------------------------------------------
|
||||
{
|
||||
asn_enc_rval_t enc_rval;;
|
||||
NR_DL_CCCH_Message_t dl_ccch_msg;
|
||||
NR_RRCSetup_t *rrcSetup;
|
||||
NR_RRCSetup_IEs_t *ie;
|
||||
NR_SRB_ToAddMod_t *SRB1_config = NULL;
|
||||
NR_PDCP_Config_t *pdcp_Config = NULL;
|
||||
NR_CellGroupConfig_t *cellGroupConfig = NULL;
|
||||
NR_RLC_BearerConfig_t *rlc_BearerConfig = NULL;
|
||||
NR_RLC_Config_t *rlc_Config = NULL;
|
||||
NR_LogicalChannelConfig_t *logicalChannelConfig = NULL;
|
||||
NR_MAC_CellGroupConfig_t *mac_CellGroupConfig = NULL;
|
||||
|
||||
char masterCellGroup_buf[1000];
|
||||
long *logicalChannelGroup = NULL;
|
||||
|
||||
memset((void *)&dl_ccch_msg, 0, sizeof(NR_DL_CCCH_Message_t));
|
||||
dl_ccch_msg.message.present = NR_DL_CCCH_MessageType_PR_c1;
|
||||
dl_ccch_msg.message.choice.c1 = CALLOC(1, sizeof(struct NR_DL_CCCH_MessageType__c1));
|
||||
dl_ccch_msg.message.choice.c1->present = NR_DL_CCCH_MessageType__c1_PR_rrcSetup;
|
||||
dl_ccch_msg.message.choice.c1->choice.rrcSetup = calloc(1, sizeof(NR_RRCSetup_t));
|
||||
|
||||
rrcSetup = dl_ccch_msg.message.choice.c1->choice.rrcSetup;
|
||||
rrcSetup->criticalExtensions.present = NR_RRCSetup__criticalExtensions_PR_rrcSetup;
|
||||
rrcSetup->rrc_TransactionIdentifier = transaction_id;
|
||||
rrcSetup->criticalExtensions.choice.rrcSetup = calloc(1, sizeof(NR_RRCSetup_IEs_t));
|
||||
ie = rrcSetup->criticalExtensions.choice.rrcSetup;
|
||||
|
||||
/****************************** radioBearerConfig ******************************/
|
||||
/* Configure SRB1 */
|
||||
if (SRB_configList) {
|
||||
free(SRB_configList);
|
||||
}
|
||||
|
||||
SRB_configList = calloc(1, sizeof(NR_SRB_ToAddModList_t));
|
||||
// SRB1
|
||||
/* TODO */
|
||||
SRB1_config = calloc(1, sizeof(NR_SRB_ToAddMod_t));
|
||||
SRB1_config->srb_Identity = 1;
|
||||
// pdcp_Config->t_Reordering
|
||||
SRB1_config->pdcp_Config = pdcp_Config;
|
||||
ie->radioBearerConfig.srb_ToAddModList = SRB_configList;
|
||||
ASN_SEQUENCE_ADD(&SRB_configList->list, SRB1_config);
|
||||
|
||||
ie->radioBearerConfig.srb3_ToRelease = NULL;
|
||||
ie->radioBearerConfig.drb_ToAddModList = NULL;
|
||||
ie->radioBearerConfig.drb_ToReleaseList = NULL;
|
||||
ie->radioBearerConfig.securityConfig = NULL;
|
||||
|
||||
/****************************** masterCellGroup ******************************/
|
||||
/* TODO */
|
||||
cellGroupConfig = calloc(1, sizeof(NR_CellGroupConfig_t));
|
||||
cellGroupConfig->cellGroupId = 0;
|
||||
|
||||
/* Rlc Bearer Config */
|
||||
/* TS38.331 9.2.1 Default SRB configurations */
|
||||
cellGroupConfig->rlc_BearerToAddModList = calloc(1, sizeof(*cellGroupConfig->rlc_BearerToAddModList));
|
||||
rlc_BearerConfig = calloc(1, sizeof(NR_RLC_BearerConfig_t));
|
||||
rlc_BearerConfig->logicalChannelIdentity = 1;
|
||||
rlc_BearerConfig->servedRadioBearer = calloc(1, sizeof(*rlc_BearerConfig->servedRadioBearer));
|
||||
rlc_BearerConfig->servedRadioBearer->present = NR_RLC_BearerConfig__servedRadioBearer_PR_srb_Identity;
|
||||
rlc_BearerConfig->servedRadioBearer->choice.srb_Identity = 1;
|
||||
rlc_BearerConfig->reestablishRLC = NULL;
|
||||
rlc_Config = calloc(1, sizeof(NR_RLC_Config_t));
|
||||
rlc_Config->present = NR_RLC_Config_PR_am;
|
||||
rlc_Config->choice.am = calloc(1, sizeof(*rlc_Config->choice.am));
|
||||
rlc_Config->choice.am->dl_AM_RLC.sn_FieldLength = calloc(1, sizeof(NR_SN_FieldLengthAM_t));
|
||||
*(rlc_Config->choice.am->dl_AM_RLC.sn_FieldLength) = NR_SN_FieldLengthAM_size12;
|
||||
rlc_Config->choice.am->dl_AM_RLC.t_Reassembly = NR_T_Reassembly_ms35;
|
||||
rlc_Config->choice.am->dl_AM_RLC.t_StatusProhibit = NR_T_StatusProhibit_ms0;
|
||||
rlc_Config->choice.am->ul_AM_RLC.sn_FieldLength = calloc(1, sizeof(NR_SN_FieldLengthAM_t));
|
||||
*(rlc_Config->choice.am->ul_AM_RLC.sn_FieldLength) = NR_SN_FieldLengthAM_size12;
|
||||
rlc_Config->choice.am->ul_AM_RLC.t_PollRetransmit = NR_T_PollRetransmit_ms45;
|
||||
rlc_Config->choice.am->ul_AM_RLC.pollPDU = NR_PollPDU_infinity;
|
||||
rlc_Config->choice.am->ul_AM_RLC.pollByte = NR_PollByte_infinity;
|
||||
rlc_Config->choice.am->ul_AM_RLC.maxRetxThreshold = NR_UL_AM_RLC__maxRetxThreshold_t8;
|
||||
rlc_BearerConfig->rlc_Config = rlc_Config;
|
||||
logicalChannelConfig = calloc(1, sizeof(NR_LogicalChannelConfig_t));
|
||||
logicalChannelConfig->ul_SpecificParameters = calloc(1, sizeof(*logicalChannelConfig->ul_SpecificParameters));
|
||||
logicalChannelConfig->ul_SpecificParameters->priority = 1;
|
||||
logicalChannelConfig->ul_SpecificParameters->prioritisedBitRate = NR_LogicalChannelConfig__ul_SpecificParameters__prioritisedBitRate_infinity;
|
||||
logicalChannelGroup = CALLOC(1, sizeof(long));
|
||||
*logicalChannelGroup = 0;
|
||||
logicalChannelConfig->ul_SpecificParameters->logicalChannelGroup = logicalChannelGroup;
|
||||
rlc_BearerConfig->mac_LogicalChannelConfig = logicalChannelConfig;
|
||||
ASN_SEQUENCE_ADD(&cellGroupConfig->rlc_BearerToAddModList->list, rlc_BearerConfig);
|
||||
|
||||
cellGroupConfig->rlc_BearerToReleaseList = NULL;
|
||||
cellGroupConfig->sCellToAddModList = NULL;
|
||||
cellGroupConfig->sCellToReleaseList = NULL;
|
||||
|
||||
/* mac CellGroup Config */
|
||||
mac_CellGroupConfig = calloc(1, sizeof(NR_MAC_CellGroupConfig_t));
|
||||
mac_CellGroupConfig->bsr_Config = calloc(1, sizeof(*mac_CellGroupConfig->bsr_Config));
|
||||
mac_CellGroupConfig->bsr_Config->periodicBSR_Timer = NR_BSR_Config__periodicBSR_Timer_sf10;
|
||||
mac_CellGroupConfig->bsr_Config->retxBSR_Timer = NR_BSR_Config__retxBSR_Timer_sf80;
|
||||
mac_CellGroupConfig->phr_Config = calloc(1, sizeof(*mac_CellGroupConfig->phr_Config));
|
||||
mac_CellGroupConfig->phr_Config->present = NR_SetupRelease_PHR_Config_PR_setup;
|
||||
mac_CellGroupConfig->phr_Config->choice.setup = calloc(1, sizeof(*mac_CellGroupConfig->phr_Config->choice.setup));
|
||||
mac_CellGroupConfig->phr_Config->choice.setup->phr_PeriodicTimer = NR_PHR_Config__phr_PeriodicTimer_sf10;
|
||||
mac_CellGroupConfig->phr_Config->choice.setup->phr_ProhibitTimer = NR_PHR_Config__phr_ProhibitTimer_sf10;
|
||||
mac_CellGroupConfig->phr_Config->choice.setup->phr_Tx_PowerFactorChange = NR_PHR_Config__phr_Tx_PowerFactorChange_dB1;
|
||||
cellGroupConfig->mac_CellGroupConfig = mac_CellGroupConfig;
|
||||
|
||||
// cellGroupConfig.physicalCellGroupConfig;
|
||||
|
||||
enc_rval = uper_encode_to_buffer(&asn_DEF_NR_CellGroupConfig,
|
||||
NULL,
|
||||
(void *)cellGroupConfig,
|
||||
masterCellGroup_buf,
|
||||
100);
|
||||
|
||||
if(enc_rval.encoded == -1) {
|
||||
LOG_E(NR_RRC, "ASN1 message CellGroupConfig encoding failed (%s, %lu)!\n",
|
||||
enc_rval.failed_type->name, enc_rval.encoded);
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (OCTET_STRING_fromBuf(&ie->masterCellGroup, masterCellGroup_buf, (enc_rval.encoded+7)/8) == -1) {
|
||||
LOG_E(NR_RRC, "fatal: OCTET_STRING_fromBuf failed\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
if ( LOG_DEBUGFLAG(DEBUG_ASN1) ) {
|
||||
xer_fprint(stdout, &asn_DEF_NR_DL_CCCH_Message, (void *)&dl_ccch_msg);
|
||||
}
|
||||
|
||||
enc_rval = uper_encode_to_buffer(&asn_DEF_NR_DL_CCCH_Message,
|
||||
NULL,
|
||||
(void *)&dl_ccch_msg,
|
||||
buffer,
|
||||
100);
|
||||
|
||||
if(enc_rval.encoded == -1) {
|
||||
LOG_E(NR_RRC, "[gNB AssertFatal]ASN1 message encoding failed (%s, %lu)!\n",
|
||||
enc_rval.failed_type->name, enc_rval.encoded);
|
||||
return -1;
|
||||
}
|
||||
|
||||
LOG_D(NR_RRC,"RRCSetup Encoded %zd bits (%zd bytes)\n",
|
||||
enc_rval.encoded,(enc_rval.encoded+7)/8);
|
||||
return((enc_rval.encoded+7)/8);
|
||||
}
|
||||
|
||||
uint8_t do_NR_SecurityModeCommand(
|
||||
const protocol_ctxt_t *const ctxt_pP,
|
||||
uint8_t *const buffer,
|
||||
const uint8_t Transaction_id,
|
||||
const uint8_t cipheringAlgorithm,
|
||||
NR_IntegrityProtAlgorithm_t *integrityProtAlgorithm
|
||||
)
|
||||
//------------------------------------------------------------------------------
|
||||
{
|
||||
NR_DL_DCCH_Message_t dl_dcch_msg;
|
||||
asn_enc_rval_t enc_rval;
|
||||
memset(&dl_dcch_msg,0,sizeof(NR_DL_DCCH_Message_t));
|
||||
dl_dcch_msg.message.present = NR_DL_DCCH_MessageType_PR_c1;
|
||||
dl_dcch_msg.message.choice.c1=CALLOC(1,sizeof(struct NR_DL_DCCH_MessageType__c1));
|
||||
dl_dcch_msg.message.choice.c1->present = NR_DL_DCCH_MessageType__c1_PR_securityModeCommand;
|
||||
dl_dcch_msg.message.choice.c1->choice.securityModeCommand = CALLOC(1, sizeof(struct NR_SecurityModeCommand));
|
||||
dl_dcch_msg.message.choice.c1->choice.securityModeCommand->rrc_TransactionIdentifier = Transaction_id;
|
||||
dl_dcch_msg.message.choice.c1->choice.securityModeCommand->criticalExtensions.present = NR_SecurityModeCommand__criticalExtensions_PR_securityModeCommand;
|
||||
|
||||
dl_dcch_msg.message.choice.c1->choice.securityModeCommand->criticalExtensions.choice.securityModeCommand =
|
||||
CALLOC(1, sizeof(struct NR_SecurityModeCommand_IEs));
|
||||
// the two following information could be based on the mod_id
|
||||
dl_dcch_msg.message.choice.c1->choice.securityModeCommand->criticalExtensions.choice.securityModeCommand->securityConfigSMC.securityAlgorithmConfig.cipheringAlgorithm
|
||||
= (NR_CipheringAlgorithm_t)cipheringAlgorithm;
|
||||
dl_dcch_msg.message.choice.c1->choice.securityModeCommand->criticalExtensions.choice.securityModeCommand->securityConfigSMC.securityAlgorithmConfig.integrityProtAlgorithm
|
||||
= integrityProtAlgorithm;
|
||||
|
||||
if ( LOG_DEBUGFLAG(DEBUG_ASN1) ) {
|
||||
xer_fprint(stdout, &asn_DEF_NR_DL_DCCH_Message, (void *)&dl_dcch_msg);
|
||||
}
|
||||
|
||||
enc_rval = uper_encode_to_buffer(&asn_DEF_NR_DL_DCCH_Message,
|
||||
NULL,
|
||||
(void *)&dl_dcch_msg,
|
||||
buffer,
|
||||
100);
|
||||
|
||||
if(enc_rval.encoded == -1) {
|
||||
LOG_I(NR_RRC, "[gNB AssertFatal]ASN1 message encoding failed (%s, %lu)!\n",
|
||||
enc_rval.failed_type->name, enc_rval.encoded);
|
||||
return -1;
|
||||
}
|
||||
|
||||
LOG_D(NR_RRC,"[gNB %d] securityModeCommand for UE %x Encoded %zd bits (%zd bytes)\n",
|
||||
ctxt_pP->module_id,
|
||||
ctxt_pP->rnti,
|
||||
enc_rval.encoded,
|
||||
(enc_rval.encoded+7)/8);
|
||||
|
||||
if (enc_rval.encoded==-1) {
|
||||
LOG_E(NR_RRC,"[gNB %d] ASN1 : securityModeCommand encoding failed for UE %x\n",
|
||||
ctxt_pP->module_id,
|
||||
ctxt_pP->rnti);
|
||||
return(-1);
|
||||
}
|
||||
|
||||
// rrc_ue_process_ueCapabilityEnquiry(0,1000,&dl_dcch_msg.message.choice.c1.choice.ueCapabilityEnquiry,0);
|
||||
// exit(-1);
|
||||
return((enc_rval.encoded+7)/8);
|
||||
}
|
||||
|
||||
/*TODO*/
|
||||
//------------------------------------------------------------------------------
|
||||
uint8_t do_NR_SA_UECapabilityEnquiry( const protocol_ctxt_t *const ctxt_pP,
|
||||
uint8_t *const buffer,
|
||||
const uint8_t Transaction_id)
|
||||
//------------------------------------------------------------------------------
|
||||
{
|
||||
NR_DL_DCCH_Message_t dl_dcch_msg;
|
||||
NR_UE_CapabilityRAT_Request_t *ue_capabilityrat_request;
|
||||
|
||||
asn_enc_rval_t enc_rval;
|
||||
memset(&dl_dcch_msg,0,sizeof(NR_DL_DCCH_Message_t));
|
||||
dl_dcch_msg.message.present = NR_DL_DCCH_MessageType_PR_c1;
|
||||
dl_dcch_msg.message.choice.c1 = CALLOC(1,sizeof(struct NR_DL_DCCH_MessageType__c1));
|
||||
dl_dcch_msg.message.choice.c1->present = NR_DL_DCCH_MessageType__c1_PR_ueCapabilityEnquiry;
|
||||
dl_dcch_msg.message.choice.c1->choice.ueCapabilityEnquiry = CALLOC(1,sizeof(struct NR_UECapabilityEnquiry));
|
||||
dl_dcch_msg.message.choice.c1->choice.ueCapabilityEnquiry->rrc_TransactionIdentifier = Transaction_id;
|
||||
dl_dcch_msg.message.choice.c1->choice.ueCapabilityEnquiry->criticalExtensions.present = NR_UECapabilityEnquiry__criticalExtensions_PR_ueCapabilityEnquiry;
|
||||
dl_dcch_msg.message.choice.c1->choice.ueCapabilityEnquiry->criticalExtensions.choice.ueCapabilityEnquiry = CALLOC(1,sizeof(struct NR_UECapabilityEnquiry_IEs));
|
||||
ue_capabilityrat_request = CALLOC(1,sizeof(NR_UE_CapabilityRAT_Request_t));
|
||||
memset(ue_capabilityrat_request,0,sizeof(NR_UE_CapabilityRAT_Request_t));
|
||||
ue_capabilityrat_request->rat_Type = NR_RAT_Type_nr;
|
||||
|
||||
ASN_SEQUENCE_ADD(&dl_dcch_msg.message.choice.c1->choice.ueCapabilityEnquiry->criticalExtensions.choice.ueCapabilityEnquiry->ue_CapabilityRAT_RequestList.list,
|
||||
ue_capabilityrat_request);
|
||||
|
||||
|
||||
if ( LOG_DEBUGFLAG(DEBUG_ASN1) ) {
|
||||
xer_fprint(stdout, &asn_DEF_NR_DL_DCCH_Message, (void *)&dl_dcch_msg);
|
||||
}
|
||||
|
||||
enc_rval = uper_encode_to_buffer(&asn_DEF_NR_DL_DCCH_Message,
|
||||
NULL,
|
||||
(void *)&dl_dcch_msg,
|
||||
buffer,
|
||||
100);
|
||||
|
||||
if(enc_rval.encoded == -1) {
|
||||
LOG_I(NR_RRC, "[gNB AssertFatal]ASN1 message encoding failed (%s, %lu)!\n",
|
||||
enc_rval.failed_type->name, enc_rval.encoded);
|
||||
return -1;
|
||||
}
|
||||
|
||||
LOG_D(NR_RRC,"[gNB %d] NR UECapabilityRequest for UE %x Encoded %zd bits (%zd bytes)\n",
|
||||
ctxt_pP->module_id,
|
||||
ctxt_pP->rnti,
|
||||
enc_rval.encoded,
|
||||
(enc_rval.encoded+7)/8);
|
||||
|
||||
if (enc_rval.encoded==-1) {
|
||||
LOG_E(NR_RRC,"[gNB %d] ASN1 : NR UECapabilityRequest encoding failed for UE %x\n",
|
||||
ctxt_pP->module_id,
|
||||
ctxt_pP->rnti);
|
||||
return(-1);
|
||||
}
|
||||
|
||||
return((enc_rval.encoded+7)/8);
|
||||
}
|
||||
|
||||
|
||||
uint8_t do_NR_RRCConnectionRelease(uint8_t *buffer,
|
||||
uint8_t Transaction_id) {
|
||||
asn_enc_rval_t enc_rval;
|
||||
NR_DL_DCCH_Message_t dl_dcch_msg;
|
||||
NR_RRCRelease_t *rrcConnectionRelease;
|
||||
memset(&dl_dcch_msg,0,sizeof(NR_DL_DCCH_Message_t));
|
||||
dl_dcch_msg.message.present = NR_DL_DCCH_MessageType_PR_c1;
|
||||
dl_dcch_msg.message.choice.c1=CALLOC(1,sizeof(struct NR_DL_DCCH_MessageType__c1));
|
||||
dl_dcch_msg.message.choice.c1->present = NR_DL_DCCH_MessageType__c1_PR_rrcRelease;
|
||||
dl_dcch_msg.message.choice.c1->choice.rrcRelease = CALLOC(1, sizeof(struct NR_RRCRelease));
|
||||
rrcConnectionRelease = dl_dcch_msg.message.choice.c1->choice.rrcRelease;
|
||||
// RRCConnectionRelease
|
||||
rrcConnectionRelease->rrc_TransactionIdentifier = Transaction_id;
|
||||
rrcConnectionRelease->criticalExtensions.present = NR_RRCRelease__criticalExtensions_PR_rrcRelease;
|
||||
rrcConnectionRelease->criticalExtensions.choice.rrcRelease = NULL;
|
||||
enc_rval = uper_encode_to_buffer(&asn_DEF_NR_DL_DCCH_Message,
|
||||
NULL,
|
||||
(void *)&dl_dcch_msg,
|
||||
buffer,
|
||||
RRC_BUF_SIZE);
|
||||
return((enc_rval.encoded+7)/8);
|
||||
}
|
||||
|
||||
uint16_t do_RRCReconfiguration(
|
||||
const protocol_ctxt_t *const ctxt_pP,
|
||||
rrc_gNB_ue_context_t *const ue_context_pP,
|
||||
uint8_t *buffer,
|
||||
uint8_t Transaction_id,
|
||||
gNB_RRC_INST *gnb_rrc_inst
|
||||
)
|
||||
{
|
||||
NR_DL_DCCH_Message_t dl_dcch_msg;
|
||||
asn_enc_rval_t enc_rval;
|
||||
NR_RRCReconfiguration_IEs_t *ie;
|
||||
NR_SRB_ToAddModList_t *SRB_configList = NULL;
|
||||
NR_SRB_ToAddModList_t *SRB_configList2 = NULL;
|
||||
NR_SRB_ToAddMod_t *SRB2_config = NULL;
|
||||
NR_DRB_ToAddModList_t *DRB_configList = NULL;
|
||||
NR_DRB_ToAddModList_t *DRB_configList2 = NULL;
|
||||
NR_DRB_ToAddMod_t *DRB_config = NULL;
|
||||
NR_SDAP_Config_t *sdap_config = NULL;
|
||||
NR_SecurityConfig_t *security_config = NULL;
|
||||
NR_DedicatedNAS_Message_t *dedicatedNAS_Message = NULL;
|
||||
|
||||
memset(&dl_dcch_msg, 0, sizeof(NR_DL_DCCH_Message_t));
|
||||
dl_dcch_msg.message.present = NR_DL_DCCH_MessageType_PR_c1;
|
||||
dl_dcch_msg.message.choice.c1 = CALLOC(1, sizeof(struct NR_DL_DCCH_MessageType__c1));
|
||||
dl_dcch_msg.message.choice.c1->present = NR_DL_DCCH_MessageType__c1_PR_rrcReconfiguration;
|
||||
|
||||
dl_dcch_msg.message.choice.c1->choice.rrcReconfiguration = calloc(1, sizeof(NR_RRCReconfiguration_t));
|
||||
dl_dcch_msg.message.choice.c1->choice.rrcReconfiguration->rrc_TransactionIdentifier = Transaction_id;
|
||||
dl_dcch_msg.message.choice.c1->choice.rrcReconfiguration->criticalExtensions.present = NR_RRCReconfiguration__criticalExtensions_PR_rrcReconfiguration;
|
||||
|
||||
/******************** Radio Bearer Config ********************/
|
||||
/* Configure SRB2 */
|
||||
SRB_configList2 = ue_context_pP->ue_context.SRB_configList2[Transaction_id];
|
||||
SRB_configList = ue_context_pP->ue_context.SRB_configList;
|
||||
SRB_configList = CALLOC(1, sizeof(*SRB_configList));
|
||||
memset(SRB_configList, 0, sizeof(*SRB_configList));
|
||||
|
||||
if (SRB_configList2) {
|
||||
free(SRB_configList2);
|
||||
}
|
||||
|
||||
SRB_configList2 = CALLOC(1, sizeof(*SRB_configList2));
|
||||
memset(SRB_configList2, 0, sizeof(*SRB_configList2));
|
||||
SRB2_config = CALLOC(1, sizeof(*SRB2_config));
|
||||
SRB2_config->srb_Identity = 2;
|
||||
ASN_SEQUENCE_ADD(&SRB_configList->list, SRB2_config);
|
||||
ASN_SEQUENCE_ADD(&SRB_configList2->list, SRB2_config);
|
||||
|
||||
/* Configure DRB */
|
||||
DRB_configList = ue_context_pP->ue_context.DRB_configList;
|
||||
if (DRB_configList) {
|
||||
free(DRB_configList);
|
||||
}
|
||||
|
||||
DRB_configList = CALLOC(1, sizeof(*DRB_configList));
|
||||
memset(DRB_configList, 0, sizeof(*DRB_configList));
|
||||
|
||||
DRB_configList2 = ue_context_pP->ue_context.DRB_configList2[Transaction_id];
|
||||
if (DRB_configList2) {
|
||||
free(DRB_configList2);
|
||||
}
|
||||
DRB_configList2 = CALLOC(1, sizeof(*DRB_configList2));
|
||||
memset(DRB_configList2, 0, sizeof(*DRB_configList2));
|
||||
|
||||
DRB_config = CALLOC(1, sizeof(*DRB_config));
|
||||
DRB_config->drb_Identity = 1;
|
||||
DRB_config->cnAssociation = CALLOC(1, sizeof(*DRB_config->cnAssociation));
|
||||
DRB_config->cnAssociation->present = NR_DRB_ToAddMod__cnAssociation_PR_sdap_Config;
|
||||
// TODO sdap_Config
|
||||
sdap_config = CALLOC(1, sizeof(NR_SDAP_Config_t));
|
||||
memset(sdap_config, 0, sizeof(NR_SDAP_Config_t));
|
||||
DRB_config->cnAssociation->choice.sdap_Config = sdap_config;
|
||||
// TODO pdcp_Config
|
||||
DRB_config->reestablishPDCP = NULL;
|
||||
DRB_config->recoverPDCP = NULL;
|
||||
DRB_config->pdcp_Config = calloc(1, sizeof(*DRB_config->pdcp_Config));
|
||||
DRB_config->pdcp_Config->drb = calloc(1,sizeof(*DRB_config->pdcp_Config->drb));
|
||||
DRB_config->pdcp_Config->drb->discardTimer = calloc(1, sizeof(*DRB_config->pdcp_Config->drb->discardTimer));
|
||||
*DRB_config->pdcp_Config->drb->discardTimer = NR_PDCP_Config__drb__discardTimer_ms30;
|
||||
DRB_config->pdcp_Config->drb->pdcp_SN_SizeUL = calloc(1, sizeof(*DRB_config->pdcp_Config->drb->pdcp_SN_SizeUL));
|
||||
*DRB_config->pdcp_Config->drb->pdcp_SN_SizeUL = NR_PDCP_Config__drb__pdcp_SN_SizeUL_len18bits;
|
||||
DRB_config->pdcp_Config->drb->pdcp_SN_SizeDL = calloc(1, sizeof(*DRB_config->pdcp_Config->drb->pdcp_SN_SizeDL));
|
||||
*DRB_config->pdcp_Config->drb->pdcp_SN_SizeDL = NR_PDCP_Config__drb__pdcp_SN_SizeDL_len18bits;
|
||||
DRB_config->pdcp_Config->drb->headerCompression.present = NR_PDCP_Config__drb__headerCompression_PR_notUsed;
|
||||
DRB_config->pdcp_Config->drb->headerCompression.choice.notUsed = 0;
|
||||
|
||||
DRB_config->pdcp_Config->drb->integrityProtection = NULL;
|
||||
DRB_config->pdcp_Config->drb->statusReportRequired = NULL;
|
||||
DRB_config->pdcp_Config->drb->outOfOrderDelivery = NULL;
|
||||
DRB_config->pdcp_Config->moreThanOneRLC = NULL;
|
||||
|
||||
DRB_config->pdcp_Config->t_Reordering = calloc(1, sizeof(*DRB_config->pdcp_Config->t_Reordering));
|
||||
*DRB_config->pdcp_Config->t_Reordering = NR_PDCP_Config__t_Reordering_ms0;
|
||||
DRB_config->pdcp_Config->ext1 = NULL;
|
||||
|
||||
ASN_SEQUENCE_ADD(&DRB_configList->list, DRB_config);
|
||||
ASN_SEQUENCE_ADD(&DRB_configList2->list, DRB_config);
|
||||
|
||||
/* Configure Security */
|
||||
// security_config = CALLOC(1, sizeof(NR_SecurityConfig_t));
|
||||
// security_config->securityAlgorithmConfig = CALLOC(1, sizeof(*ie->radioBearerConfig->securityConfig->securityAlgorithmConfig));
|
||||
// security_config->securityAlgorithmConfig->cipheringAlgorithm = NR_CipheringAlgorithm_nea0;
|
||||
// security_config->securityAlgorithmConfig->integrityProtAlgorithm = NULL;
|
||||
// security_config->keyToUse = CALLOC(1, sizeof(*ie->radioBearerConfig->securityConfig->keyToUse));
|
||||
// *security_config->keyToUse = NR_SecurityConfig__keyToUse_master;
|
||||
|
||||
ie = calloc(1, sizeof(NR_RRCReconfiguration_IEs_t));
|
||||
ie->radioBearerConfig = calloc(1, sizeof(NR_RadioBearerConfig_t));
|
||||
ie->radioBearerConfig->srb_ToAddModList = SRB_configList;
|
||||
ie->radioBearerConfig->drb_ToAddModList = DRB_configList;
|
||||
ie->radioBearerConfig->securityConfig = security_config;
|
||||
ie->radioBearerConfig->srb3_ToRelease = NULL;
|
||||
ie->radioBearerConfig->drb_ToReleaseList = NULL;
|
||||
|
||||
/******************** Secondary Cell Group ********************/
|
||||
// rrc_gNB_carrier_data_t *carrier = &(gnb_rrc_inst->carrier);
|
||||
// fill_default_secondaryCellGroup( carrier->servingcellconfigcommon,
|
||||
// ue_context_pP->ue_context.secondaryCellGroup,
|
||||
// 1,
|
||||
// 1,
|
||||
// carrier->pdsch_AntennaPorts,
|
||||
// carrier->initial_csi_index[gnb_rrc_inst->Nb_ue]);
|
||||
|
||||
/******************** Meas Config ********************/
|
||||
// measConfig
|
||||
ie->measConfig = NULL;
|
||||
// lateNonCriticalExtension
|
||||
ie->lateNonCriticalExtension = NULL;
|
||||
// nonCriticalExtension
|
||||
ie->nonCriticalExtension = calloc(1, sizeof(NR_RRCReconfiguration_v1530_IEs_t));
|
||||
dedicatedNAS_Message = calloc(1, sizeof(NR_DedicatedNAS_Message_t));
|
||||
dedicatedNAS_Message->buf = ue_context_pP->ue_context.nas_pdu.buffer;
|
||||
dedicatedNAS_Message->size = ue_context_pP->ue_context.nas_pdu.length;
|
||||
ie->nonCriticalExtension->dedicatedNAS_MessageList = calloc(1, sizeof(struct NR_RRCReconfiguration_v1530_IEs__dedicatedNAS_MessageList));
|
||||
ASN_SEQUENCE_ADD(&ie->nonCriticalExtension->dedicatedNAS_MessageList->list, dedicatedNAS_Message);
|
||||
|
||||
dl_dcch_msg.message.choice.c1->choice.rrcReconfiguration->criticalExtensions.choice.rrcReconfiguration = ie;
|
||||
|
||||
if ( LOG_DEBUGFLAG(DEBUG_ASN1) ) {
|
||||
xer_fprint(stdout, &asn_DEF_NR_DL_DCCH_Message, (void *)&dl_dcch_msg);
|
||||
}
|
||||
|
||||
enc_rval = uper_encode_to_buffer(&asn_DEF_NR_DL_DCCH_Message,
|
||||
NULL,
|
||||
(void *)&dl_dcch_msg,
|
||||
buffer,
|
||||
100);
|
||||
|
||||
if(enc_rval.encoded == -1) {
|
||||
LOG_I(NR_RRC, "[gNB AssertFatal]ASN1 message encoding failed (%s, %lu)!\n",
|
||||
enc_rval.failed_type->name, enc_rval.encoded);
|
||||
return -1;
|
||||
}
|
||||
|
||||
LOG_D(NR_RRC,"[gNB %d] RRCReconfiguration for UE %x Encoded %zd bits (%zd bytes)\n",
|
||||
ctxt_pP->module_id,
|
||||
ctxt_pP->rnti,
|
||||
enc_rval.encoded,
|
||||
(enc_rval.encoded+7)/8);
|
||||
|
||||
if (enc_rval.encoded == -1) {
|
||||
LOG_E(NR_RRC,"[gNB %d] ASN1 : RRCReconfiguration encoding failed for UE %x\n",
|
||||
ctxt_pP->module_id,
|
||||
ctxt_pP->rnti);
|
||||
return(-1);
|
||||
}
|
||||
|
||||
return((enc_rval.encoded+7)/8);
|
||||
}
|
||||
|
||||
|
||||
uint8_t do_RRCSetupRequest(uint8_t Mod_id, uint8_t *buffer,uint8_t *rv) {
|
||||
asn_enc_rval_t enc_rval;
|
||||
uint8_t buf[5],buf2=0;
|
||||
NR_UL_CCCH_Message_t ul_ccch_msg;
|
||||
NR_RRCSetupRequest_t *rrcSetupRequest;
|
||||
memset((void *)&ul_ccch_msg,0,sizeof(NR_UL_CCCH_Message_t));
|
||||
ul_ccch_msg.message.present = NR_UL_CCCH_MessageType_PR_c1;
|
||||
ul_ccch_msg.message.choice.c1 = CALLOC(1, sizeof(struct NR_UL_CCCH_MessageType__c1));
|
||||
ul_ccch_msg.message.choice.c1->present = NR_UL_CCCH_MessageType__c1_PR_rrcSetupRequest;
|
||||
ul_ccch_msg.message.choice.c1->choice.rrcSetupRequest = CALLOC(1, sizeof(NR_RRCSetupRequest_t));
|
||||
rrcSetupRequest = ul_ccch_msg.message.choice.c1->choice.rrcSetupRequest;
|
||||
|
||||
|
||||
if (1) {
|
||||
rrcSetupRequest->rrcSetupRequest.ue_Identity.present = NR_InitialUE_Identity_PR_randomValue;
|
||||
rrcSetupRequest->rrcSetupRequest.ue_Identity.choice.randomValue.size = 5;
|
||||
rrcSetupRequest->rrcSetupRequest.ue_Identity.choice.randomValue.bits_unused = 1;
|
||||
rrcSetupRequest->rrcSetupRequest.ue_Identity.choice.randomValue.buf = buf;
|
||||
rrcSetupRequest->rrcSetupRequest.ue_Identity.choice.randomValue.buf[0] = rv[0];
|
||||
rrcSetupRequest->rrcSetupRequest.ue_Identity.choice.randomValue.buf[1] = rv[1];
|
||||
rrcSetupRequest->rrcSetupRequest.ue_Identity.choice.randomValue.buf[2] = rv[2];
|
||||
rrcSetupRequest->rrcSetupRequest.ue_Identity.choice.randomValue.buf[3] = rv[3];
|
||||
rrcSetupRequest->rrcSetupRequest.ue_Identity.choice.randomValue.buf[4] = rv[4]&0xfe;
|
||||
} else {
|
||||
rrcSetupRequest->rrcSetupRequest.ue_Identity.present = NR_InitialUE_Identity_PR_ng_5G_S_TMSI_Part1;
|
||||
rrcSetupRequest->rrcSetupRequest.ue_Identity.choice.ng_5G_S_TMSI_Part1.size = 1;
|
||||
rrcSetupRequest->rrcSetupRequest.ue_Identity.choice.ng_5G_S_TMSI_Part1.bits_unused = 0;
|
||||
rrcSetupRequest->rrcSetupRequest.ue_Identity.choice.ng_5G_S_TMSI_Part1.buf = buf;
|
||||
rrcSetupRequest->rrcSetupRequest.ue_Identity.choice.ng_5G_S_TMSI_Part1.buf[0] = 0x12;
|
||||
}
|
||||
|
||||
rrcSetupRequest->rrcSetupRequest.establishmentCause = NR_EstablishmentCause_mo_Signalling; //EstablishmentCause_mo_Data;
|
||||
rrcSetupRequest->rrcSetupRequest.spare.buf = &buf2;
|
||||
rrcSetupRequest->rrcSetupRequest.spare.size=1;
|
||||
rrcSetupRequest->rrcSetupRequest.spare.bits_unused = 7;
|
||||
|
||||
if ( LOG_DEBUGFLAG(DEBUG_ASN1) ) {
|
||||
xer_fprint(stdout, &asn_DEF_NR_UL_CCCH_Message, (void *)&ul_ccch_msg);
|
||||
}
|
||||
|
||||
enc_rval = uper_encode_to_buffer(&asn_DEF_NR_UL_CCCH_Message,
|
||||
NULL,
|
||||
(void *)&ul_ccch_msg,
|
||||
buffer,
|
||||
100);
|
||||
AssertFatal (enc_rval.encoded > 0, "ASN1 message encoding failed (%s, %lu)!\n", enc_rval.failed_type->name, enc_rval.encoded);
|
||||
LOG_D(NR_RRC,"[UE] RRCSetupRequest Encoded %zd bits (%zd bytes)\n", enc_rval.encoded, (enc_rval.encoded+7)/8);
|
||||
return((enc_rval.encoded+7)/8);
|
||||
}
|
||||
//------------------------------------------------------------------------------
|
||||
uint8_t
|
||||
do_NR_RRCReconfigurationComplete(
|
||||
const protocol_ctxt_t *const ctxt_pP,
|
||||
uint8_t *buffer,
|
||||
const uint8_t Transaction_id
|
||||
)
|
||||
//------------------------------------------------------------------------------
|
||||
{
|
||||
asn_enc_rval_t enc_rval;
|
||||
NR_UL_DCCH_Message_t ul_dcch_msg;
|
||||
NR_RRCReconfigurationComplete_t *rrcReconfigurationComplete;
|
||||
memset((void *)&ul_dcch_msg,0,sizeof(NR_UL_DCCH_Message_t));
|
||||
ul_dcch_msg.message.present = NR_UL_DCCH_MessageType_PR_c1;
|
||||
ul_dcch_msg.message.choice.c1 = CALLOC(1, sizeof(struct NR_UL_DCCH_MessageType__c1));
|
||||
ul_dcch_msg.message.choice.c1->present = NR_UL_DCCH_MessageType__c1_PR_rrcReconfigurationComplete;
|
||||
ul_dcch_msg.message.choice.c1->choice.rrcReconfigurationComplete = CALLOC(1, sizeof(NR_RRCReconfigurationComplete_t));
|
||||
rrcReconfigurationComplete = ul_dcch_msg.message.choice.c1->choice.rrcReconfigurationComplete;
|
||||
rrcReconfigurationComplete->rrc_TransactionIdentifier = Transaction_id;
|
||||
rrcReconfigurationComplete->criticalExtensions.choice.rrcReconfigurationComplete = CALLOC(1, sizeof(NR_RRCReconfigurationComplete_IEs_t));
|
||||
rrcReconfigurationComplete->criticalExtensions.present =
|
||||
NR_RRCReconfigurationComplete__criticalExtensions_PR_rrcReconfigurationComplete;
|
||||
rrcReconfigurationComplete->criticalExtensions.choice.rrcReconfigurationComplete->nonCriticalExtension = NULL;
|
||||
rrcReconfigurationComplete->criticalExtensions.choice.rrcReconfigurationComplete->lateNonCriticalExtension = NULL;
|
||||
if ( LOG_DEBUGFLAG(DEBUG_ASN1) ) {
|
||||
xer_fprint(stdout, &asn_DEF_NR_UL_DCCH_Message, (void *)&ul_dcch_msg);
|
||||
}
|
||||
|
||||
enc_rval = uper_encode_to_buffer(&asn_DEF_NR_UL_DCCH_Message,
|
||||
NULL,
|
||||
(void *)&ul_dcch_msg,
|
||||
buffer,
|
||||
100);
|
||||
AssertFatal (enc_rval.encoded > 0, "ASN1 message encoding failed (%s, %lu)!\n",
|
||||
enc_rval.failed_type->name, enc_rval.encoded);
|
||||
LOG_I(NR_RRC,"rrcReconfigurationComplete Encoded %zd bits (%zd bytes)\n",enc_rval.encoded,(enc_rval.encoded+7)/8);
|
||||
return((enc_rval.encoded+7)/8);
|
||||
}
|
||||
|
||||
uint8_t do_RRCSetupComplete(uint8_t Mod_id, uint8_t *buffer, const uint8_t Transaction_id, uint8_t sel_plmn_id, const int dedicatedInfoNASLength, const char *dedicatedInfoNAS){
|
||||
asn_enc_rval_t enc_rval;
|
||||
|
||||
NR_UL_DCCH_Message_t ul_dcch_msg;
|
||||
NR_RRCSetupComplete_t *RrcSetupComplete;
|
||||
memset((void *)&ul_dcch_msg,0,sizeof(NR_UL_DCCH_Message_t));
|
||||
|
||||
uint8_t buf[6];
|
||||
|
||||
ul_dcch_msg.message.present = NR_UL_DCCH_MessageType_PR_c1;
|
||||
ul_dcch_msg.message.choice.c1 = CALLOC(1,sizeof(struct NR_UL_DCCH_MessageType__c1));
|
||||
ul_dcch_msg.message.choice.c1->present = NR_UL_DCCH_MessageType__c1_PR_rrcSetupComplete;
|
||||
ul_dcch_msg.message.choice.c1->choice.rrcSetupComplete = CALLOC(1, sizeof(NR_RRCSetupComplete_t));
|
||||
RrcSetupComplete = ul_dcch_msg.message.choice.c1->choice.rrcSetupComplete;
|
||||
RrcSetupComplete->rrc_TransactionIdentifier = Transaction_id;
|
||||
RrcSetupComplete->criticalExtensions.present = NR_RRCSetupComplete__criticalExtensions_PR_rrcSetupComplete;
|
||||
RrcSetupComplete->criticalExtensions.choice.rrcSetupComplete = CALLOC(1, sizeof(NR_RRCSetupComplete_IEs_t));
|
||||
// RrcSetupComplete->criticalExtensions.choice.rrcSetupComplete->nonCriticalExtension = CALLOC(1,
|
||||
// sizeof(*RrcSetupComplete->criticalExtensions.choice.rrcSetupComplete->nonCriticalExtension));
|
||||
RrcSetupComplete->criticalExtensions.choice.rrcSetupComplete->selectedPLMN_Identity = sel_plmn_id;
|
||||
RrcSetupComplete->criticalExtensions.choice.rrcSetupComplete->registeredAMF = NULL;
|
||||
|
||||
RrcSetupComplete->criticalExtensions.choice.rrcSetupComplete->ng_5G_S_TMSI_Value = CALLOC(1, sizeof(struct NR_RRCSetupComplete_IEs__ng_5G_S_TMSI_Value));
|
||||
RrcSetupComplete->criticalExtensions.choice.rrcSetupComplete->ng_5G_S_TMSI_Value->present = NR_RRCSetupComplete_IEs__ng_5G_S_TMSI_Value_PR_ng_5G_S_TMSI;
|
||||
RrcSetupComplete->criticalExtensions.choice.rrcSetupComplete->ng_5G_S_TMSI_Value->choice.ng_5G_S_TMSI.size = 6;
|
||||
RrcSetupComplete->criticalExtensions.choice.rrcSetupComplete->ng_5G_S_TMSI_Value->choice.ng_5G_S_TMSI.buf = buf;
|
||||
RrcSetupComplete->criticalExtensions.choice.rrcSetupComplete->ng_5G_S_TMSI_Value->choice.ng_5G_S_TMSI.buf[0] = 0x12;
|
||||
RrcSetupComplete->criticalExtensions.choice.rrcSetupComplete->ng_5G_S_TMSI_Value->choice.ng_5G_S_TMSI.buf[1] = 0x34;
|
||||
RrcSetupComplete->criticalExtensions.choice.rrcSetupComplete->ng_5G_S_TMSI_Value->choice.ng_5G_S_TMSI.buf[2] = 0x56;
|
||||
RrcSetupComplete->criticalExtensions.choice.rrcSetupComplete->ng_5G_S_TMSI_Value->choice.ng_5G_S_TMSI.buf[3] = 0x78;
|
||||
RrcSetupComplete->criticalExtensions.choice.rrcSetupComplete->ng_5G_S_TMSI_Value->choice.ng_5G_S_TMSI.buf[4] = 0x9A;
|
||||
RrcSetupComplete->criticalExtensions.choice.rrcSetupComplete->ng_5G_S_TMSI_Value->choice.ng_5G_S_TMSI.buf[5] = 0xBC;
|
||||
|
||||
memset(&RrcSetupComplete->criticalExtensions.choice.rrcSetupComplete->dedicatedNAS_Message,0,sizeof(OCTET_STRING_t));
|
||||
OCTET_STRING_fromBuf(&RrcSetupComplete->criticalExtensions.choice.rrcSetupComplete->dedicatedNAS_Message,dedicatedInfoNAS,dedicatedInfoNASLength);
|
||||
if ( LOG_DEBUGFLAG(DEBUG_ASN1) ) {
|
||||
xer_fprint(stdout, &asn_DEF_NR_UL_DCCH_Message, (void *)&ul_dcch_msg);
|
||||
}
|
||||
|
||||
enc_rval = uper_encode_to_buffer(&asn_DEF_NR_UL_DCCH_Message,
|
||||
NULL,
|
||||
(void *)&ul_dcch_msg,
|
||||
buffer,
|
||||
100);
|
||||
AssertFatal(enc_rval.encoded > 0,"ASN1 message encoding failed (%s, %lu)!\n",
|
||||
enc_rval.failed_type->name,enc_rval.encoded);
|
||||
LOG_D(NR_RRC,"RRCSetupComplete Encoded %zd bits (%zd bytes)\n",enc_rval.encoded,(enc_rval.encoded+7)/8);
|
||||
|
||||
return((enc_rval.encoded+7)/8);
|
||||
}
|
||||
|
||||
int do_DLInformationTransfer_NR (void * p) {
|
||||
return 0;
|
||||
|
||||
@@ -82,3 +82,47 @@ void do_PHYSICALCELLGROUP(uint8_t Mod_id,
|
||||
|
||||
void do_SpCellConfig(gNB_RRC_INST *rrc,
|
||||
struct NR_SpCellConfig *spconfig);
|
||||
|
||||
uint8_t do_RRCReject(uint8_t Mod_id,
|
||||
uint8_t *const buffer);
|
||||
|
||||
uint8_t do_RRCSetup(const protocol_ctxt_t *const ctxt_pP,
|
||||
rrc_gNB_ue_context_t *const ue_context_pP,
|
||||
int CC_id,
|
||||
uint8_t *const buffer,
|
||||
const uint8_t transaction_id,
|
||||
NR_SRB_ToAddModList_t *SRB_configList);
|
||||
uint8_t do_NR_SecurityModeCommand(
|
||||
const protocol_ctxt_t *const ctxt_pP,
|
||||
uint8_t *const buffer,
|
||||
const uint8_t Transaction_id,
|
||||
const uint8_t cipheringAlgorithm,
|
||||
NR_IntegrityProtAlgorithm_t *integrityProtAlgorithm);
|
||||
|
||||
uint8_t do_NR_SA_UECapabilityEnquiry( const protocol_ctxt_t *const ctxt_pP,
|
||||
uint8_t *const buffer,
|
||||
const uint8_t Transaction_id);
|
||||
|
||||
uint8_t do_NR_RRCConnectionRelease(uint8_t *buffer,
|
||||
uint8_t Transaction_id);
|
||||
uint16_t do_RRCReconfiguration(
|
||||
const protocol_ctxt_t *const ctxt_pP,
|
||||
rrc_gNB_ue_context_t *const ue_context_pP,
|
||||
uint8_t *buffer,
|
||||
uint8_t Transaction_id,
|
||||
gNB_RRC_INST *gnb_rrc_inst);
|
||||
|
||||
uint8_t do_RRCSetupComplete(uint8_t Mod_id,
|
||||
uint8_t *buffer,
|
||||
const uint8_t Transaction_id,
|
||||
uint8_t sel_plmn_id,
|
||||
const int dedicatedInfoNASLength,
|
||||
const char *dedicatedInfoNAS);
|
||||
|
||||
uint8_t do_RRCSetupRequest(uint8_t Mod_id, uint8_t *buffer,uint8_t *rv);
|
||||
|
||||
uint8_t do_NR_RRCReconfigurationComplete(
|
||||
const protocol_ctxt_t *const ctxt_pP,
|
||||
uint8_t *buffer,
|
||||
const uint8_t Transaction_id
|
||||
);
|
||||
|
||||
12881
openair2/RRC/NR/MESSAGES/asn1c/ASN1_files/nr-rrc-16.1.0.asn1
Normal file
12881
openair2/RRC/NR/MESSAGES/asn1c/ASN1_files/nr-rrc-16.1.0.asn1
Normal file
File diff suppressed because it is too large
Load Diff
@@ -54,6 +54,7 @@
|
||||
#include "NR_BCCH-BCH-Message.h"
|
||||
#include "NR_PLMN-IdentityInfo.h"
|
||||
#include "NR_MCC-MNC-Digit.h"
|
||||
#include "NR_NG-5G-S-TMSI.h"
|
||||
//#include "MCCH-Message.h"
|
||||
//#include "MBSFNAreaConfiguration-r9.h"
|
||||
//#include "SCellToAddMod-r10.h"
|
||||
@@ -89,10 +90,10 @@ typedef struct nr_uid_linear_allocator_s {
|
||||
|
||||
|
||||
#define PROTOCOL_NR_RRC_CTXT_UE_FMT PROTOCOL_CTXT_FMT
|
||||
#define PROTOCOL_NR_RRC_CTXT_UE_ARGS(CTXT_Pp) PROTOCOL_CTXT_ARGS(CTXT_Pp)
|
||||
#define PROTOCOL_NR_RRC_CTXT_UE_ARGS(CTXT_Pp) PROTOCOL_NR_CTXT_ARGS(CTXT_Pp)
|
||||
|
||||
#define PROTOCOL_NR_RRC_CTXT_FMT PROTOCOL_CTXT_FMT
|
||||
#define PROTOCOL_NR_RRC_CTXT_ARGS(CTXT_Pp) PROTOCOL_CTXT_ARGS(CTXT_Pp)
|
||||
#define PROTOCOL_NR_RRC_CTXT_ARGS(CTXT_Pp) PROTOCOL_NR_CTXT_ARGS(CTXT_Pp)
|
||||
|
||||
|
||||
#define NR_UE_MODULE_INVALID ((module_id_t) ~0) // FIXME attention! depends on type uint8_t!!!
|
||||
@@ -149,7 +150,7 @@ typedef struct UE_RRC_INFO_NR_s {
|
||||
uint32_t SIStatus;
|
||||
uint32_t SIcnt;
|
||||
uint8_t MCCHStatus[8]; // MAX_MBSFN_AREA
|
||||
uint8_t SIwindowsize; //!< Corresponds to the SIB1 si-WindowLength parameter. The unit is ms. Possible values are (final): 1,2,5,10,15,20,40
|
||||
uint16_t SIwindowsize; //!< Corresponds to the SIB1 si-WindowLength parameter. The unit is ms. Possible values are (final): 1,2,5,10,15,20,40
|
||||
uint8_t handoverTarget;
|
||||
//HO_STATE_t ho_state;
|
||||
uint16_t
|
||||
@@ -168,8 +169,9 @@ typedef struct UE_RRC_INFO_NR_s {
|
||||
|
||||
typedef struct UE_S_TMSI_NR_s {
|
||||
boolean_t presence;
|
||||
mme_code_t mme_code;
|
||||
m_tmsi_t m_tmsi;
|
||||
uint16_t amf_set_id;
|
||||
uint8_t amf_pointer;
|
||||
uint32_t fiveg_tmsi;
|
||||
} __attribute__ ((__packed__)) NR_UE_S_TMSI;
|
||||
|
||||
|
||||
@@ -246,6 +248,14 @@ typedef struct SRB_INFO_TABLE_ENTRY_NR_s {
|
||||
uint32_t Next_check_frame;
|
||||
} NR_SRB_INFO_TABLE_ENTRY;
|
||||
|
||||
typedef struct nr_rrc_guami_s {
|
||||
uint16_t mcc;
|
||||
uint16_t mnc;
|
||||
uint8_t mnc_len;
|
||||
uint8_t amf_region_id;
|
||||
uint16_t amf_set_id;
|
||||
uint8_t amf_pointer;
|
||||
} nr_rrc_guami_t;
|
||||
|
||||
typedef struct gNB_RRC_UE_s {
|
||||
uint8_t primaryCC_id;
|
||||
@@ -267,7 +277,9 @@ typedef struct gNB_RRC_UE_s {
|
||||
|
||||
|
||||
NR_UE_NR_Capability_t* UE_Capability_nr;
|
||||
int UE_Capability_size;
|
||||
NR_UE_MRDC_Capability_t* UE_Capability_MRDC;
|
||||
int UE_MRDC_Capability_size;
|
||||
|
||||
NR_CellGroupConfig_t *secondaryCellGroup;
|
||||
NR_RRCReconfiguration_t *reconfig;
|
||||
@@ -275,13 +287,12 @@ typedef struct gNB_RRC_UE_s {
|
||||
|
||||
ImsiMobileIdentity_t imsi;
|
||||
|
||||
#if defined(ENABLE_SECURITY)
|
||||
/* KeNB as derived from KASME received from EPC */
|
||||
uint8_t kenb[32];
|
||||
int8_t kenb_ncc;
|
||||
/* KgNB as derived from KASME received from EPC */
|
||||
uint8_t kgnb[32];
|
||||
int8_t kgnb_ncc;
|
||||
uint8_t nh[32];
|
||||
int8_t nh_ncc;
|
||||
#endif
|
||||
|
||||
/* Used integrity/ciphering algorithms */
|
||||
NR_CipheringAlgorithm_t ciphering_algorithm;
|
||||
e_NR_IntegrityProtAlgorithm integrity_algorithm;
|
||||
@@ -290,8 +301,10 @@ typedef struct gNB_RRC_UE_s {
|
||||
rnti_t rnti;
|
||||
uint64_t random_ue_identity;
|
||||
|
||||
/* Information from UE RRC ConnectionRequest */
|
||||
UE_S_TMSI Initialue_identity_s_TMSI;
|
||||
/* Information from UE RRC Setup Request */
|
||||
NR_UE_S_TMSI Initialue_identity_5g_s_TMSI;
|
||||
uint64_t ng_5G_S_TMSI_Part1;
|
||||
uint16_t ng_5G_S_TMSI_Part2;
|
||||
NR_EstablishmentCause_t establishment_cause;
|
||||
|
||||
/* Information from UE RRC ConnectionReestablishmentRequest */
|
||||
@@ -302,8 +315,11 @@ typedef struct gNB_RRC_UE_s {
|
||||
|
||||
/* Information from S1AP initial_context_setup_req */
|
||||
uint32_t gNB_ue_s1ap_id :24;
|
||||
uint32_t gNB_ue_ngap_id;
|
||||
uint64_t amf_ue_ngap_id:40;
|
||||
nr_rrc_guami_t ue_guami;
|
||||
|
||||
security_capabilities_t security_capabilities;
|
||||
ngap_security_capabilities_t security_capabilities;
|
||||
|
||||
/* Total number of e_rab already setup in the list */
|
||||
uint8_t setup_e_rabs;
|
||||
@@ -343,6 +359,10 @@ typedef struct gNB_RRC_UE_s {
|
||||
struct NR_MAC_CellGroupConfig *mac_CellGroupConfig;
|
||||
struct NR_PhysicalCellGroupConfig *physicalCellGroupConfig;
|
||||
|
||||
/* Nas Pdu */
|
||||
uint8_t nas_pdu_flag;
|
||||
ngap_nas_pdu_t nas_pdu;
|
||||
|
||||
} gNB_RRC_UE_t;
|
||||
|
||||
typedef uid_t ue_uid_t;
|
||||
|
||||
@@ -93,6 +93,23 @@ int generate_CG_Config(gNB_RRC_INST *rrc,
|
||||
|
||||
int parse_CG_ConfigInfo(gNB_RRC_INST *rrc, NR_CG_ConfigInfo_t *CG_ConfigInfo, x2ap_ENDC_sgnb_addition_req_t *m);
|
||||
|
||||
void
|
||||
rrc_gNB_generate_SecurityModeCommand(
|
||||
const protocol_ctxt_t *const ctxt_pP,
|
||||
rrc_gNB_ue_context_t *const ue_context_pP
|
||||
);
|
||||
|
||||
uint8_t
|
||||
rrc_gNB_get_next_transaction_identifier(
|
||||
module_id_t gnb_mod_idP
|
||||
);
|
||||
|
||||
void
|
||||
rrc_gNB_generate_UECapabilityEnquiry(
|
||||
const protocol_ctxt_t *const ctxt_pP,
|
||||
rrc_gNB_ue_context_t *const ue_context_pP
|
||||
);
|
||||
|
||||
void nr_rrc_rx_tx(void);
|
||||
|
||||
/**\brief RRC eNB task.
|
||||
@@ -101,3 +118,19 @@ void *rrc_gnb_task(void *args_p);
|
||||
|
||||
/* Trigger RRC periodic processing. To be called once per ms. */
|
||||
void nr_rrc_trigger(protocol_ctxt_t *ctxt, int CC_id, int frame, int subframe);
|
||||
|
||||
uint8_t
|
||||
nr_rrc_data_req(
|
||||
const protocol_ctxt_t *const ctxt_pP,
|
||||
const rb_id_t rb_idP,
|
||||
const mui_t muiP,
|
||||
const confirm_t confirmP,
|
||||
const sdu_size_t sdu_size,
|
||||
uint8_t *const buffer_pP,
|
||||
const pdcp_transmission_mode_t modeP
|
||||
);
|
||||
|
||||
int
|
||||
nr_rrc_mac_remove_ue(module_id_t mod_idP,
|
||||
rnti_t rntiP);
|
||||
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
483
openair2/RRC/NR/rrc_gNB_NGAP.c
Normal file
483
openair2/RRC/NR/rrc_gNB_NGAP.c
Normal file
@@ -0,0 +1,483 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file rrc_gNB_NGAP.h
|
||||
* \brief rrc NGAP procedures for gNB
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \date 2020
|
||||
* \version 0.1
|
||||
* \email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com
|
||||
* (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
*/
|
||||
|
||||
#include "rrc_gNB_NGAP.h"
|
||||
#include "RRC/L2_INTERFACE/openair_rrc_L2_interface.h"
|
||||
#include "rrc_eNB_S1AP.h"
|
||||
#include "gnb_config.h"
|
||||
#include "common/ran_context.h"
|
||||
#include "gtpv1u.h"
|
||||
|
||||
#include "asn1_conversions.h"
|
||||
#include "intertask_interface.h"
|
||||
#include "pdcp.h"
|
||||
#include "pdcp_primitives.h"
|
||||
|
||||
#include "msc.h"
|
||||
|
||||
#include "gtpv1u_eNB_task.h"
|
||||
#include "RRC/LTE/rrc_eNB_GTPV1U.h"
|
||||
|
||||
#include "S1AP_NAS-PDU.h"
|
||||
#include "executables/softmodem-common.h"
|
||||
#include "UTIL/OSA/osa_defs.h"
|
||||
|
||||
extern RAN_CONTEXT_t RC;
|
||||
|
||||
/* Value to indicate an invalid UE initial id */
|
||||
static const uint16_t UE_INITIAL_ID_INVALID = 0;
|
||||
|
||||
/*! \fn uint16_t get_next_ue_initial_id(uint8_t mod_id)
|
||||
*\brief provide an UE initial ID for NGAP initial communication.
|
||||
*\param mod_id Instance ID of gNB.
|
||||
*\return the UE initial ID.
|
||||
*/
|
||||
//------------------------------------------------------------------------------
|
||||
static uint16_t
|
||||
get_next_ue_initial_id(
|
||||
const module_id_t mod_id
|
||||
)
|
||||
//------------------------------------------------------------------------------
|
||||
{
|
||||
static uint16_t ue_initial_id[NUMBER_OF_gNB_MAX];
|
||||
ue_initial_id[mod_id]++;
|
||||
|
||||
/* Never use UE_INITIAL_ID_INVALID this is the invalid id! */
|
||||
if (ue_initial_id[mod_id] == UE_INITIAL_ID_INVALID) {
|
||||
ue_initial_id[mod_id]++;
|
||||
}
|
||||
|
||||
return ue_initial_id[mod_id];
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/*
|
||||
* Get the UE NG struct containing hashtables NG_id/UE_id.
|
||||
* Is also used to set the NG_id of the UE, depending on inputs.
|
||||
*/
|
||||
struct rrc_ue_ngap_ids_s *
|
||||
rrc_gNB_NGAP_get_ue_ids(
|
||||
gNB_RRC_INST *const rrc_instance_pP,
|
||||
const uint16_t ue_initial_id,
|
||||
const uint32_t gNB_ue_ngap_idP
|
||||
)
|
||||
//------------------------------------------------------------------------------
|
||||
{
|
||||
rrc_ue_ngap_ids_t *result = NULL;
|
||||
|
||||
/* TODO */
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
static struct rrc_gNB_ue_context_s *
|
||||
rrc_gNB_get_ue_context_from_ngap_ids(
|
||||
const instance_t instanceP,
|
||||
const uint16_t ue_initial_idP,
|
||||
const uint32_t gNB_ue_ngap_idP
|
||||
)
|
||||
//------------------------------------------------------------------------------
|
||||
{
|
||||
rrc_ue_ngap_ids_t *temp = NULL;
|
||||
temp = rrc_gNB_NGAP_get_ue_ids(RC.nrrrc[GNB_INSTANCE_TO_MODULE_ID(instanceP)], ue_initial_idP, gNB_ue_ngap_idP);
|
||||
|
||||
if (temp != NULL) {
|
||||
return rrc_gNB_get_ue_context(RC.nrrrc[GNB_INSTANCE_TO_MODULE_ID(instanceP)], temp->ue_rnti);
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
void
|
||||
nr_rrc_pdcp_config_security(
|
||||
const protocol_ctxt_t *const ctxt_pP,
|
||||
rrc_gNB_ue_context_t *const ue_context_pP,
|
||||
const uint8_t send_security_mode_command
|
||||
)
|
||||
//------------------------------------------------------------------------------
|
||||
{
|
||||
NR_SRB_ToAddModList_t *SRB_configList = ue_context_pP->ue_context.SRB_configList;
|
||||
uint8_t *kRRCenc = NULL;
|
||||
uint8_t *kRRCint = NULL;
|
||||
uint8_t *kUPenc = NULL;
|
||||
pdcp_t *pdcp_p = NULL;
|
||||
static int print_keys= 1;
|
||||
hashtable_rc_t h_rc;
|
||||
hash_key_t key;
|
||||
|
||||
#ifndef PHYSIM
|
||||
/* Derive the keys from kgnb */
|
||||
if (SRB_configList != NULL) {
|
||||
derive_key_up_enc(ue_context_pP->ue_context.ciphering_algorithm,
|
||||
ue_context_pP->ue_context.kgnb,
|
||||
&kUPenc);
|
||||
}
|
||||
|
||||
derive_key_rrc_enc(ue_context_pP->ue_context.ciphering_algorithm,
|
||||
ue_context_pP->ue_context.kgnb,
|
||||
&kRRCenc);
|
||||
derive_key_rrc_int(ue_context_pP->ue_context.integrity_algorithm,
|
||||
ue_context_pP->ue_context.kgnb,
|
||||
&kRRCint);
|
||||
#endif
|
||||
if (!IS_SOFTMODEM_IQPLAYER) {
|
||||
SET_LOG_DUMP(DEBUG_SECURITY) ;
|
||||
}
|
||||
|
||||
|
||||
if ( LOG_DUMPFLAG( DEBUG_SECURITY ) ) {
|
||||
if (print_keys == 1 ) {
|
||||
print_keys =0;
|
||||
LOG_DUMPMSG(NR_RRC, DEBUG_SECURITY, ue_context_pP->ue_context.kgnb, 32,"\nKgNB:" );
|
||||
LOG_DUMPMSG(NR_RRC, DEBUG_SECURITY, kRRCenc, 32,"\nKRRCenc:" );
|
||||
LOG_DUMPMSG(NR_RRC, DEBUG_SECURITY, kRRCint, 32,"\nKRRCint:" );
|
||||
}
|
||||
}
|
||||
|
||||
key = PDCP_COLL_KEY_VALUE(ctxt_pP->module_id, ctxt_pP->rnti, ctxt_pP->enb_flag, DCCH, SRB_FLAG_YES);
|
||||
h_rc = hashtable_get(pdcp_coll_p, key, (void **)&pdcp_p);
|
||||
|
||||
if (h_rc == HASH_TABLE_OK) {
|
||||
pdcp_config_set_security(
|
||||
ctxt_pP,
|
||||
pdcp_p,
|
||||
DCCH,
|
||||
DCCH+2,
|
||||
(send_security_mode_command == TRUE) ?
|
||||
0 | (ue_context_pP->ue_context.integrity_algorithm << 4) :
|
||||
(ue_context_pP->ue_context.ciphering_algorithm ) |
|
||||
(ue_context_pP->ue_context.integrity_algorithm << 4),
|
||||
kRRCenc,
|
||||
kRRCint,
|
||||
kUPenc);
|
||||
} else {
|
||||
LOG_E(NR_RRC,
|
||||
PROTOCOL_NR_RRC_CTXT_UE_FMT"Could not get PDCP instance for SRB DCCH %u\n",
|
||||
PROTOCOL_NR_RRC_CTXT_UE_ARGS(ctxt_pP),
|
||||
DCCH);
|
||||
}
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
/*
|
||||
* Initial UE NAS message on S1AP.
|
||||
*/
|
||||
void
|
||||
rrc_gNB_send_NGAP_NAS_FIRST_REQ(
|
||||
const protocol_ctxt_t *const ctxt_pP,
|
||||
rrc_gNB_ue_context_t *ue_context_pP,
|
||||
NR_RRCSetupComplete_IEs_t *rrcSetupComplete
|
||||
)
|
||||
//------------------------------------------------------------------------------
|
||||
{
|
||||
// gNB_RRC_INST *rrc = RC.nrrrc[ctxt_pP->module_id];
|
||||
MessageDef *message_p = NULL;
|
||||
rrc_ue_ngap_ids_t *rrc_ue_ngap_ids_p = NULL;
|
||||
// hashtable_rc_t h_rc;
|
||||
|
||||
message_p = itti_alloc_new_message(TASK_RRC_GNB, NGAP_NAS_FIRST_REQ);
|
||||
memset(&message_p->ittiMsg.ngap_nas_first_req, 0, sizeof(ngap_nas_first_req_t));
|
||||
ue_context_pP->ue_context.ue_initial_id = get_next_ue_initial_id(ctxt_pP->module_id);
|
||||
NGAP_NAS_FIRST_REQ(message_p).ue_initial_id = ue_context_pP->ue_context.ue_initial_id;
|
||||
rrc_ue_ngap_ids_p = malloc(sizeof(rrc_ue_ngap_ids_t));
|
||||
rrc_ue_ngap_ids_p->ue_initial_id = ue_context_pP->ue_context.ue_initial_id;
|
||||
rrc_ue_ngap_ids_p->gNB_ue_ngap_id = UE_INITIAL_ID_INVALID;
|
||||
rrc_ue_ngap_ids_p->ue_rnti = ctxt_pP->rnti;
|
||||
|
||||
// h_rc = hashtable_insert(RC.nrrrc[ctxt_pP->module_id]->initial_id2_s1ap_ids,
|
||||
// (hash_key_t)ue_context_pP->ue_context.ue_initial_id,
|
||||
// rrc_ue_s1ap_ids_p);
|
||||
|
||||
// if (h_rc != HASH_TABLE_OK) {
|
||||
// LOG_E(S1AP, "[eNB %d] Error while hashtable_insert in initial_id2_s1ap_ids ue_initial_id %u\n",
|
||||
// ctxt_pP->module_id,
|
||||
// ue_context_pP->ue_context.ue_initial_id);
|
||||
// }
|
||||
|
||||
/* Assume that cause is coded in the same way in RRC and NGap, just check that the value is in NGap range */
|
||||
AssertFatal(ue_context_pP->ue_context.establishment_cause < NGAP_RRC_CAUSE_LAST,
|
||||
"Establishment cause invalid (%jd/%d) for gNB %d!",
|
||||
ue_context_pP->ue_context.establishment_cause,
|
||||
NGAP_RRC_CAUSE_LAST,
|
||||
ctxt_pP->module_id);
|
||||
NGAP_NAS_FIRST_REQ(message_p).establishment_cause = ue_context_pP->ue_context.establishment_cause;
|
||||
|
||||
/* Forward NAS message */
|
||||
NGAP_NAS_FIRST_REQ(message_p).nas_pdu.buffer = rrcSetupComplete->dedicatedNAS_Message.buf;
|
||||
NGAP_NAS_FIRST_REQ(message_p).nas_pdu.length = rrcSetupComplete->dedicatedNAS_Message.size;
|
||||
// extract_imsi(NGAP_NAS_FIRST_REQ (message_p).nas_pdu.buffer,
|
||||
// NGAP_NAS_FIRST_REQ (message_p).nas_pdu.length,
|
||||
// ue_context_pP);
|
||||
|
||||
/* Fill UE identities with available information */
|
||||
NGAP_NAS_FIRST_REQ(message_p).ue_identity.presenceMask = NGAP_UE_IDENTITIES_NONE;
|
||||
/* Fill s-TMSI */
|
||||
NGAP_NAS_FIRST_REQ(message_p).ue_identity.s_tmsi.amf_set_id = ue_context_pP->ue_context.Initialue_identity_5g_s_TMSI.amf_set_id;
|
||||
NGAP_NAS_FIRST_REQ(message_p).ue_identity.s_tmsi.amf_pointer = ue_context_pP->ue_context.Initialue_identity_5g_s_TMSI.amf_pointer;
|
||||
NGAP_NAS_FIRST_REQ(message_p).ue_identity.s_tmsi.m_tmsi = ue_context_pP->ue_context.Initialue_identity_5g_s_TMSI.fiveg_tmsi;
|
||||
|
||||
/* selected_plmn_identity: IE is 1-based, convert to 0-based (C array) */
|
||||
int selected_plmn_identity = rrcSetupComplete->selectedPLMN_Identity - 1;
|
||||
NGAP_NAS_FIRST_REQ(message_p).selected_plmn_identity = selected_plmn_identity;
|
||||
|
||||
if (rrcSetupComplete->registeredAMF != NULL) {
|
||||
NR_RegisteredAMF_t *r_amf = rrcSetupComplete->registeredAMF;
|
||||
NGAP_NAS_FIRST_REQ(message_p).ue_identity.presenceMask |= NGAP_UE_IDENTITIES_guami;
|
||||
|
||||
if (r_amf->plmn_Identity != NULL) {
|
||||
if ((r_amf->plmn_Identity->mcc != NULL) && (r_amf->plmn_Identity->mcc->list.count > 0)) {
|
||||
/* Use first indicated PLMN MCC if it is defined */
|
||||
NGAP_NAS_FIRST_REQ(message_p).ue_identity.guami.mcc = *r_amf->plmn_Identity->mcc->list.array[selected_plmn_identity];
|
||||
LOG_I(NGAP, "[gNB %d] Build NGAP_NAS_FIRST_REQ adding in s_TMSI: GUMMEI MCC %u ue %x\n",
|
||||
ctxt_pP->module_id,
|
||||
NGAP_NAS_FIRST_REQ (message_p).ue_identity.guami.mcc,
|
||||
ue_context_pP->ue_context.rnti);
|
||||
}
|
||||
|
||||
if (r_amf->plmn_Identity->mnc.list.count > 0) {
|
||||
/* Use first indicated PLMN MNC if it is defined */
|
||||
NGAP_NAS_FIRST_REQ(message_p).ue_identity.guami.mnc = *r_amf->plmn_Identity->mnc.list.array[selected_plmn_identity];
|
||||
LOG_I(NGAP, "[gNB %d] Build NGAP_NAS_FIRST_REQ adding in s_TMSI: GUMMEI MNC %u ue %x\n",
|
||||
ctxt_pP->module_id,
|
||||
NGAP_NAS_FIRST_REQ (message_p).ue_identity.guami.mnc,
|
||||
ue_context_pP->ue_context.rnti);
|
||||
}
|
||||
} else {
|
||||
/* TODO */
|
||||
}
|
||||
|
||||
/* amf_Identifier */
|
||||
uint32_t amf_Id = BIT_STRING_to_uint32(&r_amf->amf_Identifier);
|
||||
NGAP_NAS_FIRST_REQ(message_p).ue_identity.guami.amf_region_id = amf_Id >> 16;
|
||||
NGAP_NAS_FIRST_REQ(message_p).ue_identity.guami.amf_set_id = ue_context_pP->ue_context.Initialue_identity_5g_s_TMSI.amf_set_id;
|
||||
NGAP_NAS_FIRST_REQ(message_p).ue_identity.guami.amf_pointer = ue_context_pP->ue_context.Initialue_identity_5g_s_TMSI.amf_pointer;
|
||||
|
||||
ue_context_pP->ue_context.ue_guami.mcc = NGAP_NAS_FIRST_REQ(message_p).ue_identity.guami.mcc;
|
||||
ue_context_pP->ue_context.ue_guami.mnc = NGAP_NAS_FIRST_REQ(message_p).ue_identity.guami.mnc;
|
||||
ue_context_pP->ue_context.ue_guami.mnc_len = NGAP_NAS_FIRST_REQ(message_p).ue_identity.guami.mnc_len;
|
||||
ue_context_pP->ue_context.ue_guami.amf_region_id = NGAP_NAS_FIRST_REQ(message_p).ue_identity.guami.amf_region_id;
|
||||
ue_context_pP->ue_context.ue_guami.amf_set_id = NGAP_NAS_FIRST_REQ(message_p).ue_identity.guami.amf_set_id;
|
||||
ue_context_pP->ue_context.ue_guami.amf_pointer = NGAP_NAS_FIRST_REQ(message_p).ue_identity.guami.amf_pointer;
|
||||
|
||||
MSC_LOG_TX_MESSAGE(MSC_NGAP_GNB,
|
||||
MSC_NGAP_AMF,
|
||||
(const char *)&message_p->ittiMsg.ngap_nas_first_req,
|
||||
sizeof(ngap_nas_first_req_t),
|
||||
MSC_AS_TIME_FMT" NGAP_NAS_FIRST_REQ gNB %u UE %x",
|
||||
MSC_AS_TIME_ARGS(ctxt_pP),
|
||||
ctxt_pP->module_id,
|
||||
ctxt_pP->rnti);
|
||||
LOG_I(NGAP, "[gNB %d] Build NGAP_NAS_FIRST_REQ adding in s_TMSI: GUAMI amf_set_id %u amf_region_id %u ue %x\n",
|
||||
ctxt_pP->module_id,
|
||||
NGAP_NAS_FIRST_REQ (message_p).ue_identity.guami.amf_set_id,
|
||||
NGAP_NAS_FIRST_REQ (message_p).ue_identity.guami.amf_region_id,
|
||||
ue_context_pP->ue_context.rnti);
|
||||
}
|
||||
|
||||
itti_send_msg_to_task (TASK_NGAP, ctxt_pP->instance, message_p);
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
int
|
||||
rrc_gNB_process_NGAP_INITIAL_CONTEXT_SETUP_REQ(
|
||||
MessageDef *msg_p,
|
||||
const char *msg_name,
|
||||
instance_t instance
|
||||
)
|
||||
//------------------------------------------------------------------------------
|
||||
{
|
||||
uint16_t ue_initial_id;
|
||||
uint32_t gNB_ue_ngap_id;
|
||||
rrc_gNB_ue_context_t *ue_context_p = NULL;
|
||||
protocol_ctxt_t ctxt;
|
||||
|
||||
ue_initial_id = NGAP_INITIAL_CONTEXT_SETUP_REQ(msg_p).ue_initial_id;
|
||||
gNB_ue_ngap_id = NGAP_INITIAL_CONTEXT_SETUP_REQ(msg_p).gNB_ue_ngap_id;
|
||||
|
||||
ue_context_p = rrc_gNB_get_ue_context_from_ngap_ids(instance, ue_initial_id, gNB_ue_ngap_id);
|
||||
LOG_I(NR_RRC, "[gNB %d] Received %s: ue_initial_id %d, gNB_ue_ngap_id %d \n",
|
||||
instance, msg_name, ue_initial_id, gNB_ue_ngap_id);
|
||||
|
||||
if (ue_context_p == NULL) {
|
||||
/* Can not associate this message to an UE index, send a failure to NGAP and discard it! */
|
||||
MessageDef *msg_fail_p = NULL;
|
||||
LOG_W(NR_RRC, "[gNB %d] In NGAP_INITIAL_CONTEXT_SETUP_REQ: unknown UE from S1AP ids (%d, %d)\n", instance, ue_initial_id, gNB_ue_ngap_id);
|
||||
msg_fail_p = itti_alloc_new_message (TASK_RRC_GNB, NGAP_INITIAL_CONTEXT_SETUP_FAIL);
|
||||
NGAP_INITIAL_CONTEXT_SETUP_FAIL (msg_fail_p).gNB_ue_ngap_id = gNB_ue_ngap_id;
|
||||
// TODO add failure cause when defined!
|
||||
itti_send_msg_to_task (TASK_NGAP, instance, msg_fail_p);
|
||||
return (-1);
|
||||
} else {
|
||||
PROTOCOL_CTXT_SET_BY_INSTANCE(&ctxt, instance, GNB_FLAG_YES, ue_context_p->ue_context.rnti, 0, 0);
|
||||
ue_context_p->ue_context.gNB_ue_ngap_id = NGAP_INITIAL_CONTEXT_SETUP_REQ (msg_p).gNB_ue_ngap_id;
|
||||
ue_context_p->ue_context.amf_ue_ngap_id = NGAP_INITIAL_CONTEXT_SETUP_REQ (msg_p).amf_ue_ngap_id;
|
||||
|
||||
/* NAS PDU */
|
||||
if (ue_context_p->ue_context.nas_pdu_flag == 1) {
|
||||
ue_context_p->ue_context.nas_pdu.length = NGAP_INITIAL_CONTEXT_SETUP_REQ(msg_p).nas_pdu.length;
|
||||
ue_context_p->ue_context.nas_pdu.buffer = NGAP_INITIAL_CONTEXT_SETUP_REQ(msg_p).nas_pdu.buffer;
|
||||
}
|
||||
|
||||
/* TODO security */
|
||||
rrc_gNB_process_security(&ctxt, ue_context_p, &(NGAP_INITIAL_CONTEXT_SETUP_REQ(msg_p).security_capabilities));
|
||||
|
||||
uint8_t send_security_mode_command = TRUE;
|
||||
|
||||
nr_rrc_pdcp_config_security(
|
||||
&ctxt,
|
||||
ue_context_p,
|
||||
send_security_mode_command);
|
||||
|
||||
if (send_security_mode_command) {
|
||||
rrc_gNB_generate_SecurityModeCommand (&ctxt, ue_context_p);
|
||||
send_security_mode_command = FALSE;
|
||||
|
||||
nr_rrc_pdcp_config_security(
|
||||
&ctxt,
|
||||
ue_context_p,
|
||||
send_security_mode_command);
|
||||
} else {
|
||||
/* rrc_gNB_generate_UECapabilityEnquiry */
|
||||
rrc_gNB_generate_UECapabilityEnquiry(&ctxt, ue_context_p);
|
||||
}
|
||||
|
||||
// in case, send the S1SP initial context response if it is not sent with the attach complete message
|
||||
if (ue_context_p->ue_context.Status == NR_RRC_RECONFIGURED) {
|
||||
LOG_I(NR_RRC, "Sending rrc_gNB_send_NGAP_INITIAL_CONTEXT_SETUP_RESP, cause %ld\n", ue_context_p->ue_context.reestablishment_cause);
|
||||
rrc_gNB_send_NGAP_INITIAL_CONTEXT_SETUP_RESP(&ctxt,ue_context_p);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
void
|
||||
rrc_gNB_send_NGAP_INITIAL_CONTEXT_SETUP_RESP(
|
||||
const protocol_ctxt_t *const ctxt_pP,
|
||||
rrc_gNB_ue_context_t *const ue_context_pP
|
||||
)
|
||||
//------------------------------------------------------------------------------
|
||||
{
|
||||
MessageDef *msg_p = NULL;
|
||||
int e_rab;
|
||||
int e_rabs_done = 0;
|
||||
int e_rabs_failed = 0;
|
||||
msg_p = itti_alloc_new_message (TASK_RRC_ENB, NGAP_INITIAL_CONTEXT_SETUP_RESP);
|
||||
NGAP_INITIAL_CONTEXT_SETUP_RESP (msg_p).gNB_ue_ngap_id = ue_context_pP->ue_context.gNB_ue_ngap_id;
|
||||
|
||||
for (e_rab = 0; e_rab < ue_context_pP->ue_context.nb_of_e_rabs; e_rab++) {
|
||||
if (ue_context_pP->ue_context.e_rab[e_rab].status == E_RAB_STATUS_DONE) {
|
||||
e_rabs_done++;
|
||||
NGAP_INITIAL_CONTEXT_SETUP_RESP (msg_p).pdusessions[e_rab].pdusession_id = ue_context_pP->ue_context.e_rab[e_rab].param.e_rab_id;
|
||||
// TODO add other information from S1-U when it will be integrated
|
||||
NGAP_INITIAL_CONTEXT_SETUP_RESP (msg_p).pdusessions[e_rab].gtp_teid = ue_context_pP->ue_context.gnb_gtp_teid[e_rab];
|
||||
memcpy(NGAP_INITIAL_CONTEXT_SETUP_RESP (msg_p).pdusessions[e_rab].gNB_addr.buffer , ue_context_pP->ue_context.gnb_gtp_addrs[e_rab].buffer, 20);
|
||||
NGAP_INITIAL_CONTEXT_SETUP_RESP (msg_p).pdusessions[e_rab].gNB_addr.length = 4;
|
||||
ue_context_pP->ue_context.e_rab[e_rab].status = E_RAB_STATUS_ESTABLISHED;
|
||||
} else {
|
||||
e_rabs_failed++;
|
||||
ue_context_pP->ue_context.e_rab[e_rab].status = E_RAB_STATUS_FAILED;
|
||||
NGAP_INITIAL_CONTEXT_SETUP_RESP (msg_p).pdusessions_failed[e_rab].pdusession_id = ue_context_pP->ue_context.e_rab[e_rab].param.e_rab_id;
|
||||
// TODO add cause when it will be integrated
|
||||
}
|
||||
}
|
||||
|
||||
MSC_LOG_TX_MESSAGE(
|
||||
MSC_RRC_GNB,
|
||||
MSC_S1AP_ENB,
|
||||
(const char *)&NGAP_INITIAL_CONTEXT_SETUP_RESP (msg_p),
|
||||
sizeof(ngap_initial_context_setup_resp_t),
|
||||
MSC_AS_TIME_FMT" INITIAL_CONTEXT_SETUP_RESP UE %X eNB_ue_s1ap_id %u e_rabs:%u succ %u fail",
|
||||
MSC_AS_TIME_ARGS(ctxt_pP),
|
||||
ue_context_pP->ue_id_rnti,
|
||||
NGAP_INITIAL_CONTEXT_SETUP_RESP (msg_p).gNB_ue_ngap_id,
|
||||
e_rabs_done, e_rabs_failed);
|
||||
NGAP_INITIAL_CONTEXT_SETUP_RESP (msg_p).nb_of_pdusessions = e_rabs_done;
|
||||
NGAP_INITIAL_CONTEXT_SETUP_RESP (msg_p).nb_of_pdusessions_failed = e_rabs_failed;
|
||||
itti_send_msg_to_task (TASK_NGAP, ctxt_pP->instance, msg_p);
|
||||
}
|
||||
|
||||
static NR_CipheringAlgorithm_t rrc_gNB_select_ciphering(uint16_t algorithms) {
|
||||
//#warning "Forced return NR_CipheringAlgorithm_nea0, to be deleted in future"
|
||||
return NR_CipheringAlgorithm_nea0;
|
||||
}
|
||||
|
||||
static e_NR_IntegrityProtAlgorithm rrc_gNB_select_integrity(uint16_t algorithms) {
|
||||
|
||||
// to be continue
|
||||
return NR_IntegrityProtAlgorithm_nia0;
|
||||
}
|
||||
|
||||
int
|
||||
rrc_gNB_process_security(
|
||||
const protocol_ctxt_t *const ctxt_pP,
|
||||
rrc_gNB_ue_context_t *const ue_context_pP,
|
||||
ngap_security_capabilities_t *security_capabilities_pP
|
||||
) {
|
||||
boolean_t changed = FALSE;
|
||||
NR_CipheringAlgorithm_t cipheringAlgorithm;
|
||||
e_NR_IntegrityProtAlgorithm integrityProtAlgorithm;
|
||||
/* Save security parameters */
|
||||
ue_context_pP->ue_context.security_capabilities = *security_capabilities_pP;
|
||||
// translation
|
||||
LOG_D(NR_RRC,
|
||||
"[eNB %d] NAS security_capabilities.encryption_algorithms %u AS ciphering_algorithm %lu NAS security_capabilities.integrity_algorithms %u AS integrity_algorithm %u\n",
|
||||
ctxt_pP->module_id,
|
||||
ue_context_pP->ue_context.security_capabilities.nRencryption_algorithms,
|
||||
(unsigned long)ue_context_pP->ue_context.ciphering_algorithm,
|
||||
ue_context_pP->ue_context.security_capabilities.nRintegrity_algorithms,
|
||||
ue_context_pP->ue_context.integrity_algorithm);
|
||||
/* Select relevant algorithms */
|
||||
cipheringAlgorithm = rrc_gNB_select_ciphering (ue_context_pP->ue_context.security_capabilities.nRencryption_algorithms);
|
||||
|
||||
if (ue_context_pP->ue_context.ciphering_algorithm != cipheringAlgorithm) {
|
||||
ue_context_pP->ue_context.ciphering_algorithm = cipheringAlgorithm;
|
||||
changed = TRUE;
|
||||
}
|
||||
|
||||
integrityProtAlgorithm = rrc_gNB_select_integrity (ue_context_pP->ue_context.security_capabilities.nRintegrity_algorithms);
|
||||
|
||||
if (ue_context_pP->ue_context.integrity_algorithm != integrityProtAlgorithm) {
|
||||
ue_context_pP->ue_context.integrity_algorithm = integrityProtAlgorithm;
|
||||
changed = TRUE;
|
||||
}
|
||||
|
||||
LOG_I (NR_RRC, "[eNB %d][UE %x] Selected security algorithms (%p): %lx, %x, %s\n",
|
||||
ctxt_pP->module_id,
|
||||
ue_context_pP->ue_context.rnti,
|
||||
security_capabilities_pP,
|
||||
(unsigned long)cipheringAlgorithm,
|
||||
integrityProtAlgorithm,
|
||||
changed ? "changed" : "same");
|
||||
return changed;
|
||||
}
|
||||
80
openair2/RRC/NR/rrc_gNB_NGAP.h
Normal file
80
openair2/RRC/NR/rrc_gNB_NGAP.h
Normal file
@@ -0,0 +1,80 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file rrc_gNB_NGAP.h
|
||||
* \brief rrc NGAP procedures for gNB
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \date 2020
|
||||
* \version 0.1
|
||||
* \email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com
|
||||
* (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
*/
|
||||
|
||||
#ifndef RRC_GNB_NGAP_H_
|
||||
#define RRC_GNB_NGAP_H_
|
||||
|
||||
#include "rrc_gNB_UE_context.h"
|
||||
#include "nr_rrc_defs.h"
|
||||
#include "nr_rrc_extern.h"
|
||||
|
||||
#include "NR_RRCSetupComplete-IEs.h"
|
||||
#include "NR_RegisteredAMF.h"
|
||||
|
||||
typedef struct rrc_ue_ngap_ids_s {
|
||||
/* Tree related data */
|
||||
RB_ENTRY(rrc_ue_ngap_ids_s) entries;
|
||||
|
||||
// keys
|
||||
uint16_t ue_initial_id;
|
||||
uint32_t gNB_ue_ngap_id;
|
||||
|
||||
// value
|
||||
rnti_t ue_rnti;
|
||||
} rrc_ue_ngap_ids_t;
|
||||
|
||||
void
|
||||
rrc_gNB_send_NGAP_NAS_FIRST_REQ(
|
||||
const protocol_ctxt_t *const ctxt_pP,
|
||||
rrc_gNB_ue_context_t *ue_context_pP,
|
||||
NR_RRCSetupComplete_IEs_t *rrcSetupComplete
|
||||
);
|
||||
|
||||
int
|
||||
rrc_gNB_process_NGAP_INITIAL_CONTEXT_SETUP_REQ(
|
||||
MessageDef *msg_p,
|
||||
const char *msg_name,
|
||||
instance_t instance
|
||||
);
|
||||
|
||||
void
|
||||
rrc_gNB_send_NGAP_INITIAL_CONTEXT_SETUP_RESP(
|
||||
const protocol_ctxt_t *const ctxt_pP,
|
||||
rrc_gNB_ue_context_t *const ue_context_pP
|
||||
);
|
||||
|
||||
int
|
||||
rrc_gNB_process_security(
|
||||
const protocol_ctxt_t *const ctxt_pP,
|
||||
rrc_gNB_ue_context_t *const ue_context_pP,
|
||||
ngap_security_capabilities_t *security_capabilities_pP
|
||||
);
|
||||
|
||||
#endif
|
||||
@@ -189,7 +189,7 @@ void rrc_gNB_free_mem_UE_context(
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
void rrc_gNB_remove_ue_context(
|
||||
const protocol_ctxt_t *const ctxt_pP,
|
||||
const protocol_ctxt_t *const ctxt_pP,
|
||||
gNB_RRC_INST *rrc_instance_pP,
|
||||
struct rrc_gNB_ue_context_s *ue_context_pP)
|
||||
//------------------------------------------------------------------------------
|
||||
@@ -220,4 +220,82 @@ void rrc_gNB_remove_ue_context(
|
||||
PROTOCOL_RRC_CTXT_UE_ARGS(ctxt_pP));
|
||||
}
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// return the ue context if there is already an UE with ue_identityP, NULL otherwise
|
||||
struct rrc_gNB_ue_context_s *
|
||||
rrc_gNB_ue_context_random_exist(
|
||||
gNB_RRC_INST *rrc_instance_pP,
|
||||
const uint64_t ue_identityP
|
||||
)
|
||||
//-----------------------------------------------------------------------------
|
||||
{
|
||||
struct rrc_gNB_ue_context_s *ue_context_p = NULL;
|
||||
RB_FOREACH(ue_context_p, rrc_nr_ue_tree_s, &rrc_instance_pP->rrc_ue_head) {
|
||||
if (ue_context_p->ue_context.random_ue_identity == ue_identityP)
|
||||
return ue_context_p;
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// return the ue context if there is already an UE with the same S-TMSI, NULL otherwise
|
||||
struct rrc_gNB_ue_context_s *
|
||||
rrc_gNB_ue_context_5g_s_tmsi_exist(
|
||||
gNB_RRC_INST *rrc_instance_pP,
|
||||
const uint64_t s_TMSI
|
||||
)
|
||||
//-----------------------------------------------------------------------------
|
||||
{
|
||||
struct rrc_gNB_ue_context_s *ue_context_p = NULL;
|
||||
RB_FOREACH(ue_context_p, rrc_nr_ue_tree_s, &rrc_instance_pP->rrc_ue_head) {
|
||||
LOG_I(NR_RRC,"checking for UE 5G S-TMSI %ld: rnti %d \n",
|
||||
s_TMSI, ue_context_p->ue_context.rnti);
|
||||
|
||||
if (ue_context_p->ue_context.ng_5G_S_TMSI_Part1 == s_TMSI) {
|
||||
return ue_context_p;
|
||||
}
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// return a new ue context structure if ue_identityP, ctxt_pP->rnti not found in collection
|
||||
struct rrc_gNB_ue_context_s *
|
||||
rrc_gNB_get_next_free_ue_context(
|
||||
const protocol_ctxt_t *const ctxt_pP,
|
||||
gNB_RRC_INST *rrc_instance_pP,
|
||||
const uint64_t ue_identityP
|
||||
)
|
||||
//-----------------------------------------------------------------------------
|
||||
{
|
||||
struct rrc_gNB_ue_context_s *ue_context_p = NULL;
|
||||
ue_context_p = rrc_gNB_get_ue_context(rrc_instance_pP, ctxt_pP->rnti);
|
||||
|
||||
if (ue_context_p == NULL) {
|
||||
ue_context_p = rrc_gNB_allocate_new_UE_context(rrc_instance_pP);
|
||||
|
||||
if (ue_context_p == NULL) {
|
||||
LOG_E(NR_RRC,
|
||||
PROTOCOL_NR_RRC_CTXT_UE_FMT" Cannot create new UE context, no memory\n",
|
||||
PROTOCOL_NR_RRC_CTXT_UE_ARGS(ctxt_pP));
|
||||
return NULL;
|
||||
}
|
||||
|
||||
ue_context_p->ue_id_rnti = ctxt_pP->rnti; // here ue_id_rnti is just a key, may be something else
|
||||
ue_context_p->ue_context.rnti = ctxt_pP->rnti; // yes duplicate, 1 may be removed
|
||||
ue_context_p->ue_context.random_ue_identity = ue_identityP;
|
||||
RB_INSERT(rrc_nr_ue_tree_s, &rrc_instance_pP->rrc_ue_head, ue_context_p);
|
||||
LOG_D(NR_RRC,
|
||||
PROTOCOL_NR_RRC_CTXT_UE_FMT" Created new UE context uid %u\n",
|
||||
PROTOCOL_NR_RRC_CTXT_UE_ARGS(ctxt_pP),
|
||||
ue_context_p->local_uid);
|
||||
return ue_context_p;
|
||||
} else {
|
||||
LOG_E(NR_RRC,
|
||||
PROTOCOL_NR_RRC_CTXT_UE_FMT" Cannot create new UE context, already exist\n",
|
||||
PROTOCOL_NR_RRC_CTXT_UE_ARGS(ctxt_pP));
|
||||
return NULL;
|
||||
}
|
||||
|
||||
return(ue_context_p);
|
||||
}
|
||||
|
||||
@@ -73,10 +73,34 @@ rrc_gNB_get_ue_context(
|
||||
rnti_t rntiP
|
||||
);
|
||||
|
||||
void rrc_gNB_free_mem_UE_context(
|
||||
const protocol_ctxt_t *const ctxt_pP,
|
||||
struct rrc_gNB_ue_context_s *const ue_context_pP
|
||||
);
|
||||
|
||||
void rrc_gNB_remove_ue_context(
|
||||
const protocol_ctxt_t* const ctxt_pP,
|
||||
gNB_RRC_INST* rrc_instance_pP,
|
||||
struct rrc_gNB_ue_context_s* ue_context_pP
|
||||
);
|
||||
|
||||
struct rrc_gNB_ue_context_s *
|
||||
rrc_gNB_ue_context_random_exist(
|
||||
gNB_RRC_INST *rrc_instance_pP,
|
||||
const uint64_t ue_identityP
|
||||
);
|
||||
|
||||
struct rrc_gNB_ue_context_s *
|
||||
rrc_gNB_ue_context_5g_s_tmsi_exist(
|
||||
gNB_RRC_INST *rrc_instance_pP,
|
||||
const uint64_t s_TMSI
|
||||
);
|
||||
|
||||
struct rrc_gNB_ue_context_s *
|
||||
rrc_gNB_get_next_free_ue_context(
|
||||
const protocol_ctxt_t *const ctxt_pP,
|
||||
gNB_RRC_INST *rrc_instance_pP,
|
||||
const uint64_t ue_identityP
|
||||
);
|
||||
|
||||
#endif
|
||||
|
||||
@@ -222,7 +222,7 @@ void fill_default_secondaryCellGroup(NR_ServingCellConfigCommon_t *servingcellco
|
||||
secondaryCellGroup->spCellConfig->rlf_TimersAndConstants->choice.setup->n310 = NR_RLF_TimersAndConstants__n310_n10;
|
||||
secondaryCellGroup->spCellConfig->rlf_TimersAndConstants->choice.setup->n311 = NR_RLF_TimersAndConstants__n311_n1;
|
||||
secondaryCellGroup->spCellConfig->rlf_TimersAndConstants->choice.setup->ext1 = calloc(1,sizeof(*secondaryCellGroup->spCellConfig->rlf_TimersAndConstants->choice.setup->ext1));
|
||||
secondaryCellGroup->spCellConfig->rlf_TimersAndConstants->choice.setup->ext1->t311_v1530 = NR_RLF_TimersAndConstants__ext1__t311_v1530_ms30000;
|
||||
secondaryCellGroup->spCellConfig->rlf_TimersAndConstants->choice.setup->ext1->t311 = NR_RLF_TimersAndConstants__ext1__t311_ms30000;
|
||||
secondaryCellGroup->spCellConfig->rlmInSyncOutOfSyncThreshold = NULL;
|
||||
secondaryCellGroup->spCellConfig->spCellConfigDedicated = calloc(1,sizeof(*secondaryCellGroup->spCellConfig->spCellConfigDedicated));
|
||||
secondaryCellGroup->spCellConfig->spCellConfigDedicated->tdd_UL_DL_ConfigurationDedicated = NULL;
|
||||
@@ -894,7 +894,7 @@ void fill_default_secondaryCellGroup(NR_ServingCellConfigCommon_t *servingcellco
|
||||
ASN_SEQUENCE_ADD(&pucchresset0->resourceList.list,pucchresset0id0);
|
||||
*pucchresset0id1=2;
|
||||
ASN_SEQUENCE_ADD(&pucchresset0->resourceList.list,pucchresset0id1);
|
||||
pucchresset0->maxPayloadMinus1=NULL;
|
||||
pucchresset0->maxPayloadSize=NULL;
|
||||
|
||||
ASN_SEQUENCE_ADD(&pucch_Config->resourceSetToAddModList->list,pucchresset0);
|
||||
|
||||
@@ -905,7 +905,7 @@ void fill_default_secondaryCellGroup(NR_ServingCellConfigCommon_t *servingcellco
|
||||
ASN_SEQUENCE_ADD(&pucchresset1->resourceList.list,pucchresset1id0);
|
||||
*pucchresset1id1=4;
|
||||
ASN_SEQUENCE_ADD(&pucchresset1->resourceList.list,pucchresset1id1);
|
||||
pucchresset1->maxPayloadMinus1=NULL;
|
||||
pucchresset1->maxPayloadSize=NULL;
|
||||
ASN_SEQUENCE_ADD(&pucch_Config->resourceSetToAddModList->list,pucchresset1);
|
||||
|
||||
pucch_Config->resourceToAddModList = calloc(1,sizeof(*pucch_Config->resourceToAddModList));
|
||||
|
||||
@@ -67,4 +67,43 @@ int8_t mac_rrc_nr_data_req_ue(const module_id_t Mod_idP,
|
||||
// todo
|
||||
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
uint8_t
|
||||
rrc_data_req_ue(
|
||||
const protocol_ctxt_t *const ctxt_pP,
|
||||
const rb_id_t rb_idP,
|
||||
const mui_t muiP,
|
||||
const confirm_t confirmP,
|
||||
const sdu_size_t sdu_sizeP,
|
||||
uint8_t *const buffer_pP,
|
||||
const pdcp_transmission_mode_t modeP
|
||||
)
|
||||
{
|
||||
MessageDef *message_p;
|
||||
// Uses a new buffer to avoid issue with PDCP buffer content that could be changed by PDCP (asynchronous message handling).
|
||||
uint8_t *message_buffer;
|
||||
message_buffer = itti_malloc (
|
||||
ctxt_pP->enb_flag ? TASK_RRC_ENB : TASK_RRC_UE,
|
||||
ctxt_pP->enb_flag ? TASK_PDCP_ENB : TASK_PDCP_UE,
|
||||
sdu_sizeP);
|
||||
memcpy (message_buffer, buffer_pP, sdu_sizeP);
|
||||
message_p = itti_alloc_new_message (ctxt_pP->enb_flag ? TASK_RRC_ENB : TASK_RRC_UE, RRC_DCCH_DATA_REQ);
|
||||
RRC_DCCH_DATA_REQ (message_p).frame = ctxt_pP->frame;
|
||||
RRC_DCCH_DATA_REQ (message_p).enb_flag = ctxt_pP->enb_flag;
|
||||
RRC_DCCH_DATA_REQ (message_p).rb_id = rb_idP;
|
||||
RRC_DCCH_DATA_REQ (message_p).muip = muiP;
|
||||
RRC_DCCH_DATA_REQ (message_p).confirmp = confirmP;
|
||||
RRC_DCCH_DATA_REQ (message_p).sdu_size = sdu_sizeP;
|
||||
RRC_DCCH_DATA_REQ (message_p).sdu_p = message_buffer;
|
||||
RRC_DCCH_DATA_REQ (message_p).mode = modeP;
|
||||
RRC_DCCH_DATA_REQ (message_p).module_id = ctxt_pP->module_id;
|
||||
RRC_DCCH_DATA_REQ (message_p).rnti = ctxt_pP->rnti;
|
||||
RRC_DCCH_DATA_REQ (message_p).eNB_index = ctxt_pP->eNB_index;
|
||||
itti_send_msg_to_task (
|
||||
TASK_PDCP_UE,
|
||||
ctxt_pP->instance,
|
||||
message_p);
|
||||
return TRUE; // TODO should be changed to a CNF message later, currently RRC lite does not used the returned value anyway.
|
||||
|
||||
}
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -53,8 +53,15 @@
|
||||
#include "NR_MIB.h"
|
||||
#include "NR_BCCH-BCH-Message.h"
|
||||
#include "NR_DL-DCCH-Message.h"
|
||||
#include "../NR/nr_rrc_defs.h"
|
||||
|
||||
#define NB_NR_UE_INST 1
|
||||
#define NB_CNX_UE 2//MAX_MANAGED_RG_PER_MOBILE
|
||||
#define NB_SIG_CNX_UE 2 //MAX_MANAGED_RG_PER_MOBILE
|
||||
|
||||
#define MAX_MEAS_OBJ 6
|
||||
#define MAX_MEAS_CONFIG 6
|
||||
#define MAX_MEAS_ID 6
|
||||
|
||||
typedef uint32_t channel_t;
|
||||
|
||||
@@ -63,14 +70,65 @@ typedef enum {
|
||||
nr_RadioBearerConfigX_r15=1
|
||||
} nsa_message_t;
|
||||
|
||||
#define MAX_UE_NR_CAPABILITY_SIZE 255
|
||||
typedef struct OAI_NR_UECapability_s {
|
||||
uint8_t sdu[MAX_UE_NR_CAPABILITY_SIZE];
|
||||
uint8_t sdu_size;
|
||||
NR_UE_NR_Capability_t *UE_NR_Capability;
|
||||
} OAI_NR_UECapability_t;
|
||||
|
||||
typedef struct NR_UE_RRC_INST_s {
|
||||
|
||||
NR_MeasConfig_t *meas_config;
|
||||
NR_CellGroupConfig_t *cell_group_config;
|
||||
NR_RadioBearerConfig_t *radio_bearer_config;
|
||||
|
||||
|
||||
NR_MeasObjectToAddMod_t *MeasObj[NB_CNX_UE][MAX_MEAS_OBJ];
|
||||
NR_ReportConfigToAddMod_t *ReportConfig[NB_CNX_UE][MAX_MEAS_CONFIG];
|
||||
NR_QuantityConfig_t *QuantityConfig[NB_CNX_UE];
|
||||
NR_MeasIdToAddMod_t *MeasId[NB_CNX_UE][MAX_MEAS_ID];
|
||||
NR_MeasGapConfig_t *measGapConfig[NB_CNX_UE];
|
||||
NR_RSRP_Range_t s_measure;
|
||||
NR_SRB_ToAddMod_t *SRB1_config[NB_CNX_UE];
|
||||
NR_SRB_ToAddMod_t *SRB2_config[NB_CNX_UE];
|
||||
NR_DRB_ToAddMod_t *DRB_config[NB_CNX_UE][8];
|
||||
rb_id_t *defaultDRB; // remember the ID of the default DRB
|
||||
|
||||
NR_SRB_INFO Srb0[NB_SIG_CNX_UE];
|
||||
NR_SRB_INFO_TABLE_ENTRY Srb1[NB_CNX_UE];
|
||||
NR_SRB_INFO_TABLE_ENTRY Srb2[NB_CNX_UE];
|
||||
|
||||
uint8_t MBMS_flag;
|
||||
OAI_NR_UECapability_t *UECap;
|
||||
uint8_t *UECapability;
|
||||
uint8_t UECapability_size;
|
||||
|
||||
NR_SystemInformation_t *si[NB_CNX_UE];
|
||||
NR_SIB1_t *sib1[NB_CNX_UE];
|
||||
NR_SIB2_t *sib2[NB_CNX_UE];
|
||||
NR_SIB3_t *sib3[NB_CNX_UE];
|
||||
NR_SIB4_t *sib4[NB_CNX_UE];
|
||||
NR_SIB5_t *sib5[NB_CNX_UE];
|
||||
NR_SIB6_t *sib6[NB_CNX_UE];
|
||||
NR_SIB7_t *sib7[NB_CNX_UE];
|
||||
NR_SIB8_t *sib8[NB_CNX_UE];
|
||||
NR_SIB9_t *sib9[NB_CNX_UE];
|
||||
NR_SIB10_r16_t *sib10[NB_CNX_UE];
|
||||
NR_SIB11_r16_t *sib11[NB_CNX_UE];
|
||||
NR_SIB12_r16_t *sib12[NB_CNX_UE];
|
||||
NR_SIB13_r16_t *sib13[NB_CNX_UE];
|
||||
NR_SIB14_r16_t *sib14[NB_CNX_UE];
|
||||
plmn_t plmnID;
|
||||
|
||||
NR_UE_RRC_INFO Info[NB_SIG_CNX_UE];
|
||||
|
||||
NR_MIB_t *mib;
|
||||
|
||||
|
||||
/* KeNB as computed from parameters within USIM card */
|
||||
uint8_t kgnb[32];
|
||||
NR_CipheringAlgorithm_t cipheringAlgorithm;
|
||||
e_NR_IntegrityProtAlgorithm integrityProtAlgorithm;
|
||||
|
||||
// lists
|
||||
// CellGroupConfig.rlc-BearerToAddModList
|
||||
RRC_LIST_TYPE(NR_RLC_BearerConfig_t, NR_maxLC_ID) RLC_Bearer_Config_list;
|
||||
@@ -118,7 +176,11 @@ typedef struct NR_UE_RRC_INST_s {
|
||||
RRC_LIST_TYPE(NR_CSI_ResourceConfig_t, NR_maxNrofCSI_ResourceConfigurations) CSI_ResourceConfig_list;
|
||||
// CellGroupConfig.spCellConfig.spCellConfigDedicated
|
||||
RRC_LIST_TYPE(NR_CSI_ReportConfig_t, NR_maxNrofCSI_ReportConfigurations) CSI_ReportConfig_list;
|
||||
|
||||
|
||||
long selected_plmn_identity;
|
||||
Rrc_State_NR_t nrRrcState;
|
||||
Rrc_Sub_State_NR_t nrRrcSubState;
|
||||
as_nas_info_t initialNasMsg;
|
||||
} NR_UE_RRC_INST_t;
|
||||
|
||||
#endif
|
||||
|
||||
@@ -114,6 +114,16 @@ int8_t mac_rrc_nr_data_req_ue(const module_id_t Mod_idP,
|
||||
const rb_id_t Srb_id,
|
||||
uint8_t *const buffer_pP);
|
||||
|
||||
|
||||
/**\brief RRC UE task.
|
||||
\param void *args_p Pointer on arguments to start the task. */
|
||||
void *rrc_nrue_task(void *args_p);
|
||||
|
||||
/**\brief RRC UE generate RRCSetupRequest message.
|
||||
\param ctxt_pP protocol context
|
||||
\param gNB_index gNB index */
|
||||
void rrc_ue_generate_RRCSetupRequest( const protocol_ctxt_t *const ctxt_pP, const uint8_t gNB_index );
|
||||
|
||||
/** @}*/
|
||||
#endif
|
||||
|
||||
|
||||
30
openair2/SDAP/nr_sdap/sdap_gNB.c
Normal file
30
openair2/SDAP/nr_sdap/sdap_gNB.c
Normal file
@@ -0,0 +1,30 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file sdap_gNB.c
|
||||
* \brief sdap tasks for gNB
|
||||
* \author Konstantinos Alexandris <Konstantinos.Alexandris@eurecom.fr>, Cedric Roux <Cedric.Roux@eurecom.fr>, Navid Nikaein <Navid.Nikaein@eurecom.fr>
|
||||
* \date 2018
|
||||
* \version 1.0
|
||||
*/
|
||||
#define SDAP_GNB
|
||||
#define SDAP_GNB_C
|
||||
|
||||
629
openair2/SIMULATION/NR_RRC/itti_sim.c
Normal file
629
openair2/SIMULATION/NR_RRC/itti_sim.c
Normal file
@@ -0,0 +1,629 @@
|
||||
/*!
|
||||
\file itti_sim.c
|
||||
|
||||
\brief simulator for itti message from node to UE
|
||||
\author Yoshio INOUE, Masayuki HARADA
|
||||
\email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com
|
||||
\date 2020
|
||||
\version 0.1
|
||||
*/
|
||||
|
||||
#include <sched.h>
|
||||
|
||||
|
||||
#include "T.h"
|
||||
|
||||
#undef MALLOC //there are two conflicting definitions, so we better make sure we don't use it at all
|
||||
#include <common/utils/assertions.h>
|
||||
|
||||
#include "msc.h"
|
||||
|
||||
#include "common/ran_context.h"
|
||||
|
||||
#include "common/config/config_userapi.h"
|
||||
#include "common/utils/load_module_shlib.h"
|
||||
#undef MALLOC //there are two conflicting definitions, so we better make sure we don't use it at all
|
||||
|
||||
#include "PHY/phy_vars.h"
|
||||
#include "SCHED/sched_common_vars.h"
|
||||
#include "LAYER2/MAC/mac_vars.h"
|
||||
#include "RRC/LTE/rrc_vars.h"
|
||||
#include "gnb_config.h"
|
||||
#include "SIMULATION/TOOLS/sim.h"
|
||||
|
||||
#ifdef SMBV
|
||||
#include "PHY/TOOLS/smbv.h"
|
||||
unsigned short config_frames[4] = {2,9,11,13};
|
||||
#endif
|
||||
|
||||
#include "common/utils/LOG/log.h"
|
||||
#include "common/utils/LOG/vcd_signal_dumper.h"
|
||||
#include "UTIL/OPT/opt.h"
|
||||
|
||||
#ifndef OPENAIR2
|
||||
#include "UTIL/OTG/otg_vars.h"
|
||||
#endif
|
||||
|
||||
#include "intertask_interface.h"
|
||||
|
||||
|
||||
#include "system.h"
|
||||
#include <openair2/GNB_APP/gnb_app.h>
|
||||
#include "PHY/TOOLS/phy_scope_interface.h"
|
||||
#include "PHY/TOOLS/nr_phy_scope.h"
|
||||
#include "stats.h"
|
||||
#include "nr-softmodem.h"
|
||||
#include "executables/softmodem-common.h"
|
||||
#include "executables/thread-common.h"
|
||||
#include "NB_IoT_interface.h"
|
||||
#include "x2ap_eNB.h"
|
||||
#include "ngap_gNB.h"
|
||||
#include "RRC/NR_UE/rrc_proto.h"
|
||||
#include "RRC/NR_UE/rrc_vars.h"
|
||||
#include "openair3/NAS/UE/nas_ue_task.h"
|
||||
|
||||
pthread_cond_t nfapi_sync_cond;
|
||||
pthread_mutex_t nfapi_sync_mutex;
|
||||
int nfapi_sync_var=-1; //!< protected by mutex \ref nfapi_sync_mutex
|
||||
|
||||
uint8_t nfapi_mode = 0; // Default to monolithic mode
|
||||
uint32_t target_dl_mcs = 28;
|
||||
uint32_t target_ul_mcs = 20;
|
||||
uint32_t timing_advance = 0;
|
||||
uint64_t num_missed_slots=0;
|
||||
|
||||
int split73=0;
|
||||
void sendFs6Ul(PHY_VARS_eNB *eNB, int UE_id, int harq_pid, int segmentID, int16_t *data, int dataLen, int r_offset) {
|
||||
AssertFatal(false, "Must not be called in this context\n");
|
||||
}
|
||||
|
||||
pthread_cond_t sync_cond;
|
||||
pthread_mutex_t sync_mutex;
|
||||
int sync_var=-1; //!< protected by mutex \ref sync_mutex.
|
||||
int config_sync_var=-1;
|
||||
|
||||
openair0_config_t openair0_cfg[MAX_CARDS];
|
||||
|
||||
volatile int start_gNB = 0;
|
||||
volatile int oai_exit = 0;
|
||||
|
||||
//static int wait_for_sync = 0;
|
||||
|
||||
unsigned int mmapped_dma=0;
|
||||
int single_thread_flag=1;
|
||||
|
||||
int8_t threequarter_fs=0;
|
||||
|
||||
uint64_t downlink_frequency[MAX_NUM_CCs][4];
|
||||
int32_t uplink_frequency_offset[MAX_NUM_CCs][4];
|
||||
|
||||
//Temp fix for inexistent NR upper layer
|
||||
unsigned char NB_gNB_INST = 1;
|
||||
|
||||
static char *itti_dump_file = NULL;
|
||||
|
||||
int UE_scan = 1;
|
||||
int UE_scan_carrier = 0;
|
||||
runmode_t mode = normal_txrx;
|
||||
static double snr_dB=20;
|
||||
|
||||
FILE *input_fd=NULL;
|
||||
|
||||
int chain_offset=0;
|
||||
|
||||
|
||||
uint8_t dci_Format = 0;
|
||||
uint8_t agregation_Level =0xFF;
|
||||
|
||||
uint8_t nb_antenna_tx = 1;
|
||||
uint8_t nb_antenna_rx = 1;
|
||||
|
||||
char ref[128] = "internal";
|
||||
char channels[128] = "0";
|
||||
|
||||
int otg_enabled;
|
||||
|
||||
extern void *udp_eNB_task(void *args_p);
|
||||
|
||||
int transmission_mode=1;
|
||||
int emulate_rf = 0;
|
||||
int numerology = 0;
|
||||
int usrp_tx_thread = 0;
|
||||
|
||||
|
||||
double cpuf;
|
||||
|
||||
extern char uecap_xer[1024];
|
||||
char uecap_xer_in=0;
|
||||
|
||||
/* see file openair2/LAYER2/MAC/main.c for why abstraction_flag is needed
|
||||
* this is very hackish - find a proper solution
|
||||
*/
|
||||
uint8_t abstraction_flag=0;
|
||||
|
||||
/* forward declarations */
|
||||
void set_default_frame_parms(nfapi_nr_config_request_scf_t *config[MAX_NUM_CCs], NR_DL_FRAME_PARMS *frame_parms[MAX_NUM_CCs]);
|
||||
|
||||
/*---------------------BMC: timespec helpers -----------------------------*/
|
||||
|
||||
struct timespec min_diff_time = { .tv_sec = 0, .tv_nsec = 0 };
|
||||
struct timespec max_diff_time = { .tv_sec = 0, .tv_nsec = 0 };
|
||||
|
||||
struct timespec clock_difftime(struct timespec start, struct timespec end) {
|
||||
struct timespec temp;
|
||||
|
||||
if ((end.tv_nsec-start.tv_nsec)<0) {
|
||||
temp.tv_sec = end.tv_sec-start.tv_sec-1;
|
||||
temp.tv_nsec = 1000000000+end.tv_nsec-start.tv_nsec;
|
||||
} else {
|
||||
temp.tv_sec = end.tv_sec-start.tv_sec;
|
||||
temp.tv_nsec = end.tv_nsec-start.tv_nsec;
|
||||
}
|
||||
|
||||
return temp;
|
||||
}
|
||||
|
||||
|
||||
|
||||
#define KNRM "\x1B[0m"
|
||||
#define KRED "\x1B[31m"
|
||||
#define KGRN "\x1B[32m"
|
||||
#define KBLU "\x1B[34m"
|
||||
#define RESET "\033[0m"
|
||||
|
||||
|
||||
void exit_function(const char *file, const char *function, const int line, const char *s) {
|
||||
int ru_id;
|
||||
|
||||
if (s != NULL) {
|
||||
printf("%s:%d %s() Exiting OAI softmodem: %s\n",file,line, function, s);
|
||||
}
|
||||
|
||||
oai_exit = 1;
|
||||
|
||||
if (RC.ru == NULL)
|
||||
exit(-1); // likely init not completed, prevent crash or hang, exit now...
|
||||
|
||||
for (ru_id=0; ru_id<RC.nb_RU; ru_id++) {
|
||||
if (RC.ru[ru_id] && RC.ru[ru_id]->rfdevice.trx_end_func) {
|
||||
RC.ru[ru_id]->rfdevice.trx_end_func(&RC.ru[ru_id]->rfdevice);
|
||||
RC.ru[ru_id]->rfdevice.trx_end_func = NULL;
|
||||
}
|
||||
|
||||
if (RC.ru[ru_id] && RC.ru[ru_id]->ifdevice.trx_end_func) {
|
||||
RC.ru[ru_id]->ifdevice.trx_end_func(&RC.ru[ru_id]->ifdevice);
|
||||
RC.ru[ru_id]->ifdevice.trx_end_func = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
sleep(1); //allow lte-softmodem threads to exit first
|
||||
exit(1);
|
||||
}
|
||||
|
||||
void wait_gNBs(void) {
|
||||
int i;
|
||||
int waiting=1;
|
||||
|
||||
while (waiting==1) {
|
||||
printf("Waiting for gNB L1 instances to all get configured ... sleeping 50ms (nb_nr_sL1_inst %d)\n",RC.nb_nr_L1_inst);
|
||||
usleep(50*1000);
|
||||
waiting=0;
|
||||
|
||||
for (i=0; i<RC.nb_nr_L1_inst; i++) {
|
||||
|
||||
if (RC.gNB[i]->configured==0) {
|
||||
waiting=1;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
printf("gNB L1 are configured\n");
|
||||
}
|
||||
|
||||
void wait_RUs(void) {
|
||||
LOG_I(PHY,"Waiting for RUs to be configured ... RC.ru_mask:%02lx\n", RC.ru_mask);
|
||||
// wait for all RUs to be configured over fronthaul
|
||||
pthread_mutex_lock(&RC.ru_mutex);
|
||||
|
||||
while (RC.ru_mask>0) {
|
||||
pthread_cond_wait(&RC.ru_cond,&RC.ru_mutex);
|
||||
printf("RC.ru_mask:%02lx\n", RC.ru_mask);
|
||||
}
|
||||
|
||||
pthread_mutex_unlock(&RC.ru_mutex);
|
||||
LOG_I(PHY,"RUs configured\n");
|
||||
}
|
||||
|
||||
|
||||
int stop_L1L2(module_id_t gnb_id) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
int restart_L1L2(module_id_t gnb_id) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
int create_gNB_tasks(uint32_t gnb_nb) {
|
||||
LOG_D(GNB_APP, "%s(gnb_nb:%d)\n", __FUNCTION__, gnb_nb);
|
||||
itti_wait_ready(1);
|
||||
|
||||
|
||||
if (gnb_nb > 0) {
|
||||
if(itti_create_task(TASK_SCTP, sctp_eNB_task, NULL) < 0){
|
||||
LOG_E(SCTP, "Create task for SCTP failed\n");
|
||||
return -1;
|
||||
}
|
||||
if (is_x2ap_enabled()) {
|
||||
if(itti_create_task(TASK_X2AP, x2ap_task, NULL) < 0){
|
||||
LOG_E(X2AP, "Create task for X2AP failed\n");
|
||||
}
|
||||
}
|
||||
else {
|
||||
LOG_I(X2AP, "X2AP is disabled.\n");
|
||||
}
|
||||
}
|
||||
|
||||
if (AMF_MODE_ENABLED && (get_softmodem_params()->phy_test==0 && get_softmodem_params()->do_ra==0)) {
|
||||
if (gnb_nb > 0) {
|
||||
if (itti_create_task (TASK_NGAP, ngap_gNB_task, NULL) < 0) {
|
||||
LOG_E(S1AP, "Create task for NGAP failed\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
||||
if(!emulate_rf){
|
||||
if (itti_create_task (TASK_UDP, udp_eNB_task, NULL) < 0) {
|
||||
LOG_E(UDP_, "Create task for UDP failed\n");
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
if (itti_create_task (TASK_GTPV1_U, >pv1u_gNB_task, NULL) < 0) {
|
||||
LOG_E(GTPU, "Create task for GTPV1U failed\n");
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if (gnb_nb > 0) {
|
||||
if (itti_create_task (TASK_GNB_APP, gNB_app_task, NULL) < 0) {
|
||||
LOG_E(GNB_APP, "Create task for gNB APP failed\n");
|
||||
return -1;
|
||||
}
|
||||
LOG_I(NR_RRC,"Creating NR RRC gNB Task\n");
|
||||
|
||||
if (itti_create_task (TASK_RRC_GNB, rrc_gnb_task, NULL) < 0) {
|
||||
LOG_E(NR_RRC, "Create task for NR RRC gNB failed\n");
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
static void get_options(void) {
|
||||
|
||||
|
||||
paramdef_t cmdline_params[] = CMDLINE_PARAMS_DESC_GNB ;
|
||||
|
||||
CONFIG_SETRTFLAG(CONFIG_NOEXITONHELP);
|
||||
get_common_options(SOFTMODEM_GNB_BIT );
|
||||
config_process_cmdline( cmdline_params,sizeof(cmdline_params)/sizeof(paramdef_t),NULL);
|
||||
CONFIG_CLEARRTFLAG(CONFIG_NOEXITONHELP);
|
||||
|
||||
|
||||
|
||||
|
||||
if ( !(CONFIG_ISFLAGSET(CONFIG_ABORT)) ) {
|
||||
memset((void *)&RC,0,sizeof(RC));
|
||||
/* Read RC configuration file */
|
||||
NRRCConfig();
|
||||
NB_gNB_INST = RC.nb_nr_inst;
|
||||
NB_RU = RC.nb_RU;
|
||||
printf("Configuration: nb_rrc_inst %d, nb_nr_L1_inst %d, nb_ru %hhu\n",NB_gNB_INST,RC.nb_nr_L1_inst,NB_RU);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
|
||||
void set_default_frame_parms(nfapi_nr_config_request_scf_t *config[MAX_NUM_CCs],
|
||||
NR_DL_FRAME_PARMS *frame_parms[MAX_NUM_CCs])
|
||||
{
|
||||
for (int CC_id=0; CC_id<MAX_NUM_CCs; CC_id++) {
|
||||
frame_parms[CC_id] = (NR_DL_FRAME_PARMS *) malloc(sizeof(NR_DL_FRAME_PARMS));
|
||||
config[CC_id] = (nfapi_nr_config_request_scf_t *) malloc(sizeof(nfapi_nr_config_request_scf_t));
|
||||
config[CC_id]->ssb_config.scs_common.value = 1;
|
||||
config[CC_id]->cell_config.frame_duplex_type.value = 1; //FDD
|
||||
config[CC_id]->carrier_config.dl_grid_size[1].value = 106;
|
||||
config[CC_id]->carrier_config.ul_grid_size[1].value = 106;
|
||||
config[CC_id]->cell_config.phy_cell_id.value = 0;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* helper function to terminate a certain ITTI task
|
||||
*/
|
||||
void terminate_task(task_id_t task_id, module_id_t mod_id) {
|
||||
LOG_I(GNB_APP, "sending TERMINATE_MESSAGE to task %s (%d)\n", itti_get_task_name(task_id), task_id);
|
||||
MessageDef *msg;
|
||||
msg = itti_alloc_new_message (ENB_APP, TERMINATE_MESSAGE);
|
||||
itti_send_msg_to_task (task_id, ENB_MODULE_ID_TO_INSTANCE(mod_id), msg);
|
||||
}
|
||||
|
||||
//extern void free_transport(PHY_VARS_gNB *);
|
||||
extern void nr_phy_free_RU(RU_t *);
|
||||
|
||||
void init_pdcp(void) {
|
||||
//if (!NODE_IS_DU(RC.rrc[0]->node_type)) {
|
||||
pdcp_layer_init();
|
||||
uint32_t pdcp_initmask = (IS_SOFTMODEM_NOS1) ?
|
||||
(PDCP_USE_NETLINK_BIT | LINK_ENB_PDCP_TO_IP_DRIVER_BIT) : LINK_ENB_PDCP_TO_GTPV1U_BIT;
|
||||
|
||||
if (IS_SOFTMODEM_NOS1) {
|
||||
printf("IS_SOFTMODEM_NOS1 option enabled \n");
|
||||
pdcp_initmask = pdcp_initmask | ENB_NAS_USE_TUN_BIT | SOFTMODEM_NOKRNMOD_BIT ;
|
||||
}
|
||||
|
||||
pdcp_module_init(pdcp_initmask);
|
||||
|
||||
pdcp_set_rlc_data_req_func((send_rlc_data_req_func_t) rlc_data_req);
|
||||
pdcp_set_pdcp_data_ind_func((pdcp_data_ind_func_t) pdcp_data_ind);
|
||||
}
|
||||
|
||||
|
||||
int create_tasks_nrue(uint32_t ue_nb) {
|
||||
LOG_D(ENB_APP, "%s(ue_nb:%d)\n", __FUNCTION__, ue_nb);
|
||||
itti_wait_ready(1);
|
||||
|
||||
if (ue_nb > 0) {
|
||||
printf("create TASK_RRC_NRUE\n");
|
||||
if (itti_create_task (TASK_RRC_NRUE, rrc_nrue_task, NULL) < 0) {
|
||||
LOG_E(NR_RRC, "Create task for RRC UE failed\n");
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
itti_wait_ready(0);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
void *itti_sim_ue_rrc_task( void *args_p) {
|
||||
MessageDef *msg_p, *message_p;
|
||||
instance_t instance;
|
||||
unsigned int ue_mod_id;
|
||||
int result;
|
||||
itti_mark_task_ready (TASK_RRC_UE_SIM);
|
||||
|
||||
while(1) {
|
||||
// Wait for a message
|
||||
itti_receive_msg (TASK_RRC_UE_SIM, &msg_p);
|
||||
instance = ITTI_MSG_INSTANCE (msg_p);
|
||||
ue_mod_id = UE_INSTANCE_TO_MODULE_ID(instance);
|
||||
|
||||
switch (ITTI_MSG_ID(msg_p)) {
|
||||
case TERMINATE_MESSAGE:
|
||||
LOG_W(NR_RRC, " *** Exiting RRC thread\n");
|
||||
itti_exit_task ();
|
||||
break;
|
||||
|
||||
case MESSAGE_TEST:
|
||||
LOG_D(NR_RRC, "[UE %d] Received %s\n", ue_mod_id, ITTI_MSG_NAME (msg_p));
|
||||
break;
|
||||
case GNB_RRC_BCCH_DATA_IND:
|
||||
message_p = itti_alloc_new_message (TASK_RRC_NRUE, NR_RRC_MAC_BCCH_DATA_IND);
|
||||
memset (NR_RRC_MAC_BCCH_DATA_IND (message_p).sdu, 0, BCCH_SDU_SIZE);
|
||||
NR_RRC_MAC_BCCH_DATA_IND (message_p).sdu_size = GNB_RRC_BCCH_DATA_IND(msg_p).size;
|
||||
memcpy (NR_RRC_MAC_BCCH_DATA_IND (message_p).sdu, GNB_RRC_BCCH_DATA_IND(msg_p).sdu, GNB_RRC_BCCH_DATA_IND(msg_p).size);
|
||||
itti_send_msg_to_task (TASK_RRC_NRUE, instance, message_p);
|
||||
break;
|
||||
case GNB_RRC_CCCH_DATA_IND:
|
||||
message_p = itti_alloc_new_message (TASK_RRC_NRUE, NR_RRC_MAC_CCCH_DATA_IND);
|
||||
printf("receive GNB_RRC_CCCH_DATA_IND\n");
|
||||
memset (NR_RRC_MAC_CCCH_DATA_IND (message_p).sdu, 0, CCCH_SDU_SIZE);
|
||||
memcpy (NR_RRC_MAC_CCCH_DATA_IND (message_p).sdu, GNB_RRC_CCCH_DATA_IND(msg_p).sdu, GNB_RRC_CCCH_DATA_IND(msg_p).size);
|
||||
NR_RRC_MAC_CCCH_DATA_IND (message_p).sdu_size = GNB_RRC_CCCH_DATA_IND(msg_p).size;
|
||||
itti_send_msg_to_task (TASK_RRC_NRUE, instance, message_p);
|
||||
break;
|
||||
case GNB_RRC_DCCH_DATA_IND:
|
||||
printf("receive GNB_RRC_DCCH_DATA_IND\n");
|
||||
message_p = itti_alloc_new_message (TASK_RRC_NRUE, NR_RRC_DCCH_DATA_IND);
|
||||
NR_RRC_DCCH_DATA_IND (message_p).dcch_index = GNB_RRC_DCCH_DATA_IND(msg_p).rbid;
|
||||
NR_RRC_DCCH_DATA_IND (message_p).sdu_size = GNB_RRC_DCCH_DATA_IND(msg_p).size;
|
||||
NR_RRC_DCCH_DATA_IND (message_p).sdu_p = GNB_RRC_DCCH_DATA_IND(msg_p).sdu;
|
||||
itti_send_msg_to_task (TASK_RRC_NRUE, instance, message_p);
|
||||
break;
|
||||
default:
|
||||
LOG_E(NR_RRC, "[UE %d] Received unexpected message %s\n", ue_mod_id, ITTI_MSG_NAME (msg_p));
|
||||
break;
|
||||
}
|
||||
|
||||
result = itti_free (ITTI_MSG_ORIGIN_ID(msg_p), msg_p);
|
||||
AssertFatal (result == EXIT_SUCCESS, "Failed to free memory (%d)!\n", result);
|
||||
msg_p = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void *itti_sim_gnb_rrc_task( void *args_p) {
|
||||
MessageDef *msg_p, *message_p;
|
||||
instance_t instance;
|
||||
unsigned int ue_mod_id;
|
||||
int result;
|
||||
itti_mark_task_ready (TASK_RRC_GNB_SIM);
|
||||
|
||||
while(1) {
|
||||
// Wait for a message
|
||||
itti_receive_msg (TASK_RRC_GNB_SIM, &msg_p);
|
||||
instance = ITTI_MSG_INSTANCE (msg_p);
|
||||
ue_mod_id = UE_INSTANCE_TO_MODULE_ID(instance);
|
||||
|
||||
switch (ITTI_MSG_ID(msg_p)) {
|
||||
case TERMINATE_MESSAGE:
|
||||
LOG_W(NR_RRC, " *** Exiting RRC thread\n");
|
||||
itti_exit_task ();
|
||||
break;
|
||||
|
||||
case MESSAGE_TEST:
|
||||
LOG_D(NR_RRC, "[UE %d] Received %s\n", ue_mod_id, ITTI_MSG_NAME (msg_p));
|
||||
break;
|
||||
case UE_RRC_CCCH_DATA_IND:
|
||||
message_p = itti_alloc_new_message (TASK_RRC_GNB, NR_RRC_MAC_CCCH_DATA_IND);
|
||||
NR_RRC_MAC_CCCH_DATA_IND (message_p).sdu_size = UE_RRC_CCCH_DATA_IND(msg_p).size;
|
||||
memset (NR_RRC_MAC_CCCH_DATA_IND (message_p).sdu, 0, CCCH_SDU_SIZE);
|
||||
memcpy (NR_RRC_MAC_CCCH_DATA_IND (message_p).sdu, UE_RRC_CCCH_DATA_IND(msg_p).sdu, UE_RRC_CCCH_DATA_IND(msg_p).size);
|
||||
itti_send_msg_to_task (TASK_RRC_GNB, instance, message_p);
|
||||
break;
|
||||
case UE_RRC_DCCH_DATA_IND:
|
||||
message_p = itti_alloc_new_message (TASK_RRC_GNB, NR_RRC_DCCH_DATA_IND);
|
||||
NR_RRC_DCCH_DATA_IND (message_p).sdu_size = UE_RRC_DCCH_DATA_IND(msg_p).size;
|
||||
NR_RRC_DCCH_DATA_IND (message_p).dcch_index = UE_RRC_DCCH_DATA_IND(msg_p).rbid;
|
||||
NR_RRC_DCCH_DATA_IND (message_p).sdu_p = UE_RRC_DCCH_DATA_IND(msg_p).sdu;
|
||||
itti_send_msg_to_task (TASK_RRC_GNB, instance, message_p);
|
||||
break;
|
||||
|
||||
default:
|
||||
LOG_E(NR_RRC, "[UE %d] Received unexpected message %s\n", ue_mod_id, ITTI_MSG_NAME (msg_p));
|
||||
break;
|
||||
}
|
||||
|
||||
result = itti_free (ITTI_MSG_ORIGIN_ID(msg_p), msg_p);
|
||||
AssertFatal (result == EXIT_SUCCESS, "Failed to free memory (%d)!\n", result);
|
||||
msg_p = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
int main( int argc, char **argv )
|
||||
{
|
||||
start_background_system();
|
||||
|
||||
///static configuration for NR at the moment
|
||||
if ( load_configmodule(argc,argv,CONFIG_ENABLECMDLINEONLY) == NULL) {
|
||||
exit_fun("[SOFTMODEM] Error, configuration module init failed\n");
|
||||
}
|
||||
set_softmodem_sighandler();
|
||||
#ifdef DEBUG_CONSOLE
|
||||
setvbuf(stdout, NULL, _IONBF, 0);
|
||||
setvbuf(stderr, NULL, _IONBF, 0);
|
||||
#endif
|
||||
|
||||
logInit();
|
||||
//configure_linux();
|
||||
printf("Reading in command-line options\n");
|
||||
get_options ();
|
||||
|
||||
if (CONFIG_ISFLAGSET(CONFIG_ABORT) ) {
|
||||
fprintf(stderr,"Getting configuration failed\n");
|
||||
exit(-1);
|
||||
}
|
||||
|
||||
// AMF_MODE_ENABLED = !IS_SOFTMODEM_NOS1;
|
||||
AMF_MODE_ENABLED = 0;
|
||||
|
||||
#if T_TRACER
|
||||
T_Config_Init();
|
||||
#endif
|
||||
//randominit (0);
|
||||
set_taus_seed (0);
|
||||
printf("configuring for RAU/RRU\n");
|
||||
|
||||
if (opp_enabled ==1) {
|
||||
reset_opp_meas();
|
||||
}
|
||||
|
||||
cpuf=get_cpu_freq_GHz();
|
||||
itti_init(TASK_MAX, THREAD_MAX, MESSAGES_ID_MAX, tasks_info, messages_info);
|
||||
// initialize mscgen log after ITTI
|
||||
MSC_INIT(MSC_E_UTRAN, THREAD_MAX+TASK_MAX);
|
||||
|
||||
|
||||
init_opt();
|
||||
|
||||
LOG_I(HW, "Version: %s\n", PACKAGE_VERSION);
|
||||
|
||||
if(IS_SOFTMODEM_NOS1)
|
||||
init_pdcp();
|
||||
|
||||
if (RC.nb_nr_inst > 0) {
|
||||
// don't create if node doesn't connect to RRC/S1/GTP
|
||||
AssertFatal(create_gNB_tasks(1) == 0,"cannot create ITTI tasks\n");
|
||||
} else {
|
||||
printf("No ITTI, Initializing L1\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if(itti_create_task (TASK_RRC_GNB_SIM, itti_sim_gnb_rrc_task, NULL) < 0){
|
||||
printf("cannot create ITTI tasks\n");
|
||||
exit(-1); // need a softer mode
|
||||
}
|
||||
|
||||
openair_rrc_top_init_ue_nr("./");
|
||||
|
||||
if (create_tasks_nrue(1) < 0) {
|
||||
printf("cannot create ITTI tasks\n");
|
||||
exit(-1); // need a softer mode
|
||||
}
|
||||
|
||||
if(itti_create_task (TASK_RRC_UE_SIM, itti_sim_ue_rrc_task, NULL) < 0){
|
||||
printf("cannot create ITTI tasks\n");
|
||||
exit(-1); // need a softer mode
|
||||
}
|
||||
|
||||
pthread_cond_init(&sync_cond,NULL);
|
||||
pthread_mutex_init(&sync_mutex, NULL);
|
||||
|
||||
printf("Sending sync to all threads\n");
|
||||
pthread_mutex_lock(&sync_mutex);
|
||||
sync_var=0;
|
||||
pthread_cond_broadcast(&sync_cond);
|
||||
pthread_mutex_unlock(&sync_mutex);
|
||||
// wait for end of program
|
||||
printf("TYPE <CTRL-C> TO TERMINATE\n");
|
||||
|
||||
usleep(100000);
|
||||
protocol_ctxt_t ctxt;
|
||||
struct rrc_gNB_ue_context_s *ue_context_p = NULL;
|
||||
|
||||
|
||||
ue_context_p = rrc_gNB_allocate_new_UE_context(RC.nrrrc[0]);
|
||||
|
||||
if(ue_context_p == NULL){
|
||||
printf("ue_context_p == NULL");
|
||||
}
|
||||
PROTOCOL_CTXT_SET_BY_INSTANCE(&ctxt,
|
||||
0,
|
||||
ENB_FLAG_YES,
|
||||
0,
|
||||
0,
|
||||
0);
|
||||
NR_UE_rrc_inst[ctxt.module_id].Info[0].State = RRC_SI_RECEIVED;
|
||||
|
||||
rrc_ue_generate_RRCSetupRequest(&ctxt, 0);
|
||||
|
||||
printf("Entering ITTI signals handler\n");
|
||||
itti_wait_tasks_end();
|
||||
printf("Returned from ITTI signal handler\n");
|
||||
oai_exit=1;
|
||||
printf("oai_exit=%d\n",oai_exit);
|
||||
|
||||
printf("stopping MODEM threads\n");
|
||||
|
||||
|
||||
/* release memory used by the RU/gNB threads (incomplete), after all
|
||||
* threads have been stopped (they partially use the same memory) */
|
||||
|
||||
pthread_cond_destroy(&sync_cond);
|
||||
pthread_mutex_destroy(&sync_mutex);
|
||||
|
||||
logClean();
|
||||
printf("Bye.\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -39,6 +39,7 @@
|
||||
#include "udp_messages_types.h"
|
||||
#include "mme_app_messages_types.h"
|
||||
#include "m2ap_messages_types.h"
|
||||
#include "ngap_messages_types.h"
|
||||
|
||||
|
||||
#endif /* MESSAGES_TYPES_H_ */
|
||||
|
||||
94
openair3/NAS/COMMON/EMM/MSG/RegistrationRequest.c
Normal file
94
openair3/NAS/COMMON/EMM/MSG/RegistrationRequest.c
Normal file
@@ -0,0 +1,94 @@
|
||||
/*! \file RegistrationRequest.c
|
||||
|
||||
\brief registration request procedures for gNB
|
||||
\author Yoshio INOUE, Masayuki HARADA
|
||||
\email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com
|
||||
\date 2020
|
||||
\version 0.1
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include "nas_log.h"
|
||||
|
||||
#include "RegistrationRequest.h"
|
||||
|
||||
int decode_registration_request(registration_request_msg *registration_request, uint8_t *buffer, uint32_t len)
|
||||
{
|
||||
uint32_t decoded = 0;
|
||||
int decoded_result = 0;
|
||||
|
||||
LOG_FUNC_IN;
|
||||
LOG_TRACE(INFO, "EMM - registration_request len = %d",
|
||||
len);
|
||||
|
||||
/* Decoding mandatory fields */
|
||||
if ((decoded_result = decode_5gs_registration_type(®istration_request->fgsregistrationtype, 0, *(buffer + decoded) & 0x0f, len - decoded)) < 0) {
|
||||
// return decoded_result;
|
||||
LOG_FUNC_RETURN(decoded_result);
|
||||
}
|
||||
|
||||
if ((decoded_result = decode_u8_nas_key_set_identifier(®istration_request->naskeysetidentifier, 0, *(buffer + decoded) >> 4, len - decoded)) < 0) {
|
||||
// return decoded_result;
|
||||
LOG_FUNC_RETURN(decoded_result);
|
||||
}
|
||||
|
||||
decoded++;
|
||||
|
||||
if ((decoded_result = decode_5gs_mobile_identity(®istration_request->fgsmobileidentity, 0, buffer + decoded, len - decoded)) < 0) {
|
||||
// return decoded_result;
|
||||
LOG_FUNC_RETURN(decoded_result);
|
||||
} else
|
||||
decoded += decoded_result;
|
||||
|
||||
|
||||
// TODO, Decoding optional fields
|
||||
|
||||
return decoded;
|
||||
}
|
||||
|
||||
int encode_registration_request(registration_request_msg *registration_request, uint8_t *buffer, uint32_t len)
|
||||
{
|
||||
int encoded = 0;
|
||||
int encode_result = 0;
|
||||
|
||||
*(buffer + encoded) = ((encode_u8_nas_key_set_identifier(®istration_request->naskeysetidentifier) & 0x0f) << 4) | (encode_5gs_registration_type(®istration_request->fgsregistrationtype) & 0x0f);
|
||||
encoded++;
|
||||
|
||||
if ((encode_result =
|
||||
encode_5gs_mobile_identity(®istration_request->fgsmobileidentity, 0, buffer +
|
||||
encoded, len - encoded)) < 0) //Return in case of error
|
||||
return encode_result;
|
||||
else
|
||||
encoded += encode_result;
|
||||
|
||||
if ((registration_request->presencemask & REGISTRATION_REQUEST_5GMM_CAPABILITY_PRESENT)
|
||||
== REGISTRATION_REQUEST_5GMM_CAPABILITY_PRESENT) {
|
||||
if ((encode_result = encode_5gmm_capability(®istration_request->fgmmcapability,
|
||||
REGISTRATION_REQUEST_5GMM_CAPABILITY_IEI, buffer + encoded, len -
|
||||
encoded)) < 0)
|
||||
// Return in case of error
|
||||
return encode_result;
|
||||
else
|
||||
encoded += encode_result;
|
||||
}
|
||||
|
||||
if ((registration_request->presencemask & REGISTRATION_REQUEST_UE_SECURITY_CAPABILITY_PRESENT)
|
||||
== REGISTRATION_REQUEST_UE_SECURITY_CAPABILITY_PRESENT) {
|
||||
if ((encode_result = encode_nrue_security_capability(®istration_request->nruesecuritycapability,
|
||||
REGISTRATION_REQUEST_UE_SECURITY_CAPABILITY_IEI, buffer + encoded, len -
|
||||
encoded)) < 0)
|
||||
// Return in case of error
|
||||
return encode_result;
|
||||
else
|
||||
encoded += encode_result;
|
||||
}
|
||||
|
||||
|
||||
// TODO, Encoding optional fields
|
||||
return encoded;
|
||||
}
|
||||
|
||||
104
openair3/NAS/COMMON/EMM/MSG/RegistrationRequest.h
Normal file
104
openair3/NAS/COMMON/EMM/MSG/RegistrationRequest.h
Normal file
@@ -0,0 +1,104 @@
|
||||
/*! \file RegistrationRequest.h
|
||||
|
||||
\brief registration request procedures for gNB
|
||||
\author Yoshio INOUE, Masayuki HARADA
|
||||
\email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com
|
||||
\date 2020
|
||||
\version 0.1
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include "ExtendedProtocolDiscriminator.h"
|
||||
#include "SecurityHeaderType.h"
|
||||
#include "SpareHalfOctet.h"
|
||||
#include "FGSMobileIdentity.h"
|
||||
#include "NasKeySetIdentifier.h"
|
||||
#include "FGSRegistrationType.h"
|
||||
#include "MessageType.h"
|
||||
#include "FGMMCapability.h"
|
||||
#include "NrUESecurityCapability.h"
|
||||
|
||||
#ifndef REGISTRATION_REQUEST_H_
|
||||
#define REGISTRATION_REQUEST_H_
|
||||
|
||||
|
||||
# define REGISTRATION_REQUEST_NON_CURRENT_NATIVE_NAS_KEYSET_PRESENT (1<<0)
|
||||
# define REGISTRATION_REQUEST_5GMM_CAPABILITY_PRESENT (1<<1)
|
||||
# define REGISTRATION_REQUEST_UE_SECURITY_CAPABILITY_PRESENT (1<<2)
|
||||
# define REGISTRATION_REQUEST_REQUESTED_NSSAI_PRESENT (1<<3)
|
||||
# define REGISTRATION_REQUEST_LAST_VISITED_REGISTERED_TAI_PRESENT (1<<4)
|
||||
# define REGISTRATION_REQUEST_S1_UE_NETWORK_CAPABILITY_PRESENT (1<<5)
|
||||
# define REGISTRATION_REQUEST_UPLINK_DATA_STATUS_PRESENT (1<<6)
|
||||
# define REGISTRATION_REQUEST_PDU_SESSION_STATUS_PRESENT (1<<7)
|
||||
# define REGISTRATION_REQUEST_MICO_INDICATION_PRESENT (1<<8)
|
||||
# define REGISTRATION_REQUEST_UE_STATUS_PRESENT (1<<9)
|
||||
# define REGISTRATION_REQUEST_ADDITIONAL_GUTI_PRESENT (1<<10)
|
||||
# define REGISTRATION_REQUEST_ALLOWED_PDU_SESSION_STATUS_PRESENT (1<<11)
|
||||
# define REGISTRATION_REQUEST_UE_USAGE_SETTING_PRESENT (1<<12)
|
||||
# define REGISTRATION_REQUEST_REQUESTED_DRX_PARAMETERS_PRESENT (1<<13)
|
||||
# define REGISTRATION_REQUEST_EPS_NAS_MESSAGE_CONTAINER_PRESENT (1<<14)
|
||||
# define REGISTRATION_REQUEST_LADN_INDICATION_PRESENT (1<<15)
|
||||
# define REGISTRATION_REQUEST_PAYLOAD_CONTAINER_TYPE_PRESENT (1<<16)
|
||||
# define REGISTRATION_REQUEST_PAYLOAD_CONTAINER_PRESENT (1<<17)
|
||||
# define REGISTRATION_REQUEST_NETWORK_SLICING_INDICATION_PRESENT (1<<18)
|
||||
# define REGISTRATION_REQUEST_5GS_UPDATE_TYPE_PRESENT (1<<19)
|
||||
# define REGISTRATION_REQUEST_NAS_MESSAGE_CONTAINER_PRESENT (1<<20)
|
||||
# define REGISTRATION_REQUEST_EPS_BEARER_CONTEXT_STATUS_PRESENT (1<<21)
|
||||
|
||||
typedef enum registration_request_iei_tag {
|
||||
REGISTRATION_REQUEST_NON_CURRENT_NATIVE_NAS_KEYSET_IEI = 0xC0, /* 0xC- = 192- */
|
||||
REGISTRATION_REQUEST_5GMM_CAPABILITY_IEI = 0x10, /* 0x10 = 16 */
|
||||
REGISTRATION_REQUEST_UE_SECURITY_CAPABILITY_IEI = 0x2E, /* 0x2E = 46 */
|
||||
REGISTRATION_REQUEST_REQUESTED_NSSAI_IEI = 0x2F, /* 0x2F = 47 */
|
||||
REGISTRATION_REQUEST_LAST_VISITED_REGISTERED_TAI_IEI = 0x52, /* 0x52 = 82 */
|
||||
REGISTRATION_REQUEST_S1_UE_NETWORK_CAPABILITY_IEI = 0x17, /* 0x17 = 23 */
|
||||
REGISTRATION_REQUEST_UPLINK_DATA_STATUS_IEI = 0x40, /* 0x40 = 64 */
|
||||
REGISTRATION_REQUEST_PDU_SESSION_STATUS_IEI = 0x50, /* 0x50 = 80 */
|
||||
REGISTRATION_REQUEST_MICO_INDICATION_IEI = 0xB0, /* 0xB- = 176- */
|
||||
REGISTRATION_REQUEST_UE_STATUS_IEI = 0x2B, /* 0x2B = 43 */
|
||||
REGISTRATION_REQUEST_ADDITIONAL_GUTI_IEI = 0x77, /* 0x77 = 119 */
|
||||
REGISTRATION_REQUEST_ALLOWED_PDU_SESSION_STATUS_IEI = 0x25, /* 0x25 = 37 */
|
||||
REGISTRATION_REQUEST_UE_USAGE_SETTING_IEI = 0x18, /* 0x18 = 24 */
|
||||
REGISTRATION_REQUEST_REQUESTED_DRX_PARAMETERS_IEI = 0x51, /* 0x51 = 81 */
|
||||
REGISTRATION_REQUEST_EPS_NAS_MESSAGE_CONTAINER_IEI = 0x70, /* 0x70 = 112 */
|
||||
REGISTRATION_REQUEST_LADN_INDICATION_IEI = 0x74, /* 0x74 = 116 */
|
||||
REGISTRATION_REQUEST_PAYLOAD_CONTAINER_TYPE_IEI = 0x80, /* 0x80 = 128 */
|
||||
REGISTRATION_REQUEST_PAYLOAD_CONTAINER_IEI = 0x7B, /* 0x7B = 123 */
|
||||
REGISTRATION_REQUEST_NETWORK_SLICING_INDICATION_IEI = 0x90, /* 0x90 = 144 */
|
||||
REGISTRATION_REQUEST_5GS_UPDATE_TYPE_IEI = 0x53, /* 0x53 = 83 */
|
||||
REGISTRATION_REQUEST_NAS_MESSAGE_CONTAINER_IEI = 0x71, /* 0x71 = 113 */
|
||||
REGISTRATION_REQUEST_EPS_BEARER_CONTEXT_STATUS_IEI = 0x60 /* 0x60 = 96 */
|
||||
} registration_request_iei;
|
||||
|
||||
/*
|
||||
* Message name: Registration request
|
||||
* Description: This message is sent by the UE to the AMF. See TS24.501 table 8.2.6.1.1.
|
||||
* Significance: dual
|
||||
* Direction: UE to network
|
||||
*/
|
||||
|
||||
typedef struct registration_request_msg_tag {
|
||||
/* Mandatory fields */
|
||||
ExtendedProtocolDiscriminator protocoldiscriminator;
|
||||
SecurityHeaderType securityheadertype:4;
|
||||
SpareHalfOctet sparehalfoctet:4;
|
||||
MessageType messagetype;
|
||||
FGSRegistrationType fgsregistrationtype;
|
||||
NasKeySetIdentifier naskeysetidentifier;
|
||||
FGSMobileIdentity fgsmobileidentity;
|
||||
|
||||
/* Optional fields */
|
||||
uint32_t presencemask;
|
||||
FGMMCapability fgmmcapability;
|
||||
NrUESecurityCapability nruesecuritycapability;
|
||||
} registration_request_msg;
|
||||
|
||||
int decode_registration_request(registration_request_msg *registrationrequest, uint8_t *buffer, uint32_t len);
|
||||
|
||||
int encode_registration_request(registration_request_msg *registrationrequest, uint8_t *buffer, uint32_t len);
|
||||
|
||||
#endif /* ! defined(REGISTRATION_REQUEST_H_) */
|
||||
|
||||
28
openair3/NAS/COMMON/IES/ExtendedProtocolDiscriminator.c
Normal file
28
openair3/NAS/COMMON/IES/ExtendedProtocolDiscriminator.c
Normal file
@@ -0,0 +1,28 @@
|
||||
/*! \file ExtendedProtocolDiscriminator.c
|
||||
|
||||
\brief Extended protocol discriminator for registration request procedures
|
||||
\author Yoshio INOUE, Masayuki HARADA
|
||||
\email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com
|
||||
\date 2020
|
||||
\version 0.1
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdint.h>
|
||||
|
||||
|
||||
#include "TLVEncoder.h"
|
||||
#include "TLVDecoder.h"
|
||||
#include "ExtendedProtocolDiscriminator.h"
|
||||
|
||||
int encode_ex_protocol_discriminator(ExtendedProtocolDiscriminator *exprotocoldiscriminator, uint8_t iei, uint8_t *buffer, uint32_t len)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
int decode_ex_protocol_discriminator(ExtendedProtocolDiscriminator *exprotocoldiscriminator, uint8_t iei, uint8_t *buffer, uint32_t len)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
26
openair3/NAS/COMMON/IES/ExtendedProtocolDiscriminator.h
Normal file
26
openair3/NAS/COMMON/IES/ExtendedProtocolDiscriminator.h
Normal file
@@ -0,0 +1,26 @@
|
||||
/*! \file ExtendedProtocolDiscriminator.h
|
||||
|
||||
\brief Extended protocol discriminator for registration request procedures
|
||||
\author Yoshio INOUE, Masayuki HARADA
|
||||
\email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com
|
||||
\date 2020
|
||||
\version 0.1
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include "OctetString.h"
|
||||
|
||||
#ifndef EXTENDED_PROTOCOL_DISCRIMINATOR_H_
|
||||
#define EXTENDED_PROTOCOL_DISCRIMINATOR_H_
|
||||
|
||||
typedef uint8_t ExtendedProtocolDiscriminator;
|
||||
|
||||
int encode_ex_protocol_discriminator(ExtendedProtocolDiscriminator *exprotocoldiscriminator, uint8_t iei, uint8_t *buffer, uint32_t len);
|
||||
|
||||
int decode_ex_protocol_discriminator(ExtendedProtocolDiscriminator *exprotocoldiscriminator, uint8_t iei, uint8_t *buffer, uint32_t len);
|
||||
|
||||
#endif /* EXTENDED PROTOCOL DISCRIMINATOR_H_ */
|
||||
|
||||
34
openair3/NAS/COMMON/IES/FGMMCapability.c
Normal file
34
openair3/NAS/COMMON/IES/FGMMCapability.c
Normal file
@@ -0,0 +1,34 @@
|
||||
/*! \file FGSMobileIdentity.c
|
||||
|
||||
\brief 5GS Mobile Identity for registration request procedures
|
||||
\author Yoshio INOUE, Masayuki HARADA
|
||||
\email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com
|
||||
\date 2020
|
||||
\version 0.1
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdint.h>
|
||||
|
||||
|
||||
#include "TLVEncoder.h"
|
||||
#include "TLVDecoder.h"
|
||||
#include "FGMMCapability.h"
|
||||
|
||||
|
||||
|
||||
int encode_5gmm_capability(FGMMCapability *fgmmcapability, uint8_t iei, uint8_t *buffer, uint32_t len)
|
||||
{
|
||||
int encoded = 0;
|
||||
if(iei){
|
||||
*buffer = fgmmcapability->iei;
|
||||
encoded++;
|
||||
*(buffer+encoded) = fgmmcapability->length;
|
||||
encoded++;
|
||||
*(buffer+encoded) = fgmmcapability->value;
|
||||
encoded++;
|
||||
}
|
||||
return encoded;
|
||||
}
|
||||
|
||||
30
openair3/NAS/COMMON/IES/FGMMCapability.h
Normal file
30
openair3/NAS/COMMON/IES/FGMMCapability.h
Normal file
@@ -0,0 +1,30 @@
|
||||
/*! \file FGSMobileIdentity.h
|
||||
|
||||
\brief 5GS Mobile Identity for registration request procedures
|
||||
\author Yoshio INOUE, Masayuki HARADA
|
||||
\email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com
|
||||
\date 2020
|
||||
\version 0.1
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include "OctetString.h"
|
||||
|
||||
#ifndef FGMM_CAPABILITY_H_
|
||||
#define FGMM_CAPABILITY_H_
|
||||
|
||||
|
||||
typedef struct {
|
||||
uint8_t iei;
|
||||
uint8_t length;
|
||||
uint8_t value;
|
||||
} FGMMCapability;
|
||||
|
||||
|
||||
int encode_5gmm_capability(FGMMCapability *fgmmcapability, uint8_t iei, uint8_t *buffer, uint32_t len);
|
||||
|
||||
#endif /* FGMM_CAPABILITY_H_ */
|
||||
|
||||
154
openair3/NAS/COMMON/IES/FGSMobileIdentity.c
Normal file
154
openair3/NAS/COMMON/IES/FGSMobileIdentity.c
Normal file
@@ -0,0 +1,154 @@
|
||||
/*! \file FGSMobileIdentity.c
|
||||
|
||||
\brief 5GS Mobile Identity for registration request procedures
|
||||
\author Yoshio INOUE, Masayuki HARADA
|
||||
\email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com
|
||||
\date 2020
|
||||
\version 0.1
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdint.h>
|
||||
|
||||
|
||||
#include "TLVEncoder.h"
|
||||
#include "TLVDecoder.h"
|
||||
#include "FGSMobileIdentity.h"
|
||||
|
||||
static int decode_guti_5gs_mobile_identity(Guti5GSMobileIdentity_t *guti, uint8_t *buffer);
|
||||
|
||||
static int encode_guti_5gs_mobile_identity(Guti5GSMobileIdentity_t *guti, uint8_t *buffer);
|
||||
|
||||
int decode_5gs_mobile_identity(FGSMobileIdentity *fgsmobileidentity, uint8_t iei, uint8_t *buffer, uint32_t len)
|
||||
{
|
||||
int decoded_rc = TLV_DECODE_VALUE_DOESNT_MATCH;
|
||||
int decoded = 0;
|
||||
uint8_t ielen = 0;
|
||||
|
||||
if (iei > 0) {
|
||||
CHECK_IEI_DECODER(iei, *buffer);
|
||||
decoded++;
|
||||
}
|
||||
|
||||
ielen = *(buffer + decoded);
|
||||
decoded++;
|
||||
CHECK_LENGTH_DECODER(len - decoded, ielen);
|
||||
|
||||
uint8_t typeofidentity = *(buffer + decoded) & 0x7;
|
||||
|
||||
if (typeofidentity == FGS_MOBILE_IDENTITY_5G_GUTI) {
|
||||
decoded_rc = decode_guti_5gs_mobile_identity(&fgsmobileidentity->guti,
|
||||
buffer + decoded);
|
||||
}
|
||||
|
||||
if (decoded_rc < 0) {
|
||||
return decoded_rc;
|
||||
}
|
||||
|
||||
return (decoded + decoded_rc);
|
||||
}
|
||||
|
||||
int encode_5gs_mobile_identity(FGSMobileIdentity *fgsmobileidentity, uint8_t iei, uint8_t *buffer, uint32_t len)
|
||||
{
|
||||
int encoded_rc = TLV_ENCODE_VALUE_DOESNT_MATCH;
|
||||
uint32_t encoded = 0;
|
||||
|
||||
if (iei > 0) {
|
||||
*buffer = iei;
|
||||
encoded++;
|
||||
}
|
||||
|
||||
encoded = encoded + 2;
|
||||
|
||||
if (fgsmobileidentity->guti.typeofidentity == FGS_MOBILE_IDENTITY_5G_GUTI) {
|
||||
encoded_rc = encode_guti_5gs_mobile_identity(&fgsmobileidentity->guti,
|
||||
buffer + encoded);
|
||||
}
|
||||
|
||||
if (encoded_rc < 0) {
|
||||
return encoded_rc;
|
||||
}
|
||||
|
||||
*(uint16_t*) buffer = htons(encoded + encoded_rc - 2 - ((iei > 0) ? 1 : 0));
|
||||
return (encoded + encoded_rc);
|
||||
}
|
||||
|
||||
static int decode_guti_5gs_mobile_identity(Guti5GSMobileIdentity_t *guti, uint8_t *buffer)
|
||||
{
|
||||
int decoded = 0;
|
||||
uint16_t temp;
|
||||
guti->spare = (*(buffer + decoded) >> 4) & 0xf;
|
||||
|
||||
/*
|
||||
* For the 5G-GUTI, bits 5 to 8 of octet 3 are coded as "1111"
|
||||
*/
|
||||
if (guti->spare != 0xf) {
|
||||
return (TLV_ENCODE_VALUE_DOESNT_MATCH);
|
||||
}
|
||||
|
||||
|
||||
guti->oddeven = (*(buffer + decoded) >> 3) & 0x1;
|
||||
|
||||
/*
|
||||
* For the 5G-GUTI, bits 4 of octet 3 are coded as "0"
|
||||
*/
|
||||
if (guti->oddeven != 0) {
|
||||
return (TLV_ENCODE_VALUE_DOESNT_MATCH);
|
||||
}
|
||||
guti->typeofidentity = *(buffer + decoded) & 0x7;
|
||||
|
||||
if (guti->typeofidentity != FGS_MOBILE_IDENTITY_5G_GUTI) {
|
||||
return (TLV_ENCODE_VALUE_DOESNT_MATCH);
|
||||
}
|
||||
|
||||
decoded++;
|
||||
guti->mccdigit2 = (*(buffer + decoded) >> 4) & 0xf;
|
||||
guti->mccdigit1 = *(buffer + decoded) & 0xf;
|
||||
decoded++;
|
||||
guti->mncdigit3 = (*(buffer + decoded) >> 4) & 0xf;
|
||||
guti->mccdigit3 = *(buffer + decoded) & 0xf;
|
||||
decoded++;
|
||||
guti->mncdigit2 = (*(buffer + decoded) >> 4) & 0xf;
|
||||
guti->mncdigit1 = *(buffer + decoded) & 0xf;
|
||||
decoded++;
|
||||
|
||||
|
||||
guti->amfregionid = *(buffer+decoded);
|
||||
decoded++;
|
||||
IES_DECODE_U16(buffer, decoded, temp);
|
||||
guti->amfsetid = temp>>3;
|
||||
guti->amfpointer = temp&0x3f;
|
||||
|
||||
IES_DECODE_U32(buffer, decoded, guti->tmsi);
|
||||
return decoded;
|
||||
}
|
||||
|
||||
|
||||
static int encode_guti_5gs_mobile_identity(Guti5GSMobileIdentity_t *guti, uint8_t *buffer)
|
||||
{
|
||||
uint32_t encoded = 0;
|
||||
uint16_t temp;
|
||||
*(buffer + encoded) = 0xf0 | ((guti->oddeven & 0x1) << 3) |
|
||||
(guti->typeofidentity & 0x7);
|
||||
encoded++;
|
||||
*(buffer + encoded) = 0x00 | ((guti->mccdigit2 & 0xf) << 4) |
|
||||
(guti->mccdigit1 & 0xf);
|
||||
encoded++;
|
||||
*(buffer + encoded) = 0x00 | ((guti->mncdigit3 & 0xf) << 4) |
|
||||
(guti->mccdigit3 & 0xf);
|
||||
encoded++;
|
||||
*(buffer + encoded) = 0x00 | ((guti->mncdigit2 & 0xf) << 4) |
|
||||
(guti->mncdigit1 & 0xf);
|
||||
encoded++;
|
||||
|
||||
*(buffer + encoded) = guti->amfregionid;
|
||||
encoded++;
|
||||
|
||||
temp = 0x00 | ((guti->amfsetid & 0x3f) << 6) | (guti->amfpointer & 0x3f);
|
||||
|
||||
IES_ENCODE_U16(buffer, encoded, temp);
|
||||
IES_ENCODE_U32(buffer, encoded, guti->tmsi);
|
||||
return encoded;
|
||||
}
|
||||
|
||||
113
openair3/NAS/COMMON/IES/FGSMobileIdentity.h
Normal file
113
openair3/NAS/COMMON/IES/FGSMobileIdentity.h
Normal file
@@ -0,0 +1,113 @@
|
||||
/*! \file FGSMobileIdentity.h
|
||||
|
||||
\brief 5GS Mobile Identity for registration request procedures
|
||||
\author Yoshio INOUE, Masayuki HARADA
|
||||
\email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com
|
||||
\date 2020
|
||||
\version 0.1
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include "OctetString.h"
|
||||
|
||||
#ifndef FGS_MOBILE_IDENTITY_H_
|
||||
#define FGS_MOBILE_IDENTITY_H_
|
||||
|
||||
|
||||
typedef struct {
|
||||
uint8_t spare:5;
|
||||
uint8_t typeofidentity:3;
|
||||
} NoIdentity5GSMobileIdentity_t;
|
||||
|
||||
typedef struct {
|
||||
uint8_t spare1:1;
|
||||
uint8_t supiformat:3;
|
||||
uint8_t spare2:1;
|
||||
uint8_t typeofidentity:3;
|
||||
uint8_t mccdigit2:4;
|
||||
uint8_t mccdigit1:4;
|
||||
uint8_t mncdigit3:4;
|
||||
uint8_t mccdigit3:4;
|
||||
uint8_t mncdigit2:4;
|
||||
uint8_t mncdigit1:4;
|
||||
uint8_t routingindicatordigit2:4;
|
||||
uint8_t routingindicatordigit1:4;
|
||||
uint8_t routingindicatordigit4:4;
|
||||
uint8_t routingindicatordigit3:4;
|
||||
uint8_t spare3:1;
|
||||
uint8_t spare4:1;
|
||||
uint8_t spare5:1;
|
||||
uint8_t spare6:1;
|
||||
uint8_t protectionschemeId:4;
|
||||
uint8_t homenetworkpki;
|
||||
} Suci5GSMobileIdentity_t;
|
||||
|
||||
typedef struct {
|
||||
uint8_t spare:4;
|
||||
uint8_t oddeven:1;
|
||||
uint8_t typeofidentity:3;
|
||||
uint8_t mccdigit2:4;
|
||||
uint8_t mccdigit1:4;
|
||||
uint8_t mncdigit3:4;
|
||||
uint8_t mccdigit3:4;
|
||||
uint8_t mncdigit2:4;
|
||||
uint8_t mncdigit1:4;
|
||||
uint8_t amfregionid;
|
||||
uint16_t amfsetid:10;
|
||||
uint16_t amfpointer:6;
|
||||
uint32_t tmsi;
|
||||
} Guti5GSMobileIdentity_t;
|
||||
|
||||
|
||||
typedef struct {
|
||||
uint8_t digit1:4;
|
||||
uint8_t oddeven:1;
|
||||
uint8_t typeofidentity:3;
|
||||
uint8_t digitp1:4;
|
||||
uint8_t digitp:4;
|
||||
} Imei5GSMobileIdentity_t;
|
||||
|
||||
typedef Imei5GSMobileIdentity_t Imeisv5GSMobileIdentity_t;
|
||||
|
||||
|
||||
typedef struct {
|
||||
uint8_t digit1:4;
|
||||
uint8_t spare:1;
|
||||
uint8_t typeofidentity:3;
|
||||
uint16_t amfsetid:10;
|
||||
uint16_t amfpointer:6;
|
||||
uint32_t tmsi;
|
||||
} Stmsi5GSMobileIdentity_t;
|
||||
|
||||
typedef struct {
|
||||
uint8_t spare:5;
|
||||
uint8_t typeofidentity:3;
|
||||
uint8_t macaddr;
|
||||
} Macaddr5GSMobileIdentity_t;
|
||||
|
||||
typedef union FGSMobileIdentity_tag {
|
||||
#define FGS_MOBILE_IDENTITY_NOIDENTITY 0b000
|
||||
#define FGS_MOBILE_IDENTITY_SUCI 0b001
|
||||
#define FGS_MOBILE_IDENTITY_5G_GUTI 0b010
|
||||
#define FGS_MOBILE_IDENTITY_IMEI 0b011
|
||||
#define FGS_MOBILE_IDENTITY_5GS_TMSI 0b100
|
||||
#define FGS_MOBILE_IDENTITY_IMEISV 0b101
|
||||
#define FGS_MOBILE_IDENTITY_MAC_ADDR 0b110
|
||||
NoIdentity5GSMobileIdentity_t noidentity;
|
||||
Suci5GSMobileIdentity_t suci;
|
||||
Guti5GSMobileIdentity_t guti;
|
||||
Imei5GSMobileIdentity_t imei;
|
||||
Stmsi5GSMobileIdentity_t stmsi;
|
||||
Imeisv5GSMobileIdentity_t imeisv;
|
||||
Macaddr5GSMobileIdentity_t macaddress;
|
||||
} FGSMobileIdentity;
|
||||
|
||||
int encode_5gs_mobile_identity(FGSMobileIdentity *fgsmobileidentity, uint8_t iei, uint8_t *buffer, uint32_t len);
|
||||
|
||||
int decode_5gs_mobile_identity(FGSMobileIdentity *fgsmobileidentity, uint8_t iei, uint8_t *buffer, uint32_t len);
|
||||
|
||||
#endif /* FGS MOBILE IDENTITY_H_ */
|
||||
|
||||
44
openair3/NAS/COMMON/IES/FGSRegistrationType.c
Normal file
44
openair3/NAS/COMMON/IES/FGSRegistrationType.c
Normal file
@@ -0,0 +1,44 @@
|
||||
/*! \file FGSRegistrationType.c
|
||||
|
||||
\brief 5GS Registration Type for registration request procedures
|
||||
\author Yoshio INOUE, Masayuki HARADA
|
||||
\email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com
|
||||
\date 2020
|
||||
\version 0.1
|
||||
*/
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdint.h>
|
||||
|
||||
|
||||
#include "TLVEncoder.h"
|
||||
#include "TLVDecoder.h"
|
||||
#include "FGSRegistrationType.h"
|
||||
|
||||
int decode_5gs_registration_type(FGSRegistrationType *fgsregistrationtype, uint8_t iei, uint8_t value, uint32_t len)
|
||||
{
|
||||
int decoded = 0;
|
||||
uint8_t *buffer = &value;
|
||||
if (iei > 0) {
|
||||
CHECK_IEI_DECODER((*buffer & 0xf0), iei);
|
||||
}
|
||||
|
||||
*fgsregistrationtype = *buffer & 0x7;
|
||||
decoded++;
|
||||
|
||||
return decoded;
|
||||
}
|
||||
|
||||
int encode_5gs_registration_type(FGSRegistrationType *fgsregistrationtype)
|
||||
{
|
||||
uint8_t bufferReturn;
|
||||
uint8_t *buffer = &bufferReturn;
|
||||
uint8_t encoded = 0;
|
||||
uint8_t iei = 0;
|
||||
*(buffer + encoded) = 0x00 | (iei & 0xf0) | 0x8|
|
||||
(*fgsregistrationtype & 0x7);
|
||||
encoded++;
|
||||
|
||||
return bufferReturn;
|
||||
}
|
||||
|
||||
35
openair3/NAS/COMMON/IES/FGSRegistrationType.h
Normal file
35
openair3/NAS/COMMON/IES/FGSRegistrationType.h
Normal file
@@ -0,0 +1,35 @@
|
||||
/*! \file FGSRegistrationType.h
|
||||
|
||||
\brief 5GS Registration Type for registration request procedures
|
||||
\author Yoshio INOUE, Masayuki HARADA
|
||||
\email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com
|
||||
\date 2020
|
||||
\version 0.1
|
||||
*/
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include "OctetString.h"
|
||||
|
||||
#ifndef FGS_REGISTRATION_TYPE_H_
|
||||
#define FGS_REGISTRATION_TYPE_H_
|
||||
|
||||
#define FGS_REGISTRATION_TYPE_MINIMUM_LENGTH 1
|
||||
#define FGS_REGISTRATION_TYPE_MAXIMUM_LENGTH 1
|
||||
|
||||
typedef uint8_t FGSRegistrationType;
|
||||
|
||||
|
||||
#define INITIAL_REGISTRATION 0b001
|
||||
#define MOBILITY_REGISTRATION_UPDATING 0b010
|
||||
#define PERIODIC_REGISTRATION_UPDATING 0b011
|
||||
#define EMERGENCY_REGISTRATION 0b100
|
||||
|
||||
int encode_5gs_registration_type(FGSRegistrationType *fgsregistrationtype);
|
||||
|
||||
int decode_5gs_registration_type(FGSRegistrationType *fgsregistrationtype, uint8_t iei, uint8_t value, uint32_t len);
|
||||
|
||||
|
||||
#endif /* FGS_REGISTRATION_TYPE_H_*/
|
||||
|
||||
42
openair3/NAS/COMMON/IES/NrUESecurityCapability.c
Normal file
42
openair3/NAS/COMMON/IES/NrUESecurityCapability.c
Normal file
@@ -0,0 +1,42 @@
|
||||
/*! \file FGSMobileIdentity.c
|
||||
|
||||
\brief 5GS Mobile Identity for registration request procedures
|
||||
\author Yoshio INOUE, Masayuki HARADA
|
||||
\email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com
|
||||
\date 2020
|
||||
\version 0.1
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdint.h>
|
||||
|
||||
|
||||
#include "TLVEncoder.h"
|
||||
#include "TLVDecoder.h"
|
||||
#include "NrUESecurityCapability.h"
|
||||
|
||||
|
||||
|
||||
int encode_nrue_security_capability(NrUESecurityCapability *nruesecuritycapability, uint8_t iei, uint8_t *buffer, uint32_t len)
|
||||
{
|
||||
int encoded = 0;
|
||||
if(iei){
|
||||
*buffer = nruesecuritycapability->iei;
|
||||
encoded++;
|
||||
*(buffer+encoded) = nruesecuritycapability->length;
|
||||
encoded++;
|
||||
*(buffer+encoded) = nruesecuritycapability->fg_EA;
|
||||
encoded++;
|
||||
*(buffer+encoded) = nruesecuritycapability->fg_IA;
|
||||
encoded++;
|
||||
*(buffer+encoded) = nruesecuritycapability->EEA;
|
||||
encoded++;
|
||||
*(buffer+encoded) = nruesecuritycapability->EIA;
|
||||
encoded++;
|
||||
if((nruesecuritycapability->length - 4) > 0)
|
||||
encoded = encoded + nruesecuritycapability->length - 4;
|
||||
}
|
||||
return encoded;
|
||||
}
|
||||
|
||||
33
openair3/NAS/COMMON/IES/NrUESecurityCapability.h
Normal file
33
openair3/NAS/COMMON/IES/NrUESecurityCapability.h
Normal file
@@ -0,0 +1,33 @@
|
||||
/*! \file FGSMobileIdentity.h
|
||||
|
||||
\brief 5GS Mobile Identity for registration request procedures
|
||||
\author Yoshio INOUE, Masayuki HARADA
|
||||
\email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com
|
||||
\date 2020
|
||||
\version 0.1
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include "OctetString.h"
|
||||
|
||||
#ifndef NRUE_SECURITY_CAPABILITY_H_
|
||||
#define NRUE_SECURITY_CAPABILITY_H_
|
||||
|
||||
|
||||
typedef struct {
|
||||
uint8_t iei;
|
||||
uint8_t length;
|
||||
uint8_t fg_EA;
|
||||
uint8_t fg_IA;
|
||||
uint8_t EEA;
|
||||
uint8_t EIA;
|
||||
} NrUESecurityCapability;
|
||||
|
||||
|
||||
int encode_nrue_security_capability(NrUESecurityCapability *nruesecuritycapability, uint8_t iei, uint8_t *buffer, uint32_t len);
|
||||
|
||||
#endif /* NRUE_SECURITY_CAPABILITY_H_ */
|
||||
|
||||
28
openair3/NAS/COMMON/IES/SpareHalfOctet.c
Normal file
28
openair3/NAS/COMMON/IES/SpareHalfOctet.c
Normal file
@@ -0,0 +1,28 @@
|
||||
/*! \file SpareHalfOctet.c
|
||||
|
||||
\brief registration request procedures for gNB
|
||||
\author Yoshio INOUE, Masayuki HARADA
|
||||
\email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com
|
||||
\date 2020
|
||||
\version 0.1
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdint.h>
|
||||
|
||||
|
||||
#include "TLVEncoder.h"
|
||||
#include "TLVDecoder.h"
|
||||
#include "SpareHalfOctet.h"
|
||||
|
||||
int decode_spare_half_octet(SpareHalfOctet *sparehalfoctet, uint8_t iei, uint8_t *buffer, uint32_t len)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
int encode_spare_half_octet(SpareHalfOctet *sparehalfoctet, uint8_t iei, uint8_t *buffer, uint32_t len)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
29
openair3/NAS/COMMON/IES/SpareHalfOctet.h
Normal file
29
openair3/NAS/COMMON/IES/SpareHalfOctet.h
Normal file
@@ -0,0 +1,29 @@
|
||||
/*! \file SpareHalfOctet.h
|
||||
|
||||
\brief registration request procedures for gNB
|
||||
\author Yoshio INOUE, Masayuki HARADA
|
||||
\email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com
|
||||
\date 2020
|
||||
\version 0.1
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include "OctetString.h"
|
||||
|
||||
#ifndef SPARE_HALF_OCTET_H_
|
||||
#define SPARE_HALF_OCTET_H_
|
||||
|
||||
#define SPARE_HALF_OCTET_MINIMUM_LENGTH 1
|
||||
#define SPARE_HALF_OCTET_MAXIMUM_LENGTH 1
|
||||
|
||||
typedef uint8_t SpareHalfOctet;
|
||||
|
||||
int encode_spare_half_octet(SpareHalfOctet *sparehalfoctet, uint8_t iei, uint8_t *buffer, uint32_t len);
|
||||
|
||||
int decode_spare_half_octet(SpareHalfOctet *sparehalfoctet, uint8_t iei, uint8_t *buffer, uint32_t len);
|
||||
|
||||
#endif /* SPARE HALF OCTET_H_ */
|
||||
|
||||
0
openair3/NAS/NR_UE/.gitkeep
Normal file
0
openair3/NAS/NR_UE/.gitkeep
Normal file
148
openair3/NAS/NR_UE/nr_nas_msg_sim.c
Normal file
148
openair3/NAS/NR_UE/nr_nas_msg_sim.c
Normal file
@@ -0,0 +1,148 @@
|
||||
|
||||
/*! \file nr_nas_msg_sim.c
|
||||
|
||||
\brief simulator for nr nas message
|
||||
\author Yoshio INOUE, Masayuki HARADA
|
||||
\email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com
|
||||
\date 2020
|
||||
\version 0.1
|
||||
*/
|
||||
|
||||
#include <string.h> // memset
|
||||
#include <stdlib.h> // malloc, free
|
||||
|
||||
#include "nas_log.h"
|
||||
#include "TLVDecoder.h"
|
||||
#include "TLVEncoder.h"
|
||||
#include "nr_nas_msg_sim.h"
|
||||
|
||||
|
||||
static int _nas_mm_msg_encode_header(const mm_msg_header_t *header,
|
||||
uint8_t *buffer, uint32_t len) {
|
||||
int size = 0;
|
||||
|
||||
/* Check the buffer length */
|
||||
if (len < sizeof(mm_msg_header_t)) {
|
||||
return (TLV_ENCODE_BUFFER_TOO_SHORT);
|
||||
}
|
||||
|
||||
/* Check the protocol discriminator */
|
||||
if (header->ex_protocol_discriminator != FGS_MOBILITY_MANAGEMENT_MESSAGE) {
|
||||
LOG_TRACE(ERROR, "ESM-MSG - Unexpected extened protocol discriminator: 0x%x",
|
||||
header->ex_protocol_discriminator);
|
||||
return (TLV_ENCODE_PROTOCOL_NOT_SUPPORTED);
|
||||
}
|
||||
|
||||
/* Encode the extendedprotocol discriminator */
|
||||
ENCODE_U8(buffer + size, header->ex_protocol_discriminator, size);
|
||||
/* Encode the security header type */
|
||||
ENCODE_U8(buffer + size, (header->security_header_type & 0xf), size);
|
||||
/* Encode the message type */
|
||||
ENCODE_U8(buffer + size, header->message_type, size);
|
||||
return (size);
|
||||
}
|
||||
|
||||
|
||||
int mm_msg_encode(MM_msg *mm_msg, uint8_t *buffer, uint32_t len) {
|
||||
LOG_FUNC_IN;
|
||||
int header_result;
|
||||
int encode_result;
|
||||
uint8_t msg_type = mm_msg->header.message_type;
|
||||
|
||||
|
||||
/* First encode the EMM message header */
|
||||
header_result = _nas_mm_msg_encode_header(&mm_msg->header, buffer, len);
|
||||
|
||||
if (header_result < 0) {
|
||||
LOG_TRACE(ERROR, "EMM-MSG - Failed to encode EMM message header "
|
||||
"(%d)", header_result);
|
||||
LOG_FUNC_RETURN(header_result);
|
||||
}
|
||||
|
||||
buffer += header_result;
|
||||
len -= header_result;
|
||||
|
||||
switch(msg_type) {
|
||||
case REGISTRATION_REQUEST:
|
||||
encode_result = encode_registration_request(&mm_msg->registration_request, buffer, len);
|
||||
break;
|
||||
|
||||
default:
|
||||
LOG_TRACE(ERROR, "EMM-MSG - Unexpected message type: 0x%x",
|
||||
mm_msg->header.message_type);
|
||||
encode_result = TLV_ENCODE_WRONG_MESSAGE_TYPE;
|
||||
break;
|
||||
/* TODO: Handle not standard layer 3 messages: SERVICE_REQUEST */
|
||||
}
|
||||
|
||||
if (encode_result < 0) {
|
||||
LOG_TRACE(ERROR, "EMM-MSG - Failed to encode L3 EMM message 0x%x "
|
||||
"(%d)", mm_msg->header.message_type, encode_result);
|
||||
}
|
||||
|
||||
if (encode_result < 0)
|
||||
LOG_FUNC_RETURN (encode_result);
|
||||
|
||||
LOG_FUNC_RETURN (header_result + encode_result);
|
||||
}
|
||||
|
||||
|
||||
|
||||
void generateRegistrationRequest(as_nas_info_t *initialNasMsg) {
|
||||
int size = sizeof(mm_msg_header_t);
|
||||
fgs_nas_message_t nas_msg;
|
||||
memset(&nas_msg, 0, sizeof(fgs_nas_message_t));
|
||||
MM_msg *mm_msg;
|
||||
|
||||
mm_msg = &nas_msg.plain.mm_msg;
|
||||
// set header
|
||||
mm_msg->header.ex_protocol_discriminator = FGS_MOBILITY_MANAGEMENT_MESSAGE;
|
||||
mm_msg->header.security_header_type = PLAIN_5GS_MSG;
|
||||
mm_msg->header.message_type = REGISTRATION_REQUEST;
|
||||
|
||||
|
||||
// set registration request
|
||||
mm_msg->registration_request.protocoldiscriminator = FGS_MOBILITY_MANAGEMENT_MESSAGE;
|
||||
size += 1;
|
||||
mm_msg->registration_request.securityheadertype = PLAIN_5GS_MSG;
|
||||
size += 1;
|
||||
mm_msg->registration_request.messagetype = REGISTRATION_REQUEST;
|
||||
size += 1;
|
||||
mm_msg->registration_request.fgsregistrationtype = INITIAL_REGISTRATION;
|
||||
mm_msg->registration_request.naskeysetidentifier.naskeysetidentifier = NAS_KEY_SET_IDENTIFIER_NOT_AVAILABLE;
|
||||
size += 1;
|
||||
mm_msg->registration_request.fgsmobileidentity.guti.typeofidentity = FGS_MOBILE_IDENTITY_5G_GUTI;
|
||||
// mm_msg->registration_request.fgsmobileidentity.guti.amfregionid = 1;
|
||||
// mm_msg->registration_request.fgsmobileidentity.guti.amfpointer = 1;
|
||||
// mm_msg->registration_request.fgsmobileidentity.guti.amfsetid = 1;
|
||||
mm_msg->registration_request.fgsmobileidentity.guti.tmsi = 10;
|
||||
mm_msg->registration_request.fgsmobileidentity.guti.mncdigit1 = 9;
|
||||
mm_msg->registration_request.fgsmobileidentity.guti.mncdigit2 = 3;
|
||||
mm_msg->registration_request.fgsmobileidentity.guti.mccdigit1 = 2;
|
||||
mm_msg->registration_request.fgsmobileidentity.guti.mccdigit2 = 0;
|
||||
mm_msg->registration_request.fgsmobileidentity.guti.mccdigit3 = 8;
|
||||
|
||||
size += 13;
|
||||
|
||||
mm_msg->registration_request.presencemask |= REGISTRATION_REQUEST_5GMM_CAPABILITY_PRESENT;
|
||||
mm_msg->registration_request.fgmmcapability.iei = REGISTRATION_REQUEST_5GMM_CAPABILITY_IEI;
|
||||
mm_msg->registration_request.fgmmcapability.length = 1;
|
||||
mm_msg->registration_request.fgmmcapability.value = 0x7;
|
||||
size += 3;
|
||||
|
||||
mm_msg->registration_request.presencemask |= REGISTRATION_REQUEST_UE_SECURITY_CAPABILITY_PRESENT;
|
||||
mm_msg->registration_request.nruesecuritycapability.iei = REGISTRATION_REQUEST_UE_SECURITY_CAPABILITY_IEI;
|
||||
mm_msg->registration_request.nruesecuritycapability.length = 8;
|
||||
mm_msg->registration_request.nruesecuritycapability.fg_EA = 0x80;
|
||||
mm_msg->registration_request.nruesecuritycapability.fg_IA = 0x20;
|
||||
mm_msg->registration_request.nruesecuritycapability.EEA = 0;
|
||||
mm_msg->registration_request.nruesecuritycapability.EIA = 0;
|
||||
size += 10;
|
||||
|
||||
// encode the message
|
||||
initialNasMsg->data = (Byte_t *)malloc(size * sizeof(Byte_t));
|
||||
|
||||
initialNasMsg->length = mm_msg_encode(mm_msg, (uint8_t*)(initialNasMsg->data), size);
|
||||
|
||||
|
||||
}
|
||||
73
openair3/NAS/NR_UE/nr_nas_msg_sim.h
Normal file
73
openair3/NAS/NR_UE/nr_nas_msg_sim.h
Normal file
@@ -0,0 +1,73 @@
|
||||
/*! \file nr_nas_msg_sim.h
|
||||
|
||||
\brief simulator for nr nas message
|
||||
\author Yoshio INOUE, Masayuki HARADA
|
||||
\email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com
|
||||
\date 2020
|
||||
\version 0.1
|
||||
*/
|
||||
|
||||
|
||||
#ifndef __NR_NAS_MSG_SIM_H__
|
||||
#define __NR_NAS_MSG_SIM_H__
|
||||
|
||||
#include "RegistrationRequest.h"
|
||||
#include "as_message.h"
|
||||
|
||||
|
||||
#define PLAIN_5GS_MSG 0b0000
|
||||
#define INTEGRITY_PROTECTED 0b0001
|
||||
|
||||
#define REGISTRATION_REQUEST 0b01000001 /* 65 = 0x41 */
|
||||
#define INITIAL_REGISTRATION 0b001
|
||||
|
||||
|
||||
typedef enum fgs_protocol_discriminator_e {
|
||||
/* Protocol discriminator identifier for 5GS Mobility Management */
|
||||
FGS_MOBILITY_MANAGEMENT_MESSAGE = 0x7E,
|
||||
|
||||
/* Protocol discriminator identifier for 5GS Session Management */
|
||||
FGS_SESSION_MANAGEMENT_MESSAGE = 0x2E,
|
||||
} fgs_protocol_discriminator_t;
|
||||
|
||||
|
||||
typedef struct {
|
||||
uint8_t ex_protocol_discriminator;
|
||||
uint8_t security_header_type;
|
||||
uint8_t message_type;
|
||||
} mm_msg_header_t;
|
||||
|
||||
/* Structure of security protected header */
|
||||
typedef struct {
|
||||
fgs_protocol_discriminator_t protocol_discriminator;
|
||||
uint8_t security_header_type;
|
||||
uint32_t message_authentication_code;
|
||||
uint8_t sequence_number;
|
||||
} fgs_nas_message_security_header_t;
|
||||
|
||||
typedef union {
|
||||
mm_msg_header_t header;
|
||||
registration_request_msg registration_request;
|
||||
} MM_msg;
|
||||
|
||||
|
||||
|
||||
typedef struct {
|
||||
MM_msg mm_msg; /* 5GS Mobility Management messages */
|
||||
} fgs_nas_message_plain_t;
|
||||
|
||||
typedef struct {
|
||||
fgs_nas_message_security_header_t header;
|
||||
fgs_nas_message_plain_t plain;
|
||||
} fgs_nas_message_security_protected_t;
|
||||
|
||||
|
||||
typedef union {
|
||||
fgs_nas_message_security_header_t header;
|
||||
fgs_nas_message_security_protected_t security_protected;
|
||||
fgs_nas_message_plain_t plain;
|
||||
} fgs_nas_message_t;
|
||||
|
||||
void generateRegistrationRequest(as_nas_info_t *initialNasMsg);
|
||||
|
||||
#endif /* __NR_NAS_MSG_SIM_H__*/
|
||||
6886
openair3/NGAP/MESSAGES/ASN1/ASN1_files/ngap-15.8.0.asn1
Normal file
6886
openair3/NGAP/MESSAGES/ASN1/ASN1_files/ngap-15.8.0.asn1
Normal file
File diff suppressed because it is too large
Load Diff
41
openair3/NGAP/ngap_common.c
Normal file
41
openair3/NGAP/ngap_common.c
Normal file
@@ -0,0 +1,41 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file ngap_common.c
|
||||
* \brief ngap procedures for both gNB and AMF
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \email yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
* \date 2020
|
||||
* \version 0.1
|
||||
*/
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#include "ngap_common.h"
|
||||
#include "NGAP_NGAP-PDU.h"
|
||||
|
||||
|
||||
int asn1_xer_print = 0;
|
||||
|
||||
|
||||
void ngap_handle_criticality(NGAP_Criticality_t criticality)
|
||||
{
|
||||
}
|
||||
163
openair3/NGAP/ngap_common.h
Normal file
163
openair3/NGAP/ngap_common.h
Normal file
@@ -0,0 +1,163 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file ngap_common.h
|
||||
* \brief ngap procedures for both gNB and AMF
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \email yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
* \date 2020
|
||||
* \version 0.1
|
||||
*/
|
||||
|
||||
/** @defgroup _ngap_impl_ NGAP Layer Reference Implementation
|
||||
* @ingroup _ref_implementation_
|
||||
* @{
|
||||
*/
|
||||
|
||||
|
||||
#if HAVE_CONFIG_H_
|
||||
# include "config.h"
|
||||
#endif
|
||||
|
||||
#ifndef NGAP_COMMON_H_
|
||||
#define NGAP_COMMON_H_
|
||||
|
||||
|
||||
#include "common/utils/LOG/log.h"
|
||||
/* replace ASN_DEBUG defined in asn_internal.h by oai tracing system
|
||||
Would be cleaner to modify asn_internal.h but it seems to come
|
||||
from non oai source, with BSD license, so prefer to do that here..
|
||||
*/
|
||||
#ifdef ASN_DEBUG
|
||||
# undef ASN_DEBUG
|
||||
#endif
|
||||
#define ASN_DEBUG( x... ) LOG_I(ASN, x)
|
||||
|
||||
#include "NGAP_ProtocolIE-Field.h"
|
||||
#include "NGAP_NGAP-PDU.h"
|
||||
#include "NGAP_InitiatingMessage.h"
|
||||
#include "NGAP_SuccessfulOutcome.h"
|
||||
#include "NGAP_UnsuccessfulOutcome.h"
|
||||
#include "NGAP_ProtocolIE-Field.h"
|
||||
#include "NGAP_ProtocolIE-FieldPair.h"
|
||||
#include "NGAP_ProtocolIE-ContainerPair.h"
|
||||
#include "NGAP_ProtocolExtensionField.h"
|
||||
#include "NGAP_ProtocolExtensionContainer.h"
|
||||
#include "NGAP_asn_constant.h"
|
||||
#include "NGAP_SupportedTAItem.h"
|
||||
#include "NGAP_ServedGUAMIItem.h"
|
||||
#include "NGAP_BroadcastPLMNItem.h"
|
||||
#include "NGAP_SliceSupportItem.h"
|
||||
#include "NGAP_PLMNSupportItem.h"
|
||||
#include "NGAP_PDUSessionResourceSetupResponseTransfer.h"
|
||||
#include "NGAP_PDUSessionResourceSetupUnsuccessfulTransfer.h"
|
||||
#include "NGAP_PDUSessionResourceSetupItemCxtRes.h"
|
||||
#include "NGAP_PDUSessionResourceFailedToSetupItemCxtRes.h"
|
||||
#include "NGAP_PDUSessionResourceSetupItemSUReq.h"
|
||||
#include "NGAP_PDUSessionResourceSetupItemSURes.h"
|
||||
#include "NGAP_PDUSessionResourceFailedToSetupItemSURes.h"
|
||||
#include "NGAP_AssociatedQosFlowItem.h"
|
||||
#include "NGAP_PDUSessionResourceSetupRequestTransfer.h"
|
||||
#include "NGAP_PDUSessionResourceSetupItemCxtReq.h"
|
||||
#include "NGAP_QosFlowSetupRequestItem.h"
|
||||
#include "NGAP_AllowedNSSAI-Item.h"
|
||||
#include "NGAP_PDUSessionResourceModifyItemModRes.h"
|
||||
#include "NGAP_PDUSessionResourceFailedToModifyItemModRes.h"
|
||||
#include "NGAP_PDUSessionResourceModifyUnsuccessfulTransfer.h"
|
||||
#include "NGAP_PDUSessionResourceReleasedItemRelRes.h"
|
||||
#include "NGAP_PDUSessionResourceToReleaseItemRelCmd.h"
|
||||
#include "NGAP_PDUSessionResourceModifyItemModReq.h"
|
||||
#include "NGAP_PDUSessionResourceModifyRequestTransfer.h"
|
||||
#include "NGAP_QosFlowAddOrModifyRequestItem.h"
|
||||
#include "NGAP_TAIListForPagingItem.h"
|
||||
#include "NGAP_GNB-ID.h"
|
||||
#include "NGAP_GlobalGNB-ID.h"
|
||||
#include "NGAP_GTPTunnel.h"
|
||||
#include "NGAP_UE-NGAP-ID-pair.h"
|
||||
#include "NGAP_UserLocationInformationNR.h"
|
||||
|
||||
/* Checking version of ASN1C compiler */
|
||||
#if (ASN1C_ENVIRONMENT_VERSION < ASN1C_MINIMUM_VERSION)
|
||||
# error "You are compiling ngap with the wrong version of ASN1C"
|
||||
#endif
|
||||
|
||||
#ifndef FALSE
|
||||
# define FALSE (0)
|
||||
#endif
|
||||
#ifndef TRUE
|
||||
# define TRUE (!FALSE)
|
||||
#endif
|
||||
|
||||
#define NGAP_UE_ID_FMT "0x%06"PRIX32
|
||||
|
||||
extern int asn_debug;
|
||||
extern int asn1_xer_print;
|
||||
|
||||
#if defined(ENB_MODE)
|
||||
# include "common/utils/LOG/log.h"
|
||||
# include "ngap_gNB_default_values.h"
|
||||
# define NGAP_ERROR(x, args...) LOG_E(NGAP, x, ##args)
|
||||
# define NGAP_WARN(x, args...) LOG_W(NGAP, x, ##args)
|
||||
# define NGAP_TRAF(x, args...) LOG_I(NGAP, x, ##args)
|
||||
# define NGAP_INFO(x, args...) LOG_I(NGAP, x, ##args)
|
||||
# define NGAP_DEBUG(x, args...) LOG_I(NGAP, x, ##args)
|
||||
#else
|
||||
# include "amf_default_values.h"
|
||||
# define NGAP_ERROR(x, args...) do { fprintf(stdout, "[NGAP][E]"x, ##args); } while(0)
|
||||
# define NGAP_WARN(x, args...) do { fprintf(stdout, "[NGAP][W]"x, ##args); } while(0)
|
||||
# define NGAP_TRAF(x, args...) do { fprintf(stdout, "[NGAP][T]"x, ##args); } while(0)
|
||||
# define NGAP_INFO(x, args...) do { fprintf(stdout, "[NGAP][I]"x, ##args); } while(0)
|
||||
# define NGAP_DEBUG(x, args...) do { fprintf(stdout, "[NGAP][D]"x, ##args); } while(0)
|
||||
#endif
|
||||
|
||||
|
||||
#define NGAP_FIND_PROTOCOLIE_BY_ID(IE_TYPE, ie, container, IE_ID, mandatory) \
|
||||
do {\
|
||||
IE_TYPE **ptr; \
|
||||
ie = NULL; \
|
||||
for (ptr = container->protocolIEs.list.array; \
|
||||
ptr < &container->protocolIEs.list.array[container->protocolIEs.list.count]; \
|
||||
ptr++) { \
|
||||
if((*ptr)->id == IE_ID) { \
|
||||
ie = *ptr; \
|
||||
break; \
|
||||
} \
|
||||
} \
|
||||
if (ie == NULL ) { \
|
||||
NGAP_ERROR("NGAP_FIND_PROTOCOLIE_BY_ID: %s %d: ie is NULL\n",__FILE__,__LINE__);\
|
||||
} \
|
||||
if (mandatory) DevAssert(ie != NULL); \
|
||||
} while(0)
|
||||
/** \brief Function callback prototype.
|
||||
**/
|
||||
typedef int (*ngap_message_decoded_callback)(
|
||||
uint32_t assoc_id,
|
||||
uint32_t stream,
|
||||
NGAP_NGAP_PDU_t *pdu
|
||||
);
|
||||
|
||||
/** \brief Handle criticality
|
||||
\param criticality Criticality of the IE
|
||||
@returns void
|
||||
**/
|
||||
void ngap_handle_criticality(NGAP_Criticality_t criticality);
|
||||
|
||||
#endif /* NGAP_COMMON_H_ */
|
||||
562
openair3/NGAP/ngap_gNB.c
Normal file
562
openair3/NGAP/ngap_gNB.c
Normal file
@@ -0,0 +1,562 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file ngap_gNB.c
|
||||
* \brief NGAP gNB task
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \date 2020
|
||||
* \email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
* \version 1.0
|
||||
* @ingroup _ngap
|
||||
*/
|
||||
|
||||
|
||||
#include <pthread.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdint.h>
|
||||
#include <crypt.h>
|
||||
|
||||
#include "tree.h"
|
||||
#include "queue.h"
|
||||
|
||||
#include "intertask_interface.h"
|
||||
|
||||
#include "ngap_gNB_default_values.h"
|
||||
|
||||
#include "ngap_common.h"
|
||||
|
||||
#include "ngap_gNB_defs.h"
|
||||
#include "ngap_gNB.h"
|
||||
#include "ngap_gNB_encoder.h"
|
||||
#include "ngap_gNB_handlers.h"
|
||||
#include "ngap_gNB_nnsf.h"
|
||||
|
||||
#include "ngap_gNB_nas_procedures.h"
|
||||
#include "ngap_gNB_management_procedures.h"
|
||||
#include "ngap_gNB_context_management_procedures.h"
|
||||
|
||||
#include "ngap_gNB_itti_messaging.h"
|
||||
|
||||
#include "ngap_gNB_ue_context.h" // test, to be removed
|
||||
#include "msc.h"
|
||||
|
||||
#include "assertions.h"
|
||||
#include "conversions.h"
|
||||
#if defined(TEST_S1C_AMF)
|
||||
#include "oaisim_amf_test_s1c.h"
|
||||
#endif
|
||||
|
||||
ngap_gNB_config_t ngap_config;
|
||||
|
||||
static int ngap_gNB_generate_ng_setup_request(
|
||||
ngap_gNB_instance_t *instance_p, ngap_gNB_amf_data_t *ngap_amf_data_p);
|
||||
|
||||
void ngap_gNB_handle_register_gNB(instance_t instance, ngap_register_gnb_req_t *ngap_register_gNB);
|
||||
|
||||
void ngap_gNB_handle_sctp_association_resp(instance_t instance, sctp_new_association_resp_t *sctp_new_association_resp);
|
||||
|
||||
uint32_t ngap_generate_gNB_id(void) {
|
||||
char *out;
|
||||
char hostname[50];
|
||||
int ret;
|
||||
uint32_t gNB_id;
|
||||
/* Retrieve the host name */
|
||||
ret = gethostname(hostname, sizeof(hostname));
|
||||
DevAssert(ret == 0);
|
||||
out = crypt(hostname, "eurecom");
|
||||
DevAssert(out != NULL);
|
||||
gNB_id = ((out[0] << 24) | (out[1] << 16) | (out[2] << 8) | out[3]);
|
||||
return gNB_id;
|
||||
}
|
||||
|
||||
static void ngap_gNB_register_amf(ngap_gNB_instance_t *instance_p,
|
||||
net_ip_address_t *amf_ip_address,
|
||||
net_ip_address_t *local_ip_addr,
|
||||
uint16_t in_streams,
|
||||
uint16_t out_streams,
|
||||
uint8_t broadcast_plmn_num,
|
||||
uint8_t broadcast_plmn_index[PLMN_LIST_MAX_SIZE]) {
|
||||
MessageDef *message_p = NULL;
|
||||
sctp_new_association_req_t *sctp_new_association_req_p = NULL;
|
||||
ngap_gNB_amf_data_t *ngap_amf_data_p = NULL;
|
||||
struct ngap_gNB_amf_data_s *amf = NULL;
|
||||
DevAssert(instance_p != NULL);
|
||||
DevAssert(amf_ip_address != NULL);
|
||||
message_p = itti_alloc_new_message(TASK_NGAP, SCTP_NEW_ASSOCIATION_REQ);
|
||||
sctp_new_association_req_p = &message_p->ittiMsg.sctp_new_association_req;
|
||||
sctp_new_association_req_p->port = NGAP_PORT_NUMBER;
|
||||
sctp_new_association_req_p->ppid = NGAP_SCTP_PPID;
|
||||
sctp_new_association_req_p->in_streams = in_streams;
|
||||
sctp_new_association_req_p->out_streams = out_streams;
|
||||
memcpy(&sctp_new_association_req_p->remote_address,
|
||||
amf_ip_address,
|
||||
sizeof(*amf_ip_address));
|
||||
memcpy(&sctp_new_association_req_p->local_address,
|
||||
local_ip_addr,
|
||||
sizeof(*local_ip_addr));
|
||||
NGAP_INFO("[gNB %d] check the amf registration state\n",instance_p->instance);
|
||||
amf = NULL;
|
||||
|
||||
if ( amf == NULL ) {
|
||||
/* Create new AMF descriptor */
|
||||
ngap_amf_data_p = calloc(1, sizeof(*ngap_amf_data_p));
|
||||
DevAssert(ngap_amf_data_p != NULL);
|
||||
ngap_amf_data_p->cnx_id = ngap_gNB_fetch_add_global_cnx_id();
|
||||
sctp_new_association_req_p->ulp_cnx_id = ngap_amf_data_p->cnx_id;
|
||||
ngap_amf_data_p->assoc_id = -1;
|
||||
ngap_amf_data_p->broadcast_plmn_num = broadcast_plmn_num;
|
||||
memcpy(&ngap_amf_data_p->amf_s1_ip,
|
||||
amf_ip_address,
|
||||
sizeof(*amf_ip_address));
|
||||
for (int i = 0; i < broadcast_plmn_num; ++i)
|
||||
ngap_amf_data_p->broadcast_plmn_index[i] = broadcast_plmn_index[i];
|
||||
|
||||
ngap_amf_data_p->ngap_gNB_instance = instance_p;
|
||||
STAILQ_INIT(&ngap_amf_data_p->served_guami);
|
||||
/* Insert the new descriptor in list of known AMF
|
||||
* but not yet associated.
|
||||
*/
|
||||
RB_INSERT(ngap_amf_map, &instance_p->ngap_amf_head, ngap_amf_data_p);
|
||||
ngap_amf_data_p->state = NGAP_GNB_STATE_WAITING;
|
||||
instance_p->ngap_amf_nb ++;
|
||||
instance_p->ngap_amf_pending_nb ++;
|
||||
} else if (amf->state == NGAP_GNB_STATE_WAITING) {
|
||||
instance_p->ngap_amf_pending_nb ++;
|
||||
sctp_new_association_req_p->ulp_cnx_id = amf->cnx_id;
|
||||
NGAP_INFO("[gNB %d] AMF already registered, retrive the data (state %d, cnx %d, amf_nb %d, amf_pending_nb %d)\n",
|
||||
instance_p->instance,
|
||||
amf->state, amf->cnx_id,
|
||||
instance_p->ngap_amf_nb, instance_p->ngap_amf_pending_nb);
|
||||
/*ngap_amf_data_p->cnx_id = amf->cnx_id;
|
||||
sctp_new_association_req_p->ulp_cnx_id = amf->cnx_id;
|
||||
|
||||
ngap_amf_data_p->assoc_id = -1;
|
||||
ngap_amf_data_p->ngap_gNB_instance = instance_p;
|
||||
*/
|
||||
} else {
|
||||
NGAP_WARN("[gNB %d] AMF already registered but not in the waiting state, retrive the data (state %d, cnx %d, amf_nb %d, amf_pending_nb %d)\n",
|
||||
instance_p->instance,
|
||||
amf->state, amf->cnx_id,
|
||||
instance_p->ngap_amf_nb, instance_p->ngap_amf_pending_nb);
|
||||
}
|
||||
|
||||
itti_send_msg_to_task(TASK_SCTP, instance_p->instance, message_p);
|
||||
}
|
||||
|
||||
|
||||
void ngap_gNB_handle_register_gNB(instance_t instance, ngap_register_gnb_req_t *ngap_register_gNB) {
|
||||
ngap_gNB_instance_t *new_instance;
|
||||
uint8_t index;
|
||||
DevAssert(ngap_register_gNB != NULL);
|
||||
/* Look if the provided instance already exists */
|
||||
new_instance = ngap_gNB_get_instance(instance);
|
||||
|
||||
if (new_instance != NULL) {
|
||||
/* Checks if it is a retry on the same gNB */
|
||||
DevCheck(new_instance->gNB_id == ngap_register_gNB->gNB_id, new_instance->gNB_id, ngap_register_gNB->gNB_id, 0);
|
||||
DevCheck(new_instance->cell_type == ngap_register_gNB->cell_type, new_instance->cell_type, ngap_register_gNB->cell_type, 0);
|
||||
DevCheck(new_instance->num_plmn == ngap_register_gNB->num_plmn, new_instance->num_plmn, ngap_register_gNB->num_plmn, 0);
|
||||
DevCheck(new_instance->tac == ngap_register_gNB->tac, new_instance->tac, ngap_register_gNB->tac, 0);
|
||||
|
||||
for (int i = 0; i < new_instance->num_plmn; i++) {
|
||||
DevCheck(new_instance->mcc[i] == ngap_register_gNB->mcc[i], new_instance->mcc[i], ngap_register_gNB->mcc[i], 0);
|
||||
DevCheck(new_instance->mnc[i] == ngap_register_gNB->mnc[i], new_instance->mnc[i], ngap_register_gNB->mnc[i], 0);
|
||||
DevCheck(new_instance->mnc_digit_length[i] == ngap_register_gNB->mnc_digit_length[i], new_instance->mnc_digit_length[i], ngap_register_gNB->mnc_digit_length[i], 0);
|
||||
}
|
||||
|
||||
DevCheck(new_instance->default_drx == ngap_register_gNB->default_drx, new_instance->default_drx, ngap_register_gNB->default_drx, 0);
|
||||
} else {
|
||||
new_instance = calloc(1, sizeof(ngap_gNB_instance_t));
|
||||
DevAssert(new_instance != NULL);
|
||||
RB_INIT(&new_instance->ngap_ue_head);
|
||||
RB_INIT(&new_instance->ngap_amf_head);
|
||||
/* Copy usefull parameters */
|
||||
new_instance->instance = instance;
|
||||
new_instance->gNB_name = ngap_register_gNB->gNB_name;
|
||||
new_instance->gNB_id = ngap_register_gNB->gNB_id;
|
||||
new_instance->cell_type = ngap_register_gNB->cell_type;
|
||||
new_instance->tac = ngap_register_gNB->tac;
|
||||
|
||||
memcpy(&new_instance->gNB_ng_ip,
|
||||
&ngap_register_gNB->gnb_ip_address,
|
||||
sizeof(ngap_register_gNB->gnb_ip_address));
|
||||
|
||||
for (int i = 0; i < ngap_register_gNB->num_plmn; i++) {
|
||||
new_instance->mcc[i] = ngap_register_gNB->mcc[i];
|
||||
new_instance->mnc[i] = ngap_register_gNB->mnc[i];
|
||||
new_instance->mnc_digit_length[i] = ngap_register_gNB->mnc_digit_length[i];
|
||||
|
||||
new_instance->num_nssai[i] = ngap_register_gNB->num_nssai[i];
|
||||
}
|
||||
|
||||
new_instance->num_plmn = ngap_register_gNB->num_plmn;
|
||||
new_instance->default_drx = ngap_register_gNB->default_drx;
|
||||
|
||||
memcpy(new_instance->s_nssai, ngap_register_gNB->s_nssai, sizeof(ngap_register_gNB->s_nssai));
|
||||
|
||||
/* Add the new instance to the list of gNB (meaningfull in virtual mode) */
|
||||
ngap_gNB_insert_new_instance(new_instance);
|
||||
NGAP_INFO("Registered new gNB[%d] and %s gNB id %u\n",
|
||||
instance,
|
||||
ngap_register_gNB->cell_type == CELL_MACRO_GNB ? "macro" : "home",
|
||||
ngap_register_gNB->gNB_id);
|
||||
}
|
||||
|
||||
DevCheck(ngap_register_gNB->nb_amf <= NGAP_MAX_NB_AMF_IP_ADDRESS,
|
||||
NGAP_MAX_NB_AMF_IP_ADDRESS, ngap_register_gNB->nb_amf, 0);
|
||||
|
||||
/* Trying to connect to provided list of AMF ip address */
|
||||
for (index = 0; index < ngap_register_gNB->nb_amf; index++) {
|
||||
net_ip_address_t *amf_ip = &ngap_register_gNB->amf_ip_address[index];
|
||||
struct ngap_gNB_amf_data_s *amf = NULL;
|
||||
RB_FOREACH(amf, ngap_amf_map, &new_instance->ngap_amf_head) {
|
||||
/* Compare whether IPv4 and IPv6 information is already present, in which
|
||||
* wase we do not register again */
|
||||
if (amf->amf_s1_ip.ipv4 == amf_ip->ipv4 && (!amf_ip->ipv4
|
||||
|| strncmp(amf->amf_s1_ip.ipv4_address, amf_ip->ipv4_address, 16) == 0)
|
||||
&& amf->amf_s1_ip.ipv6 == amf_ip->ipv6 && (!amf_ip->ipv6
|
||||
|| strncmp(amf->amf_s1_ip.ipv6_address, amf_ip->ipv6_address, 46) == 0))
|
||||
break;
|
||||
}
|
||||
if (amf)
|
||||
continue;
|
||||
ngap_gNB_register_amf(new_instance,
|
||||
amf_ip,
|
||||
&ngap_register_gNB->gnb_ip_address,
|
||||
ngap_register_gNB->sctp_in_streams,
|
||||
ngap_register_gNB->sctp_out_streams,
|
||||
ngap_register_gNB->broadcast_plmn_num[index],
|
||||
ngap_register_gNB->broadcast_plmn_index[index]);
|
||||
}
|
||||
}
|
||||
|
||||
void ngap_gNB_handle_sctp_association_resp(instance_t instance, sctp_new_association_resp_t *sctp_new_association_resp) {
|
||||
ngap_gNB_instance_t *instance_p;
|
||||
ngap_gNB_amf_data_t *ngap_amf_data_p;
|
||||
DevAssert(sctp_new_association_resp != NULL);
|
||||
instance_p = ngap_gNB_get_instance(instance);
|
||||
DevAssert(instance_p != NULL);
|
||||
ngap_amf_data_p = ngap_gNB_get_AMF(instance_p, -1,
|
||||
sctp_new_association_resp->ulp_cnx_id);
|
||||
DevAssert(ngap_amf_data_p != NULL);
|
||||
|
||||
if (sctp_new_association_resp->sctp_state != SCTP_STATE_ESTABLISHED) {
|
||||
NGAP_WARN("Received unsuccessful result for SCTP association (%u), instance %d, cnx_id %u\n",
|
||||
sctp_new_association_resp->sctp_state,
|
||||
instance,
|
||||
sctp_new_association_resp->ulp_cnx_id);
|
||||
ngap_handle_ng_setup_message(ngap_amf_data_p, sctp_new_association_resp->sctp_state == SCTP_STATE_SHUTDOWN);
|
||||
return;
|
||||
}
|
||||
|
||||
/* Update parameters */
|
||||
ngap_amf_data_p->assoc_id = sctp_new_association_resp->assoc_id;
|
||||
ngap_amf_data_p->in_streams = sctp_new_association_resp->in_streams;
|
||||
ngap_amf_data_p->out_streams = sctp_new_association_resp->out_streams;
|
||||
/* Prepare new NG Setup Request */
|
||||
ngap_gNB_generate_ng_setup_request(instance_p, ngap_amf_data_p);
|
||||
}
|
||||
|
||||
static
|
||||
void ngap_gNB_handle_sctp_data_ind(sctp_data_ind_t *sctp_data_ind) {
|
||||
int result;
|
||||
DevAssert(sctp_data_ind != NULL);
|
||||
#if defined(TEST_S1C_AMF)
|
||||
amf_test_s1_notify_sctp_data_ind(sctp_data_ind->assoc_id, sctp_data_ind->stream,
|
||||
sctp_data_ind->buffer, sctp_data_ind->buffer_length);
|
||||
#else
|
||||
ngap_gNB_handle_message(sctp_data_ind->assoc_id, sctp_data_ind->stream,
|
||||
sctp_data_ind->buffer, sctp_data_ind->buffer_length);
|
||||
#endif
|
||||
result = itti_free(TASK_UNKNOWN, sctp_data_ind->buffer);
|
||||
AssertFatal (result == EXIT_SUCCESS, "Failed to free memory (%d)!\n", result);
|
||||
}
|
||||
|
||||
void ngap_gNB_init(void) {
|
||||
NGAP_DEBUG("Starting NGAP layer\n");
|
||||
ngap_gNB_prepare_internal_data();
|
||||
itti_mark_task_ready(TASK_NGAP);
|
||||
MSC_START_USE();
|
||||
}
|
||||
|
||||
void *ngap_gNB_process_itti_msg(void *notUsed) {
|
||||
MessageDef *received_msg = NULL;
|
||||
int result;
|
||||
itti_receive_msg(TASK_NGAP, &received_msg);
|
||||
|
||||
switch (ITTI_MSG_ID(received_msg)) {
|
||||
case TERMINATE_MESSAGE:
|
||||
NGAP_WARN(" *** Exiting NGAP thread\n");
|
||||
itti_exit_task();
|
||||
break;
|
||||
|
||||
case NGAP_REGISTER_GNB_REQ: {
|
||||
/* Register a new gNB.
|
||||
* in Virtual mode gNBs will be distinguished using the mod_id/
|
||||
* Each gNB has to send an NGAP_REGISTER_GNB message with its
|
||||
* own parameters.
|
||||
*/
|
||||
ngap_gNB_handle_register_gNB(ITTI_MESSAGE_GET_INSTANCE(received_msg),
|
||||
&NGAP_REGISTER_GNB_REQ(received_msg));
|
||||
}
|
||||
break;
|
||||
|
||||
case SCTP_NEW_ASSOCIATION_RESP: {
|
||||
ngap_gNB_handle_sctp_association_resp(ITTI_MESSAGE_GET_INSTANCE(received_msg),
|
||||
&received_msg->ittiMsg.sctp_new_association_resp);
|
||||
}
|
||||
break;
|
||||
|
||||
case SCTP_DATA_IND: {
|
||||
ngap_gNB_handle_sctp_data_ind(&received_msg->ittiMsg.sctp_data_ind);
|
||||
}
|
||||
break;
|
||||
|
||||
case NGAP_NAS_FIRST_REQ: {
|
||||
ngap_gNB_handle_nas_first_req(ITTI_MESSAGE_GET_INSTANCE(received_msg),
|
||||
&NGAP_NAS_FIRST_REQ(received_msg));
|
||||
}
|
||||
break;
|
||||
|
||||
case NGAP_UPLINK_NAS: {
|
||||
ngap_gNB_nas_uplink(ITTI_MESSAGE_GET_INSTANCE(received_msg),
|
||||
&NGAP_UPLINK_NAS(received_msg));
|
||||
}
|
||||
break;
|
||||
|
||||
case NGAP_UE_CAPABILITIES_IND: {
|
||||
ngap_gNB_ue_capabilities(ITTI_MESSAGE_GET_INSTANCE(received_msg),
|
||||
&NGAP_UE_CAPABILITIES_IND(received_msg));
|
||||
}
|
||||
break;
|
||||
|
||||
case NGAP_INITIAL_CONTEXT_SETUP_RESP: {
|
||||
ngap_gNB_initial_ctxt_resp(ITTI_MESSAGE_GET_INSTANCE(received_msg),
|
||||
&NGAP_INITIAL_CONTEXT_SETUP_RESP(received_msg));
|
||||
}
|
||||
break;
|
||||
|
||||
case NGAP_PDUSESSION_SETUP_RESP: {
|
||||
ngap_gNB_pdusession_setup_resp(ITTI_MESSAGE_GET_INSTANCE(received_msg),
|
||||
&NGAP_PDUSESSION_SETUP_RESP(received_msg));
|
||||
}
|
||||
break;
|
||||
|
||||
case NGAP_PDUSESSION_MODIFY_RESP: {
|
||||
ngap_gNB_pdusession_modify_resp(ITTI_MESSAGE_GET_INSTANCE(received_msg),
|
||||
&NGAP_PDUSESSION_MODIFY_RESP(received_msg));
|
||||
}
|
||||
break;
|
||||
|
||||
case NGAP_NAS_NON_DELIVERY_IND: {
|
||||
ngap_gNB_nas_non_delivery_ind(ITTI_MESSAGE_GET_INSTANCE(received_msg),
|
||||
&NGAP_NAS_NON_DELIVERY_IND(received_msg));
|
||||
}
|
||||
break;
|
||||
|
||||
case NGAP_PATH_SWITCH_REQ: {
|
||||
ngap_gNB_path_switch_req(ITTI_MESSAGE_GET_INSTANCE(received_msg),
|
||||
&NGAP_PATH_SWITCH_REQ(received_msg));
|
||||
}
|
||||
break;
|
||||
|
||||
case NGAP_PDUSESSION_MODIFICATION_IND: {
|
||||
ngap_gNB_generate_PDUSESSION_Modification_Indication(ITTI_MESSAGE_GET_INSTANCE(received_msg),
|
||||
&NGAP_PDUSESSION_MODIFICATION_IND(received_msg));
|
||||
}
|
||||
break;
|
||||
|
||||
case NGAP_UE_CONTEXT_RELEASE_COMPLETE: {
|
||||
ngap_ue_context_release_complete(ITTI_MESSAGE_GET_INSTANCE(received_msg),
|
||||
&NGAP_UE_CONTEXT_RELEASE_COMPLETE(received_msg));
|
||||
}
|
||||
break;
|
||||
|
||||
case NGAP_UE_CONTEXT_RELEASE_REQ: {
|
||||
ngap_gNB_instance_t *ngap_gNB_instance_p = NULL; // test
|
||||
struct ngap_gNB_ue_context_s *ue_context_p = NULL; // test
|
||||
ngap_ue_context_release_req(ITTI_MESSAGE_GET_INSTANCE(received_msg),
|
||||
&NGAP_UE_CONTEXT_RELEASE_REQ(received_msg));
|
||||
ngap_gNB_instance_p = ngap_gNB_get_instance(ITTI_MESSAGE_GET_INSTANCE(received_msg)); // test
|
||||
DevAssert(ngap_gNB_instance_p != NULL); // test
|
||||
|
||||
if ((ue_context_p = ngap_gNB_get_ue_context(ngap_gNB_instance_p,
|
||||
NGAP_UE_CONTEXT_RELEASE_REQ(received_msg).gNB_ue_ngap_id)) == NULL) { // test
|
||||
/* The context for this gNB ue ngap id doesn't exist in the map of gNB UEs */
|
||||
NGAP_ERROR("Failed to find ue context associated with gNB ue ngap id: %u\n",
|
||||
NGAP_UE_CONTEXT_RELEASE_REQ(received_msg).gNB_ue_ngap_id); // test
|
||||
} // test
|
||||
}
|
||||
break;
|
||||
|
||||
case NGAP_PDUSESSION_RELEASE_RESPONSE: {
|
||||
ngap_gNB_pdusession_release_resp(ITTI_MESSAGE_GET_INSTANCE(received_msg),
|
||||
&NGAP_PDUSESSION_RELEASE_RESPONSE(received_msg));
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
NGAP_ERROR("Received unhandled message: %d:%s\n",
|
||||
ITTI_MSG_ID(received_msg), ITTI_MSG_NAME(received_msg));
|
||||
break;
|
||||
}
|
||||
|
||||
result = itti_free (ITTI_MSG_ORIGIN_ID(received_msg), received_msg);
|
||||
AssertFatal (result == EXIT_SUCCESS, "Failed to free memory (%d)!\n", result);
|
||||
received_msg = NULL;
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
void *ngap_gNB_task(void *arg) {
|
||||
ngap_gNB_init();
|
||||
|
||||
while (1) {
|
||||
(void) ngap_gNB_process_itti_msg(NULL);
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
/*
|
||||
* gNB generate a NG setup request towards AMF
|
||||
*/
|
||||
static int ngap_gNB_generate_ng_setup_request(
|
||||
ngap_gNB_instance_t *instance_p,
|
||||
ngap_gNB_amf_data_t *ngap_amf_data_p)
|
||||
//-----------------------------------------------------------------------------
|
||||
{
|
||||
NGAP_NGAP_PDU_t pdu;
|
||||
NGAP_NGSetupRequest_t *out = NULL;
|
||||
NGAP_NGSetupRequestIEs_t *ie = NULL;
|
||||
NGAP_SupportedTAItem_t *ta = NULL;
|
||||
NGAP_BroadcastPLMNItem_t *plmn = NULL;
|
||||
NGAP_SliceSupportItem_t *ssi = NULL;
|
||||
uint8_t *buffer = NULL;
|
||||
uint32_t len = 0;
|
||||
int ret = 0;
|
||||
DevAssert(instance_p != NULL);
|
||||
DevAssert(ngap_amf_data_p != NULL);
|
||||
ngap_amf_data_p->state = NGAP_GNB_STATE_WAITING;
|
||||
/* Prepare the NGAP message to encode */
|
||||
memset(&pdu, 0, sizeof(pdu));
|
||||
pdu.present = NGAP_NGAP_PDU_PR_initiatingMessage;
|
||||
pdu.choice.initiatingMessage = CALLOC(1, sizeof(struct NGAP_InitiatingMessage));
|
||||
pdu.choice.initiatingMessage->procedureCode = NGAP_ProcedureCode_id_NGSetup;
|
||||
pdu.choice.initiatingMessage->criticality = NGAP_Criticality_reject;
|
||||
pdu.choice.initiatingMessage->value.present = NGAP_InitiatingMessage__value_PR_NGSetupRequest;
|
||||
out = &pdu.choice.initiatingMessage->value.choice.NGSetupRequest;
|
||||
/* mandatory */
|
||||
ie = (NGAP_NGSetupRequestIEs_t *)calloc(1, sizeof(NGAP_NGSetupRequestIEs_t));
|
||||
ie->id = NGAP_ProtocolIE_ID_id_GlobalRANNodeID;
|
||||
ie->criticality = NGAP_Criticality_reject;
|
||||
ie->value.present = NGAP_NGSetupRequestIEs__value_PR_GlobalRANNodeID;
|
||||
ie->value.choice.GlobalRANNodeID.present = NGAP_GlobalRANNodeID_PR_globalGNB_ID;
|
||||
ie->value.choice.GlobalRANNodeID.choice.globalGNB_ID = CALLOC(1, sizeof(struct NGAP_GlobalGNB_ID));
|
||||
MCC_MNC_TO_PLMNID(instance_p->mcc[ngap_amf_data_p->broadcast_plmn_index[0]],
|
||||
instance_p->mnc[ngap_amf_data_p->broadcast_plmn_index[0]],
|
||||
instance_p->mnc_digit_length[ngap_amf_data_p->broadcast_plmn_index[0]],
|
||||
&(ie->value.choice.GlobalRANNodeID.choice.globalGNB_ID->pLMNIdentity));
|
||||
ie->value.choice.GlobalRANNodeID.choice.globalGNB_ID->gNB_ID.present = NGAP_GNB_ID_PR_gNB_ID;
|
||||
MACRO_GNB_ID_TO_BIT_STRING(instance_p->gNB_id,
|
||||
&ie->value.choice.GlobalRANNodeID.choice.globalGNB_ID->gNB_ID.choice.gNB_ID);
|
||||
NGAP_INFO("%u -> %02x%02x%02x%02x\n", instance_p->gNB_id,
|
||||
ie->value.choice.GlobalRANNodeID.choice.globalGNB_ID->gNB_ID.choice.gNB_ID.buf[0],
|
||||
ie->value.choice.GlobalRANNodeID.choice.globalGNB_ID->gNB_ID.choice.gNB_ID.buf[1],
|
||||
ie->value.choice.GlobalRANNodeID.choice.globalGNB_ID->gNB_ID.choice.gNB_ID.buf[2],
|
||||
ie->value.choice.GlobalRANNodeID.choice.globalGNB_ID->gNB_ID.choice.gNB_ID.buf[3]);
|
||||
ASN_SEQUENCE_ADD(&out->protocolIEs.list, ie);
|
||||
|
||||
/* optional */
|
||||
if (instance_p->gNB_name) {
|
||||
ie = (NGAP_NGSetupRequestIEs_t *)calloc(1, sizeof(NGAP_NGSetupRequestIEs_t));
|
||||
ie->id = NGAP_ProtocolIE_ID_id_RANNodeName;
|
||||
ie->criticality = NGAP_Criticality_ignore;
|
||||
ie->value.present = NGAP_NGSetupRequestIEs__value_PR_RANNodeName;
|
||||
OCTET_STRING_fromBuf(&ie->value.choice.RANNodeName, instance_p->gNB_name,
|
||||
strlen(instance_p->gNB_name));
|
||||
ASN_SEQUENCE_ADD(&out->protocolIEs.list, ie);
|
||||
}
|
||||
|
||||
/* mandatory */
|
||||
ie = (NGAP_NGSetupRequestIEs_t *)calloc(1, sizeof(NGAP_NGSetupRequestIEs_t));
|
||||
ie->id = NGAP_ProtocolIE_ID_id_SupportedTAList;
|
||||
ie->criticality = NGAP_Criticality_reject;
|
||||
ie->value.present = NGAP_NGSetupRequestIEs__value_PR_SupportedTAList;
|
||||
{
|
||||
ta = (NGAP_SupportedTAItem_t *)calloc(1, sizeof(NGAP_SupportedTAItem_t));
|
||||
INT24_TO_OCTET_STRING(instance_p->tac, &ta->tAC);
|
||||
{
|
||||
for (int i = 0; i < ngap_amf_data_p->broadcast_plmn_num; ++i) {
|
||||
plmn = (NGAP_BroadcastPLMNItem_t *)calloc(1, sizeof(NGAP_BroadcastPLMNItem_t));
|
||||
MCC_MNC_TO_TBCD(instance_p->mcc[ngap_amf_data_p->broadcast_plmn_index[i]],
|
||||
instance_p->mnc[ngap_amf_data_p->broadcast_plmn_index[i]],
|
||||
instance_p->mnc_digit_length[ngap_amf_data_p->broadcast_plmn_index[i]],
|
||||
&plmn->pLMNIdentity);
|
||||
|
||||
for(int si = 0; si < instance_p->num_nssai[i]; si++) {
|
||||
ssi = (NGAP_SliceSupportItem_t *)calloc(1, sizeof(NGAP_SliceSupportItem_t));
|
||||
INT8_TO_OCTET_STRING(instance_p->s_nssai[i][si].sST, &ssi->s_NSSAI.sST);
|
||||
|
||||
if(instance_p->s_nssai[i]->sD_flag) {
|
||||
ssi->s_NSSAI.sD = calloc(1, sizeof(NGAP_SD_t));
|
||||
ssi->s_NSSAI.sD->buf = calloc(3, sizeof(uint8_t));
|
||||
ssi->s_NSSAI.sD->size = 3;
|
||||
ssi->s_NSSAI.sD->buf[0] = instance_p->s_nssai[i][si].sD[0];
|
||||
ssi->s_NSSAI.sD->buf[1] = instance_p->s_nssai[i][si].sD[1];
|
||||
ssi->s_NSSAI.sD->buf[2] = instance_p->s_nssai[i][si].sD[2];
|
||||
}
|
||||
|
||||
|
||||
ASN_SEQUENCE_ADD(&plmn->tAISliceSupportList.list, ssi);
|
||||
}
|
||||
|
||||
ASN_SEQUENCE_ADD(&ta->broadcastPLMNList.list, plmn);
|
||||
}
|
||||
}
|
||||
ASN_SEQUENCE_ADD(&ie->value.choice.SupportedTAList.list, ta);
|
||||
}
|
||||
ASN_SEQUENCE_ADD(&out->protocolIEs.list, ie);
|
||||
|
||||
/* mandatory */
|
||||
ie = (NGAP_NGSetupRequestIEs_t *)calloc(1, sizeof(NGAP_NGSetupRequestIEs_t));
|
||||
ie->id = NGAP_ProtocolIE_ID_id_DefaultPagingDRX;
|
||||
ie->criticality = NGAP_Criticality_ignore;
|
||||
ie->value.present = NGAP_NGSetupRequestIEs__value_PR_PagingDRX;
|
||||
ie->value.choice.PagingDRX = instance_p->default_drx;
|
||||
ASN_SEQUENCE_ADD(&out->protocolIEs.list, ie);
|
||||
|
||||
|
||||
if (ngap_gNB_encode_pdu(&pdu, &buffer, &len) < 0) {
|
||||
NGAP_ERROR("Failed to encode NG setup request\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Non UE-Associated signalling -> stream = 0 */
|
||||
ngap_gNB_itti_send_sctp_data_req(instance_p->instance, ngap_amf_data_p->assoc_id, buffer, len, 0);
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
64
openair3/NGAP/ngap_gNB.h
Normal file
64
openair3/NGAP/ngap_gNB.h
Normal file
@@ -0,0 +1,64 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file ngap_gNB.h
|
||||
* \brief NGAP gNB task
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \date 2020
|
||||
* \email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
* \version 1.0
|
||||
* @ingroup _ngap
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdint.h>
|
||||
|
||||
/** @defgroup _ngap_impl_ NGAP Layer Reference Implementation for gNB
|
||||
* @ingroup _ref_implementation_
|
||||
* @{
|
||||
*/
|
||||
|
||||
#ifndef NGAP_GNB_H_
|
||||
#define NGAP_GNB_H_
|
||||
|
||||
typedef struct ngap_gNB_config_s {
|
||||
// MME related params
|
||||
unsigned char amf_enabled; ///< AMF enabled ?
|
||||
unsigned char ngap_enabled; ///< NGAP enabled ?
|
||||
} ngap_gNB_config_t;
|
||||
|
||||
extern ngap_gNB_config_t ngap_config;
|
||||
|
||||
#define AMF_MODE_ENABLED ngap_config.amf_enabled
|
||||
#define NGAP_CONF_MODE ngap_config.ngap_enabled
|
||||
|
||||
|
||||
void *ngap_gNB_process_itti_msg(void*);
|
||||
void ngap_gNB_init(void);
|
||||
void *ngap_gNB_task(void *arg);
|
||||
|
||||
uint32_t ngap_generate_gNB_id(void);
|
||||
|
||||
#endif /* NGAP_GNB_H_ */
|
||||
|
||||
/**
|
||||
* @}
|
||||
*/
|
||||
271
openair3/NGAP/ngap_gNB_context_management_procedures.c
Normal file
271
openair3/NGAP/ngap_gNB_context_management_procedures.c
Normal file
@@ -0,0 +1,271 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file ngap_gNB_context_management_procedures.c
|
||||
* \brief NGAP context management procedures
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \date 2020
|
||||
* \email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
* \version 1.0
|
||||
* @ingroup _ngap
|
||||
*/
|
||||
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include "assertions.h"
|
||||
#include "conversions.h"
|
||||
|
||||
#include "intertask_interface.h"
|
||||
|
||||
#include "ngap_common.h"
|
||||
#include "ngap_gNB_defs.h"
|
||||
|
||||
#include "ngap_gNB_itti_messaging.h"
|
||||
|
||||
#include "ngap_gNB_encoder.h"
|
||||
#include "ngap_gNB_nnsf.h"
|
||||
#include "ngap_gNB_ue_context.h"
|
||||
#include "ngap_gNB_nas_procedures.h"
|
||||
#include "ngap_gNB_management_procedures.h"
|
||||
#include "ngap_gNB_context_management_procedures.h"
|
||||
#include "msc.h"
|
||||
|
||||
|
||||
int ngap_ue_context_release_complete(instance_t instance,
|
||||
ngap_ue_release_complete_t *ue_release_complete_p)
|
||||
{
|
||||
|
||||
ngap_gNB_instance_t *ngap_gNB_instance_p = NULL;
|
||||
struct ngap_gNB_ue_context_s *ue_context_p = NULL;
|
||||
NGAP_NGAP_PDU_t pdu;
|
||||
NGAP_UEContextReleaseComplete_t *out;
|
||||
NGAP_UEContextReleaseComplete_IEs_t *ie;
|
||||
uint8_t *buffer;
|
||||
uint32_t length;
|
||||
|
||||
/* Retrieve the NGAP gNB instance associated with Mod_id */
|
||||
ngap_gNB_instance_p = ngap_gNB_get_instance(instance);
|
||||
|
||||
DevAssert(ue_release_complete_p != NULL);
|
||||
DevAssert(ngap_gNB_instance_p != NULL);
|
||||
|
||||
/*RB_FOREACH(ue_context_p, ngap_ue_map, &ngap_gNB_instance_p->ngap_ue_head) {
|
||||
NGAP_WARN("in ngap_ue_map: UE context gNB_ue_ngap_id %u amf_ue_ngap_id %u state %u\n",
|
||||
ue_context_p->gNB_ue_ngap_id, ue_context_p->amf_ue_ngap_id,
|
||||
ue_context_p->ue_state);
|
||||
}*/
|
||||
if ((ue_context_p = ngap_gNB_get_ue_context(ngap_gNB_instance_p,
|
||||
ue_release_complete_p->gNB_ue_ngap_id)) == NULL) {
|
||||
/* The context for this gNB ue ngap id doesn't exist in the map of gNB UEs */
|
||||
NGAP_WARN("Failed to find ue context associated with gNB ue ngap id: %u\n",
|
||||
ue_release_complete_p->gNB_ue_ngap_id);
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Prepare the NGAP message to encode */
|
||||
memset(&pdu, 0, sizeof(pdu));
|
||||
pdu.present = NGAP_NGAP_PDU_PR_successfulOutcome;
|
||||
pdu.choice.successfulOutcome = CALLOC(1, sizeof(struct NGAP_SuccessfulOutcome));
|
||||
pdu.choice.successfulOutcome->procedureCode = NGAP_ProcedureCode_id_UEContextRelease;
|
||||
pdu.choice.successfulOutcome->criticality = NGAP_Criticality_reject;
|
||||
pdu.choice.successfulOutcome->value.present = NGAP_SuccessfulOutcome__value_PR_UEContextReleaseComplete;
|
||||
out = &pdu.choice.successfulOutcome->value.choice.UEContextReleaseComplete;
|
||||
|
||||
/* mandatory */
|
||||
ie = (NGAP_UEContextReleaseComplete_IEs_t *)calloc(1, sizeof(NGAP_UEContextReleaseComplete_IEs_t));
|
||||
ie->id = NGAP_ProtocolIE_ID_id_AMF_UE_NGAP_ID;
|
||||
ie->criticality = NGAP_Criticality_ignore;
|
||||
ie->value.present = NGAP_UEContextReleaseComplete_IEs__value_PR_AMF_UE_NGAP_ID;
|
||||
asn_uint642INTEGER(&ie->value.choice.AMF_UE_NGAP_ID, ue_context_p->amf_ue_ngap_id);
|
||||
ASN_SEQUENCE_ADD(&out->protocolIEs.list, ie);
|
||||
|
||||
/* mandatory */
|
||||
ie = (NGAP_UEContextReleaseComplete_IEs_t *)calloc(1, sizeof(NGAP_UEContextReleaseComplete_IEs_t));
|
||||
ie->id = NGAP_ProtocolIE_ID_id_RAN_UE_NGAP_ID;
|
||||
ie->criticality = NGAP_Criticality_ignore;
|
||||
ie->value.present = NGAP_UEContextReleaseComplete_IEs__value_PR_RAN_UE_NGAP_ID;
|
||||
ie->value.choice.RAN_UE_NGAP_ID = ue_release_complete_p->gNB_ue_ngap_id;
|
||||
ASN_SEQUENCE_ADD(&out->protocolIEs.list, ie);
|
||||
|
||||
|
||||
if (ngap_gNB_encode_pdu(&pdu, &buffer, &length) < 0) {
|
||||
/* Encode procedure has failed... */
|
||||
NGAP_ERROR("Failed to encode UE context release complete\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
MSC_LOG_TX_MESSAGE(
|
||||
MSC_NGAP_GNB,
|
||||
MSC_NGAP_AMF,
|
||||
buffer,
|
||||
length,
|
||||
MSC_AS_TIME_FMT" UEContextRelease successfulOutcome gNB_ue_ngap_id %u amf_ue_ngap_id %lu",
|
||||
0,0, //MSC_AS_TIME_ARGS(ctxt_pP),
|
||||
ue_release_complete_p->gNB_ue_ngap_id,
|
||||
ue_context_p->amf_ue_ngap_id);
|
||||
|
||||
/* UE associated signalling -> use the allocated stream */
|
||||
ngap_gNB_itti_send_sctp_data_req(ngap_gNB_instance_p->instance,
|
||||
ue_context_p->amf_ref->assoc_id, buffer,
|
||||
length, ue_context_p->tx_stream);
|
||||
|
||||
//LG ngap_gNB_itti_send_sctp_close_association(ngap_gNB_instance_p->instance,
|
||||
// ue_context_p->amf_ref->assoc_id);
|
||||
// release UE context
|
||||
struct ngap_gNB_ue_context_s *ue_context2_p = NULL;
|
||||
|
||||
if ((ue_context2_p = RB_REMOVE(ngap_ue_map, &ngap_gNB_instance_p->ngap_ue_head, ue_context_p))
|
||||
!= NULL) {
|
||||
NGAP_WARN("Removed UE context gNB_ue_ngap_id %u\n",
|
||||
ue_context2_p->gNB_ue_ngap_id);
|
||||
ngap_gNB_free_ue_context(ue_context2_p);
|
||||
} else {
|
||||
NGAP_WARN("Removing UE context gNB_ue_ngap_id %u: did not find context\n",
|
||||
ue_context_p->gNB_ue_ngap_id);
|
||||
}
|
||||
/*RB_FOREACH(ue_context_p, ngap_ue_map, &ngap_gNB_instance_p->ngap_ue_head) {
|
||||
NGAP_WARN("in ngap_ue_map: UE context gNB_ue_ngap_id %u amf_ue_ngap_id %u state %u\n",
|
||||
ue_context_p->gNB_ue_ngap_id, ue_context_p->amf_ue_ngap_id,
|
||||
ue_context_p->ue_state);
|
||||
}*/
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
int ngap_ue_context_release_req(instance_t instance,
|
||||
ngap_ue_release_req_t *ue_release_req_p)
|
||||
{
|
||||
ngap_gNB_instance_t *ngap_gNB_instance_p = NULL;
|
||||
struct ngap_gNB_ue_context_s *ue_context_p = NULL;
|
||||
NGAP_NGAP_PDU_t pdu;
|
||||
NGAP_UEContextReleaseRequest_t *out;
|
||||
NGAP_UEContextReleaseRequest_IEs_t *ie;
|
||||
uint8_t *buffer = NULL;
|
||||
uint32_t length;
|
||||
/* Retrieve the NGAP gNB instance associated with Mod_id */
|
||||
ngap_gNB_instance_p = ngap_gNB_get_instance(instance);
|
||||
|
||||
DevAssert(ue_release_req_p != NULL);
|
||||
DevAssert(ngap_gNB_instance_p != NULL);
|
||||
|
||||
if ((ue_context_p = ngap_gNB_get_ue_context(ngap_gNB_instance_p,
|
||||
ue_release_req_p->gNB_ue_ngap_id)) == NULL) {
|
||||
/* The context for this gNB ue ngap id doesn't exist in the map of gNB UEs */
|
||||
NGAP_WARN("Failed to find ue context associated with gNB ue ngap id: %u\n",
|
||||
ue_release_req_p->gNB_ue_ngap_id);
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* Prepare the NGAP message to encode */
|
||||
memset(&pdu, 0, sizeof(pdu));
|
||||
pdu.present = NGAP_NGAP_PDU_PR_initiatingMessage;
|
||||
pdu.choice.initiatingMessage = CALLOC(1, sizeof(struct NGAP_InitiatingMessage));
|
||||
pdu.choice.initiatingMessage->procedureCode = NGAP_ProcedureCode_id_UEContextReleaseRequest;
|
||||
pdu.choice.initiatingMessage->criticality = NGAP_Criticality_ignore;
|
||||
pdu.choice.initiatingMessage->value.present = NGAP_InitiatingMessage__value_PR_UEContextReleaseRequest;
|
||||
out = &pdu.choice.initiatingMessage->value.choice.UEContextReleaseRequest;
|
||||
|
||||
/* mandatory */
|
||||
ie = (NGAP_UEContextReleaseRequest_IEs_t *)calloc(1, sizeof(NGAP_UEContextReleaseRequest_IEs_t));
|
||||
ie->id = NGAP_ProtocolIE_ID_id_AMF_UE_NGAP_ID;
|
||||
ie->criticality = NGAP_Criticality_reject;
|
||||
ie->value.present = NGAP_UEContextReleaseRequest_IEs__value_PR_AMF_UE_NGAP_ID;
|
||||
asn_uint642INTEGER(&ie->value.choice.AMF_UE_NGAP_ID, ue_context_p->amf_ue_ngap_id);
|
||||
ASN_SEQUENCE_ADD(&out->protocolIEs.list, ie);
|
||||
|
||||
/* mandatory */
|
||||
ie = (NGAP_UEContextReleaseRequest_IEs_t *)calloc(1, sizeof(NGAP_UEContextReleaseRequest_IEs_t));
|
||||
ie->id = NGAP_ProtocolIE_ID_id_RAN_UE_NGAP_ID;
|
||||
ie->criticality = NGAP_Criticality_reject;
|
||||
ie->value.present = NGAP_UEContextReleaseRequest_IEs__value_PR_RAN_UE_NGAP_ID;
|
||||
ie->value.choice.RAN_UE_NGAP_ID = ue_release_req_p->gNB_ue_ngap_id;
|
||||
ASN_SEQUENCE_ADD(&out->protocolIEs.list, ie);
|
||||
|
||||
/* mandatory */
|
||||
ie = (NGAP_UEContextReleaseRequest_IEs_t *)calloc(1, sizeof(NGAP_UEContextReleaseRequest_IEs_t));
|
||||
ie->id = NGAP_ProtocolIE_ID_id_Cause;
|
||||
ie->criticality = NGAP_Criticality_ignore;
|
||||
ie->value.present = NGAP_UEContextReleaseRequest_IEs__value_PR_Cause;
|
||||
|
||||
switch (ue_release_req_p->cause) {
|
||||
case NGAP_Cause_PR_radioNetwork:
|
||||
ie->value.choice.Cause.present = NGAP_Cause_PR_radioNetwork;
|
||||
ie->value.choice.Cause.choice.radioNetwork = ue_release_req_p->cause_value;
|
||||
break;
|
||||
|
||||
case NGAP_Cause_PR_transport:
|
||||
ie->value.choice.Cause.present = NGAP_Cause_PR_transport;
|
||||
ie->value.choice.Cause.choice.transport = ue_release_req_p->cause_value;
|
||||
break;
|
||||
|
||||
case NGAP_Cause_PR_nas:
|
||||
ie->value.choice.Cause.present = NGAP_Cause_PR_nas;
|
||||
ie->value.choice.Cause.choice.nas = ue_release_req_p->cause_value;
|
||||
break;
|
||||
|
||||
case NGAP_Cause_PR_protocol:
|
||||
ie->value.choice.Cause.present = NGAP_Cause_PR_protocol;
|
||||
ie->value.choice.Cause.choice.protocol = ue_release_req_p->cause_value;
|
||||
break;
|
||||
|
||||
case NGAP_Cause_PR_misc:
|
||||
ie->value.choice.Cause.present = NGAP_Cause_PR_misc;
|
||||
ie->value.choice.Cause.choice.misc = ue_release_req_p->cause_value;
|
||||
break;
|
||||
|
||||
case NGAP_Cause_PR_NOTHING:
|
||||
default:
|
||||
ie->value.choice.Cause.present = NGAP_Cause_PR_NOTHING;
|
||||
break;
|
||||
}
|
||||
|
||||
ASN_SEQUENCE_ADD(&out->protocolIEs.list, ie);
|
||||
|
||||
|
||||
|
||||
if (ngap_gNB_encode_pdu(&pdu, &buffer, &length) < 0) {
|
||||
/* Encode procedure has failed... */
|
||||
NGAP_ERROR("Failed to encode UE context release complete\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
MSC_LOG_TX_MESSAGE(
|
||||
MSC_NGAP_GNB,
|
||||
MSC_NGAP_AMF,
|
||||
buffer,
|
||||
length,
|
||||
MSC_AS_TIME_FMT" UEContextReleaseRequest initiatingMessage gNB_ue_ngap_id %u amf_ue_ngap_id %lu",
|
||||
0,0,//MSC_AS_TIME_ARGS(ctxt_pP),
|
||||
ue_release_req_p->gNB_ue_ngap_id,
|
||||
ue_context_p->amf_ue_ngap_id);
|
||||
|
||||
/* UE associated signalling -> use the allocated stream */
|
||||
ngap_gNB_itti_send_sctp_data_req(ngap_gNB_instance_p->instance,
|
||||
ue_context_p->amf_ref->assoc_id, buffer,
|
||||
length, ue_context_p->tx_stream);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
41
openair3/NGAP/ngap_gNB_context_management_procedures.h
Normal file
41
openair3/NGAP/ngap_gNB_context_management_procedures.h
Normal file
@@ -0,0 +1,41 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file ngap_gNB_context_management_procedures.h
|
||||
* \brief NGAP context management procedures
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \date 2020
|
||||
* \email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
* \version 1.0
|
||||
* @ingroup _ngap
|
||||
*/
|
||||
|
||||
#ifndef NGAP_GNB_CONTEXT_MANAGEMENT_PROCEDURES_H_
|
||||
#define NGAP_GNB_CONTEXT_MANAGEMENT_PROCEDURES_H_
|
||||
|
||||
|
||||
int ngap_ue_context_release_complete(instance_t instance,
|
||||
ngap_ue_release_complete_t *ue_release_complete_p);
|
||||
|
||||
int ngap_ue_context_release_req(instance_t instance,
|
||||
ngap_ue_release_req_t *ue_release_req_p);
|
||||
|
||||
#endif /* NGAP_GNB_CONTEXT_MANAGEMENT_PROCEDURES_H_ */
|
||||
188
openair3/NGAP/ngap_gNB_decoder.c
Normal file
188
openair3/NGAP/ngap_gNB_decoder.c
Normal file
@@ -0,0 +1,188 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file ngap_gNB_decoder.c
|
||||
* \brief ngap pdu decode procedures for gNB
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \email yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
* \date 2020
|
||||
* \version 0.1
|
||||
*/
|
||||
|
||||
|
||||
#include <stdio.h>
|
||||
|
||||
#include "assertions.h"
|
||||
|
||||
#include "intertask_interface.h"
|
||||
|
||||
#include "ngap_common.h"
|
||||
#include "ngap_gNB_decoder.h"
|
||||
|
||||
static int ngap_gNB_decode_initiating_message(NGAP_NGAP_PDU_t *pdu) {
|
||||
asn_encode_to_new_buffer_result_t res = { NULL, {0, NULL, NULL} };
|
||||
DevAssert(pdu != NULL);
|
||||
|
||||
switch(pdu->choice.initiatingMessage->procedureCode) {
|
||||
case NGAP_ProcedureCode_id_DownlinkNASTransport:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
break;
|
||||
|
||||
case NGAP_ProcedureCode_id_InitialContextSetup:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
break;
|
||||
|
||||
case NGAP_ProcedureCode_id_UEContextRelease:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
break;
|
||||
|
||||
case NGAP_ProcedureCode_id_Paging:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
NGAP_INFO("Paging initiating message\n");
|
||||
free(res.buffer);
|
||||
break;
|
||||
|
||||
case NGAP_ProcedureCode_id_PDUSessionResourceSetup:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
NGAP_INFO("PDUSESSIONSetup initiating message\n");
|
||||
break;
|
||||
|
||||
case NGAP_ProcedureCode_id_PDUSessionResourceModify:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
NGAP_INFO("PDUSESSIONModify initiating message\n");
|
||||
break;
|
||||
|
||||
case NGAP_ProcedureCode_id_PDUSessionResourceRelease:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
NGAP_INFO("TODO PDUSESSIONRelease initiating message\n");
|
||||
break;
|
||||
|
||||
case NGAP_ProcedureCode_id_ErrorIndication:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
NGAP_INFO("TODO ErrorIndication initiating message\n");
|
||||
break;
|
||||
|
||||
default:
|
||||
NGAP_ERROR("Unknown procedure ID (%d) for initiating message\n",
|
||||
(int)pdu->choice.initiatingMessage->procedureCode);
|
||||
AssertFatal( 0, "Unknown procedure ID (%d) for initiating message\n",
|
||||
(int)pdu->choice.initiatingMessage->procedureCode);
|
||||
return -1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int ngap_gNB_decode_successful_outcome(NGAP_NGAP_PDU_t *pdu) {
|
||||
asn_encode_to_new_buffer_result_t res = { NULL, {0, NULL, NULL} };
|
||||
DevAssert(pdu != NULL);
|
||||
|
||||
switch(pdu->choice.successfulOutcome->procedureCode) {
|
||||
case NGAP_ProcedureCode_id_NGSetup:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
break;
|
||||
|
||||
case NGAP_ProcedureCode_id_PathSwitchRequest:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
break;
|
||||
|
||||
case NGAP_ProcedureCode_id_PDUSessionResourceModifyIndication:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
break;
|
||||
|
||||
|
||||
default:
|
||||
NGAP_ERROR("Unknown procedure ID (%d) for successfull outcome message\n",
|
||||
(int)pdu->choice.successfulOutcome->procedureCode);
|
||||
return -1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int ngap_gNB_decode_unsuccessful_outcome(NGAP_NGAP_PDU_t *pdu) {
|
||||
asn_encode_to_new_buffer_result_t res = { NULL, {0, NULL, NULL} };
|
||||
DevAssert(pdu != NULL);
|
||||
|
||||
switch(pdu->choice.unsuccessfulOutcome->procedureCode) {
|
||||
case NGAP_ProcedureCode_id_NGSetup:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
break;
|
||||
case NGAP_ProcedureCode_id_PathSwitchRequest:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
break;
|
||||
|
||||
default:
|
||||
NGAP_ERROR("Unknown procedure ID (%d) for unsuccessfull outcome message\n",
|
||||
(int)pdu->choice.unsuccessfulOutcome->procedureCode);
|
||||
return -1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int ngap_gNB_decode_pdu(NGAP_NGAP_PDU_t *pdu, const uint8_t *const buffer,
|
||||
const uint32_t length) {
|
||||
asn_dec_rval_t dec_ret;
|
||||
DevAssert(pdu != NULL);
|
||||
DevAssert(buffer != NULL);
|
||||
dec_ret = aper_decode(NULL,
|
||||
&asn_DEF_NGAP_NGAP_PDU,
|
||||
(void **)&pdu,
|
||||
buffer,
|
||||
length,
|
||||
0,
|
||||
0);
|
||||
|
||||
if (dec_ret.code != RC_OK) {
|
||||
NGAP_ERROR("Failed to decode pdu\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
switch(pdu->present) {
|
||||
case NGAP_NGAP_PDU_PR_initiatingMessage:
|
||||
return ngap_gNB_decode_initiating_message(pdu);
|
||||
|
||||
case NGAP_NGAP_PDU_PR_successfulOutcome:
|
||||
return ngap_gNB_decode_successful_outcome(pdu);
|
||||
|
||||
case NGAP_NGAP_PDU_PR_unsuccessfulOutcome:
|
||||
return ngap_gNB_decode_unsuccessful_outcome(pdu);
|
||||
|
||||
default:
|
||||
NGAP_DEBUG("Unknown presence (%d) or not implemented\n", (int)pdu->present);
|
||||
break;
|
||||
}
|
||||
|
||||
return -1;
|
||||
}
|
||||
37
openair3/NGAP/ngap_gNB_decoder.h
Normal file
37
openair3/NGAP/ngap_gNB_decoder.h
Normal file
@@ -0,0 +1,37 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
/*! \file ngap_gNB_decoder.h
|
||||
* \brief ngap pdu decode procedures for gNB
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \email yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
* \date 2020
|
||||
* \version 0.1
|
||||
*/
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#ifndef NGAP_GNB_DECODER_H_
|
||||
#define NGAP_GNB_DECODER_H_
|
||||
|
||||
int ngap_gNB_decode_pdu(NGAP_NGAP_PDU_t *pdu, const uint8_t *const buffer,
|
||||
const uint32_t length) __attribute__ ((warn_unused_result));
|
||||
|
||||
#endif /* NGAP_GNB_DECODER_H_ */
|
||||
45
openair3/NGAP/ngap_gNB_default_values.h
Normal file
45
openair3/NGAP/ngap_gNB_default_values.h
Normal file
@@ -0,0 +1,45 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
/*! \file ngap_gNB_default_values.h
|
||||
* \brief ngap default values
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \email yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
* \date 2020
|
||||
* \version 0.1
|
||||
*/
|
||||
|
||||
#ifndef NGAP_GNB_DEFAULT_VALUES_H_
|
||||
#define NGAP_GNB_DEFAULT_VALUES_H_
|
||||
|
||||
#define GNB_TAC (1)
|
||||
#define GNB_MCC (208)
|
||||
#define GNB_MNC (92)
|
||||
|
||||
#define GNB_NAME "Eurecom GNB"
|
||||
#define GNB_NAME_FORMAT (GNB_NAME" %u")
|
||||
|
||||
#define NGAP_PORT_NUMBER (38412)
|
||||
#define NGAP_SCTP_PPID (60)
|
||||
|
||||
#define X2AP_PORT_NUMBER (36422)
|
||||
#define X2AP_SCTP_PPID (27)
|
||||
|
||||
#endif /* NGAP_GNB_DEFAULT_VALUES_H_ */
|
||||
298
openair3/NGAP/ngap_gNB_defs.h
Normal file
298
openair3/NGAP/ngap_gNB_defs.h
Normal file
@@ -0,0 +1,298 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file ngap_gNB_defs.h
|
||||
* \brief ngap define procedures for gNB
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \email yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
* \date 2020
|
||||
* \version 0.1
|
||||
*/
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#include "queue.h"
|
||||
#include "tree.h"
|
||||
|
||||
#ifndef NGAP_GNB_DEFS_H_
|
||||
#define NGAP_GNB_DEFS_H_
|
||||
|
||||
#define NGAP_GNB_NAME_LENGTH_MAX (150)
|
||||
|
||||
typedef enum {
|
||||
/* Disconnected state: initial state for any association. */
|
||||
NGAP_GNB_STATE_DISCONNECTED = 0x0,
|
||||
/* State waiting for S1 Setup response message if gNB is AMF accepted or
|
||||
* S1 Setup failure if AMF rejects the gNB.
|
||||
*/
|
||||
NGAP_GNB_STATE_WAITING = 0x1,
|
||||
/* The gNB is successfully connected to AMF, UE contexts can be created. */
|
||||
NGAP_GNB_STATE_CONNECTED = 0x2,
|
||||
/* The AMF has sent an overload start message. Once the AMF disables the
|
||||
* OVERLOAD marker, the state of the association will be
|
||||
* NGAP_GNB_STATE_CONNECTED.
|
||||
*/
|
||||
NGAP_GNB_OVERLOAD = 0x3,
|
||||
/* Max number of states available */
|
||||
NGAP_GNB_STATE_MAX,
|
||||
} ngap_gNB_state_t;
|
||||
|
||||
/* If the Overload Action IE in the OVERLOAD START message is set to
|
||||
* - “reject all RRC connection establishments for non-emergency mobile
|
||||
* originated data transfer E(i.e. reject traffic corresponding to RRC cause
|
||||
* “mo-data E(TS 36.331 [16])), or
|
||||
* - “reject all RRC connection establishments for signalling E(i.e. reject
|
||||
* traffic corresponding to RRC cause “modata Eand “mo-signalling E * (TS 38.331 [16])),or
|
||||
* - “only permit RRC connection establishments for emergency sessions and
|
||||
* mobile terminated services E(i.e. only permit traffic corresponding to RRC
|
||||
* cause “emergency Eand “mt-Access E(TS 36.331 [16])).
|
||||
*
|
||||
* NOTE: When the Overload Action IE is set to “only permit RRC connection
|
||||
* establishments for emergency sessions and mobile terminated services E
|
||||
* emergency calls with RRC cause “highPriorityAcess Efrom high priority users
|
||||
* are rejected (TS 24.301 [24]).
|
||||
*/
|
||||
typedef enum {
|
||||
NGAP_OVERLOAD_REJECT_MO_DATA = 0x0,
|
||||
NGAP_OVERLOAD_REJECT_ALL_SIGNALLING = 0x1,
|
||||
NGAP_OVERLOAD_ONLY_EMERGENCY_AND_MT = 0x2,
|
||||
NGAP_NO_OVERLOAD = 0x3,
|
||||
NGAP_OVERLOAD_MAX,
|
||||
} ngap_overload_state_t;
|
||||
|
||||
/* Served PLMN identity element */
|
||||
struct plmn_identity_s {
|
||||
uint16_t mcc;
|
||||
uint16_t mnc;
|
||||
uint8_t mnc_digit_length;
|
||||
STAILQ_ENTRY(plmn_identity_s) next;
|
||||
};
|
||||
|
||||
/* Served amf region id for a particular AMF */
|
||||
struct served_region_id_s {
|
||||
uint8_t amf_region_id;
|
||||
STAILQ_ENTRY(served_region_id_s) next;
|
||||
};
|
||||
|
||||
/* Served amf set id for a particular AMF */
|
||||
struct amf_set_id_s {
|
||||
uint16_t amf_set_id;
|
||||
STAILQ_ENTRY(amf_set_id_s) next;
|
||||
};
|
||||
|
||||
/* Served amf pointer for a particular AMF */
|
||||
struct amf_pointer_s {
|
||||
uint8_t amf_pointer;
|
||||
STAILQ_ENTRY(amf_pointer_s) next;
|
||||
};
|
||||
|
||||
|
||||
/* Served guami element */
|
||||
struct served_guami_s {
|
||||
/* Number of AMF served PLMNs */
|
||||
uint8_t nb_served_plmns;
|
||||
/* List of served PLMNs by AMF */
|
||||
STAILQ_HEAD(served_plmns_s, plmn_identity_s) served_plmns;
|
||||
|
||||
/* Number of region id in list */
|
||||
uint8_t nb_region_id;
|
||||
/* Served group id list */
|
||||
STAILQ_HEAD(served_region_ids_s, served_region_id_s) served_region_ids;
|
||||
|
||||
/* Number of AMF set id */
|
||||
uint8_t nb_amf_set_id;
|
||||
/* AMF Set id to uniquely identify an AMF within an AMF pool area */
|
||||
STAILQ_HEAD(amf_set_ids_s, amf_set_id_s) amf_set_ids;
|
||||
|
||||
/* Number of AMF pointer */
|
||||
uint8_t nb_amf_pointer;
|
||||
/* AMF pointer to uniquely identify an AMF within an AMF pool area */
|
||||
STAILQ_HEAD(amf_pointers_s, amf_pointer_s) amf_pointers;
|
||||
|
||||
/* Next GUAMI element */
|
||||
STAILQ_ENTRY(served_guami_s) next;
|
||||
};
|
||||
|
||||
/* NSSAI element */
|
||||
struct slice_support_s{
|
||||
uint8_t sST;
|
||||
uint8_t sD_flag;
|
||||
uint8_t sD[3];
|
||||
|
||||
/* Next slice element */
|
||||
STAILQ_ENTRY(slice_support_s) next;
|
||||
};
|
||||
|
||||
|
||||
/* plmn support element */
|
||||
struct plmn_support_s {
|
||||
struct plmn_identity_s plmn_identity;
|
||||
|
||||
/* Number of slice support in list */
|
||||
uint8_t nb_slice_s;
|
||||
/* Served group id list */
|
||||
STAILQ_HEAD(slice_supports_s, slice_support_s) slice_supports;
|
||||
|
||||
/* Next plmn support element */
|
||||
STAILQ_ENTRY(plmn_support_s) next;
|
||||
};
|
||||
|
||||
|
||||
struct ngap_gNB_instance_s;
|
||||
|
||||
/* This structure describes association of a gNB to a AMF */
|
||||
typedef struct ngap_gNB_amf_data_s {
|
||||
/* AMF descriptors tree, ordered by sctp assoc id */
|
||||
RB_ENTRY(ngap_gNB_amf_data_s) entry;
|
||||
|
||||
/* This is the optional name provided by the AMF */
|
||||
char *amf_name;
|
||||
|
||||
/* AMF NGAP IP address */
|
||||
net_ip_address_t amf_s1_ip;
|
||||
|
||||
/* List of served GUAMI per AMF. There is one GUAMI per RAT with a max
|
||||
* number of 8 RATs but in our case only one is used. The LTE related pool
|
||||
* configuration is included on the first place in the list.
|
||||
*/
|
||||
STAILQ_HEAD(served_guamis_s, served_guami_s) served_guami;
|
||||
|
||||
/* Relative processing capacity of an AMF with respect to the other AMFs
|
||||
* in the pool in order to load-balance AMFs within a pool as defined
|
||||
* in TS 23.401.
|
||||
*/
|
||||
uint8_t relative_amf_capacity;
|
||||
|
||||
/*
|
||||
* List of PLMN Support per AMF.
|
||||
*
|
||||
*/
|
||||
STAILQ_HEAD(plmn_supports_s, plmn_support_s) plmn_supports;
|
||||
|
||||
/* Current AMF overload information (if any). */
|
||||
ngap_overload_state_t overload_state;
|
||||
/* Current gNB->AMF NGAP association state */
|
||||
ngap_gNB_state_t state;
|
||||
|
||||
/* Next usable stream for UE signalling */
|
||||
int32_t nextstream;
|
||||
|
||||
/* Number of input/ouput streams */
|
||||
uint16_t in_streams;
|
||||
uint16_t out_streams;
|
||||
|
||||
/* Connexion id used between SCTP/NGAP */
|
||||
uint16_t cnx_id;
|
||||
|
||||
/* SCTP association id */
|
||||
int32_t assoc_id;
|
||||
|
||||
/* This is served PLMN IDs communicated to the AMF via an index over the
|
||||
* MCC/MNC array in ngap_gNB_instance */
|
||||
uint8_t broadcast_plmn_num;
|
||||
uint8_t broadcast_plmn_index[PLMN_LIST_MAX_SIZE];
|
||||
|
||||
|
||||
/* Only meaningfull in virtual mode */
|
||||
struct ngap_gNB_instance_s *ngap_gNB_instance;
|
||||
} ngap_gNB_amf_data_t;
|
||||
|
||||
typedef struct ngap_gNB_NSSAI_s{
|
||||
uint8_t sST;
|
||||
uint8_t sD_flag;
|
||||
uint8_t sD[3];
|
||||
}ngap_gNB_NSSAI_t;
|
||||
|
||||
typedef struct ngap_gNB_instance_s {
|
||||
/* Next ngap gNB association.
|
||||
* Only used for virtual mode.
|
||||
*/
|
||||
STAILQ_ENTRY(ngap_gNB_instance_s) ngap_gNB_entries;
|
||||
|
||||
/* Number of AMF requested by gNB (tree size) */
|
||||
uint32_t ngap_amf_nb;
|
||||
/* Number of AMF for which association is pending */
|
||||
uint32_t ngap_amf_pending_nb;
|
||||
/* Number of AMF successfully associated to gNB */
|
||||
uint32_t ngap_amf_associated_nb;
|
||||
/* Tree of NGAP AMF associations ordered by association ID */
|
||||
RB_HEAD(ngap_amf_map, ngap_gNB_amf_data_s) ngap_amf_head;
|
||||
|
||||
/* TODO: add a map ordered by relative AMF capacity */
|
||||
|
||||
/* Tree of UE ordered by gNB_ue_ngap_id's */
|
||||
RB_HEAD(ngap_ue_map, ngap_gNB_ue_context_s) ngap_ue_head;
|
||||
|
||||
/* For virtual mode, mod_id as defined in the rest of the L1/L2 stack */
|
||||
instance_t instance;
|
||||
|
||||
/* Displayable name of gNB */
|
||||
char *gNB_name;
|
||||
|
||||
/* Unique gNB_id to identify the gNB within EPC.
|
||||
* In our case the gNB is a macro gNB so the id will be 20 bits long.
|
||||
* For Home gNB id, this field should be 36 bits long.
|
||||
*/
|
||||
uint32_t gNB_id;
|
||||
/* The type of the cell */
|
||||
enum cell_type_e cell_type;
|
||||
|
||||
/* Tracking area code */
|
||||
uint32_t tac;
|
||||
|
||||
/* gNB NGAP IP address */
|
||||
net_ip_address_t gNB_ng_ip;
|
||||
|
||||
/* Mobile Country Code
|
||||
* Mobile Network Code
|
||||
*/
|
||||
uint16_t mcc[PLMN_LIST_MAX_SIZE];
|
||||
uint16_t mnc[PLMN_LIST_MAX_SIZE];
|
||||
uint8_t mnc_digit_length[PLMN_LIST_MAX_SIZE];
|
||||
uint8_t num_plmn;
|
||||
|
||||
uint16_t num_nssai[PLMN_LIST_MAX_SIZE];
|
||||
ngap_gNB_NSSAI_t s_nssai[PLMN_LIST_MAX_SIZE][8];
|
||||
|
||||
/* Default Paging DRX of the gNB as defined in TS 38.304 */
|
||||
ngap_paging_drx_t default_drx;
|
||||
} ngap_gNB_instance_t;
|
||||
|
||||
typedef struct {
|
||||
/* List of served gNBs
|
||||
* Only used for virtual mode
|
||||
*/
|
||||
STAILQ_HEAD(ngap_gNB_instances_head_s, ngap_gNB_instance_s) ngap_gNB_instances_head;
|
||||
/* Nb of registered gNBs */
|
||||
uint8_t nb_registered_gNBs;
|
||||
|
||||
/* Generate a unique connexion id used between NGAP and SCTP */
|
||||
uint16_t global_cnx_id;
|
||||
} ngap_gNB_internal_data_t;
|
||||
|
||||
int ngap_gNB_compare_assoc_id(
|
||||
struct ngap_gNB_amf_data_s *p1, struct ngap_gNB_amf_data_s *p2);
|
||||
|
||||
/* Generate the tree management functions */
|
||||
RB_PROTOTYPE(ngap_amf_map, ngap_gNB_amf_data_s, entry,
|
||||
ngap_gNB_compare_assoc_id);
|
||||
|
||||
#endif /* NGAP_GNB_DEFS_H_ */
|
||||
223
openair3/NGAP/ngap_gNB_encoder.c
Normal file
223
openair3/NGAP/ngap_gNB_encoder.c
Normal file
@@ -0,0 +1,223 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file ngap_gNB_encoder.c
|
||||
* \brief ngap pdu encode procedures for gNB
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \email yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
* \date 2020
|
||||
* \version 0.1
|
||||
*/
|
||||
|
||||
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include "assertions.h"
|
||||
#include "conversions.h"
|
||||
#include "intertask_interface.h"
|
||||
#include "ngap_common.h"
|
||||
#include "ngap_gNB_encoder.h"
|
||||
|
||||
static inline int ngap_gNB_encode_initiating(NGAP_NGAP_PDU_t *pdu,
|
||||
uint8_t **buffer,
|
||||
uint32_t *len);
|
||||
|
||||
static inline int ngap_gNB_encode_successfull_outcome(NGAP_NGAP_PDU_t *pdu,
|
||||
uint8_t **buffer, uint32_t *len);
|
||||
|
||||
static inline int ngap_gNB_encode_unsuccessfull_outcome(NGAP_NGAP_PDU_t *pdu,
|
||||
uint8_t **buffer, uint32_t *len);
|
||||
|
||||
int ngap_gNB_encode_pdu(NGAP_NGAP_PDU_t *pdu, uint8_t **buffer, uint32_t *len) {
|
||||
int ret = -1;
|
||||
DevAssert(pdu != NULL);
|
||||
DevAssert(buffer != NULL);
|
||||
DevAssert(len != NULL);
|
||||
|
||||
switch(pdu->present) {
|
||||
case NGAP_NGAP_PDU_PR_initiatingMessage:
|
||||
ret = ngap_gNB_encode_initiating(pdu, buffer, len);
|
||||
break;
|
||||
|
||||
case NGAP_NGAP_PDU_PR_successfulOutcome:
|
||||
ret = ngap_gNB_encode_successfull_outcome(pdu, buffer, len);
|
||||
break;
|
||||
|
||||
case NGAP_NGAP_PDU_PR_unsuccessfulOutcome:
|
||||
ret = ngap_gNB_encode_unsuccessfull_outcome(pdu, buffer, len);
|
||||
break;
|
||||
|
||||
default:
|
||||
NGAP_DEBUG("Unknown message outcome (%d) or not implemented",
|
||||
(int)pdu->present);
|
||||
return -1;
|
||||
}
|
||||
|
||||
ASN_STRUCT_FREE_CONTENTS_ONLY(asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
return ret;
|
||||
}
|
||||
|
||||
static inline
|
||||
int ngap_gNB_encode_initiating(NGAP_NGAP_PDU_t *pdu,
|
||||
uint8_t **buffer, uint32_t *len) {
|
||||
asn_encode_to_new_buffer_result_t res = { NULL, {0, NULL, NULL} };
|
||||
DevAssert(pdu != NULL);
|
||||
|
||||
switch(pdu->choice.initiatingMessage->procedureCode) {
|
||||
case NGAP_ProcedureCode_id_NGSetup:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
break;
|
||||
|
||||
case NGAP_ProcedureCode_id_UplinkNASTransport:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
break;
|
||||
|
||||
case NGAP_ProcedureCode_id_UERadioCapabilityInfoIndication:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
break;
|
||||
|
||||
case NGAP_ProcedureCode_id_InitialUEMessage:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
break;
|
||||
|
||||
case NGAP_ProcedureCode_id_NASNonDeliveryIndication:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
break;
|
||||
|
||||
case NGAP_ProcedureCode_id_UEContextReleaseRequest:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
break;
|
||||
|
||||
case NGAP_ProcedureCode_id_PathSwitchRequest:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
break;
|
||||
|
||||
case NGAP_ProcedureCode_id_PDUSessionResourceModifyIndication:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
break;
|
||||
|
||||
default:
|
||||
NGAP_DEBUG("Unknown procedure ID (%d) for initiating message\n",
|
||||
(int)pdu->choice.initiatingMessage->procedureCode);
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (asn1_xer_print) {
|
||||
xer_fprint(stdout, &asn_DEF_NGAP_NGAP_PDU, (void *)pdu);
|
||||
}
|
||||
|
||||
memset(&res, 0, sizeof(res));
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_ALIGNED_CANONICAL_PER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
*buffer = res.buffer;
|
||||
*len = res.result.encoded;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static inline
|
||||
int ngap_gNB_encode_successfull_outcome(NGAP_NGAP_PDU_t *pdu,
|
||||
uint8_t **buffer, uint32_t *len) {
|
||||
asn_encode_to_new_buffer_result_t res = { NULL, {0, NULL, NULL} };
|
||||
DevAssert(pdu != NULL);
|
||||
|
||||
switch(pdu->choice.successfulOutcome->procedureCode) {
|
||||
case NGAP_ProcedureCode_id_InitialContextSetup:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
break;
|
||||
|
||||
case NGAP_ProcedureCode_id_UEContextRelease:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
break;
|
||||
|
||||
case NGAP_ProcedureCode_id_PDUSessionResourceSetup:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
NGAP_INFO("PDUSESSIONSetup successful message\n");
|
||||
break;
|
||||
|
||||
case NGAP_ProcedureCode_id_PDUSessionResourceModify:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
NGAP_INFO("PDUSESSIONModify successful message\n");
|
||||
break;
|
||||
|
||||
case NGAP_ProcedureCode_id_PDUSessionResourceRelease:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
NGAP_INFO("PDUSESSION Release successful message\n");
|
||||
break;
|
||||
|
||||
default:
|
||||
NGAP_WARN("Unknown procedure ID (%d) for successfull outcome message\n",
|
||||
(int)pdu->choice.successfulOutcome->procedureCode);
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (asn1_xer_print) {
|
||||
xer_fprint(stdout, &asn_DEF_NGAP_NGAP_PDU, (void *)pdu);
|
||||
}
|
||||
|
||||
memset(&res, 0, sizeof(res));
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_ALIGNED_CANONICAL_PER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
*buffer = res.buffer;
|
||||
*len = res.result.encoded;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static inline
|
||||
int ngap_gNB_encode_unsuccessfull_outcome(NGAP_NGAP_PDU_t *pdu,
|
||||
uint8_t **buffer, uint32_t *len) {
|
||||
asn_encode_to_new_buffer_result_t res = { NULL, {0, NULL, NULL} };
|
||||
DevAssert(pdu != NULL);
|
||||
|
||||
switch(pdu->choice.unsuccessfulOutcome->procedureCode) {
|
||||
case NGAP_ProcedureCode_id_InitialContextSetup:
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_CANONICAL_XER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
free(res.buffer);
|
||||
break;
|
||||
|
||||
default:
|
||||
NGAP_DEBUG("Unknown procedure ID (%d) for unsuccessfull outcome message\n",
|
||||
(int)pdu->choice.unsuccessfulOutcome->procedureCode);
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (asn1_xer_print) {
|
||||
xer_fprint(stdout, &asn_DEF_NGAP_NGAP_PDU, (void *)pdu);
|
||||
}
|
||||
|
||||
memset(&res, 0, sizeof(res));
|
||||
res = asn_encode_to_new_buffer(NULL, ATS_ALIGNED_CANONICAL_PER, &asn_DEF_NGAP_NGAP_PDU, pdu);
|
||||
*buffer = res.buffer;
|
||||
*len = res.result.encoded;
|
||||
return 0;
|
||||
}
|
||||
36
openair3/NGAP/ngap_gNB_encoder.h
Normal file
36
openair3/NGAP/ngap_gNB_encoder.h
Normal file
@@ -0,0 +1,36 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file ngap_gNB_encoder.h
|
||||
* \brief ngap pdu encode procedures for gNB
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \email yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
* \date 2020
|
||||
* \version 0.1
|
||||
*/
|
||||
|
||||
#ifndef NGAP_GNB_ENCODER_H_
|
||||
#define NGAP_GNB_ENCODER_H_
|
||||
|
||||
int ngap_gNB_encode_pdu(NGAP_NGAP_PDU_t *pdu, uint8_t **buffer, uint32_t *len)
|
||||
__attribute__ ((warn_unused_result));
|
||||
|
||||
#endif /* NGAP_GNB_ENCODER_H_ */
|
||||
1883
openair3/NGAP/ngap_gNB_handlers.c
Normal file
1883
openair3/NGAP/ngap_gNB_handlers.c
Normal file
File diff suppressed because it is too large
Load Diff
38
openair3/NGAP/ngap_gNB_handlers.h
Normal file
38
openair3/NGAP/ngap_gNB_handlers.h
Normal file
@@ -0,0 +1,38 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file ngap_gNB_handlers.h
|
||||
* \brief ngap messages handlers for gNB part
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \email yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
* \date 2020
|
||||
* \version 0.1
|
||||
*/
|
||||
|
||||
#ifndef NGAP_GNB_HANDLERS_H_
|
||||
#define NGAP_GNB_HANDLERS_H_
|
||||
|
||||
void ngap_handle_ng_setup_message(ngap_gNB_amf_data_t *amf_desc_p, int sctp_shutdown);
|
||||
|
||||
int ngap_gNB_handle_message(uint32_t assoc_id, int32_t stream,
|
||||
const uint8_t * const data, const uint32_t data_length);
|
||||
|
||||
#endif /* NGAP_GNB_HANDLERS_H_ */
|
||||
85
openair3/NGAP/ngap_gNB_itti_messaging.c
Normal file
85
openair3/NGAP/ngap_gNB_itti_messaging.c
Normal file
@@ -0,0 +1,85 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file ngap_gNB_itti_messaging.c
|
||||
* \brief ngap itti messages handlers for gNB
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \email yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
* \date 2020
|
||||
* \version 0.1
|
||||
*/
|
||||
|
||||
#include "intertask_interface.h"
|
||||
|
||||
#include "ngap_gNB_itti_messaging.h"
|
||||
|
||||
void ngap_gNB_itti_send_sctp_data_req(instance_t instance, int32_t assoc_id, uint8_t *buffer,
|
||||
uint32_t buffer_length, uint16_t stream)
|
||||
{
|
||||
MessageDef *message_p;
|
||||
sctp_data_req_t *sctp_data_req;
|
||||
|
||||
message_p = itti_alloc_new_message(TASK_NGAP, SCTP_DATA_REQ);
|
||||
|
||||
sctp_data_req = &message_p->ittiMsg.sctp_data_req;
|
||||
|
||||
sctp_data_req->assoc_id = assoc_id;
|
||||
sctp_data_req->buffer = buffer;
|
||||
sctp_data_req->buffer_length = buffer_length;
|
||||
sctp_data_req->stream = stream;
|
||||
|
||||
itti_send_msg_to_task(TASK_SCTP, instance, message_p);
|
||||
}
|
||||
|
||||
void ngap_gNB_itti_send_nas_downlink_ind(instance_t instance,
|
||||
uint16_t ue_initial_id,
|
||||
uint32_t gNB_ue_ngap_id,
|
||||
uint8_t *nas_pdu,
|
||||
uint32_t nas_pdu_length)
|
||||
{
|
||||
MessageDef *message_p;
|
||||
ngap_downlink_nas_t *ngap_downlink_nas;
|
||||
|
||||
message_p = itti_alloc_new_message(TASK_NGAP, NGAP_DOWNLINK_NAS);
|
||||
|
||||
ngap_downlink_nas = &message_p->ittiMsg.ngap_downlink_nas;
|
||||
|
||||
ngap_downlink_nas->ue_initial_id = ue_initial_id;
|
||||
ngap_downlink_nas->gNB_ue_ngap_id = gNB_ue_ngap_id;
|
||||
ngap_downlink_nas->nas_pdu.buffer = malloc(sizeof(uint8_t) * nas_pdu_length);
|
||||
memcpy(ngap_downlink_nas->nas_pdu.buffer, nas_pdu, nas_pdu_length);
|
||||
ngap_downlink_nas->nas_pdu.length = nas_pdu_length;
|
||||
|
||||
itti_send_msg_to_task(TASK_RRC_GNB, instance, message_p);
|
||||
}
|
||||
|
||||
void ngap_gNB_itti_send_sctp_close_association(instance_t instance, int32_t assoc_id)
|
||||
{
|
||||
MessageDef *message_p = NULL;
|
||||
sctp_close_association_t *sctp_close_association_p = NULL;
|
||||
|
||||
message_p = itti_alloc_new_message(TASK_NGAP, SCTP_CLOSE_ASSOCIATION);
|
||||
sctp_close_association_p = &message_p->ittiMsg.sctp_close_association;
|
||||
sctp_close_association_p->assoc_id = assoc_id;
|
||||
|
||||
itti_send_msg_to_task(TASK_SCTP, instance, message_p);
|
||||
}
|
||||
|
||||
46
openair3/NGAP/ngap_gNB_itti_messaging.h
Normal file
46
openair3/NGAP/ngap_gNB_itti_messaging.h
Normal file
@@ -0,0 +1,46 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file ngap_gNB_itti_messaging.h
|
||||
* \brief ngap itti messages handlers for gNB
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \email yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
* \date 2020
|
||||
* \version 0.1
|
||||
*/
|
||||
|
||||
#ifndef NGAP_GNB_ITTI_MESSAGING_H_
|
||||
#define NGAP_GNB_ITTI_MESSAGING_H_
|
||||
|
||||
void ngap_gNB_itti_send_sctp_data_req(instance_t instance, int32_t assoc_id, uint8_t *buffer,
|
||||
uint32_t buffer_length, uint16_t stream);
|
||||
|
||||
void ngap_gNB_itti_send_nas_downlink_ind(instance_t instance,
|
||||
uint16_t ue_initial_id,
|
||||
uint32_t gNB_ue_ngap_id,
|
||||
uint8_t *nas_pdu,
|
||||
uint32_t nas_pdu_length);
|
||||
|
||||
void ngap_gNB_itti_send_sctp_close_association(instance_t instance,
|
||||
int32_t assoc_id);
|
||||
|
||||
|
||||
#endif /* NGAP_GNB_ITTI_MESSAGING_H_ */
|
||||
193
openair3/NGAP/ngap_gNB_management_procedures.c
Normal file
193
openair3/NGAP/ngap_gNB_management_procedures.c
Normal file
@@ -0,0 +1,193 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file ngap_gNB_management_procedures.c
|
||||
* \brief NGAP gNB task
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \date 2020
|
||||
* \email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
* \version 1.0
|
||||
* @ingroup _ngap
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include "intertask_interface.h"
|
||||
|
||||
#include "assertions.h"
|
||||
#include "conversions.h"
|
||||
|
||||
#include "ngap_common.h"
|
||||
#include "ngap_gNB_defs.h"
|
||||
#include "ngap_gNB.h"
|
||||
|
||||
ngap_gNB_internal_data_t ngap_gNB_internal_data;
|
||||
|
||||
RB_GENERATE(ngap_amf_map, ngap_gNB_amf_data_s, entry, ngap_gNB_compare_assoc_id);
|
||||
|
||||
int ngap_gNB_compare_assoc_id(
|
||||
struct ngap_gNB_amf_data_s *p1, struct ngap_gNB_amf_data_s *p2)
|
||||
{
|
||||
if (p1->assoc_id == -1) {
|
||||
if (p1->cnx_id < p2->cnx_id) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (p1->cnx_id > p2->cnx_id) {
|
||||
return 1;
|
||||
}
|
||||
} else {
|
||||
if (p1->assoc_id < p2->assoc_id) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (p1->assoc_id > p2->assoc_id) {
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
/* Matching reference */
|
||||
return 0;
|
||||
}
|
||||
|
||||
uint16_t ngap_gNB_fetch_add_global_cnx_id(void)
|
||||
{
|
||||
return ++ngap_gNB_internal_data.global_cnx_id;
|
||||
}
|
||||
|
||||
void ngap_gNB_prepare_internal_data(void)
|
||||
{
|
||||
memset(&ngap_gNB_internal_data, 0, sizeof(ngap_gNB_internal_data));
|
||||
STAILQ_INIT(&ngap_gNB_internal_data.ngap_gNB_instances_head);
|
||||
}
|
||||
|
||||
void ngap_gNB_insert_new_instance(ngap_gNB_instance_t *new_instance_p)
|
||||
{
|
||||
DevAssert(new_instance_p != NULL);
|
||||
|
||||
STAILQ_INSERT_TAIL(&ngap_gNB_internal_data.ngap_gNB_instances_head,
|
||||
new_instance_p, ngap_gNB_entries);
|
||||
}
|
||||
|
||||
struct ngap_gNB_amf_data_s *ngap_gNB_get_AMF(
|
||||
ngap_gNB_instance_t *instance_p,
|
||||
int32_t assoc_id, uint16_t cnx_id)
|
||||
{
|
||||
struct ngap_gNB_amf_data_s temp;
|
||||
struct ngap_gNB_amf_data_s *found;
|
||||
|
||||
memset(&temp, 0, sizeof(struct ngap_gNB_amf_data_s));
|
||||
|
||||
temp.assoc_id = assoc_id;
|
||||
temp.cnx_id = cnx_id;
|
||||
|
||||
if (instance_p == NULL) {
|
||||
STAILQ_FOREACH(instance_p, &ngap_gNB_internal_data.ngap_gNB_instances_head,
|
||||
ngap_gNB_entries) {
|
||||
found = RB_FIND(ngap_amf_map, &instance_p->ngap_amf_head, &temp);
|
||||
|
||||
if (found != NULL) {
|
||||
return found;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
return RB_FIND(ngap_amf_map, &instance_p->ngap_amf_head, &temp);
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
struct ngap_gNB_amf_data_s *ngap_gNB_get_AMF_from_instance(
|
||||
ngap_gNB_instance_t *instance_p)
|
||||
{
|
||||
|
||||
struct ngap_gNB_amf_data_s *amf = NULL;
|
||||
struct ngap_gNB_amf_data_s *amf_next = NULL;
|
||||
|
||||
for (amf = RB_MIN(ngap_amf_map, &instance_p->ngap_amf_head); amf!=NULL ; amf = amf_next) {
|
||||
amf_next = RB_NEXT(ngap_amf_map, &instance_p->ngap_amf_head, amf);
|
||||
if (amf->ngap_gNB_instance == instance_p) {
|
||||
return amf;
|
||||
}
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
ngap_gNB_instance_t *ngap_gNB_get_instance(instance_t instance)
|
||||
{
|
||||
ngap_gNB_instance_t *temp = NULL;
|
||||
|
||||
STAILQ_FOREACH(temp, &ngap_gNB_internal_data.ngap_gNB_instances_head,
|
||||
ngap_gNB_entries) {
|
||||
if (temp->instance == instance) {
|
||||
/* Matching occurence */
|
||||
return temp;
|
||||
}
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
void ngap_gNB_remove_amf_desc(ngap_gNB_instance_t * instance)
|
||||
{
|
||||
|
||||
struct ngap_gNB_amf_data_s *amf = NULL;
|
||||
struct ngap_gNB_amf_data_s *amfNext = NULL;
|
||||
struct plmn_identity_s* plmnInfo;
|
||||
struct served_region_id_s* regionInfo;
|
||||
struct served_guami_s* guamInfo;
|
||||
struct amf_set_id_s* amfSet;
|
||||
struct amf_pointer_s* amfPoint;
|
||||
for (amf = RB_MIN(ngap_amf_map, &instance->ngap_amf_head); amf; amf = amfNext) {
|
||||
amfNext = RB_NEXT(ngap_amf_map, &instance->ngap_amf_head, amf);
|
||||
RB_REMOVE(ngap_amf_map, &instance->ngap_amf_head, amf);
|
||||
while (!STAILQ_EMPTY(&amf->served_guami)) {
|
||||
guamInfo = STAILQ_FIRST(&amf->served_guami);
|
||||
STAILQ_REMOVE_HEAD(&amf->served_guami, next);
|
||||
|
||||
while (!STAILQ_EMPTY(&guamInfo->served_plmns)) {
|
||||
plmnInfo = STAILQ_FIRST(&guamInfo->served_plmns);
|
||||
STAILQ_REMOVE_HEAD(&guamInfo->served_plmns, next);
|
||||
free(plmnInfo);
|
||||
}
|
||||
while (!STAILQ_EMPTY(&guamInfo->served_region_ids)) {
|
||||
regionInfo = STAILQ_FIRST(&guamInfo->served_region_ids);
|
||||
STAILQ_REMOVE_HEAD(&guamInfo->served_region_ids, next);
|
||||
free(regionInfo);
|
||||
}
|
||||
while (!STAILQ_EMPTY(&guamInfo->amf_set_ids)) {
|
||||
amfSet = STAILQ_FIRST(&guamInfo->amf_set_ids);
|
||||
STAILQ_REMOVE_HEAD(&guamInfo->amf_set_ids, next);
|
||||
free(amfSet);
|
||||
}
|
||||
while (!STAILQ_EMPTY(&guamInfo->amf_pointers)) {
|
||||
amfPoint = STAILQ_FIRST(&guamInfo->amf_pointers);
|
||||
STAILQ_REMOVE_HEAD(&guamInfo->amf_pointers, next);
|
||||
free(amfPoint);
|
||||
}
|
||||
free(guamInfo);
|
||||
}
|
||||
free(amf);
|
||||
}
|
||||
}
|
||||
50
openair3/NGAP/ngap_gNB_management_procedures.h
Normal file
50
openair3/NGAP/ngap_gNB_management_procedures.h
Normal file
@@ -0,0 +1,50 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file ngap_gNB_management_procedures.h
|
||||
* \brief NGAP gNB task
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \date 2020
|
||||
* \email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
* \version 1.0
|
||||
* @ingroup _ngap
|
||||
*/
|
||||
|
||||
#ifndef NGAP_GNB_MANAGEMENT_PROCEDURES_H_
|
||||
#define NGAP_GNB_MANAGEMENT_PROCEDURES_H_
|
||||
|
||||
struct ngap_gNB_amf_data_s *ngap_gNB_get_AMF(
|
||||
ngap_gNB_instance_t *instance_p,
|
||||
int32_t assoc_id, uint16_t cnx_id);
|
||||
|
||||
struct ngap_gNB_amf_data_s *ngap_gNB_get_AMF_from_instance(ngap_gNB_instance_t *instance_p);
|
||||
|
||||
void ngap_gNB_remove_amf_desc(ngap_gNB_instance_t * instance);
|
||||
|
||||
void ngap_gNB_insert_new_instance(ngap_gNB_instance_t *new_instance_p);
|
||||
|
||||
ngap_gNB_instance_t *ngap_gNB_get_instance(uint8_t mod_id);
|
||||
|
||||
uint16_t ngap_gNB_fetch_add_global_cnx_id(void);
|
||||
|
||||
void ngap_gNB_prepare_internal_data(void);
|
||||
|
||||
#endif /* NGAP_GNB_MANAGEMENT_PROCEDURES_H_ */
|
||||
1463
openair3/NGAP/ngap_gNB_nas_procedures.c
Normal file
1463
openair3/NGAP/ngap_gNB_nas_procedures.c
Normal file
File diff suppressed because it is too large
Load Diff
68
openair3/NGAP/ngap_gNB_nas_procedures.h
Normal file
68
openair3/NGAP/ngap_gNB_nas_procedures.h
Normal file
@@ -0,0 +1,68 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file ngap_gNB_nas_procedures.h
|
||||
* \brief NGAP gNb NAS procedure handler
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \date 2020
|
||||
* \email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
* \version 1.0
|
||||
* @ingroup _ngap
|
||||
*/
|
||||
|
||||
#ifndef NGAP_GNB_NAS_PROCEDURES_H_
|
||||
#define NGAP_GNB_NAS_PROCEDURES_H_
|
||||
|
||||
int ngap_gNB_handle_nas_downlink(
|
||||
uint32_t assoc_id,
|
||||
uint32_t stream,
|
||||
NGAP_NGAP_PDU_t *pdu);
|
||||
|
||||
int ngap_gNB_nas_uplink(instance_t instance, ngap_uplink_nas_t *ngap_uplink_nas_p);
|
||||
|
||||
int ngap_gNB_nas_non_delivery_ind(instance_t instance,
|
||||
ngap_nas_non_delivery_ind_t *ngap_nas_non_delivery_ind);
|
||||
|
||||
int ngap_gNB_handle_nas_first_req(
|
||||
instance_t instance, ngap_nas_first_req_t *ngap_nas_first_req_p);
|
||||
|
||||
int ngap_gNB_initial_ctxt_resp(
|
||||
instance_t instance, ngap_initial_context_setup_resp_t *initial_ctxt_resp_p);
|
||||
|
||||
int ngap_gNB_ue_capabilities(instance_t instance,
|
||||
ngap_ue_cap_info_ind_t *ue_cap_info_ind_p);
|
||||
|
||||
int ngap_gNB_pdusession_setup_resp(instance_t instance,
|
||||
ngap_pdusession_setup_resp_t *pdusession_setup_resp_p);
|
||||
|
||||
int ngap_gNB_pdusession_modify_resp(instance_t instance,
|
||||
ngap_pdusession_modify_resp_t *pdusession_modify_resp_p);
|
||||
|
||||
int ngap_gNB_pdusession_release_resp(instance_t instance,
|
||||
ngap_pdusession_release_resp_t *pdusession_release_resp_p);
|
||||
|
||||
int ngap_gNB_path_switch_req(instance_t instance,
|
||||
ngap_path_switch_req_t *path_switch_req_p);
|
||||
|
||||
int ngap_gNB_generate_PDUSESSION_Modification_Indication(
|
||||
instance_t instance, ngap_pdusession_modification_ind_t *pdusession_modification_ind);
|
||||
|
||||
#endif /* NGAP_GNB_NAS_PROCEDURES_H_ */
|
||||
410
openair3/NGAP/ngap_gNB_nnsf.c
Normal file
410
openair3/NGAP/ngap_gNB_nnsf.c
Normal file
@@ -0,0 +1,410 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file ngap_gNB_nnsf.c
|
||||
* \brief ngap NAS node selection functions
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \date 2020
|
||||
* \version 0.1
|
||||
* \email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
*/
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#include "intertask_interface.h"
|
||||
|
||||
#include "ngap_common.h"
|
||||
|
||||
#include "ngap_gNB_defs.h"
|
||||
#include "ngap_gNB_nnsf.h"
|
||||
|
||||
struct ngap_gNB_amf_data_s *
|
||||
ngap_gNB_nnsf_select_amf(ngap_gNB_instance_t *instance_p,
|
||||
ngap_rrc_establishment_cause_t cause)
|
||||
{
|
||||
struct ngap_gNB_amf_data_s *amf_data_p = NULL;
|
||||
struct ngap_gNB_amf_data_s *amf_highest_capacity_p = NULL;
|
||||
uint8_t current_capacity = 0;
|
||||
|
||||
RB_FOREACH(amf_data_p, ngap_amf_map, &instance_p->ngap_amf_head) {
|
||||
if (amf_data_p->state != NGAP_GNB_STATE_CONNECTED) {
|
||||
/* The association between AMF and gNB is not ready for the moment,
|
||||
* go to the next known AMF.
|
||||
*/
|
||||
if (amf_data_p->state == NGAP_GNB_OVERLOAD) {
|
||||
/* AMF is overloaded. We have to check the RRC establishment
|
||||
* cause and take decision to the select this AMF depending on
|
||||
* the overload state.
|
||||
*/
|
||||
if ((cause == NGAP_RRC_CAUSE_MO_DATA)
|
||||
&& (amf_data_p->overload_state == NGAP_OVERLOAD_REJECT_MO_DATA)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if ((amf_data_p->overload_state == NGAP_OVERLOAD_REJECT_ALL_SIGNALLING)
|
||||
&& ((cause == NGAP_RRC_CAUSE_MO_SIGNALLING) || (cause == NGAP_RRC_CAUSE_MO_DATA))) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if ((amf_data_p->overload_state == NGAP_OVERLOAD_ONLY_EMERGENCY_AND_MT)
|
||||
&& ((cause == NGAP_RRC_CAUSE_MO_SIGNALLING) || (cause == NGAP_RRC_CAUSE_MO_DATA)
|
||||
|| (cause == NGAP_RRC_CAUSE_HIGH_PRIO_ACCESS))) {
|
||||
continue;
|
||||
}
|
||||
|
||||
/* At this point, the RRC establishment can be handled by the AMF
|
||||
* even if it is in overload state.
|
||||
*/
|
||||
} else {
|
||||
/* The AMF is not overloaded, association is simply not ready. */
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
if (current_capacity < amf_data_p->relative_amf_capacity) {
|
||||
/* We find a better AMF, keep a reference to it */
|
||||
current_capacity = amf_data_p->relative_amf_capacity;
|
||||
amf_highest_capacity_p = amf_data_p;
|
||||
}
|
||||
}
|
||||
|
||||
return amf_highest_capacity_p;
|
||||
}
|
||||
|
||||
struct ngap_gNB_amf_data_s *
|
||||
ngap_gNB_nnsf_select_amf_by_plmn_id(ngap_gNB_instance_t *instance_p,
|
||||
ngap_rrc_establishment_cause_t cause,
|
||||
int selected_plmn_identity)
|
||||
{
|
||||
struct ngap_gNB_amf_data_s *amf_data_p = NULL;
|
||||
struct ngap_gNB_amf_data_s *amf_highest_capacity_p = NULL;
|
||||
uint8_t current_capacity = 0;
|
||||
|
||||
RB_FOREACH(amf_data_p, ngap_amf_map, &instance_p->ngap_amf_head) {
|
||||
struct served_guami_s *guami_p = NULL;
|
||||
struct plmn_identity_s *served_plmn_p = NULL;
|
||||
if (amf_data_p->state != NGAP_GNB_STATE_CONNECTED) {
|
||||
/* The association between AMF and gNB is not ready for the moment,
|
||||
* go to the next known AMF.
|
||||
*/
|
||||
if (amf_data_p->state == NGAP_GNB_OVERLOAD) {
|
||||
/* AMF is overloaded. We have to check the RRC establishment
|
||||
* cause and take decision to the select this AMF depending on
|
||||
* the overload state.
|
||||
*/
|
||||
if ((cause == NGAP_RRC_CAUSE_MO_DATA)
|
||||
&& (amf_data_p->overload_state == NGAP_OVERLOAD_REJECT_MO_DATA)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if ((amf_data_p->overload_state == NGAP_OVERLOAD_REJECT_ALL_SIGNALLING)
|
||||
&& ((cause == NGAP_RRC_CAUSE_MO_SIGNALLING) || (cause == NGAP_RRC_CAUSE_MO_DATA))) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if ((amf_data_p->overload_state == NGAP_OVERLOAD_ONLY_EMERGENCY_AND_MT)
|
||||
&& ((cause == NGAP_RRC_CAUSE_MO_SIGNALLING) || (cause == NGAP_RRC_CAUSE_MO_DATA)
|
||||
|| (cause == NGAP_RRC_CAUSE_HIGH_PRIO_ACCESS))) {
|
||||
continue;
|
||||
}
|
||||
|
||||
/* At this point, the RRC establishment can be handled by the AMF
|
||||
* even if it is in overload state.
|
||||
*/
|
||||
} else {
|
||||
/* The AMF is not overloaded, association is simply not ready. */
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
/* Looking for served GUAMI PLMN Identity selected matching the one provided by the UE */
|
||||
STAILQ_FOREACH(guami_p, &amf_data_p->served_guami, next) {
|
||||
STAILQ_FOREACH(served_plmn_p, &guami_p->served_plmns, next) {
|
||||
if ((served_plmn_p->mcc == instance_p->mcc[selected_plmn_identity]) &&
|
||||
(served_plmn_p->mnc == instance_p->mnc[selected_plmn_identity])) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
/* if found, we can stop the outer loop, too */
|
||||
if (served_plmn_p) break;
|
||||
}
|
||||
/* if we didn't find such a served PLMN, go on with the next AMF */
|
||||
if (!served_plmn_p) continue;
|
||||
|
||||
if (current_capacity < amf_data_p->relative_amf_capacity) {
|
||||
/* We find a better AMF, keep a reference to it */
|
||||
current_capacity = amf_data_p->relative_amf_capacity;
|
||||
amf_highest_capacity_p = amf_data_p;
|
||||
}
|
||||
}
|
||||
|
||||
return amf_highest_capacity_p;
|
||||
}
|
||||
|
||||
struct ngap_gNB_amf_data_s *
|
||||
ngap_gNB_nnsf_select_amf_by_amf_setid(ngap_gNB_instance_t *instance_p,
|
||||
ngap_rrc_establishment_cause_t cause,
|
||||
int selected_plmn_identity,
|
||||
uint8_t amf_setid)
|
||||
{
|
||||
struct ngap_gNB_amf_data_s *amf_data_p = NULL;
|
||||
|
||||
RB_FOREACH(amf_data_p, ngap_amf_map, &instance_p->ngap_amf_head) {
|
||||
struct served_guami_s *guami_p = NULL;
|
||||
|
||||
if (amf_data_p->state != NGAP_GNB_STATE_CONNECTED) {
|
||||
/* The association between AMF and gNB is not ready for the moment,
|
||||
* go to the next known AMF.
|
||||
*/
|
||||
if (amf_data_p->state == NGAP_GNB_OVERLOAD) {
|
||||
/* AMF is overloaded. We have to check the RRC establishment
|
||||
* cause and take decision to the select this AMF depending on
|
||||
* the overload state.
|
||||
*/
|
||||
if ((cause == NGAP_RRC_CAUSE_MO_DATA)
|
||||
&& (amf_data_p->overload_state == NGAP_OVERLOAD_REJECT_MO_DATA)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if ((amf_data_p->overload_state == NGAP_OVERLOAD_REJECT_ALL_SIGNALLING)
|
||||
&& ((cause == NGAP_RRC_CAUSE_MO_SIGNALLING) || (cause == NGAP_RRC_CAUSE_MO_DATA))) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if ((amf_data_p->overload_state == NGAP_OVERLOAD_ONLY_EMERGENCY_AND_MT)
|
||||
&& ((cause == NGAP_RRC_CAUSE_MO_SIGNALLING) || (cause == NGAP_RRC_CAUSE_MO_DATA)
|
||||
|| (cause == NGAP_RRC_CAUSE_HIGH_PRIO_ACCESS))) {
|
||||
continue;
|
||||
}
|
||||
|
||||
/* At this point, the RRC establishment can be handled by the AMF
|
||||
* even if it is in overload state.
|
||||
*/
|
||||
} else {
|
||||
/* The AMF is not overloaded, association is simply not ready. */
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
/* Looking for AMF code matching the one provided by NAS */
|
||||
STAILQ_FOREACH(guami_p, &amf_data_p->served_guami, next) {
|
||||
struct amf_set_id_s *amf_setid_p = NULL;
|
||||
struct plmn_identity_s *served_plmn_p = NULL;
|
||||
|
||||
STAILQ_FOREACH(served_plmn_p, &guami_p->served_plmns, next) {
|
||||
if ((served_plmn_p->mcc == instance_p->mcc[selected_plmn_identity]) &&
|
||||
(served_plmn_p->mnc == instance_p->mnc[selected_plmn_identity])) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
STAILQ_FOREACH(amf_setid_p, &guami_p->amf_set_ids, next) {
|
||||
if (amf_setid_p->amf_set_id == amf_setid) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/* The AMF matches the parameters provided by the NAS layer ->
|
||||
* the AMF is knwown and the association is ready.
|
||||
* Return the reference to the AMF to use it for this UE.
|
||||
*/
|
||||
if (amf_setid_p && served_plmn_p) {
|
||||
return amf_data_p;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* At this point no AMF matches the selected PLMN and AMF code. In this case,
|
||||
* return NULL. That way the RRC layer should know about it and reject RRC
|
||||
* connectivity. */
|
||||
return NULL;
|
||||
}
|
||||
|
||||
struct ngap_gNB_amf_data_s *
|
||||
ngap_gNB_nnsf_select_amf_by_guami(ngap_gNB_instance_t *instance_p,
|
||||
ngap_rrc_establishment_cause_t cause,
|
||||
ngap_guami_t guami)
|
||||
{
|
||||
struct ngap_gNB_amf_data_s *amf_data_p = NULL;
|
||||
|
||||
RB_FOREACH(amf_data_p, ngap_amf_map, &instance_p->ngap_amf_head) {
|
||||
struct served_guami_s *guami_p = NULL;
|
||||
|
||||
if (amf_data_p->state != NGAP_GNB_STATE_CONNECTED) {
|
||||
/* The association between AMF and gNB is not ready for the moment,
|
||||
* go to the next known AMF.
|
||||
*/
|
||||
if (amf_data_p->state == NGAP_GNB_OVERLOAD) {
|
||||
/* AMF is overloaded. We have to check the RRC establishment
|
||||
* cause and take decision to the select this AMF depending on
|
||||
* the overload state.
|
||||
*/
|
||||
if ((cause == NGAP_RRC_CAUSE_MO_DATA)
|
||||
&& (amf_data_p->overload_state == NGAP_OVERLOAD_REJECT_MO_DATA)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if ((amf_data_p->overload_state == NGAP_OVERLOAD_REJECT_ALL_SIGNALLING)
|
||||
&& ((cause == NGAP_RRC_CAUSE_MO_SIGNALLING) || (cause == NGAP_RRC_CAUSE_MO_DATA))) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if ((amf_data_p->overload_state == NGAP_OVERLOAD_ONLY_EMERGENCY_AND_MT)
|
||||
&& ((cause == NGAP_RRC_CAUSE_MO_SIGNALLING) || (cause == NGAP_RRC_CAUSE_MO_DATA)
|
||||
|| (cause == NGAP_RRC_CAUSE_HIGH_PRIO_ACCESS))) {
|
||||
continue;
|
||||
}
|
||||
|
||||
/* At this point, the RRC establishment can be handled by the AMF
|
||||
* even if it is in overload state.
|
||||
*/
|
||||
} else {
|
||||
/* The AMF is not overloaded, association is simply not ready. */
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
/* Looking for AMF guami matching the one provided by NAS */
|
||||
STAILQ_FOREACH(guami_p, &amf_data_p->served_guami, next) {
|
||||
struct served_region_id_s *region_id_p = NULL;
|
||||
struct amf_set_id_s *amf_set_id_p = NULL;
|
||||
struct amf_pointer_s *pointer_p = NULL;
|
||||
struct plmn_identity_s *served_plmn_p = NULL;
|
||||
|
||||
STAILQ_FOREACH(served_plmn_p, &guami_p->served_plmns, next) {
|
||||
if ((served_plmn_p->mcc == guami.mcc) &&
|
||||
(served_plmn_p->mnc == guami.mnc)) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
STAILQ_FOREACH(region_id_p, &guami_p->served_region_ids, next) {
|
||||
if (region_id_p->amf_region_id == guami.amf_region_id) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
STAILQ_FOREACH(amf_set_id_p, &guami_p->amf_set_ids, next) {
|
||||
if (amf_set_id_p->amf_set_id == guami.amf_set_id) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
STAILQ_FOREACH(pointer_p, &guami_p->amf_pointers, next) {
|
||||
if (pointer_p->amf_pointer == guami.amf_pointer) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/* The AMF matches the parameters provided by the NAS layer ->
|
||||
* the AMF is knwown and the association is ready.
|
||||
* Return the reference to the AMF to use it for this UE.
|
||||
*/
|
||||
if ((region_id_p != NULL) &&
|
||||
(amf_set_id_p != NULL) &&
|
||||
(pointer_p != NULL) &&
|
||||
(served_plmn_p != NULL)) {
|
||||
return amf_data_p;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* At this point no AMF matches the provided GUAMI. In this case, return
|
||||
* NULL. That way the RRC layer should know about it and reject RRC
|
||||
* connectivity. */
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
struct ngap_gNB_amf_data_s *
|
||||
ngap_gNB_nnsf_select_amf_by_guami_no_cause(ngap_gNB_instance_t *instance_p,
|
||||
ngap_guami_t guami)
|
||||
{
|
||||
struct ngap_gNB_amf_data_s *amf_data_p = NULL;
|
||||
struct ngap_gNB_amf_data_s *amf_highest_capacity_p = NULL;
|
||||
uint8_t current_capacity = 0;
|
||||
|
||||
|
||||
RB_FOREACH(amf_data_p, ngap_amf_map, &instance_p->ngap_amf_head) {
|
||||
struct served_guami_s *guami_p = NULL;
|
||||
|
||||
if (amf_data_p->state != NGAP_GNB_STATE_CONNECTED) {
|
||||
/* The association between AMF and gNB is not ready for the moment,
|
||||
* go to the next known AMF.
|
||||
*/
|
||||
if (amf_data_p->state == NGAP_GNB_OVERLOAD) {
|
||||
/* AMF is overloaded. We have to check the RRC establishment
|
||||
* cause and take decision to the select this AMF depending on
|
||||
* the overload state.
|
||||
*/
|
||||
} else {
|
||||
/* The AMF is not overloaded, association is simply not ready. */
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
if (current_capacity < amf_data_p->relative_amf_capacity) {
|
||||
/* We find a better AMF, keep a reference to it */
|
||||
current_capacity = amf_data_p->relative_amf_capacity;
|
||||
amf_highest_capacity_p = amf_data_p;
|
||||
}
|
||||
|
||||
/* Looking for AMF guami matching the one provided by NAS */
|
||||
STAILQ_FOREACH(guami_p, &amf_data_p->served_guami, next) {
|
||||
struct served_region_id_s *region_id_p = NULL;
|
||||
struct amf_set_id_s *amf_set_id_p = NULL;
|
||||
struct plmn_identity_s *served_plmn_p = NULL;
|
||||
|
||||
STAILQ_FOREACH(served_plmn_p, &guami_p->served_plmns, next) {
|
||||
if ((served_plmn_p->mcc == guami.mcc) &&
|
||||
(served_plmn_p->mnc == guami.mnc)) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
STAILQ_FOREACH(amf_set_id_p, &guami_p->amf_set_ids, next) {
|
||||
if (amf_set_id_p->amf_set_id == guami.amf_set_id) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
STAILQ_FOREACH(region_id_p, &guami_p->served_region_ids, next) {
|
||||
if (region_id_p->amf_region_id == guami.amf_region_id) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/* The AMF matches the parameters provided by the NAS layer ->
|
||||
* the AMF is knwown and the association is ready.
|
||||
* Return the reference to the AMF to use it for this UE.
|
||||
*/
|
||||
if ((region_id_p != NULL) &&
|
||||
(amf_set_id_p != NULL) &&
|
||||
(served_plmn_p != NULL)) {
|
||||
return amf_data_p;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* At this point no AMF matches the provided GUAMI. Select the one with the
|
||||
* highest relative capacity.
|
||||
* In case the list of known AMF is empty, simply return NULL, that way the RRC
|
||||
* layer should know about it and reject RRC connectivity.
|
||||
*/
|
||||
|
||||
return amf_highest_capacity_p;
|
||||
}
|
||||
57
openair3/NGAP/ngap_gNB_nnsf.h
Normal file
57
openair3/NGAP/ngap_gNB_nnsf.h
Normal file
@@ -0,0 +1,57 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file ngap_gNB_nnsf.h
|
||||
* \brief ngap NAS node selection functions
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \date 2020
|
||||
* \version 0.1
|
||||
* \email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
*/
|
||||
|
||||
#ifndef NGAP_GNB_NNSF_H_
|
||||
#define NGAP_GNB_NNSF_H_
|
||||
|
||||
struct ngap_gNB_amf_data_s *
|
||||
ngap_gNB_nnsf_select_amf(ngap_gNB_instance_t *instance_p,
|
||||
ngap_rrc_establishment_cause_t cause);
|
||||
|
||||
struct ngap_gNB_amf_data_s *
|
||||
ngap_gNB_nnsf_select_amf_by_plmn_id(ngap_gNB_instance_t *instance_p,
|
||||
ngap_rrc_establishment_cause_t cause,
|
||||
int selected_plmn_identity);
|
||||
|
||||
struct ngap_gNB_amf_data_s*
|
||||
ngap_gNB_nnsf_select_amf_by_amf_setid(ngap_gNB_instance_t *instance_p,
|
||||
ngap_rrc_establishment_cause_t cause,
|
||||
int selected_plmn_identity,
|
||||
uint8_t amf_setid);
|
||||
|
||||
struct ngap_gNB_amf_data_s*
|
||||
ngap_gNB_nnsf_select_amf_by_guami(ngap_gNB_instance_t *instance_p,
|
||||
ngap_rrc_establishment_cause_t cause,
|
||||
ngap_guami_t guami);
|
||||
|
||||
struct ngap_gNB_amf_data_s*
|
||||
ngap_gNB_nnsf_select_amf_by_guami_no_cause(ngap_gNB_instance_t *instance_p,
|
||||
ngap_guami_t guami);
|
||||
|
||||
#endif /* NGAP_GNB_NNSF_H_ */
|
||||
79
openair3/NGAP/ngap_gNB_overload.c
Normal file
79
openair3/NGAP/ngap_gNB_overload.c
Normal file
@@ -0,0 +1,79 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file ngap_gNB_overload.c
|
||||
* \brief ngap procedures for overload messages within gNB
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \date 2020
|
||||
* \version 0.1
|
||||
* \email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
*/
|
||||
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include "intertask_interface.h"
|
||||
|
||||
#include "ngap_common.h"
|
||||
#include "ngap_gNB_defs.h"
|
||||
|
||||
#include "ngap_gNB.h"
|
||||
#include "ngap_gNB_ue_context.h"
|
||||
#include "ngap_gNB_encoder.h"
|
||||
#include "ngap_gNB_overload.h"
|
||||
#include "ngap_gNB_management_procedures.h"
|
||||
|
||||
#include "assertions.h"
|
||||
|
||||
int ngap_gNB_handle_overload_start(uint32_t assoc_id,
|
||||
uint32_t stream,
|
||||
NGAP_NGAP_PDU_t *pdu)
|
||||
{
|
||||
//TODO
|
||||
return 0;
|
||||
}
|
||||
|
||||
int ngap_gNB_handle_overload_stop(uint32_t assoc_id,
|
||||
uint32_t stream,
|
||||
NGAP_NGAP_PDU_t *pdu)
|
||||
{
|
||||
/* We received Overload stop message, meaning that the AMF is no more
|
||||
* overloaded. This is an empty message, with only message header and no
|
||||
* Information Element.
|
||||
*/
|
||||
DevAssert(pdu != NULL);
|
||||
|
||||
ngap_gNB_amf_data_t *amf_desc_p;
|
||||
|
||||
/* Non UE-associated signalling -> stream 0 */
|
||||
DevCheck(stream == 0, stream, 0, 0);
|
||||
|
||||
if ((amf_desc_p = ngap_gNB_get_AMF(NULL, assoc_id, 0)) == NULL) {
|
||||
/* No AMF context associated */
|
||||
return -1;
|
||||
}
|
||||
|
||||
amf_desc_p->state = NGAP_GNB_STATE_CONNECTED;
|
||||
amf_desc_p->overload_state = NGAP_NO_OVERLOAD;
|
||||
return 0;
|
||||
}
|
||||
53
openair3/NGAP/ngap_gNB_overload.h
Normal file
53
openair3/NGAP/ngap_gNB_overload.h
Normal file
@@ -0,0 +1,53 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file ngap_gNB_overload.h
|
||||
* \brief ngap procedures for overload messages within gNB
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \date 2020
|
||||
* \version 0.1
|
||||
* \email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
*/
|
||||
|
||||
#ifndef NGAP_GNB_OVERLOAD_H_
|
||||
#define NGAP_GNB_OVERLOAD_H_
|
||||
|
||||
/**
|
||||
* \brief Handle an overload start message
|
||||
**/
|
||||
// int ngap_gNB_handle_overload_start(gNB_amf_desc_t *gNB_desc_p,
|
||||
// sctp_queue_item_t *packet_p,
|
||||
// struct ngap_message_s *message_p);
|
||||
int ngap_gNB_handle_overload_start(uint32_t assoc_id,
|
||||
uint32_t stream,
|
||||
NGAP_NGAP_PDU_t *pdu);
|
||||
|
||||
/**
|
||||
* \brief Handle an overload stop message
|
||||
**/
|
||||
// int ngap_gNB_handle_overload_stop(gNB_amf_desc_t *gNB_desc_p,
|
||||
// sctp_queue_item_t *packet_p,
|
||||
// struct ngap_message_s *message_p);
|
||||
int ngap_gNB_handle_overload_stop(uint32_t assoc_id,
|
||||
uint32_t stream,
|
||||
NGAP_NGAP_PDU_t *pdu);
|
||||
|
||||
#endif /* NGAP_GNB_OVERLOAD_H_ */
|
||||
66
openair3/NGAP/ngap_gNB_trace.c
Normal file
66
openair3/NGAP/ngap_gNB_trace.c
Normal file
@@ -0,0 +1,66 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file ngap_gNB_trace.c
|
||||
* \brief ngap trace procedures for gNB
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \date 2020
|
||||
* \version 0.1
|
||||
* \email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
*/
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
#include "assertions.h"
|
||||
|
||||
#include "intertask_interface.h"
|
||||
|
||||
#include "ngap_gNB_default_values.h"
|
||||
|
||||
#include "ngap_common.h"
|
||||
#include "ngap_gNB_defs.h"
|
||||
|
||||
#include "ngap_gNB.h"
|
||||
#include "ngap_gNB_ue_context.h"
|
||||
#include "ngap_gNB_encoder.h"
|
||||
#include "ngap_gNB_trace.h"
|
||||
#include "ngap_gNB_itti_messaging.h"
|
||||
#include "ngap_gNB_management_procedures.h"
|
||||
|
||||
|
||||
int ngap_gNB_handle_trace_start(uint32_t assoc_id,
|
||||
uint32_t stream,
|
||||
NGAP_NGAP_PDU_t *pdu)
|
||||
{
|
||||
//TODO
|
||||
return 0;
|
||||
}
|
||||
|
||||
int ngap_gNB_handle_deactivate_trace(uint32_t assoc_id,
|
||||
uint32_t stream,
|
||||
NGAP_NGAP_PDU_t *message_p)
|
||||
{
|
||||
// NGAP_DeactivateTraceIEs_t *deactivate_trace_p;
|
||||
//
|
||||
// deactivate_trace_p = &message_p->msg.deactivateTraceIEs;
|
||||
|
||||
return 0;
|
||||
}
|
||||
54
openair3/NGAP/ngap_gNB_trace.h
Normal file
54
openair3/NGAP/ngap_gNB_trace.h
Normal file
@@ -0,0 +1,54 @@
|
||||
/*
|
||||
* Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership.
|
||||
* The OpenAirInterface Software Alliance licenses this file to You under
|
||||
* the OAI Public License, Version 1.1 (the "License"); you may not use this file
|
||||
* except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.openairinterface.org/?page_id=698
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*-------------------------------------------------------------------------------
|
||||
* For more information about the OpenAirInterface (OAI) Software Alliance:
|
||||
* contact@openairinterface.org
|
||||
*/
|
||||
|
||||
/*! \file ngap_gNB_trace.h
|
||||
* \brief ngap trace procedures for gNB
|
||||
* \author Yoshio INOUE, Masayuki HARADA
|
||||
* \date 2020
|
||||
* \version 0.1
|
||||
* \email: yoshio.inoue@fujitsu.com,masayuki.harada@fujitsu.com (yoshio.inoue%40fujitsu.com%2cmasayuki.harada%40fujitsu.com)
|
||||
*/
|
||||
|
||||
#ifndef NGAP_GNB_TRACE_H_
|
||||
#define NGAP_GNB_TRACE_H_
|
||||
|
||||
// int ngap_gNB_generate_trace_failure(sctp_data_t *sctp_data_p,
|
||||
// int32_t stream,
|
||||
// uint32_t gNB_ue_ngap_id,
|
||||
// uint32_t amf_ue_ngap_id,
|
||||
// E_UTRAN_Trace_ID_t *trace_id,
|
||||
// Cause_t *cause_p);
|
||||
|
||||
// int ngap_gNB_handle_trace_start(gNB_amf_desc_t *gNB_desc_p,
|
||||
// sctp_queue_item_t *packet_p,
|
||||
// struct ngap_message_s *message_p);
|
||||
int ngap_gNB_handle_trace_start(uint32_t assoc_id,
|
||||
uint32_t stream,
|
||||
NGAP_NGAP_PDU_t *pdu);
|
||||
|
||||
// int ngap_gNB_handle_deactivate_trace(gNB_amf_desc_t *gNB_desc_p,
|
||||
// sctp_queue_item_t *packet_p,
|
||||
// struct ngap_message_s *message_p);
|
||||
int ngap_gNB_handle_deactivate_trace(uint32_t assoc_id,
|
||||
uint32_t stream,
|
||||
NGAP_NGAP_PDU_t *pdu);
|
||||
|
||||
#endif /* NGAP_GNB_TRACE_H_ */
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user