Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
O
OpenXG-RAN
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Analytics
Analytics
CI / CD
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
Michael Black
OpenXG-RAN
Commits
a826af58
Commit
a826af58
authored
Jan 13, 2022
by
athanassopoulos
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
SDAP Initial Implementation
parent
5a3eeac5
Changes
18
Show whitespace changes
Inline
Side-by-side
Showing
18 changed files
with
938 additions
and
153 deletions
+938
-153
cmake_targets/CMakeLists.txt
cmake_targets/CMakeLists.txt
+2
-1
common/utils/LOG/log.c
common/utils/LOG/log.c
+1
-0
common/utils/LOG/log.h
common/utils/LOG/log.h
+1
-0
common/utils/T/T_messages.txt
common/utils/T/T_messages.txt
+21
-0
doc/FEATURE_SET.md
doc/FEATURE_SET.md
+16
-0
openair2/COMMON/platform_types.h
openair2/COMMON/platform_types.h
+9
-0
openair2/LAYER2/nr_pdcp/nr_pdcp_entity.c
openair2/LAYER2/nr_pdcp/nr_pdcp_entity.c
+2
-2
openair2/LAYER2/nr_pdcp/nr_pdcp_entity.h
openair2/LAYER2/nr_pdcp/nr_pdcp_entity.h
+1
-1
openair2/LAYER2/nr_pdcp/nr_pdcp_oai_api.c
openair2/LAYER2/nr_pdcp/nr_pdcp_oai_api.c
+46
-50
openair2/LAYER2/nr_pdcp/nr_pdcp_oai_api.h
openair2/LAYER2/nr_pdcp/nr_pdcp_oai_api.h
+3
-0
openair2/LAYER2/nr_pdcp/nr_pdcp_ue_manager.c
openair2/LAYER2/nr_pdcp/nr_pdcp_ue_manager.c
+2
-2
openair2/RRC/NR/rrc_gNB.c
openair2/RRC/NR/rrc_gNB.c
+4
-4
openair2/SDAP/nr_sdap/nr_sdap.c
openair2/SDAP/nr_sdap/nr_sdap.c
+73
-0
openair2/SDAP/nr_sdap/nr_sdap.h
openair2/SDAP/nr_sdap/nr_sdap.h
+59
-0
openair2/SDAP/nr_sdap/nr_sdap_entity.c
openair2/SDAP/nr_sdap/nr_sdap_entity.c
+474
-0
openair2/SDAP/nr_sdap/nr_sdap_entity.h
openair2/SDAP/nr_sdap/nr_sdap_entity.h
+167
-0
openair2/SDAP/nr_sdap/nr_sdap_gnb.c
openair2/SDAP/nr_sdap/nr_sdap_gnb.c
+0
-87
openair3/ocp-gtpu/gtp_itf.cpp
openair3/ocp-gtpu/gtp_itf.cpp
+57
-6
No files found.
cmake_targets/CMakeLists.txt
View file @
a826af58
...
...
@@ -1779,7 +1779,8 @@ set(NR_PDCP_SRC
)
set
(
NR_SDAP_SRC
${
OPENAIR2_DIR
}
/SDAP/nr_sdap/nr_sdap_gnb.c
${
OPENAIR2_DIR
}
/SDAP/nr_sdap/nr_sdap.c
${
OPENAIR2_DIR
}
/SDAP/nr_sdap/nr_sdap_entity.c
)
set
(
L2_SRC
...
...
common/utils/LOG/log.c
View file @
a826af58
...
...
@@ -478,6 +478,7 @@ int logInit (void)
register_log_component
(
"NAS"
,
"log"
,
NAS
);
register_log_component
(
"UDP"
,
""
,
UDP_
);
register_log_component
(
"GTPU"
,
""
,
GTPU
);
register_log_component
(
"SDAP"
,
""
,
SDAP
);
register_log_component
(
"S1AP"
,
""
,
S1AP
);
register_log_component
(
"F1AP"
,
""
,
F1AP
);
register_log_component
(
"M2AP"
,
""
,
M2AP
);
...
...
common/utils/LOG/log.h
View file @
a826af58
...
...
@@ -215,6 +215,7 @@ typedef enum {
OCM
,
UDP_
,
GTPU
,
SDAP
,
SPGW
,
S1AP
,
F1AP
,
...
...
common/utils/T/T_messages.txt
View file @
a826af58
...
...
@@ -944,6 +944,27 @@ ID = LEGACY_GTPU_TRACE
GROUP = ALL:LEGACY_GTPU:LEGACY_GROUP_TRACE:LEGACY
FORMAT = string,log
ID = LEGACY_SDAP_INFO
DESC = SDAP legacy logs - info level
GROUP = ALL:LEGACY_SDAP:LEGACY_GROUP_INFO:LEGACY
FORMAT = string,log
ID = LEGACY_SDAP_ERROR
DESC = SDAP legacy logs - error level
GROUP = ALL:LEGACY_SDAP:LEGACY_GROUP_ERROR:LEGACY
FORMAT = string,log
ID = LEGACY_SDAP_WARNING
DESC = SDAP legacy logs - warning level
GROUP = ALL:LEGACY_SDAP:LEGACY_GROUP_WARNING:LEGACY
FORMAT = string,log
ID = LEGACY_SDAP_DEBUG
DESC = SDAP legacy logs - debug level
GROUP = ALL:LEGACY_SDAP:LEGACY_GROUP_DEBUG:LEGACY
FORMAT = string,log
ID = LEGACY_SDAP_TRACE
DESC = SDAP legacy logs - trace level
GROUP = ALL:LEGACY_SDAP:LEGACY_GROUP_TRACE:LEGACY
FORMAT = string,log
ID = LEGACY_TMR_INFO
DESC = TMR legacy logs - info level
GROUP = ALL:LEGACY_TMR:LEGACY_GROUP_INFO:LEGACY
...
...
doc/FEATURE_SET.md
View file @
a826af58
...
...
@@ -351,6 +351,14 @@ The following features are valid for the gNB and the 5G-NR UE.
-
Interfaces with RRC, RLC
-
Interfaces with gtp-u (data Tx/Rx over N3 and F1-U interfaces)
**gNB SDAP**
-
Send/Receive operations according to 37.324 Rel.15
-
Establishment/Handling of SDAP entities.
-
Transfer of User Plane Data
-
Mapping between a QoS flow and a DRB for both DL and UL
-
Marking QoS flow ID in both DL and UL packets
-
Reflective QoS flow to DRB mapping for UL SDAP data PDUs
**gNB RRC**
-
NR RRC (38.331) Rel 16 messages using new asn1c
-
LTE RRC (36.331) also updated to Rel 15
...
...
@@ -400,6 +408,7 @@ The following features are valid for the gNB and the 5G-NR UE.
-
New gtp-u implementation supporting both N3 and F1-U interfaces according to 29.281 Rel.15
-
Interfaces with RRC, F1AP for tunnel creation
-
Interfaces with PDCP and RLC for data send/receive at the CU and DU respectively (F1-U interface)
-
Interface with SDAP for data send/receive, capture of GTP-U Optional Header, GTP-U Extension Header and PDU Session Container.
# OpenAirInterface 5G-NR UE Feature Set #
...
...
@@ -502,6 +511,13 @@ The following features are valid for the gNB and the 5G-NR UE.
-
Radio bearer establishment/handling and association with PDCP entities
-
Interfaces with RRC, RLC
**UE SDAP**
*
Tx/Rx operations operations according to 37.324 Rel.15
-
Establishment/Handling of SDAP entities.
-
Transfer of User Plane Data
-
Reflective Mapping
-
RRC Signaling Mapping
**UE RRC**
*
Integration of RRC messages and procedures supporting UE 5G SA connection according to 38.331 Rel.16
-
RRCSetupRequest/RRCSetup/RRCSetupComplete
...
...
openair2/COMMON/platform_types.h
View file @
a826af58
...
...
@@ -233,11 +233,20 @@ typedef uint8_t pdusessionid_t;
//-----------------------------------------------------------------------------
// may be ITTI not enabled, but type instance is useful also for OTG,
typedef
intptr_t
instance_t
;
typedef
struct
sdap_protocol_ctxt_s
{
boolean_t
rqi
;
uint8_t
qfi
;
boolean_t
dc
;
int
pdusession_id
;
}
sdap_protocol_ctxt_t
;
typedef
struct
protocol_ctxt_s
{
module_id_t
module_id
;
/*!< \brief Virtualized module identifier */
eNB_flag_t
enb_flag
;
/*!< \brief Flag to indicate eNB (1) or UE (0) */
instance_t
instance
;
/*!< \brief ITTI or OTG module identifier */
rnti_t
rnti
;
sdap_protocol_ctxt_t
sdap
;
frame_t
frame
;
/*!< \brief LTE frame number.*/
sub_frame_t
subframe
;
/*!< \brief LTE sub frame number.*/
eNB_index_t
eNB_index
;
/*!< \brief valid for UE indicating the index of connected eNB(s) */
...
...
openair2/LAYER2/nr_pdcp/nr_pdcp_entity.c
View file @
a826af58
...
...
@@ -368,7 +368,7 @@ nr_pdcp_entity_t *new_nr_pdcp_entity(
ret
->
set_security
=
nr_pdcp_entity_set_security
;
ret
->
set_time
=
nr_pdcp_entity_set_time
;
ret
->
delete
=
nr_pdcp_entity_delete
;
ret
->
delete
_entity
=
nr_pdcp_entity_delete
;
ret
->
deliver_sdu
=
deliver_sdu
;
ret
->
deliver_sdu_data
=
deliver_sdu_data
;
...
...
openair2/LAYER2/nr_pdcp/nr_pdcp_entity.h
View file @
a826af58
...
...
@@ -39,7 +39,7 @@ typedef struct nr_pdcp_entity_t {
void
(
*
recv_pdu
)(
struct
nr_pdcp_entity_t
*
entity
,
char
*
buffer
,
int
size
);
void
(
*
recv_sdu
)(
struct
nr_pdcp_entity_t
*
entity
,
char
*
buffer
,
int
size
,
int
sdu_id
);
void
(
*
delete
)(
struct
nr_pdcp_entity_t
*
entity
);
void
(
*
delete
_entity
)(
struct
nr_pdcp_entity_t
*
entity
);
/* set_security: pass -1 to integrity_algorithm / ciphering_algorithm
* to keep the current algorithm
...
...
openair2/LAYER2/nr_pdcp/nr_pdcp_oai_api.c
View file @
a826af58
...
...
@@ -36,7 +36,8 @@
#include "pdcp.h"
#include "LAYER2/nr_rlc/nr_rlc_oai_api.h"
#include <openair3/ocp-gtpu/gtp_itf.h>
#include "openair2/SDAP/nr_sdap/nr_sdap_gnb.h"
#include "openair2/SDAP/nr_sdap/nr_sdap.h"
#include "nr_pdcp_oai_api.h"
#define TODO do { \
printf("%s:%d:%s: todo\n", __FILE__, __LINE__, __FUNCTION__); \
...
...
@@ -438,7 +439,11 @@ static void *enb_tun_read_thread(void *_)
ctxt
.
rnti
=
rnti
;
pdcp_data_req
(
&
ctxt
,
SRB_FLAG_NO
,
rb_id
,
RLC_MUI_UNDEFINED
,
ctxt
.
sdap
.
qfi
=
7
;
ctxt
.
sdap
.
rqi
=
0
;
ctxt
.
sdap
.
pdusession_id
=
10
;
sdap_data_req
(
&
ctxt
,
SRB_FLAG_NO
,
rb_id
,
RLC_MUI_UNDEFINED
,
RLC_SDU_CONFIRM_NO
,
len
,
(
unsigned
char
*
)
rx_buf
,
PDCP_TRANSMISSION_MODE_DATA
,
NULL
,
NULL
);
}
...
...
@@ -481,7 +486,11 @@ static void *ue_tun_read_thread(void *_)
ctxt
.
rnti
=
rnti
;
pdcp_data_req
(
&
ctxt
,
SRB_FLAG_NO
,
rb_id
,
RLC_MUI_UNDEFINED
,
ctxt
.
sdap
.
dc
=
SDAP_HDR_UL_DATA_PDU
;
ctxt
.
sdap
.
qfi
=
7
;
ctxt
.
sdap
.
pdusession_id
=
10
;
sdap_data_req
(
&
ctxt
,
SRB_FLAG_NO
,
rb_id
,
RLC_MUI_UNDEFINED
,
RLC_SDU_CONFIRM_NO
,
len
,
(
unsigned
char
*
)
rx_buf
,
PDCP_TRANSMISSION_MODE_DATA
,
NULL
,
NULL
);
}
...
...
@@ -607,28 +616,13 @@ uint64_t nr_pdcp_module_init(uint64_t _pdcp_optmask, int id)
static
void
deliver_sdu_drb
(
void
*
_ue
,
nr_pdcp_entity_t
*
entity
,
char
*
buf
,
int
size
)
{
extern
int
nas_sock_fd
[];
int
len
;
nr_pdcp_ue_t
*
ue
=
_ue
;
MessageDef
*
message_p
;
uint8_t
*
gtpu_buffer_p
;
int
rb_id
;
int
i
;
if
(
IS_SOFTMODEM_NOS1
||
UE_NAS_USE_TUN
)
{
LOG_D
(
PDCP
,
"IP packet received, to be sent to TUN interface"
);
if
(
entity
->
has_sdapDLheader
){
size
-=
SDAP_HDR_LENGTH
;
len
=
write
(
nas_sock_fd
[
0
],
&
buf
[
SDAP_HDR_LENGTH
],
size
);
}
else
{
len
=
write
(
nas_sock_fd
[
0
],
buf
,
size
);
}
if
(
len
!=
size
)
{
LOG_E
(
PDCP
,
"%s:%d:%s: fatal error %d: %s
\n
"
,
__FILE__
,
__LINE__
,
__FUNCTION__
,
errno
,
strerror
(
errno
));
}
LOG_D
(
PDCP
,
"IP packet received with size %d, to be sent to SDAP interface, UE rnti: %d
\n
"
,
size
,
ue
->
rnti
);
sdap_data_ind
(
entity
,
ue
->
rnti
,
buf
,
size
);
}
else
{
for
(
i
=
0
;
i
<
5
;
i
++
)
{
...
...
@@ -644,30 +638,8 @@ static void deliver_sdu_drb(void *_ue, nr_pdcp_entity_t *entity,
rb_found:
{
int
offset
=
0
;
if
(
entity
->
has_sdap
==
1
&&
entity
->
has_sdapULheader
==
1
)
offset
=
1
;
// this is the offset of the SDAP header in bytes
message_p
=
itti_alloc_new_message_sized
(
TASK_PDCP_ENB
,
0
,
GTPV1U_GNB_TUNNEL_DATA_REQ
,
sizeof
(
gtpv1u_gnb_tunnel_data_req_t
)
+
size
+
GTPU_HEADER_OVERHEAD_MAX
-
offset
);
AssertFatal
(
message_p
!=
NULL
,
"OUT OF MEMORY"
);
gtpv1u_gnb_tunnel_data_req_t
*
req
=&
GTPV1U_GNB_TUNNEL_DATA_REQ
(
message_p
);
gtpu_buffer_p
=
(
uint8_t
*
)(
req
+
1
);
memcpy
(
gtpu_buffer_p
+
GTPU_HEADER_OVERHEAD_MAX
,
buf
+
offset
,
size
-
offset
);
req
->
buffer
=
gtpu_buffer_p
;
req
->
length
=
size
-
offset
;
req
->
offset
=
GTPU_HEADER_OVERHEAD_MAX
;
req
->
rnti
=
ue
->
rnti
;
req
->
pdusession_id
=
entity
->
pdusession_id
;
if
(
offset
==
1
)
{
LOG_I
(
PDCP
,
"%s() (drb %d) SDAP header %2x
\n
"
,
__func__
,
rb_id
,
buf
[
0
]);
sdap_gnb_ul_header_handler
(
buf
[
0
]);
// Handler for the UL gNB SDAP Header
}
LOG_D
(
PDCP
,
"%s() (drb %d) sending message to gtp size %d
\n
"
,
__func__
,
rb_id
,
size
-
offset
);
itti_send_msg_to_task
(
TASK_GTPV1_U
,
INSTANCE_DEFAULT
,
message_p
);
LOG_D
(
PDCP
,
"%s() (drb %d) sending message to SDAP size %d
\n
"
,
__func__
,
rb_id
,
size
);
sdap_data_ind
(
entity
,
ue
->
rnti
,
buf
,
size
);
}
}
}
...
...
@@ -967,6 +939,9 @@ static void add_drb_am(int is_gnb, int rnti, struct NR_DRB_ToAddMod *s,
int
has_sdap
=
0
;
int
has_sdapULheader
=
0
;
int
has_sdapDLheader
=
0
;
boolean_t
is_sdap_DefaultDRB
=
false
;
NR_QFI_t
*
mappedQFIs2Add
=
NULL
;
uint8_t
mappedQFIs2AddCount
=
0
;
if
(
s
->
cnAssociation
->
present
==
NR_DRB_ToAddMod__cnAssociation_PR_eps_BearerIdentity
)
pdusession_id
=
s
->
cnAssociation
->
choice
.
eps_BearerIdentity
;
else
{
...
...
@@ -978,6 +953,10 @@ static void add_drb_am(int is_gnb, int rnti, struct NR_DRB_ToAddMod *s,
has_sdap
=
1
;
has_sdapULheader
=
s
->
cnAssociation
->
choice
.
sdap_Config
->
sdap_HeaderUL
==
NR_SDAP_Config__sdap_HeaderUL_present
?
1
:
0
;
has_sdapDLheader
=
s
->
cnAssociation
->
choice
.
sdap_Config
->
sdap_HeaderDL
==
NR_SDAP_Config__sdap_HeaderDL_present
?
1
:
0
;
is_sdap_DefaultDRB
=
s
->
cnAssociation
->
choice
.
sdap_Config
->
defaultDRB
==
true
?
1
:
0
;
mappedQFIs2Add
=
(
NR_QFI_t
*
)
s
->
cnAssociation
->
choice
.
sdap_Config
->
mappedQoS_FlowsToAdd
->
list
.
array
[
0
];
mappedQFIs2AddCount
=
s
->
cnAssociation
->
choice
.
sdap_Config
->
mappedQoS_FlowsToAdd
->
list
.
count
;
LOG_D
(
SDAP
,
"Captured mappedQoS_FlowsToAdd from RRC: %ld
\n
"
,
*
mappedQFIs2Add
);
}
/* TODO(?): accept different UL and DL SN sizes? */
if
(
sn_size_ul
!=
sn_size_dl
)
{
...
...
@@ -1009,6 +988,14 @@ static void add_drb_am(int is_gnb, int rnti, struct NR_DRB_ToAddMod *s,
nr_pdcp_ue_add_drb_pdcp_entity
(
ue
,
drb_id
,
pdcp_drb
);
LOG_D
(
PDCP
,
"%s:%d:%s: added drb %d to ue rnti %x
\n
"
,
__FILE__
,
__LINE__
,
__FUNCTION__
,
drb_id
,
rnti
);
new_nr_sdap_entity
(
rnti
,
pdusession_id
,
is_sdap_DefaultDRB
,
drb_id
,
mappedQFIs2Add
,
mappedQFIs2AddCount
);
LOG_D
(
SDAP
,
"Added SDAP entity to ue rnti %x with pdusession_id %d
\n
"
,
rnti
,
pdusession_id
);
}
nr_pdcp_manager_unlock
(
nr_pdcp_ue_manager
);
}
...
...
@@ -1140,7 +1127,7 @@ void nr_DRB_preconfiguration(uint16_t crnti)
NR_DRB_ToAddMod_t
*
drb_ToAddMod
=
calloc
(
1
,
sizeof
(
*
drb_ToAddMod
));
drb_ToAddMod
->
cnAssociation
=
calloc
(
1
,
sizeof
(
*
drb_ToAddMod
->
cnAssociation
));
drb_ToAddMod
->
cnAssociation
->
present
=
NR_DRB_ToAddMod__cnAssociation_PR_eps_BearerIdentity
;
drb_ToAddMod
->
cnAssociation
->
choice
.
eps_BearerIdentity
=
5
;
drb_ToAddMod
->
cnAssociation
->
choice
.
eps_BearerIdentity
=
10
;
drb_ToAddMod
->
drb_Identity
=
1
;
drb_ToAddMod
->
reestablishPDCP
=
NULL
;
drb_ToAddMod
->
recoverPDCP
=
NULL
;
...
...
@@ -1450,3 +1437,12 @@ void nr_pdcp_tick(int frame, int subframe)
nr_pdcp_wakeup_timer_thread
(
nr_pdcp_current_time
);
}
}
nr_pdcp_entity_t
*
nr_pdcp_find_entity_sdap
(
int
rnti
,
uint8_t
sdap_drb_id
){
nr_pdcp_ue_t
*
ue
;
ue
=
nr_pdcp_manager_get_ue
(
nr_pdcp_ue_manager
,
rnti
);
if
(
ue
->
drb
[
sdap_drb_id
-
1
])
return
ue
->
drb
[
sdap_drb_id
-
1
];
return
NULL
;
}
openair2/LAYER2/nr_pdcp/nr_pdcp_oai_api.h
0 → 100644
View file @
a826af58
#include "openair2/COMMON/platform_types.h"
nr_pdcp_entity_t
*
nr_pdcp_find_entity_sdap
(
int
rnti
,
uint8_t
sdap_drb_id
);
openair2/LAYER2/nr_pdcp/nr_pdcp_ue_manager.c
View file @
a826af58
...
...
@@ -127,11 +127,11 @@ void nr_pdcp_manager_remove_ue(nr_pdcp_ue_manager_t *_m, int rnti)
for
(
j
=
0
;
j
<
2
;
j
++
)
if
(
ue
->
srb
[
j
]
!=
NULL
)
ue
->
srb
[
j
]
->
delete
(
ue
->
srb
[
j
]);
ue
->
srb
[
j
]
->
delete
_entity
(
ue
->
srb
[
j
]);
for
(
j
=
0
;
j
<
5
;
j
++
)
if
(
ue
->
drb
[
j
]
!=
NULL
)
ue
->
drb
[
j
]
->
delete
(
ue
->
drb
[
j
]);
ue
->
drb
[
j
]
->
delete
_entity
(
ue
->
drb
[
j
]);
free
(
ue
);
...
...
openair2/RRC/NR/rrc_gNB.c
View file @
a826af58
...
...
@@ -818,7 +818,6 @@ rrc_gNB_generate_dedicatedRRCReconfiguration(
uint8_t
buffer
[
RRC_BUF_SIZE
];
uint16_t
size
;
int
qos_flow_index
=
0
;
NR_QFI_t
qfi
=
0
;
int
pdu_sessions_done
=
0
;
int
i
;
NR_CellGroupConfig_t
*
cellGroupConfig
;
...
...
@@ -870,14 +869,15 @@ rrc_gNB_generate_dedicatedRRCReconfiguration(
memset
(
sdap_config
,
0
,
sizeof
(
NR_SDAP_Config_t
));
sdap_config
->
pdu_Session
=
ue_context_pP
->
ue_context
.
pduSession
[
i
].
param
.
pdusession_id
;
sdap_config
->
sdap_HeaderDL
=
NR_SDAP_Config__sdap_HeaderDL_present
;
sdap_config
->
sdap_HeaderUL
=
NR_SDAP_Config__sdap_HeaderUL_
ab
sent
;
sdap_config
->
sdap_HeaderUL
=
NR_SDAP_Config__sdap_HeaderUL_
pre
sent
;
sdap_config
->
defaultDRB
=
TRUE
;
sdap_config
->
mappedQoS_FlowsToAdd
=
calloc
(
1
,
sizeof
(
struct
NR_SDAP_Config__mappedQoS_FlowsToAdd
));
memset
(
sdap_config
->
mappedQoS_FlowsToAdd
,
0
,
sizeof
(
struct
NR_SDAP_Config__mappedQoS_FlowsToAdd
));
for
(
qos_flow_index
=
0
;
qos_flow_index
<
ue_context_pP
->
ue_context
.
pduSession
[
i
].
param
.
nb_qos
;
qos_flow_index
++
)
{
qfi
=
ue_context_pP
->
ue_context
.
pduSession
[
i
].
param
.
qos
[
qos_flow_index
].
qfi
;
ASN_SEQUENCE_ADD
(
&
sdap_config
->
mappedQoS_FlowsToAdd
->
list
,
&
qfi
);
NR_QFI_t
*
qfi
=
calloc
(
1
,
sizeof
(
NR_QFI_t
));
*
qfi
=
ue_context_pP
->
ue_context
.
pduSession
[
i
].
param
.
qos
[
qos_flow_index
].
qfi
;
ASN_SEQUENCE_ADD
(
&
sdap_config
->
mappedQoS_FlowsToAdd
->
list
,
qfi
);
}
sdap_config
->
mappedQoS_FlowsToRelease
=
NULL
;
DRB_config
->
cnAssociation
->
choice
.
sdap_Config
=
sdap_config
;
...
...
openair2/SDAP/nr_sdap/nr_sdap
_gnb.h
→
openair2/SDAP/nr_sdap/nr_sdap
.c
View file @
a826af58
...
...
@@ -19,32 +19,9 @@
* contact@openairinterface.org
*/
#ifndef _NR_SDAP_GNB_
#define _NR_SDAP_GNB_
#include "nr_sdap.h"
#include "openair2/COMMON/platform_types.h"
#include "common/utils/LOG/log.h"
#define SDAP_BITMASK_DC (0x80)
#define SDAP_BITMASK_R (0x40)
#define SDAP_BITMASK_QFI (0x3F)
#define SDAP_HDR_UL_DATA_PDU (1)
#define SDAP_HDR_UL_CTRL_PDU (0)
#define SDAP_HDR_LENGTH (1)
typedef
struct
nr_sdap_dl_hdr_s
{
uint8_t
QFI
:
6
;
uint8_t
RQI
:
1
;
uint8_t
RDI
:
1
;
}
__attribute__
((
packed
))
nr_sdap_dl_hdr_t
;
typedef
struct
nr_sdap_ul_hdr_s
{
uint8_t
QFI
:
6
;
uint8_t
R
:
1
;
uint8_t
DC
:
1
;
}
__attribute__
((
packed
))
nr_sdap_ul_hdr_t
;
boolean_t
sdap_gnb_data_req
(
protocol_ctxt_t
*
ctxt_p
,
boolean_t
sdap_data_req
(
protocol_ctxt_t
*
ctxt_p
,
const
srb_flag_t
srb_flag
,
const
rb_id_t
rb_id
,
const
mui_t
mui
,
...
...
@@ -53,9 +30,44 @@ boolean_t sdap_gnb_data_req(protocol_ctxt_t *ctxt_p,
unsigned
char
*
const
sdu_buffer
,
const
pdcp_transmission_mode_t
pt_mode
,
const
uint32_t
*
sourceL2Id
,
const
uint32_t
*
destinationL2Id
);
const
uint32_t
*
destinationL2Id
)
{
nr_sdap_entity_t
*
sdap_entity
;
sdap_entity
=
nr_sdap_get_entity
(
ctxt_p
->
rnti
,
ctxt_p
->
sdap
.
pdusession_id
);
if
(
sdap_entity
==
NULL
)
{
LOG_E
(
SDAP
,
"%s:%d:%s: Entity not found with ue rnti: %x and pdusession id: %d
\n
"
,
__FILE__
,
__LINE__
,
__FUNCTION__
,
ctxt_p
->
rnti
,
ctxt_p
->
sdap
.
pdusession_id
);
return
0
;
}
boolean_t
ret
=
sdap_entity
->
tx_entity
(
sdap_entity
,
ctxt_p
,
srb_flag
,
rb_id
,
mui
,
confirm
,
sdu_buffer_size
,
sdu_buffer
,
pt_mode
,
sourceL2Id
,
destinationL2Id
);
return
ret
;
}
void
sdap_data_ind
(
nr_pdcp_entity_t
*
pdcp_entity
,
int
rnti
,
char
*
buf
,
int
size
)
{
nr_sdap_entity_t
*
sdap_entity
;
sdap_entity
=
nr_sdap_get_entity
(
rnti
,
pdcp_entity
->
pdusession_id
);
void
sdap_gnb_ul_header_handler
(
char
sdap_gnb_ul_hdr
);
if
(
sdap_entity
==
NULL
)
{
LOG_E
(
SDAP
,
"%s:%d:%s: Entity not found
\n
"
,
__FILE__
,
__LINE__
,
__FUNCTION__
);
return
;
}
#endif
\ No newline at end of file
sdap_entity
->
rx_entity
(
sdap_entity
,
pdcp_entity
,
rnti
,
buf
,
size
);
}
openair2/SDAP/nr_sdap/
sdap_gNB.c
→
openair2/SDAP/nr_sdap/
nr_sdap.h
View file @
a826af58
...
...
@@ -19,12 +19,41 @@
* 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
#ifndef _NR_SDAP_GNB_H_
#define _NR_SDAP_GNB_H_
#include "openair2/COMMON/platform_types.h"
#include "common/utils/LOG/log.h"
#include "nr_sdap_entity.h"
/*
* TS 37.324 4.4 Functions
* Transfer of user plane data
* Downlink - gNB
* Uplink - nrUE
*/
boolean_t
sdap_data_req
(
protocol_ctxt_t
*
ctxt_p
,
const
srb_flag_t
srb_flag
,
const
rb_id_t
rb_id
,
const
mui_t
mui
,
const
confirm_t
confirm
,
const
sdu_size_t
sdu_buffer_size
,
unsigned
char
*
const
sdu_buffer
,
const
pdcp_transmission_mode_t
pt_mode
,
const
uint32_t
*
sourceL2Id
,
const
uint32_t
*
destinationL2Id
);
/*
* TS 37.324 4.4 Functions
* Transfer of user plane data
* Uplink - gNB
* Downlink - nrUE
*/
#define SDAP_GNB
#define SDAP_GNB_C
void
sdap_data_ind
(
nr_pdcp_entity_t
*
pdcp_entity
,
int
rnti
,
char
*
buf
,
int
size
);
#endif
openair2/SDAP/nr_sdap/nr_sdap_entity.c
0 → 100644
View file @
a826af58
/*
* 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_sdap_entity.h"
#include "common/utils/LOG/log.h"
#include <openair2/LAYER2/PDCP_v10.1.0/pdcp.h>
#include <openair3/ocp-gtpu/gtp_itf.h>
#include "openair2/LAYER2/nr_pdcp/nr_pdcp_oai_api.h"
#include <stdlib.h>
#include <string.h>
#include <pthread.h>
typedef
struct
{
nr_sdap_entity_t
*
sdap_entity_llist
;
}
nr_sdap_entity_info
;
static
nr_sdap_entity_info
sdap_info
;
static
boolean_t
nr_sdap_tx_entity
(
nr_sdap_entity_t
*
entity
,
protocol_ctxt_t
*
ctxt_p
,
const
srb_flag_t
srb_flag
,
const
rb_id_t
rb_id
,
const
mui_t
mui
,
const
confirm_t
confirm
,
const
sdu_size_t
sdu_buffer_size
,
unsigned
char
*
const
sdu_buffer
,
const
pdcp_transmission_mode_t
pt_mode
,
const
uint32_t
*
sourceL2Id
,
const
uint32_t
*
destinationL2Id
)
{
/* The offset of the SDAP header, it might be 0 if the has_sdap is not true in the pdcp entity. */
int
offset
=
0
;
boolean_t
ret
=
false
;
/*Hardcode DRB ID given from upper layer (ue/enb_tun_read_thread rb_id), it will change if we have SDAP*/
rb_id_t
sdap_drb_id
=
rb_id
;
int
pdcp_ent_has_sdap
=
0
;
if
(
sdu_buffer
==
NULL
)
{
LOG_E
(
SDAP
,
"%s:%d:%s: NULL sdu_buffer
\n
"
,
__FILE__
,
__LINE__
,
__FUNCTION__
);
exit
(
1
);
}
uint8_t
sdap_buf
[
SDAP_MAX_PDU
];
nr_pdcp_entity_t
*
pdcp_entity
=
entity
->
qfi2drb_map
(
entity
,
ctxt_p
->
sdap
.
qfi
,
rb_id
);
if
(
pdcp_entity
){
sdap_drb_id
=
pdcp_entity
->
rb_id
;
pdcp_ent_has_sdap
=
pdcp_entity
->
has_sdap
;
}
if
(
!
pdcp_ent_has_sdap
){
ret
=
pdcp_data_req
(
ctxt_p
,
srb_flag
,
sdap_drb_id
,
mui
,
confirm
,
sdu_buffer_size
,
sdu_buffer
,
pt_mode
,
sourceL2Id
,
destinationL2Id
);
if
(
!
ret
)
LOG_E
(
SDAP
,
"%s:%d:%s: PDCP refused PDU
\n
"
,
__FILE__
,
__LINE__
,
__FUNCTION__
);
return
ret
;
}
if
(
sdu_buffer_size
==
0
||
sdu_buffer_size
>
8999
)
{
LOG_E
(
SDAP
,
"%s:%d:%s: NULL or 0 or exceeded sdu_buffer_size (over max PDCP SDU)
\n
"
,
__FILE__
,
__LINE__
,
__FUNCTION__
);
return
0
;
}
if
(
ctxt_p
->
enb_flag
)
{
// gNB
offset
=
SDAP_HDR_LENGTH
;
/*
* TS 37.324 4.4 Functions
* marking QoS flow ID in DL packets.
*
* Construct the DL SDAP data PDU.
*/
nr_sdap_dl_hdr_t
sdap_hdr
;
sdap_hdr
.
QFI
=
ctxt_p
->
sdap
.
qfi
;
sdap_hdr
.
RQI
=
ctxt_p
->
sdap
.
rqi
;
sdap_hdr
.
RDI
=
0
;
// SDAP Hardcoded Value
/* Add the SDAP DL Header to the buffer */
memcpy
(
&
sdap_buf
[
0
],
&
sdap_hdr
,
SDAP_HDR_LENGTH
);
memcpy
(
&
sdap_buf
[
SDAP_HDR_LENGTH
],
sdu_buffer
,
sdu_buffer_size
);
LOG_D
(
SDAP
,
"TX Entity QFI: %u
\n
"
,
sdap_hdr
.
QFI
);
LOG_D
(
SDAP
,
"TX Entity RQI: %u
\n
"
,
sdap_hdr
.
RQI
);
LOG_D
(
SDAP
,
"TX Entity RDI: %u
\n
"
,
sdap_hdr
.
RDI
);
}
else
{
// nrUE
offset
=
SDAP_HDR_LENGTH
;
/*
* TS 37.324 4.4 Functions
* marking QoS flow ID in UL packets.
*
* 5.2.1 Uplink
* construct the UL SDAP data PDU as specified in the subclause 6.2.2.3.
*/
nr_sdap_ul_hdr_t
sdap_hdr
;
sdap_hdr
.
QFI
=
ctxt_p
->
sdap
.
qfi
;
sdap_hdr
.
R
=
0
;
sdap_hdr
.
DC
=
ctxt_p
->
sdap
.
dc
;
/* Add the SDAP UL Header to the buffer */
memcpy
(
&
sdap_buf
[
0
],
&
sdap_hdr
,
SDAP_HDR_LENGTH
);
memcpy
(
&
sdap_buf
[
SDAP_HDR_LENGTH
],
sdu_buffer
,
sdu_buffer_size
);
LOG_D
(
SDAP
,
"TX Entity QFI: %u
\n
"
,
sdap_hdr
.
QFI
);
LOG_D
(
SDAP
,
"TX Entity R: %u
\n
"
,
sdap_hdr
.
R
);
LOG_D
(
SDAP
,
"TX Entity DC: %u
\n
"
,
sdap_hdr
.
DC
);
}
/*
* TS 37.324 5.2 Data transfer
* 5.2.1 Uplink UE side
* submit the constructed UL SDAP data PDU to the lower layers
*
* Downlink gNB side
*/
ret
=
pdcp_data_req
(
ctxt_p
,
srb_flag
,
sdap_drb_id
,
mui
,
confirm
,
sdu_buffer_size
+
offset
,
sdap_buf
,
pt_mode
,
sourceL2Id
,
destinationL2Id
);
if
(
!
ret
)
LOG_E
(
SDAP
,
"%s:%d:%s: PDCP refused PDU
\n
"
,
__FILE__
,
__LINE__
,
__FUNCTION__
);
return
ret
;
}
static
void
nr_sdap_rx_entity
(
nr_sdap_entity_t
*
entity
,
nr_pdcp_entity_t
*
pdcp_entity
,
int
rnti
,
char
*
buf
,
int
size
)
{
/* The offset of the SDAP header, it might be 0 if the has_sdap is not true in the pdcp entity. */
int
offset
=
0
;
if
(
pdcp_entity
->
is_gnb
)
{
// gNB
if
(
pdcp_entity
->
has_sdap
&&
pdcp_entity
->
has_sdapULheader
)
{
// Handling the SDAP Header
offset
=
SDAP_HDR_LENGTH
;
nr_sdap_ul_hdr_t
*
sdap_hdr
=
(
nr_sdap_ul_hdr_t
*
)
buf
;
LOG_D
(
SDAP
,
"RX Entity Received QFI : %u
\n
"
,
sdap_hdr
->
QFI
);
LOG_D
(
SDAP
,
"RX Entity Received Reserved bit : %u
\n
"
,
sdap_hdr
->
R
);
LOG_D
(
SDAP
,
"RX Entity Received DC bit : %u
\n
"
,
sdap_hdr
->
DC
);
switch
(
sdap_hdr
->
DC
)
{
case
SDAP_HDR_UL_DATA_PDU
:
LOG_D
(
SDAP
,
"RX Entity Received SDAP Data PDU
\n
"
);
break
;
case
SDAP_HDR_UL_CTRL_PDU
:
LOG_D
(
SDAP
,
"RX Entity Received SDAP Control PDU
\n
"
);
break
;
}
}
// Pushing SDAP SDU to GTP-U Layer
MessageDef
*
message_p
;
uint8_t
*
gtpu_buffer_p
;
gtpu_buffer_p
=
itti_malloc
(
TASK_PDCP_ENB
,
TASK_GTPV1_U
,
size
+
GTPU_HEADER_OVERHEAD_MAX
-
offset
);
AssertFatal
(
gtpu_buffer_p
!=
NULL
,
"OUT OF MEMORY"
);
memcpy
(
&
gtpu_buffer_p
[
GTPU_HEADER_OVERHEAD_MAX
],
buf
+
offset
,
size
-
offset
);
message_p
=
itti_alloc_new_message
(
TASK_PDCP_ENB
,
0
,
GTPV1U_GNB_TUNNEL_DATA_REQ
);
AssertFatal
(
message_p
!=
NULL
,
"OUT OF MEMORY"
);
GTPV1U_GNB_TUNNEL_DATA_REQ
(
message_p
).
buffer
=
gtpu_buffer_p
;
GTPV1U_GNB_TUNNEL_DATA_REQ
(
message_p
).
length
=
size
-
offset
;
GTPV1U_GNB_TUNNEL_DATA_REQ
(
message_p
).
offset
=
GTPU_HEADER_OVERHEAD_MAX
;
GTPV1U_GNB_TUNNEL_DATA_REQ
(
message_p
).
rnti
=
rnti
;
GTPV1U_GNB_TUNNEL_DATA_REQ
(
message_p
).
pdusession_id
=
pdcp_entity
->
pdusession_id
;
LOG_D
(
SDAP
,
"%s() sending message to gtp size %d
\n
"
,
__func__
,
size
-
offset
);
itti_send_msg_to_task
(
TASK_VARIABLE
,
INSTANCE_DEFAULT
,
message_p
);
}
else
{
//nrUE
/*
* TS 37.324 5.2 Data transfer
* 5.2.2 Downlink
* if the DRB from which this SDAP data PDU is received is configured by RRC with the presence of SDAP header.
*/
if
(
pdcp_entity
->
has_sdap
&&
pdcp_entity
->
has_sdapDLheader
)
{
// Handling the SDAP Header
offset
=
SDAP_HDR_LENGTH
;
/*
* TS 37.324 5.2 Data transfer
* 5.2.2 Downlink
* retrieve the SDAP SDU from the DL SDAP data PDU as specified in the subclause 6.2.2.2.
*/
nr_sdap_dl_hdr_t
*
sdap_hdr
=
(
nr_sdap_dl_hdr_t
*
)
buf
;
LOG_D
(
SDAP
,
"RX Entity Received QFI : %u
\n
"
,
sdap_hdr
->
QFI
);
LOG_D
(
SDAP
,
"RX Entity Received RQI : %u
\n
"
,
sdap_hdr
->
RQI
);
LOG_D
(
SDAP
,
"RX Entity Received RDI : %u
\n
"
,
sdap_hdr
->
RDI
);
/*
* TS 37.324 5.2 Data transfer
* 5.2.2 Downlink
* Perform reflective QoS flow to DRB mapping as specified in the subclause 5.3.2.
*/
if
(
sdap_hdr
->
RDI
==
SDAP_REFLECTIVE_MAPPING
)
{
/*
* TS 37.324 5.3 QoS flow to DRB Mapping
* 5.3.2 Reflective mapping
* If there is no stored QoS flow to DRB mapping rule for the QoS flow and a default DRB is configured.
*/
if
(
!
entity
->
qfi2drb_table
[
sdap_hdr
->
QFI
]
&&
entity
->
default_drb
->
rb_id
){
nr_sdap_ul_hdr_t
sdap_ctrl_pdu
=
entity
->
sdap_construct_ctrl_pdu
(
sdap_hdr
->
QFI
);
nr_pdcp_entity_t
*
sdap_ctrl_pdu_drb
=
entity
->
sdap_map_ctrl_pdu
(
entity
,
pdcp_entity
,
SDAP_CTRL_PDU_MAP_DEF_DRB
,
sdap_hdr
->
QFI
);
entity
->
sdap_submit_ctrl_pdu
(
rnti
,
sdap_ctrl_pdu_drb
,
sdap_ctrl_pdu
);
}
/*
* TS 37.324 5.3 QoS flow to DRB mapping
* 5.3.2 Reflective mapping
* if the stored QoS flow to DRB mapping rule for the QoS flow
* is different from the QoS flow to DRB mapping of the DL SDAP data PDU
* and
* the DRB according to the stored QoS flow to DRB mapping rule is configured by RRC
* with the presence of UL SDAP header
*/
if
(
(
pdcp_entity
->
rb_id
!=
entity
->
qfi2drb_table
[
sdap_hdr
->
QFI
]
->
rb_id
)
&&
pdcp_entity
->
has_sdapULheader
){
nr_sdap_ul_hdr_t
sdap_ctrl_pdu
=
entity
->
sdap_construct_ctrl_pdu
(
sdap_hdr
->
QFI
);
nr_pdcp_entity_t
*
sdap_ctrl_pdu_drb
=
entity
->
sdap_map_ctrl_pdu
(
entity
,
pdcp_entity
,
SDAP_CTRL_PDU_MAP_RULE_DRB
,
sdap_hdr
->
QFI
);
entity
->
sdap_submit_ctrl_pdu
(
rnti
,
sdap_ctrl_pdu_drb
,
sdap_ctrl_pdu
);
}
/*
* TS 37.324 5.3 QoS flow to DRB Mapping
* 5.3.2 Reflective mapping
* store the QoS flow to DRB mapping of the DL SDAP data PDU as the QoS flow to DRB mapping rule for the UL.
*/
entity
->
qfi2drb_table
[
sdap_hdr
->
QFI
]
->
rb_id
=
pdcp_entity
->
rb_id
;
}
/*
* TS 37.324 5.2 Data transfer
* 5.2.2 Downlink
* perform RQI handling as specified in the subclause 5.4
*/
if
(
sdap_hdr
->
RQI
==
SDAP_RQI_HANDLING
)
{
LOG_W
(
SDAP
,
"UE - TODD 5.4
\n
"
);
}
}
/* else - retrieve the SDAP SDU from the DL SDAP data PDU as specified in the subclause 6.2.2.1 */
/*
* TS 37.324 5.2 Data transfer
* 5.2.2 Downlink
* deliver the retrieved SDAP SDU to the upper layer.
*/
extern
int
nas_sock_fd
[];
int
len
=
write
(
nas_sock_fd
[
0
],
&
buf
[
offset
],
size
-
offset
);
LOG_D
(
SDAP
,
"RX Entity len : %d
\n
"
,
len
);
LOG_D
(
SDAP
,
"RX Entity size : %d
\n
"
,
size
);
LOG_D
(
SDAP
,
"RX Entity offset : %d
\n
"
,
offset
);
if
(
len
!=
size
-
offset
)
LOG_E
(
SDAP
,
"%s:%d:%s: fatal
\n
"
,
__FILE__
,
__LINE__
,
__FUNCTION__
);
}
}
void
nr_sdap_qfi2drb_map_update
(
nr_sdap_entity_t
*
entity
,
uint8_t
qfi
,
uint8_t
drb
){
if
(
qfi
<
SDAP_MAX_QFI
&&
qfi
>
SDAP_MAP_RULE_EMPTY
&&
drb
>
0
&&
drb
<=
AVLBL_DRB
)
{
nr_pdcp_entity_t
*
pdcp_entity
;
pdcp_entity
=
nr_pdcp_find_entity_sdap
(
entity
->
rnti
,
drb
);
if
(
!
pdcp_entity
){
LOG_D
(
SDAP
,
"Map Update failed - PDCP Entity does not exist, should create it
\n
"
);
LOG_D
(
SDAP
,
"Map Update failed - Mapping to default DRB
\n
"
);
entity
->
qfi2drb_table
[
qfi
]
=
entity
->
default_drb
;
}
entity
->
qfi2drb_table
[
qfi
]
=
pdcp_entity
;
LOG_D
(
SDAP
,
"Updated QFI to DRB Map: QFI %u -> DRB %d
\n
"
,
qfi
,
entity
->
qfi2drb_table
[
qfi
]
->
rb_id
);
}
}
void
nr_sdap_qfi2drb_map_del
(
nr_sdap_entity_t
*
entity
,
uint8_t
qfi
){
entity
->
qfi2drb_table
[
qfi
]
=
SDAP_NO_MAPPING_RULE
;
LOG_D
(
SDAP
,
"Deleted QFI to DRB Map for QFI %u
\n
"
,
qfi
);
}
nr_pdcp_entity_t
*
nr_sdap_qfi2drb_map
(
nr_sdap_entity_t
*
entity
,
uint8_t
qfi
,
long
upper_layer_rb_id
){
nr_pdcp_entity_t
*
pdcp_entity
;
pdcp_entity
=
entity
->
qfi2drb_table
[
qfi
];
if
(
pdcp_entity
){
return
pdcp_entity
;
}
else
if
(
entity
->
default_drb
)
{
LOG_D
(
SDAP
,
"Mapped QFI %u to Default DRB
\n
"
,
qfi
);
entity
->
qfi2drb_map_update
(
entity
,
qfi
,
entity
->
default_drb
->
rb_id
);
return
entity
->
default_drb
;
}
else
{
/* Update map for Hardcode DRB ID given from upper layer (ue/enb_tun_read_thread rb_id)*/
entity
->
qfi2drb_map_update
(
entity
,
qfi
,
upper_layer_rb_id
);
return
SDAP_MAP_RULE_EMPTY
;
}
return
pdcp_entity
;
}
nr_sdap_ul_hdr_t
nr_sdap_construct_ctrl_pdu
(
uint8_t
qfi
){
nr_sdap_ul_hdr_t
sdap_end_marker_hdr
;
sdap_end_marker_hdr
.
QFI
=
qfi
;
sdap_end_marker_hdr
.
R
=
0
;
sdap_end_marker_hdr
.
DC
=
SDAP_HDR_UL_CTRL_PDU
;
LOG_D
(
SDAP
,
"Constructed Control PDU with QFI:%u R:%u DC:%u
\n
"
,
sdap_end_marker_hdr
.
QFI
,
sdap_end_marker_hdr
.
R
,
sdap_end_marker_hdr
.
DC
);
return
sdap_end_marker_hdr
;
}
nr_pdcp_entity_t
*
nr_sdap_map_ctrl_pdu
(
nr_sdap_entity_t
*
entity
,
nr_pdcp_entity_t
*
pdcp_entity
,
int
map_type
,
uint8_t
dl_qfi
){
nr_pdcp_entity_t
*
drb_of_endmarker
=
NULL
;
if
(
map_type
==
SDAP_CTRL_PDU_MAP_DEF_DRB
){
drb_of_endmarker
=
entity
->
default_drb
;
LOG_D
(
SDAP
,
"Mapped Control PDU to default drb
\n
"
);
}
if
(
map_type
==
SDAP_CTRL_PDU_MAP_RULE_DRB
){
drb_of_endmarker
=
entity
->
qfi2drb_map
(
entity
,
dl_qfi
,
pdcp_entity
->
rb_id
);
LOG_D
(
SDAP
,
"Mapped Control PDU according to the mapping rule, qfi %u
\n
"
,
dl_qfi
);
}
return
drb_of_endmarker
;
}
void
nr_sdap_submit_ctrl_pdu
(
int
rnti
,
nr_pdcp_entity_t
*
sdap_ctrl_pdu_drb
,
nr_sdap_ul_hdr_t
ctrl_pdu
){
if
(
sdap_ctrl_pdu_drb
){
sdap_ctrl_pdu_drb
->
recv_sdu
(
sdap_ctrl_pdu_drb
,
(
char
*
)
&
ctrl_pdu
,
SDAP_HDR_LENGTH
,
RLC_MUI_UNDEFINED
);
LOG_D
(
SDAP
,
"Sent Control PDU to PDCP Layer.
\n
"
);
}
}
void
nr_sdap_ue_qfi2drb_config
(
nr_sdap_entity_t
*
existing_sdap_entity
,
nr_pdcp_entity_t
*
pdcp_entity
,
uint16_t
rnti
,
NR_QFI_t
*
mapped_qfi_2_add
,
uint8_t
mappedQFIs2AddCount
,
uint8_t
drb_identity
)
{
uint8_t
qfi
=
0
;
for
(
int
i
=
0
;
i
<
mappedQFIs2AddCount
;
i
++
){
qfi
=
mapped_qfi_2_add
[
i
];
if
(
existing_sdap_entity
->
default_drb
&&
existing_sdap_entity
->
qfi2drb_table
[
qfi
]
==
SDAP_NO_MAPPING_RULE
){
nr_sdap_ul_hdr_t
sdap_ctrl_pdu
=
existing_sdap_entity
->
sdap_construct_ctrl_pdu
(
qfi
);
nr_pdcp_entity_t
*
sdap_ctrl_pdu_drb
=
existing_sdap_entity
->
sdap_map_ctrl_pdu
(
existing_sdap_entity
,
pdcp_entity
,
SDAP_CTRL_PDU_MAP_DEF_DRB
,
qfi
);
existing_sdap_entity
->
sdap_submit_ctrl_pdu
(
rnti
,
sdap_ctrl_pdu_drb
,
sdap_ctrl_pdu
);
}
if
(
existing_sdap_entity
->
qfi2drb_table
[
qfi
]
->
rb_id
!=
drb_identity
&&
pdcp_entity
->
has_sdapULheader
){
nr_sdap_ul_hdr_t
sdap_ctrl_pdu
=
existing_sdap_entity
->
sdap_construct_ctrl_pdu
(
qfi
);
nr_pdcp_entity_t
*
sdap_ctrl_pdu_drb
=
existing_sdap_entity
->
sdap_map_ctrl_pdu
(
existing_sdap_entity
,
pdcp_entity
,
SDAP_CTRL_PDU_MAP_RULE_DRB
,
qfi
);
existing_sdap_entity
->
sdap_submit_ctrl_pdu
(
rnti
,
sdap_ctrl_pdu_drb
,
sdap_ctrl_pdu
);
}
}
}
nr_sdap_entity_t
*
new_nr_sdap_entity
(
uint16_t
rnti
,
int
pdusession_id
,
boolean_t
is_defaultDRB
,
uint8_t
drb_identity
,
NR_QFI_t
*
mapped_qfi_2_add
,
uint8_t
mappedQFIs2AddCount
)
{
if
(
nr_sdap_get_entity
(
rnti
,
pdusession_id
))
{
LOG_E
(
SDAP
,
"SDAP Entity for UE already exists.
\n
"
);
nr_sdap_entity_t
*
existing_sdap_entity
=
nr_sdap_get_entity
(
rnti
,
pdusession_id
);
nr_pdcp_entity_t
*
pdcp_entity
=
existing_sdap_entity
->
default_drb
;
nr_sdap_ue_qfi2drb_config
(
existing_sdap_entity
,
pdcp_entity
,
rnti
,
mapped_qfi_2_add
,
mappedQFIs2AddCount
,
drb_identity
);
return
existing_sdap_entity
;
}
nr_sdap_entity_t
*
sdap_entity
;
sdap_entity
=
calloc
(
1
,
sizeof
(
nr_sdap_entity_t
));
if
(
sdap_entity
==
NULL
)
{
LOG_E
(
SDAP
,
"SDAP Entity creation failed, out of memory
\n
"
);
exit
(
1
);
}
sdap_entity
->
rnti
=
rnti
;
sdap_entity
->
pdusession_id
=
pdusession_id
;
sdap_entity
->
tx_entity
=
nr_sdap_tx_entity
;
sdap_entity
->
rx_entity
=
nr_sdap_rx_entity
;
sdap_entity
->
sdap_construct_ctrl_pdu
=
nr_sdap_construct_ctrl_pdu
;
sdap_entity
->
sdap_map_ctrl_pdu
=
nr_sdap_map_ctrl_pdu
;
sdap_entity
->
sdap_submit_ctrl_pdu
=
nr_sdap_submit_ctrl_pdu
;
sdap_entity
->
qfi2drb_map_update
=
nr_sdap_qfi2drb_map_update
;
sdap_entity
->
qfi2drb_map_delete
=
nr_sdap_qfi2drb_map_del
;
sdap_entity
->
qfi2drb_map
=
nr_sdap_qfi2drb_map
;
if
(
is_defaultDRB
)
{
nr_pdcp_entity_t
*
pdcp_entity
=
nr_pdcp_find_entity_sdap
(
sdap_entity
->
rnti
,
drb_identity
);
sdap_entity
->
default_drb
=
pdcp_entity
;
LOG_I
(
SDAP
,
"Default DRB for the created SDAP entity: %d
\n
"
,
sdap_entity
->
default_drb
->
rb_id
);
if
(
mappedQFIs2AddCount
)
{
for
(
int
i
=
0
;
i
<
mappedQFIs2AddCount
;
i
++
)
{
LOG_D
(
SDAP
,
"Mapped QFI to Add : %ld
\n
"
,
mapped_qfi_2_add
[
i
]);
sdap_entity
->
qfi2drb_map_update
(
sdap_entity
,
mapped_qfi_2_add
[
i
],
sdap_entity
->
default_drb
->
rb_id
);
}
}
}
sdap_entity
->
next_entity
=
sdap_info
.
sdap_entity_llist
;
sdap_info
.
sdap_entity_llist
=
sdap_entity
;
return
sdap_entity
;
}
nr_sdap_entity_t
*
nr_sdap_get_entity
(
uint16_t
rnti
,
int
pdusession_id
)
{
nr_sdap_entity_t
*
sdap_entity
;
sdap_entity
=
sdap_info
.
sdap_entity_llist
;
if
(
sdap_entity
==
NULL
)
return
NULL
;
while
(
sdap_entity
->
rnti
!=
rnti
&&
sdap_entity
->
next_entity
!=
NULL
)
{
sdap_entity
=
sdap_entity
->
next_entity
;
}
if
(
sdap_entity
->
rnti
==
rnti
&&
sdap_entity
->
pdusession_id
==
pdusession_id
)
return
sdap_entity
;
return
NULL
;
}
void
delete_nr_sdap_entity
(
uint16_t
rnti
)
{
nr_sdap_entity_t
*
entityPtr
,
*
entityPrev
=
NULL
;
entityPtr
=
sdap_info
.
sdap_entity_llist
;
if
(
entityPtr
->
rnti
==
rnti
)
{
sdap_info
.
sdap_entity_llist
=
sdap_info
.
sdap_entity_llist
->
next_entity
;
free
(
entityPtr
);
}
else
{
while
(
entityPtr
->
rnti
!=
rnti
&&
entityPtr
->
next_entity
!=
NULL
)
{
entityPrev
=
entityPtr
;
entityPtr
=
entityPtr
->
next_entity
;
}
if
(
entityPtr
->
rnti
!=
rnti
)
{
entityPrev
->
next_entity
=
entityPtr
->
next_entity
;
free
(
entityPtr
);
}
}
}
openair2/SDAP/nr_sdap/nr_sdap_entity.h
0 → 100644
View file @
a826af58
/*
* 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_SDAP_ENTITY_H_
#define _NR_SDAP_ENTITY_H_
#include <stdint.h>
#include "openair2/COMMON/platform_types.h"
#include "openair2/LAYER2/nr_pdcp/nr_pdcp_entity.h"
#include "NR_RadioBearerConfig.h"
#define SDAP_BITMASK_DC (0x80)
#define SDAP_BITMASK_R (0x40)
#define SDAP_BITMASK_QFI (0x3F)
#define SDAP_BITMASK_RQI (0x40)
#define SDAP_HDR_UL_DATA_PDU (1)
#define SDAP_HDR_UL_CTRL_PDU (0)
#define SDAP_HDR_LENGTH (1)
#define SDAP_MAX_QFI (64)
#define SDAP_MAP_RULE_EMPTY (0)
#define AVLBL_DRB (5)
#define SDAP_NO_MAPPING_RULE (0)
#define SDAP_REFLECTIVE_MAPPING (1)
#define SDAP_RQI_HANDLING (1)
#define SDAP_CTRL_PDU_MAP_DEF_DRB (0)
#define SDAP_CTRL_PDU_MAP_RULE_DRB (1)
#define SDAP_MAX_PDU (9000)
/*
* The values of QoS Flow ID (QFI) and Reflective QoS Indication,
* are located in the PDU Session Container, which is conveyed by
* the GTP-U Extension Header. Inside the DL PDU SESSION INFORMATION frame.
* TS 38.415 Fig. 5.5.2.1-1
*/
typedef
struct
nr_sdap_dl_hdr_s
{
uint8_t
QFI
:
6
;
uint8_t
RQI
:
1
;
uint8_t
RDI
:
1
;
}
__attribute__
((
packed
))
nr_sdap_dl_hdr_t
;
typedef
struct
nr_sdap_ul_hdr_s
{
uint8_t
QFI
:
6
;
uint8_t
R
:
1
;
uint8_t
DC
:
1
;
}
__attribute__
((
packed
))
nr_sdap_ul_hdr_t
;
typedef
struct
nr_sdap_entity_s
{
uint16_t
rnti
;
nr_pdcp_entity_t
*
default_drb
;
int
pdusession_id
;
nr_pdcp_entity_t
*
qfi2drb_table
[
SDAP_MAX_QFI
];
void
(
*
qfi2drb_map_update
)(
struct
nr_sdap_entity_s
*
entity
,
uint8_t
qfi
,
uint8_t
drb
);
void
(
*
qfi2drb_map_delete
)(
struct
nr_sdap_entity_s
*
entity
,
uint8_t
qfi
);
nr_pdcp_entity_t
*
(
*
qfi2drb_map
)(
struct
nr_sdap_entity_s
*
entity
,
uint8_t
qfi
,
long
upper_layer_rb_id
);
nr_sdap_ul_hdr_t
(
*
sdap_construct_ctrl_pdu
)(
uint8_t
qfi
);
nr_pdcp_entity_t
*
(
*
sdap_map_ctrl_pdu
)(
struct
nr_sdap_entity_s
*
entity
,
nr_pdcp_entity_t
*
pdcp_entity
,
int
map_type
,
uint8_t
dl_qfi
);
void
(
*
sdap_submit_ctrl_pdu
)(
int
rnti
,
nr_pdcp_entity_t
*
sdap_ctrl_pdu_drb
,
nr_sdap_ul_hdr_t
ctrl_pdu
);
boolean_t
(
*
tx_entity
)(
struct
nr_sdap_entity_s
*
entity
,
protocol_ctxt_t
*
ctxt_p
,
const
srb_flag_t
srb_flag
,
const
rb_id_t
rb_id
,
const
mui_t
mui
,
const
confirm_t
confirm
,
const
sdu_size_t
sdu_buffer_size
,
unsigned
char
*
const
sdu_buffer
,
const
pdcp_transmission_mode_t
pt_mode
,
const
uint32_t
*
sourceL2Id
,
const
uint32_t
*
destinationL2Id
);
void
(
*
rx_entity
)(
struct
nr_sdap_entity_s
*
entity
,
nr_pdcp_entity_t
*
pdcp_entity
,
int
rnti
,
char
*
buf
,
int
size
);
/* List of entities */
struct
nr_sdap_entity_s
*
next_entity
;
}
nr_sdap_entity_t
;
/* QFI to DRB Mapping Related Function */
void
nr_sdap_qfi2drb_map_update
(
nr_sdap_entity_t
*
entity
,
uint8_t
qfi
,
uint8_t
drb
);
/* QFI to DRB Mapping Related Function */
void
nr_sdap_qfi2drb_map_del
(
nr_sdap_entity_t
*
entity
,
uint8_t
qfi
);
/*
* TS 37.324
* 4.4 Functions
* Mapping between a QoS flow and a DRB for both DL and UL.
*
* 5.2.1 Uplink
* If there is no stored QoS flow to DRB mapping rule for the QoS flow as specified in the subclause 5.3, map the SDAP SDU to the default DRB
* else, map the SDAP SDU to the DRB according to the stored QoS flow to DRB mapping rule.
*/
nr_pdcp_entity_t
*
nr_sdap_qfi2drb_map
(
nr_sdap_entity_t
*
entity
,
uint8_t
qfi
,
long
upper_layer_rb_id
);
/*
* TS 37.324 5.3 QoS flow to DRB Mapping
* construct an end-marker control PDU, as specified in the subclause 6.2.3, for the QoS flow;
*/
nr_sdap_ul_hdr_t
nr_sdap_construct_ctrl_pdu
(
uint8_t
qfi
);
/*
* TS 37.324 5.3 QoS flow to DRB Mapping
* map the end-marker control PDU to the
* 1.) default DRB or
* 2.) DRB according to the stored QoS flow to DRB mapping rule
*/
nr_pdcp_entity_t
*
nr_sdap_map_ctrl_pdu
(
nr_sdap_entity_t
*
entity
,
nr_pdcp_entity_t
*
pdcp_entity
,
int
map_type
,
uint8_t
dl_qfi
);
/*
* TS 37.324 5.3 QoS flow to DRB Mapping
* Submit the end-marker control PDU to the lower layer.
*/
void
nr_sdap_submit_ctrl_pdu
(
int
rnti
,
nr_pdcp_entity_t
*
sdap_ctrl_pdu_drb
,
nr_sdap_ul_hdr_t
ctrl_pdu
);
/*
* TS 37.324 5.3 QoS flow to DRB Mapping
* 5.3.1 Configuration Procedures
*/
void
nr_sdap_ue_qfi2drb_config
(
nr_sdap_entity_t
*
existing_sdap_entity
,
nr_pdcp_entity_t
*
pdcp_entity
,
uint16_t
rnti
,
NR_QFI_t
*
mapped_qfi_2_add
,
uint8_t
mappedQFIs2AddCount
,
uint8_t
drb_identity
);
/*
* TS 37.324 4.4 5.1.1 SDAP entity establishment
* Establish an SDAP entity.
*/
nr_sdap_entity_t
*
new_nr_sdap_entity
(
uint16_t
rnti
,
int
pdusession_id
,
boolean_t
is_defaultDRB
,
uint8_t
default_DRB
,
NR_QFI_t
*
mapped_qfi_2_add
,
uint8_t
mappedQFIs2AddCount
);
/* Entity Handling Related Functions */
nr_sdap_entity_t
*
nr_sdap_get_entity
(
uint16_t
rnti
,
int
pdusession_id
);
/* Entity Handling Related Functions */
void
delete_nr_sdap_entity
(
uint16_t
rnti
);
#endif
openair2/SDAP/nr_sdap/nr_sdap_gnb.c
deleted
100644 → 0
View file @
5a3eeac5
/*
* 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_sdap_gnb.h"
#include <openair2/LAYER2/PDCP_v10.1.0/pdcp.h>
boolean_t
sdap_gnb_data_req
(
protocol_ctxt_t
*
ctxt_p
,
const
srb_flag_t
srb_flag
,
const
rb_id_t
rb_id
,
const
mui_t
mui
,
const
confirm_t
confirm
,
const
sdu_size_t
sdu_buffer_size
,
unsigned
char
*
const
sdu_buffer
,
const
pdcp_transmission_mode_t
pt_mode
,
const
uint32_t
*
sourceL2Id
,
const
uint32_t
*
destinationL2Id
)
{
if
(
sdu_buffer
==
NULL
)
{
LOG_E
(
PDCP
,
"%s:%d:%s: SDAP Layer gNB - NULL sdu_buffer
\n
"
,
__FILE__
,
__LINE__
,
__FUNCTION__
);
exit
(
1
);
}
if
(
sdu_buffer_size
==
0
)
{
LOG_E
(
PDCP
,
"%s:%d:%s: SDAP Layer gNB - NULL or 0 sdu_buffer_size
\n
"
,
__FILE__
,
__LINE__
,
__FUNCTION__
);
exit
(
1
);
}
uint8_t
*
sdap_buf
=
(
uint8_t
*
)
malloc
(
sdu_buffer_size
+
SDAP_HDR_LENGTH
);
nr_sdap_dl_hdr_t
sdap_hdr
;
sdap_hdr
.
RDI
=
0
;
// SDAP_Hardcoded -
sdap_hdr
.
RQI
=
0
;
// SDAP_Hardcoded - Should get this info from DL_PDU_SESSION_INFORMATION
sdap_hdr
.
QFI
=
1
;
// SDAP_Hardcoded - Should get this info from DL_PDU_SESSION_INFORMATION
memcpy
(
&
sdap_buf
[
0
],
&
sdap_hdr
,
1
);
memcpy
(
&
sdap_buf
[
1
],
sdu_buffer
,
sdu_buffer_size
);
rb_id_t
sdap_drb_id
=
rb_id
;
// SDAP_Hardcoded - Should get this info from QFI to DRB mapping table
boolean_t
ret
=
pdcp_data_req
(
ctxt_p
,
srb_flag
,
sdap_drb_id
,
mui
,
confirm
,
sdu_buffer_size
+
1
,
sdap_buf
,
pt_mode
,
sourceL2Id
,
destinationL2Id
);
if
(
!
ret
)
{
LOG_E
(
PDCP
,
"%s:%d:%s: SDAP Layer gNB - PDCP DL refused PDU
\n
"
,
__FILE__
,
__LINE__
,
__FUNCTION__
);
free
(
sdap_buf
);
return
0
;
}
free
(
sdap_buf
);
return
1
;
}
void
sdap_gnb_ul_header_handler
(
char
sdap_gnb_ul_hdr
)
{
nr_sdap_ul_hdr_t
*
sdap_hdr_ul
=
(
nr_sdap_ul_hdr_t
*
)
&
sdap_gnb_ul_hdr
;
switch
(
sdap_hdr_ul
->
DC
)
{
case
SDAP_HDR_UL_DATA_PDU
:
LOG_I
(
PDCP
,
"%s:%d:%s: SDAP Layer gNB - UL Received SDAP Data PDU
\n
"
,
__FILE__
,
__LINE__
,
__FUNCTION__
);
break
;
case
SDAP_HDR_UL_CTRL_PDU
:
LOG_I
(
PDCP
,
"%s:%d:%s: SDAP Layer gNB - Received SDAP Control PDU
\n
"
,
__FILE__
,
__LINE__
,
__FUNCTION__
);
break
;
}
}
\ No newline at end of file
openair3/ocp-gtpu/gtp_itf.cpp
View file @
a826af58
...
...
@@ -17,7 +17,7 @@ extern "C" {
#include <openair2/COMMON/gtpv1_u_messages_types.h>
#include <openair3/ocp-gtpu/gtp_itf.h>
#include <openair2/LAYER2/PDCP_v10.1.0/pdcp.h>
#include "openair2/SDAP/nr_sdap/nr_sdap
_gnb
.h"
#include "openair2/SDAP/nr_sdap/nr_sdap.h"
//#include <openair1/PHY/phy_extern.h>
#pragma pack(1)
...
...
@@ -34,8 +34,35 @@ typedef struct Gtpv1uMsgHeader {
teid_t
teid
;
}
__attribute__
((
packed
))
Gtpv1uMsgHeaderT
;
typedef
struct
Gtpv1uMsgHeaderOptFields
{
uint8_t
seqNum1Oct
;
uint8_t
seqNum2Oct
;
uint8_t
NPDUNum
;
uint8_t
NextExtHeaderType
;
}
__attribute__
((
packed
))
Gtpv1uMsgHeaderOptFieldsT
;
typedef
struct
PDUSessionContainer
{
uint8_t
spare
:
4
;
uint8_t
PDU_type
:
4
;
uint8_t
QFI
:
6
;
uint8_t
RQI
:
1
;
uint8_t
PPP
:
1
;
}
__attribute__
((
packed
))
PDUSessionContainerT
;
typedef
struct
Gtpv1uExtHeader
{
uint8_t
ExtHeaderLen
;
PDUSessionContainerT
pdusession_cntr
;
//uint8_t NextExtHeaderType;
}
__attribute__
((
packed
))
Gtpv1uExtHeaderT
;
#pragma pack()
// TS 29.281, fig 5.2.1-3
#define PDU_SESSION_CONTAINER (0x85)
// TS 29.281, 5.2.1
#define EXT_HDR_LNTH_OCTET_UNITS (4)
#define NO_MORE_EXT_HDRS (0)
// TS 29.060, table 7.1 defines the possible message types
// here are all the possible messages (3GPP R16)
#define GTP_ECHO_REQ (1)
...
...
@@ -65,6 +92,7 @@ typedef struct {
rnti_t
rnti
;
ebi_t
incoming_rb_id
;
gtpCallback
callBack
;
int
pdusession_id
;
}
rntiData_t
;
class
gtpEndPoint
{
...
...
@@ -449,6 +477,8 @@ teid_t newGtpuCreateTunnel(instance_t instance, rnti_t rnti, int incoming_bearer
inst
->
te2ue_mapping
[
incoming_teid
].
callBack
=
callBack
;
inst
->
te2ue_mapping
[
incoming_teid
].
pdusession_id
=
(
uint8_t
)
outgoing_bearer_id
;
gtpv1u_bearer_t
*
tmp
=&
inst
->
ue2te_mapping
[
rnti
].
bearers
[
outgoing_bearer_id
];
int
addrs_length_in_bytes
=
remoteAddr
.
length
/
8
;
...
...
@@ -574,7 +604,7 @@ int gtpv1u_create_ngu_tunnel( const instance_t instance,
create_tunnel_req
->
pdusession_id
[
i
],
create_tunnel_req
->
outgoing_teid
[
i
],
create_tunnel_req
->
dst_addr
[
i
],
dstport
,
sdap_
gnb_
data_req
);
sdap_data_req
);
create_tunnel_resp
->
status
=
0
;
create_tunnel_resp
->
rnti
=
create_tunnel_req
->
rnti
;
create_tunnel_resp
->
num_tunnels
=
create_tunnel_req
->
num_tunnels
;
...
...
@@ -815,10 +845,28 @@ static int Gtpv1uHandleGpdu(int h,
return
GTPNOK
;
}
int
offset
=
8
;
int
offset
=
sizeof
(
Gtpv1uMsgHeaderT
);
uint8_t
qfi
=
0
;
boolean_t
rqi
=
FALSE
;
if
(
msgHdr
->
E
||
msgHdr
->
S
||
msgHdr
->
PN
)
offset
+=
8
;
if
(
msgHdr
->
E
||
msgHdr
->
S
||
msgHdr
->
PN
){
Gtpv1uMsgHeaderOptFieldsT
*
msgHdrOpt
=
(
Gtpv1uMsgHeaderOptFieldsT
*
)(
msgBuf
+
offset
);
offset
+=
sizeof
(
Gtpv1uMsgHeaderOptFieldsT
);
if
(
msgHdr
->
E
&&
msgHdrOpt
->
NextExtHeaderType
==
PDU_SESSION_CONTAINER
){
Gtpv1uExtHeaderT
*
msgHdrExt
=
(
Gtpv1uExtHeaderT
*
)(
msgBuf
+
offset
);
offset
+=
msgHdrExt
->
ExtHeaderLen
*
EXT_HDR_LNTH_OCTET_UNITS
;
qfi
=
msgHdrExt
->
pdusession_cntr
.
QFI
;
rqi
=
msgHdrExt
->
pdusession_cntr
.
RQI
;
/*
* Check if the next extension header type of GTP extension header is set to 0
* We can not put it in the struct Gtpv1uExtHeaderT because the length is dynamic.
*/
if
(
*
(
msgBuf
+
offset
-
1
)
!=
NO_MORE_EXT_HDRS
)
LOG_W
(
GTPU
,
"Warning - Next extension header is not zero, handle it
\n
"
);
}
}
// This context is not good for gtp
// frame, ... has no meaning
...
...
@@ -828,6 +876,9 @@ static int Gtpv1uHandleGpdu(int h,
ctxt
.
enb_flag
=
1
;
ctxt
.
instance
=
inst
->
addr
.
originInstance
;
ctxt
.
rnti
=
tunnel
->
second
.
rnti
;
ctxt
.
sdap
.
qfi
=
qfi
;
ctxt
.
sdap
.
rqi
=
rqi
;
ctxt
.
sdap
.
pdusession_id
=
tunnel
->
second
.
pdusession_id
;
ctxt
.
frame
=
0
;
ctxt
.
subframe
=
0
;
ctxt
.
eNB_index
=
0
;
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment