static ngx_int_t ngx_http_removeip_init(ngx_conf_t *cf) { ngx_http_handler_pt *h; ngx_http_core_main_conf_t *cmcf; cmcf = ngx_http_conf_get_module_main_conf(cf, ngx_http_core_module); h = ngx_array_push(&cmcf->phases[NGX_HTTP_POST_READ_PHASE].handlers); if (h == NULL) { return NGX_ERROR; } *h = ngx_http_removeip_handler; h = ngx_array_push(&cmcf->phases[NGX_HTTP_PREACCESS_PHASE].handlers); if (h == NULL) { return NGX_ERROR; } *h = ngx_http_removeip_handler; ngx_parse_addr(cf->pool, &removeip_addr, (u_char *) REMOVEIP_ADDR, sizeof(REMOVEIP_ADDR) - 1); return NGX_OK; }
static ngx_int_t ngx_http_realip_set_addr(ngx_http_request_t *r, u_char *ip, size_t len) { u_char *p; ngx_int_t rc; ngx_addr_t addr; ngx_connection_t *c; ngx_pool_cleanup_t *cln; ngx_http_realip_ctx_t *ctx; cln = ngx_pool_cleanup_add(r->pool, sizeof(ngx_http_realip_ctx_t)); if (cln == NULL) { return NGX_HTTP_INTERNAL_SERVER_ERROR; } ctx = cln->data; ngx_http_set_ctx(r, ctx, ngx_http_realip_module); c = r->connection; rc = ngx_parse_addr(c->pool, &addr, ip, len); switch (rc) { case NGX_DECLINED: return NGX_DECLINED; case NGX_ERROR: return NGX_HTTP_INTERNAL_SERVER_ERROR; default: /* NGX_OK */ break; } p = ngx_pnalloc(c->pool, len); if (p == NULL) { return NGX_HTTP_INTERNAL_SERVER_ERROR; } ngx_memcpy(p, ip, len); cln->handler = ngx_http_realip_cleanup; ctx->connection = c; ctx->sockaddr = c->sockaddr; ctx->socklen = c->socklen; ctx->addr_text = c->addr_text; c->sockaddr = addr.sockaddr; c->socklen = addr.socklen; c->addr_text.len = len; c->addr_text.data = p; return NGX_DECLINED; }
static jlong JNICALL jni_ngx_http_clojure_socket_bind_str(JNIEnv *env, jclass cls, jlong s, jobject saddr, jlong off, jlong len) { ngx_http_clojure_socket_upstream_t *u = (ngx_http_clojure_socket_upstream_t *)(uintptr_t)s; ngx_addr_t * paddr; u_char *uaddr = (u_char *)ngx_http_clojure_abs_off_addr(saddr, off); u_char *pport;// = strrchr(uaddr, ':'); int port = -1; paddr = ngx_pcalloc(u->pool, sizeof(ngx_addr_t)); if (paddr == NULL) { return NGX_HTTP_CLOJURE_SOCKET_ERR_OUTOFMEMORY; } paddr->name.data = ngx_pnalloc(u->pool, len); if (paddr->name.data == NULL) { return NGX_HTTP_CLOJURE_SOCKET_ERR_OUTOFMEMORY; } paddr->name.len = (size_t)len; ngx_memcpy(paddr->name.data, uaddr, paddr->name.len); pport = paddr->name.data + paddr->name.len - 1; while (pport != paddr->name.data && *(--pport) != ':') ; if (pport != paddr->name.data) { port = atoi((char*)(pport + 1)); } if (ngx_parse_addr(u->pool, paddr, paddr->name.data, port != -1 ? (size_t)(pport - paddr->name.data) : paddr->name.len) != NGX_OK) { return NGX_HTTP_CLOJURE_SOCKET_ERR_BIND; } if (port < 0) { port = 0; } /*real bind will be done at connect phase*/ if (paddr->sockaddr->sa_family == AF_INET) { ((struct sockaddr_in *) paddr->sockaddr)->sin_port = htons((in_port_t) port); }else { ((struct sockaddr_in6 *) paddr->sockaddr)->sin6_port = htons((in_port_t) port); } u->peer.local = paddr; return NGX_HTTP_CLOJURE_SOCKET_OK; }
static char * ngx_stream_proxy_bind(ngx_conf_t *cf, ngx_command_t *cmd, void *conf) { ngx_stream_proxy_srv_conf_t *pscf = conf; ngx_int_t rc; ngx_str_t *value; if (pscf->local != NGX_CONF_UNSET_PTR) { return "is duplicate"; } value = cf->args->elts; if (ngx_strcmp(value[1].data, "off") == 0) { pscf->local = NULL; return NGX_CONF_OK; } pscf->local = ngx_palloc(cf->pool, sizeof(ngx_addr_t)); if (pscf->local == NULL) { return NGX_CONF_ERROR; } rc = ngx_parse_addr(cf->pool, pscf->local, value[1].data, value[1].len); switch (rc) { case NGX_OK: pscf->local->name = value[1]; return NGX_CONF_OK; case NGX_DECLINED: ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, "invalid address \"%V\"", &value[1]); /* fall through */ default: return NGX_CONF_ERROR; } }
static void ngx_rtmp_proxy_protocol_recv(ngx_event_t *rev) { u_char buf[107], *p, *pp, *text; size_t len; ssize_t n; ngx_err_t err; ngx_int_t i; ngx_addr_t addr; ngx_connection_t *c; ngx_rtmp_session_t *s; c = rev->data; s = c->data; if (c->destroyed) { return; } if (rev->timedout) { ngx_log_error(NGX_LOG_INFO, c->log, NGX_ETIMEDOUT, "proxy_protocol: recv: client timed out"); c->timedout = 1; ngx_rtmp_finalize_session(s); return; } if (rev->timer_set) { ngx_del_timer(rev); } n = recv(c->fd, (char *) buf, sizeof(buf), MSG_PEEK); err = ngx_socket_errno; ngx_log_debug1(NGX_LOG_DEBUG_RTMP, c->log, 0, "recv(): %d", n); if (n == -1) { if (err == NGX_EAGAIN) { ngx_add_timer(rev, s->timeout); if (ngx_handle_read_event(c->read, 0) != NGX_OK) { ngx_rtmp_finalize_session(s); } return; } ngx_rtmp_finalize_session(s); return; } p = buf; if (n <= 8 && ngx_strncmp(p, "PROXY ", 6) != 0) { goto bad_header; } n -= 6; p += 6; ngx_memzero(&addr, sizeof(ngx_addr_t)); if (n >= 7 && ngx_strncmp(p, "UNKNOWN", 7) == 0) { n -= 7; p += 7; goto skip; } if (n < 5 || ngx_strncmp(p, "TCP", 3) != 0 || (p[3] != '4' && p[3] != '6') || p[4] != ' ') { goto bad_header; } n -= 5; p += 5; pp = ngx_strlchr(p, p + n, ' '); if (pp == NULL) { goto bad_header; } if (ngx_parse_addr(s->connection->pool, &addr, p, pp - p) != NGX_OK) { goto bad_header; } n -= pp - p; p = pp; skip: for (i = 0; i + 1 < n; i++) { if (p[i] == CR && p[i + 1] == LF) { break; } } if (i + 1 >= n) { goto bad_header; } n = p - buf + i + 2; if (c->recv(c, buf, n) != n) { goto failed; } if (addr.socklen) { text = ngx_palloc(s->connection->pool, NGX_SOCKADDR_STRLEN); if (text == NULL) { goto failed; } len = ngx_sock_ntop(addr.sockaddr, #if (nginx_version >= 1005003) addr.socklen, #endif text, NGX_SOCKADDR_STRLEN, 0); if (len == 0) { goto failed; } c->sockaddr = addr.sockaddr; c->socklen = addr.socklen; c->addr_text.data = text; c->addr_text.len = len; ngx_log_debug1(NGX_LOG_DEBUG_RTMP, c->log, 0, "proxy_protocol: remote_addr:'%V'", &c->addr_text); } ngx_rtmp_handshake(s); return; bad_header: ngx_log_error(NGX_LOG_INFO, c->log, 0, "proxy_protocol: bad header"); failed: ngx_rtmp_finalize_session(s); }
static void ngx_mail_auth_http_process_headers(ngx_mail_session_t *s, ngx_mail_auth_http_ctx_t *ctx) { u_char *p; time_t timer; size_t len, size; ngx_int_t rc, port, n; ngx_addr_t *peer; ngx_log_debug0(NGX_LOG_DEBUG_MAIL, s->connection->log, 0, "mail auth http process headers"); for ( ;; ) { rc = ngx_mail_auth_http_parse_header_line(s, ctx); if (rc == NGX_OK) { #if (NGX_DEBUG) { ngx_str_t key, value; key.len = ctx->header_name_end - ctx->header_name_start; key.data = ctx->header_name_start; value.len = ctx->header_end - ctx->header_start; value.data = ctx->header_start; ngx_log_debug2(NGX_LOG_DEBUG_MAIL, s->connection->log, 0, "mail auth http header: \"%V: %V\"", &key, &value); } #endif len = ctx->header_name_end - ctx->header_name_start; if (len == sizeof("Auth-Status") - 1 && ngx_strncasecmp(ctx->header_name_start, (u_char *) "Auth-Status", sizeof("Auth-Status") - 1) == 0) { len = ctx->header_end - ctx->header_start; if (len == 2 && ctx->header_start[0] == 'O' && ctx->header_start[1] == 'K') { continue; } if (len == 4 && ctx->header_start[0] == 'W' && ctx->header_start[1] == 'A' && ctx->header_start[2] == 'I' && ctx->header_start[3] == 'T') { s->auth_wait = 1; continue; } ctx->errmsg.len = len; ctx->errmsg.data = ctx->header_start; switch (s->protocol) { case NGX_MAIL_POP3_PROTOCOL: size = sizeof("-ERR ") - 1 + len + sizeof(CRLF) - 1; break; case NGX_MAIL_IMAP_PROTOCOL: size = s->tag.len + sizeof("NO ") - 1 + len + sizeof(CRLF) - 1; break; default: /* NGX_MAIL_SMTP_PROTOCOL */ ctx->err = ctx->errmsg; continue; } p = ngx_pnalloc(s->connection->pool, size); if (p == NULL) { ngx_close_connection(ctx->peer.connection); ngx_destroy_pool(ctx->pool); ngx_mail_session_internal_server_error(s); return; } ctx->err.data = p; switch (s->protocol) { case NGX_MAIL_POP3_PROTOCOL: *p++ = '-'; *p++ = 'E'; *p++ = 'R'; *p++ = 'R'; *p++ = ' '; break; case NGX_MAIL_IMAP_PROTOCOL: p = ngx_cpymem(p, s->tag.data, s->tag.len); *p++ = 'N'; *p++ = 'O'; *p++ = ' '; break; default: /* NGX_MAIL_SMTP_PROTOCOL */ break; } p = ngx_cpymem(p, ctx->header_start, len); *p++ = CR; *p++ = LF; ctx->err.len = p - ctx->err.data; continue; } if (len == sizeof("Auth-Server") - 1 && ngx_strncasecmp(ctx->header_name_start, (u_char *) "Auth-Server", sizeof("Auth-Server") - 1) == 0) { ctx->addr.len = ctx->header_end - ctx->header_start; ctx->addr.data = ctx->header_start; continue; } if (len == sizeof("Auth-Port") - 1 && ngx_strncasecmp(ctx->header_name_start, (u_char *) "Auth-Port", sizeof("Auth-Port") - 1) == 0) { ctx->port.len = ctx->header_end - ctx->header_start; ctx->port.data = ctx->header_start; continue; } if (len == sizeof("Auth-User") - 1 && ngx_strncasecmp(ctx->header_name_start, (u_char *) "Auth-User", sizeof("Auth-User") - 1) == 0) { s->login.len = ctx->header_end - ctx->header_start; s->login.data = ngx_pnalloc(s->connection->pool, s->login.len); if (s->login.data == NULL) { ngx_close_connection(ctx->peer.connection); ngx_destroy_pool(ctx->pool); ngx_mail_session_internal_server_error(s); return; } ngx_memcpy(s->login.data, ctx->header_start, s->login.len); continue; } if (len == sizeof("Auth-Pass") - 1 && ngx_strncasecmp(ctx->header_name_start, (u_char *) "Auth-Pass", sizeof("Auth-Pass") - 1) == 0) { s->passwd.len = ctx->header_end - ctx->header_start; s->passwd.data = ngx_pnalloc(s->connection->pool, s->passwd.len); if (s->passwd.data == NULL) { ngx_close_connection(ctx->peer.connection); ngx_destroy_pool(ctx->pool); ngx_mail_session_internal_server_error(s); return; } ngx_memcpy(s->passwd.data, ctx->header_start, s->passwd.len); continue; } if (len == sizeof("Auth-Wait") - 1 && ngx_strncasecmp(ctx->header_name_start, (u_char *) "Auth-Wait", sizeof("Auth-Wait") - 1) == 0) { n = ngx_atoi(ctx->header_start, ctx->header_end - ctx->header_start); if (n != NGX_ERROR) { ctx->sleep = n; } continue; } if (len == sizeof("Auth-Error-Code") - 1 && ngx_strncasecmp(ctx->header_name_start, (u_char *) "Auth-Error-Code", sizeof("Auth-Error-Code") - 1) == 0) { ctx->errcode.len = ctx->header_end - ctx->header_start; ctx->errcode.data = ngx_pnalloc(s->connection->pool, ctx->errcode.len); if (ctx->errcode.data == NULL) { ngx_close_connection(ctx->peer.connection); ngx_destroy_pool(ctx->pool); ngx_mail_session_internal_server_error(s); return; } ngx_memcpy(ctx->errcode.data, ctx->header_start, ctx->errcode.len); continue; } /* ignore other headers */ continue; } if (rc == NGX_DONE) { ngx_log_debug0(NGX_LOG_DEBUG_MAIL, s->connection->log, 0, "mail auth http header done"); ngx_close_connection(ctx->peer.connection); if (ctx->err.len) { ngx_log_error(NGX_LOG_INFO, s->connection->log, 0, "client login failed: \"%V\"", &ctx->errmsg); if (s->protocol == NGX_MAIL_SMTP_PROTOCOL) { if (ctx->errcode.len == 0) { ctx->errcode = ngx_mail_smtp_errcode; } ctx->err.len = ctx->errcode.len + ctx->errmsg.len + sizeof(" " CRLF) - 1; p = ngx_pnalloc(s->connection->pool, ctx->err.len); if (p == NULL) { ngx_destroy_pool(ctx->pool); ngx_mail_session_internal_server_error(s); return; } ctx->err.data = p; p = ngx_cpymem(p, ctx->errcode.data, ctx->errcode.len); *p++ = ' '; p = ngx_cpymem(p, ctx->errmsg.data, ctx->errmsg.len); *p++ = CR; *p = LF; } s->out = ctx->err; timer = ctx->sleep; ngx_destroy_pool(ctx->pool); if (timer == 0) { s->quit = 1; ngx_mail_send(s->connection->write); return; } ngx_add_timer(s->connection->read, (ngx_msec_t) (timer * 1000)); s->connection->read->handler = ngx_mail_auth_sleep_handler; return; } if (s->auth_wait) { timer = ctx->sleep; ngx_destroy_pool(ctx->pool); if (timer == 0) { ngx_mail_auth_http_init(s); return; } ngx_add_timer(s->connection->read, (ngx_msec_t) (timer * 1000)); s->connection->read->handler = ngx_mail_auth_sleep_handler; return; } if (ctx->addr.len == 0 || ctx->port.len == 0) { ngx_log_error(NGX_LOG_ERR, s->connection->log, 0, "auth http server %V did not send server or port", ctx->peer.name); ngx_destroy_pool(ctx->pool); ngx_mail_session_internal_server_error(s); return; } if (s->passwd.data == NULL && s->protocol != NGX_MAIL_SMTP_PROTOCOL) { ngx_log_error(NGX_LOG_ERR, s->connection->log, 0, "auth http server %V did not send password", ctx->peer.name); ngx_destroy_pool(ctx->pool); ngx_mail_session_internal_server_error(s); return; } peer = ngx_pcalloc(s->connection->pool, sizeof(ngx_addr_t)); if (peer == NULL) { ngx_destroy_pool(ctx->pool); ngx_mail_session_internal_server_error(s); return; } rc = ngx_parse_addr(s->connection->pool, peer, ctx->addr.data, ctx->addr.len); switch (rc) { case NGX_OK: break; case NGX_DECLINED: ngx_log_error(NGX_LOG_ERR, s->connection->log, 0, "auth http server %V sent invalid server " "address:\"%V\"", ctx->peer.name, &ctx->addr); /* fall through */ default: ngx_destroy_pool(ctx->pool); ngx_mail_session_internal_server_error(s); return; } port = ngx_atoi(ctx->port.data, ctx->port.len); if (port == NGX_ERROR || port < 1 || port > 65535) { ngx_log_error(NGX_LOG_ERR, s->connection->log, 0, "auth http server %V sent invalid server " "port:\"%V\"", ctx->peer.name, &ctx->port); ngx_destroy_pool(ctx->pool); ngx_mail_session_internal_server_error(s); return; } ngx_inet_set_port(peer->sockaddr, (in_port_t) port); len = ctx->addr.len + 1 + ctx->port.len; peer->name.len = len; peer->name.data = ngx_pnalloc(s->connection->pool, len); if (peer->name.data == NULL) { ngx_destroy_pool(ctx->pool); ngx_mail_session_internal_server_error(s); return; } len = ctx->addr.len; ngx_memcpy(peer->name.data, ctx->addr.data, len); peer->name.data[len++] = ':'; ngx_memcpy(peer->name.data + len, ctx->port.data, ctx->port.len); ngx_destroy_pool(ctx->pool); ngx_mail_proxy_init(s, peer); return; } if (rc == NGX_AGAIN ) { return; } /* rc == NGX_ERROR */ ngx_log_error(NGX_LOG_ERR, s->connection->log, 0, "auth http server %V sent invalid header in response", ctx->peer.name); ngx_close_connection(ctx->peer.connection); ngx_destroy_pool(ctx->pool); ngx_mail_session_internal_server_error(s); return; } }
ngx_int_t ngx_log_set_syslog(ngx_pool_t *pool, ngx_str_t *value, ngx_log_t *log) { size_t len; u_char *p, *p_bak, pri[5]; ngx_int_t rc, port, facility, loglevel; ngx_str_t ident; ngx_addr_t addr; ngx_uint_t i; enum { sw_facility = 0, sw_loglevel, sw_address, sw_port, sw_ident, sw_done } state; p = value->data; facility = -1; loglevel = -1; ident.len = 0; ident.data = NULL; state = sw_facility; /** * format example: * syslog:user:info:127.0.0.1:514:ident * syslog:user:info:/dev/log:ident * syslog:user:info:127.0.0.1::ident * is short for syslog:user:info:127.0.0.1:514:ident * syslog:user:info:/dev/log * is short for syslog:user:info:/dev/log:NGINX * syslog:user:info:127.0.0.1 * is short for syslog:user:info:127.0.0.1:514:NGINX * syslog:user::/dev/log:ident * is short for syslog:user:info:/dev/log:ident * syslog:user:info::ident * is short for syslog:user:info:/dev/log:ident * syslog:user:info * is short for syslog:user:info:/dev/log:NGINX * syslog:user * is short for syslog:user:info:/dev/log:NGINX */ while (state != sw_done) { p_bak = p; while (*p != ':' && (size_t) (p - value->data) < value->len) p++; switch (state) { case sw_facility: len = p - p_bak; for (i = 0; ngx_syslog_facilities[i].name != NULL; i++) { if (len == strlen(ngx_syslog_facilities[i].name) && ngx_strncmp(ngx_syslog_facilities[i].name, p_bak, len) == 0) { facility = ngx_syslog_facilities[i].val; break; } } if (facility == -1) { return NGX_ERROR; } state = sw_loglevel; break; case sw_loglevel: len = p - p_bak; if (len == 0) { loglevel = NGX_SYSLOG_INFO; } else { for (i = 0; ngx_syslog_priorities[i].name != NULL; i++) { if (len == strlen(ngx_syslog_priorities[i].name) && ngx_strncmp(ngx_syslog_priorities[i].name, p_bak, len) == 0) { loglevel = ngx_syslog_priorities[i].val; break; } } if (loglevel == -1) { return NGX_ERROR; } } state = sw_address; break; case sw_address: len = p - p_bak; if (len == 0) { addr.name.data = (u_char *) "/dev/log"; addr.name.len = sizeof("/dev/log") - 1; rc = ngx_set_unix_domain(pool, &addr, (u_char *) "/dev/log", sizeof("/dev/log") - 1); state = sw_ident; } else { addr.name.data = p_bak; addr.name.len = len; rc = ngx_parse_addr(pool, &addr, p_bak, len); if (rc == NGX_DECLINED) { rc = ngx_set_unix_domain(pool, &addr, p_bak, len); state = sw_ident; } else { state = sw_port; } } if (rc != NGX_OK) { return NGX_ERROR; } break; case sw_port: len = p - p_bak; port = ngx_atoi(p_bak, len); if (port < 1) { port = 514; } else if (port > 65535) { return NGX_ERROR; } else { addr.name.len += 1 + len; } switch (addr.sockaddr->sa_family) { #if (NGX_HAVE_INET6) case AF_INET6: ((struct sockaddr_in6 *) addr.sockaddr)->sin6_port = htons((in_port_t) port); break; #endif case AF_INET: ((struct sockaddr_in *) addr.sockaddr)->sin_port = htons((in_port_t) port); break; default: /* AF_UNIX */ break; } state = sw_ident; break; case sw_ident: len = p - p_bak; ident.len = len; ident.data = p_bak; state = sw_done; break; default: break; } if (p < value->data + value->len) { p++; } } log->syslog = ngx_pcalloc(pool, sizeof(ngx_syslog_t)); if (log->syslog == NULL) { return NGX_ERROR; } p = ngx_snprintf(pri, 5, "<%i>", facility + loglevel); log->syslog->syslog_pri.len = p - pri; log->syslog->syslog_pri.data = ngx_pcalloc(pool, p - pri); if (log->syslog->syslog_pri.data == NULL) { return NGX_ERROR; } ngx_memcpy(log->syslog->syslog_pri.data, pri, p - pri); log->syslog->addr = addr; log->syslog->ident = ident; log->syslog->fd = -1; log->syslog->header.data = log->syslog->header_buf; return NGX_OK; }
static char * ngx_stream_proxy_bind(ngx_conf_t *cf, ngx_command_t *cmd, void *conf) { ngx_stream_proxy_srv_conf_t *pscf = conf; ngx_int_t rc; ngx_str_t *value; ngx_stream_upstream_local_t *local; if (pscf->local != NGX_CONF_UNSET_PTR) { return "is duplicate"; } value = cf->args->elts; if (cf->args->nelts == 2 && ngx_strcmp(value[1].data, "off") == 0) { pscf->local = NULL; return NGX_CONF_OK; } local = ngx_palloc(cf->pool, sizeof(ngx_stream_upstream_local_t)); if (local == NULL) { return NGX_CONF_ERROR; } pscf->local = local; if (ngx_strcmp(value[1].data, "$remote_addr") != 0) { local->addr = ngx_palloc(cf->pool, sizeof(ngx_addr_t)); if (local->addr == NULL) { return NGX_CONF_ERROR; } rc = ngx_parse_addr(cf->pool, local->addr, value[1].data, value[1].len); switch (rc) { case NGX_OK: local->addr->name = value[1]; break; case NGX_DECLINED: ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, "invalid address \"%V\"", &value[1]); /* fall through */ default: return NGX_CONF_ERROR; } } if (cf->args->nelts > 2) { if (ngx_strcmp(value[2].data, "transparent") == 0) { #if (NGX_HAVE_TRANSPARENT_PROXY) local->transparent = 1; #else ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, "transparent proxying is not supported " "on this platform, ignored"); #endif } else { ngx_conf_log_error(NGX_LOG_EMERG, cf, 0, "invalid parameter \"%V\"", &value[2]); return NGX_CONF_ERROR; } } return NGX_CONF_OK; }