mirror of
https://github.com/asterisk/asterisk.git
synced 2025-09-05 12:16:00 +00:00
(closes issue #11825)
Reported by: ctooley Patches: additional_eivr_commands.patch uploaded by ctooley (license 136) Tested by: ctooley git-svn-id: https://origsvn.digium.com/svn/asterisk/trunk@103662 65c4cc65-6c06-0410-ace0-fbb531ad65f3
This commit is contained in:
@@ -85,7 +85,11 @@ struct gen_state {
|
||||
int sample_queue;
|
||||
};
|
||||
|
||||
static void send_child_event(FILE *handle, const char event, const char *data,
|
||||
static int eivr_comm(struct ast_channel *chan, struct ivr_localuser *u,
|
||||
int eivr_events_fd, int eivr_commands_fd, int eivr_errors_fd,
|
||||
const char *args);
|
||||
|
||||
static void send_eivr_event(FILE *handle, const char event, const char *data,
|
||||
const struct ast_channel *chan)
|
||||
{
|
||||
char tmp[256];
|
||||
@@ -222,6 +226,69 @@ static struct ast_generator gen =
|
||||
generate: gen_generate,
|
||||
};
|
||||
|
||||
static void ast_eivr_getvariable(struct ast_channel *chan, char *data, char *outbuf, int outbuflen)
|
||||
{
|
||||
// original input data: "G,var1,var2,"
|
||||
// data passed as "data": "var1,var2"
|
||||
char *inbuf, *variable;
|
||||
|
||||
const char *value;
|
||||
char *saveptr;
|
||||
int j;
|
||||
|
||||
outbuf[0] = 0;
|
||||
|
||||
for (j = 1, inbuf = data; ; j++, inbuf = NULL) {
|
||||
variable = strtok_r(inbuf, ",", &saveptr);
|
||||
if (variable == NULL) {
|
||||
int outstrlen = strlen(outbuf);
|
||||
if(outstrlen && outbuf[outstrlen - 1] == ',') {
|
||||
outbuf[outstrlen - 1] = 0;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
value = pbx_builtin_getvar_helper(chan, variable);
|
||||
if(!value)
|
||||
value = "";
|
||||
strncat(outbuf,variable,outbuflen);
|
||||
strncat(outbuf,"=",outbuflen);
|
||||
strncat(outbuf,value,outbuflen);
|
||||
strncat(outbuf,",",outbuflen);
|
||||
}
|
||||
};
|
||||
|
||||
static void ast_eivr_setvariable(struct ast_channel *chan, char *data)
|
||||
{
|
||||
char buf[1024];
|
||||
char *value;
|
||||
|
||||
char *inbuf, *variable;
|
||||
|
||||
char *saveptr;
|
||||
int j;
|
||||
|
||||
for(j=1, inbuf=data; ; j++, inbuf=NULL) {
|
||||
variable = strtok_r(inbuf, ",", &saveptr);
|
||||
ast_chan_log(LOG_DEBUG, chan, "Setting up a variable: %s\n", variable);
|
||||
if(variable) {
|
||||
//variable contains "varname=value"
|
||||
strncpy(buf, variable, sizeof(buf));
|
||||
value = strchr(buf, '=');
|
||||
if(!value)
|
||||
value="";
|
||||
else {
|
||||
value[0] = 0;
|
||||
value++;
|
||||
}
|
||||
pbx_builtin_setvar_helper(chan, buf, value);
|
||||
}
|
||||
else break;
|
||||
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
static struct playlist_entry *make_entry(const char *filename)
|
||||
{
|
||||
struct playlist_entry *entry;
|
||||
@@ -243,10 +310,7 @@ static int app_exec(struct ast_channel *chan, void *data)
|
||||
int res = -1;
|
||||
int gen_active = 0;
|
||||
int pid;
|
||||
char *buf, *command;
|
||||
FILE *child_commands = NULL;
|
||||
FILE *child_errors = NULL;
|
||||
FILE *child_events = NULL;
|
||||
char *buf, *pipe_delim_argbuf, *pdargbuf_ptr;
|
||||
struct ivr_localuser foo = {
|
||||
.playlist = AST_LIST_HEAD_INIT_VALUE,
|
||||
.finishlist = AST_LIST_HEAD_INIT_VALUE,
|
||||
@@ -271,25 +335,26 @@ static int app_exec(struct ast_channel *chan, void *data)
|
||||
buf = ast_strdupa(data);
|
||||
AST_STANDARD_APP_ARGS(args, buf);
|
||||
|
||||
//copy args and replace commas with pipes
|
||||
pipe_delim_argbuf = ast_strdupa(data);
|
||||
while((pdargbuf_ptr = strchr(pipe_delim_argbuf, ',')) != NULL)
|
||||
pdargbuf_ptr[0] = '|';
|
||||
|
||||
if (pipe(child_stdin)) {
|
||||
ast_chan_log(LOG_WARNING, chan, "Could not create pipe for child input: %s\n", strerror(errno));
|
||||
goto exit;
|
||||
}
|
||||
|
||||
if (pipe(child_stdout)) {
|
||||
ast_chan_log(LOG_WARNING, chan, "Could not create pipe for child output: %s\n", strerror(errno));
|
||||
goto exit;
|
||||
}
|
||||
|
||||
if (pipe(child_stderr)) {
|
||||
ast_chan_log(LOG_WARNING, chan, "Could not create pipe for child errors: %s\n", strerror(errno));
|
||||
goto exit;
|
||||
}
|
||||
|
||||
if (chan->_state != AST_STATE_UP) {
|
||||
ast_answer(chan);
|
||||
}
|
||||
|
||||
if (ast_activate_generator(chan, &gen, u) < 0) {
|
||||
ast_chan_log(LOG_WARNING, chan, "Failed to activate generator\n");
|
||||
goto exit;
|
||||
@@ -322,17 +387,6 @@ static int app_exec(struct ast_channel *chan, void *data)
|
||||
_exit(1);
|
||||
} else {
|
||||
/* parent process */
|
||||
int child_events_fd = child_stdin[1];
|
||||
int child_commands_fd = child_stdout[0];
|
||||
int child_errors_fd = child_stderr[0];
|
||||
struct ast_frame *f;
|
||||
int ms;
|
||||
int exception;
|
||||
int ready_fd;
|
||||
int waitfds[2] = { child_errors_fd, child_commands_fd };
|
||||
struct ast_channel *rchan;
|
||||
|
||||
pthread_sigmask(SIG_SETMASK, &oldset, NULL);
|
||||
|
||||
close(child_stdin[0]);
|
||||
child_stdin[0] = 0;
|
||||
@@ -340,228 +394,263 @@ static int app_exec(struct ast_channel *chan, void *data)
|
||||
child_stdout[1] = 0;
|
||||
close(child_stderr[1]);
|
||||
child_stderr[1] = 0;
|
||||
res = eivr_comm(chan, u, child_stdin[1], child_stdout[0], child_stderr[0], pipe_delim_argbuf);
|
||||
|
||||
if (!(child_events = fdopen(child_events_fd, "w"))) {
|
||||
ast_chan_log(LOG_WARNING, chan, "Could not open stream for child events\n");
|
||||
goto exit;
|
||||
}
|
||||
exit:
|
||||
if (gen_active)
|
||||
ast_deactivate_generator(chan);
|
||||
|
||||
if (!(child_commands = fdopen(child_commands_fd, "r"))) {
|
||||
ast_chan_log(LOG_WARNING, chan, "Could not open stream for child commands\n");
|
||||
goto exit;
|
||||
}
|
||||
if (child_stdin[0])
|
||||
close(child_stdin[0]);
|
||||
|
||||
if (!(child_errors = fdopen(child_errors_fd, "r"))) {
|
||||
ast_chan_log(LOG_WARNING, chan, "Could not open stream for child errors\n");
|
||||
goto exit;
|
||||
}
|
||||
if (child_stdin[1])
|
||||
close(child_stdin[1]);
|
||||
|
||||
setvbuf(child_events, NULL, _IONBF, 0);
|
||||
setvbuf(child_commands, NULL, _IONBF, 0);
|
||||
setvbuf(child_errors, NULL, _IONBF, 0);
|
||||
if (child_stdout[0])
|
||||
close(child_stdout[0]);
|
||||
|
||||
res = 0;
|
||||
if (child_stdout[1])
|
||||
close(child_stdout[1]);
|
||||
|
||||
while (1) {
|
||||
if (ast_test_flag(chan, AST_FLAG_ZOMBIE)) {
|
||||
ast_chan_log(LOG_NOTICE, chan, "Is a zombie\n");
|
||||
res = -1;
|
||||
break;
|
||||
}
|
||||
if (child_stderr[0])
|
||||
close(child_stderr[0]);
|
||||
|
||||
if (ast_check_hangup(chan)) {
|
||||
ast_chan_log(LOG_NOTICE, chan, "Got check_hangup\n");
|
||||
send_child_event(child_events, 'H', NULL, chan);
|
||||
res = -1;
|
||||
break;
|
||||
}
|
||||
if (child_stderr[1])
|
||||
close(child_stderr[1]);
|
||||
|
||||
ready_fd = 0;
|
||||
ms = 100;
|
||||
errno = 0;
|
||||
exception = 0;
|
||||
while ((entry = AST_LIST_REMOVE_HEAD(&u->playlist, list)))
|
||||
ast_free(entry);
|
||||
|
||||
rchan = ast_waitfor_nandfds(&chan, 1, waitfds, 2, &exception, &ready_fd, &ms);
|
||||
|
||||
if (!AST_LIST_EMPTY(&u->finishlist)) {
|
||||
AST_LIST_LOCK(&u->finishlist);
|
||||
while ((entry = AST_LIST_REMOVE_HEAD(&u->finishlist, list))) {
|
||||
send_child_event(child_events, 'F', entry->filename, chan);
|
||||
ast_free(entry);
|
||||
}
|
||||
AST_LIST_UNLOCK(&u->finishlist);
|
||||
}
|
||||
|
||||
if (rchan) {
|
||||
/* the channel has something */
|
||||
f = ast_read(chan);
|
||||
if (!f) {
|
||||
ast_chan_log(LOG_NOTICE, chan, "Returned no frame\n");
|
||||
send_child_event(child_events, 'H', NULL, chan);
|
||||
res = -1;
|
||||
break;
|
||||
}
|
||||
|
||||
if (f->frametype == AST_FRAME_DTMF) {
|
||||
send_child_event(child_events, f->subclass, NULL, chan);
|
||||
if (u->option_autoclear) {
|
||||
if (!u->abort_current_sound && !u->playing_silence)
|
||||
send_child_event(child_events, 'T', NULL, chan);
|
||||
AST_LIST_LOCK(&u->playlist);
|
||||
while ((entry = AST_LIST_REMOVE_HEAD(&u->playlist, list))) {
|
||||
send_child_event(child_events, 'D', entry->filename, chan);
|
||||
ast_free(entry);
|
||||
}
|
||||
if (!u->playing_silence)
|
||||
u->abort_current_sound = 1;
|
||||
AST_LIST_UNLOCK(&u->playlist);
|
||||
}
|
||||
} else if ((f->frametype == AST_FRAME_CONTROL) && (f->subclass == AST_CONTROL_HANGUP)) {
|
||||
ast_chan_log(LOG_NOTICE, chan, "Got AST_CONTROL_HANGUP\n");
|
||||
send_child_event(child_events, 'H', NULL, chan);
|
||||
ast_frfree(f);
|
||||
res = -1;
|
||||
break;
|
||||
}
|
||||
ast_frfree(f);
|
||||
} else if (ready_fd == child_commands_fd) {
|
||||
char input[1024];
|
||||
|
||||
if (exception || feof(child_commands)) {
|
||||
ast_chan_log(LOG_WARNING, chan, "Child process went away\n");
|
||||
res = -1;
|
||||
break;
|
||||
}
|
||||
|
||||
if (!fgets(input, sizeof(input), child_commands))
|
||||
continue;
|
||||
|
||||
command = ast_strip(input);
|
||||
|
||||
if (option_debug)
|
||||
ast_chan_log(LOG_DEBUG, chan, "got command '%s'\n", input);
|
||||
|
||||
if (strlen(input) < 4)
|
||||
continue;
|
||||
|
||||
if (input[0] == 'S') {
|
||||
if (ast_fileexists(&input[2], NULL, u->chan->language) == -1) {
|
||||
ast_chan_log(LOG_WARNING, chan, "Unknown file requested '%s'\n", &input[2]);
|
||||
send_child_event(child_events, 'Z', NULL, chan);
|
||||
strcpy(&input[2], "exception");
|
||||
}
|
||||
if (!u->abort_current_sound && !u->playing_silence)
|
||||
send_child_event(child_events, 'T', NULL, chan);
|
||||
AST_LIST_LOCK(&u->playlist);
|
||||
while ((entry = AST_LIST_REMOVE_HEAD(&u->playlist, list))) {
|
||||
send_child_event(child_events, 'D', entry->filename, chan);
|
||||
ast_free(entry);
|
||||
}
|
||||
if (!u->playing_silence)
|
||||
u->abort_current_sound = 1;
|
||||
entry = make_entry(&input[2]);
|
||||
if (entry)
|
||||
AST_LIST_INSERT_TAIL(&u->playlist, entry, list);
|
||||
AST_LIST_UNLOCK(&u->playlist);
|
||||
} else if (input[0] == 'A') {
|
||||
if (ast_fileexists(&input[2], NULL, u->chan->language) == -1) {
|
||||
ast_chan_log(LOG_WARNING, chan, "Unknown file requested '%s'\n", &input[2]);
|
||||
send_child_event(child_events, 'Z', NULL, chan);
|
||||
strcpy(&input[2], "exception");
|
||||
}
|
||||
entry = make_entry(&input[2]);
|
||||
if (entry) {
|
||||
AST_LIST_LOCK(&u->playlist);
|
||||
AST_LIST_INSERT_TAIL(&u->playlist, entry, list);
|
||||
AST_LIST_UNLOCK(&u->playlist);
|
||||
}
|
||||
} else if (input[0] == 'E') {
|
||||
ast_chan_log(LOG_NOTICE, chan, "Exiting: %s\n", &input[2]);
|
||||
send_child_event(child_events, 'E', NULL, chan);
|
||||
res = 0;
|
||||
break;
|
||||
} else if (input[0] == 'H') {
|
||||
ast_chan_log(LOG_NOTICE, chan, "Hanging up: %s\n", &input[2]);
|
||||
send_child_event(child_events, 'H', NULL, chan);
|
||||
res = -1;
|
||||
break;
|
||||
} else if (input[0] == 'O') {
|
||||
if (!strcasecmp(&input[2], "autoclear"))
|
||||
u->option_autoclear = 1;
|
||||
else if (!strcasecmp(&input[2], "noautoclear"))
|
||||
u->option_autoclear = 0;
|
||||
else
|
||||
ast_chan_log(LOG_WARNING, chan, "Unknown option requested '%s'\n", &input[2]);
|
||||
} else if (input[0] == 'V') {
|
||||
char *c;
|
||||
c = strchr(&input[2], '=');
|
||||
if (!c) {
|
||||
send_child_event(child_events, 'Z', NULL, chan);
|
||||
} else {
|
||||
*c++ = '\0';
|
||||
pbx_builtin_setvar_helper(chan, &input[2], c);
|
||||
}
|
||||
}
|
||||
} else if (ready_fd == child_errors_fd) {
|
||||
char input[1024];
|
||||
|
||||
if (exception || feof(child_errors)) {
|
||||
ast_chan_log(LOG_WARNING, chan, "Child process went away\n");
|
||||
res = -1;
|
||||
break;
|
||||
}
|
||||
|
||||
if (fgets(input, sizeof(input), child_errors)) {
|
||||
command = ast_strip(input);
|
||||
ast_chan_log(LOG_NOTICE, chan, "stderr: %s\n", command);
|
||||
}
|
||||
} else if ((ready_fd < 0) && ms) {
|
||||
if (errno == 0 || errno == EINTR)
|
||||
continue;
|
||||
|
||||
ast_chan_log(LOG_WARNING, chan, "Wait failed (%s)\n", strerror(errno));
|
||||
break;
|
||||
}
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
||||
exit:
|
||||
if (gen_active)
|
||||
ast_deactivate_generator(chan);
|
||||
|
||||
if (child_events)
|
||||
fclose(child_events);
|
||||
|
||||
if (child_commands)
|
||||
fclose(child_commands);
|
||||
|
||||
if (child_errors)
|
||||
fclose(child_errors);
|
||||
|
||||
if (child_stdin[0])
|
||||
close(child_stdin[0]);
|
||||
|
||||
if (child_stdin[1])
|
||||
close(child_stdin[1]);
|
||||
|
||||
if (child_stdout[0])
|
||||
close(child_stdout[0]);
|
||||
|
||||
if (child_stdout[1])
|
||||
close(child_stdout[1]);
|
||||
|
||||
if (child_stderr[0])
|
||||
close(child_stderr[0]);
|
||||
|
||||
if (child_stderr[1])
|
||||
close(child_stderr[1]);
|
||||
|
||||
while ((entry = AST_LIST_REMOVE_HEAD(&u->playlist, list)))
|
||||
ast_free(entry);
|
||||
|
||||
return res;
|
||||
}
|
||||
|
||||
static int eivr_comm(struct ast_channel *chan, struct ivr_localuser *u,
|
||||
int eivr_events_fd, int eivr_commands_fd, int eivr_errors_fd,
|
||||
const char *args)
|
||||
{
|
||||
struct playlist_entry *entry;
|
||||
struct ast_frame *f;
|
||||
int ms;
|
||||
int exception;
|
||||
int ready_fd;
|
||||
int waitfds[2] = { eivr_commands_fd, eivr_errors_fd };
|
||||
struct ast_channel *rchan;
|
||||
char *command;
|
||||
int res = -1;
|
||||
|
||||
FILE *eivr_commands = NULL;
|
||||
FILE *eivr_errors = NULL;
|
||||
FILE *eivr_events = NULL;
|
||||
|
||||
if (!(eivr_events = fdopen(eivr_events_fd, "w"))) {
|
||||
ast_chan_log(LOG_WARNING, chan, "Could not open stream to send events\n");
|
||||
goto exit;
|
||||
}
|
||||
if (!(eivr_commands = fdopen(eivr_commands_fd, "r"))) {
|
||||
ast_chan_log(LOG_WARNING, chan, "Could not open stream to receive commands\n");
|
||||
goto exit;
|
||||
}
|
||||
if(eivr_errors_fd) { /*if opening a socket connection, error stream will not be used*/
|
||||
if (!(eivr_errors = fdopen(eivr_errors_fd, "r"))) {
|
||||
ast_chan_log(LOG_WARNING, chan, "Could not open stream to receive errors\n");
|
||||
goto exit;
|
||||
}
|
||||
}
|
||||
|
||||
setvbuf(eivr_events, NULL, _IONBF, 0);
|
||||
setvbuf(eivr_commands, NULL, _IONBF, 0);
|
||||
if(eivr_errors)
|
||||
setvbuf(eivr_errors, NULL, _IONBF, 0);
|
||||
|
||||
res = 0;
|
||||
|
||||
while (1) {
|
||||
if (ast_test_flag(chan, AST_FLAG_ZOMBIE)) {
|
||||
ast_chan_log(LOG_NOTICE, chan, "Is a zombie\n");
|
||||
res = -1;
|
||||
break;
|
||||
}
|
||||
if (ast_check_hangup(chan)) {
|
||||
ast_chan_log(LOG_NOTICE, chan, "Got check_hangup\n");
|
||||
send_eivr_event(eivr_events, 'H', NULL, chan);
|
||||
res = -1;
|
||||
break;
|
||||
}
|
||||
|
||||
ready_fd = 0;
|
||||
ms = 100;
|
||||
errno = 0;
|
||||
exception = 0;
|
||||
|
||||
rchan = ast_waitfor_nandfds(&chan, 1, waitfds, 2, &exception, &ready_fd, &ms);
|
||||
|
||||
if (!AST_LIST_EMPTY(&u->finishlist)) {
|
||||
AST_LIST_LOCK(&u->finishlist);
|
||||
while ((entry = AST_LIST_REMOVE_HEAD(&u->finishlist, list))) {
|
||||
send_eivr_event(eivr_events, 'F', entry->filename, chan);
|
||||
ast_free(entry);
|
||||
}
|
||||
AST_LIST_UNLOCK(&u->finishlist);
|
||||
}
|
||||
|
||||
if (rchan) {
|
||||
/* the channel has something */
|
||||
f = ast_read(chan);
|
||||
if (!f) {
|
||||
ast_chan_log(LOG_NOTICE, chan, "Returned no frame\n");
|
||||
send_eivr_event(eivr_events, 'H', NULL, chan);
|
||||
res = -1;
|
||||
break;
|
||||
}
|
||||
if (f->frametype == AST_FRAME_DTMF) {
|
||||
send_eivr_event(eivr_events, f->subclass, NULL, chan);
|
||||
if (u->option_autoclear) {
|
||||
if (!u->abort_current_sound && !u->playing_silence)
|
||||
send_eivr_event(eivr_events, 'T', NULL, chan);
|
||||
AST_LIST_LOCK(&u->playlist);
|
||||
while ((entry = AST_LIST_REMOVE_HEAD(&u->playlist, list))) {
|
||||
send_eivr_event(eivr_events, 'D', entry->filename, chan);
|
||||
ast_free(entry);
|
||||
}
|
||||
if (!u->playing_silence)
|
||||
u->abort_current_sound = 1;
|
||||
AST_LIST_UNLOCK(&u->playlist);
|
||||
}
|
||||
} else if ((f->frametype == AST_FRAME_CONTROL) && (f->subclass == AST_CONTROL_HANGUP)) {
|
||||
ast_chan_log(LOG_NOTICE, chan, "Got AST_CONTROL_HANGUP\n");
|
||||
send_eivr_event(eivr_events, 'H', NULL, chan);
|
||||
ast_frfree(f);
|
||||
res = -1;
|
||||
break;
|
||||
}
|
||||
ast_frfree(f);
|
||||
} else if (ready_fd == eivr_commands_fd) {
|
||||
char input[1024];
|
||||
|
||||
if (exception || feof(eivr_commands)) {
|
||||
ast_chan_log(LOG_WARNING, chan, "Child process went away\n");
|
||||
res = -1;
|
||||
break;
|
||||
}
|
||||
|
||||
if (!fgets(input, sizeof(input), eivr_commands))
|
||||
continue;
|
||||
|
||||
command = ast_strip(input);
|
||||
|
||||
if (option_debug)
|
||||
ast_chan_log(LOG_DEBUG, chan, "got command '%s'\n", input);
|
||||
|
||||
if (strlen(input) < 4)
|
||||
continue;
|
||||
|
||||
if (input[0] == 'P') {
|
||||
send_eivr_event(eivr_events, 'P', args, chan);
|
||||
|
||||
} else if (input[0] == 'S') {
|
||||
if (ast_fileexists(&input[2], NULL, u->chan->language) == -1) {
|
||||
ast_chan_log(LOG_WARNING, chan, "Unknown file requested '%s'\n", &input[2]);
|
||||
send_eivr_event(eivr_events, 'Z', NULL, chan);
|
||||
strcpy(&input[2], "exception");
|
||||
}
|
||||
if (!u->abort_current_sound && !u->playing_silence)
|
||||
send_eivr_event(eivr_events, 'T', NULL, chan);
|
||||
AST_LIST_LOCK(&u->playlist);
|
||||
while ((entry = AST_LIST_REMOVE_HEAD(&u->playlist, list))) {
|
||||
send_eivr_event(eivr_events, 'D', entry->filename, chan);
|
||||
ast_free(entry);
|
||||
}
|
||||
if (!u->playing_silence)
|
||||
u->abort_current_sound = 1;
|
||||
entry = make_entry(&input[2]);
|
||||
if (entry)
|
||||
AST_LIST_INSERT_TAIL(&u->playlist, entry, list);
|
||||
AST_LIST_UNLOCK(&u->playlist);
|
||||
} else if (input[0] == 'A') {
|
||||
if (ast_fileexists(&input[2], NULL, u->chan->language) == -1) {
|
||||
ast_chan_log(LOG_WARNING, chan, "Unknown file requested '%s'\n", &input[2]);
|
||||
send_eivr_event(eivr_events, 'Z', NULL, chan);
|
||||
strcpy(&input[2], "exception");
|
||||
}
|
||||
entry = make_entry(&input[2]);
|
||||
if (entry) {
|
||||
AST_LIST_LOCK(&u->playlist);
|
||||
AST_LIST_INSERT_TAIL(&u->playlist, entry, list);
|
||||
AST_LIST_UNLOCK(&u->playlist);
|
||||
}
|
||||
} else if (input[0] == 'G') {
|
||||
// A get variable message: "G,variable1,variable2,..."
|
||||
char response[2048];
|
||||
ast_chan_log(LOG_NOTICE, chan, "Getting a Variable out of the channel: %s\n", &input[2]);
|
||||
ast_eivr_getvariable(chan, &input[2], response, sizeof(response));
|
||||
send_eivr_event(eivr_events, 'G', response, chan);
|
||||
} else if (input[0] == 'V') {
|
||||
// A set variable message: "V,variablename=foo"
|
||||
ast_chan_log(LOG_NOTICE, chan, "Setting a Variable up: %s\n", &input[2]);
|
||||
ast_eivr_setvariable(chan, &input[2]);
|
||||
} else if (input[0] == 'L') {
|
||||
ast_chan_log(LOG_NOTICE, chan, "Log message from EIVR: %s\n", &input[2]);
|
||||
} else if (input[0] == 'X') {
|
||||
ast_chan_log(LOG_NOTICE, chan, "Exiting ExternalIVR: %s\n", &input[2]);
|
||||
//TODO: add deprecation debug message for X command here
|
||||
res = 0;
|
||||
break;
|
||||
} else if (input[0] == 'E') {
|
||||
ast_chan_log(LOG_NOTICE, chan, "Exiting: %s\n", &input[2]);
|
||||
send_eivr_event(eivr_events, 'E', NULL, chan);
|
||||
res = 0;
|
||||
break;
|
||||
} else if (input[0] == 'H') {
|
||||
ast_chan_log(LOG_NOTICE, chan, "Hanging up: %s\n", &input[2]);
|
||||
send_eivr_event(eivr_events, 'H', NULL, chan);
|
||||
res = -1;
|
||||
break;
|
||||
} else if (input[0] == 'O') {
|
||||
if (!strcasecmp(&input[2], "autoclear"))
|
||||
u->option_autoclear = 1;
|
||||
else if (!strcasecmp(&input[2], "noautoclear"))
|
||||
u->option_autoclear = 0;
|
||||
else
|
||||
ast_chan_log(LOG_WARNING, chan, "Unknown option requested '%s'\n", &input[2]);
|
||||
}
|
||||
} else if (eivr_errors_fd && ready_fd == eivr_errors_fd) {
|
||||
char input[1024];
|
||||
|
||||
if (exception || feof(eivr_errors)) {
|
||||
ast_chan_log(LOG_WARNING, chan, "Child process went away\n");
|
||||
res = -1;
|
||||
break;
|
||||
}
|
||||
if (fgets(input, sizeof(input), eivr_errors)) {
|
||||
command = ast_strip(input);
|
||||
ast_chan_log(LOG_NOTICE, chan, "stderr: %s\n", command);
|
||||
}
|
||||
} else if ((ready_fd < 0) && ms) {
|
||||
if (errno == 0 || errno == EINTR)
|
||||
continue;
|
||||
|
||||
ast_chan_log(LOG_WARNING, chan, "Wait failed (%s)\n", strerror(errno));
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
exit:
|
||||
|
||||
if (eivr_events)
|
||||
fclose(eivr_events);
|
||||
|
||||
if (eivr_commands)
|
||||
fclose(eivr_commands);
|
||||
|
||||
if (eivr_errors)
|
||||
fclose(eivr_errors);
|
||||
|
||||
return res;
|
||||
|
||||
}
|
||||
|
||||
static int unload_module(void)
|
||||
{
|
||||
return ast_unregister_application(app);
|
||||
|
Reference in New Issue
Block a user