ARI POST DTMF: Make not compete with channel's media thread.

There can be one and only one thread handling a channel's media at a time.
Otherwise, we don't know which thread is going to handle the media frames.

ASTERISK-27625

Change-Id: I4d6a2fe7386ea447ee199003bf8ad681cb30454e
This commit is contained in:
Richard Mudgett
2018-06-13 16:41:43 -05:00
parent 7d874c1af7
commit da54605b8a
3 changed files with 115 additions and 34 deletions

View File

@@ -873,25 +873,37 @@ int ast_vm_test_destroy_user(const char *context, const char *mailbox)
}
#endif
int ast_dtmf_stream(struct ast_channel *chan, struct ast_channel *peer, const char *digits, int between, unsigned int duration)
static int external_sleep(struct ast_channel *chan, int ms)
{
usleep(ms * 1000);
return 0;
}
static int dtmf_stream(struct ast_channel *chan, const char *digits, int between, unsigned int duration, int is_external)
{
const char *ptr;
int res;
struct ast_silence_generator *silgen = NULL;
int (*my_sleep)(struct ast_channel *chan, int ms);
int (*my_senddigit)(struct ast_channel *chan, char digit, unsigned int duration);
if (is_external) {
my_sleep = external_sleep;
my_senddigit = ast_senddigit_external;
} else {
my_sleep = ast_safe_sleep;
my_senddigit = ast_senddigit;
}
if (!between) {
between = 100;
}
if (peer && ast_autoservice_start(peer)) {
return -1;
}
/* Need a quiet time before sending digits. */
if (ast_opt_transmit_silence) {
silgen = ast_channel_start_silence_generator(chan);
}
res = ast_safe_sleep(chan, 100);
res = my_sleep(chan, 100);
if (res) {
goto dtmf_stream_cleanup;
}
@@ -899,12 +911,14 @@ int ast_dtmf_stream(struct ast_channel *chan, struct ast_channel *peer, const ch
for (ptr = digits; *ptr; ptr++) {
if (*ptr == 'w') {
/* 'w' -- wait half a second */
if ((res = ast_safe_sleep(chan, 500))) {
res = my_sleep(chan, 500);
if (res) {
break;
}
} else if (*ptr == 'W') {
/* 'W' -- wait a second */
if ((res = ast_safe_sleep(chan, 1000))) {
res = my_sleep(chan, 1000);
if (res) {
break;
}
} else if (strchr("0123456789*#abcdfABCDF", *ptr)) {
@@ -913,10 +927,11 @@ int ast_dtmf_stream(struct ast_channel *chan, struct ast_channel *peer, const ch
ast_indicate(chan, AST_CONTROL_FLASH);
} else {
/* Character represents valid DTMF */
ast_senddigit(chan, *ptr, duration);
my_senddigit(chan, *ptr, duration);
}
/* pause between digits */
if ((res = ast_safe_sleep(chan, between))) {
res = my_sleep(chan, between);
if (res) {
break;
}
} else {
@@ -928,6 +943,18 @@ dtmf_stream_cleanup:
if (silgen) {
ast_channel_stop_silence_generator(chan, silgen);
}
return res;
}
int ast_dtmf_stream(struct ast_channel *chan, struct ast_channel *peer, const char *digits, int between, unsigned int duration)
{
int res;
if (peer && ast_autoservice_start(peer)) {
return -1;
}
res = dtmf_stream(chan, digits, between, duration, 0);
if (peer && ast_autoservice_stop(peer)) {
res = -1;
}
@@ -935,6 +962,11 @@ dtmf_stream_cleanup:
return res;
}
void ast_dtmf_stream_external(struct ast_channel *chan, const char *digits, int between, unsigned int duration)
{
dtmf_stream(chan, digits, between, duration, 1);
}
struct linear_state {
int fd;
int autoclose;