summaryrefslogtreecommitdiff
path: root/channels
diff options
context:
space:
mode:
Diffstat (limited to 'channels')
-rw-r--r--channels/chan_dahdi.c34
-rw-r--r--channels/sig_analog.c33
2 files changed, 44 insertions, 23 deletions
diff --git a/channels/chan_dahdi.c b/channels/chan_dahdi.c
index f0d4ad18a..27683170e 100644
--- a/channels/chan_dahdi.c
+++ b/channels/chan_dahdi.c
@@ -9700,14 +9700,25 @@ static void *analog_ss_thread(void *data)
if (p->cid_signalling == CID_SIG_DTMF) {
int k = 0;
cs = NULL;
- ast_debug(1, "Receiving DTMF cid on "
- "channel %s\n", chan->name);
+ ast_debug(1, "Receiving DTMF cid on channel %s\n", chan->name);
dahdi_setlinear(p->subs[idx].dfd, 0);
- res = 2000;
+ /*
+ * We are the only party interested in the Rx stream since
+ * we have not answered yet. We don't need or even want DTMF
+ * emulation. The DTMF digits can come so fast that emulation
+ * can drop some of them.
+ */
+ ast_set_flag(chan, AST_FLAG_END_DTMF_ONLY);
+ res = 4000;/* This is a typical OFF time between rings. */
for (;;) {
struct ast_frame *f;
res = ast_waitfor(chan, res);
if (res <= 0) {
+ /*
+ * We do not need to restore the dahdi_setlinear()
+ * or AST_FLAG_END_DTMF_ONLY flag settings since we
+ * are hanging up the channel.
+ */
ast_log(LOG_WARNING, "DTMFCID timed out waiting for ring. "
"Exiting simple switch\n");
ast_hangup(chan);
@@ -9717,22 +9728,24 @@ static void *analog_ss_thread(void *data)
if (!f)
break;
if (f->frametype == AST_FRAME_DTMF) {
- dtmfbuf[k++] = f->subclass.integer;
+ if (k < ARRAY_LEN(dtmfbuf) - 1) {
+ dtmfbuf[k++] = f->subclass.integer;
+ }
ast_debug(1, "CID got digit '%c'\n", f->subclass.integer);
- res = 2000;
+ res = 4000;/* This is a typical OFF time between rings. */
}
ast_frfree(f);
if (chan->_state == AST_STATE_RING ||
chan->_state == AST_STATE_RINGING)
break; /* Got ring */
}
+ ast_clear_flag(chan, AST_FLAG_END_DTMF_ONLY);
dtmfbuf[k] = '\0';
dahdi_setlinear(p->subs[idx].dfd, p->subs[idx].linear);
/* Got cid and ring. */
ast_debug(1, "CID got string '%s'\n", dtmfbuf);
callerid_get_dtmf(dtmfbuf, dtmfcid, &flags);
- ast_debug(1, "CID is '%s', flags %d\n",
- dtmfcid, flags);
+ ast_debug(1, "CID is '%s', flags %d\n", dtmfcid, flags);
/* If first byte is NULL, we have no cid */
if (!ast_strlen_zero(dtmfcid))
number = dtmfcid;
@@ -9815,13 +9828,10 @@ static void *analog_ss_thread(void *data)
if (p->cid_signalling == CID_SIG_V23_JP) {
res = dahdi_set_hook(p->subs[SUB_REAL].dfd, DAHDI_ONHOOK);
usleep(1);
- res = 4000;
- } else {
-
- /* Finished with Caller*ID, now wait for a ring to make sure there really is a call coming */
- res = 2000;
}
+ /* Finished with Caller*ID, now wait for a ring to make sure there really is a call coming */
+ res = 4000;/* This is a typical OFF time between rings. */
for (;;) {
struct ast_frame *f;
res = ast_waitfor(chan, res);
diff --git a/channels/sig_analog.c b/channels/sig_analog.c
index f8b1ede45..34935ef33 100644
--- a/channels/sig_analog.c
+++ b/channels/sig_analog.c
@@ -2119,16 +2119,27 @@ static void *__analog_ss_thread(void *data)
int i = 0;
int oldlinearity;
cs = NULL;
- ast_debug(1, "Receiving DTMF cid on "
- "channel %s\n", chan->name);
+ ast_debug(1, "Receiving DTMF cid on channel %s\n", chan->name);
oldlinearity = analog_set_linear_mode(p, index, 0);
- res = 2000;
+ /*
+ * We are the only party interested in the Rx stream since
+ * we have not answered yet. We don't need or even want DTMF
+ * emulation. The DTMF digits can come so fast that emulation
+ * can drop some of them.
+ */
+ ast_set_flag(chan, AST_FLAG_END_DTMF_ONLY);
+ res = 4000;/* This is a typical OFF time between rings. */
for (;;) {
struct ast_frame *f;
res = ast_waitfor(chan, res);
if (res <= 0) {
+ /*
+ * We do not need to restore the analog_set_linear_mode()
+ * or AST_FLAG_END_DTMF_ONLY flag settings since we
+ * are hanging up the channel.
+ */
ast_log(LOG_WARNING, "DTMFCID timed out waiting for ring. "
"Exiting simple switch\n");
ast_hangup(chan);
@@ -2138,15 +2149,18 @@ static void *__analog_ss_thread(void *data)
break;
}
if (f->frametype == AST_FRAME_DTMF) {
- dtmfbuf[i++] = f->subclass.integer;
+ if (i < ARRAY_LEN(dtmfbuf) - 1) {
+ dtmfbuf[i++] = f->subclass.integer;
+ }
ast_debug(1, "CID got digit '%c'\n", f->subclass.integer);
- res = 2000;
+ res = 4000;/* This is a typical OFF time between rings. */
}
ast_frfree(f);
if (chan->_state == AST_STATE_RING || chan->_state == AST_STATE_RINGING) {
break; /* Got ring */
}
}
+ ast_clear_flag(chan, AST_FLAG_END_DTMF_ONLY);
dtmfbuf[i] = '\0';
analog_set_linear_mode(p, index, oldlinearity);
@@ -2154,8 +2168,7 @@ static void *__analog_ss_thread(void *data)
/* Got cid and ring. */
ast_debug(1, "CID got string '%s'\n", dtmfbuf);
callerid_get_dtmf(dtmfbuf, dtmfcid, &flags);
- ast_debug(1, "CID is '%s', flags %d\n",
- dtmfcid, flags);
+ ast_debug(1, "CID is '%s', flags %d\n", dtmfcid, flags);
/* If first byte is NULL, we have no cid */
if (!ast_strlen_zero(dtmfcid)) {
number = dtmfcid;
@@ -2207,12 +2220,10 @@ static void *__analog_ss_thread(void *data)
if (p->cid_signalling == CID_SIG_V23_JP) {
res = analog_on_hook(p);
usleep(1);
- res = 4000;
- } else {
- /* Finished with Caller*ID, now wait for a ring to make sure there really is a call coming */
- res = 2000;
}
+ /* Finished with Caller*ID, now wait for a ring to make sure there really is a call coming */
+ res = 4000;/* This is a typical OFF time between rings. */
for (;;) {
struct ast_frame *f;
res = ast_waitfor(chan, res);