aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--Makefile76
-rw-r--r--UPGRADE.txt3
-rw-r--r--apps/app_festival.c14
-rw-r--r--apps/app_page.c30
-rw-r--r--apps/app_voicemail.c164
-rw-r--r--channel.c9
-rw-r--r--channels/chan_agent.c15
-rw-r--r--channels/chan_local.c21
-rw-r--r--channels/chan_sip.c6
-rw-r--r--configs/voicemail.conf.sample3
-rw-r--r--doc/README.misdn5
-rw-r--r--pbx.c2
12 files changed, 184 insertions, 164 deletions
diff --git a/Makefile b/Makefile
index f2bb7ad28..9c35ecbf1 100644
--- a/Makefile
+++ b/Makefile
@@ -592,17 +592,16 @@ datafiles: all
mkdir -p $(DESTDIR)$(AGI_DIR)
update:
- @if [ -d CVS ]; then \
- if [ -f patches/.applied ]; then \
- patches=`cat patches/.applied`; \
- fi; \
- if [ ! -z "$$patches" ]; then \
- for x in $$patches; do \
- echo "Unapplying $$x..."; \
- patch -R -p0 < patches/$$x; \
- done; \
- rm -f patches/.applied; \
+ @if [ -d .svn ]; then \
+ echo "Updating from Subversion..." ; \
+ svn update | tee update.out; \
+ rm -f .version; \
+ if [ `grep -c ^C update.out` -gt 0 ]; then \
+ echo ; echo "The following files have conflicts:" ; \
+ grep ^C update.out | cut -b4- ; \
fi ; \
+ rm -f update.out; \
+ elif [ -d CVS ]; then \
echo "Updating from CVS..." ; \
cvs -q -z3 update -Pd | tee update.out; \
rm -f .version; \
@@ -611,19 +610,8 @@ update:
grep ^C update.out | cut -d' ' -f2- ; \
fi ; \
rm -f update.out; \
- if [ ! -z "$$patches" ]; then \
- for x in $$patches; do \
- if [ -f patches/$$x ]; then \
- echo "Applying patch $$x..."; \
- patch -p0 < patches/$$x; \
- echo $$x >> patches/.applied; \
- else \
- echo "Patch $$x no longer relevant"; \
- fi; \
- done; \
- fi; \
else \
- echo "Not CVS"; \
+ echo "Not under version control"; \
fi
NEWHEADERS=$(notdir $(wildcard include/asterisk/*.h))
@@ -911,47 +899,3 @@ cleantest:
if cmp -s .cleancount .lastclean ; then echo ; else \
$(MAKE) clean; cp -f .cleancount .lastclean;\
fi
-
-patchlist:
- @echo "Experimental Patches:"
- @for x in patches/*; do \
- patch=`basename $$x`; \
- if [ "$$patch" = "CVS" ]; then \
- continue; \
- fi; \
- if grep -q ^$$patch$$ patches/.applied; then \
- echo "$$patch (applied)"; \
- else \
- echo "$$patch (available)"; \
- fi; \
- done
-
-apply:
- @if [ -z "$(PATCH)" ]; then \
- echo "Usage: make PATCH=<patchname> apply"; \
- elif grep -q ^$(PATCH)$$ patches/.applied 2>/dev/null; then \
- echo "Patch $(PATCH) is already applied"; \
- elif [ -f "patches/$(PATCH)" ]; then \
- echo "Applying patch $(PATCH)"; \
- patch -p0 < patches/$(PATCH); \
- echo "$(PATCH)" >> patches/.applied; \
- else \
- echo "No such patch $(PATCH) in patches directory"; \
- fi
-
-unapply:
- @if [ -z "$(PATCH)" ]; then \
- echo "Usage: make PATCH=<patchname> unapply"; \
- elif grep -v -q ^$(PATCH)$$ patches/.applied 2>/dev/null; then \
- echo "Patch $(PATCH) is not applied"; \
- elif [ -f "patches/$(PATCH)" ]; then \
- echo "Un-applying patch $(PATCH)"; \
- patch -p0 -R < patches/$(PATCH); \
- rm -f patches/.tmpapplied || :; \
- mv patches/.applied patches/.tmpapplied; \
- cat patches/.tmpapplied | grep -v ^$(PATCH)$$ > patches/.applied; \
- rm -f patches/.tmpapplied; \
- else \
- echo "No such patch $(PATCH) in patches directory"; \
- fi
-
diff --git a/UPGRADE.txt b/UPGRADE.txt
index db9eab845..76e557773 100644
--- a/UPGRADE.txt
+++ b/UPGRADE.txt
@@ -133,7 +133,8 @@ Applications:
* The application VoiceMailMain now only matches the 'default' context if
none is specified in the arguments. (This was the previously
- documented behavior, however, we didn't follow that behavior.)
+ documented behavior, however, we didn't follow that behavior.) The old
+ behavior can be restored by setting searchcontexts=yes in voicemail.conf.
Queues:
diff --git a/apps/app_festival.c b/apps/app_festival.c
index 03753642c..186a50ae7 100644
--- a/apps/app_festival.c
+++ b/apps/app_festival.c
@@ -455,8 +455,20 @@ static int festival_exec(struct ast_channel *chan, void *vdata)
/* This assumes only one waveform will come back, also LP is unlikely */
wave = 0;
do {
+ int read_data;
for (n=0; n < 3; )
- n += read(fd,ack+n,3-n);
+ {
+ read_data = read(fd,ack+n,3-n);
+ /* this avoids falling in infinite loop
+ * in case that festival server goes down
+ * */
+ if ( read_data == -1 )
+ {
+ ast_log(LOG_WARNING,"Unable to read from cache/festival fd");
+ return -1;
+ }
+ n += read_data;
+ }
ack[3] = '\0';
if (strcmp(ack,"WV\n") == 0) { /* receive a waveform */
ast_log(LOG_DEBUG,"Festival WV command\n");
diff --git a/apps/app_page.c b/apps/app_page.c
index 441208fd9..39a0eb4bc 100644
--- a/apps/app_page.c
+++ b/apps/app_page.c
@@ -40,6 +40,7 @@ ASTERISK_FILE_VERSION(__FILE__, "$Revision$")
#include "asterisk/module.h"
#include "asterisk/file.h"
#include "asterisk/app.h"
+#include "asterisk/chanvars.h"
static const char *tdesc = "Page Multiple Phones";
@@ -77,13 +78,14 @@ struct calloutdata {
char tech[64];
char resource[256];
char meetmeopts[64];
+ struct ast_variable *variables;
};
static void *page_thread(void *data)
{
struct calloutdata *cd = data;
ast_pbx_outgoing_app(cd->tech, AST_FORMAT_SLINEAR, cd->resource, 30000,
- "MeetMe", cd->meetmeopts, NULL, 0, cd->cidnum, cd->cidname, NULL, NULL);
+ "MeetMe", cd->meetmeopts, NULL, 0, cd->cidnum, cd->cidname, cd->variables, NULL);
free(cd);
return NULL;
}
@@ -91,6 +93,9 @@ static void *page_thread(void *data)
static void launch_page(struct ast_channel *chan, const char *meetmeopts, const char *tech, const char *resource)
{
struct calloutdata *cd;
+ const char *varname;
+ struct ast_variable *lastvar = NULL;
+ struct ast_var_t *varptr;
pthread_t t;
pthread_attr_t attr;
cd = malloc(sizeof(struct calloutdata));
@@ -101,6 +106,29 @@ static void launch_page(struct ast_channel *chan, const char *meetmeopts, const
ast_copy_string(cd->tech, tech, sizeof(cd->tech));
ast_copy_string(cd->resource, resource, sizeof(cd->resource));
ast_copy_string(cd->meetmeopts, meetmeopts, sizeof(cd->meetmeopts));
+
+ AST_LIST_TRAVERSE(&chan->varshead, varptr, entries) {
+ if (!(varname = ast_var_full_name(varptr)))
+ continue;
+ if (varname[0] == '_') {
+ struct ast_variable *newvar = NULL;
+
+ if (varname[1] == '_') {
+ newvar = ast_variable_new(varname, ast_var_value(varptr));
+ } else {
+ newvar = ast_variable_new(&varname[1], ast_var_value(varptr));
+ }
+
+ if (newvar) {
+ if (lastvar)
+ lastvar->next = newvar;
+ else
+ cd->variables = newvar;
+ lastvar = newvar;
+ }
+ }
+ }
+
pthread_attr_init(&attr);
pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED);
if (ast_pthread_create(&t, &attr, page_thread, cd)) {
diff --git a/apps/app_voicemail.c b/apps/app_voicemail.c
index 2dab9fac0..1bc88ce2f 100644
--- a/apps/app_voicemail.c
+++ b/apps/app_voicemail.c
@@ -110,6 +110,7 @@ ASTERISK_FILE_VERSION(__FILE__, "$Revision$")
#define VM_ATTACH (1 << 11)
#define VM_DELETE (1 << 12)
#define VM_ALLOCED (1 << 13)
+#define VM_SEARCH (1 << 14)
#define ERROR_LOCK_PATH -100
@@ -534,12 +535,11 @@ static struct ast_vm_user *find_user_realtime(struct ast_vm_user *ivm, const cha
ast_set_flag(retval, VM_ALLOCED);
if (mailbox)
ast_copy_string(retval->mailbox, mailbox, sizeof(retval->mailbox));
- if (context)
- ast_copy_string(retval->context, context, sizeof(retval->context));
- else
- strcpy(retval->context, "default");
populate_defaults(retval);
- var = ast_load_realtime("voicemail", "mailbox", mailbox, "context", retval->context, NULL);
+ if (ast_test_flag((&globalflags), VM_SEARCH))
+ var = ast_load_realtime("voicemail", "mailbox", mailbox, NULL);
+ else
+ var = ast_load_realtime("voicemail", "mailbox", mailbox, "context", retval->context, NULL);
if (var) {
tmp = var;
while(tmp) {
@@ -554,6 +554,8 @@ static struct ast_vm_user *find_user_realtime(struct ast_vm_user *ivm, const cha
ast_copy_string(retval->email, tmp->value, sizeof(retval->email));
} else if (!strcasecmp(tmp->name, "fullname")) {
ast_copy_string(retval->fullname, tmp->value, sizeof(retval->fullname));
+ } else if (!strcasecmp(tmp->name, "context")) {
+ ast_copy_string(retval->context, tmp->value, sizeof(retval->context));
} else
apply_option(retval, tmp->name, tmp->value);
tmp = tmp->next;
@@ -574,13 +576,14 @@ static struct ast_vm_user *find_user(struct ast_vm_user *ivm, const char *contex
ast_mutex_lock(&vmlock);
cur = users;
- if (!context)
+ if (!context && !ast_test_flag((&globalflags), VM_SEARCH))
context = "default";
while (cur) {
- if ((!strcasecmp(context, cur->context)) &&
- (!strcasecmp(mailbox, cur->mailbox)))
- break;
+ if (ast_test_flag((&globalflags), VM_SEARCH) && !strcasecmp(mailbox, cur->mailbox))
+ break;
+ if ((!strcasecmp(context, cur->context)) && (!strcasecmp(mailbox, cur->mailbox)))
+ break;
cur=cur->next;
}
if (cur) {
@@ -660,91 +663,89 @@ static void vm_change_password(struct ast_vm_user *vmu, const char *newpassword)
}
while (!feof(configin)) {
+ char *user = NULL, *pass = NULL, *rest = NULL, *comment = NULL, *tmpctx = NULL, *tmpctxend = NULL;
+
/* Read in the line */
fgets(inbuf, sizeof(inbuf), configin);
linenum++;
- if (!feof(configin)) {
- char *user = NULL, *pass = NULL, *rest = NULL,
- *comment = NULL, *tmpctx = NULL, *tmpctxend = NULL;
-
- if (ast_strlen_zero(inbuf)) {
- fprintf(configout, "\n");
- continue;
- }
- /* Make a backup of it */
- ast_copy_string(orig, inbuf, sizeof(orig));
-
- /*
- Read the file line by line, split each line into a comment and command section
- only parse the command portion of the line
- */
- if (inbuf[strlen(inbuf) - 1] == '\n')
- inbuf[strlen(inbuf) - 1] = '\0';
+ if (ast_strlen_zero(inbuf)) {
+ fprintf(configout, "\n");
+ continue;
+ }
+
+ /* Make a backup of it */
+ ast_copy_string(orig, inbuf, sizeof(orig));
+
+ /*
+ Read the file line by line, split each line into a comment and command section
+ only parse the command portion of the line
+ */
+ if (inbuf[strlen(inbuf) - 1] == '\n')
+ inbuf[strlen(inbuf) - 1] = '\0';
- if ((comment = strchr(inbuf, ';')))
- *comment++ = '\0'; /* Now inbuf is terminated just before the comment */
+ if ((comment = strchr(inbuf, ';')))
+ *comment++ = '\0'; /* Now inbuf is terminated just before the comment */
- if (ast_strlen_zero(inbuf)) {
+ if (ast_strlen_zero(inbuf)) {
+ fprintf(configout, "%s", orig);
+ continue;
+ }
+
+ /* Check for a context, first '[' to first ']' */
+ if ((tmpctx = strchr(inbuf, '['))) {
+ tmpctxend = strchr(tmpctx, ']');
+ if (tmpctxend) {
+ /* Valid context */
+ ast_copy_string(currcontext, tmpctx + 1, tmpctxend - tmpctx);
fprintf(configout, "%s", orig);
continue;
}
-
- /* Check for a context, first '[' to first ']' */
- if ((tmpctx = strchr(inbuf, '['))) {
- tmpctxend = strchr(tmpctx, ']');
- if (tmpctxend) {
- /* Valid context */
- ast_copy_string(currcontext, tmpctx + 1, tmpctxend - tmpctx);
- fprintf(configout, "%s", orig);
- continue;
- }
- }
-
- /* This isn't a context line, check for MBX => PSWD... */
- user = inbuf;
- if ((pass = strchr(user, '='))) {
- /* We have a line in the form of aaaaa=aaaaaa */
+ }
+
+ /* This isn't a context line, check for MBX => PSWD... */
+ user = inbuf;
+ if ((pass = strchr(user, '='))) {
+ /* We have a line in the form of aaaaa=aaaaaa */
+ *pass++ = '\0';
+
+ user = ast_strip(user);
+
+ if (*pass == '>')
*pass++ = '\0';
-
- user = ast_strip(user);
- if (*pass == '>')
- *pass++ = '\0';
+ pass = ast_skip_blanks(pass);
- pass = ast_skip_blanks(pass);
-
- /*
- Since no whitespace allowed in fields, or more correctly white space
- inside the fields is there for a purpose, we can just terminate pass
- at the comma or EOL whichever comes first.
- */
- if ((rest = strchr(pass, ',')))
- *rest++ = '\0';
+ /*
+ Since no whitespace allowed in fields, or more correctly white space
+ inside the fields is there for a purpose, we can just terminate pass
+ at the comma or EOL whichever comes first.
+ */
+ if ((rest = strchr(pass, ',')))
+ *rest++ = '\0';
+ } else {
+ user = NULL;
+ }
+
+ /* Compare user, pass AND context */
+ if (!ast_strlen_zero(user) && !strcmp(user, vmu->mailbox) &&
+ !ast_strlen_zero(pass) && !strcmp(pass, vmu->password) &&
+ !strcasecmp(currcontext, vmu->context)) {
+ /* This is the line */
+ if (rest) {
+ fprintf(configout, "%s => %s,%s", user, newpassword, rest);
} else {
- user = NULL;
- }
-
- /* Compare user, pass AND context */
- if (!ast_strlen_zero(user) && !strcmp(user, vmu->mailbox) &&
- !ast_strlen_zero(pass) && !strcmp(pass, vmu->password) &&
- !strcasecmp(currcontext, vmu->context)) {
- /* This is the line */
- if (rest) {
- fprintf(configout, "%s => %s,%s", user, newpassword, rest);
- } else {
- fprintf(configout, "%s => %s", user, newpassword);
- }
- /* If there was a comment on the line print it out */
- if (comment) {
- fprintf(configout, ";%s\n", comment);
- } else {
- fprintf(configout, "\n");
- }
+ fprintf(configout, "%s => %s", user, newpassword);
+ }
+ /* If there was a comment on the line print it out */
+ if (comment) {
+ fprintf(configout, ";%s\n", comment);
} else {
- /* Put it back like it was */
- fprintf(configout, "%s", orig);
+ fprintf(configout, "\n");
}
+ } else {
+ /* Put it back like it was */
+ fprintf(configout, "%s", orig);
}
}
fclose(configin);
@@ -5812,6 +5813,7 @@ static int load_config(void)
struct ast_variable *var;
char *notifystr = NULL;
char *astattach;
+ char *astsearch;
char *astsaycid;
char *send_voicemail;
char *astcallop;
@@ -5865,6 +5867,10 @@ static int load_config(void)
astattach = "yes";
ast_set2_flag((&globalflags), ast_true(astattach), VM_ATTACH);
+ if (!(astsearch = ast_variable_retrieve(cfg, "general", "searchcontexts")))
+ astsearch = "no";
+ ast_set2_flag((&globalflags), ast_true(astsearch), VM_SEARCH);
+
#ifdef USE_ODBC_STORAGE
strcpy(odbc_database, "asterisk");
if ((thresholdstr = ast_variable_retrieve(cfg, "general", "odbcstorage"))) {
diff --git a/channel.c b/channel.c
index e86afb25e..85a2882ff 100644
--- a/channel.c
+++ b/channel.c
@@ -909,8 +909,11 @@ void ast_channel_free(struct ast_channel *chan)
free(chan->tech_pvt);
}
+ if (chan->sched)
+ sched_context_destroy(chan->sched);
+
ast_copy_string(name, chan->name, sizeof(name));
-
+
/* Stop monitoring */
if (chan->monitor) {
chan->monitor->stop( chan, 0 );
@@ -1294,8 +1297,10 @@ int ast_hangup(struct ast_channel *chan)
ast_closestream(chan->stream);
if (chan->vstream) /* Close video stream */
ast_closestream(chan->vstream);
- if (chan->sched)
+ if (chan->sched) {
sched_context_destroy(chan->sched);
+ chan->sched = NULL;
+ }
if (chan->generatordata) /* Clear any tone stuff remaining */
chan->generator->release(chan, chan->generatordata);
diff --git a/channels/chan_agent.c b/channels/chan_agent.c
index e2ef0f203..a754f8a8f 100644
--- a/channels/chan_agent.c
+++ b/channels/chan_agent.c
@@ -910,15 +910,16 @@ static int agent_ack_sleep( void *data )
static struct ast_channel *agent_bridgedchannel(struct ast_channel *chan, struct ast_channel *bridge)
{
- struct agent_pvt *p;
+ struct agent_pvt *p = bridge->tech_pvt;
struct ast_channel *ret=NULL;
-
- p = bridge->tech_pvt;
- if (chan == p->chan)
- ret = bridge->_bridge;
- else if (chan == bridge->_bridge)
- ret = p->chan;
+ if (p) {
+ if (chan == p->chan)
+ ret = bridge->_bridge;
+ else if (chan == bridge->_bridge)
+ ret = p->chan;
+ }
+
if (option_debug)
ast_log(LOG_DEBUG, "Asked for bridged channel on '%s'/'%s', returning '%s'\n", chan->name, bridge->name, ret ? ret->name : "<none>");
return ret;
diff --git a/channels/chan_local.c b/channels/chan_local.c
index 6dec650ab..f843fd95d 100644
--- a/channels/chan_local.c
+++ b/channels/chan_local.c
@@ -320,6 +320,8 @@ static int local_call(struct ast_channel *ast, char *dest, int timeout)
{
struct local_pvt *p = ast->tech_pvt;
int res;
+ struct ast_var_t *varptr = NULL, *new;
+ size_t len, namelen;
ast_mutex_lock(&p->lock);
if (p->owner->cid.cid_num)
@@ -345,9 +347,22 @@ static int local_call(struct ast_channel *ast, char *dest, int timeout)
strncpy(p->chan->language, p->owner->language, sizeof(p->chan->language) - 1);
strncpy(p->chan->accountcode, p->owner->accountcode, sizeof(p->chan->accountcode) - 1);
p->chan->cdrflags = p->owner->cdrflags;
- /* move the channel variables from the incoming channel to the outgoing channel */
- AST_LIST_HEAD_SET_NOLOCK(&p->chan->varshead, AST_LIST_FIRST(&p->owner->varshead));
- AST_LIST_HEAD_INIT_NOLOCK(&p->owner->varshead);
+
+ /* copy the channel variables from the incoming channel to the outgoing channel */
+ /* Note that due to certain assumptions, they MUST be in the same order */
+ AST_LIST_TRAVERSE(&p->owner->varshead, varptr, entries) {
+ namelen = strlen(varptr->name);
+ len = sizeof(struct ast_var_t) + namelen + strlen(varptr->value) + 2;
+ new = malloc(len);
+ if (new) {
+ memcpy(new, varptr, len);
+ new->value = &(new->name[0]) + namelen + 1;
+ AST_LIST_INSERT_TAIL(&p->chan->varshead, new, entries);
+ } else {
+ ast_log(LOG_ERROR, "Out of memory!\n");
+ }
+ }
+
p->launchedpbx = 1;
/* Start switch on sub channel */
diff --git a/channels/chan_sip.c b/channels/chan_sip.c
index 0daf12f89..c93f21fa3 100644
--- a/channels/chan_sip.c
+++ b/channels/chan_sip.c
@@ -8604,8 +8604,6 @@ static void handle_request_info(struct sip_pvt *p, struct sip_request *req)
return;
}
- if (sipdebug)
- ast_verbose("* DTMF-relay event received: '%c'\n", buf[0]);
if (buf[0] == '*')
event = 10;
else if (buf[0] == '#')
@@ -8618,6 +8616,8 @@ static void handle_request_info(struct sip_pvt *p, struct sip_request *req)
/* send a FLASH event */
struct ast_frame f = { AST_FRAME_CONTROL, AST_CONTROL_FLASH, };
ast_queue_frame(p->owner, &f);
+ if (sipdebug)
+ ast_verbose("* DTMF-relay event received: FLASH\n");
} else {
/* send a DTMF event */
struct ast_frame f = { AST_FRAME_DTMF, };
@@ -8631,6 +8631,8 @@ static void handle_request_info(struct sip_pvt *p, struct sip_request *req)
f.subclass = 'A' + (event - 12);
}
ast_queue_frame(p->owner, &f);
+ if (sipdebug)
+ ast_verbose("* DTMF-relay event received: %c\n", f.subclass);
}
transmit_response(p, "200 OK", req);
return;
diff --git a/configs/voicemail.conf.sample b/configs/voicemail.conf.sample
index ba917abca..8558235a6 100644
--- a/configs/voicemail.conf.sample
+++ b/configs/voicemail.conf.sample
@@ -160,6 +160,9 @@ emaildateformat=%A, %B %d, %Y at %r
sendvoicemail=yes ; Context to Send voicemail from [option 5 from the advanced menu]
; if not listed, sending messages from inside voicemail will not be
; permitted
+; searchcontexts=yes ; Current default behavior is to search only the default context
+ ; if one is not specified. The older behavior was to search all contexts.
+ ; This option restores the old behavior [DEFAULT=no]
; callback=fromvm ; Context to call back from
; if not listed, calling the sender back will not be permitted
; review=yes ; Allow sender to review/rerecord their message before saving it [OFF by default
diff --git a/doc/README.misdn b/doc/README.misdn
index 522cda9c0..2ff0b9bfe 100644
--- a/doc/README.misdn
+++ b/doc/README.misdn
@@ -282,7 +282,10 @@ should be enough. the messages are divided in asterisk and misdn parts.
Misdn Debug messages begin with an 'I', asterisk messages begin with an '*',
the rest is clear I think.
-Please take a trace of the problem and send this trace via mail to bugs@beronet.com
+Please take a trace of the problem and open a report in the Asterisk issue
+tracker at http://bugs.digium.com in the "channel drivers" project,
+"chan_misdn" category. Read the bug guidelines to make sure you
+provide all the information needed.
Examples
diff --git a/pbx.c b/pbx.c
index 950cc2ffc..8ba552def 100644
--- a/pbx.c
+++ b/pbx.c
@@ -5217,7 +5217,7 @@ int ast_pbx_outgoing_app(const char *type, int format, void *data, int timeout,
goto outgoing_app_cleanup;
}
memset(as, 0, sizeof(struct async_stat));
- chan = ast_request_and_dial(type, format, data, timeout, reason, cid_num, cid_name);
+ chan = __ast_request_and_dial(type, format, data, timeout, reason, cid_num, cid_name, &oh);
if (!chan) {
free(as);
res = -1;