osmith has uploaded this change for review. ( https://gerrit.osmocom.org/c/osmo-bsc-nat/+/27473 )
Change subject: Store MSC ......................................................................
Store MSC
Expect one MSC to be configured in the address book (part of the cs7 section in the config, see doc/examples/osmo-bsc-nat/osmo-bsc-nat.cfg) and store it on start up.
Store the MSC in a list, as we may potentially support multiple MSCs in the future. Also that makes it symmetric to the BSC list.
Prepare a FSM for MSC, as the next patch will extend this FSM to send a RESET to the MSC on start up.
Don't use the stored MSCs in the forwarding logic just yet, a future commit will replace the current forwarding code with proper connection mappings.
Related: SYS#5560 Change-Id: I711df0c649728f1007857fbfda500ed5ef69287b --- M include/osmocom/bsc_nat/Makefile.am M include/osmocom/bsc_nat/bsc_nat.h A include/osmocom/bsc_nat/msc_fsm.h M src/osmo-bsc-nat/Makefile.am M src/osmo-bsc-nat/bsc_nat.c M src/osmo-bsc-nat/bsc_nat_fsm.c M src/osmo-bsc-nat/bssap.c M src/osmo-bsc-nat/main.c A src/osmo-bsc-nat/msc_fsm.c 9 files changed, 161 insertions(+), 16 deletions(-)
git pull ssh://gerrit.osmocom.org:29418/osmo-bsc-nat refs/changes/73/27473/1
diff --git a/include/osmocom/bsc_nat/Makefile.am b/include/osmocom/bsc_nat/Makefile.am index 76aada0..4c2bd09 100644 --- a/include/osmocom/bsc_nat/Makefile.am +++ b/include/osmocom/bsc_nat/Makefile.am @@ -3,5 +3,6 @@ bsc_nat_fsm.h \ bssap.h \ logging.h \ + msc_fsm.h \ vty.h \ $(NULL) diff --git a/include/osmocom/bsc_nat/bsc_nat.h b/include/osmocom/bsc_nat/bsc_nat.h index eb48f08..0807d83 100644 --- a/include/osmocom/bsc_nat/bsc_nat.h +++ b/include/osmocom/bsc_nat/bsc_nat.h @@ -29,6 +29,12 @@ struct osmo_sccp_user *scu; };
+struct msc { + struct llist_head list; + struct osmo_sccp_addr addr; + struct osmo_fsm_inst *fi; +}; + struct bsc { struct llist_head list; struct osmo_sccp_addr addr; @@ -40,12 +46,18 @@ struct bsc_nat_sccp_inst *cn; struct bsc_nat_sccp_inst *ran;
+ struct llist_head mscs; /* list of struct msc */ struct llist_head bscs; /* list of struct bsc */ };
struct bsc_nat *bsc_nat_alloc(void *tall_ctx); void bsc_nat_free(struct bsc_nat *bsc_nat);
+struct msc *bsc_nat_msc_add(struct bsc_nat *bsc_nat, struct osmo_sccp_addr *addr); +struct msc *bsc_nat_msc_add_from_addr_book(struct bsc_nat *bsc_nat); +struct msc *bsc_nat_msc_get(struct bsc_nat *bsc_nat); +void bsc_nat_msc_del(struct bsc_nat *bsc_nat, struct msc *msc); + struct bsc *bsc_nat_bsc_add(struct bsc_nat *bsc_nat, struct osmo_sccp_addr *addr); struct bsc *bsc_nat_bsc_get_by_pc(struct bsc_nat *bsc_nat, uint32_t pointcode); void bsc_nat_bsc_del(struct bsc_nat *bsc_nat, struct bsc *bsc); diff --git a/include/osmocom/bsc_nat/msc_fsm.h b/include/osmocom/bsc_nat/msc_fsm.h new file mode 100644 index 0000000..0ea3024 --- /dev/null +++ b/include/osmocom/bsc_nat/msc_fsm.h @@ -0,0 +1,21 @@ +/* (C) 2022 by sysmocom - s.f.m.c. GmbH info@sysmocom.de + * Author: Oliver Smith osmith@sysmocom.de + * All Rights Reserved + * + * 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 Affero General Public License for more details. + * + * You should have received a copy of the GNU Affero General Public License + * along with this program. If not, see http://www.gnu.org/lienses/. + * + */ +#pragma once + +void msc_fsm_alloc(struct msc *msc); diff --git a/src/osmo-bsc-nat/Makefile.am b/src/osmo-bsc-nat/Makefile.am index 445c098..2c2d9fa 100644 --- a/src/osmo-bsc-nat/Makefile.am +++ b/src/osmo-bsc-nat/Makefile.am @@ -30,6 +30,7 @@ bssap.c \ logging.c \ main.c \ + msc_fsm.c \ vty.c \ $(NULL)
diff --git a/src/osmo-bsc-nat/bsc_nat.c b/src/osmo-bsc-nat/bsc_nat.c index 5a6e84e..b8c87dd 100644 --- a/src/osmo-bsc-nat/bsc_nat.c +++ b/src/osmo-bsc-nat/bsc_nat.c @@ -21,6 +21,7 @@ #include <osmocom/bsc_nat/bsc_nat.h> #include <osmocom/bsc_nat/bsc_nat_fsm.h> #include <osmocom/bsc_nat/logging.h> +#include <osmocom/bsc_nat/msc_fsm.h> #include <osmocom/core/talloc.h> #include <osmocom/core/utils.h>
@@ -39,6 +40,7 @@ OSMO_ASSERT(bsc_nat->ran); talloc_set_name_const(bsc_nat->ran, "struct bsc_nat_sccp_inst (RAN)");
+ INIT_LLIST_HEAD(&bsc_nat->mscs); INIT_LLIST_HEAD(&bsc_nat->bscs);
bsc_nat_fsm_alloc(bsc_nat); @@ -46,6 +48,56 @@ return bsc_nat; }
+struct msc *bsc_nat_msc_add(struct bsc_nat *bsc_nat, struct osmo_sccp_addr *addr) +{ + struct msc *msc = talloc_zero(bsc_nat, struct msc); + + OSMO_ASSERT(msc); + talloc_set_name(msc, "MSC(PC=%s)", osmo_ss7_pointcode_print(NULL, addr->pc)); + + LOGP(DMAIN, LOGL_DEBUG, "Add %s\n", talloc_get_name(msc)); + + msc->addr = *addr; + + INIT_LLIST_HEAD(&msc->list); + llist_add(&msc->list, &bsc_nat->mscs); + + msc_fsm_alloc(msc); + + return msc; +} + +struct msc *bsc_nat_msc_add_from_addr_book(struct bsc_nat *bsc_nat) +{ + struct osmo_sccp_addr addr; + + /* For now only one MSC is supported */ + if (osmo_sccp_addr_by_name_local(&addr, "msc", bsc_nat->cn->ss7_inst) < 0) { + LOGP(DMAIN, LOGL_ERROR, "Configuration error, MSC not found in address book\n"); + return NULL; + } + + return bsc_nat_msc_add(bsc_nat, &addr); +} + + +struct msc *bsc_nat_msc_get(struct bsc_nat *bsc_nat) +{ + /* For now only one MSC is supported */ + + OSMO_ASSERT(!llist_empty(&bsc_nat->mscs)); + + return llist_first_entry(&bsc_nat->mscs, struct msc, list); +} + +void bsc_nat_msc_del(struct bsc_nat *bsc_nat, struct msc *msc) +{ + LOGP(DMAIN, LOGL_DEBUG, "Del %s\n", talloc_get_name(msc)); + llist_del(&msc->list); + osmo_fsm_inst_free(msc->fi); + talloc_free(msc); +} + struct bsc *bsc_nat_bsc_add(struct bsc_nat *bsc_nat, struct osmo_sccp_addr *addr) { struct bsc *bsc = talloc_zero(bsc_nat, struct bsc); @@ -84,6 +136,7 @@
void bsc_nat_free(struct bsc_nat *bsc_nat) { + struct msc *msc; struct bsc *bsc;
if (bsc_nat->fi) { @@ -91,6 +144,10 @@ bsc_nat->fi = NULL; }
+ llist_for_each_entry(msc, &bsc_nat->mscs, list) { + bsc_nat_msc_del(bsc_nat, msc); + } + llist_for_each_entry(bsc, &bsc_nat->bscs, list) { bsc_nat_bsc_del(bsc_nat, bsc); } diff --git a/src/osmo-bsc-nat/bsc_nat_fsm.c b/src/osmo-bsc-nat/bsc_nat_fsm.c index 3091687..b35376d 100644 --- a/src/osmo-bsc-nat/bsc_nat_fsm.c +++ b/src/osmo-bsc-nat/bsc_nat_fsm.c @@ -186,22 +186,7 @@
case OSMO_PRIM(OSMO_SCU_PRIM_N_UNITDATA, PRIM_OP_INDICATION): /* connection-less data received */ - addr = &prim->u.unitdata.calling_addr; - - if (sccp_sap_get_peer_addr_out(sccp_inst, addr, &peer_addr_out) < 0) - goto error; - - LOGP(DMAIN, LOGL_DEBUG, "Fwd to %s\n", bsc_nat_print_addr(g_bsc_nat->ran, &peer_addr_out)); - - /* oph->msg stores oph and unitdata msg. Move oph->msg->data to - * unitdata msg and send it again. */ - msgb_pull_to_l2(oph->msg); - osmo_sccp_tx_unitdata(g_bsc_nat->ran->scu, - &g_bsc_nat->ran->addr, - &peer_addr_out, - oph->msg->data, - msgb_length(oph->msg)); - rc = 0; + rc = bssap_handle_udt(sccp_inst, &prim->u.unitdata.calling_addr, oph->msg, msgb_l2len(oph->msg)); break;
default: diff --git a/src/osmo-bsc-nat/bssap.c b/src/osmo-bsc-nat/bssap.c index af6c8b3..ef12192 100644 --- a/src/osmo-bsc-nat/bssap.c +++ b/src/osmo-bsc-nat/bssap.c @@ -20,6 +20,7 @@ #include "config.h" #include <osmocom/bsc_nat/bsc_nat.h> #include <osmocom/bsc_nat/logging.h> +#include <osmocom/bsc_nat/msc_fsm.h> #include <osmocom/core/msgb.h> #include <osmocom/gsm/gsm0808.h> #include <osmocom/sigtran/sccp_helpers.h> diff --git a/src/osmo-bsc-nat/main.c b/src/osmo-bsc-nat/main.c index ef4b78d..86a774f 100644 --- a/src/osmo-bsc-nat/main.c +++ b/src/osmo-bsc-nat/main.c @@ -199,6 +199,9 @@
bsc_nat_fsm_start(g_bsc_nat);
+ if (!bsc_nat_msc_add_from_addr_book(g_bsc_nat)) + exit(1); + while (!osmo_select_shutdown_done()) osmo_select_main_ctx(0);
diff --git a/src/osmo-bsc-nat/msc_fsm.c b/src/osmo-bsc-nat/msc_fsm.c new file mode 100644 index 0000000..30434f4 --- /dev/null +++ b/src/osmo-bsc-nat/msc_fsm.c @@ -0,0 +1,64 @@ +/* (C) 2022 by sysmocom - s.f.m.c. GmbH info@sysmocom.de + * Author: Oliver Smith osmith@sysmocom.de + * All Rights Reserved + * + * 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 Affero General Public License for more details. + * + * You should have received a copy of the GNU Affero General Public License + * along with this program. If not, see http://www.gnu.org/lienses/. + * + */ + +#include "config.h" +#include <osmocom/bsc_nat/bsc_nat.h> +#include <osmocom/bsc_nat/bssap.h> +#include <osmocom/bsc_nat/logging.h> +#include <osmocom/core/fsm.h> +#include <osmocom/sigtran/sccp_sap.h> + +#define X(s) (1 << (s)) + +enum msc_fsm_states { + MSC_FSM_ST_DISCONNECTED, +}; + +static struct osmo_fsm_state msc_fsm_states[] = { + [MSC_FSM_ST_DISCONNECTED] = { + .name = "DISCONNECTED", + .in_event_mask = 0 + , + .out_state_mask = 0 + , + }, +}; + +const struct value_string msc_fsm_event_names[] = { + { 0, NULL } +}; + +struct osmo_fsm msc_fsm = { + .name = "MSC", + .states = msc_fsm_states, + .num_states = ARRAY_SIZE(msc_fsm_states), + .log_subsys = DMAIN, + .event_names = msc_fsm_event_names, +}; + +static __attribute__((constructor)) void msc_fsm_init(void) +{ + OSMO_ASSERT(osmo_fsm_register(&msc_fsm) == 0); +} + +void msc_fsm_alloc(struct msc *msc) +{ + msc->fi = osmo_fsm_inst_alloc(&msc_fsm, msc, msc, LOGL_INFO, NULL); + OSMO_ASSERT(msc->fi); +}