diff options
author | Holger Hans Peter Freyther <zecke@selfish.org> | 2012-09-11 18:02:46 +0200 |
---|---|---|
committer | Holger Hans Peter Freyther <zecke@selfish.org> | 2012-09-11 18:02:46 +0200 |
commit | ca5d2111131101f7b8df40207b4c597b0e53f2cb (patch) | |
tree | ca2cb035b0b5ea736e6e9a0713d267837dd09db1 | |
parent | c11889f3dd305055dc7c6f4dd6c68d328eb6f2bf (diff) | |
parent | 31b245b91afa21fbf6907c0f08b548a210d7ac70 (diff) |
Merge branch 'feature/local-mscs'
-rw-r--r-- | openbsc/include/openbsc/osmo_msc_data.h | 8 | ||||
-rw-r--r-- | openbsc/src/osmo-bsc/osmo_bsc_filter.c | 25 | ||||
-rw-r--r-- | openbsc/src/osmo-bsc/osmo_bsc_msc.c | 1 | ||||
-rw-r--r-- | openbsc/src/osmo-bsc/osmo_bsc_vty.c | 34 |
4 files changed, 67 insertions, 1 deletions
diff --git a/openbsc/include/openbsc/osmo_msc_data.h b/openbsc/include/openbsc/osmo_msc_data.h index 0f3f92724..0bda66225 100644 --- a/openbsc/include/openbsc/osmo_msc_data.h +++ b/openbsc/include/openbsc/osmo_msc_data.h @@ -35,12 +35,20 @@ struct gsm_audio_support { ver : 7; }; +enum { + MSC_CON_TYPE_NORMAL, + MSC_CON_TYPE_LOCAL, +}; + struct osmo_msc_data { struct llist_head entry; /* Back pointer */ struct gsm_network *network; + int allow_emerg; + int type; + /* Connection data */ char *bsc_token; int ping_timeout; diff --git a/openbsc/src/osmo-bsc/osmo_bsc_filter.c b/openbsc/src/osmo-bsc/osmo_bsc_filter.c index 200360ac9..fa7f2d928 100644 --- a/openbsc/src/osmo-bsc/osmo_bsc_filter.c +++ b/openbsc/src/osmo-bsc/osmo_bsc_filter.c @@ -106,6 +106,21 @@ static int handle_page_resp(struct gsm_subscriber_connection *conn, struct msgb subscr_put(subscr); return 0; } + +static int is_cm_service_for_emerg(struct msgb *msg) +{ + struct gsm48_service_request *cm; + struct gsm48_hdr *gh = msgb_l3(msg); + + if (msgb_l3len(msg) < sizeof(*gh) + sizeof(*cm)) { + LOGP(DMSC, LOGL_ERROR, "CM ServiceRequest does not fit.\n"); + return 0; + } + + cm = (struct gsm48_service_request *) &gh->data[0]; + return cm->cm_service_type == GSM48_CMSERV_EMERGENCY; +} + struct osmo_msc_data *bsc_find_msc(struct gsm_subscriber_connection *conn, struct msgb *msg) { @@ -115,6 +130,7 @@ struct osmo_msc_data *bsc_find_msc(struct gsm_subscriber_connection *conn, struct osmo_bsc_data *bsc; struct osmo_msc_data *msc, *pag_msc; struct gsm_subscriber *subscr; + int is_emerg = 0; bsc = conn->bts->network->bsc_data; @@ -135,13 +151,20 @@ struct osmo_msc_data *bsc_find_msc(struct gsm_subscriber_connection *conn, */ if (pdisc == GSM48_PDISC_RR && mtype == GSM48_MT_RR_PAG_RESP) goto paging; - else + else if (pdisc == GSM48_PDISC_MM && mtype == GSM48_MT_MM_CM_SERV_REQ) { + is_emerg = is_cm_service_for_emerg(msg); + goto round_robin; + } else goto round_robin; round_robin: llist_for_each_entry(msc, &bsc->mscs, entry) { if (!msc->msc_con->is_authenticated) continue; + if (!is_emerg && msc->type != MSC_CON_TYPE_NORMAL) + continue; + if (is_emerg && !msc->allow_emerg) + continue; /* force round robin by moving it to the end */ llist_move_tail(&msc->entry, &bsc->mscs); diff --git a/openbsc/src/osmo-bsc/osmo_bsc_msc.c b/openbsc/src/osmo-bsc/osmo_bsc_msc.c index 617a59aee..55532dbd4 100644 --- a/openbsc/src/osmo-bsc/osmo_bsc_msc.c +++ b/openbsc/src/osmo-bsc/osmo_bsc_msc.c @@ -492,6 +492,7 @@ struct osmo_msc_data *osmo_msc_data_alloc(struct gsm_network *net, int nr) msc_data->rtp_base = 4000; msc_data->nr = nr; + msc_data->allow_emerg = 1; return msc_data; } diff --git a/openbsc/src/osmo-bsc/osmo_bsc_vty.c b/openbsc/src/osmo-bsc/osmo_bsc_vty.c index 04f9bf440..9f1eb6969 100644 --- a/openbsc/src/osmo-bsc/osmo_bsc_vty.c +++ b/openbsc/src/osmo-bsc/osmo_bsc_vty.c @@ -114,6 +114,11 @@ static void write_msc(struct vty *vty, struct osmo_msc_data *msc) llist_for_each_entry(dest, &msc->dests, list) vty_out(vty, " dest %s %d %d%s", dest->ip, dest->port, dest->dscp, VTY_NEWLINE); + + vty_out(vty, " type %s%s", msc->type == MSC_CON_TYPE_NORMAL ? + "normal" : "local", VTY_NEWLINE); + vty_out(vty, " allow-emergency %s%s", msc->allow_emerg ? + "allow" : "deny", VTY_NEWLINE); } static int config_write_msc(struct vty *vty) @@ -332,6 +337,33 @@ DEFUN(cfg_net_msc_welcome_ussd, return CMD_SUCCESS; } +DEFUN(cfg_net_msc_type, + cfg_net_msc_type_cmd, + "type (normal|local)", + "Select the MSC type\n" + "Plain GSM MSC\n" "Special MSC for local call routing\n") +{ + struct osmo_msc_data *data = osmo_msc_data(vty); + + if (strcmp(argv[0], "normal") == 0) + data->type = MSC_CON_TYPE_NORMAL; + else if (strcmp(argv[0], "local") == 0) + data->type = MSC_CON_TYPE_LOCAL; + + return CMD_SUCCESS; +} + +DEFUN(cfg_net_msc_emerg, + cfg_net_msc_emerg_cmd, + "allow-emergency (allow|deny)", + "Allow CM ServiceRequests with type emergency\n" + "Allow\n" "Deny\n") +{ + struct osmo_msc_data *data = osmo_msc_data(vty); + data->allow_emerg = strcmp("allow", argv[0]) == 0; + return CMD_SUCCESS; +} + DEFUN(cfg_net_bsc_mid_call_text, cfg_net_bsc_mid_call_text_cmd, "mid-call-text .TEXT", @@ -419,6 +451,8 @@ int bsc_vty_init_extra(void) install_element(MSC_NODE, &cfg_net_msc_ping_time_cmd); install_element(MSC_NODE, &cfg_net_msc_pong_time_cmd); install_element(MSC_NODE, &cfg_net_msc_welcome_ussd_cmd); + install_element(MSC_NODE, &cfg_net_msc_type_cmd); + install_element(MSC_NODE, &cfg_net_msc_emerg_cmd); install_element_ve(&show_statistics_cmd); install_element_ve(&show_mscs_cmd); |