comment and cleanup the main thread.
On passing, fix a bug: close the socket if the allocation of a structure for the new session fails. (the bugfix is a candidate for 1.4) git-svn-id: https://origsvn.digium.com/svn/asterisk/trunk@45561 65c4cc65-6c06-0410-ace0-fbb531ad65f3
This commit is contained in:
parent
eb3767cafe
commit
71cf14207c
|
@ -2046,29 +2046,32 @@ static void *session_do(void *data)
|
|||
return NULL;
|
||||
}
|
||||
|
||||
/*! \brief The thread accepting connections on the manager interface port.
|
||||
* As a side effect, it purges stale sessions, one per each iteration,
|
||||
* which is at least every 5 seconds.
|
||||
*/
|
||||
static void *accept_thread(void *ignore)
|
||||
{
|
||||
int as;
|
||||
struct sockaddr_in sin;
|
||||
socklen_t sinlen;
|
||||
struct eventqent *eqe;
|
||||
struct mansession *s;
|
||||
struct protoent *p;
|
||||
int arg = 1;
|
||||
int flags;
|
||||
pthread_attr_t attr;
|
||||
time_t now;
|
||||
struct pollfd pfds[1];
|
||||
|
||||
pthread_attr_init(&attr);
|
||||
pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED);
|
||||
|
||||
for (;;) {
|
||||
time(&now);
|
||||
struct mansession *s;
|
||||
time_t now = time(NULL);
|
||||
int as;
|
||||
struct sockaddr_in sin;
|
||||
socklen_t sinlen;
|
||||
struct protoent *p;
|
||||
int flags;
|
||||
struct pollfd pfds[1];
|
||||
|
||||
AST_LIST_LOCK(&sessions);
|
||||
AST_LIST_TRAVERSE_SAFE_BEGIN(&sessions, s, list) {
|
||||
if (s->sessiontimeout && (now > s->sessiontimeout) && !s->inuse) {
|
||||
AST_LIST_REMOVE_CURRENT(&sessions, list);
|
||||
ast_atomic_fetchadd_int(&num_sessions, -1);
|
||||
if (s->authenticated && (option_verbose > 1) && displayconnects) {
|
||||
ast_verbose(VERBOSE_PREFIX_2 "HTTP Manager '%s' timed out from %s\n",
|
||||
s->username, ast_inet_ntoa(s->sin.sin_addr));
|
||||
|
@ -2082,13 +2085,11 @@ static void *accept_thread(void *ignore)
|
|||
always keep at least one in the queue */
|
||||
/* XXX why do we need one entry in the queue ? */
|
||||
while (master_eventq->next && !master_eventq->usecount) {
|
||||
eqe = master_eventq;
|
||||
struct eventqent *eqe = master_eventq;
|
||||
master_eventq = master_eventq->next;
|
||||
free(eqe);
|
||||
}
|
||||
AST_LIST_UNLOCK(&sessions);
|
||||
if (s)
|
||||
ast_atomic_fetchadd_int(&num_sessions, -1);
|
||||
|
||||
sinlen = sizeof(sin);
|
||||
pfds[0].fd = asock;
|
||||
|
@ -2104,30 +2105,34 @@ static void *accept_thread(void *ignore)
|
|||
}
|
||||
p = getprotobyname("tcp");
|
||||
if (p) {
|
||||
int arg = 1;
|
||||
if( setsockopt(as, p->p_proto, TCP_NODELAY, (char *)&arg, sizeof(arg) ) < 0 ) {
|
||||
ast_log(LOG_WARNING, "Failed to set manager tcp connection to TCP_NODELAY mode: %s\n", strerror(errno));
|
||||
}
|
||||
}
|
||||
if (!(s = ast_calloc(1, sizeof(*s))))
|
||||
s = ast_calloc(1, sizeof(*s)); /* allocate a new record */
|
||||
if (!s) {
|
||||
close(as);
|
||||
continue;
|
||||
}
|
||||
|
||||
ast_atomic_fetchadd_int(&num_sessions, 1);
|
||||
|
||||
memcpy(&s->sin, &sin, sizeof(sin));
|
||||
s->sin = sin;
|
||||
s->writetimeout = 100;
|
||||
s->waiting_thread = AST_PTHREADT_NULL;
|
||||
|
||||
if (!block_sockets) {
|
||||
/* For safety, make sure socket is non-blocking */
|
||||
flags = fcntl(as, F_GETFL);
|
||||
fcntl(as, F_SETFL, flags | O_NONBLOCK);
|
||||
} else {
|
||||
flags = fcntl(as, F_GETFL);
|
||||
fcntl(as, F_SETFL, flags & ~O_NONBLOCK);
|
||||
}
|
||||
flags = fcntl(as, F_GETFL);
|
||||
if (!block_sockets) /* For safety, make sure socket is non-blocking */
|
||||
flags |= O_NONBLOCK;
|
||||
else
|
||||
flags &= ~O_NONBLOCK;
|
||||
fcntl(as, F_SETFL, flags);
|
||||
|
||||
ast_mutex_init(&s->__lock);
|
||||
s->fd = as;
|
||||
s->send_events = -1;
|
||||
|
||||
ast_atomic_fetchadd_int(&num_sessions, 1);
|
||||
AST_LIST_LOCK(&sessions);
|
||||
AST_LIST_INSERT_HEAD(&sessions, s, list);
|
||||
/* Find the last place in the master event queue and hook ourselves
|
||||
|
|
Loading…
Reference in New Issue