Merge some of Mahmut's patches

git-svn-id: https://origsvn.digium.com/svn/asterisk/trunk@666 65c4cc65-6c06-0410-ace0-fbb531ad65f3
This commit is contained in:
Mark Spencer
2003-03-20 17:21:54 +00:00
parent d5251a8505
commit d0d50a4ad7
4 changed files with 68 additions and 26 deletions

View File

@@ -223,21 +223,36 @@ static int agent_call(struct ast_channel *ast, char *dest, int timeout)
struct agent_pvt *p = ast->pvt->pvt;
int res = -1;
ast_pthread_mutex_lock(&p->lock);
ast_verbose( VERBOSE_PREFIX_3 "agent_call, call to agent '%s' call on '%s'\n", p->agent, p->chan->name);
ast_log( LOG_DEBUG, "Playing beep, lang '%s'\n", p->chan->language);
res = ast_streamfile(p->chan, "beep", p->chan->language);
if (!res)
ast_log( LOG_DEBUG, "Played beep, result '%d'\n", res);
if (!res) {
res = ast_waitstream(p->chan, "");
ast_log( LOG_DEBUG, "Waited for stream, result '%d'\n", res);
}
if (!res) {
res = ast_set_read_format(p->chan, ast_best_codec(p->chan->nativeformats));
ast_log( LOG_DEBUG, "Set read format, result '%d'\n", res);
if (res)
ast_log(LOG_WARNING, "Unable to set read format to %d\n", ast_best_codec(p->chan->nativeformats));
}
else {
// Agent hung-up
p->chan = NULL;
}
if (!res) {
ast_set_write_format(p->chan, ast_best_codec(p->chan->nativeformats));
ast_log( LOG_DEBUG, "Set write format, result '%d'\n", res);
if (res)
ast_log(LOG_WARNING, "Unable to set write format to %d\n", ast_best_codec(p->chan->nativeformats));
}
/* Call is immediately up */
ast_setstate(ast, AST_STATE_UP);
if( !res )
{
/* Call is immediately up */
ast_setstate(ast, AST_STATE_UP);
}
CLEANUP(ast,p);
ast_pthread_mutex_unlock(&p->lock);
return res;
@@ -250,9 +265,6 @@ static int agent_hangup(struct ast_channel *ast)
p->owner = NULL;
ast->pvt->pvt = NULL;
p->app_sleep_cond = 1;
ast_pthread_mutex_unlock(&p->lock);
/* Release ownership of the agent to other threads (presumably running the login app). */
ast_pthread_mutex_unlock(&p->app_lock);
if (p->chan) {
/* If they're dead, go ahead and hang up on the agent now */
ast_pthread_mutex_lock(&p->chan->lock);
@@ -260,9 +272,20 @@ static int agent_hangup(struct ast_channel *ast)
ast_softhangup(p->chan, AST_SOFTHANGUP_EXPLICIT);
ast_moh_start(p->chan, p->moh);
ast_pthread_mutex_unlock(&p->chan->lock);
} else if (p->dead)
ast_pthread_mutex_unlock(&p->lock);
/* Release ownership of the agent to other threads (presumably running the login app). */
ast_pthread_mutex_unlock(&p->app_lock);
} else if (p->dead) {
/* Go ahead and lose it */
ast_pthread_mutex_unlock(&p->lock);
/* Release ownership of the agent to other threads (presumably running the login app). */
ast_pthread_mutex_unlock(&p->app_lock);
free(p);
} else {
ast_pthread_mutex_unlock(&p->lock);
/* Release ownership of the agent to other threads (presumably running the login app). */
ast_pthread_mutex_unlock(&p->app_lock);
}
return 0;
}
@@ -333,6 +356,15 @@ static struct ast_channel *agent_new(struct agent_pvt *p, int state)
ast_pthread_mutex_unlock(&p->lock); /* For other thread to read the condition. */
ast_pthread_mutex_lock(&p->app_lock);
ast_pthread_mutex_lock(&p->lock);
if( !p->chan )
{
ast_log(LOG_WARNING, "Agent disconnected while we were connecting the call\n");
p->owner = NULL;
tmp->pvt->pvt = NULL;
p->app_sleep_cond = 1;
ast_channel_free( tmp );
return NULL;
}
}
p->owning_app = pthread_self();
/* After the above step, there should not be any blockers. */
@@ -486,9 +518,6 @@ static int login_exec(struct ast_channel *chan, void *data)
char *opt_user = NULL;
char *options = NULL;
int play_announcement;
struct timespec required;
struct timespec remaining;
int delay;
LOCAL_USER_ADD(u);
@@ -577,21 +606,12 @@ static int login_exec(struct ast_channel *chan, void *data)
ast_pthread_mutex_unlock(&p->lock);
ast_pthread_mutex_unlock(&agentlock);
while (res >= 0) {
/* If we are not the owner, delay here for a while
* so other interested threads can kick in. */
delay = 0;
ast_pthread_mutex_lock(&p->lock);
if (p->chan != chan)
res = -1;
if (p->owner)
delay = 1;
ast_pthread_mutex_unlock(&p->lock);
if (delay) {
sched_yield();
required.tv_sec = 0;
required.tv_nsec = 20 * 1000 * 1000;
nanosleep( &required, &remaining );
}
/* Yield here so other interested threads can kick in. */
sched_yield();
if (res)
break;
@@ -603,12 +623,15 @@ static int login_exec(struct ast_channel *chan, void *data)
res = ast_safe_sleep_conditional( chan, 1000,
agent_cont_sleep, p );
pthread_mutex_unlock( &p->app_lock );
sched_yield();
}
ast_pthread_mutex_lock(&p->lock);
if (res && p->owner)
ast_log(LOG_WARNING, "Huh? We broke out when there was still an owner?\n");
/* Log us off if appropriate */
if (p->chan == chan)
p->chan = NULL;
ast_pthread_mutex_unlock(&p->lock);
if (option_verbose > 2)
ast_verbose(VERBOSE_PREFIX_3 "Agent '%s' logged out\n", p->agent);
manager_event(EVENT_FLAG_AGENT, "Agentlogoff",