From af3a1221b27c93770d11c6055ad017ab057f8b2a Mon Sep 17 00:00:00 2001 From: Andreas Eversberg Date: Mon, 23 Dec 2013 11:13:19 +0100 Subject: Add ringer support to built-in MNCC application of mobile --- src/host/layer23/include/osmocom/bb/mobile/mncc.h | 6 +++ .../layer23/include/osmocom/bb/mobile/settings.h | 3 ++ src/host/layer23/src/mobile/mnccms.c | 57 ++++++++++++++++++++++ src/host/layer23/src/mobile/vty_interface.c | 31 ++++++++++++ 4 files changed, 97 insertions(+) diff --git a/src/host/layer23/include/osmocom/bb/mobile/mncc.h b/src/host/layer23/include/osmocom/bb/mobile/mncc.h index cad1883c..a73a882c 100644 --- a/src/host/layer23/include/osmocom/bb/mobile/mncc.h +++ b/src/host/layer23/include/osmocom/bb/mobile/mncc.h @@ -44,6 +44,9 @@ struct gsm_call { uint8_t dtmf_state; uint8_t dtmf_index; char dtmf[32]; /* dtmf sequence */ + + struct osmo_timer_list ringer_timer; + uint8_t ringer_state; }; #define DTMF_ST_IDLE 0 /* no DTMF active */ @@ -52,6 +55,9 @@ struct gsm_call { #define DTMF_ST_STOP 3 /* DTMF stopped, waiting for resp. */ #define DTMF_ST_SPACE 4 /* wait space between tones */ +#define RINGER_MARK 0, 500000 +#define RINGER_SPACE 0, 250000 + #define MNCC_SETUP_REQ 0x0101 #define MNCC_SETUP_IND 0x0102 #define MNCC_SETUP_RSP 0x0103 diff --git a/src/host/layer23/include/osmocom/bb/mobile/settings.h b/src/host/layer23/include/osmocom/bb/mobile/settings.h index cb1cac4a..37f87873 100644 --- a/src/host/layer23/include/osmocom/bb/mobile/settings.h +++ b/src/host/layer23/include/osmocom/bb/mobile/settings.h @@ -101,6 +101,9 @@ struct gsm_settings { uint8_t class_dtm; uint8_t dtm_mac; uint8_t dtm_egprs; + + /* Ring tone */ + uint8_t ringtone; /* 0 = off */ }; struct gsm_settings_abbrev { diff --git a/src/host/layer23/src/mobile/mnccms.c b/src/host/layer23/src/mobile/mnccms.c index d364ca34..4fc08853 100644 --- a/src/host/layer23/src/mobile/mnccms.c +++ b/src/host/layer23/src/mobile/mnccms.c @@ -39,6 +39,7 @@ static LLIST_HEAD(call_list); void mncc_set_cause(struct gsm_mncc *data, int loc, int val); static int dtmf_statemachine(struct gsm_call *call, struct gsm_mncc *mncc); static void timeout_dtmf(void *arg); +static void timeout_ringer(void *arg); int mncc_answer(struct osmocom_ms *ms); /* @@ -62,11 +63,65 @@ static void stop_dtmf_timer(struct gsm_call *call) } } +/* Ringer */ +static void update_ringer(struct gsm_call *call) +{ + struct osmocom_ms *ms = call->ms; + + if (call->ring) { + struct gsm_settings *set = &ms->settings; + + /* ringer on */ + if (set->ringtone == 0) { + LOGP(DCC, LOGL_INFO, "Ringer disabled\n"); + return; + } + if (osmo_timer_pending(&call->ringer_timer)) + return; + LOGP(DCC, LOGL_INFO, "starting Ringer\n"); + call->ringer_timer.cb = timeout_ringer; + call->ringer_timer.data = call; + osmo_timer_schedule(&call->ringer_timer, RINGER_MARK); + l1ctl_tx_ringer_req(ms, set->ringtone); + call->ringer_state = 1; + } else { + /* ringer off */ + if (!osmo_timer_pending(&call->ringer_timer)) + return; + LOGP(DCC, LOGL_INFO, "stop Ringer\n"); + osmo_timer_del(&call->ringer_timer); + if (call->ringer_state) + l1ctl_tx_ringer_req(ms, 0); + } +} + +static void timeout_ringer(void *arg) +{ + struct gsm_call *call = arg; + struct osmocom_ms *ms = call->ms; + + /* on <-> off */ + call->ringer_state = 1 - call->ringer_state; + + if (call->ringer_state) { + struct gsm_settings *set = &ms->settings; + + osmo_timer_schedule(&call->ringer_timer, RINGER_MARK); + l1ctl_tx_ringer_req(ms, set->ringtone); + } else { + osmo_timer_schedule(&call->ringer_timer, RINGER_SPACE); + l1ctl_tx_ringer_req(ms, 0); + } +} + /* free call instance */ static void free_call(struct gsm_call *call) { stop_dtmf_timer(call); + call->ring = 0; + update_ringer(call); + llist_del(&call->entry); DEBUGP(DMNCC, "(call %x) Call removed.\n", call->callref); talloc_free(call); @@ -483,6 +538,7 @@ int mncc_recv_mobile(struct osmocom_ms *ms, int msg_type, void *arg) call->hold = 1; } call->ring = 1; + update_ringer(call); memset(&mncc, 0, sizeof(struct gsm_mncc)); mncc.callref = call->callref; mncc_tx_to_cc(ms, MNCC_ALERT_REQ, &mncc); @@ -650,6 +706,7 @@ int mncc_answer(struct osmocom_ms *ms) return -EBUSY; } alerting->ring = 0; + update_ringer(alerting); alerting->hold = 0; memset(&rsp, 0, sizeof(struct gsm_mncc)); diff --git a/src/host/layer23/src/mobile/vty_interface.c b/src/host/layer23/src/mobile/vty_interface.c index 22eb036f..975b0d7d 100644 --- a/src/host/layer23/src/mobile/vty_interface.c +++ b/src/host/layer23/src/mobile/vty_interface.c @@ -1348,6 +1348,11 @@ static void config_write_ms(struct vty *vty, struct osmocom_ms *ms) struct gsm_settings_abbrev *abbrev; vty_out(vty, "ms %s%s", ms->name, VTY_NEWLINE); + if (set->ringtone) + vty_out(vty, " ringtone %d%s", set->ringtone, VTY_NEWLINE); + else + if (!hide_default) + vty_out(vty, " no ringtone%s", VTY_NEWLINE); vty_out(vty, " layer2-socket %s%s", set->layer2_socket_path, VTY_NEWLINE); vty_out(vty, " sap-socket %s%s", set->sap_socket_path, VTY_NEWLINE); @@ -2231,6 +2236,30 @@ DEFUN(cfg_ms_no_nb_dedicated, cfg_ms_no_nb_dedicated_cmd, return CMD_SUCCESS; } +DEFUN(cfg_ms_ringtone, cfg_ms_ringtone_cmd, + "ringtone <0-255>", + "Enable ring tone\nVolume of ring tone") +{ + struct osmocom_ms *ms = vty->index; + struct gsm_settings *set = &ms->settings; + + set->ringtone = atoi(argv[0]); + + return CMD_SUCCESS; +} + +DEFUN(cfg_ms_no_ringtone, cfg_ms_no_ringtone_cmd, + "no ringtone", + NO_MS_NB_STR "Disable Ring tone") +{ + struct osmocom_ms *ms = vty->index; + struct gsm_settings *set = &ms->settings; + + set->ringtone = 0; + + return CMD_SUCCESS; +} + static int config_write_dummy(struct vty *vty) { return CMD_SUCCESS; @@ -2991,6 +3020,8 @@ int ms_vty_init(void) install_element(MS_NODE, &cfg_ms_no_nb_idle_cmd); install_element(MS_NODE, &cfg_ms_nb_dedicated_cmd); install_element(MS_NODE, &cfg_ms_no_nb_dedicated_cmd); + install_element(MS_NODE, &cfg_ms_ringtone_cmd); + install_element(MS_NODE, &cfg_ms_no_ringtone_cmd); install_element(MS_NODE, &cfg_ms_support_cmd); install_node(&support_node, config_write_dummy); install_default(SUPPORT_NODE); -- cgit v1.2.3