From bee02fc34fc074420894fbcbd21d7ea38d90cbd4 Mon Sep 17 00:00:00 2001 From: Neels Hofmeyr Date: Wed, 20 Jul 2022 14:05:41 +0200 Subject: [PATCH] add VTY option gtp/mockup, for VTY tests To avoid actions that require cap_net_admin permissions on build servers, add this option to "dry run" all kernel GTP actions. Same will be added for netfilter rules. On startup, osmo-upf opens sockets to GTP kernel module / NFT ctx. However, on build servers, this would require giving cap_net_admin permissions just to run the VTY tests. Related: SYS#5599 Change-Id: I3b9c796186307fd8562abcff3f0ccfab0e88b6c8 --- doc/examples/osmo-upf/osmo-upf-mockup.cfg | 17 +++++++++++++++++ include/osmocom/upf/upf.h | 3 +++ osmoappdesc.py | 4 ++-- src/osmo-upf/up_gtp_action.c | 6 ++++++ src/osmo-upf/upf_gtp.c | 14 +++++++++++++- src/osmo-upf/upf_vty.c | 22 ++++++++++++++++++++++ tests/Makefile.am | 2 +- 7 files changed, 64 insertions(+), 4 deletions(-) create mode 100644 doc/examples/osmo-upf/osmo-upf-mockup.cfg diff --git a/doc/examples/osmo-upf/osmo-upf-mockup.cfg b/doc/examples/osmo-upf/osmo-upf-mockup.cfg new file mode 100644 index 0000000..50003be --- /dev/null +++ b/doc/examples/osmo-upf/osmo-upf-mockup.cfg @@ -0,0 +1,17 @@ +log stderr + logging filter all 1 + logging color 1 + logging print level 1 + logging print category 1 + logging print category-hex 0 + logging print file basename last + logging print extended-timestamp 1 + logging level set-all debug + logging level set-all notice + logging level set-all info + +timer pfcp x24 5000 +pfcp + local-addr 127.0.0.1 +gtp + mockup diff --git a/include/osmocom/upf/upf.h b/include/osmocom/upf/upf.h index b8065dd..3802057 100644 --- a/include/osmocom/upf/upf.h +++ b/include/osmocom/upf/upf.h @@ -73,6 +73,9 @@ struct g_upf { struct up_endpoint *ep; } pfcp; struct { + /* if true, don't actually send commands to the GTP kernel module, just return success. */ + bool mockup; + /* GTP devices as in osmo-upf.cfg */ struct gtp_vty_cfg vty_cfg; diff --git a/osmoappdesc.py b/osmoappdesc.py index 0cdbd1d..796c112 100644 --- a/osmoappdesc.py +++ b/osmoappdesc.py @@ -15,13 +15,13 @@ # along with this program. If not, see app_configs = { - "osmo-upf": ["doc/examples/osmo-upf/osmo-upf.cfg"] + "osmo-upf": ["doc/examples/osmo-upf/osmo-upf-mockup.cfg"] } apps = [(4275, "src/osmo-upf/osmo-upf", "OsmoUPF", "osmo-upf") ] vty_command = ["./src/osmo-upf/osmo-upf", "-c", - "doc/examples/osmo-upf/osmo-upf.cfg"] + "doc/examples/osmo-upf/osmo-upf-mockup.cfg"] vty_app = apps[0] diff --git a/src/osmo-upf/up_gtp_action.c b/src/osmo-upf/up_gtp_action.c index 47aa3ac..bffb85a 100644 --- a/src/osmo-upf/up_gtp_action.c +++ b/src/osmo-upf/up_gtp_action.c @@ -83,6 +83,12 @@ static int up_gtp_action_enable_disable(struct up_gtp_action *a, bool enable) switch (a->kind) { case UP_GTP_U_ENDECAPS: + if (g_upf->gtp.mockup) { + LOG_UP_GTP_ACTION(a, LOGL_NOTICE, "gtp/mockup active, skipping GTP action %s\n", + enable ? "enable" : "disable"); + return 0; + } + /* use the first available GTP device. * TODO: select by interface name? */ diff --git a/src/osmo-upf/upf_gtp.c b/src/osmo-upf/upf_gtp.c index e3435a9..6a8deac 100644 --- a/src/osmo-upf/upf_gtp.c +++ b/src/osmo-upf/upf_gtp.c @@ -167,7 +167,14 @@ int upf_gtp_dev_open(const char *name, bool create_gtp_dev, const char *local_ad }, }; int rc; - struct upf_gtp_dev *dev = upf_gtp_dev_alloc(name, local_addr); + struct upf_gtp_dev *dev; + + if (g_upf->gtp.mockup) { + LOGP(DGTP, LOGL_NOTICE, "gtp/mockup active: not opening GTP device '%s'\n", name); + return 0; + } + + dev = upf_gtp_dev_alloc(name, local_addr); if (!dev) return -EIO; @@ -245,6 +252,11 @@ void upf_gtp_genl_close() /* Open an MNL socket which allows to create and remove GTP devices (requires CAP_NET_ADMIN). */ int upf_gtp_genl_open() { + if (g_upf->gtp.mockup) { + LOGP(DGTP, LOGL_NOTICE, "gtp/mockup active: not opening mnl_socket\n"); + return 0; + } + if (g_upf->gtp.nl && g_upf->gtp.genl_id >= 0) return 0; diff --git a/src/osmo-upf/upf_vty.c b/src/osmo-upf/upf_vty.c index 73d86d1..1212864 100644 --- a/src/osmo-upf/upf_vty.c +++ b/src/osmo-upf/upf_vty.c @@ -96,6 +96,9 @@ static int config_write_gtp(struct vty *vty) struct gtp_vty_cfg_dev *d; vty_out(vty, "gtp%s", VTY_NEWLINE); + if (g_upf->gtp.mockup) + vty_out(vty, " mockup%s", VTY_NEWLINE); + llist_for_each_entry(d, >p_vty.devs, entry) { if (d->create) { vty_out(vty, " dev create %s", d->dev_name); @@ -111,6 +114,23 @@ static int config_write_gtp(struct vty *vty) #define DEV_STR "Configure the GTP device to use for encaps/decaps.\n" +DEFUN(cfg_gtp_mockup, cfg_gtp_mockup_cmd, + "mockup", + "don't actually send commands to the GTP kernel module, just return success\n") +{ + g_upf->gtp.mockup = true; + return CMD_SUCCESS; +} + +DEFUN(cfg_gtp_no_mockup, cfg_gtp_no_mockup_cmd, + "no mockup", + NO_STR + "operate GTP kernel module normally\n") +{ + g_upf->gtp.mockup = false; + return CMD_SUCCESS; +} + DEFUN(cfg_gtp_dev_create, cfg_gtp_dev_create_cmd, "dev create DEVNAME [LISTEN_ADDR]", DEV_STR @@ -279,6 +299,8 @@ void upf_vty_init() install_node(&cfg_gtp_node, config_write_gtp); install_element(CONFIG_NODE, &cfg_gtp_cmd); + install_element(GTP_NODE, &cfg_gtp_mockup_cmd); + install_element(GTP_NODE, &cfg_gtp_no_mockup_cmd); install_element(GTP_NODE, &cfg_gtp_dev_create_cmd); install_element(GTP_NODE, &cfg_gtp_dev_use_cmd); install_element(GTP_NODE, &cfg_gtp_dev_del_cmd); diff --git a/tests/Makefile.am b/tests/Makefile.am index 66510f0..dbdb5f2 100644 --- a/tests/Makefile.am +++ b/tests/Makefile.am @@ -48,7 +48,7 @@ VTY_TEST ?= *.vty vty-test: osmo_verify_transcript_vty.py -v \ -n OsmoUPF -p 4275 \ - -r "$(top_builddir)/src/osmo-upf/osmo-upf -c $(top_srcdir)/doc/examples/osmo-upf/osmo-upf.cfg" \ + -r "$(top_builddir)/src/osmo-upf/osmo-upf -c $(top_srcdir)/doc/examples/osmo-upf/osmo-upf-mockup.cfg" \ $(U) $(srcdir)/$(VTY_TEST) check-local: atconfig $(TESTSUITE)