* [PATCH v2 2/2] plugins/gemalto: added voice support
2018-10-14 14:17 [PATCH v2 0/2] Gemalto: support for voicecall Giacinto Cifelli
@ 2018-10-14 14:17 ` Giacinto Cifelli
2018-10-14 16:50 ` Jonas Bonn
0 siblings, 1 reply; 6+ messages in thread
From: Giacinto Cifelli @ 2018-10-14 14:17 UTC (permalink / raw)
To: ofono
[-- Attachment #1: Type: text/plain, Size: 1434 bytes --]
The plugin for Gemalto modems is enriched with all voice-related atoms,
as well as USSD.
All except the voicecall itself are from the atmodem, while the
voicecall is from gemaltomodem.
---
plugins/gemalto.c | 11 +++++++++++
1 file changed, 11 insertions(+)
diff --git a/plugins/gemalto.c b/plugins/gemalto.c
index 0fcf30d8..8a965748 100644
--- a/plugins/gemalto.c
+++ b/plugins/gemalto.c
@@ -571,6 +571,10 @@ static void gemalto_pre_sim(struct ofono_modem *modem)
ofono_devinfo_create(modem, 0, "atmodem", data->app);
ofono_location_reporting_create(modem, 0, "gemaltomodem", data->app);
+
+ ofono_modem_set_integer(modem, "GemaltoVtsQuotes", 1);
+ ofono_voicecall_create(modem, 0, "gemaltomodem", data->app);
+
data->sim = ofono_sim_create(modem, OFONO_VENDOR_GEMALTO, "atmodem",
data->app);
@@ -597,6 +601,13 @@ static void gemalto_post_sim(struct ofono_modem *modem)
if (gprs && gc)
ofono_gprs_add_context(gprs, gc);
+ ofono_ussd_create(modem, 0, "atmodem", data->app);
+
+ ofono_call_forwarding_create(modem, 0, "atmodem", data->app);
+ ofono_call_settings_create(modem, 0, "atmodem", data->app);
+ ofono_call_meter_create(modem, 0, "atmodem", data->app);
+ ofono_call_barring_create(modem, 0, "atmodem", data->app);
+
if (!g_strcmp0(model, GEMALTO_MODEL_ALS3_PLS8x))
ofono_lte_create(modem, OFONO_VENDOR_CINTERION,
"atmodem", data->app);
--
2.17.1
^ permalink raw reply related [flat|nested] 6+ messages in thread
* Re: [PATCH v2 2/2] plugins/gemalto: added voice support
2018-10-14 14:17 ` [PATCH v2 2/2] plugins/gemalto: added voice support Giacinto Cifelli
@ 2018-10-14 16:50 ` Jonas Bonn
2018-10-14 17:03 ` Giacinto Cifelli
0 siblings, 1 reply; 6+ messages in thread
From: Jonas Bonn @ 2018-10-14 16:50 UTC (permalink / raw)
To: ofono
[-- Attachment #1: Type: text/plain, Size: 1634 bytes --]
On 14/10/18 16:17, Giacinto Cifelli wrote:
> The plugin for Gemalto modems is enriched with all voice-related atoms,
> as well as USSD.
> All except the voicecall itself are from the atmodem, while the
> voicecall is from gemaltomodem.
> ---
> plugins/gemalto.c | 11 +++++++++++
> 1 file changed, 11 insertions(+)
>
> diff --git a/plugins/gemalto.c b/plugins/gemalto.c
> index 0fcf30d8..8a965748 100644
> --- a/plugins/gemalto.c
> +++ b/plugins/gemalto.c
> @@ -571,6 +571,10 @@ static void gemalto_pre_sim(struct ofono_modem *modem)
>
> ofono_devinfo_create(modem, 0, "atmodem", data->app);
> ofono_location_reporting_create(modem, 0, "gemaltomodem", data->app);
> +
> + ofono_modem_set_integer(modem, "GemaltoVtsQuotes", 1);
Do you really mean to set this unconditionally for all models?
/Jonas
> + ofono_voicecall_create(modem, 0, "gemaltomodem", data->app);
> +
> data->sim = ofono_sim_create(modem, OFONO_VENDOR_GEMALTO, "atmodem",
> data->app);
>
> @@ -597,6 +601,13 @@ static void gemalto_post_sim(struct ofono_modem *modem)
> if (gprs && gc)
> ofono_gprs_add_context(gprs, gc);
>
> + ofono_ussd_create(modem, 0, "atmodem", data->app);
> +
> + ofono_call_forwarding_create(modem, 0, "atmodem", data->app);
> + ofono_call_settings_create(modem, 0, "atmodem", data->app);
> + ofono_call_meter_create(modem, 0, "atmodem", data->app);
> + ofono_call_barring_create(modem, 0, "atmodem", data->app);
> +
> if (!g_strcmp0(model, GEMALTO_MODEL_ALS3_PLS8x))
> ofono_lte_create(modem, OFONO_VENDOR_CINTERION,
> "atmodem", data->app);
^ permalink raw reply [flat|nested] 6+ messages in thread
* Re: [PATCH v2 2/2] plugins/gemalto: added voice support
2018-10-14 16:50 ` Jonas Bonn
@ 2018-10-14 17:03 ` Giacinto Cifelli
0 siblings, 0 replies; 6+ messages in thread
From: Giacinto Cifelli @ 2018-10-14 17:03 UTC (permalink / raw)
To: ofono
[-- Attachment #1: Type: text/plain, Size: 1737 bytes --]
Hi Jonas,
I answer here to the point about VTS with quotes.
On Sun, Oct 14, 2018 at 6:50 PM Jonas Bonn <jonas@southpole.se> wrote:
>
>
>
> On 14/10/18 16:17, Giacinto Cifelli wrote:
> > The plugin for Gemalto modems is enriched with all voice-related atoms,
> > as well as USSD.
> > All except the voicecall itself are from the atmodem, while the
> > voicecall is from gemaltomodem.
> > ---
> > plugins/gemalto.c | 11 +++++++++++
> > 1 file changed, 11 insertions(+)
> >
> > diff --git a/plugins/gemalto.c b/plugins/gemalto.c
> > index 0fcf30d8..8a965748 100644
> > --- a/plugins/gemalto.c
> > +++ b/plugins/gemalto.c
> > @@ -571,6 +571,10 @@ static void gemalto_pre_sim(struct ofono_modem *modem)
> >
> > ofono_devinfo_create(modem, 0, "atmodem", data->app);
> > ofono_location_reporting_create(modem, 0, "gemaltomodem", data->app);
> > +
> > + ofono_modem_set_integer(modem, "GemaltoVtsQuotes", 1);
>
> Do you really mean to set this unconditionally for all models?
The current supported modules for the gemalto plugin, and also TC65
for the cinterion plugin, require quotes.
But not the EHS6.
I need to add quite a few modules in the gemalto plugin, but for now
there are still too many patches to push before.
So for now, it is fixed, but later it will depend on the model.
I won't be patching the cinterion plugin, because I have the
impression it is not used anymore.
Several things don't work anymore as they were when this was implemented.
I intend, however, to merge it with the gemalto one, and then I will
take care of it.
Most Gemalto modules can work over USB or RS232, so it still makes
sense to maintain the serial interface.
>
> /Jonas
>
Giacinto
^ permalink raw reply [flat|nested] 6+ messages in thread
* [PATCH v2 1/2] Gemalto: voicecall atom
@ 2018-10-17 20:24 Giacinto Cifelli
2018-10-17 20:24 ` [PATCH v2 2/2] plugins/gemalto: added voice support Giacinto Cifelli
2018-10-17 22:04 ` [PATCH v2 1/2] Gemalto: voicecall atom Denis Kenzior
0 siblings, 2 replies; 6+ messages in thread
From: Giacinto Cifelli @ 2018-10-17 20:24 UTC (permalink / raw)
To: ofono
[-- Attachment #1: Type: text/plain, Size: 18252 bytes --]
Added voicecall atom specific for Gemalto modems.
This atom uses the URC ^SLCC to monitor the call status, as well as
incoming calls.
Note the use in the atom of the variable GemaltoVtsQuotes: this is
needed to support future modules, as of today not yet available in the
plugin.
---
Makefile.am | 3 +-
drivers/gemaltomodem/gemaltomodem.c | 3 +
drivers/gemaltomodem/gemaltomodem.h | 5 +
drivers/gemaltomodem/voicecall.c | 578 ++++++++++++++++++++++++++++
4 files changed, 588 insertions(+), 1 deletion(-)
create mode 100644 drivers/gemaltomodem/voicecall.c
diff --git a/Makefile.am b/Makefile.am
index 6667524f..e8e4ed95 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -397,7 +397,8 @@ builtin_modules += gemaltomodem
builtin_sources += drivers/atmodem/atutil.h \
drivers/gemaltomodem/gemaltomodem.h \
drivers/gemaltomodem/gemaltomodem.c \
- drivers/gemaltomodem/location-reporting.c
+ drivers/gemaltomodem/location-reporting.c \
+ drivers/gemaltomodem/voicecall.c
builtin_modules += xmm7modem
builtin_sources += drivers/atmodem/atutil.h \
diff --git a/drivers/gemaltomodem/gemaltomodem.c b/drivers/gemaltomodem/gemaltomodem.c
index 91cf238a..4818ac66 100644
--- a/drivers/gemaltomodem/gemaltomodem.c
+++ b/drivers/gemaltomodem/gemaltomodem.c
@@ -3,6 +3,7 @@
* oFono - Open Source Telephony
*
* Copyright (C) 2017 Vincent Cesson. All rights reserved.
+ * Copyright (C) 2018 Gemalto M2M
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -35,12 +36,14 @@
static int gemaltomodem_init(void)
{
gemalto_location_reporting_init();
+ gemalto_voicecall_init();
return 0;
}
static void gemaltomodem_exit(void)
{
+ gemalto_voicecall_exit();
gemalto_location_reporting_exit();
}
diff --git a/drivers/gemaltomodem/gemaltomodem.h b/drivers/gemaltomodem/gemaltomodem.h
index 7ea1e8fb..b08ab438 100644
--- a/drivers/gemaltomodem/gemaltomodem.h
+++ b/drivers/gemaltomodem/gemaltomodem.h
@@ -3,6 +3,7 @@
* oFono - Open Source Telephony
*
* Copyright (C) 2017 Vincent Cesson. All rights reserved.
+ * Copyright (C) 2018 Gemalto M2M
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -23,3 +24,7 @@
extern void gemalto_location_reporting_init();
extern void gemalto_location_reporting_exit();
+
+extern void gemalto_voicecall_init();
+extern void gemalto_voicecall_exit();
+
diff --git a/drivers/gemaltomodem/voicecall.c b/drivers/gemaltomodem/voicecall.c
new file mode 100644
index 00000000..f27dd815
--- /dev/null
+++ b/drivers/gemaltomodem/voicecall.c
@@ -0,0 +1,578 @@
+/*
+ *
+ * oFono - Open Source Telephony
+ *
+ * Copyright (C) 2008-2011 Intel Corporation. All rights reserved.
+ * Copyright (C) 2018 Gemalto M2M
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation.
+ *
+ * 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 General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+ *
+ */
+
+#ifdef HAVE_CONFIG_H
+#include <config.h>
+#endif
+
+#include <string.h>
+#include <stdlib.h>
+#include <stdio.h>
+#include <errno.h>
+
+#include <glib.h>
+
+#include <ofono/log.h>
+#include <ofono/modem.h>
+#include <ofono/voicecall.h>
+
+#include "gatchat.h"
+#include "gatresult.h"
+
+#include "common.h"
+
+#include "gemaltomodem.h"
+
+static const char *clcc_prefix[] = { "+CLCC:", NULL };
+static const char *none_prefix[] = { NULL };
+
+struct voicecall_data {
+ GAtChat *chat;
+ GSList *calls;
+ unsigned int local_release;
+ GSList *new_calls;
+};
+
+struct release_id_req {
+ struct ofono_voicecall *vc;
+ ofono_voicecall_cb_t cb;
+ void *data;
+ int id;
+};
+
+struct change_state_req {
+ struct ofono_voicecall *vc;
+ ofono_voicecall_cb_t cb;
+ void *data;
+ int affected_types;
+};
+
+static void generic_cb(gboolean ok, GAtResult *result, gpointer user_data)
+{
+ struct change_state_req *req = user_data;
+ struct voicecall_data *vd = ofono_voicecall_get_data(req->vc);
+ struct ofono_error error;
+
+ decode_at_error(&error, g_at_result_final_response(result));
+
+ if (ok && req->affected_types) {
+ GSList *l;
+ struct ofono_call *call;
+
+ for (l = vd->calls; l; l = l->next) {
+ call = l->data;
+
+ if (req->affected_types & (1 << call->status))
+ vd->local_release |= (1 << call->id);
+ }
+ }
+
+ req->cb(&error, req->data);
+}
+
+static void gemalto_call_common(const char *cmd, struct ofono_voicecall *vc,
+ GAtResultFunc result_cb, unsigned int affected_types,
+ ofono_voicecall_cb_t cb, void *data)
+{
+ struct voicecall_data *vd = ofono_voicecall_get_data(vc);
+ struct change_state_req *req = g_new0(struct change_state_req, 1);
+
+ req->vc = vc;
+ req->cb = cb;
+ req->data = data;
+ req->affected_types = affected_types;
+
+ if (g_at_chat_send(vd->chat, cmd, none_prefix,
+ result_cb, req, g_free) > 0)
+ return;
+
+ g_free(req);
+ CALLBACK_WITH_FAILURE(cb, data);
+}
+
+static void gemalto_answer(struct ofono_voicecall *vc,
+ ofono_voicecall_cb_t cb, void *data)
+{
+ gemalto_call_common("ATA", vc, generic_cb, 0, cb, data);
+}
+
+static void gemalto_hangup_all(struct ofono_voicecall *vc,
+ ofono_voicecall_cb_t cb, void *data)
+{
+ unsigned int affected = (1 << CALL_STATUS_INCOMING) |
+ (1 << CALL_STATUS_DIALING) |
+ (1 << CALL_STATUS_ALERTING) |
+ (1 << CALL_STATUS_WAITING) |
+ (1 << CALL_STATUS_HELD) |
+ (1 << CALL_STATUS_ACTIVE);
+
+ /* Hangup all calls */
+ gemalto_call_common("AT+CHUP", vc, generic_cb, affected, cb, data);
+}
+
+static void gemalto_hangup(struct ofono_voicecall *vc,
+ ofono_voicecall_cb_t cb, void *data)
+{
+ unsigned int affected = (1 << CALL_STATUS_ACTIVE);
+
+ /* Hangup current active call */
+ gemalto_call_common("AT+CHLD=1", vc, generic_cb, affected, cb, data);
+}
+
+static void gemalto_hold_all_active(struct ofono_voicecall *vc,
+ ofono_voicecall_cb_t cb, void *data)
+{
+ unsigned int affected = (1 << CALL_STATUS_ACTIVE);
+ gemalto_call_common("AT+CHLD=2", vc, generic_cb, affected, cb, data);
+}
+
+static void gemalto_release_all_held(struct ofono_voicecall *vc,
+ ofono_voicecall_cb_t cb, void *data)
+{
+ unsigned int affected = (1 << CALL_STATUS_INCOMING) |
+ (1 << CALL_STATUS_WAITING);
+
+ gemalto_call_common("AT+CHLD=0", vc, generic_cb, affected, cb, data);
+}
+
+static void gemalto_set_udub(struct ofono_voicecall *vc,
+ ofono_voicecall_cb_t cb, void *data)
+{
+ unsigned int affected = (1 << CALL_STATUS_INCOMING) |
+ (1 << CALL_STATUS_WAITING);
+
+ gemalto_call_common("AT+CHLD=0", vc, generic_cb, affected, cb, data);
+}
+
+static void gemalto_release_all_active(struct ofono_voicecall *vc,
+ ofono_voicecall_cb_t cb, void *data)
+{
+ unsigned int affected = (1 << CALL_STATUS_ACTIVE);
+
+ gemalto_call_common("AT+CHLD=1", vc, generic_cb, affected, cb, data);
+}
+
+static void release_id_cb(gboolean ok, GAtResult *result,
+ gpointer user_data)
+{
+ struct release_id_req *req = user_data;
+ struct voicecall_data *vd = ofono_voicecall_get_data(req->vc);
+ struct ofono_error error;
+
+ decode_at_error(&error, g_at_result_final_response(result));
+
+ if (ok)
+ vd->local_release = 1 << req->id;
+
+ req->cb(&error, req->data);
+}
+
+static void gemalto_release_specific(struct ofono_voicecall *vc, int id,
+ ofono_voicecall_cb_t cb, void *data)
+{
+ struct voicecall_data *vd = ofono_voicecall_get_data(vc);
+ struct release_id_req *req = g_new0(struct release_id_req, 1);
+ char buf[32];
+
+ req->vc = vc;
+ req->cb = cb;
+ req->data = data;
+ req->id = id;
+
+ snprintf(buf, sizeof(buf), "AT+CHLD=1%d", id);
+
+ if (g_at_chat_send(vd->chat, buf, none_prefix,
+ release_id_cb, req, g_free) > 0)
+ return;
+
+ g_free(req);
+ CALLBACK_WITH_FAILURE(cb, data);
+}
+
+static void gemalto_private_chat(struct ofono_voicecall *vc, int id,
+ ofono_voicecall_cb_t cb, void *data)
+{
+ char buf[32];
+
+ snprintf(buf, sizeof(buf), "AT+CHLD=2%d", id);
+ gemalto_call_common(buf, vc, generic_cb, 0, cb, data);
+}
+
+static void gemalto_create_multiparty(struct ofono_voicecall *vc,
+ ofono_voicecall_cb_t cb, void *data)
+{
+ gemalto_call_common("AT+CHLD=3", vc, generic_cb, 0, cb, data);
+}
+
+static void gemalto_transfer(struct ofono_voicecall *vc,
+ ofono_voicecall_cb_t cb, void *data)
+{
+ /* Held & Active */
+ unsigned int affected = (1 << CALL_STATUS_ACTIVE) |
+ (1 << CALL_STATUS_HELD);
+
+ /* Transfer can puts held & active calls together and disconnects
+ * from both. However, some networks support transferring of
+ * dialing/ringing calls as well.
+ */
+ affected |= (1 << CALL_STATUS_DIALING) |
+ (1 << CALL_STATUS_ALERTING);
+
+ gemalto_call_common("AT+CHLD=4", vc, generic_cb, affected, cb, data);
+}
+
+static void gemalto_send_dtmf(struct ofono_voicecall *vc, const char *dtmf,
+ ofono_voicecall_cb_t cb, void *data)
+{
+ int len = strlen(dtmf);
+ int s;
+ int i;
+ char *buf;
+ struct ofono_modem *modem = ofono_voicecall_get_modem(vc);
+ int use_quotes = ofono_modem_get_integer(modem, "GemaltoVtsQuotes");
+
+ /* strlen("+VTS=\"T\";") = 9 + initial AT + null */
+ buf = (char *)alloca(len * 9 + 3);
+
+ if (use_quotes)
+ s = sprintf(buf, "AT+VTS=\"%c\"", dtmf[0]);
+ else
+ s = sprintf(buf, "AT+VTS=%c", dtmf[0]);
+
+ for (i = 1; i < len; i++) {
+
+ if (use_quotes)
+ s += sprintf(buf + s, ";+VTS=\"%c\"", dtmf[i]);
+ else
+ s += sprintf(buf + s, ";+VTS=%c", dtmf[i]);
+ }
+
+ gemalto_call_common(buf, vc, generic_cb, 0, cb, data);
+}
+
+static void gemalto_dial(struct ofono_voicecall *vc,
+ const struct ofono_phone_number *ph,
+ enum ofono_clir_option clir, ofono_voicecall_cb_t cb,
+ void *data)
+{
+ struct cb_data *cbd = cb_data_new(cb, data);
+ char buf[256];
+ size_t len;
+
+ cbd->user = vc;
+
+ if (ph->type == 145)
+ len = snprintf(buf, sizeof(buf), "ATD+%s", ph->number);
+ else
+ len = snprintf(buf, sizeof(buf), "ATD%s", ph->number);
+
+ switch (clir) {
+ case OFONO_CLIR_OPTION_INVOCATION:
+ len += snprintf(buf+len, sizeof(buf)-len, "I");
+ break;
+ case OFONO_CLIR_OPTION_SUPPRESSION:
+ len += snprintf(buf+len, sizeof(buf)-len, "i");
+ break;
+ default:
+ break;
+ }
+
+ snprintf(buf+len, sizeof(buf)-len, ";");
+
+ gemalto_call_common(buf, vc, generic_cb, 0, cb, data);
+}
+
+static void gemalto_parse_slcc(GAtResult *result, GSList **l,
+ ofono_bool_t *ret_mpty, gboolean *last)
+{
+ GAtResultIter iter;
+ int id, dir, status, type;
+ ofono_bool_t mpty;
+ struct ofono_call *call;
+ const char *str = "";
+ int number_type = 129;
+
+ if (last)
+ *last = TRUE;
+
+ g_at_result_iter_init(&iter, result);
+
+ g_at_result_iter_next(&iter, "^SLCC:");
+
+ if (!g_at_result_iter_next_number(&iter, &id))
+ return;
+
+ if (last)
+ *last = FALSE;
+
+ if (id == 0)
+ return;
+
+ if (!g_at_result_iter_next_number(&iter, &dir))
+ return;
+
+ if (!g_at_result_iter_next_number(&iter, &status))
+ return;
+
+ if (status > 5)
+ return;
+
+ if (!g_at_result_iter_next_number(&iter, &type))
+ return;
+
+ if (!g_at_result_iter_next_number(&iter, &mpty))
+ return;
+
+ /* skip 'Reserved=0' parameter, only difference from CLCC */
+ if (!g_at_result_iter_skip_next(&iter))
+ return;
+
+ if (g_at_result_iter_next_string(&iter, &str))
+ g_at_result_iter_next_number(&iter, &number_type);
+
+ call = g_new0(struct ofono_call, 1);
+ ofono_call_init(call);
+ call->id = id;
+ call->direction = dir;
+ call->status = status;
+ call->type = type;
+ strncpy(call->phone_number.number, str,
+ OFONO_MAX_PHONE_NUMBER_LENGTH);
+ call->phone_number.type = number_type;
+
+ if (strlen(str) > 0)
+ call->clip_validity = 2;
+ else
+ call->clip_validity = 0;
+
+ *l = g_slist_insert_sorted(*l, call, at_util_call_compare);
+
+ if (ret_mpty)
+ *ret_mpty = mpty;
+
+}
+
+static void clcc_cb(gboolean ok, GAtResult *result, gpointer user_data)
+{
+ struct ofono_voicecall *vc = user_data;
+ struct voicecall_data *vd = ofono_voicecall_get_data(vc);
+ GSList *l;
+
+ if (!ok)
+ return;
+
+ vd->calls = at_util_parse_clcc(result, NULL);
+
+ for (l = vd->calls; l; l = l->next)
+ ofono_voicecall_notify(vc, l->data);
+}
+
+/*
+ * ^SLCC, except for one RFU parameter (see above in the parsing), is identical
+ * to +CLCC, but as URC it is parsed line by line, and the last line is
+ * indicated by an empty "^SLCC:" (equivalent to the "OK" for CLCC).
+ */
+static void slcc_notify(GAtResult *result, gpointer user_data)
+{
+ struct ofono_voicecall *vc = user_data;
+ struct voicecall_data *vd = ofono_voicecall_get_data(vc);
+ GSList *n, *o;
+ struct ofono_call *nc, *oc;
+ gboolean last;
+
+ gemalto_parse_slcc(result, &vd->new_calls, NULL, &last);
+
+ if (!last)
+ return;
+
+ n = vd->new_calls;
+ o = vd->calls;
+
+ while (n || o) {
+ nc = n ? n->data : NULL;
+ oc = o ? o->data : NULL;
+
+ if (oc && (nc == NULL || (nc->id > oc->id))) {
+ enum ofono_disconnect_reason reason;
+
+ if (vd->local_release & (1 << oc->id))
+ reason = OFONO_DISCONNECT_REASON_LOCAL_HANGUP;
+ else
+ reason = OFONO_DISCONNECT_REASON_REMOTE_HANGUP;
+
+ if (!oc->type)
+ ofono_voicecall_disconnected(vc, oc->id,
+ reason, NULL);
+
+ o = o->next;
+ } else if (nc && (oc == NULL || (nc->id < oc->id))) {
+
+ if (nc->type == 0) /* new call, signal it */
+ ofono_voicecall_notify(vc, nc);
+
+ n = n->next;
+ } else {
+
+ DBG("modify call part");
+
+ /* notify in case of changes */
+ if (memcmp(nc, oc, sizeof(*nc)))
+ ofono_voicecall_notify(vc, nc);
+
+ n = n->next;
+ o = o->next;
+ }
+ }
+
+ g_slist_free_full(vd->calls, g_free);
+ vd->calls = vd->new_calls;
+ vd->new_calls = NULL;
+ vd->local_release = 0;
+}
+
+static void cssi_notify(GAtResult *result, gpointer user_data)
+{
+ struct ofono_voicecall *vc = user_data;
+ GAtResultIter iter;
+ int code, index;
+
+ g_at_result_iter_init(&iter, result);
+
+ if (!g_at_result_iter_next(&iter, "+CSSI:"))
+ return;
+
+ if (!g_at_result_iter_next_number(&iter, &code))
+ return;
+
+ if (!g_at_result_iter_next_number(&iter, &index))
+ index = 0;
+
+ ofono_voicecall_ssn_mo_notify(vc, 0, code, index);
+}
+
+static void cssu_notify(GAtResult *result, gpointer user_data)
+{
+ struct ofono_voicecall *vc = user_data;
+ GAtResultIter iter;
+ int code;
+ int index;
+ const char *num;
+ struct ofono_phone_number ph;
+
+ ph.number[0] = '\0';
+ ph.type = 129;
+
+ g_at_result_iter_init(&iter, result);
+
+ if (!g_at_result_iter_next(&iter, "+CSSU:"))
+ return;
+
+ if (!g_at_result_iter_next_number(&iter, &code))
+ return;
+
+ if (!g_at_result_iter_next_number_default(&iter, -1, &index))
+ goto out;
+
+ if (!g_at_result_iter_next_string(&iter, &num))
+ goto out;
+
+ strncpy(ph.number, num, OFONO_MAX_PHONE_NUMBER_LENGTH);
+
+ if (!g_at_result_iter_next_number(&iter, &ph.type))
+ return;
+
+out:
+ ofono_voicecall_ssn_mt_notify(vc, 0, code, index, &ph);
+}
+
+static void gemalto_voicecall_initialized(gboolean ok, GAtResult *result,
+ gpointer user_data)
+{
+ struct ofono_voicecall *vc = user_data;
+ struct voicecall_data *vd = ofono_voicecall_get_data(vc);
+
+ DBG("voicecall_init: registering to notifications");
+
+ /* NO CARRIER, NO ANSWER, BUSY, NO DIALTONE are handled through SLCC */
+ g_at_chat_register(vd->chat, "^SLCC:", slcc_notify, FALSE, vc, NULL);
+ g_at_chat_register(vd->chat, "+CSSI:", cssi_notify, FALSE, vc, NULL);
+ g_at_chat_register(vd->chat, "+CSSU:", cssu_notify, FALSE, vc, NULL);
+
+ ofono_voicecall_register(vc);
+
+ /* Populate the call list */
+ g_at_chat_send(vd->chat, "AT+CLCC", clcc_prefix, clcc_cb, vc, NULL);
+}
+
+static int gemalto_voicecall_probe(struct ofono_voicecall *vc,
+ unsigned int vendor, void *data)
+{
+ GAtChat *chat = data;
+ struct voicecall_data *vd;
+
+ vd = g_new0(struct voicecall_data, 1);
+ vd->chat = g_at_chat_clone(chat);
+ ofono_voicecall_set_data(vc, vd);
+ g_at_chat_send(vd->chat, "AT+CSSN=1,1", NULL, NULL, NULL, NULL);
+ g_at_chat_send(vd->chat, "AT^SLCC=1", NULL,
+ gemalto_voicecall_initialized, vc, NULL);
+ return 0;
+}
+
+static void gemalto_voicecall_remove(struct ofono_voicecall *vc)
+{
+ struct voicecall_data *vd = ofono_voicecall_get_data(vc);
+
+ ofono_voicecall_set_data(vc, NULL);
+
+ g_at_chat_unref(vd->chat);
+ g_free(vd);
+}
+
+static const struct ofono_voicecall_driver driver = {
+ .name = "gemaltomodem",
+ .probe = gemalto_voicecall_probe,
+ .remove = gemalto_voicecall_remove,
+ .dial = gemalto_dial,
+ .answer = gemalto_answer,
+ .hangup_all = gemalto_hangup_all,
+ .hangup_active = gemalto_hangup,
+ .hold_all_active = gemalto_hold_all_active,
+ .release_all_held = gemalto_release_all_held,
+ .set_udub = gemalto_set_udub,
+ .release_all_active = gemalto_release_all_active,
+ .release_specific = gemalto_release_specific,
+ .private_chat = gemalto_private_chat,
+ .create_multiparty = gemalto_create_multiparty,
+ .transfer = gemalto_transfer,
+ .send_tones = gemalto_send_dtmf
+};
+
+void gemalto_voicecall_init(void)
+{
+ ofono_voicecall_driver_register(&driver);
+}
+
+void gemalto_voicecall_exit(void)
+{
+ ofono_voicecall_driver_unregister(&driver);
+}
--
2.17.1
^ permalink raw reply related [flat|nested] 6+ messages in thread
* [PATCH v2 2/2] plugins/gemalto: added voice support
2018-10-17 20:24 [PATCH v2 1/2] Gemalto: voicecall atom Giacinto Cifelli
@ 2018-10-17 20:24 ` Giacinto Cifelli
2018-10-17 22:04 ` [PATCH v2 1/2] Gemalto: voicecall atom Denis Kenzior
1 sibling, 0 replies; 6+ messages in thread
From: Giacinto Cifelli @ 2018-10-17 20:24 UTC (permalink / raw)
To: ofono
[-- Attachment #1: Type: text/plain, Size: 1744 bytes --]
The plugin for Gemalto modems is enriched with all voice-related atoms,
as well as USSD.
All except the voicecall itself are from the atmodem, while the
voicecall is from gemaltomodem.
---
plugins/gemalto.c | 12 ++++++++++++
1 file changed, 12 insertions(+)
diff --git a/plugins/gemalto.c b/plugins/gemalto.c
index 0fcf30d8..5d3c77a9 100644
--- a/plugins/gemalto.c
+++ b/plugins/gemalto.c
@@ -3,6 +3,7 @@
* oFono - Open Source Telephony
*
* Copyright (C) 2017 Vincent Cesson. All rights reserved.
+ * Copyright (C) 2018 Gemalto M2M
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -571,6 +572,10 @@ static void gemalto_pre_sim(struct ofono_modem *modem)
ofono_devinfo_create(modem, 0, "atmodem", data->app);
ofono_location_reporting_create(modem, 0, "gemaltomodem", data->app);
+
+ ofono_modem_set_integer(modem, "GemaltoVtsQuotes", 1);
+ ofono_voicecall_create(modem, 0, "gemaltomodem", data->app);
+
data->sim = ofono_sim_create(modem, OFONO_VENDOR_GEMALTO, "atmodem",
data->app);
@@ -597,6 +602,13 @@ static void gemalto_post_sim(struct ofono_modem *modem)
if (gprs && gc)
ofono_gprs_add_context(gprs, gc);
+ ofono_ussd_create(modem, 0, "atmodem", data->app);
+
+ ofono_call_forwarding_create(modem, 0, "atmodem", data->app);
+ ofono_call_settings_create(modem, 0, "atmodem", data->app);
+ ofono_call_meter_create(modem, 0, "atmodem", data->app);
+ ofono_call_barring_create(modem, 0, "atmodem", data->app);
+
if (!g_strcmp0(model, GEMALTO_MODEL_ALS3_PLS8x))
ofono_lte_create(modem, OFONO_VENDOR_CINTERION,
"atmodem", data->app);
--
2.17.1
^ permalink raw reply related [flat|nested] 6+ messages in thread
* Re: [PATCH v2 1/2] Gemalto: voicecall atom
2018-10-17 20:24 [PATCH v2 1/2] Gemalto: voicecall atom Giacinto Cifelli
2018-10-17 20:24 ` [PATCH v2 2/2] plugins/gemalto: added voice support Giacinto Cifelli
@ 2018-10-17 22:04 ` Denis Kenzior
1 sibling, 0 replies; 6+ messages in thread
From: Denis Kenzior @ 2018-10-17 22:04 UTC (permalink / raw)
To: ofono
[-- Attachment #1: Type: text/plain, Size: 795 bytes --]
On 10/17/2018 03:24 PM, Giacinto Cifelli wrote:
> Added voicecall atom specific for Gemalto modems.
> This atom uses the URC ^SLCC to monitor the call status, as well as
> incoming calls.
> Note the use in the atom of the variable GemaltoVtsQuotes: this is
> needed to support future modules, as of today not yet available in the
> plugin.
> ---
> Makefile.am | 3 +-
> drivers/gemaltomodem/gemaltomodem.c | 3 +
> drivers/gemaltomodem/gemaltomodem.h | 5 +
> drivers/gemaltomodem/voicecall.c | 578 ++++++++++++++++++++++++++++
> 4 files changed, 588 insertions(+), 1 deletion(-)
> create mode 100644 drivers/gemaltomodem/voicecall.c
>
I went ahead and applied both of these after cleaning up some style issues.
Regards,
-Denis
^ permalink raw reply [flat|nested] 6+ messages in thread
end of thread, other threads:[~2018-10-17 22:04 UTC | newest]
Thread overview: 6+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2018-10-17 20:24 [PATCH v2 1/2] Gemalto: voicecall atom Giacinto Cifelli
2018-10-17 20:24 ` [PATCH v2 2/2] plugins/gemalto: added voice support Giacinto Cifelli
2018-10-17 22:04 ` [PATCH v2 1/2] Gemalto: voicecall atom Denis Kenzior
-- strict thread matches above, loose matches on Subject: below --
2018-10-14 14:17 [PATCH v2 0/2] Gemalto: support for voicecall Giacinto Cifelli
2018-10-14 14:17 ` [PATCH v2 2/2] plugins/gemalto: added voice support Giacinto Cifelli
2018-10-14 16:50 ` Jonas Bonn
2018-10-14 17:03 ` Giacinto Cifelli
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox