[Asterisk-code-review] chan dahdi.c: Flush the DAHDI write buffer after starting DTMF. (asterisk[certified/13.1])

Mark Michelson asteriskteam at digium.com
Wed Aug 12 13:37:36 CDT 2015


Mark Michelson has submitted this change and it was merged.

Change subject: chan_dahdi.c: Flush the DAHDI write buffer after starting DTMF.
......................................................................


chan_dahdi.c: Flush the DAHDI write buffer after starting DTMF.

Pressing DTMF digits on a phone to go out on a DAHDI channel can result in
the digit not being recognized or even heard by the peer.

Phone -> Asterisk -> DAHDI/channel

Turns out the DAHDI behavior with DTMF generation (and any other generated
tones) is exposed by the "buffers=" setting in chan_dahdi.conf.  When
Asterisk requests to start sending DTMF then DAHDI waits until its write
buffer is empty before generating any samples for the DTMF tones.  When
Asterisk subsequently requests DAHDI to stop sending DTMF then DAHDI
immediately stops generating the DTMF samples.  As a result, the more
samples there are in the DAHDI write buffer the shorter the time DTMF
actually gets sent on the wire.  If there are more samples in the write
buffer than the time DTMF is supposed to be sent then no DTMF gets sent on
the wire.  With the "buffers=12,half" setting and each buffer representing
20 ms of samples then the DAHDI write buffer is going to contain around
120 ms of samples.  For DTMF to be recognized by the peer the actual sent
DTMF duration needs to be a minimum of 40 ms.  Therefore, the intended
duration needs to be a minimum of 160 ms for the peer to receive the
minimum DTMF digit duration to recognize it.

A simple and effective solution to work around the DAHDI behavior is for
Asterisk to flush the DAHDI write buffer when sending DTMF so the full
duration of DTMF is actually sent on the wire.  When someone is going to
send DTMF they are not likely to be talking before sending the tones so
the flushed write samples are expected to just contain silence.

* Made dahdi_digit_begin() flush the DAHDI write buffer after requesting
to send a DTMF digit.

ASTERISK-25315 #close
Reported by John Hardin

Change-Id: Ib56262c708cb7858082156bfc70ebd0a220efa6a
---
M channels/chan_dahdi.c
1 file changed, 16 insertions(+), 4 deletions(-)

Approvals:
  Mark Michelson: Looks good to me, approved
  Anonymous Coward #1000019: Verified
  Joshua Colp: Looks good to me, but someone else must approve



diff --git a/channels/chan_dahdi.c b/channels/chan_dahdi.c
index dbf3de9..6985303 100644
--- a/channels/chan_dahdi.c
+++ b/channels/chan_dahdi.c
@@ -4198,7 +4198,7 @@
 {
 	struct dahdi_pvt *pvt;
 	int idx;
-	int dtmf = -1;
+	int dtmf;
 	int res;
 
 	pvt = ast_channel_tech_pvt(chan);
@@ -4221,8 +4221,11 @@
 		break;
 	}
 #endif
-	if ((dtmf = digit_to_dtmfindex(digit)) == -1)
+	dtmf = digit_to_dtmfindex(digit);
+	if (dtmf == -1) {
+		/* Not a valid DTMF digit */
 		goto out;
+	}
 
 	if (pvt->pulse || ioctl(pvt->subs[SUB_REAL].dfd, DAHDI_SENDTONE, &dtmf)) {
 		char dial_str[] = { 'T', digit, '\0' };
@@ -4232,10 +4235,19 @@
 			pvt->dialing = 1;
 		}
 	} else {
-		ast_debug(1, "Channel %s started VLDTMF digit '%c'\n",
-			ast_channel_name(chan), digit);
 		pvt->dialing = 1;
 		pvt->begindigit = digit;
+
+		/* Flush the write buffer in DAHDI to start sending the digit immediately. */
+		dtmf = DAHDI_FLUSH_WRITE;
+		res = ioctl(pvt->subs[SUB_REAL].dfd, DAHDI_FLUSH, &dtmf);
+		if (res) {
+			ast_log(LOG_WARNING, "Unable to flush the DAHDI write buffer to send DTMF on channel %d: %s\n",
+				pvt->channel, strerror(errno));
+		}
+
+		ast_debug(1, "Channel %s started VLDTMF digit '%c'\n",
+			ast_channel_name(chan), digit);
 	}
 
 out:

-- 
To view, visit https://gerrit.asterisk.org/1068
To unsubscribe, visit https://gerrit.asterisk.org/settings

Gerrit-MessageType: merged
Gerrit-Change-Id: Ib56262c708cb7858082156bfc70ebd0a220efa6a
Gerrit-PatchSet: 1
Gerrit-Project: asterisk
Gerrit-Branch: certified/13.1
Gerrit-Owner: Richard Mudgett <rmudgett at digium.com>
Gerrit-Reviewer: Anonymous Coward #1000019
Gerrit-Reviewer: Joshua Colp <jcolp at digium.com>
Gerrit-Reviewer: Mark Michelson <mmichelson at digium.com>



More information about the asterisk-code-review mailing list