mirror of
https://gitea.osmocom.org/cellular-infrastructure/osmo-upf.git
synced 2025-10-23 08:12:03 +00:00
move next_teid from up_endpoint to g_upf
up_endpoint is about the PFCP endpoint, handing out local TEID is about local GTP endpoints. Move the TEID allocation to g_upf / upf.c. An upcoming patch will use a hash table in g_upf to speed up lookup whether a local TEID is already in use; cosmetically prepare for that. Change-Id: I8eae5b53c563400ddfded264678d9cfb28b6f737
This commit is contained in:
@@ -39,11 +39,9 @@ struct up_endpoint {
|
||||
struct llist_head peers;
|
||||
|
||||
uint64_t next_seid_state;
|
||||
uint32_t next_teid_state;
|
||||
};
|
||||
|
||||
struct up_endpoint *up_endpoint_init(void *ctx, const struct osmo_sockaddr *local_addr);
|
||||
void up_endpoint_free(struct up_endpoint **ep);
|
||||
|
||||
uint64_t up_endpoint_next_seid(struct up_endpoint *ep);
|
||||
uint32_t up_endpoint_next_teid(struct up_endpoint *ep);
|
||||
|
@@ -115,6 +115,10 @@ struct g_upf {
|
||||
uint32_t next_chain_id_state;
|
||||
} tunmap;
|
||||
|
||||
struct {
|
||||
uint32_t next_local_teid_state;
|
||||
} gtp;
|
||||
|
||||
struct llist_head netinst;
|
||||
};
|
||||
|
||||
@@ -134,3 +138,5 @@ int upf_pfcp_listen();
|
||||
|
||||
int upf_gtp_devs_open();
|
||||
void upf_gtp_devs_close();
|
||||
|
||||
uint32_t upf_next_local_teid(void);
|
||||
|
@@ -271,17 +271,6 @@ static struct up_session *up_endpoint_find_session(struct up_endpoint *ep, uint6
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static struct up_session *up_endpoint_find_session_by_local_teid(struct up_endpoint *ep, uint32_t teid)
|
||||
{
|
||||
struct up_peer *peer;
|
||||
llist_for_each_entry(peer, &ep->peers, entry) {
|
||||
struct up_session *session = up_session_find_by_local_teid(peer, teid);
|
||||
if (session)
|
||||
return session;
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
uint64_t up_endpoint_next_seid(struct up_endpoint *ep)
|
||||
{
|
||||
uint64_t sanity;
|
||||
@@ -294,26 +283,6 @@ uint64_t up_endpoint_next_seid(struct up_endpoint *ep)
|
||||
return 0;
|
||||
}
|
||||
|
||||
static uint32_t up_endpoint_inc_teid(struct up_endpoint *ep)
|
||||
{
|
||||
ep->next_teid_state++;
|
||||
if (!ep->next_teid_state)
|
||||
ep->next_teid_state++;
|
||||
return ep->next_teid_state;
|
||||
}
|
||||
|
||||
uint32_t up_endpoint_next_teid(struct up_endpoint *ep)
|
||||
{
|
||||
uint32_t sanity;
|
||||
for (sanity = 2342; sanity; sanity--) {
|
||||
uint32_t next_teid = up_endpoint_inc_teid(ep);
|
||||
if (up_endpoint_find_session_by_local_teid(ep, next_teid))
|
||||
continue;
|
||||
return next_teid;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
void up_endpoint_free(struct up_endpoint **_ep)
|
||||
{
|
||||
struct up_peer *peer;
|
||||
|
@@ -185,7 +185,6 @@ static enum osmo_pfcp_cause up_session_choose_f_teid(struct up_session *session,
|
||||
bool choose_id_present, uint8_t choose_id,
|
||||
const char *netinst_name)
|
||||
{
|
||||
struct up_endpoint *up_ep = session->up_peer->up_endpoint;
|
||||
struct chosen_f_teid *chosen = NULL;
|
||||
|
||||
if (choose_id_present)
|
||||
@@ -206,7 +205,7 @@ static enum osmo_pfcp_cause up_session_choose_f_teid(struct up_session *session,
|
||||
return rc;
|
||||
|
||||
/* Choose a new TEID */
|
||||
dst->fixed.teid = up_endpoint_next_teid(up_ep);
|
||||
dst->fixed.teid = upf_next_local_teid();
|
||||
if (dst->fixed.teid == 0) {
|
||||
LOGPFSML(session->fi, LOGL_ERROR, "Failed to allocate an unused TEID\n");
|
||||
return OSMO_PFCP_CAUSE_PFCP_ENTITY_IN_CONGESTION;
|
||||
|
@@ -29,6 +29,8 @@
|
||||
|
||||
#include <osmocom/upf/upf.h>
|
||||
#include <osmocom/upf/up_endpoint.h>
|
||||
#include <osmocom/upf/up_peer.h>
|
||||
#include <osmocom/upf/up_session.h>
|
||||
#include <osmocom/upf/upf_gtp.h>
|
||||
|
||||
struct g_upf *g_upf = NULL;
|
||||
@@ -98,3 +100,34 @@ int upf_gtp_devs_open()
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
static bool upf_is_local_teid_in_use(uint32_t teid)
|
||||
{
|
||||
struct up_peer *peer;
|
||||
llist_for_each_entry(peer, &g_upf->pfcp.ep->peers, entry) {
|
||||
struct up_session *session = up_session_find_by_local_teid(peer, teid);
|
||||
if (session)
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
static uint32_t upf_next_local_teid_inc(void)
|
||||
{
|
||||
g_upf->gtp.next_local_teid_state++;
|
||||
if (!g_upf->gtp.next_local_teid_state)
|
||||
g_upf->gtp.next_local_teid_state++;
|
||||
return g_upf->gtp.next_local_teid_state;
|
||||
}
|
||||
|
||||
uint32_t upf_next_local_teid(void)
|
||||
{
|
||||
uint32_t sanity;
|
||||
for (sanity = 2342; sanity; sanity--) {
|
||||
uint32_t next_teid = upf_next_local_teid_inc();
|
||||
if (upf_is_local_teid_in_use(next_teid))
|
||||
continue;
|
||||
return next_teid;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
Reference in New Issue
Block a user