GTP PDCP change rnti to ue id

This commit is contained in:
Sakthivel Velumani
2022-12-13 12:42:32 +01:00
committed by laurent
parent a97dfedb78
commit ec21db63eb
36 changed files with 417 additions and 550 deletions
+115 -132
View File
@@ -108,18 +108,18 @@ typedef struct gtpv1u_bearer_s {
} gtpv1u_bearer_t;
typedef struct {
map<int, gtpv1u_bearer_t> bearers;
map<ue_id_t, gtpv1u_bearer_t> bearers;
teid_t outgoing_teid;
} teidData_t;
typedef struct {
rnti_t rnti;
ue_id_t ue_id;
ebi_t incoming_rb_id;
gtpCallback callBack;
teid_t outgoing_teid;
gtpCallbackSDAP callBackSDAP;
int pdusession_id;
} rntiData_t;
} ueidData_t;
class gtpEndPoint {
public:
@@ -127,8 +127,8 @@ class gtpEndPoint {
uint8_t foundAddr[20];
int foundAddrLen;
int ipVersion;
map<int,teidData_t> ue2te_mapping;
map<int,rntiData_t> te2ue_mapping;
map<uint64_t,teidData_t> ue2te_mapping;
map<uint64_t,ueidData_t> te2ue_mapping;
// we use the same port number for source and destination address
// this allow using non standard gtp port number (different from 2152)
// and so, for example tu run 4G and 5G cores on one system
@@ -141,7 +141,7 @@ class gtpEndPoints {
public:
pthread_mutex_t gtp_lock=PTHREAD_MUTEX_INITIALIZER;
// the instance id will be the Linux socket handler, as this is uniq
map<int, gtpEndPoint> instances;
map<uint64_t, gtpEndPoint> instances;
~gtpEndPoints() {
// automatically close all sockets on quit
@@ -184,20 +184,20 @@ instance_t legacyInstanceMapping=0;
gtpEndPoint * inst=&instChk->second;
#define getRntiRetVoid(insT, RnTi) \
auto ptrRnti=insT->ue2te_mapping.find(RnTi); \
#define getUeRetVoid(insT, Ue) \
auto ptrUe=insT->ue2te_mapping.find(Ue); \
\
if ( ptrRnti==insT->ue2te_mapping.end() ) { \
LOG_E(GTPU, "[%ld] gtpv1uSend failed: while getting ue rnti %x in hashtable ue_mapping\n", instance, rnti); \
if ( ptrUe==insT->ue2te_mapping.end() ) { \
LOG_E(GTPU, "[%ld] gtpv1uSend failed: while getting ue id %ld in hashtable ue_mapping\n", instance, ue_id); \
pthread_mutex_unlock(&globGtp.gtp_lock); \
return; \
}
#define getRntiRetInt(insT, RnTi) \
auto ptrRnti=insT->ue2te_mapping.find(RnTi); \
#define getUeRetInt(insT, Ue) \
auto ptrUe=insT->ue2te_mapping.find(Ue); \
\
if ( ptrRnti==insT->ue2te_mapping.end() ) { \
LOG_E(GTPU, "[%ld] gtpv1uSend failed: while getting ue rnti %x in hashtable ue_mapping\n", instance, rnti); \
if ( ptrUe==insT->ue2te_mapping.end() ) { \
LOG_E(GTPU, "[%ld] gtpv1uSend failed: while getting ue id %ld in hashtable ue_mapping\n", instance, ue_id); \
pthread_mutex_unlock(&globGtp.gtp_lock); \
return GTPNOK; \
}
@@ -281,58 +281,25 @@ static int gtpv1uCreateAndSendMsg(int h,
return !GTPNOK;
}
static void gtpv1uSend(instance_t instance, gtpv1u_enb_tunnel_data_req_t *req, bool seqNumFlag, bool npduNumFlag) {
static void gtpv1uSend(instance_t instance, gtpv1u_tunnel_data_req_t *req, bool seqNumFlag, bool npduNumFlag) {
uint8_t *buffer=req->buffer+req->offset;
size_t length=req->length;
rnti_t rnti=req->rnti;
int rab_id=req->rab_id;
ue_id_t ue_id=req->ue_id;
int bearer_id=req->bearer_id;
pthread_mutex_lock(&globGtp.gtp_lock);
getInstRetVoid(compatInst(instance));
getRntiRetVoid(inst, rnti);
getUeRetVoid(inst, ue_id);
map<int, gtpv1u_bearer_t>::iterator ptr2=ptrRnti->second.bearers.find(rab_id);
auto ptr2=ptrUe->second.bearers.find(bearer_id);
if ( ptr2 == ptrRnti->second.bearers.end() ) {
LOG_E(GTPU,"[%ld] GTP-U instance: sending a packet to a non existant RNTI:RAB: %x/%x\n", instance, rnti, rab_id);
if ( ptr2 == ptrUe->second.bearers.end() ) {
LOG_E(GTPU,"[%ld] GTP-U instance: sending a packet to a non existant UE:RAB: %lx/%x\n", instance, ue_id, bearer_id);
pthread_mutex_unlock(&globGtp.gtp_lock);
return;
}
LOG_D(GTPU,"[%ld] sending a packet to RNTI:RAB:teid %x/%x/%x, len %lu, oldseq %d, oldnum %d\n",
instance, rnti, rab_id,ptr2->second.teid_outgoing,length, ptr2->second.seqNum,ptr2->second.npduNum );
if(seqNumFlag)
ptr2->second.seqNum++;
if(npduNumFlag)
ptr2->second.npduNum++;
// copy to release the mutex
gtpv1u_bearer_t tmp=ptr2->second;
pthread_mutex_unlock(&globGtp.gtp_lock);
gtpv1uCreateAndSendMsg(
compatInst(instance), tmp.outgoing_ip_addr, tmp.outgoing_port, GTP_GPDU, tmp.teid_outgoing, buffer, length, seqNumFlag, npduNumFlag, tmp.seqNum, tmp.npduNum, NO_MORE_EXT_HDRS, NULL, 0);
}
static void gtpv1uSend2(instance_t instance, gtpv1u_gnb_tunnel_data_req_t *req, bool seqNumFlag, bool npduNumFlag) {
uint8_t *buffer=req->buffer+req->offset;
size_t length=req->length;
rnti_t rnti=req->rnti;
int rab_id=req->pdusession_id;
pthread_mutex_lock(&globGtp.gtp_lock);
getInstRetVoid(compatInst(instance));
getRntiRetVoid(inst, rnti);
map<int, gtpv1u_bearer_t>::iterator ptr2=ptrRnti->second.bearers.find(rab_id);
if ( ptr2 == ptrRnti->second.bearers.end() ) {
LOG_D(GTPU,"GTP-U instance: %ld sending a packet to a non existant RNTI:RAB: %x/%x\n", instance, rnti, rab_id);
pthread_mutex_unlock(&globGtp.gtp_lock);
return;
}
LOG_D(GTPU,"[%ld] GTP-U sending a packet to RNTI:RAB:teid %x/%x/%x, len %lu, oldseq %d, oldnum %d\n",
instance, rnti, rab_id,ptr2->second.teid_outgoing,length, ptr2->second.seqNum,ptr2->second.npduNum );
LOG_D(GTPU,"[%ld] sending a packet to UE:RAB:teid %lx/%x/%x, len %lu, oldseq %d, oldnum %d\n",
instance, ue_id, bearer_id,ptr2->second.teid_outgoing,length, ptr2->second.seqNum,ptr2->second.npduNum );
if(seqNumFlag)
ptr2->second.seqNum++;
@@ -404,16 +371,16 @@ static void fillDlDeliveryStatusReport(extensionHeader_t *extensionHeader, uint3
}
static void gtpv1uSendDlDeliveryStatus(instance_t instance, gtpv1u_DU_buffer_report_req_t *req){
rnti_t rnti=req->rnti;
int rab_id=req->pdusession_id;
ue_id_t ue_id=req->ue_id;
int bearer_id=req->pdusession_id;
pthread_mutex_lock(&globGtp.gtp_lock);
getInstRetVoid(compatInst(instance));
getRntiRetVoid(inst, rnti);
getUeRetVoid(inst, ue_id);
map<int, gtpv1u_bearer_t>::iterator ptr2=ptrRnti->second.bearers.find(rab_id);
auto ptr2=ptrUe->second.bearers.find(bearer_id);
if ( ptr2 == ptrRnti->second.bearers.end() ) {
LOG_D(GTPU,"GTP-U instance: %ld sending a packet to a non existant RNTI:RAB: %x/%x\n", instance, rnti, rab_id);
if ( ptr2 == ptrUe->second.bearers.end() ) {
LOG_D(GTPU,"GTP-U instance: %ld sending a packet to a non existant UE ID:RAB: %lu/%x\n", instance, ue_id, bearer_id);
pthread_mutex_unlock(&globGtp.gtp_lock);
return;
}
@@ -422,8 +389,8 @@ static void gtpv1uSendDlDeliveryStatus(instance_t instance, gtpv1u_DU_buffer_rep
extensionHeader = (extensionHeader_t *) calloc(1, sizeof(extensionHeader_t));
fillDlDeliveryStatusReport(extensionHeader, req->buffer_availability,0);
LOG_I(GTPU,"[%ld] GTP-U sending DL Data Delivery status to RNTI:RAB:teid %x/%x/%x, oldseq %d, oldnum %d\n",
instance, rnti, rab_id,ptr2->second.teid_outgoing, ptr2->second.seqNum,ptr2->second.npduNum );
LOG_I(GTPU,"[%ld] GTP-U sending DL Data Delivery status to UE ID:RAB:teid %lu/%x/%x, oldseq %d, oldnum %d\n",
instance, ue_id, bearer_id,ptr2->second.teid_outgoing, ptr2->second.seqNum,ptr2->second.npduNum );
// copy to release the mutex
gtpv1u_bearer_t tmp=ptr2->second;
pthread_mutex_unlock(&globGtp.gtp_lock);
@@ -431,23 +398,23 @@ static void gtpv1uSendDlDeliveryStatus(instance_t instance, gtpv1u_DU_buffer_rep
compatInst(instance), tmp.outgoing_ip_addr, tmp.outgoing_port, GTP_GPDU, tmp.teid_outgoing, NULL, 0, false, false, 0, 0, NR_RAN_CONTAINER, extensionHeader->buffer, extensionHeader->length);
}
static void gtpv1uEndTunnel(instance_t instance, gtpv1u_enb_tunnel_data_req_t *req) {
rnti_t rnti=req->rnti;
int rab_id=req->rab_id;
static void gtpv1uEndTunnel(instance_t instance, gtpv1u_tunnel_data_req_t *req) {
ue_id_t ue_id=req->ue_id;
int bearer_id=req->bearer_id;
pthread_mutex_lock(&globGtp.gtp_lock);
getInstRetVoid(compatInst(instance));
getRntiRetVoid(inst, rnti);
getUeRetVoid(inst, ue_id);
map<int, gtpv1u_bearer_t>::iterator ptr2=ptrRnti->second.bearers.find(rab_id);
auto ptr2=ptrUe->second.bearers.find(bearer_id);
if ( ptr2 == ptrRnti->second.bearers.end() ) {
LOG_E(GTPU,"[%ld] GTP-U sending a packet to a non existant RNTI:RAB: %x/%x\n", instance, rnti, rab_id);
if ( ptr2 == ptrUe->second.bearers.end() ) {
LOG_E(GTPU,"[%ld] GTP-U sending a packet to a non existant UE:RAB: %lx/%x\n", instance, ue_id, bearer_id);
pthread_mutex_unlock(&globGtp.gtp_lock);
return;
}
LOG_D(GTPU,"[%ld] sending a end packet packet to RNTI:RAB:teid %x/%x/%x\n",
instance, rnti, rab_id,ptr2->second.teid_outgoing);
LOG_D(GTPU,"[%ld] sending a end packet packet to UE:RAB:teid %lx/%x/%x\n",
instance, ue_id, bearer_id,ptr2->second.teid_outgoing);
gtpv1u_bearer_t tmp=ptr2->second;
pthread_mutex_unlock(&globGtp.gtp_lock);
Gtpv1uMsgHeaderT msgHdr;
@@ -579,15 +546,15 @@ instance_t gtpv1Init(openAddr_t context) {
return id;
}
void GtpuUpdateTunnelOutgoingTeid(instance_t instance, rnti_t rnti, ebi_t bearer_id, teid_t newOutgoingTeid) {
void GtpuUpdateTunnelOutgoingTeid(instance_t instance, ue_id_t ue_id, ebi_t bearer_id, teid_t newOutgoingTeid) {
pthread_mutex_lock(&globGtp.gtp_lock);
getInstRetVoid(compatInst(instance));
getRntiRetVoid(inst, rnti);
getUeRetVoid(inst, ue_id);
map<int, gtpv1u_bearer_t>::iterator ptr2=ptrRnti->second.bearers.find(bearer_id);
auto ptr2=ptrUe->second.bearers.find(bearer_id);
if ( ptr2 == ptrRnti->second.bearers.end() ) {
LOG_E(GTPU,"[%ld] Update tunnel for a existing rnti %x, but wrong bearer_id %u\n", instance, rnti, bearer_id);
if ( ptr2 == ptrUe->second.bearers.end() ) {
LOG_E(GTPU,"[%ld] Update tunnel for a existing ue id %lu, but wrong bearer_id %u\n", instance, ue_id, bearer_id);
pthread_mutex_unlock(&globGtp.gtp_lock);
return;
}
@@ -599,7 +566,7 @@ void GtpuUpdateTunnelOutgoingTeid(instance_t instance, rnti_t rnti, ebi_t bearer
}
teid_t newGtpuCreateTunnel(instance_t instance,
rnti_t rnti,
ue_id_t ue_id,
int incoming_bearer_id,
int outgoing_bearer_id,
teid_t outgoing_teid,
@@ -610,10 +577,10 @@ teid_t newGtpuCreateTunnel(instance_t instance,
gtpCallbackSDAP callBackSDAP) {
pthread_mutex_lock(&globGtp.gtp_lock);
getInstRetInt(compatInst(instance));
auto it=inst->ue2te_mapping.find(rnti);
auto it=inst->ue2te_mapping.find(ue_id);
if ( it != inst->ue2te_mapping.end() && it->second.bearers.find(outgoing_bearer_id) != it->second.bearers.end()) {
LOG_W(GTPU,"[%ld] Create a config for a already existing GTP tunnel (rnti %x)\n", instance, rnti);
LOG_W(GTPU,"[%ld] Create a config for a already existing GTP tunnel (ue id %lu)\n", instance, ue_id);
inst->ue2te_mapping.erase(it);
}
@@ -624,7 +591,7 @@ teid_t newGtpuCreateTunnel(instance_t instance,
incoming_teid=gtpv1uNewTeid();
};
inst->te2ue_mapping[incoming_teid].rnti=rnti;
inst->te2ue_mapping[incoming_teid].ue_id=ue_id;
inst->te2ue_mapping[incoming_teid].incoming_rb_id= incoming_bearer_id;
@@ -636,7 +603,7 @@ teid_t newGtpuCreateTunnel(instance_t instance,
inst->te2ue_mapping[incoming_teid].pdusession_id = (uint8_t)outgoing_bearer_id;
gtpv1u_bearer_t *tmp=&inst->ue2te_mapping[rnti].bearers[outgoing_bearer_id];
gtpv1u_bearer_t *tmp=&inst->ue2te_mapping[ue_id].bearers[outgoing_bearer_id];
int addrs_length_in_bytes = remoteAddr.length / 8;
@@ -652,7 +619,7 @@ teid_t newGtpuCreateTunnel(instance_t instance,
case 20:
memcpy(&tmp->outgoing_ip_addr,remoteAddr.buffer,4);
memcpy(&tmp->outgoing_ip6_addr.s6_addr,
memcpy(tmp->outgoing_ip6_addr.s6_addr,
remoteAddr.buffer+4,
16);
@@ -667,9 +634,9 @@ teid_t newGtpuCreateTunnel(instance_t instance,
pthread_mutex_unlock(&globGtp.gtp_lock);
char ip4[INET_ADDRSTRLEN];
char ip6[INET6_ADDRSTRLEN];
LOG_I(GTPU, "[%ld] Created tunnel for RNTI %x, teid for DL: %x, teid for UL %x to remote IPv4: %s, IPv6 %s\n",
LOG_I(GTPU, "[%ld] Created tunnel for UE ID %lu, teid for DL: %x, teid for UL %x to remote IPv4: %s, IPv6 %s\n",
instance,
rnti,
ue_id,
tmp->teid_incoming,
tmp->teid_outgoing,
inet_ntop(AF_INET,(void *)&tmp->outgoing_ip_addr, ip4,INET_ADDRSTRLEN ),
@@ -680,7 +647,7 @@ teid_t newGtpuCreateTunnel(instance_t instance,
int gtpv1u_create_s1u_tunnel(instance_t instance,
const gtpv1u_enb_create_tunnel_req_t *create_tunnel_req,
gtpv1u_enb_create_tunnel_resp_t *create_tunnel_resp) {
LOG_D(GTPU, "[%ld] Start create tunnels for RNTI %x, num_tunnels %d, sgw_S1u_teid %x\n",
LOG_D(GTPU, "[%ld] Start create tunnels for UE ID %u, num_tunnels %d, sgw_S1u_teid %x\n",
instance,
create_tunnel_req->rnti,
create_tunnel_req->num_tunnels,
@@ -722,7 +689,7 @@ int gtpv1u_create_s1u_tunnel(instance_t instance,
int gtpv1u_update_s1u_tunnel(
const instance_t instance,
const gtpv1u_enb_create_tunnel_req_t *const create_tunnel_req,
const gtpv1u_enb_create_tunnel_req_t *const create_tunnel_req,
const rnti_t prior_rnti
) {
LOG_D(GTPU, "[%ld] Start update tunnels for old RNTI %x, new RNTI %x, num_tunnels %d, sgw_S1u_teid %x, eps_bearer_id %x\n",
@@ -743,7 +710,7 @@ int gtpv1u_update_s1u_tunnel(
auto it=inst->ue2te_mapping.find(prior_rnti);
if ( it != inst->ue2te_mapping.end() ) {
LOG_W(GTPU,"[%ld] Update a not existing tunnel, start create the new one (new rnti %x, old rnti %x)\n", instance, create_tunnel_req->rnti, prior_rnti);
LOG_W(GTPU,"[%ld] Update a not existing tunnel, start create the new one (new ue id %u, old ue id %u)\n", instance, create_tunnel_req->rnti, prior_rnti);
pthread_mutex_unlock(&globGtp.gtp_lock);
gtpv1u_enb_create_tunnel_resp_t tmp;
(void)gtpv1u_create_s1u_tunnel(instance, create_tunnel_req, &tmp);
@@ -759,9 +726,9 @@ int gtpv1u_update_s1u_tunnel(
int gtpv1u_create_ngu_tunnel( const instance_t instance,
const gtpv1u_gnb_create_tunnel_req_t *const create_tunnel_req,
gtpv1u_gnb_create_tunnel_resp_t *const create_tunnel_resp) {
LOG_D(GTPU, "[%ld] Start create tunnels for RNTI %x, num_tunnels %d, sgw_S1u_teid %x\n",
LOG_D(GTPU, "[%ld] Start create tunnels for ue id %lu, num_tunnels %d, sgw_S1u_teid %x\n",
instance,
create_tunnel_req->rnti,
create_tunnel_req->ue_id,
create_tunnel_req->num_tunnels,
create_tunnel_req->outgoing_teid[0]);
pthread_mutex_lock(&globGtp.gtp_lock);
@@ -773,7 +740,7 @@ int gtpv1u_create_ngu_tunnel( const instance_t instance,
pthread_mutex_unlock(&globGtp.gtp_lock);
for (int i = 0; i < create_tunnel_req->num_tunnels; i++) {
teid_t teid = newGtpuCreateTunnel(instance,
create_tunnel_req->rnti,
create_tunnel_req->ue_id,
create_tunnel_req->incoming_rb_id[i],
create_tunnel_req->pdusession_id[i],
create_tunnel_req->outgoing_teid[i],
@@ -783,7 +750,7 @@ int gtpv1u_create_ngu_tunnel( const instance_t instance,
pdcp_data_req,
sdap_data_req);
create_tunnel_resp->status=0;
create_tunnel_resp->rnti=create_tunnel_req->rnti;
create_tunnel_resp->ue_id=create_tunnel_req->ue_id;
create_tunnel_resp->num_tunnels=create_tunnel_req->num_tunnels;
create_tunnel_resp->gnb_NGu_teid[i]=teid;
memcpy(create_tunnel_resp->gnb_addr.buffer,addr,sizeof(addr));
@@ -796,7 +763,7 @@ int gtpv1u_create_ngu_tunnel( const instance_t instance,
int gtpv1u_update_ngu_tunnel(
const instance_t instanceP,
const gtpv1u_gnb_create_tunnel_req_t *const create_tunnel_req_pP,
const rnti_t prior_rnti
const ue_id_t prior_ueid
) {
AssertFatal( false, "to be developped\n");
return GTPNOK;
@@ -809,60 +776,60 @@ int gtpv1u_create_x2u_tunnel(
AssertFatal( false, "to be developped\n");
}
int newGtpuDeleteAllTunnels(instance_t instance, rnti_t rnti) {
LOG_D(GTPU, "[%ld] Start delete tunnels for RNTI %x\n",
instance, rnti);
int newGtpuDeleteAllTunnels(instance_t instance, ue_id_t ue_id) {
LOG_D(GTPU, "[%ld] Start delete tunnels for ue id %lu\n",
instance, ue_id);
pthread_mutex_lock(&globGtp.gtp_lock);
getInstRetInt(compatInst(instance));
getRntiRetInt(inst, rnti);
getUeRetInt(inst, ue_id);
int nb=0;
for (auto j=ptrRnti->second.bearers.begin();
j!=ptrRnti->second.bearers.end();
for (auto j=ptrUe->second.bearers.begin();
j!=ptrUe->second.bearers.end();
++j) {
inst->te2ue_mapping.erase(j->second.teid_incoming);
nb++;
}
inst->ue2te_mapping.erase(ptrRnti);
inst->ue2te_mapping.erase(ptrUe);
pthread_mutex_unlock(&globGtp.gtp_lock);
LOG_I(GTPU, "[%ld] Deleted all tunnels for RNTI %x (%d tunnels deleted)\n", instance, rnti, nb);
LOG_I(GTPU, "[%ld] Deleted all tunnels for ue id %ld (%d tunnels deleted)\n", instance, ue_id, nb);
return !GTPNOK;
}
// Legacy delete tunnel finish by deleting all the rnti
// Legacy delete tunnel finish by deleting all the ue id
// so the list of bearer provided is only a design bug
int gtpv1u_delete_s1u_tunnel( const instance_t instance,
const gtpv1u_enb_delete_tunnel_req_t *const req_pP) {
return newGtpuDeleteAllTunnels(instance, req_pP->rnti);
}
int newGtpuDeleteTunnels(instance_t instance, rnti_t rnti, int nbTunnels, pdusessionid_t *pdusession_id) {
LOG_D(GTPU, "[%ld] Start delete tunnels for RNTI %x\n",
instance, rnti);
int newGtpuDeleteTunnels(instance_t instance, ue_id_t ue_id, int nbTunnels, pdusessionid_t *pdusession_id) {
LOG_D(GTPU, "[%ld] Start delete tunnels for ue id %lu\n",
instance, ue_id);
pthread_mutex_lock(&globGtp.gtp_lock);
getInstRetInt(compatInst(instance));
getRntiRetInt(inst, rnti);
getUeRetInt(inst, ue_id);
int nb=0;
for (int i=0; i<nbTunnels; i++) {
auto ptr2=ptrRnti->second.bearers.find(pdusession_id[i]);
auto ptr2=ptrUe->second.bearers.find(pdusession_id[i]);
if ( ptr2 == ptrRnti->second.bearers.end() ) {
LOG_E(GTPU,"[%ld] GTP-U instance: delete of not existing tunnel RNTI:RAB: %x/%x\n", instance, rnti,pdusession_id[i]);
if ( ptr2 == ptrUe->second.bearers.end() ) {
LOG_E(GTPU,"[%ld] GTP-U instance: delete of not existing tunnel UE ID:RAB: %ld/%x\n", instance, ue_id, pdusession_id[i]);
} else {
inst->te2ue_mapping.erase(ptr2->second.teid_incoming);
nb++;
}
}
if (ptrRnti->second.bearers.size() == 0 )
// no tunnels on this rnti, erase the ue entry
inst->ue2te_mapping.erase(ptrRnti);
if (ptrUe->second.bearers.size() == 0 )
// no tunnels on this ue id, erase the ue entry
inst->ue2te_mapping.erase(ptrUe);
pthread_mutex_unlock(&globGtp.gtp_lock);
LOG_I(GTPU, "[%ld] Deleted all tunnels for RNTI %x (%d tunnels deleted)\n", instance, rnti, nb);
LOG_I(GTPU, "[%ld] Deleted all tunnels for ue id %lu (%d tunnels deleted)\n", instance, ue_id, nb);
return !GTPNOK;
}
@@ -874,7 +841,7 @@ int gtpv1u_delete_x2u_tunnel( const instance_t instanceP,
int gtpv1u_delete_ngu_tunnel( const instance_t instance,
gtpv1u_gnb_delete_tunnel_req_t *req) {
return newGtpuDeleteTunnels(instance, req->rnti, req->num_pdusession, req->pdusession_id);
return newGtpuDeleteTunnels(instance, req->ue_id, req->num_pdusession, req->pdusession_id);
}
static int Gtpv1uHandleEchoReq(int h,
@@ -954,7 +921,7 @@ static int Gtpv1uHandleEndMarker(int h,
ctxt.module_id = 0;
ctxt.enb_flag = 1;
ctxt.instance = inst->addr.originInstance;
ctxt.rnti = tunnel->second.rnti;
ctxt.rnti = tunnel->second.ue_id;
ctxt.frame = 0;
ctxt.subframe = 0;
ctxt.eNB_index = 0;
@@ -1087,7 +1054,7 @@ static int Gtpv1uHandleGpdu(int h,
ctxt.module_id = 0;
ctxt.enb_flag = 1;
ctxt.instance = inst->addr.originInstance;
ctxt.rnti = tunnel->second.rnti;
ctxt.rnti = tunnel->second.ue_id;
ctxt.frame = 0;
ctxt.subframe = 0;
ctxt.eNB_index = 0;
@@ -1105,11 +1072,33 @@ static int Gtpv1uHandleGpdu(int h,
if (sdu_buffer_size > 0) {
if (qfi != -1 && tunnel->second.callBackSDAP) {
if (!tunnel->second.callBackSDAP(&ctxt, srb_flag, rb_id, mui, confirm, sdu_buffer_size, sdu_buffer, mode, &sourceL2Id, &destinationL2Id, qfi, rqi, tunnel->second.pdusession_id))
LOG_E(GTPU, "[%d] down layer refused incoming packet\n", h);
if ( !tunnel->second.callBackSDAP(&ctxt,
tunnel->second.ue_id,
srb_flag,
rb_id,
mui,
confirm,
sdu_buffer_size,
sdu_buffer,
mode,
&sourceL2Id,
&destinationL2Id,
qfi,
rqi,
tunnel->second.pdusession_id) )
LOG_E(GTPU,"[%d] down layer refused incoming packet\n", h);
} else {
if (!tunnel->second.callBack(&ctxt, srb_flag, rb_id, mui, confirm, sdu_buffer_size, sdu_buffer, mode, &sourceL2Id, &destinationL2Id))
LOG_E(GTPU, "[%d] down layer refused incoming packet\n", h);
if ( !tunnel->second.callBack(&ctxt,
srb_flag,
rb_id,
mui,
confirm,
sdu_buffer_size,
sdu_buffer,
mode,
&sourceL2Id,
&destinationL2Id) )
LOG_E(GTPU,"[%d] down layer refused incoming packet\n", h);
}
}
@@ -1231,16 +1220,10 @@ void *gtpv1uTask(void *args) {
switch (ITTI_MSG_ID(message_p)) {
// DATA TO BE SENT TO UDP
case GTPV1U_ENB_TUNNEL_DATA_REQ: {
gtpv1uSend(compatInst(ITTI_MSG_DESTINATION_INSTANCE(message_p)),
&GTPV1U_ENB_TUNNEL_DATA_REQ(message_p), false, false);
itti_free(TASK_GTPV1_U, GTPV1U_ENB_TUNNEL_DATA_REQ(message_p).buffer);
}
break;
case GTPV1U_GNB_TUNNEL_DATA_REQ: {
gtpv1uSend2(compatInst(ITTI_MSG_DESTINATION_INSTANCE(message_p)),
&GTPV1U_GNB_TUNNEL_DATA_REQ(message_p), false, false);
case GTPV1U_TUNNEL_DATA_REQ: {
gtpv1uSend(compatInst(ITTI_MSG_DESTINATION_INSTANCE(message_p)),
&GTPV1U_TUNNEL_DATA_REQ(message_p), false, false);
}
break;
@@ -1259,8 +1242,8 @@ void *gtpv1uTask(void *args) {
case GTPV1U_ENB_END_MARKER_REQ:
gtpv1uEndTunnel(compatInst(ITTI_MSG_DESTINATION_INSTANCE(message_p)),
&GTPV1U_ENB_TUNNEL_DATA_REQ(message_p));
itti_free(TASK_GTPV1_U, GTPV1U_ENB_TUNNEL_DATA_REQ(message_p).buffer);
&GTPV1U_TUNNEL_DATA_REQ(message_p));
itti_free(TASK_GTPV1_U, GTPV1U_TUNNEL_DATA_REQ(message_p).buffer);
break;
case GTPV1U_ENB_DATA_FORWARDING_REQ:
+133 -66
View File
@@ -8,80 +8,147 @@
extern "C" {
#endif
typedef bool (*gtpCallback)(protocol_ctxt_t *ctxt_pP,
const srb_flag_t srb_flagP,
const rb_id_t rb_idP,
const mui_t muiP,
const confirm_t confirmP,
const sdu_size_t sdu_buffer_sizeP,
unsigned char *const sdu_buffer_pP,
const pdcp_transmission_mode_t modeP,
const uint32_t *sourceL2Id,
const uint32_t *destinationL2Id);
typedef bool (*gtpCallback)(protocol_ctxt_t *ctxt_pP,
const srb_flag_t srb_flagP,
const rb_id_t rb_idP,
const mui_t muiP,
const confirm_t confirmP,
const sdu_size_t sdu_buffer_sizeP,
unsigned char *const sdu_buffer_pP,
const pdcp_transmission_mode_t modeP,
const uint32_t *sourceL2Id,
const uint32_t *destinationL2Id);
typedef bool (*gtpCallbackSDAP)(protocol_ctxt_t *ctxt_pP,
const srb_flag_t srb_flagP,
const rb_id_t rb_idP,
const mui_t muiP,
const confirm_t confirmP,
const sdu_size_t sdu_buffer_sizeP,
unsigned char *const sdu_buffer_pP,
const pdcp_transmission_mode_t modeP,
const uint32_t *sourceL2Id,
const uint32_t *destinationL2Id,
const uint8_t qfi,
const bool rqi,
const int pdusession_id);
typedef bool (*gtpCallbackSDAP)(protocol_ctxt_t *ctxt_pP,
const ue_id_t ue_id,
const srb_flag_t srb_flagP,
const rb_id_t rb_idP,
const mui_t muiP,
const confirm_t confirmP,
const sdu_size_t sdu_buffer_sizeP,
unsigned char *const sdu_buffer_pP,
const pdcp_transmission_mode_t modeP,
const uint32_t *sourceL2Id,
const uint32_t *destinationL2Id,
const uint8_t qfi,
const bool rqi,
const int pdusession_id);
typedef struct openAddr_s {
char originHost[HOST_NAME_MAX];
char originService[HOST_NAME_MAX];
char destinationHost[HOST_NAME_MAX];
char destinationService[HOST_NAME_MAX];
instance_t originInstance;
} openAddr_t;
typedef struct openAddr_s {
char originHost[HOST_NAME_MAX];
char originService[HOST_NAME_MAX];
char destinationHost[HOST_NAME_MAX];
char destinationService[HOST_NAME_MAX];
instance_t originInstance;
} openAddr_t;
typedef struct extensionHeader_s{
uint8_t buffer[500];
uint8_t length;
}extensionHeader_t;
typedef struct extensionHeader_s{
uint8_t buffer[500];
uint8_t length;
}extensionHeader_t;
// the init function create a gtp instance and return the gtp instance id
// the parameter originInstance will be sent back in each message from gtp to the creator
void gtpv1uReceiver(int h);
void gtpv1uProcessTimeout(int handle,void *arg);
int gtpv1u_create_s1u_tunnel(const instance_t instance, const gtpv1u_enb_create_tunnel_req_t *create_tunnel_req,
gtpv1u_enb_create_tunnel_resp_t *create_tunnel_resp);
int gtpv1u_update_s1u_tunnel(const instance_t instanceP,
const gtpv1u_enb_create_tunnel_req_t *create_tunnel_req_pP,
const rnti_t prior_rnti
);
int gtpv1u_delete_s1u_tunnel( const instance_t instance, const gtpv1u_enb_delete_tunnel_req_t *const req_pP);
int gtpv1u_delete_s1u_tunnel( const instance_t instance, const gtpv1u_enb_delete_tunnel_req_t *const req_pP);
// the init function create a gtp instance and return the gtp instance id
// the parameter originInstance will be sent back in each message from gtp to the creator
void gtpv1uReceiver(int h);
void gtpv1uProcessTimeout(int handle,void *arg);
int gtpv1u_create_s1u_tunnel(const instance_t instance, const gtpv1u_enb_create_tunnel_req_t *create_tunnel_req,
gtpv1u_enb_create_tunnel_resp_t *create_tunnel_resp);
int gtpv1u_update_s1u_tunnel(const instance_t instanceP,
const gtpv1u_enb_create_tunnel_req_t *create_tunnel_req_pP,
const rnti_t prior_rnti
);
int gtpv1u_create_x2u_tunnel(
const instance_t instanceP,
const gtpv1u_enb_create_x2u_tunnel_req_t *const create_tunnel_req_pP,
gtpv1u_enb_create_x2u_tunnel_resp_t *const create_tunnel_resp_pP);
int gtpv1u_delete_s1u_tunnel( const instance_t instance, const gtpv1u_enb_delete_tunnel_req_t *const req_pP);
int gtpv1u_create_x2u_tunnel(const instance_t instanceP,
const gtpv1u_enb_create_x2u_tunnel_req_t *const create_tunnel_req_pP,
gtpv1u_enb_create_x2u_tunnel_resp_t *const create_tunnel_resp_pP);
// New API
teid_t newGtpuCreateTunnel(instance_t instance,
rnti_t rnti,
int incoming_bearer_id,
int outgoing_rb_id,
teid_t teid,
int outgoing_qfi,
transport_layer_addr_t remoteAddr,
int port,
gtpCallback callBack,
gtpCallbackSDAP callBackSDAP);
void GtpuUpdateTunnelOutgoingTeid(instance_t instance, rnti_t rnti, ebi_t bearer_id, teid_t newOutgoingTeid);
int newGtpuDeleteAllTunnels(instance_t instance, rnti_t rnti);
int newGtpuDeleteTunnels(instance_t instance, rnti_t rnti, int nbTunnels, pdusessionid_t *pdusession_id);
instance_t gtpv1Init(openAddr_t context);
void *gtpv1uTask(void *args);
int gtpv1u_delete_x2u_tunnel( const instance_t instanceP,
const gtpv1u_enb_delete_tunnel_req_t *const req_pP);
int
gtpv1u_create_ngu_tunnel(
const instance_t instanceP,
const gtpv1u_gnb_create_tunnel_req_t *const create_tunnel_req_pP,
gtpv1u_gnb_create_tunnel_resp_t *const create_tunnel_resp_pP);
int gtpv1u_delete_ngu_tunnel( const instance_t instance,
gtpv1u_gnb_delete_tunnel_req_t *req);
int gtpv1u_update_ngu_tunnel( const instance_t instanceP,
const gtpv1u_gnb_create_tunnel_req_t *const create_tunnel_req_pP,
const ue_id_t prior_rnti
);
// New API
teid_t newGtpuCreateTunnel(instance_t instance,
ue_id_t ue_id,
int incoming_bearer_id,
int outgoing_rb_id,
teid_t teid,
int outgoing_qfi,
transport_layer_addr_t remoteAddr,
int port,
gtpCallback callBack,
gtpCallbackSDAP callBackSDAP);
void GtpuUpdateTunnelOutgoingTeid(instance_t instance,
ue_id_t ue_id,
ebi_t bearer_id,
teid_t newOutgoingTeid);
int newGtpuDeleteAllTunnels(instance_t instance, ue_id_t ue_id);
int newGtpuDeleteTunnels(instance_t instance, ue_id_t ue_id, int nbTunnels, pdusessionid_t *pdusession_id);
instance_t gtpv1Init(openAddr_t context);
void *gtpv1uTask(void *args);
// Legacy to fix
typedef struct gtpv1u_data_s {
/* RB tree of UEs */
hash_table_t *ue_mapping;
} gtpv1u_data_t;
#define GTPV1U_BEARER_OFFSET 3
#define GTPV1U_MAX_BEARERS_ID (max_val_LTE_DRB_Identity - GTPV1U_BEARER_OFFSET)
typedef enum {
BEARER_DOWN = 0,
BEARER_IN_CONFIG,
BEARER_UP,
BEARER_DL_HANDOVER,
BEARER_UL_HANDOVER,
BEARER_MAX,
} bearer_state_t;
typedef struct fixMe_gtpv1u_bearer_s {
/* TEID used in dl and ul */
teid_t teid_eNB; ///< eNB TEID
uintptr_t teid_eNB_stack_session; ///< eNB TEID
teid_t teid_sgw; ///< Remote TEID
in_addr_t sgw_ip_addr;
struct in6_addr sgw_ip6_addr;
teid_t teid_teNB;
in_addr_t tenb_ip_addr; ///< target eNB ipv4
struct in6_addr tenb_ip6_addr; ///< target eNB ipv6
tcp_udp_port_t port;
//NwGtpv1uStackSessionHandleT stack_session;
bearer_state_t state;
} fixMe_gtpv1u_bearer_t;
typedef struct gtpv1u_ue_data_s {
/* UE identifier for oaisim stack */
rnti_t ue_id;
/* Unique identifier used between PDCP and GTP-U to distinguish UEs */
uint32_t instance_id;
int num_bearers;
/* Bearer related data.
* Note that the first LCID available for data is 3 and we fixed the maximum
* number of e-rab per UE to be (32 [id range]), max RB is 11. The real rb id will 3 + rab_id (3..32).
*/
fixMe_gtpv1u_bearer_t bearers[GTPV1U_MAX_BEARERS_ID];
//RB_ENTRY(gtpv1u_ue_data_s) gtpv1u_ue_node;
} gtpv1u_ue_data_t;
#ifdef __cplusplus
}
#endif
-113
View File
@@ -1,113 +0,0 @@
/*
* 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 gtpv1u_eNB_task.h
* \brief
* \author Lionel Gauthier
* \company Eurecom
* \email: lionel.gauthier@eurecom.fr
*/
#ifndef GTPV1U_ENB_TASK_H_
#define GTPV1U_ENB_TASK_H_
typedef struct gtpv1u_data_s {
/* RB tree of UEs */
hash_table_t *ue_mapping;
} gtpv1u_data_t;
#define GTPV1U_BEARER_OFFSET 3
#define GTPV1U_MAX_BEARERS_ID (max_val_LTE_DRB_Identity - GTPV1U_BEARER_OFFSET)
typedef enum {
BEARER_DOWN = 0,
BEARER_IN_CONFIG,
BEARER_UP,
BEARER_DL_HANDOVER,
BEARER_UL_HANDOVER,
BEARER_MAX,
} bearer_state_t;
typedef struct fixMe_gtpv1u_bearer_s {
/* TEID used in dl and ul */
teid_t teid_eNB; ///< eNB TEID
uintptr_t teid_eNB_stack_session; ///< eNB TEID
teid_t teid_sgw; ///< Remote TEID
in_addr_t sgw_ip_addr;
struct in6_addr sgw_ip6_addr;
teid_t teid_teNB;
in_addr_t tenb_ip_addr; ///< target eNB ipv4
struct in6_addr tenb_ip6_addr; ///< target eNB ipv6
tcp_udp_port_t port;
//NwGtpv1uStackSessionHandleT stack_session;
bearer_state_t state;
} fixMe_gtpv1u_bearer_t;
typedef struct gtpv1u_ue_data_s {
/* UE identifier for oaisim stack */
rnti_t ue_id;
/* Unique identifier used between PDCP and GTP-U to distinguish UEs */
uint32_t instance_id;
int num_bearers;
/* Bearer related data.
* Note that the first LCID available for data is 3 and we fixed the maximum
* number of e-rab per UE to be (32 [id range]), max RB is 11. The real rb id will 3 + rab_id (3..32).
*/
fixMe_gtpv1u_bearer_t bearers[GTPV1U_MAX_BEARERS_ID];
//RB_ENTRY(gtpv1u_ue_data_s) gtpv1u_ue_node;
} gtpv1u_ue_data_t;
/*
int
gtpv1u_new_data_req(
uint8_t enb_id,
uint8_t ue_id,
uint8_t rab_id,
uint8_t *buffer,
uint32_t buf_len,
uint32_t buf_offset);*/
int gtpv1u_eNB_init(void);
void *gtpv1u_eNB_process_itti_msg(void *);
void *gtpv1u_eNB_task(void *args);
int
gtpv1u_create_x2u_tunnel(
const instance_t instanceP,
const gtpv1u_enb_create_x2u_tunnel_req_t *const create_tunnel_req_pP,
gtpv1u_enb_create_x2u_tunnel_resp_t *const create_tunnel_resp_pP);
int
gtpv1u_create_s1u_tunnel(
const instance_t instanceP,
const gtpv1u_enb_create_tunnel_req_t *const create_tunnel_req_pP,
gtpv1u_enb_create_tunnel_resp_t *const create_tunnel_resp_pP);
int
gtpv1u_update_s1u_tunnel(
const instance_t instanceP,
const gtpv1u_enb_create_tunnel_req_t *const create_tunnel_req_pP,
const rnti_t prior_rnti);
int gtpv1u_delete_x2u_tunnel(
const instance_t instanceP,
const gtpv1u_enb_delete_tunnel_req_t *const req_pP);
#endif /* GTPV1U_ENB_TASK_H_ */
-54
View File
@@ -1,54 +0,0 @@
/* 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 gtpv1u_gNB_task.h
* \brief
* \author Lionel Gauthier Panos Matzakos
* \company Eurecom
* \email: lionel.gauthier@eurecom.fr
*/
#ifndef GTPV1U_GNB_TASK_H_
#define GTPV1U_GNB_TASK_H_
int gtpv1u_gNB_init(void);
void *gtpv1u_gNB_task(void *args);
void *nr_gtpv1u_gNB_task(void *args);
int
gtpv1u_create_ngu_tunnel(
const instance_t instanceP,
const gtpv1u_gnb_create_tunnel_req_t *const create_tunnel_req_pP,
gtpv1u_gnb_create_tunnel_resp_t *const create_tunnel_resp_pP);
int
gtpv1u_update_ngu_tunnel(
const instance_t instanceP,
const gtpv1u_gnb_create_tunnel_req_t *const create_tunnel_req_pP,
const rnti_t prior_rnti
);
int gtpv1u_delete_ngu_tunnel( const instance_t instance,
gtpv1u_gnb_delete_tunnel_req_t *req);
#endif /* GTPV1U_GNB_TASK_H_ */