mirror of
https://github.com/open5gs/open5gs.git
synced 2026-05-05 23:37:22 +00:00
fix indentation in PGW
This commit is contained in:
parent
7e08f7fc45
commit
27d5208ea3
9 changed files with 322 additions and 228 deletions
|
|
@ -1,3 +1,22 @@
|
|||
/*
|
||||
* Copyright (C) 2019 by Sukchan Lee <acetcom@gmail.com>
|
||||
*
|
||||
* This file is part of Open5GS.
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include "pgw-event.h"
|
||||
#include "pgw-context.h"
|
||||
|
||||
|
|
@ -77,20 +96,19 @@ const char* pgw_event_get_name(pgw_event_t *e)
|
|||
if (e == NULL)
|
||||
return OGS_FSM_NAME_INIT_SIG;
|
||||
|
||||
switch (e->id)
|
||||
{
|
||||
case OGS_FSM_ENTRY_SIG:
|
||||
return OGS_FSM_NAME_ENTRY_SIG;
|
||||
case OGS_FSM_EXIT_SIG:
|
||||
return OGS_FSM_NAME_EXIT_SIG;
|
||||
switch (e->id) {
|
||||
case OGS_FSM_ENTRY_SIG:
|
||||
return OGS_FSM_NAME_ENTRY_SIG;
|
||||
case OGS_FSM_EXIT_SIG:
|
||||
return OGS_FSM_NAME_EXIT_SIG;
|
||||
|
||||
case PGW_EVT_S5C_MESSAGE:
|
||||
return "PGW_EVT_S5C_MESSAGE";
|
||||
case PGW_EVT_GX_MESSAGE:
|
||||
return "PGW_EVT_GX_SESSION_MSG";
|
||||
case PGW_EVT_S5C_MESSAGE:
|
||||
return "PGW_EVT_S5C_MESSAGE";
|
||||
case PGW_EVT_GX_MESSAGE:
|
||||
return "PGW_EVT_GX_SESSION_MSG";
|
||||
|
||||
default:
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
return "UNKNOWN_EVENT";
|
||||
|
|
|
|||
|
|
@ -1,11 +1,30 @@
|
|||
#ifndef __PGW_EVENT_H__
|
||||
#define __PGW_EVENT_H__
|
||||
/*
|
||||
* Copyright (C) 2019 by Sukchan Lee <acetcom@gmail.com>
|
||||
*
|
||||
* This file is part of Open5GS.
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef PGW_EVENT_H
|
||||
#define PGW_EVENT_H
|
||||
|
||||
#include "ogs-core.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif /* __cplusplus */
|
||||
#endif
|
||||
|
||||
typedef enum {
|
||||
PGW_EVT_BASE = OGS_FSM_USER_SIG,
|
||||
|
|
@ -36,6 +55,6 @@ const char *pgw_event_get_name(pgw_event_t *e);
|
|||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif /* __cplusplus */
|
||||
#endif
|
||||
|
||||
#endif /* __PGW_EVENT_H__ */
|
||||
#endif /* PGW_EVENT_H */
|
||||
|
|
|
|||
|
|
@ -1,11 +1,30 @@
|
|||
#ifndef __PGW_FD_PATH_H__
|
||||
#define __PGW_FD_PATH_H__
|
||||
/*
|
||||
* Copyright (C) 2019 by Sukchan Lee <acetcom@gmail.com>
|
||||
*
|
||||
* This file is part of Open5GS.
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef PGW_FD_PATH_H
|
||||
#define PGW_FD_PATH_H
|
||||
|
||||
#include "pgw-context.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif /* __cplusplus */
|
||||
#endif
|
||||
|
||||
typedef struct gtp_xact_s gtp_xact_t;
|
||||
|
||||
|
|
@ -17,7 +36,7 @@ void pgw_gx_send_ccr(pgw_sess_t *sess, gtp_xact_t *xact,
|
|||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif /* __cplusplus */
|
||||
#endif
|
||||
|
||||
#endif /* __PGW_FD_PATH_H__ */
|
||||
#endif /* PGW_FD_PATH_H */
|
||||
|
||||
|
|
|
|||
|
|
@ -25,7 +25,7 @@
|
|||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif /* __cplusplus */
|
||||
#endif
|
||||
|
||||
int pgw_gtp_open();
|
||||
void pgw_gtp_close();
|
||||
|
|
|
|||
|
|
@ -1,3 +1,22 @@
|
|||
/*
|
||||
* Copyright (C) 2019 by Sukchan Lee <acetcom@gmail.com>
|
||||
*
|
||||
* This file is part of Open5GS.
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include "pgw-context.h"
|
||||
#include "fd/gx/gx-message.h"
|
||||
#include "pgw-gtp-path.h"
|
||||
|
|
@ -94,8 +113,7 @@ static int bearer_binding(pgw_sess_t *sess, gx_message_t *gx_message)
|
|||
ogs_assert(sess);
|
||||
ogs_assert(gx_message);
|
||||
|
||||
for (i = 0; i < gx_message->num_of_pcc_rule; i++)
|
||||
{
|
||||
for (i = 0; i < gx_message->num_of_pcc_rule; i++) {
|
||||
gtp_xact_t *xact = NULL;
|
||||
gtp_header_t h;
|
||||
ogs_pkbuf_t *pkbuf = NULL;
|
||||
|
|
@ -107,21 +125,18 @@ static int bearer_binding(pgw_sess_t *sess, gx_message_t *gx_message)
|
|||
int tft_presence = 0;
|
||||
|
||||
ogs_assert(pcc_rule);
|
||||
if (pcc_rule->name == NULL)
|
||||
{
|
||||
if (pcc_rule->name == NULL) {
|
||||
ogs_error("No PCC Rule Name");
|
||||
continue;
|
||||
}
|
||||
|
||||
if (pcc_rule->type == PCC_RULE_TYPE_INSTALL)
|
||||
{
|
||||
if (pcc_rule->type == PCC_RULE_TYPE_INSTALL) {
|
||||
bearer = pgw_bearer_find_by_qci_arp(sess,
|
||||
pcc_rule->qos.qci,
|
||||
pcc_rule->qos.arp.priority_level,
|
||||
pcc_rule->qos.arp.pre_emption_capability,
|
||||
pcc_rule->qos.arp.pre_emption_vulnerability);
|
||||
if (!bearer)
|
||||
{
|
||||
if (!bearer) {
|
||||
bearer = pgw_bearer_add(sess);
|
||||
ogs_assert(bearer);
|
||||
|
||||
|
|
@ -132,13 +147,10 @@ static int bearer_binding(pgw_sess_t *sess, gx_message_t *gx_message)
|
|||
ogs_assert(pcc_rule->num_of_flow);
|
||||
|
||||
bearer_created = 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
} else {
|
||||
ogs_assert(strcmp(bearer->name, pcc_rule->name) == 0);
|
||||
|
||||
if (pcc_rule->num_of_flow)
|
||||
{
|
||||
if (pcc_rule->num_of_flow) {
|
||||
/* Remove all previous flow */
|
||||
pgw_pf_remove_all(bearer);
|
||||
|
||||
|
|
@ -153,8 +165,7 @@ static int bearer_binding(pgw_sess_t *sess, gx_message_t *gx_message)
|
|||
(pcc_rule->qos.gbr.downlink &&
|
||||
bearer->qos.gbr.downlink != pcc_rule->qos.gbr.downlink) ||
|
||||
(pcc_rule->qos.gbr.uplink &&
|
||||
bearer->qos.gbr.uplink != pcc_rule->qos.gbr.uplink))
|
||||
{
|
||||
bearer->qos.gbr.uplink != pcc_rule->qos.gbr.uplink)) {
|
||||
/* Update QoS parameter */
|
||||
memcpy(&bearer->qos, &pcc_rule->qos, sizeof(qos_t));
|
||||
|
||||
|
|
@ -162,16 +173,14 @@ static int bearer_binding(pgw_sess_t *sess, gx_message_t *gx_message)
|
|||
qos_presence = 1;
|
||||
}
|
||||
|
||||
if (tft_presence == 0 && qos_presence == 0)
|
||||
{
|
||||
if (tft_presence == 0 && qos_presence == 0) {
|
||||
ogs_warn("[IGNORE] Update Bearer Request : "
|
||||
"Both QoS and TFT is NULL");
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
for (j = 0; j < pcc_rule->num_of_flow; j++)
|
||||
{
|
||||
for (j = 0; j < pcc_rule->num_of_flow; j++) {
|
||||
flow_t *flow = &pcc_rule->flow[j];
|
||||
pgw_rule_t rule;
|
||||
pgw_pf_t *pf = NULL;
|
||||
|
|
@ -191,16 +200,13 @@ static int bearer_binding(pgw_sess_t *sess, gx_message_t *gx_message)
|
|||
|
||||
memset(&h, 0, sizeof(gtp_header_t));
|
||||
|
||||
if (bearer_created == 1)
|
||||
{
|
||||
if (bearer_created == 1) {
|
||||
h.type = GTP_CREATE_BEARER_REQUEST_TYPE;
|
||||
h.teid = sess->sgw_s5c_teid;
|
||||
|
||||
rv = pgw_s5c_build_create_bearer_request(&pkbuf, h.type, bearer);
|
||||
ogs_assert(rv == OGS_OK);
|
||||
}
|
||||
else
|
||||
{
|
||||
} else {
|
||||
h.type = GTP_UPDATE_BEARER_REQUEST_TYPE;
|
||||
h.teid = sess->sgw_s5c_teid;
|
||||
|
||||
|
|
@ -214,9 +220,7 @@ static int bearer_binding(pgw_sess_t *sess, gx_message_t *gx_message)
|
|||
|
||||
rv = gtp_xact_commit(xact);
|
||||
ogs_assert(rv == OGS_OK);
|
||||
}
|
||||
else if (pcc_rule->type == PCC_RULE_TYPE_REMOVE)
|
||||
{
|
||||
} else if (pcc_rule->type == PCC_RULE_TYPE_REMOVE) {
|
||||
bearer = pgw_bearer_find_by_name(sess, pcc_rule->name);
|
||||
ogs_assert(bearer);
|
||||
|
||||
|
|
|
|||
|
|
@ -1,5 +1,24 @@
|
|||
#ifndef __PGW_GX_HANDLER_H__
|
||||
#define __PGW_GX_HANDLER_H__
|
||||
/*
|
||||
* Copyright (C) 2019 by Sukchan Lee <acetcom@gmail.com>
|
||||
*
|
||||
* This file is part of Open5GS.
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef PGW_GX_HANDLER_H
|
||||
#define PGW_GX_HANDLER_H
|
||||
|
||||
#include "gtp/gtp-message.h"
|
||||
|
||||
|
|
@ -7,7 +26,7 @@
|
|||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif /* __cplusplus */
|
||||
#endif
|
||||
|
||||
void pgw_gx_handle_cca_initial_request(
|
||||
pgw_sess_t *sess, gx_message_t *gx_message,
|
||||
|
|
@ -20,6 +39,6 @@ void pgw_gx_handle_re_auth_request(
|
|||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif /* __cplusplus */
|
||||
#endif
|
||||
|
||||
#endif /* __PGW_GX_HANDLER_H__ */
|
||||
#endif /* PGW_GX_HANDLER_H */
|
||||
|
|
|
|||
|
|
@ -1,3 +1,22 @@
|
|||
/*
|
||||
* Copyright (C) 2019 by Sukchan Lee <acetcom@gmail.com>
|
||||
*
|
||||
* This file is part of Open5GS.
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#include "gtp/gtp-xact.h"
|
||||
|
||||
#include "app/context.h"
|
||||
|
|
@ -67,15 +86,13 @@ static void pgw_main(void *data)
|
|||
ogs_fsm_create(&pgw_sm, pgw_state_initial, pgw_state_final);
|
||||
ogs_fsm_init(&pgw_sm, 0);
|
||||
|
||||
for ( ;; )
|
||||
{
|
||||
for ( ;; ) {
|
||||
ogs_pollset_poll(pgw_self()->pollset,
|
||||
ogs_timer_mgr_next(pgw_self()->timer_mgr));
|
||||
|
||||
ogs_timer_mgr_expire(pgw_self()->timer_mgr);
|
||||
|
||||
for ( ;; )
|
||||
{
|
||||
for ( ;; ) {
|
||||
pgw_event_t *e = NULL;
|
||||
|
||||
rv = ogs_queue_trypop(pgw_self()->queue, (void**)&e);
|
||||
|
|
|
|||
|
|
@ -1,3 +1,22 @@
|
|||
/*
|
||||
* Copyright (C) 2019 by Sukchan Lee <acetcom@gmail.com>
|
||||
*
|
||||
* This file is part of Open5GS.
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#define _DEFAULT_SOURCE 1
|
||||
#define _BSD_SOURCE 1
|
||||
|
||||
|
|
@ -44,14 +63,12 @@ int pgw_compile_packet_filter(pgw_rule_t *pgw_rule, char *description)
|
|||
av[0] = NULL;
|
||||
|
||||
/* ACTION */
|
||||
if (!description) {
|
||||
/* FIXME : OLD gcc generates uninitialized warning */
|
||||
if (!description) { /* FIXME : OLD gcc generates uninitialized warning */
|
||||
ogs_assert_if_reached();
|
||||
return OGS_ERROR;
|
||||
}
|
||||
token = strtok_r(description, " ", &saveptr);
|
||||
if (strcmp(token, "permit") != 0)
|
||||
{
|
||||
if (strcmp(token, "permit") != 0) {
|
||||
ogs_error("Not begins with reserved keyword : 'permit'");
|
||||
return OGS_ERROR;
|
||||
}
|
||||
|
|
@ -59,16 +76,14 @@ int pgw_compile_packet_filter(pgw_rule_t *pgw_rule, char *description)
|
|||
|
||||
/* Save DIRECTION */
|
||||
dir = token = strtok_r(NULL, " ", &saveptr);
|
||||
if (strcmp(token, "out") != 0)
|
||||
{
|
||||
if (strcmp(token, "out") != 0) {
|
||||
ogs_error("Not begins with reserved keyword : 'permit out'");
|
||||
return OGS_ERROR;
|
||||
}
|
||||
|
||||
/* ADDR */
|
||||
token = strtok_r(NULL, " ", &saveptr);
|
||||
while(token != NULL)
|
||||
{
|
||||
while (token != NULL) {
|
||||
av[i++] = token;
|
||||
token = strtok_r(NULL, " ", &saveptr);
|
||||
}
|
||||
|
|
@ -82,81 +97,68 @@ int pgw_compile_packet_filter(pgw_rule_t *pgw_rule, char *description)
|
|||
|
||||
memset(pgw_rule, 0, sizeof(pgw_rule_t));
|
||||
for (l = rule->act_ofs, cmd = rule->cmd;
|
||||
l > 0 ; l -= F_LEN(cmd) , cmd += F_LEN(cmd))
|
||||
{
|
||||
switch(cmd->opcode)
|
||||
{
|
||||
case O_PROTO:
|
||||
pgw_rule->proto = cmd->arg1;
|
||||
break;
|
||||
case O_IP_SRC:
|
||||
case O_IP_SRC_MASK:
|
||||
{
|
||||
uint32_t *a = ((ipfw_insn_u32 *)cmd)->d;
|
||||
pgw_rule->ipv4_local = 1;
|
||||
pgw_rule->ip.local.addr[0] = a[0];
|
||||
if (cmd->opcode == O_IP_SRC_MASK)
|
||||
pgw_rule->ip.local.mask[0] = a[1];
|
||||
else
|
||||
pgw_rule->ip.local.mask[0] = 0xffffffff;
|
||||
break;
|
||||
}
|
||||
case O_IP_DST:
|
||||
case O_IP_DST_MASK:
|
||||
{
|
||||
uint32_t *a = ((ipfw_insn_u32 *)cmd)->d;
|
||||
pgw_rule->ipv4_remote = 1;
|
||||
pgw_rule->ip.remote.addr[0] = a[0];
|
||||
if (cmd->opcode == O_IP_DST_MASK)
|
||||
pgw_rule->ip.remote.mask[0] = a[1];
|
||||
else
|
||||
pgw_rule->ip.remote.mask[0] = 0xffffffff;
|
||||
break;
|
||||
}
|
||||
case O_IP6_SRC:
|
||||
case O_IP6_SRC_MASK:
|
||||
{
|
||||
uint32_t *a = ((ipfw_insn_u32 *)cmd)->d;
|
||||
pgw_rule->ipv6_local = 1;
|
||||
memcpy(pgw_rule->ip.local.addr, a, IPV6_LEN);
|
||||
if (cmd->opcode == O_IP6_SRC_MASK)
|
||||
memcpy(pgw_rule->ip.local.mask, a+4, IPV6_LEN);
|
||||
else
|
||||
n2mask((struct in6_addr *)pgw_rule->ip.local.mask, 128);
|
||||
break;
|
||||
}
|
||||
case O_IP6_DST:
|
||||
case O_IP6_DST_MASK:
|
||||
{
|
||||
uint32_t *a = ((ipfw_insn_u32 *)cmd)->d;
|
||||
pgw_rule->ipv6_remote = 1;
|
||||
memcpy(pgw_rule->ip.remote.addr, a, IPV6_LEN);
|
||||
if (cmd->opcode == O_IP6_DST_MASK)
|
||||
memcpy(pgw_rule->ip.remote.mask, a+4, IPV6_LEN);
|
||||
else
|
||||
n2mask((struct in6_addr *)pgw_rule->ip.remote.mask, 128);
|
||||
break;
|
||||
}
|
||||
case O_IP_SRCPORT:
|
||||
{
|
||||
uint16_t *p = ((ipfw_insn_u16 *)cmd)->ports;
|
||||
pgw_rule->port.local.low = p[0];
|
||||
pgw_rule->port.local.high = p[1];
|
||||
break;
|
||||
}
|
||||
case O_IP_DSTPORT:
|
||||
{
|
||||
uint16_t *p = ((ipfw_insn_u16 *)cmd)->ports;
|
||||
pgw_rule->port.remote.low = p[0];
|
||||
pgw_rule->port.remote.high = p[1];
|
||||
break;
|
||||
}
|
||||
l > 0 ; l -= F_LEN(cmd) , cmd += F_LEN(cmd)) {
|
||||
uint32_t *a = NULL;
|
||||
uint16_t *p = NULL;
|
||||
switch (cmd->opcode) {
|
||||
case O_PROTO:
|
||||
pgw_rule->proto = cmd->arg1;
|
||||
break;
|
||||
case O_IP_SRC:
|
||||
case O_IP_SRC_MASK:
|
||||
a = ((ipfw_insn_u32 *)cmd)->d;
|
||||
pgw_rule->ipv4_local = 1;
|
||||
pgw_rule->ip.local.addr[0] = a[0];
|
||||
if (cmd->opcode == O_IP_SRC_MASK)
|
||||
pgw_rule->ip.local.mask[0] = a[1];
|
||||
else
|
||||
pgw_rule->ip.local.mask[0] = 0xffffffff;
|
||||
break;
|
||||
case O_IP_DST:
|
||||
case O_IP_DST_MASK:
|
||||
a = ((ipfw_insn_u32 *)cmd)->d;
|
||||
pgw_rule->ipv4_remote = 1;
|
||||
pgw_rule->ip.remote.addr[0] = a[0];
|
||||
if (cmd->opcode == O_IP_DST_MASK)
|
||||
pgw_rule->ip.remote.mask[0] = a[1];
|
||||
else
|
||||
pgw_rule->ip.remote.mask[0] = 0xffffffff;
|
||||
break;
|
||||
case O_IP6_SRC:
|
||||
case O_IP6_SRC_MASK:
|
||||
a = ((ipfw_insn_u32 *)cmd)->d;
|
||||
pgw_rule->ipv6_local = 1;
|
||||
memcpy(pgw_rule->ip.local.addr, a, IPV6_LEN);
|
||||
if (cmd->opcode == O_IP6_SRC_MASK)
|
||||
memcpy(pgw_rule->ip.local.mask, a+4, IPV6_LEN);
|
||||
else
|
||||
n2mask((struct in6_addr *)pgw_rule->ip.local.mask, 128);
|
||||
break;
|
||||
case O_IP6_DST:
|
||||
case O_IP6_DST_MASK:
|
||||
a = ((ipfw_insn_u32 *)cmd)->d;
|
||||
pgw_rule->ipv6_remote = 1;
|
||||
memcpy(pgw_rule->ip.remote.addr, a, IPV6_LEN);
|
||||
if (cmd->opcode == O_IP6_DST_MASK)
|
||||
memcpy(pgw_rule->ip.remote.mask, a+4, IPV6_LEN);
|
||||
else
|
||||
n2mask((struct in6_addr *)pgw_rule->ip.remote.mask, 128);
|
||||
break;
|
||||
case O_IP_SRCPORT:
|
||||
p = ((ipfw_insn_u16 *)cmd)->ports;
|
||||
pgw_rule->port.local.low = p[0];
|
||||
pgw_rule->port.local.high = p[1];
|
||||
break;
|
||||
case O_IP_DSTPORT:
|
||||
p = ((ipfw_insn_u16 *)cmd)->ports;
|
||||
pgw_rule->port.remote.low = p[0];
|
||||
pgw_rule->port.remote.high = p[1];
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
memset(&zero_rule, 0, sizeof(pgw_rule_t));
|
||||
if (memcmp(pgw_rule, &zero_rule, sizeof(pgw_rule_t)) == 0)
|
||||
{
|
||||
if (memcmp(pgw_rule, &zero_rule, sizeof(pgw_rule_t)) == 0) {
|
||||
ogs_error("Cannot find Flow-Description");
|
||||
return OGS_ERROR;
|
||||
}
|
||||
|
|
@ -180,8 +182,7 @@ static int decode_ipv6_header(
|
|||
endp = p + ntohs(ip6_h->ip6_plen);
|
||||
|
||||
jp = p + sizeof(struct ip6_hbh);
|
||||
while(p == endp) /* Jumbo Frame */
|
||||
{
|
||||
while (p == endp) { /* Jumbo Frame */
|
||||
uint32_t jp_len = 0;
|
||||
struct ip6_opt_jumbo *jumbo = NULL;
|
||||
|
||||
|
|
@ -190,44 +191,41 @@ static int decode_ipv6_header(
|
|||
jumbo = (struct ip6_opt_jumbo *)jp;
|
||||
memcpy(&jp_len, jumbo->ip6oj_jumbo_len, sizeof(jp_len));
|
||||
jp_len = ntohl(jp_len);
|
||||
switch(jumbo->ip6oj_type)
|
||||
{
|
||||
case IP6OPT_JUMBO:
|
||||
endp = p + jp_len;
|
||||
break;
|
||||
case 0:
|
||||
jp++;
|
||||
break;
|
||||
default:
|
||||
jp += (sizeof(struct ip6_opt) + jp_len);
|
||||
break;
|
||||
switch (jumbo->ip6oj_type) {
|
||||
case IP6OPT_JUMBO:
|
||||
endp = p + jp_len;
|
||||
break;
|
||||
case 0:
|
||||
jp++;
|
||||
break;
|
||||
default:
|
||||
jp += (sizeof(struct ip6_opt) + jp_len);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
while(p < endp)
|
||||
{
|
||||
while (p < endp) {
|
||||
struct ip6_ext *ext = (struct ip6_ext *)p;
|
||||
switch(nxt)
|
||||
{
|
||||
case IPPROTO_HOPOPTS:
|
||||
case IPPROTO_ROUTING:
|
||||
case IPPROTO_DSTOPTS:
|
||||
case 135: /* mobility */
|
||||
case 139: /* host identity, experimental */
|
||||
case 140: /* shim6 */
|
||||
case 253: /* testing, experimental */
|
||||
case 254: /* testing, experimental */
|
||||
p += ((ext->ip6e_len << 3) + 8);
|
||||
break;
|
||||
case IPPROTO_FRAGMENT:
|
||||
p += sizeof(struct ip6_frag);
|
||||
break;
|
||||
case IPPROTO_AH:
|
||||
p += ((ext->ip6e_len + 2) << 2);
|
||||
break;
|
||||
default: /* Upper Layer */
|
||||
done = 1;
|
||||
break;
|
||||
switch (nxt) {
|
||||
case IPPROTO_HOPOPTS:
|
||||
case IPPROTO_ROUTING:
|
||||
case IPPROTO_DSTOPTS:
|
||||
case 135: /* mobility */
|
||||
case 139: /* host identity, experimental */
|
||||
case 140: /* shim6 */
|
||||
case 253: /* testing, experimental */
|
||||
case 254: /* testing, experimental */
|
||||
p += ((ext->ip6e_len << 3) + 8);
|
||||
break;
|
||||
case IPPROTO_FRAGMENT:
|
||||
p += sizeof(struct ip6_frag);
|
||||
break;
|
||||
case IPPROTO_AH:
|
||||
p += ((ext->ip6e_len + 2) << 2);
|
||||
break;
|
||||
default: /* Upper Layer */
|
||||
done = 1;
|
||||
break;
|
||||
|
||||
}
|
||||
if (done)
|
||||
|
|
@ -258,8 +256,7 @@ pgw_bearer_t *pgw_bearer_find_by_packet(ogs_pkbuf_t *pkt)
|
|||
ogs_assert(pkt->len);
|
||||
|
||||
ip_h = (struct ip *)pkt->data;
|
||||
if (ip_h->ip_v == 4)
|
||||
{
|
||||
if (ip_h->ip_v == 4) {
|
||||
ip_h = (struct ip *)pkt->data;
|
||||
ip6_h = NULL;
|
||||
|
||||
|
|
@ -269,9 +266,7 @@ pgw_bearer_t *pgw_bearer_find_by_packet(ogs_pkbuf_t *pkt)
|
|||
src_addr = &ip_h->ip_src.s_addr;
|
||||
dst_addr = &ip_h->ip_dst.s_addr;
|
||||
addr_len = 4;
|
||||
}
|
||||
else if (ip_h->ip_v == 6)
|
||||
{
|
||||
} else if (ip_h->ip_v == 6) {
|
||||
ip_h = NULL;
|
||||
ip6_h = (struct ip6_hdr *)pkt->data;
|
||||
|
||||
|
|
@ -281,8 +276,7 @@ pgw_bearer_t *pgw_bearer_find_by_packet(ogs_pkbuf_t *pkt)
|
|||
dst_addr = (uint32_t *)ip6_h->ip6_dst.s6_addr;
|
||||
addr_len = 16;
|
||||
|
||||
}
|
||||
else
|
||||
} else
|
||||
ogs_error("Invalid IP version = %d", ip_h->ip_v);
|
||||
|
||||
ogs_debug("[PGW] PROTO:%d SRC:%08x %08x %08x %08x",
|
||||
|
|
@ -307,8 +301,7 @@ pgw_bearer_t *pgw_bearer_find_by_packet(ogs_pkbuf_t *pkt)
|
|||
INET6_NTOP(&sess->ipv6->addr, buf));
|
||||
|
||||
if ((sess->ipv4 && memcmp(dst_addr, sess->ipv4->addr, addr_len) == 0) ||
|
||||
(sess->ipv6 && memcmp(dst_addr, sess->ipv6->addr, addr_len) == 0))
|
||||
{
|
||||
(sess->ipv6 && memcmp(dst_addr, sess->ipv6->addr, addr_len) == 0)) {
|
||||
pgw_bearer_t *default_bearer = NULL;
|
||||
pgw_bearer_t *bearer = NULL;
|
||||
|
||||
|
|
@ -321,18 +314,15 @@ pgw_bearer_t *pgw_bearer_find_by_packet(ogs_pkbuf_t *pkt)
|
|||
|
||||
bearer = pgw_bearer_next(default_bearer);
|
||||
/* Find the bearer with matched */
|
||||
for (; bearer; bearer = pgw_bearer_next(bearer))
|
||||
{
|
||||
for (; bearer; bearer = pgw_bearer_next(bearer)) {
|
||||
pgw_pf_t *pf = NULL;
|
||||
|
||||
if (bearer->ebi == 0)
|
||||
{
|
||||
if (bearer->ebi == 0) {
|
||||
/* Create Bearer Response is not received */
|
||||
continue;
|
||||
}
|
||||
|
||||
for (pf = pgw_pf_first(bearer); pf; pf = pgw_pf_next(pf))
|
||||
{
|
||||
for (pf = pgw_pf_first(bearer); pf; pf = pgw_pf_next(pf)) {
|
||||
int k;
|
||||
uint32_t src_mask[4];
|
||||
uint32_t dst_mask[4];
|
||||
|
|
@ -362,13 +352,11 @@ pgw_bearer_t *pgw_bearer_find_by_packet(ogs_pkbuf_t *pkt)
|
|||
ntohl(pf->rule.ip.remote.mask[2]),
|
||||
ntohl(pf->rule.ip.remote.mask[3]));
|
||||
|
||||
if (pf->direction != 1)
|
||||
{
|
||||
if (pf->direction != 1) {
|
||||
continue;
|
||||
}
|
||||
|
||||
for (k = 0; k < 4; k++)
|
||||
{
|
||||
for (k = 0; k < 4; k++) {
|
||||
src_mask[k] = src_addr[k] & pf->rule.ip.local.mask[k];
|
||||
dst_mask[k] = dst_addr[k] & pf->rule.ip.remote.mask[k];
|
||||
}
|
||||
|
|
@ -376,19 +364,15 @@ pgw_bearer_t *pgw_bearer_find_by_packet(ogs_pkbuf_t *pkt)
|
|||
if (memcmp(src_mask, pf->rule.ip.local.addr,
|
||||
addr_len) == 0 &&
|
||||
memcmp(dst_mask, pf->rule.ip.remote.addr,
|
||||
addr_len) == 0)
|
||||
{
|
||||
addr_len) == 0) {
|
||||
/* Protocol match */
|
||||
if (pf->rule.proto == 0) /* IP */
|
||||
{
|
||||
if (pf->rule.proto == 0) { /* IP */
|
||||
/* No need to match port */
|
||||
break;
|
||||
}
|
||||
|
||||
if (pf->rule.proto == proto)
|
||||
{
|
||||
if (pf->rule.proto == IPPROTO_TCP)
|
||||
{
|
||||
if (pf->rule.proto == proto) {
|
||||
if (pf->rule.proto == IPPROTO_TCP) {
|
||||
struct tcphdr *tcph =
|
||||
(struct tcphdr *)
|
||||
((char *)pkt->data + ip_hlen);
|
||||
|
|
@ -396,38 +380,32 @@ pgw_bearer_t *pgw_bearer_find_by_packet(ogs_pkbuf_t *pkt)
|
|||
/* Source port */
|
||||
if (pf->rule.port.local.low &&
|
||||
ntohs(tcph->th_sport) <
|
||||
pf->rule.port.local.low)
|
||||
{
|
||||
pf->rule.port.local.low) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (pf->rule.port.local.high &&
|
||||
ntohs(tcph->th_sport) >
|
||||
pf->rule.port.local.high)
|
||||
{
|
||||
pf->rule.port.local.high) {
|
||||
continue;
|
||||
}
|
||||
|
||||
/* Dst Port*/
|
||||
if (pf->rule.port.remote.low &&
|
||||
ntohs(tcph->th_dport) <
|
||||
pf->rule.port.remote.low)
|
||||
{
|
||||
pf->rule.port.remote.low) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (pf->rule.port.remote.high &&
|
||||
ntohs(tcph->th_dport) >
|
||||
pf->rule.port.remote.high)
|
||||
{
|
||||
pf->rule.port.remote.high) {
|
||||
continue;
|
||||
}
|
||||
|
||||
/* Matched */
|
||||
break;
|
||||
}
|
||||
else if (pf->rule.proto == IPPROTO_UDP)
|
||||
{
|
||||
} else if (pf->rule.proto == IPPROTO_UDP) {
|
||||
struct udphdr *udph =
|
||||
(struct udphdr *)
|
||||
((char *)pkt->data + ip_hlen);
|
||||
|
|
@ -435,38 +413,32 @@ pgw_bearer_t *pgw_bearer_find_by_packet(ogs_pkbuf_t *pkt)
|
|||
/* Source port */
|
||||
if (pf->rule.port.local.low &&
|
||||
ntohs(udph->uh_sport) <
|
||||
pf->rule.port.local.low)
|
||||
{
|
||||
pf->rule.port.local.low) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (pf->rule.port.local.high &&
|
||||
ntohs(udph->uh_sport) >
|
||||
pf->rule.port.local.high)
|
||||
{
|
||||
pf->rule.port.local.high) {
|
||||
continue;
|
||||
}
|
||||
|
||||
/* Dst Port*/
|
||||
if (pf->rule.port.remote.low &&
|
||||
ntohs(udph->uh_dport) <
|
||||
pf->rule.port.remote.low)
|
||||
{
|
||||
pf->rule.port.remote.low) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (pf->rule.port.remote.high &&
|
||||
ntohs(udph->uh_dport) >
|
||||
pf->rule.port.remote.high)
|
||||
{
|
||||
pf->rule.port.remote.high) {
|
||||
continue;
|
||||
}
|
||||
|
||||
/* Matched */
|
||||
break;
|
||||
}
|
||||
else
|
||||
{
|
||||
} else {
|
||||
/* No need to match port */
|
||||
break;
|
||||
}
|
||||
|
|
@ -476,8 +448,7 @@ pgw_bearer_t *pgw_bearer_find_by_packet(ogs_pkbuf_t *pkt)
|
|||
|
||||
}
|
||||
|
||||
if (pf)
|
||||
{
|
||||
if (pf) {
|
||||
bearer = pf->bearer;
|
||||
ogs_debug("Found Dedicated Bearer : EBI[%d]", bearer->ebi);
|
||||
break;
|
||||
|
|
|
|||
|
|
@ -1,9 +1,36 @@
|
|||
#ifndef __PGW_IPFW_H__
|
||||
#define __PGW_IPFW_H__
|
||||
/*
|
||||
* Copyright (C) 2019 by Sukchan Lee <acetcom@gmail.com>
|
||||
*
|
||||
* This file is part of Open5GS.
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#ifndef PGW_IPFW_H
|
||||
#define PGW_IPFW_H
|
||||
|
||||
#include "pgw-context.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
int pgw_compile_packet_filter(pgw_rule_t *pf, char *description);
|
||||
pgw_bearer_t *pgw_bearer_find_by_packet(ogs_pkbuf_t *pkt);
|
||||
|
||||
#endif /* __PGW_IPFW_H__ */
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* PGW_IPFW_H */
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue