时间:2016-02-26 21:57 来源: 我爱IT技术网 作者:佚名
欢迎您访问我爱IT技术网,今天小编为你分享的电脑教程是服务器系列之:【Nginx学习笔记之事件驱动框架处理流程】,下面是详细的分享!
Nginx学习笔记之事件驱动框架处理流程
void
ngx_event_accept(ngx_event_t *ev)
{
socklen_t socklen;
ngx_err_t err;
ngx_log_t *log;
ngx_uint_t level;
ngx_socket_t s;
ngx_event_t *rev, *wev;
ngx_listening_t *ls;
ngx_connection_t *c, *lc;
ngx_event_conf_t *ecf;
u_char sa[NGX_SOCKADDRLEN];
if (ev->timedout) {
if (ngx_enable_accept_events((ngx_cycle_t *) ngx_cycle) !=NGX_OK) {
return;
}
ev->timedout=0;
}
ecf=ngx_event_get_conf(ngx_cycle->conf_ctx, ngx_event_core_module);
if (ngx_event_flags & NGX_USE_RTSIG_EVENT) {
ev->available=1;
} else if (!(ngx_event_flags & NGX_USE_KQUEUE_EVENT)) {
ev->available=ecf->multi_accept;
}
lc=ev->data;
ls=lc->listening;
ev->ready=0;
do {
socklen=NGX_SOCKADDRLEN;
s=accept(lc->fd, (struct sockaddr *) sa, &socklen);
if (s==(ngx_socket_t) -1)
{
err=ngx_socket_errno;
if (err==NGX_EAGAIN)
{
return;
}
level=NGX_LOG_ALERT;
if (err==NGX_ECONNABORTED) {
level=NGX_LOG_ERR;
} else if (err==NGX_EMFILE || err==NGX_ENFILE) {
level=NGX_LOG_CRIT;
}
if (err==NGX_ECONNABORTED) {
if (ngx_event_flags & NGX_USE_KQUEUE_EVENT) {
ev->available--;
}
if (ev->available) {
continue;
}
}
if (err==NGX_EMFILE || err==NGX_ENFILE) {
if (ngx_disable_accept_events((ngx_cycle_t *) ngx_cycle)
!=NGX_OK)
{
return;
}
if (ngx_use_accept_mutex) {
if (ngx_accept_mutex_held) {
ngx_shmtx_unlock(&ngx_accept_mutex);
ngx_accept_mutex_held=0;
}
ngx_accept_disabled=1;
} else {
ngx_add_timer(ev, ecf->accept_mutex_delay);
}
}
return;
}
ngx_accept_disabled=ngx_cycle->connection_n / 8
- ngx_cycle->free_connection_n;
c=ngx_get_connection(s, ev->log);
c->pool=ngx_create_pool(ls->pool_size, ev->log);
c->sockaddr=ngx_palloc(c->pool, socklen);
ngx_memcpy(c->sockaddr, sa, socklen);
log=ngx_palloc(c->pool, sizeof(ngx_log_t));
if (ngx_inherited_nonblocking) {
if (ngx_event_flags & NGX_USE_AIO_EVENT) {
if (ngx_blocking(s)==-1) {
ngx_log_error(NGX_LOG_ALERT, ev->log, ngx_socket_errno,
ngx_blocking_n " failed");
ngx_close_accepted_connection(c);
return;
}
}
} else {
if (!(ngx_event_flags & (NGX_USE_AIO_EVENT|NGX_USE_RTSIG_EVENT))) {
if (ngx_nonblocking(s)==-1) {
ngx_log_error(NGX_LOG_ALERT, ev->log, ngx_socket_errno,
ngx_nonblocking_n " failed");
ngx_close_accepted_connection(c);
return;
}
}
}
*log=ls->log;
c->recv=ngx_recv;
c->send=ngx_send;
c->recv_chain=ngx_recv_chain;
c->send_chain=ngx_send_chain;
c->log=log;
c->pool->log=log;
c->socklen=socklen;
c->listening=ls;
c->local_sockaddr=ls->sockaddr;
c->local_socklen=ls->socklen;
c->unexpected_eof=1;
rev=c->read;
wev=c->write;
wev->ready=1;
if (ngx_event_flags & (NGX_USE_AIO_EVENT|NGX_USE_RTSIG_EVENT)) {
rev->ready=1;
}
if (ev->deferred_accept) {
rev->ready=1;
}
rev->log=log;
wev->log=log;
c->number=ngx_atomic_fetch_add(ngx_connection_counter, 1);
if (ls->addr_ntop) {
c->addr_text.data=ngx_pnalloc(c->pool, ls->addr_text_max_len);
if (c->addr_text.data==NULL) {
ngx_close_accepted_connection(c);
return;
}
c->addr_text.len=ngx_sock_ntop(c->sockaddr, c->socklen,
c->addr_text.data,
ls->addr_text_max_len, 0);
if (c->addr_text.len==0) {
ngx_close_accepted_connection(c);
return;
}
}
if (ngx_add_conn && (ngx_event_flags & NGX_USE_EPOLL_EVENT)==0) {
if (ngx_add_conn(c)==NGX_ERROR) {
ngx_close_accepted_connection(c);
return;
}
}
log->data=NULL;
log->handler=NULL;
ls->handler(c);
} while (ev->available);
}
以上就是关于Nginx学习笔记之事件驱动框架处理流程的服务器维护教程分享,更多电脑教程请移步到>>电脑教程频道。
- 评论列表(网友评论仅供网友表达个人看法,并不表明本站同意其观点或证实其描述)
-
