diff options
-rw-r--r-- | apps/app_dial.c | 3 | ||||
-rw-r--r-- | apps/app_meetme.c | 4 | ||||
-rw-r--r-- | apps/app_while.c | 5 | ||||
-rw-r--r-- | channels/chan_agent.c | 12 | ||||
-rw-r--r-- | channels/chan_h323.c | 6 | ||||
-rw-r--r-- | channels/chan_iax2.c | 11 | ||||
-rw-r--r-- | channels/chan_misdn.c | 2 | ||||
-rw-r--r-- | channels/chan_sip.c | 29 | ||||
-rw-r--r-- | channels/chan_skinny.c | 2 | ||||
-rw-r--r-- | include/asterisk/astobj2.h | 1 | ||||
-rw-r--r-- | main/asterisk.c | 14 | ||||
-rw-r--r-- | main/astobj2.c | 15 | ||||
-rw-r--r-- | main/manager.c | 3 | ||||
-rw-r--r-- | main/pbx.c | 2 |
14 files changed, 90 insertions, 19 deletions
diff --git a/apps/app_dial.c b/apps/app_dial.c index 142fe9f25..ce2bffeb3 100644 --- a/apps/app_dial.c +++ b/apps/app_dial.c @@ -1583,6 +1583,9 @@ static int dial_exec_full(struct ast_channel *chan, void *data, struct ast_flags /* Again, keep going even if there's an error */ ast_debug(1, "ast call on peer returned %d\n", res); ast_verb(3, "Couldn't call %s\n", numsubst); + if (tc->hangupcause) { + chan->hangupcause = tc->hangupcause; + } ast_hangup(tc); tc = NULL; ast_free(tmp); diff --git a/apps/app_meetme.c b/apps/app_meetme.c index 13f61df00..9f7f3afc3 100644 --- a/apps/app_meetme.c +++ b/apps/app_meetme.c @@ -1379,6 +1379,10 @@ static void sla_queue_event_full(enum sla_event_type type, { struct sla_event *event; + if (sla.thread == AST_PTHREADT_NULL) { + return; + } + if (!(event = ast_calloc(1, sizeof(*event)))) return; diff --git a/apps/app_while.c b/apps/app_while.c index 1c61d966e..405e78c3c 100644 --- a/apps/app_while.c +++ b/apps/app_while.c @@ -160,11 +160,16 @@ static int _while_exec(struct ast_channel *chan, void *data, int end) return -1; } +#if 0 /* dont want run away loops if the chan isn't even up this is up for debate since it slows things down a tad ...... + + Debate is over... this prevents While/EndWhile from working + within the "h" extension. Not good. */ if (ast_waitfordigit(chan,1) < 0) return -1; +#endif for (x=0;;x++) { if (get_index(chan, prefix, x)) { diff --git a/channels/chan_agent.c b/channels/chan_agent.c index ebfa11147..de7bb1125 100644 --- a/channels/chan_agent.c +++ b/channels/chan_agent.c @@ -657,9 +657,15 @@ static int agent_indicate(struct ast_channel *ast, int condition, const void *da struct agent_pvt *p = ast->tech_pvt; int res = -1; ast_mutex_lock(&p->lock); - if (p->chan && !ast_check_hangup(p->chan)) - res = p->chan->tech->indicate ? p->chan->tech->indicate(p->chan, condition, data, datalen) : -1; - else + if (p->chan && !ast_check_hangup(p->chan)) { + while (ast_channel_trylock(p->chan)) { + ast_channel_unlock(ast); + usleep(1); + ast_channel_lock(ast); + } + res = p->chan->tech->indicate ? p->chan->tech->indicate(p->chan, condition, data, datalen) : -1; + ast_channel_unlock(p->chan); + } else res = 0; ast_mutex_unlock(&p->lock); return res; diff --git a/channels/chan_h323.c b/channels/chan_h323.c index 26cf3a6b8..c24cbe71c 100644 --- a/channels/chan_h323.c +++ b/channels/chan_h323.c @@ -2609,7 +2609,7 @@ static int restart_monitor(void) pthread_kill(monitor_thread, SIGURG); } else { /* Start a new monitor */ - if (ast_pthread_create_detached_background(&monitor_thread, NULL, do_monitor, NULL) < 0) { + if (ast_pthread_create_background(&monitor_thread, NULL, do_monitor, NULL) < 0) { monitor_thread = AST_PTHREADT_NULL; ast_mutex_unlock(&monlock); ast_log(LOG_ERROR, "Unable to start monitor thread.\n"); @@ -3301,9 +3301,9 @@ static int unload_module(void) } if (!ast_mutex_lock(&monlock)) { if ((monitor_thread != AST_PTHREADT_STOP) && (monitor_thread != AST_PTHREADT_NULL)) { - /* this causes a seg, anyone know why? */ - if (monitor_thread != pthread_self()) + if (monitor_thread != pthread_self()) { pthread_cancel(monitor_thread); + } pthread_kill(monitor_thread, SIGURG); pthread_join(monitor_thread, NULL); } diff --git a/channels/chan_iax2.c b/channels/chan_iax2.c index 2c2e11c52..107df395b 100644 --- a/channels/chan_iax2.c +++ b/channels/chan_iax2.c @@ -1664,12 +1664,21 @@ static int __find_callno(unsigned short callno, unsigned short dcallno, struct s /* This will occur on the first response to a message that we initiated, * such as a PING. */ + if (dcallno) { + ast_mutex_lock(&iaxsl[dcallno]); + } if (callno && dcallno && iaxs[dcallno] && !iaxs[dcallno]->peercallno && match(sin, callno, dcallno, iaxs[dcallno], check_dcallno)) { iaxs[dcallno]->peercallno = callno; res = dcallno; store_by_peercallno(iaxs[dcallno]); + if (!res || !return_locked) { + ast_mutex_unlock(&iaxsl[dcallno]); + } return res; } + if (dcallno) { + ast_mutex_unlock(&iaxsl[dcallno]); + } #ifdef IAX_OLD_FIND /* If we get here, we SHOULD NOT find a call structure for this @@ -6977,7 +6986,7 @@ static int update_registry(struct sockaddr_in *sin, int callno, char *devtype, i /* Make sure our call still exists, an INVAL at the right point may make it go away */ if (!iaxs[callno]) { - res = 0; + res = -1; goto return_unref; } diff --git a/channels/chan_misdn.c b/channels/chan_misdn.c index 15cdb7ce9..123971327 100644 --- a/channels/chan_misdn.c +++ b/channels/chan_misdn.c @@ -2479,7 +2479,7 @@ static int misdn_indication(struct ast_channel *ast, int cond, const void *data, } chan_misdn_log(3, p->bc->port, " --> * SEND: State Ring pid:%d\n", p->bc ? p->bc->pid : -1); - ast_setstate(ast, AST_STATE_RINGING); + ast_setstate(ast, AST_STATE_RING); if ( !p->bc->nt && (p->originator == ORG_MISDN) && !p->incoming_early_audio ) chan_misdn_log(2, p->bc->port, " --> incoming_early_audio off\n"); diff --git a/channels/chan_sip.c b/channels/chan_sip.c index adf9ab905..05f63c61a 100644 --- a/channels/chan_sip.c +++ b/channels/chan_sip.c @@ -4280,8 +4280,11 @@ static int sip_call(struct ast_channel *ast, char *dest, int timeout) res = update_call_counter(p, INC_CALL_RINGING); - if (res == -1) + if (res == -1) { return res; + } else { + ast->hangupcause = AST_CAUSE_USER_BUSY; + } p->callingpres = ast->cid.cid_pres; p->jointcapability = ast_translate_available_formats(p->capability, p->prefcodec); @@ -15266,7 +15269,7 @@ static int handle_response_register(struct sip_pvt *p, int resp, char *rest, str break; case 200: /* 200 OK */ if (!r) { - ast_log(LOG_WARNING, "Got 200 OK on REGISTER that isn't a register\n"); + ast_log(LOG_WARNING, "Got 200 OK on REGISTER, but there isn't a registry entry for '%s' (we probably already got the OK)\n", S_OR(p->peername, p->username)); p->needdestroy = 1; return 0; } @@ -15445,6 +15448,20 @@ static void handle_response(struct sip_pvt *p, int resp, char *rest, struct sip_ Fix assigned to Rizzo :-) */ /* check_via_response(p, req); */ + + /* RFC 3261 Section 15 specifies that if we receive a 408 or 481 + * in response to a BYE, then we should end the current dialog + * and session. There is no mention in the spec of other 4XX responses, + * but it is known that at least one phone manufacturer potentially + * will send a 404 in response to a BYE, so we'll be liberal in what + * we accept and end the dialog and session if we receive any 4XX + * response to a BYE. + */ + if (resp >= 400 && resp < 500 && sipmethod == SIP_BYE) { + p->needdestroy = 1; + return; + } + if (p->relatedpeer && p->method == SIP_OPTIONS) { /* We don't really care what the response is, just that it replied back. Well, as long as it's not a 100 response... since we might @@ -20706,6 +20723,14 @@ static struct sip_peer *build_peer(const char *name, struct ast_variable *v, str ast_log(LOG_WARNING, "Qualification of peer '%s' should be 'yes', 'no', or a number of milliseconds at line %d of sip.conf\n", peer->name, v->lineno); peer->maxms = 0; } + if (realtime && !ast_test_flag(&global_flags[1], SIP_PAGE2_RTCACHEFRIENDS) && peer->maxms > 0) { + /* This would otherwise cause a network storm, where the + * qualify response refreshes the peer from the database, + * which in turn causes another qualify to be sent, ad + * infinitum. */ + ast_log(LOG_WARNING, "Qualify is incompatible with dynamic uncached realtime. Please either turn rtcachefriends on or turn qualify off on peer '%s'\n", peer->name); + peer->maxms = 0; + } } else if (!strcasecmp(v->name, "qualifyfreq")) { int i; if (sscanf(v->value, "%d", &i) == 1) diff --git a/channels/chan_skinny.c b/channels/chan_skinny.c index f415ad6ca..ae6cc573d 100644 --- a/channels/chan_skinny.c +++ b/channels/chan_skinny.c @@ -5747,7 +5747,7 @@ static void *accept_thread(void *ignore) sessions = s; ast_mutex_unlock(&sessionlock); - if (ast_pthread_create_detached(&tcp_thread, NULL, skinny_session, s)) { + if (ast_pthread_create(&tcp_thread, NULL, skinny_session, s)) { destroy_session(s); } } diff --git a/include/asterisk/astobj2.h b/include/asterisk/astobj2.h index bb63496ca..322e4732c 100644 --- a/include/asterisk/astobj2.h +++ b/include/asterisk/astobj2.h @@ -211,6 +211,7 @@ int ao2_unlock(void *a); #define ao2_unlock(a) _ao2_unlock(a, __FILE__, __PRETTY_FUNCTION__, __LINE__, #a) int _ao2_unlock(void *a, const char *file, const char *func, int line, const char *var); #endif +int ao2_trylock(void *user_data); /*! * diff --git a/main/asterisk.c b/main/asterisk.c index 81c4c73b7..b8a95064d 100644 --- a/main/asterisk.c +++ b/main/asterisk.c @@ -3028,11 +3028,6 @@ int main(int argc, char *argv[]) if (ast_opt_console && !option_verbose) ast_verbose("[ Booting...\n"); - if (ast_opt_always_fork && (ast_opt_remote || ast_opt_console)) { - ast_log(LOG_WARNING, "'alwaysfork' is not compatible with console or remote console mode; ignored\n"); - ast_clear_flag(&ast_options, AST_OPT_FLAG_ALWAYS_FORK); - } - /* For remote connections, change the name of the remote connection. * We do this for the benefit of init scripts (which need to know if/when * the main asterisk process has died yet). */ @@ -3043,8 +3038,10 @@ int main(int argc, char *argv[]) } } - if (ast_opt_console && !option_verbose) + if (ast_opt_console && !option_verbose) { ast_verbose("[ Reading Master Configuration ]\n"); + } + ast_readconfig(); if (ast_opt_remote && remotesock != NULL) @@ -3053,6 +3050,11 @@ int main(int argc, char *argv[]) if (!ast_language_is_prefix && !ast_opt_remote) ast_log(LOG_WARNING, "The 'languageprefix' option in asterisk.conf is deprecated; in a future release it will be removed, and your sound files will need to be organized in the 'new style' language layout.\n"); + if (ast_opt_always_fork && (ast_opt_remote || ast_opt_console)) { + ast_log(LOG_WARNING, "'alwaysfork' is not compatible with console or remote console mode; ignored\n"); + ast_clear_flag(&ast_options, AST_OPT_FLAG_ALWAYS_FORK); + } + if (ast_opt_dump_core) { struct rlimit l; memset(&l, 0, sizeof(l)); diff --git a/main/astobj2.c b/main/astobj2.c index 77f0f2962..212b64ed9 100644 --- a/main/astobj2.c +++ b/main/astobj2.c @@ -170,6 +170,21 @@ int _ao2_unlock(void *user_data, const char *file, const char *func, int line, c #endif } +int ao2_trylock(void *user_data) +{ + struct astobj2 *p = INTERNAL_OBJ(user_data); + int ret; + + if (p == NULL) + return -1; + ret = ast_mutex_trylock(&p->priv_data.lock); +#ifdef AO2_DEBUG + if (!ret) + ast_atomic_fetchadd_int(&ao2.total_locked, 1); +#endif + return ret; +} + /* * The argument is a pointer to the user portion. */ diff --git a/main/manager.c b/main/manager.c index e0ab9a16b..0076f64f3 100644 --- a/main/manager.c +++ b/main/manager.c @@ -2059,7 +2059,8 @@ static int action_command(struct mansession *s, const struct message *m) /*! \brief helper function for originate */ struct fast_originate_helper { char tech[AST_MAX_EXTENSION]; - char data[AST_MAX_EXTENSION]; + /*! data can contain a channel name, extension number, username, password, etc. */ + char data[512]; int timeout; int format; /*!< Codecs used for a call */ char app[AST_MAX_APP]; diff --git a/main/pbx.c b/main/pbx.c index 4c8f23caf..3a78612b3 100644 --- a/main/pbx.c +++ b/main/pbx.c @@ -6795,7 +6795,7 @@ int ast_add_extension2(struct ast_context *con, } res = 0; /* some compilers will think it is uninitialized otherwise */ for (e = con->root; e; el = e, e = e->next) { /* scan the extension list */ - res = ext_cmp(e->exten, extension); + res = ext_cmp(e->exten, tmp->exten); if (res == 0) { /* extension match, now look at cidmatch */ if (!e->matchcid && !tmp->matchcid) res = 0; |