comparison src/imap/ngx_imap_proxy_module.c @ 258:6ae1357b7b7c NGINX_0_4_14

nginx 0.4.14 *) Feature: the "proxy_pass_error_message" directive in IMAP/POP3 proxy. *) Feature: now configure detects system PCRE library on FreeBSD, Linux, and NetBSD. *) Bugfix: ngx_http_perl_module did not work with perl built with the threads support; bug appeared in 0.3.38. *) Bugfix: ngx_http_perl_module did not work if perl was called recursively. *) Bugfix: nginx ignored a host name in an request line. *) Bugfix: a worker process may got caught in an endless loop, if a FastCGI server sent too many data to the stderr. *) Bugfix: the $upstream_response_time variable may be negative if the system time was changed backward. *) Bugfix: the "Auth-Login-Attempt" parameter was not sent to IMAP/POP3 proxy authentication server when POP3 was used. *) Bugfix: a segmentation fault might occur if connect to IMAP/POP3 proxy authentication server failed.
author Igor Sysoev <http://sysoev.ru>
date Mon, 27 Nov 2006 00:00:00 +0300
parents 56688ed172c8
children 0effe91f6083
comparison
equal deleted inserted replaced
257:0e566ee1bcd5 258:6ae1357b7b7c
11 #include <ngx_imap.h> 11 #include <ngx_imap.h>
12 12
13 13
14 typedef struct { 14 typedef struct {
15 ngx_flag_t enable; 15 ngx_flag_t enable;
16 ngx_flag_t pass_error_message;
16 size_t buffer_size; 17 size_t buffer_size;
17 ngx_msec_t timeout; 18 ngx_msec_t timeout;
18 } ngx_imap_proxy_conf_t; 19 } ngx_imap_proxy_conf_t;
19 20
20 21
23 static void ngx_imap_proxy_pop3_handler(ngx_event_t *rev); 24 static void ngx_imap_proxy_pop3_handler(ngx_event_t *rev);
24 static void ngx_imap_proxy_dummy_handler(ngx_event_t *ev); 25 static void ngx_imap_proxy_dummy_handler(ngx_event_t *ev);
25 static ngx_int_t ngx_imap_proxy_read_response(ngx_imap_session_t *s, 26 static ngx_int_t ngx_imap_proxy_read_response(ngx_imap_session_t *s,
26 ngx_uint_t state); 27 ngx_uint_t state);
27 static void ngx_imap_proxy_handler(ngx_event_t *ev); 28 static void ngx_imap_proxy_handler(ngx_event_t *ev);
29 static void ngx_imap_proxy_upstream_error(ngx_imap_session_t *s);
28 static void ngx_imap_proxy_internal_server_error(ngx_imap_session_t *s); 30 static void ngx_imap_proxy_internal_server_error(ngx_imap_session_t *s);
29 static void ngx_imap_proxy_close_session(ngx_imap_session_t *s); 31 static void ngx_imap_proxy_close_session(ngx_imap_session_t *s);
30 static void *ngx_imap_proxy_create_conf(ngx_conf_t *cf); 32 static void *ngx_imap_proxy_create_conf(ngx_conf_t *cf);
31 static char *ngx_imap_proxy_merge_conf(ngx_conf_t *cf, void *parent, 33 static char *ngx_imap_proxy_merge_conf(ngx_conf_t *cf, void *parent,
32 void *child); 34 void *child);
51 { ngx_string("proxy_timeout"), 53 { ngx_string("proxy_timeout"),
52 NGX_IMAP_MAIN_CONF|NGX_IMAP_SRV_CONF|NGX_CONF_TAKE1, 54 NGX_IMAP_MAIN_CONF|NGX_IMAP_SRV_CONF|NGX_CONF_TAKE1,
53 ngx_conf_set_msec_slot, 55 ngx_conf_set_msec_slot,
54 NGX_IMAP_SRV_CONF_OFFSET, 56 NGX_IMAP_SRV_CONF_OFFSET,
55 offsetof(ngx_imap_proxy_conf_t, timeout), 57 offsetof(ngx_imap_proxy_conf_t, timeout),
58 NULL },
59
60 { ngx_string("proxy_pass_error_message"),
61 NGX_IMAP_MAIN_CONF|NGX_IMAP_SRV_CONF|NGX_CONF_TAKE1,
62 ngx_conf_set_flag_slot,
63 NGX_IMAP_SRV_CONF_OFFSET,
64 offsetof(ngx_imap_proxy_conf_t, pass_error_message),
56 NULL }, 65 NULL },
57 66
58 ngx_null_command 67 ngx_null_command
59 }; 68 };
60 69
202 if (rc == NGX_AGAIN) { 211 if (rc == NGX_AGAIN) {
203 return; 212 return;
204 } 213 }
205 214
206 if (rc == NGX_ERROR) { 215 if (rc == NGX_ERROR) {
207 ngx_imap_proxy_internal_server_error(s); 216 ngx_imap_proxy_upstream_error(s);
208 return; 217 return;
209 } 218 }
210 219
211 switch (s->imap_state) { 220 switch (s->imap_state) {
212 221
347 if (rc == NGX_AGAIN) { 356 if (rc == NGX_AGAIN) {
348 return; 357 return;
349 } 358 }
350 359
351 if (rc == NGX_ERROR) { 360 if (rc == NGX_ERROR) {
352 ngx_imap_proxy_internal_server_error(s); 361 ngx_imap_proxy_upstream_error(s);
353 return; 362 return;
354 } 363 }
355 364
356 switch (s->imap_state) { 365 switch (s->imap_state) {
357 366
450 459
451 460
452 static ngx_int_t 461 static ngx_int_t
453 ngx_imap_proxy_read_response(ngx_imap_session_t *s, ngx_uint_t state) 462 ngx_imap_proxy_read_response(ngx_imap_session_t *s, ngx_uint_t state)
454 { 463 {
455 u_char *p; 464 u_char *p;
456 ssize_t n; 465 ssize_t n;
457 ngx_buf_t *b; 466 ngx_buf_t *b;
467 ngx_imap_proxy_conf_t *pcf;
458 468
459 s->connection->log->action = "reading response from upstream"; 469 s->connection->log->action = "reading response from upstream";
460 470
461 b = s->proxy->buffer; 471 b = s->proxy->buffer;
462 472
521 } 531 }
522 break; 532 break;
523 } 533 }
524 } 534 }
525 535
526 *(b->last - 2) = '\0'; 536 pcf = ngx_imap_get_module_srv_conf(s, ngx_imap_proxy_module);
527 ngx_log_error(NGX_LOG_ERR, s->connection->log, 0, 537
528 "upstream sent invalid response: \"%s\"", p); 538 if (pcf->pass_error_message == 0) {
539 *(b->last - 2) = '\0';
540 ngx_log_error(NGX_LOG_ERR, s->connection->log, 0,
541 "upstream sent invalid response: \"%s\"", p);
542 return NGX_ERROR;
543 }
544
545 s->out.len = b->last - p - 2;
546 s->out.data = p;
547
548 ngx_log_error(NGX_LOG_INFO, s->connection->log, 0,
549 "upstream sent invalid response: \"%V\"", &s->out);
550
551 s->out.len = b->last - b->pos;
552 s->out.data = b->pos;
529 553
530 return NGX_ERROR; 554 return NGX_ERROR;
531 } 555 }
532 556
533 557
696 } 720 }
697 } 721 }
698 722
699 723
700 static void 724 static void
701 ngx_imap_proxy_internal_server_error(ngx_imap_session_t *s) 725 ngx_imap_proxy_upstream_error(ngx_imap_session_t *s)
702 { 726 {
703 if (s->proxy->upstream.connection) { 727 if (s->proxy->upstream.connection) {
704 ngx_log_debug1(NGX_LOG_DEBUG_IMAP, s->connection->log, 0, 728 ngx_log_debug1(NGX_LOG_DEBUG_IMAP, s->connection->log, 0,
705 "close imap proxy connection: %d", 729 "close imap proxy connection: %d",
706 s->proxy->upstream.connection->fd); 730 s->proxy->upstream.connection->fd);
707 731
708 ngx_close_connection(s->proxy->upstream.connection); 732 ngx_close_connection(s->proxy->upstream.connection);
709 } 733 }
710 734
711 ngx_imap_session_internal_server_error(s); 735 if (s->out.len == 0) {
736 ngx_imap_session_internal_server_error(s);
737 return;
738 }
739
740 s->quit = 1;
741 ngx_imap_send(s->connection->write);
712 } 742 }
713 743
714 744
715 static void 745 static void
716 ngx_imap_proxy_close_session(ngx_imap_session_t *s) 746 ngx_imap_proxy_internal_server_error(ngx_imap_session_t *s)
717 { 747 {
718 if (s->proxy->upstream.connection) { 748 if (s->proxy->upstream.connection) {
719 ngx_log_debug1(NGX_LOG_DEBUG_IMAP, s->connection->log, 0, 749 ngx_log_debug1(NGX_LOG_DEBUG_IMAP, s->connection->log, 0,
720 "close imap proxy connection: %d", 750 "close imap proxy connection: %d",
721 s->proxy->upstream.connection->fd); 751 s->proxy->upstream.connection->fd);
722 752
723 ngx_close_connection(s->proxy->upstream.connection); 753 ngx_close_connection(s->proxy->upstream.connection);
724 } 754 }
725 755
756 ngx_imap_session_internal_server_error(s);
757 }
758
759
760 static void
761 ngx_imap_proxy_close_session(ngx_imap_session_t *s)
762 {
763 if (s->proxy->upstream.connection) {
764 ngx_log_debug1(NGX_LOG_DEBUG_IMAP, s->connection->log, 0,
765 "close imap proxy connection: %d",
766 s->proxy->upstream.connection->fd);
767
768 ngx_close_connection(s->proxy->upstream.connection);
769 }
770
726 ngx_imap_close_connection(s->connection); 771 ngx_imap_close_connection(s->connection);
727 } 772 }
728 773
729 774
730 static void * 775 static void *
736 if (pcf == NULL) { 781 if (pcf == NULL) {
737 return NGX_CONF_ERROR; 782 return NGX_CONF_ERROR;
738 } 783 }
739 784
740 pcf->enable = NGX_CONF_UNSET; 785 pcf->enable = NGX_CONF_UNSET;
786 pcf->pass_error_message = NGX_CONF_UNSET;
741 pcf->buffer_size = NGX_CONF_UNSET_SIZE; 787 pcf->buffer_size = NGX_CONF_UNSET_SIZE;
742 pcf->timeout = NGX_CONF_UNSET_MSEC; 788 pcf->timeout = NGX_CONF_UNSET_MSEC;
743 789
744 return pcf; 790 return pcf;
745 } 791 }
750 { 796 {
751 ngx_imap_proxy_conf_t *prev = parent; 797 ngx_imap_proxy_conf_t *prev = parent;
752 ngx_imap_proxy_conf_t *conf = child; 798 ngx_imap_proxy_conf_t *conf = child;
753 799
754 ngx_conf_merge_value(conf->enable, prev->enable, 0); 800 ngx_conf_merge_value(conf->enable, prev->enable, 0);
801 ngx_conf_merge_value(conf->pass_error_message, prev->pass_error_message, 0);
755 ngx_conf_merge_size_value(conf->buffer_size, prev->buffer_size, 802 ngx_conf_merge_size_value(conf->buffer_size, prev->buffer_size,
756 (size_t) ngx_pagesize); 803 (size_t) ngx_pagesize);
757 ngx_conf_merge_msec_value(conf->timeout, prev->timeout, 24 * 60 * 60000); 804 ngx_conf_merge_msec_value(conf->timeout, prev->timeout, 24 * 60 * 60000);
758 805
759 return NGX_CONF_OK; 806 return NGX_CONF_OK;