From 8d8c6c94c06d4aba1d0f500d1a08735a3140b870 Mon Sep 17 00:00:00 2001 From: Grzegorz Sluja <grzegorz.sluja@iopsys.eu> Date: Wed, 5 Mar 2025 15:37:32 +0000 Subject: [PATCH] Handle hangup cause for ringing and callwt stop signals, REF 16384 The ringing and callwt stop signals received in voicemngr includes additional information sent by asterisk about the hangup cause. If the data=answered in mentioned signals then the call is answered by other extension connected to the same line to which incoming call was proceeded. Otherwise the signals are received with data=null what means it is a missed call. Handle it properly in voicemngr, sending the corresponding information to dectmngr about the reason of stop-ringing. --- libvoice/voice-types.h | 7 +++++++ line-dect.c | 1 + line.c | 14 +++++++++++--- line.h | 2 ++ ubus.c | 18 +++++++++++------- 5 files changed, 32 insertions(+), 10 deletions(-) diff --git a/libvoice/voice-types.h b/libvoice/voice-types.h index d246732..95f1ef3 100644 --- a/libvoice/voice-types.h +++ b/libvoice/voice-types.h @@ -73,6 +73,12 @@ typedef enum flash_spec { FLASH_SPEC_ETSI, } flash_spec; +// The possible values of DECTMNGR_RPC_PARAM_HANGUPCAUSE +enum hangup_cause { + HANGUPCAUSE_UNANSWERED = 0, + HANGUPCAUSE_ANSWERED_ELSEWERE, +}; + /* * UBUS related definitions */ @@ -84,5 +90,6 @@ typedef enum flash_spec { // Parameters #define DECTMNGR_RPC_PARAM_EXTENSION_ID "extension_id" #define DECTMNGR_RPC_PARAM_PCM_ID "pcm_id" +#define DECTMNGR_RPC_PARAM_HANGUPCAUSE "hangupcause" #endif diff --git a/line-dect.c b/line-dect.c index af839a8..3d9454b 100644 --- a/line-dect.c +++ b/line-dect.c @@ -131,6 +131,7 @@ int ubus_process_queued_reqs_to_dectmngr(void) { case ACTION_RINGING_STOP: dectmngr_rpc.action = req->action; dectmngr_rpc.extension_id = voicemngr_line_to_dectmngr_line(req->line); + dectmngr_rpc.params.hangupcause = req->hangupcause; if(ubus_dectmngr_rpc(&dectmngr_rpc, req)) { free(req); return -1; diff --git a/line.c b/line.c index 5cb2203..3784e53 100644 --- a/line.c +++ b/line.c @@ -156,9 +156,9 @@ static void setCallerName(const char *data, char *callerName) static int line_signal_ring(int line, int pcm, enum VOICE_SIGNAL signal, const char *data, struct voice_ubus_req_t *ubus_req) { struct line_req_t *line_req = NULL; - int start_ring = data && strcmp(data, "0") != 0; + int start_ring = data && strcmp(data, "0") != 0 && strcmp(data, "answered") != 0; - ENDPT_DBG("line=%d, pcm=%d, data=%s\n", line, pcm, data); + ENDPT_DBG("line=%d, pcm=%d, data=%s, start_ring: %d\n", line, pcm, data, start_ring); pcm_states_dump(__func__, line); // Relay the request to dectmngr if the line is DECT @@ -210,6 +210,10 @@ static int line_signal_ring(int line, int pcm, enum VOICE_SIGNAL signal, const c line_req->action = ACTION_SIG_RING; } else { line_req->action = ACTION_RINGING_STOP; + if (strcmp(data, "answered") == 0) + line_req->hangupcause = HANGUPCAUSE_ANSWERED_ELSEWERE; + else + line_req->hangupcause = HANGUPCAUSE_UNANSWERED; } line_req->caller_id[0] = 0; // Discard enable/disable char or it will become the caller ID } else { @@ -220,6 +224,10 @@ static int line_signal_ring(int line, int pcm, enum VOICE_SIGNAL signal, const c if(line_req) { if(!start_ring) { line_req->action = ACTION_RINGING_STOP; + if (strcmp(data, "answered") == 0) + line_req->hangupcause = HANGUPCAUSE_ANSWERED_ELSEWERE; + else + line_req->hangupcause = HANGUPCAUSE_UNANSWERED; } line_req->caller_id[0] = 0; // Discard enable/disable char or it will become the caller ID break; @@ -323,7 +331,7 @@ int line_signal(int line, const char *signame, const char *data, struct voice_ub res = line_signal_ring(line, get_callid_state(lines[line].pcm_callid[PCM_1]) == CALLID_INVALID ? PCM_1 : PCM_0, VOICE_SIG_CALLID, data, ubus_req); lines[line].signaled_call_waiting = 1; - } else if(data && (data[0] == '0')) { + } else if(data && ((data[0] == '0') || (strcmp(data, "answered") == 0))) { // stop call waiting when accepted but not close the connection on the accepted line res = line_signal_ring(line, get_callid_state(lines[line].pcm_callid[PCM_1]) == CALLID_OBTAINING ? PCM_1 : PCM_0, VOICE_SIG_CALL_WAITING, data, ubus_req); diff --git a/line.h b/line.h index 64a212d..7287c37 100644 --- a/line.h +++ b/line.h @@ -42,6 +42,7 @@ struct line_req_t { char caller_name[MAX_CALLER_NAME]; // Caller Name struct voice_ubus_req_t ubus; struct timespec time_stamp; + enum hangup_cause hangupcause; }; struct dectmngr_rpc_t { @@ -50,6 +51,7 @@ struct dectmngr_rpc_t { int pcm_id; union { // Action specific parameters will be added here + enum hangup_cause hangupcause; } params; }; diff --git a/ubus.c b/ubus.c index ce4f3cf..10c7d40 100644 --- a/ubus.c +++ b/ubus.c @@ -568,22 +568,24 @@ static int ubus_request_signal(struct ubus_context *uctx, struct ubus_object *ob } signame = blobmsg_get_string(keys[SIGNAL_TYPE]); - ENDPT_DBG("line=%d, signame=%s\n", line, signame); // on or off signal? enable = "0"; - data = NULL; state = blobmsg_get_string(keys[SIGNAL_STATE]); if (strcmp(state, "on") == 0) { enable = "1"; - // Do we have extra data that should be passed to endpoint? - if (keys[SIGNAL_DATA]) - data = blobmsg_get_string(keys[SIGNAL_DATA]); } else if (strcmp(state, "off")) { ENDPT_ERR("Error! invalid state %s\n", state); return UBUS_STATUS_INVALID_ARGUMENT; } + // Do we have extra data that should be passed to endpoint? + if (keys[SIGNAL_DATA]) + data = blobmsg_get_string(keys[SIGNAL_DATA]); + else + data = NULL; + + ENDPT_DBG("line=%d, signame=%s, state=%s, data=%s\n", line, signame, state, data?data:""); // Prepare for possibly deferring the request memset(&ubusReq, 0, sizeof(struct voice_ubus_req_t)); clock_gettime(CLOCK_MONOTONIC, &ubusReq.timeStamp); @@ -1205,9 +1207,11 @@ int ubus_dectmngr_rpc(const struct dectmngr_rpc_t *dectmngr_rpc, const struct li switch (dectmngr_rpc->action) { case ACTION_RINGING_STOP: blobmsg_add_u32(&bb, DECTMNGR_RPC_PARAM_EXTENSION_ID, dectmngr_rpc->extension_id); + blobmsg_add_u32(&bb, DECTMNGR_RPC_PARAM_HANGUPCAUSE, dectmngr_rpc->params.hangupcause); res = ubus_invoke_async(ctx, dectmngr_rpc_id, DECTMNGR_RPC_RINGING_STOP, bb.head, req); - ENDPT_DBG("Invoke ubus call %s %s {'%s':%d}\n", DECTMNGR_RPC_UBUS_OBJECT, DECTMNGR_RPC_RINGING_STOP, - DECTMNGR_RPC_PARAM_EXTENSION_ID, dectmngr_rpc->extension_id); + ENDPT_DBG("Invoke ubus call %s %s {'%s':%d,'%s':%d}\n", DECTMNGR_RPC_UBUS_OBJECT, DECTMNGR_RPC_RINGING_STOP, + DECTMNGR_RPC_PARAM_EXTENSION_ID, dectmngr_rpc->extension_id, + DECTMNGR_RPC_PARAM_HANGUPCAUSE, dectmngr_rpc->params.hangupcause); break; case ACTION_CONN_CLOSE: -- GitLab