summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorHolger Hans Peter Freyther <zecke@selfish.org>2011-06-04 19:58:26 +0200
committerHolger Hans Peter Freyther <zecke@selfish.org>2012-05-02 19:24:28 +0200
commit522676b9a8eb56d235b5a66f641bd1b0a918b676 (patch)
treee4ceca564c95e1f489a97ea00c26774813d756c0
parent1cd6c789cf4fcd5ac76e1ad72aac85dc987f191c (diff)
bsc: Prepare to have multiple MSC connections
We now have a list of MSCs but in the code we will try to access the MSC with the nr 0.
-rw-r--r--openbsc/include/openbsc/osmo_msc_data.h14
-rw-r--r--openbsc/src/libcommon/gsm_data.c9
-rw-r--r--openbsc/src/osmo-bsc/osmo_bsc_ctrl.c8
-rw-r--r--openbsc/src/osmo-bsc/osmo_bsc_main.c19
-rw-r--r--openbsc/src/osmo-bsc/osmo_bsc_msc.c40
-rw-r--r--openbsc/src/osmo-bsc/osmo_bsc_sccp.c7
-rw-r--r--openbsc/src/osmo-bsc/osmo_bsc_vty.c27
7 files changed, 96 insertions, 28 deletions
diff --git a/openbsc/include/openbsc/osmo_msc_data.h b/openbsc/include/openbsc/osmo_msc_data.h
index 384549ec0..0f3f92724 100644
--- a/openbsc/include/openbsc/osmo_msc_data.h
+++ b/openbsc/include/openbsc/osmo_msc_data.h
@@ -1,8 +1,8 @@
/*
* Data for the true BSC
*
- * (C) 2010 by Holger Hans Peter Freyther <zecke@selfish.org>
- * (C) 2010 by On-Waves
+ * (C) 2010-2011 by Holger Hans Peter Freyther <zecke@selfish.org>
+ * (C) 2010-2011 by On-Waves
* All Rights Reserved
*
* This program is free software; you can redistribute it and/or modify
@@ -36,6 +36,8 @@ struct gsm_audio_support {
};
struct osmo_msc_data {
+ struct llist_head entry;
+
/* Back pointer */
struct gsm_network *network;
@@ -62,6 +64,8 @@ struct osmo_msc_data {
/* mgcp agent */
struct osmo_wqueue mgcp_agent;
+
+ int nr;
};
/*
@@ -71,7 +75,7 @@ struct osmo_bsc_data {
struct gsm_network *network;
/* msc configuration */
- struct osmo_msc_data msc;
+ struct llist_head mscs;
/* rf ctl related bits */
char *mid_call_txt;
@@ -87,4 +91,8 @@ int msc_queue_write(struct bsc_msc_connection *conn, struct msgb *msg, int proto
int osmo_bsc_audio_init(struct gsm_network *network);
+struct osmo_msc_data *osmo_msc_data_find(struct gsm_network *, int);
+struct osmo_msc_data *osmo_msc_data_alloc(struct gsm_network *, int);
+
+
#endif
diff --git a/openbsc/src/libcommon/gsm_data.c b/openbsc/src/libcommon/gsm_data.c
index 1f5b86456..0dfad6c29 100644
--- a/openbsc/src/libcommon/gsm_data.c
+++ b/openbsc/src/libcommon/gsm_data.c
@@ -87,6 +87,7 @@ struct gsm_network *gsm_network_init(uint16_t country_code, uint16_t network_cod
/* Init back pointer */
net->bsc_data->network = net;
+ INIT_LLIST_HEAD(&net->bsc_data->mscs);
net->country_code = country_code;
net->network_code = network_code;
@@ -141,14 +142,6 @@ struct gsm_network *gsm_network_init(uint16_t country_code, uint16_t network_cod
net->mncc_recv = mncc_recv;
- INIT_LLIST_HEAD(&net->bsc_data->msc.dests);
- net->bsc_data->msc.ping_timeout = 20;
- net->bsc_data->msc.pong_timeout = 5;
- net->bsc_data->msc.core_ncc = -1;
- net->bsc_data->msc.core_mcc = -1;
- net->bsc_data->msc.rtp_base = 4000;
- net->bsc_data->msc.network = net;
-
gsm_net_update_ctype(net);
return net;
diff --git a/openbsc/src/osmo-bsc/osmo_bsc_ctrl.c b/openbsc/src/osmo-bsc/osmo_bsc_ctrl.c
index 889f85a30..123e538e0 100644
--- a/openbsc/src/osmo-bsc/osmo_bsc_ctrl.c
+++ b/openbsc/src/osmo-bsc/osmo_bsc_ctrl.c
@@ -287,6 +287,8 @@ static int set_bts_loc(struct ctrl_cmd *cmd, void *data)
int ret;
struct gsm_network *gsmnet = (struct gsm_network *)data;
struct gsm_bts *bts = (struct gsm_bts *) cmd->node;
+ struct osmo_msc_data *msc;
+
if (!bts) {
cmd->reply = "bts not found.";
return CTRL_CMD_ERROR;
@@ -324,8 +326,10 @@ static int set_bts_loc(struct ctrl_cmd *cmd, void *data)
ret = get_bts_loc(cmd, data);
- if (!location_equal(curloc, lastloc))
- generate_location_state_trap(bts, gsmnet->bsc_data->msc.msc_con);
+ if (!location_equal(curloc, lastloc)) {
+ llist_for_each_entry(msc, &gsmnet->bsc_data->mscs, entry)
+ generate_location_state_trap(bts, msc->msc_con);
+ }
cleanup_locations(&bts->loc_list);
diff --git a/openbsc/src/osmo-bsc/osmo_bsc_main.c b/openbsc/src/osmo-bsc/osmo_bsc_main.c
index 65ef4e0a2..484eb66e8 100644
--- a/openbsc/src/osmo-bsc/osmo_bsc_main.c
+++ b/openbsc/src/osmo-bsc/osmo_bsc_main.c
@@ -141,6 +141,8 @@ static struct vty_app_info vty_info = {
extern int bsc_shutdown_net(struct gsm_network *net);
static void signal_handler(int signal)
{
+ struct osmo_msc_data *msc;
+
fprintf(stdout, "signal %u received\n", signal);
switch (signal) {
@@ -160,11 +162,8 @@ static void signal_handler(int signal)
case SIGUSR2:
if (!bsc_gsmnet->bsc_data)
return;
- if (!bsc_gsmnet->bsc_data->msc.msc_con)
- return;
- if (!bsc_gsmnet->bsc_data->msc.msc_con->is_connected)
- return;
- bsc_msc_lost(bsc_gsmnet->bsc_data->msc.msc_con);
+ llist_for_each_entry(msc, &bsc_gsmnet->bsc_data->mscs, entry)
+ bsc_msc_lost(msc->msc_con);
break;
default:
break;
@@ -173,6 +172,7 @@ static void signal_handler(int signal)
int main(int argc, char **argv)
{
+ struct osmo_msc_data *msc;
struct osmo_bsc_data *data;
int rc;
@@ -232,11 +232,14 @@ int main(int argc, char **argv)
}
}
- if (osmo_bsc_msc_init(&bsc_gsmnet->bsc_data->msc) != 0) {
- LOGP(DNAT, LOGL_ERROR, "Failed to start up. Exiting.\n");
- exit(1);
+ llist_for_each_entry(msc, &bsc_gsmnet->bsc_data->mscs, entry) {
+ if (osmo_bsc_msc_init(msc) != 0) {
+ LOGP(DNAT, LOGL_ERROR, "Failed to start up. Exiting.\n");
+ exit(1);
+ }
}
+
if (osmo_bsc_sccp_init(bsc_gsmnet) != 0) {
LOGP(DNM, LOGL_ERROR, "Failed to register SCCP.\n");
exit(1);
diff --git a/openbsc/src/osmo-bsc/osmo_bsc_msc.c b/openbsc/src/osmo-bsc/osmo_bsc_msc.c
index 0ee83121f..31cbfb2a5 100644
--- a/openbsc/src/osmo-bsc/osmo_bsc_msc.c
+++ b/openbsc/src/osmo-bsc/osmo_bsc_msc.c
@@ -452,3 +452,43 @@ int osmo_bsc_msc_init(struct osmo_msc_data *data)
return 0;
}
+
+struct osmo_msc_data *osmo_msc_data_find(struct gsm_network *net, int nr)
+{
+ struct osmo_msc_data *msc_data;
+
+ llist_for_each_entry(msc_data, &net->bsc_data->mscs, entry)
+ if (msc_data->nr == nr)
+ return msc_data;
+ return NULL;
+}
+
+struct osmo_msc_data *osmo_msc_data_alloc(struct gsm_network *net, int nr)
+{
+ struct osmo_msc_data *msc_data;
+
+ /* check if there is already one */
+ msc_data = osmo_msc_data_find(net, nr);
+ if (msc_data)
+ return msc_data;
+
+ msc_data = talloc_zero(net, struct osmo_msc_data);
+ if (!msc_data)
+ return NULL;
+
+ llist_add_tail(&msc_data->entry, &net->bsc_data->mscs);
+
+ /* Init back pointer */
+ msc_data->network = net;
+
+ INIT_LLIST_HEAD(&msc_data->dests);
+ msc_data->ping_timeout = 20;
+ msc_data->pong_timeout = 5;
+ msc_data->core_ncc = -1;
+ msc_data->core_mcc = -1;
+ msc_data->rtp_base = 4000;
+
+ msc_data->nr = nr;
+
+ return msc_data;
+}
diff --git a/openbsc/src/osmo-bsc/osmo_bsc_sccp.c b/openbsc/src/osmo-bsc/osmo_bsc_sccp.c
index b5ab67ff1..46ffd5760 100644
--- a/openbsc/src/osmo-bsc/osmo_bsc_sccp.c
+++ b/openbsc/src/osmo-bsc/osmo_bsc_sccp.c
@@ -195,7 +195,12 @@ int bsc_create_new_connection(struct gsm_subscriber_connection *conn)
struct sccp_connection *sccp;
net = conn->bts->network;
- msc = &net->bsc_data->msc;
+ msc = osmo_msc_data_find(net, 0);
+ if (!msc) {
+ LOGP(DMSC, LOGL_ERROR, "Failed to select a MSC.\n");
+ return -1;
+ }
+
if (!msc->msc_con->is_authenticated) {
LOGP(DMSC, LOGL_ERROR, "Not connected to a MSC. Not forwarding data.\n");
return -1;
diff --git a/openbsc/src/osmo-bsc/osmo_bsc_vty.c b/openbsc/src/osmo-bsc/osmo_bsc_vty.c
index 8e687e308..8cf5a1438 100644
--- a/openbsc/src/osmo-bsc/osmo_bsc_vty.c
+++ b/openbsc/src/osmo-bsc/osmo_bsc_vty.c
@@ -36,7 +36,7 @@ static struct osmo_bsc_data *osmo_bsc_data(struct vty *vty)
static struct osmo_msc_data *osmo_msc_data(struct vty *vty)
{
- return &bsc_gsmnet->bsc_data->msc;
+ return osmo_msc_data_find(bsc_gsmnet, (int) vty->index);
}
static struct cmd_node msc_node = {
@@ -48,17 +48,23 @@ static struct cmd_node msc_node = {
DEFUN(cfg_net_msc, cfg_net_msc_cmd,
"msc", "Configure MSC details")
{
- vty->index = bsc_gsmnet;
- vty->node = MSC_NODE;
+ int index = 0;
+ struct osmo_msc_data *msc;
+
+ msc = osmo_msc_data_alloc(bsc_gsmnet, index);
+ if (!msc) {
+ vty_out(vty, "%%Failed to allocate MSC data.%s", VTY_NEWLINE);
+ return CMD_WARNING;
+ }
+ vty->index = (void *) index;
+ vty->node = MSC_NODE;
return CMD_SUCCESS;
}
-static int config_write_msc(struct vty *vty)
+static void write_msc(struct vty *vty, struct osmo_msc_data *msc)
{
struct bsc_msc_dest *dest;
- struct osmo_bsc_data *bsc = osmo_bsc_data(vty);
- struct osmo_msc_data *msc = &bsc->msc;
vty_out(vty, "msc%s", VTY_NEWLINE);
if (msc->bsc_token)
@@ -95,6 +101,15 @@ static int config_write_msc(struct vty *vty)
llist_for_each_entry(dest, &msc->dests, list)
vty_out(vty, " dest %s %d %d%s", dest->ip, dest->port,
dest->dscp, VTY_NEWLINE);
+}
+
+static int config_write_msc(struct vty *vty)
+{
+ struct osmo_msc_data *msc;
+ struct osmo_bsc_data *bsc = osmo_bsc_data(vty);
+
+ llist_for_each_entry(msc, &bsc->mscs, entry)
+ write_msc(vty, msc);
if (bsc->mid_call_txt)
vty_out(vty, " mid-call-text %s%s", bsc->mid_call_txt, VTY_NEWLINE);