diff options
-rw-r--r-- | openbsc/include/openbsc/bsc_api.h | 2 | ||||
-rw-r--r-- | openbsc/include/openbsc/osmo_bsc.h | 3 | ||||
-rw-r--r-- | openbsc/src/libbsc/bsc_api.c | 5 | ||||
-rw-r--r-- | openbsc/src/osmo-bsc/osmo_bsc_bssap.c | 7 | ||||
-rw-r--r-- | openbsc/src/osmo-bsc/osmo_bsc_ctrl.c | 76 |
5 files changed, 89 insertions, 4 deletions
diff --git a/openbsc/include/openbsc/bsc_api.h b/openbsc/include/openbsc/bsc_api.h index f52984f39..a21fb74d8 100644 --- a/openbsc/include/openbsc/bsc_api.h +++ b/openbsc/include/openbsc/bsc_api.h @@ -52,4 +52,6 @@ int gsm0808_page(struct gsm_bts *bts, unsigned int page_group, unsigned int mi_len, uint8_t *mi, int chan_type); int gsm0808_clear(struct gsm_subscriber_connection *conn); +struct llist_head *bsc_api_sub_connections(struct gsm_network *net); + #endif diff --git a/openbsc/include/openbsc/osmo_bsc.h b/openbsc/include/openbsc/osmo_bsc.h index 7e931c8d9..cd4e4deb9 100644 --- a/openbsc/include/openbsc/osmo_bsc.h +++ b/openbsc/include/openbsc/osmo_bsc.h @@ -22,6 +22,9 @@ struct osmo_bsc_sccp_con { struct llist_head entry; int ciphering_handled; + + /* for audio handling */ + uint16_t cic; int rtp_port; /* SCCP connection realted */ diff --git a/openbsc/src/libbsc/bsc_api.c b/openbsc/src/libbsc/bsc_api.c index 04a4619a7..5ce0bc41d 100644 --- a/openbsc/src/libbsc/bsc_api.c +++ b/openbsc/src/libbsc/bsc_api.c @@ -857,3 +857,8 @@ static __attribute__((constructor)) void on_dso_load_bsc(void) { osmo_signal_register_handler(SS_LCHAN, bsc_handle_lchan_signal, NULL); } + +struct llist_head *bsc_api_sub_connections(struct gsm_network *net) +{ + return &sub_connections; +} diff --git a/openbsc/src/osmo-bsc/osmo_bsc_bssap.c b/openbsc/src/osmo-bsc/osmo_bsc_bssap.c index f58d96f03..dda31578e 100644 --- a/openbsc/src/osmo-bsc/osmo_bsc_bssap.c +++ b/openbsc/src/osmo-bsc/osmo_bsc_bssap.c @@ -299,7 +299,6 @@ static int bssmap_handle_assignm_req(struct osmo_bsc_sccp_con *conn, struct osmo_msc_data *msc; struct tlv_parsed tp; uint8_t *data; - uint16_t cic; uint8_t timeslot; uint8_t multiplex; enum gsm48_chan_mode chan_mode = GSM48_CMODE_SIGN; @@ -322,9 +321,9 @@ static int bssmap_handle_assignm_req(struct osmo_bsc_sccp_con *conn, goto reject; } - cic = ntohs(read_data16(TLVP_VAL(&tp, GSM0808_IE_CIRCUIT_IDENTITY_CODE))); - timeslot = cic & 0x1f; - multiplex = (cic & ~0x1f) >> 5; + conn->cic = ntohs(read_data16(TLVP_VAL(&tp, GSM0808_IE_CIRCUIT_IDENTITY_CODE))); + timeslot = conn->cic & 0x1f; + multiplex = (conn->cic & ~0x1f) >> 5; /* * Currently we only support a limited subset of all diff --git a/openbsc/src/osmo-bsc/osmo_bsc_ctrl.c b/openbsc/src/osmo-bsc/osmo_bsc_ctrl.c index 883205781..6b6b8a1f2 100644 --- a/openbsc/src/osmo-bsc/osmo_bsc_ctrl.c +++ b/openbsc/src/osmo-bsc/osmo_bsc_ctrl.c @@ -25,6 +25,7 @@ #include <openbsc/osmo_bsc_rf.h> #include <openbsc/osmo_msc_data.h> #include <openbsc/signal.h> +#include <openbsc/gsm_04_80.h> #include <osmocom/core/linuxlist.h> #include <osmocom/core/signal.h> @@ -631,6 +632,78 @@ static int verify_net_inform_msc(struct ctrl_cmd *cmd, const char *value, void * return 0; } +CTRL_CMD_DEFINE(net_ussd_notify, "ussd-notify-v1"); +static int get_net_ussd_notify(struct ctrl_cmd *cmd, void *data) +{ + cmd->reply = "There is nothing to read"; + return CTRL_CMD_ERROR; +} + +static int set_net_ussd_notify(struct ctrl_cmd *cmd, void *data) +{ + struct gsm_subscriber_connection *conn; + struct gsm_network *net; + char *saveptr = NULL; + char *cic_str, *alert_str, *text_str; + int cic, alert; + + /* Verify has done the test for us */ + cic_str = strtok_r(cmd->value, ",", &saveptr); + alert_str = strtok_r(NULL, ",", &saveptr); + text_str = strtok_r(NULL, ",", &saveptr); + + if (!cic_str || !alert_str || !text_str) { + cmd->reply = "Programming issue. How did this pass verify?"; + return CTRL_CMD_ERROR; + } + + cmd->reply = "No connection found"; + + cic = atoi(cic_str); + alert = atoi(alert_str); + + net = cmd->node; + llist_for_each_entry(conn, bsc_api_sub_connections(net), entry) { + if (!conn->sccp_con) + continue; + + if (conn->sccp_con->cic != cic) + continue; + + /* + * This is a hack. My E71 does not like to immediately + * receive a release complete on a TCH. So schedule a + * release complete to clear any previous attempt. The + * right thing would be to track invokeId and only send + * the release complete when we get a returnResultLast + * for this invoke id. + */ + gsm0480_send_releaseComplete(conn); + gsm0480_send_ussdNotify(conn, alert, text_str); + cmd->reply = "Found a connection"; + break; + } + + return CTRL_CMD_REPLY; +} + +static int verify_net_ussd_notify(struct ctrl_cmd *cmd, const char *value, void *data) +{ + char *saveptr = NULL; + char *inp, *cic, *alert, *text; + + inp = talloc_strdup(cmd, value); + + cic = strtok_r(inp, ",", &saveptr); + alert = strtok_r(NULL, ",", &saveptr); + text = strtok_r(NULL, ",", &saveptr); + + talloc_free(inp); + if (!cic || !alert || !text) + return 1; + return 0; +} + static int msc_signal_handler(unsigned int subsys, unsigned int signal, void *handler_data, void *signal_data) { @@ -689,6 +762,9 @@ int bsc_ctrl_cmds_install(struct gsm_network *net) rc = ctrl_cmd_install(CTRL_NODE_ROOT, &cmd_net_inform_msc); if (rc) goto end; + rc = ctrl_cmd_install(CTRL_NODE_ROOT, &cmd_net_ussd_notify); + if (rc) + goto end; rc = osmo_signal_register_handler(SS_L_INPUT, &bts_connection_status_trap_cb, net); end: |