changeset 216:fa32d59d9a15 NGINX_0_3_55

nginx 0.3.55 *) Feature: the "stub" parameter in the "include" SSI command. *) Feature: the "block" SSI command. *) Feature: the unicode2nginx script was added to contrib. *) Bugfix: if a "root" was specified by variable only, then the root was relative to a server prefix. *) Bugfix: if the request contained "//" or "/./" and escaped symbols after them, then the proxied request was sent unescaped. *) Bugfix: the $r->headers_in("Cookie") of the ngx_http_perl_module now returns all "Cookie" header lines. *) Bugfix: a segmentation fault occurred if "client_body_in_file_only on" was used and nginx switched to a next upstream. *) Bugfix: on some condition while reconfiguration character codes inside the "charset_map" may be treated invalid; bug appeared in 0.3.50.
author Igor Sysoev <http://sysoev.ru>
date Fri, 28 Jul 2006 00:00:00 +0400
parents 84a7f4bc1133
children a346c23fc94e
files CHANGES CHANGES.ru auto/make conf/koi-utf conf/mime.types conf/win-utf contrib/README contrib/unicode2nginx/koi-utf contrib/unicode2nginx/unicode-to-nginx.pl contrib/unicode2nginx/win-utf src/core/nginx.h src/core/ngx_file.c src/event/ngx_event.c src/http/modules/ngx_http_access_module.c src/http/modules/ngx_http_addition_filter_module.c src/http/modules/ngx_http_auth_basic_module.c src/http/modules/ngx_http_autoindex_module.c src/http/modules/ngx_http_charset_filter_module.c src/http/modules/ngx_http_chunked_filter_module.c src/http/modules/ngx_http_dav_module.c src/http/modules/ngx_http_empty_gif_module.c src/http/modules/ngx_http_fastcgi_module.c src/http/modules/ngx_http_index_module.c src/http/modules/ngx_http_log_module.c src/http/modules/ngx_http_memcached_module.c src/http/modules/ngx_http_proxy_module.c src/http/modules/ngx_http_realip_module.c src/http/modules/ngx_http_rewrite_module.c src/http/modules/ngx_http_ssi_filter_module.c src/http/modules/ngx_http_ssi_filter_module.h src/http/modules/ngx_http_ssl_module.c src/http/modules/ngx_http_stub_status_module.c src/http/modules/ngx_http_userid_filter_module.c src/http/modules/perl/nginx.xs src/http/modules/perl/ngx_http_perl_module.c src/http/ngx_http.h src/http/ngx_http_copy_filter_module.c src/http/ngx_http_core_module.c src/http/ngx_http_core_module.h src/http/ngx_http_header_filter_module.c src/http/ngx_http_parse.c src/http/ngx_http_postpone_filter_module.c src/http/ngx_http_request.c src/http/ngx_http_request.h src/http/ngx_http_request_body.c src/http/ngx_http_upstream.c src/http/ngx_http_variables.c src/http/ngx_http_write_filter_module.c
diffstat 48 files changed, 873 insertions(+), 120 deletions(-) [+]
line wrap: on
line diff
--- a/CHANGES	Tue Jul 11 00:00:00 2006 +0400
+++ b/CHANGES	Fri Jul 28 00:00:00 2006 +0400
@@ -1,4 +1,30 @@
 
+Changes with nginx 0.3.55                                        28 Jul 2006
+
+    *) Feature: the "stub" parameter in the "include" SSI command.
+
+    *) Feature: the "block" SSI command.
+
+    *) Feature: the unicode2nginx script was added to contrib.
+
+    *) Bugfix: if a "root" was specified by variable only, then the root 
+       was relative to a server prefix.
+
+    *) Bugfix: if the request contained "//" or "/./" and escaped symbols 
+       after them, then the proxied request was sent unescaped.
+
+    *) Bugfix: the $r->headers_in("Cookie") of the ngx_http_perl_module now 
+       returns all "Cookie" header lines.
+
+    *) Bugfix: a segmentation fault occurred if 
+       "client_body_in_file_only on" was used and nginx was switches to a 
+       next upstream.
+
+    *) Bugfix: on some condition while reconfiguration character codes 
+       inside the "charset_map" may be treated invalid; bug appeared in 
+       0.3.50.
+
+
 Changes with nginx 0.3.54                                        11 Jul 2006
 
     *) Feature: nginx now logs the subrequest information to the error log.
@@ -156,7 +182,7 @@
 
 Changes with nginx 0.3.44                                        04 May 2006
 
-    *) Feature: the "wait" parameter in the SSI "include" command.
+    *) Feature: the "wait" parameter in the "include" SSI command.
 
     *) Feature: the Ukrainian and Byelorussian characters were added to 
        koi-win conversion table.
--- a/CHANGES.ru	Tue Jul 11 00:00:00 2006 +0400
+++ b/CHANGES.ru	Fri Jul 28 00:00:00 2006 +0400
@@ -1,4 +1,31 @@
 
+Изменения в nginx 0.3.55                                          28.07.2006
+
+    *) Добавление: параметр stub в команде SSI include.
+
+    *) Добавление: команда SSI block.
+
+    *) Добавление: скрипт unicode2nginx добавлен в contrib.
+
+    *) Исправление: если root был задан только переменной, то корень 
+       задавался относительно префикса сервера.
+
+    *) Исправление: если в запросе был "//" или "/.", и после этого 
+       закодированные символы в виде "%XX", то проксируемый запрос 
+       передавался незакодированным.
+
+    *) Исправление: метод $r->headers_in("Cookie") модуля 
+       ngx_http_perl_module теперь возвращает все строки "Cookie" в 
+       заголовке запроса.
+
+    *) Исправление: происходил segmentation fault, если использовался 
+       "client_body_in_file_only on" и делался переход к следующему бэкенду.
+
+    *) Исправление: при некоторых условиях во время переконфигурации коды 
+       символов в внутри директивы charset_map могли считаться неверными; 
+       ошибка появилась в 0.3.50.
+
+
 Изменения в nginx 0.3.54                                          11.07.2006
 
     *) Добавление: nginx теперь записывает в лог информацию о подзапросах.
@@ -161,7 +188,7 @@
 
 Изменения в nginx 0.3.44                                          04.05.2006
 
-    *) Добавление: параметр wait в команде SSI inlcude.
+    *) Добавление: параметр wait в команде SSI include.
 
     *) Добавление: в таблицу перекодировки koi-win добавлены украинские и 
        белорусские символы.
--- a/auto/make	Tue Jul 11 00:00:00 2006 +0400
+++ b/auto/make	Fri Jul 28 00:00:00 2006 +0400
@@ -175,8 +175,10 @@
     | sed -e "s/  *\([^ ][^ ]*\)/$ngx_long_regex_cont\1/g" \
           -e "s/\//$ngx_regex_dirsep/g"`
 
-ngx_libs=${CORE_LIBS:+`echo $NGX_LD_OPT $CORE_LIBS \
-    | sed -e "s/\//$ngx_regex_dirsep/g" -e "s/^/$ngx_long_regex_cont/"`}
+if test -n "$NGX_LD_OPT$CORE_LIBS"; then
+    ngx_libs=`echo $NGX_LD_OPT $CORE_LIBS \
+        | sed -e "s/\//$ngx_regex_dirsep/g" -e "s/^/$ngx_long_regex_cont/"`
+fi
 
 ngx_link=${CORE_LINK:+`echo $CORE_LINK \
     | sed -e "s/\//$ngx_regex_dirsep/g" -e "s/^/$ngx_long_regex_cont/"`}
--- a/conf/koi-utf	Tue Jul 11 00:00:00 2006 +0400
+++ b/conf/koi-utf	Fri Jul 28 00:00:00 2006 +0400
@@ -1,3 +1,9 @@
+
+# This map is not a full koi8-r <> utf8 map: it does not contain
+# box-drawing and some other characters.  Besides this map contains
+# several koi8-u and Byelorussian letters which are not in koi8-r.
+# If you need a full and standard map, use contrib/unicode2nginx/koi-utf
+# map instead.
 
 charset_map  koi8-r  utf-8 {
 
--- a/conf/mime.types	Tue Jul 11 00:00:00 2006 +0400
+++ b/conf/mime.types	Fri Jul 28 00:00:00 2006 +0400
@@ -14,6 +14,7 @@
     image/png                             png;
     image/x-icon                          ico;
     image/x-jng                           jng;
+    image/vnd.wap.wbmp                    wbmp;
 
     application/java-archive              jar war ear;
     application/mac-binhex40              hqx;
--- a/conf/win-utf	Tue Jul 11 00:00:00 2006 +0400
+++ b/conf/win-utf	Fri Jul 28 00:00:00 2006 +0400
@@ -1,3 +1,7 @@
+
+# This map is not a full windows-1251 <> utf8 map: it does not
+# contain Serbian and Macedonian letters.  If you need a full map,
+# use contrib/unicode2nginx/win-utf map instead.
 
 charset_map  windows-1251  utf-8 {
 
--- a/contrib/README	Tue Jul 11 00:00:00 2006 +0400
+++ b/contrib/README	Fri Jul 28 00:00:00 2006 +0400
@@ -1,6 +1,15 @@
 
-geo2nginx.pl 	by Andrei Nigmatulin
+geo2nginx.pl 		by Andrei Nigmatulin
+
+	The perl script to convert CSV geoip database ( free download
+	at http://www.maxmind.com/app/geoip_country ) to format, suitable
+	for use by the ngx_http_geo_module.
+
 
-	The perl script to convert CSV geoip database (free download
-	at http://www.maxmind.com/app/geoip_country) to format, suitable
-	for use with ngx_http_geo_module.
+unicode2nginx		by Maxim Dounin
+
+	The perl script to convert unicode mappings ( available
+	at http://www.unicode.org/Public/MAPPINGS/ ) to the nginx
+	configuration file format.
+	Two generated full maps for windows-1251 and koi8-r.
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/contrib/unicode2nginx/koi-utf	Fri Jul 28 00:00:00 2006 +0400
@@ -0,0 +1,131 @@
+charset_map  koi8-r  utf-8 {
+
+    80  E29480 ; #	BOX DRAWINGS LIGHT HORIZONTAL
+    81  E29482 ; #	BOX DRAWINGS LIGHT VERTICAL
+    82  E2948C ; #	BOX DRAWINGS LIGHT DOWN AND RIGHT
+    83  E29490 ; #	BOX DRAWINGS LIGHT DOWN AND LEFT
+    84  E29494 ; #	BOX DRAWINGS LIGHT UP AND RIGHT
+    85  E29498 ; #	BOX DRAWINGS LIGHT UP AND LEFT
+    86  E2949C ; #	BOX DRAWINGS LIGHT VERTICAL AND RIGHT
+    87  E294A4 ; #	BOX DRAWINGS LIGHT VERTICAL AND LEFT
+    88  E294AC ; #	BOX DRAWINGS LIGHT DOWN AND HORIZONTAL
+    89  E294B4 ; #	BOX DRAWINGS LIGHT UP AND HORIZONTAL
+    8A  E294BC ; #	BOX DRAWINGS LIGHT VERTICAL AND HORIZONTAL
+    8B  E29680 ; #	UPPER HALF BLOCK
+    8C  E29684 ; #	LOWER HALF BLOCK
+    8D  E29688 ; #	FULL BLOCK
+    8E  E2968C ; #	LEFT HALF BLOCK
+    8F  E29690 ; #	RIGHT HALF BLOCK
+    90  E29691 ; #	LIGHT SHADE
+    91  E29692 ; #	MEDIUM SHADE
+    92  E29693 ; #	DARK SHADE
+    93  E28CA0 ; #	TOP HALF INTEGRAL
+    94  E296A0 ; #	BLACK SQUARE
+    95  E28899 ; #	BULLET OPERATOR
+    96  E2889A ; #	SQUARE ROOT
+    97  E28988 ; #	ALMOST EQUAL TO
+    98  E289A4 ; #	LESS-THAN OR EQUAL TO
+    99  E289A5 ; #	GREATER-THAN OR EQUAL TO
+    9A  C2A0 ; #	NO-BREAK SPACE
+    9B  E28CA1 ; #	BOTTOM HALF INTEGRAL
+    9C  C2B0 ; #	DEGREE SIGN
+    9D  C2B2 ; #	SUPERSCRIPT TWO
+    9E  C2B7 ; #	MIDDLE DOT
+    9F  C3B7 ; #	DIVISION SIGN
+    A0  E29590 ; #	BOX DRAWINGS DOUBLE HORIZONTAL
+    A1  E29591 ; #	BOX DRAWINGS DOUBLE VERTICAL
+    A2  E29592 ; #	BOX DRAWINGS DOWN SINGLE AND RIGHT DOUBLE
+    A3  D191 ; #	CYRILLIC SMALL LETTER IO
+    A4  E29593 ; #	BOX DRAWINGS DOWN DOUBLE AND RIGHT SINGLE
+    A5  E29594 ; #	BOX DRAWINGS DOUBLE DOWN AND RIGHT
+    A6  E29595 ; #	BOX DRAWINGS DOWN SINGLE AND LEFT DOUBLE
+    A7  E29596 ; #	BOX DRAWINGS DOWN DOUBLE AND LEFT SINGLE
+    A8  E29597 ; #	BOX DRAWINGS DOUBLE DOWN AND LEFT
+    A9  E29598 ; #	BOX DRAWINGS UP SINGLE AND RIGHT DOUBLE
+    AA  E29599 ; #	BOX DRAWINGS UP DOUBLE AND RIGHT SINGLE
+    AB  E2959A ; #	BOX DRAWINGS DOUBLE UP AND RIGHT
+    AC  E2959B ; #	BOX DRAWINGS UP SINGLE AND LEFT DOUBLE
+    AD  E2959C ; #	BOX DRAWINGS UP DOUBLE AND LEFT SINGLE
+    AE  E2959D ; #	BOX DRAWINGS DOUBLE UP AND LEFT
+    AF  E2959E ; #	BOX DRAWINGS VERTICAL SINGLE AND RIGHT DOUBLE
+    B0  E2959F ; #	BOX DRAWINGS VERTICAL DOUBLE AND RIGHT SINGLE
+    B1  E295A0 ; #	BOX DRAWINGS DOUBLE VERTICAL AND RIGHT
+    B2  E295A1 ; #	BOX DRAWINGS VERTICAL SINGLE AND LEFT DOUBLE
+    B3  D081 ; #	CYRILLIC CAPITAL LETTER IO
+    B4  E295A2 ; #	BOX DRAWINGS VERTICAL DOUBLE AND LEFT SINGLE
+    B5  E295A3 ; #	BOX DRAWINGS DOUBLE VERTICAL AND LEFT
+    B6  E295A4 ; #	BOX DRAWINGS DOWN SINGLE AND HORIZONTAL DOUBLE
+    B7  E295A5 ; #	BOX DRAWINGS DOWN DOUBLE AND HORIZONTAL SINGLE
+    B8  E295A6 ; #	BOX DRAWINGS DOUBLE DOWN AND HORIZONTAL
+    B9  E295A7 ; #	BOX DRAWINGS UP SINGLE AND HORIZONTAL DOUBLE
+    BA  E295A8 ; #	BOX DRAWINGS UP DOUBLE AND HORIZONTAL SINGLE
+    BB  E295A9 ; #	BOX DRAWINGS DOUBLE UP AND HORIZONTAL
+    BC  E295AA ; #	BOX DRAWINGS VERTICAL SINGLE AND HORIZONTAL DOUBLE
+    BD  E295AB ; #	BOX DRAWINGS VERTICAL DOUBLE AND HORIZONTAL SINGLE
+    BE  E295AC ; #	BOX DRAWINGS DOUBLE VERTICAL AND HORIZONTAL
+    BF  C2A9 ; #	COPYRIGHT SIGN
+    C0  D18E ; #	CYRILLIC SMALL LETTER YU
+    C1  D0B0 ; #	CYRILLIC SMALL LETTER A
+    C2  D0B1 ; #	CYRILLIC SMALL LETTER BE
+    C3  D186 ; #	CYRILLIC SMALL LETTER TSE
+    C4  D0B4 ; #	CYRILLIC SMALL LETTER DE
+    C5  D0B5 ; #	CYRILLIC SMALL LETTER IE
+    C6  D184 ; #	CYRILLIC SMALL LETTER EF
+    C7  D0B3 ; #	CYRILLIC SMALL LETTER GHE
+    C8  D185 ; #	CYRILLIC SMALL LETTER HA
+    C9  D0B8 ; #	CYRILLIC SMALL LETTER I
+    CA  D0B9 ; #	CYRILLIC SMALL LETTER SHORT I
+    CB  D0BA ; #	CYRILLIC SMALL LETTER KA
+    CC  D0BB ; #	CYRILLIC SMALL LETTER EL
+    CD  D0BC ; #	CYRILLIC SMALL LETTER EM
+    CE  D0BD ; #	CYRILLIC SMALL LETTER EN
+    CF  D0BE ; #	CYRILLIC SMALL LETTER O
+    D0  D0BF ; #	CYRILLIC SMALL LETTER PE
+    D1  D18F ; #	CYRILLIC SMALL LETTER YA
+    D2  D180 ; #	CYRILLIC SMALL LETTER ER
+    D3  D181 ; #	CYRILLIC SMALL LETTER ES
+    D4  D182 ; #	CYRILLIC SMALL LETTER TE
+    D5  D183 ; #	CYRILLIC SMALL LETTER U
+    D6  D0B6 ; #	CYRILLIC SMALL LETTER ZHE
+    D7  D0B2 ; #	CYRILLIC SMALL LETTER VE
+    D8  D18C ; #	CYRILLIC SMALL LETTER SOFT SIGN
+    D9  D18B ; #	CYRILLIC SMALL LETTER YERU
+    DA  D0B7 ; #	CYRILLIC SMALL LETTER ZE
+    DB  D188 ; #	CYRILLIC SMALL LETTER SHA
+    DC  D18D ; #	CYRILLIC SMALL LETTER E
+    DD  D189 ; #	CYRILLIC SMALL LETTER SHCHA
+    DE  D187 ; #	CYRILLIC SMALL LETTER CHE
+    DF  D18A ; #	CYRILLIC SMALL LETTER HARD SIGN
+    E0  D0AE ; #	CYRILLIC CAPITAL LETTER YU
+    E1  D090 ; #	CYRILLIC CAPITAL LETTER A
+    E2  D091 ; #	CYRILLIC CAPITAL LETTER BE
+    E3  D0A6 ; #	CYRILLIC CAPITAL LETTER TSE
+    E4  D094 ; #	CYRILLIC CAPITAL LETTER DE
+    E5  D095 ; #	CYRILLIC CAPITAL LETTER IE
+    E6  D0A4 ; #	CYRILLIC CAPITAL LETTER EF
+    E7  D093 ; #	CYRILLIC CAPITAL LETTER GHE
+    E8  D0A5 ; #	CYRILLIC CAPITAL LETTER HA
+    E9  D098 ; #	CYRILLIC CAPITAL LETTER I
+    EA  D099 ; #	CYRILLIC CAPITAL LETTER SHORT I
+    EB  D09A ; #	CYRILLIC CAPITAL LETTER KA
+    EC  D09B ; #	CYRILLIC CAPITAL LETTER EL
+    ED  D09C ; #	CYRILLIC CAPITAL LETTER EM
+    EE  D09D ; #	CYRILLIC CAPITAL LETTER EN
+    EF  D09E ; #	CYRILLIC CAPITAL LETTER O
+    F0  D09F ; #	CYRILLIC CAPITAL LETTER PE
+    F1  D0AF ; #	CYRILLIC CAPITAL LETTER YA
+    F2  D0A0 ; #	CYRILLIC CAPITAL LETTER ER
+    F3  D0A1 ; #	CYRILLIC CAPITAL LETTER ES
+    F4  D0A2 ; #	CYRILLIC CAPITAL LETTER TE
+    F5  D0A3 ; #	CYRILLIC CAPITAL LETTER U
+    F6  D096 ; #	CYRILLIC CAPITAL LETTER ZHE
+    F7  D092 ; #	CYRILLIC CAPITAL LETTER VE
+    F8  D0AC ; #	CYRILLIC CAPITAL LETTER SOFT SIGN
+    F9  D0AB ; #	CYRILLIC CAPITAL LETTER YERU
+    FA  D097 ; #	CYRILLIC CAPITAL LETTER ZE
+    FB  D0A8 ; #	CYRILLIC CAPITAL LETTER SHA
+    FC  D0AD ; #	CYRILLIC CAPITAL LETTER E
+    FD  D0A9 ; #	CYRILLIC CAPITAL LETTER SHCHA
+    FE  D0A7 ; #	CYRILLIC CAPITAL LETTER CHE
+    FF  D0AA ; #	CYRILLIC CAPITAL LETTER HARD SIGN
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/contrib/unicode2nginx/unicode-to-nginx.pl	Fri Jul 28 00:00:00 2006 +0400
@@ -0,0 +1,45 @@
+#!/usr/bin/perl -w
+
+# Convert unicode mappings to nginx configuration file format.
+
+# You may find useful mappings in various places, including
+# unicode.org official site:
+#
+# http://www.unicode.org/Public/MAPPINGS/VENDORS/MICSFT/WINDOWS/CP1251.TXT
+# http://www.unicode.org/Public/MAPPINGS/VENDORS/MISC/KOI8-R.TXT
+
+# Needs perl 5.6 or later.
+
+# Written by Maxim Dounin, mdounin@rambler-co.ru
+
+###############################################################################
+
+require 5.006;
+
+while (<>) {
+	# Skip comments and empty lines
+
+	next if /^#/;
+	next if /^\s*$/;
+	chomp;
+
+	# Convert mappings
+
+	if (/^\s*0x(..)\s*0x(....)\s*(#.*)/) {
+		# Mapping <from-code> <unicode-code> "#" <unicode-name>
+		my $cs_code = $1;
+		my $un_code = $2;
+		my $un_name = $3;
+
+		# Produce UTF-8 sequence from character code;
+
+		my $un_utf8 = join('', map { sprintf("%02X", $_) } unpack("C*", pack("U", hex($un_code))));
+
+		print "    $cs_code  $un_utf8 ; $un_name\n";
+
+	} else {
+		warn "Unrecognized line: '$_'";
+	}
+}
+
+###############################################################################
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/contrib/unicode2nginx/win-utf	Fri Jul 28 00:00:00 2006 +0400
@@ -0,0 +1,130 @@
+charset_map  windows-1251  utf-8 {
+
+    80  D082 ; #CYRILLIC CAPITAL LETTER DJE
+    81  D083 ; #CYRILLIC CAPITAL LETTER GJE
+    82  E2809A ; #SINGLE LOW-9 QUOTATION MARK
+    83  D193 ; #CYRILLIC SMALL LETTER GJE
+    84  E2809E ; #DOUBLE LOW-9 QUOTATION MARK
+    85  E280A6 ; #HORIZONTAL ELLIPSIS
+    86  E280A0 ; #DAGGER
+    87  E280A1 ; #DOUBLE DAGGER
+    88  E282AC ; #EURO SIGN
+    89  E280B0 ; #PER MILLE SIGN
+    8A  D089 ; #CYRILLIC CAPITAL LETTER LJE
+    8B  E280B9 ; #SINGLE LEFT-POINTING ANGLE QUOTATION MARK
+    8C  D08A ; #CYRILLIC CAPITAL LETTER NJE
+    8D  D08C ; #CYRILLIC CAPITAL LETTER KJE
+    8E  D08B ; #CYRILLIC CAPITAL LETTER TSHE
+    8F  D08F ; #CYRILLIC CAPITAL LETTER DZHE
+    90  D192 ; #CYRILLIC SMALL LETTER DJE
+    91  E28098 ; #LEFT SINGLE QUOTATION MARK
+    92  E28099 ; #RIGHT SINGLE QUOTATION MARK
+    93  E2809C ; #LEFT DOUBLE QUOTATION MARK
+    94  E2809D ; #RIGHT DOUBLE QUOTATION MARK
+    95  E280A2 ; #BULLET
+    96  E28093 ; #EN DASH
+    97  E28094 ; #EM DASH
+    99  E284A2 ; #TRADE MARK SIGN
+    9A  D199 ; #CYRILLIC SMALL LETTER LJE
+    9B  E280BA ; #SINGLE RIGHT-POINTING ANGLE QUOTATION MARK
+    9C  D19A ; #CYRILLIC SMALL LETTER NJE
+    9D  D19C ; #CYRILLIC SMALL LETTER KJE
+    9E  D19B ; #CYRILLIC SMALL LETTER TSHE
+    9F  D19F ; #CYRILLIC SMALL LETTER DZHE
+    A0  C2A0 ; #NO-BREAK SPACE
+    A1  D08E ; #CYRILLIC CAPITAL LETTER SHORT U
+    A2  D19E ; #CYRILLIC SMALL LETTER SHORT U
+    A3  D088 ; #CYRILLIC CAPITAL LETTER JE
+    A4  C2A4 ; #CURRENCY SIGN
+    A5  D290 ; #CYRILLIC CAPITAL LETTER GHE WITH UPTURN
+    A6  C2A6 ; #BROKEN BAR
+    A7  C2A7 ; #SECTION SIGN
+    A8  D081 ; #CYRILLIC CAPITAL LETTER IO
+    A9  C2A9 ; #COPYRIGHT SIGN
+    AA  D084 ; #CYRILLIC CAPITAL LETTER UKRAINIAN IE
+    AB  C2AB ; #LEFT-POINTING DOUBLE ANGLE QUOTATION MARK
+    AC  C2AC ; #NOT SIGN
+    AD  C2AD ; #SOFT HYPHEN
+    AE  C2AE ; #REGISTERED SIGN
+    AF  D087 ; #CYRILLIC CAPITAL LETTER YI
+    B0  C2B0 ; #DEGREE SIGN
+    B1  C2B1 ; #PLUS-MINUS SIGN
+    B2  D086 ; #CYRILLIC CAPITAL LETTER BYELORUSSIAN-UKRAINIAN I
+    B3  D196 ; #CYRILLIC SMALL LETTER BYELORUSSIAN-UKRAINIAN I
+    B4  D291 ; #CYRILLIC SMALL LETTER GHE WITH UPTURN
+    B5  C2B5 ; #MICRO SIGN
+    B6  C2B6 ; #PILCROW SIGN
+    B7  C2B7 ; #MIDDLE DOT
+    B8  D191 ; #CYRILLIC SMALL LETTER IO
+    B9  E28496 ; #NUMERO SIGN
+    BA  D194 ; #CYRILLIC SMALL LETTER UKRAINIAN IE
+    BB  C2BB ; #RIGHT-POINTING DOUBLE ANGLE QUOTATION MARK
+    BC  D198 ; #CYRILLIC SMALL LETTER JE
+    BD  D085 ; #CYRILLIC CAPITAL LETTER DZE
+    BE  D195 ; #CYRILLIC SMALL LETTER DZE
+    BF  D197 ; #CYRILLIC SMALL LETTER YI
+    C0  D090 ; #CYRILLIC CAPITAL LETTER A
+    C1  D091 ; #CYRILLIC CAPITAL LETTER BE
+    C2  D092 ; #CYRILLIC CAPITAL LETTER VE
+    C3  D093 ; #CYRILLIC CAPITAL LETTER GHE
+    C4  D094 ; #CYRILLIC CAPITAL LETTER DE
+    C5  D095 ; #CYRILLIC CAPITAL LETTER IE
+    C6  D096 ; #CYRILLIC CAPITAL LETTER ZHE
+    C7  D097 ; #CYRILLIC CAPITAL LETTER ZE
+    C8  D098 ; #CYRILLIC CAPITAL LETTER I
+    C9  D099 ; #CYRILLIC CAPITAL LETTER SHORT I
+    CA  D09A ; #CYRILLIC CAPITAL LETTER KA
+    CB  D09B ; #CYRILLIC CAPITAL LETTER EL
+    CC  D09C ; #CYRILLIC CAPITAL LETTER EM
+    CD  D09D ; #CYRILLIC CAPITAL LETTER EN
+    CE  D09E ; #CYRILLIC CAPITAL LETTER O
+    CF  D09F ; #CYRILLIC CAPITAL LETTER PE
+    D0  D0A0 ; #CYRILLIC CAPITAL LETTER ER
+    D1  D0A1 ; #CYRILLIC CAPITAL LETTER ES
+    D2  D0A2 ; #CYRILLIC CAPITAL LETTER TE
+    D3  D0A3 ; #CYRILLIC CAPITAL LETTER U
+    D4  D0A4 ; #CYRILLIC CAPITAL LETTER EF
+    D5  D0A5 ; #CYRILLIC CAPITAL LETTER HA
+    D6  D0A6 ; #CYRILLIC CAPITAL LETTER TSE
+    D7  D0A7 ; #CYRILLIC CAPITAL LETTER CHE
+    D8  D0A8 ; #CYRILLIC CAPITAL LETTER SHA
+    D9  D0A9 ; #CYRILLIC CAPITAL LETTER SHCHA
+    DA  D0AA ; #CYRILLIC CAPITAL LETTER HARD SIGN
+    DB  D0AB ; #CYRILLIC CAPITAL LETTER YERU
+    DC  D0AC ; #CYRILLIC CAPITAL LETTER SOFT SIGN
+    DD  D0AD ; #CYRILLIC CAPITAL LETTER E
+    DE  D0AE ; #CYRILLIC CAPITAL LETTER YU
+    DF  D0AF ; #CYRILLIC CAPITAL LETTER YA
+    E0  D0B0 ; #CYRILLIC SMALL LETTER A
+    E1  D0B1 ; #CYRILLIC SMALL LETTER BE
+    E2  D0B2 ; #CYRILLIC SMALL LETTER VE
+    E3  D0B3 ; #CYRILLIC SMALL LETTER GHE
+    E4  D0B4 ; #CYRILLIC SMALL LETTER DE
+    E5  D0B5 ; #CYRILLIC SMALL LETTER IE
+    E6  D0B6 ; #CYRILLIC SMALL LETTER ZHE
+    E7  D0B7 ; #CYRILLIC SMALL LETTER ZE
+    E8  D0B8 ; #CYRILLIC SMALL LETTER I
+    E9  D0B9 ; #CYRILLIC SMALL LETTER SHORT I
+    EA  D0BA ; #CYRILLIC SMALL LETTER KA
+    EB  D0BB ; #CYRILLIC SMALL LETTER EL
+    EC  D0BC ; #CYRILLIC SMALL LETTER EM
+    ED  D0BD ; #CYRILLIC SMALL LETTER EN
+    EE  D0BE ; #CYRILLIC SMALL LETTER O
+    EF  D0BF ; #CYRILLIC SMALL LETTER PE
+    F0  D180 ; #CYRILLIC SMALL LETTER ER
+    F1  D181 ; #CYRILLIC SMALL LETTER ES
+    F2  D182 ; #CYRILLIC SMALL LETTER TE
+    F3  D183 ; #CYRILLIC SMALL LETTER U
+    F4  D184 ; #CYRILLIC SMALL LETTER EF
+    F5  D185 ; #CYRILLIC SMALL LETTER HA
+    F6  D186 ; #CYRILLIC SMALL LETTER TSE
+    F7  D187 ; #CYRILLIC SMALL LETTER CHE
+    F8  D188 ; #CYRILLIC SMALL LETTER SHA
+    F9  D189 ; #CYRILLIC SMALL LETTER SHCHA
+    FA  D18A ; #CYRILLIC SMALL LETTER HARD SIGN
+    FB  D18B ; #CYRILLIC SMALL LETTER YERU
+    FC  D18C ; #CYRILLIC SMALL LETTER SOFT SIGN
+    FD  D18D ; #CYRILLIC SMALL LETTER E
+    FE  D18E ; #CYRILLIC SMALL LETTER YU
+    FF  D18F ; #CYRILLIC SMALL LETTER YA
+}
--- a/src/core/nginx.h	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/core/nginx.h	Fri Jul 28 00:00:00 2006 +0400
@@ -8,7 +8,7 @@
 #define _NGINX_H_INCLUDED_
 
 
-#define NGINX_VER          "nginx/0.3.54"
+#define NGINX_VER          "nginx/0.3.55"
 
 #define NGINX_VAR          "NGINX"
 #define NGX_OLDPID_EXT     ".oldbin"
--- a/src/core/ngx_file.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/core/ngx_file.c	Fri Jul 28 00:00:00 2006 +0400
@@ -25,11 +25,8 @@
             return rc;
         }
 
-        if (tf->log_level == NGX_LOG_NOTICE) {
-            ngx_log_error(NGX_LOG_NOTICE, tf->file.log, 0, tf->warn);
-
-        } else if (tf->log_level == NGX_LOG_WARN) {
-            ngx_log_error(NGX_LOG_WARN, tf->file.log, 0, "%s %V",
+        if (tf->log_level) {
+            ngx_log_error(tf->log_level, tf->file.log, 0, "%s %V",
                           tf->warn, &tf->file.name);
         }
     }
--- a/src/event/ngx_event.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/event/ngx_event.c	Fri Jul 28 00:00:00 2006 +0400
@@ -137,14 +137,14 @@
       NULL },
 
     { ngx_string("multi_accept"),
-      NGX_EVENT_CONF|NGX_CONF_TAKE1,
+      NGX_EVENT_CONF|NGX_CONF_FLAG,
       ngx_conf_set_flag_slot,
       0,
       offsetof(ngx_event_conf_t, multi_accept),
       NULL },
 
     { ngx_string("accept_mutex"),
-      NGX_EVENT_CONF|NGX_CONF_TAKE1,
+      NGX_EVENT_CONF|NGX_CONF_FLAG,
       ngx_conf_set_flag_slot,
       0,
       offsetof(ngx_event_conf_t, accept_mutex),
--- a/src/http/modules/ngx_http_access_module.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/modules/ngx_http_access_module.c	Fri Jul 28 00:00:00 2006 +0400
@@ -55,7 +55,7 @@
 
 
 
-ngx_http_module_t  ngx_http_access_module_ctx = {
+static ngx_http_module_t  ngx_http_access_module_ctx = {
     NULL,                                  /* preconfiguration */
     NULL,                                  /* postconfiguration */
 
--- a/src/http/modules/ngx_http_addition_filter_module.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/modules/ngx_http_addition_filter_module.c	Fri Jul 28 00:00:00 2006 +0400
@@ -143,7 +143,7 @@
         ctx->before_body_sent = 1;
 
         if (conf->before_body.len) {
-            if (ngx_http_subrequest(r, &conf->before_body, NULL, 0)
+            if (ngx_http_subrequest(r, &conf->before_body, NULL, NULL, 0)
                 == NGX_ERROR)
             {
                 return NGX_ERROR;
@@ -167,7 +167,7 @@
         return rc;
     }
 
-    if (ngx_http_subrequest(r, &conf->after_body, NULL, 0) == NGX_ERROR) {
+    if (ngx_http_subrequest(r, &conf->after_body, NULL, NULL, 0) == NGX_ERROR) {
         return NGX_ERROR;
     }
 
--- a/src/http/modules/ngx_http_auth_basic_module.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/modules/ngx_http_auth_basic_module.c	Fri Jul 28 00:00:00 2006 +0400
@@ -60,7 +60,7 @@
 };
 
 
-ngx_http_module_t  ngx_http_auth_basic_module_ctx = {
+static ngx_http_module_t  ngx_http_auth_basic_module_ctx = {
     NULL,                                  /* preconfiguration */
     NULL,                                  /* postconfiguration */
 
--- a/src/http/modules/ngx_http_autoindex_module.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/modules/ngx_http_autoindex_module.c	Fri Jul 28 00:00:00 2006 +0400
@@ -81,7 +81,7 @@
 };
 
 
-ngx_http_module_t  ngx_http_autoindex_module_ctx = {
+static ngx_http_module_t  ngx_http_autoindex_module_ctx = {
     NULL,                                  /* preconfiguration */
     NULL,                                  /* postconfiguration */
 
--- a/src/http/modules/ngx_http_charset_filter_module.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/modules/ngx_http_charset_filter_module.c	Fri Jul 28 00:00:00 2006 +0400
@@ -1325,6 +1325,9 @@
 
     if (ngx_strcasecmp(name->data, "utf-8") == 0) {
         c->utf8 = 1;
+
+    } else {
+        c->utf8 = 0;
     }
 
     return i;
--- a/src/http/modules/ngx_http_chunked_filter_module.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/modules/ngx_http_chunked_filter_module.c	Fri Jul 28 00:00:00 2006 +0400
@@ -95,8 +95,11 @@
 
         size += ngx_buf_size(cl->buf);
 
-        if (cl->buf->flush || ngx_buf_in_memory(cl->buf) || cl->buf->in_file) {
-
+        if (cl->buf->flush
+            || cl->buf->sync
+            || ngx_buf_in_memory(cl->buf)
+            || cl->buf->in_file)
+        {
             tl = ngx_alloc_chain_link(r->pool);
             if (tl == NULL) {
                 return NGX_ERROR;
--- a/src/http/modules/ngx_http_dav_module.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/modules/ngx_http_dav_module.c	Fri Jul 28 00:00:00 2006 +0400
@@ -57,7 +57,7 @@
 };
 
 
-ngx_http_module_t  ngx_http_dav_module_ctx = {
+static ngx_http_module_t  ngx_http_dav_module_ctx = {
     NULL,                                  /* preconfiguration */
     NULL,                                  /* postconfiguration */
 
--- a/src/http/modules/ngx_http_empty_gif_module.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/modules/ngx_http_empty_gif_module.c	Fri Jul 28 00:00:00 2006 +0400
@@ -74,7 +74,7 @@
 };
 
 
-ngx_http_module_t  ngx_http_empty_gif_module_ctx = {
+static ngx_http_module_t  ngx_http_empty_gif_module_ctx = {
     NULL,                          /* preconfiguration */
     NULL,                          /* postconfiguration */
 
--- a/src/http/modules/ngx_http_fastcgi_module.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/modules/ngx_http_fastcgi_module.c	Fri Jul 28 00:00:00 2006 +0400
@@ -347,7 +347,7 @@
 };
 
 
-ngx_http_module_t  ngx_http_fastcgi_module_ctx = {
+static ngx_http_module_t  ngx_http_fastcgi_module_ctx = {
     ngx_http_fastcgi_add_variables,        /* preconfiguration */
     NULL,                                  /* postconfiguration */
 
--- a/src/http/modules/ngx_http_index_module.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/modules/ngx_http_index_module.c	Fri Jul 28 00:00:00 2006 +0400
@@ -72,7 +72,7 @@
 };
 
 
-ngx_http_module_t  ngx_http_index_module_ctx = {
+static ngx_http_module_t  ngx_http_index_module_ctx = {
     NULL,                                  /* preconfiguration */
     NULL,                                  /* postconfiguration */
 
--- a/src/http/modules/ngx_http_log_module.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/modules/ngx_http_log_module.c	Fri Jul 28 00:00:00 2006 +0400
@@ -142,7 +142,7 @@
 };
 
 
-ngx_http_module_t  ngx_http_log_module_ctx = {
+static ngx_http_module_t  ngx_http_log_module_ctx = {
     ngx_http_log_set_formats,              /* preconfiguration */
     ngx_http_log_init,                     /* postconfiguration */
 
--- a/src/http/modules/ngx_http_memcached_module.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/modules/ngx_http_memcached_module.c	Fri Jul 28 00:00:00 2006 +0400
@@ -112,7 +112,7 @@
 };
 
 
-ngx_http_module_t  ngx_http_memcached_module_ctx = {
+static ngx_http_module_t  ngx_http_memcached_module_ctx = {
     NULL,                                  /* preconfiguration */
     NULL,                                  /* postconfiguration */
 
--- a/src/http/modules/ngx_http_proxy_module.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/modules/ngx_http_proxy_module.c	Fri Jul 28 00:00:00 2006 +0400
@@ -327,7 +327,7 @@
 };
 
 
-ngx_http_module_t  ngx_http_proxy_module_ctx = {
+static ngx_http_module_t  ngx_http_proxy_module_ctx = {
     ngx_http_proxy_add_variables,          /* preconfiguration */
     NULL,                                  /* postconfiguration */
 
--- a/src/http/modules/ngx_http_realip_module.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/modules/ngx_http_realip_module.c	Fri Jul 28 00:00:00 2006 +0400
@@ -61,7 +61,7 @@
 
 
 
-ngx_http_module_t  ngx_http_realip_module_ctx = {
+static ngx_http_module_t  ngx_http_realip_module_ctx = {
     NULL,                                  /* preconfiguration */
     NULL,                                  /* postconfiguration */
 
--- a/src/http/modules/ngx_http_rewrite_module.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/modules/ngx_http_rewrite_module.c	Fri Jul 28 00:00:00 2006 +0400
@@ -102,7 +102,7 @@
 };
 
 
-ngx_http_module_t  ngx_http_rewrite_module_ctx = {
+static ngx_http_module_t  ngx_http_rewrite_module_ctx = {
     NULL,                                  /* preconfiguration */
     NULL,                                  /* postconfiguration */
 
--- a/src/http/modules/ngx_http_ssi_filter_module.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/modules/ngx_http_ssi_filter_module.c	Fri Jul 28 00:00:00 2006 +0400
@@ -36,6 +36,13 @@
 } ngx_http_ssi_var_t;
 
 
+typedef struct {
+    ngx_str_t     name;
+    ngx_chain_t  *bufs;
+    ngx_uint_t    count;
+} ngx_http_ssi_block_t;
+
+
 typedef enum {
     ssi_start_state = 0,
     ssi_tag_state,
@@ -83,6 +90,10 @@
     ngx_http_ssi_ctx_t *ctx, ngx_str_t **params);
 static ngx_int_t ngx_http_ssi_endif(ngx_http_request_t *r,
     ngx_http_ssi_ctx_t *ctx, ngx_str_t **params);
+static ngx_int_t ngx_http_ssi_block(ngx_http_request_t *r,
+    ngx_http_ssi_ctx_t *ctx, ngx_str_t **params);
+static ngx_int_t ngx_http_ssi_endblock(ngx_http_request_t *r,
+    ngx_http_ssi_ctx_t *ctx, ngx_str_t **params);
 
 static ngx_int_t ngx_http_ssi_date_gmt_local_variable(ngx_http_request_t *r,
     ngx_http_variable_value_t *v,  uintptr_t gmt);
@@ -189,6 +200,7 @@
 #define  NGX_HTTP_SSI_INCLUDE_VIRTUAL  0
 #define  NGX_HTTP_SSI_INCLUDE_FILE     1
 #define  NGX_HTTP_SSI_INCLUDE_WAIT     2
+#define  NGX_HTTP_SSI_INCLUDE_STUB     3
 
 #define  NGX_HTTP_SSI_ECHO_VAR         0
 #define  NGX_HTTP_SSI_ECHO_DEFAULT     1
@@ -201,11 +213,14 @@
 
 #define  NGX_HTTP_SSI_IF_EXPR          0
 
+#define  NGX_HTTP_SSI_BLOCK_NAME       0
+
 
 static ngx_http_ssi_param_t  ngx_http_ssi_include_params[] = {
     { ngx_string("virtual"), NGX_HTTP_SSI_INCLUDE_VIRTUAL, 0, 0 },
     { ngx_string("file"), NGX_HTTP_SSI_INCLUDE_FILE, 0, 0 },
     { ngx_string("wait"), NGX_HTTP_SSI_INCLUDE_WAIT, 0, 0 },
+    { ngx_string("stub"), NGX_HTTP_SSI_INCLUDE_STUB, 0, 0 },
     { ngx_null_string, 0, 0, 0 }
 };
 
@@ -237,6 +252,12 @@
 };
 
 
+static ngx_http_ssi_param_t  ngx_http_ssi_block_params[] = {
+    { ngx_string("name"), NGX_HTTP_SSI_BLOCK_NAME, 1, 0 },
+    { ngx_null_string, 0, 0, 0 }
+};
+
+
 static ngx_http_ssi_param_t  ngx_http_ssi_no_params[] = {
     { ngx_null_string, 0, 0, 0 }
 };
@@ -244,21 +265,27 @@
 
 static ngx_http_ssi_command_t  ngx_http_ssi_commands[] = {
     { ngx_string("include"), ngx_http_ssi_include,
-                       ngx_http_ssi_include_params, 0, 1 },
-    { ngx_string("echo"), ngx_http_ssi_echo, ngx_http_ssi_echo_params, 0, 0 },
+                       ngx_http_ssi_include_params, 0, 0, 1 },
+    { ngx_string("echo"), ngx_http_ssi_echo,
+                       ngx_http_ssi_echo_params, 0, 0, 0 },
     { ngx_string("config"), ngx_http_ssi_config,
-                       ngx_http_ssi_config_params, 0, 0 },
-    { ngx_string("set"), ngx_http_ssi_set, ngx_http_ssi_set_params, 0, 0 },
-
-    { ngx_string("if"), ngx_http_ssi_if, ngx_http_ssi_if_params, 0, 0 },
+                       ngx_http_ssi_config_params, 0, 0, 0 },
+    { ngx_string("set"), ngx_http_ssi_set, ngx_http_ssi_set_params, 0, 0, 0 },
+
+    { ngx_string("if"), ngx_http_ssi_if, ngx_http_ssi_if_params, 0, 0, 0 },
     { ngx_string("elif"), ngx_http_ssi_if, ngx_http_ssi_if_params,
-                       NGX_HTTP_SSI_COND_IF, 0 },
+                       NGX_HTTP_SSI_COND_IF, 0, 0 },
     { ngx_string("else"), ngx_http_ssi_else, ngx_http_ssi_no_params,
-                       NGX_HTTP_SSI_COND_IF, 0 },
+                       NGX_HTTP_SSI_COND_IF, 0, 0 },
     { ngx_string("endif"), ngx_http_ssi_endif, ngx_http_ssi_no_params,
-                       NGX_HTTP_SSI_COND_ELSE, 0 },
-
-    { ngx_null_string, NULL, NULL, 0, 0 }
+                       NGX_HTTP_SSI_COND_ELSE, 0, 0 },
+
+    { ngx_string("block"), ngx_http_ssi_block,
+                       ngx_http_ssi_block_params, 0, 0, 0 },
+    { ngx_string("endblock"), ngx_http_ssi_endblock,
+                       ngx_http_ssi_no_params, 0, 1, 0 },
+
+    { ngx_null_string, NULL, NULL, 0, 0, 0 }
 };
 
 
@@ -348,13 +375,15 @@
 static ngx_int_t
 ngx_http_ssi_body_filter(ngx_http_request_t *r, ngx_chain_t *in)
 {
+    size_t                     len;
     ngx_int_t                  rc;
     ngx_buf_t                 *b;
     ngx_uint_t                 i, index;
-    ngx_chain_t               *cl;
+    ngx_chain_t               *cl, **ll;
     ngx_table_elt_t           *param;
     ngx_connection_t          *c;
-    ngx_http_ssi_ctx_t        *ctx;
+    ngx_http_ssi_ctx_t        *ctx, *mctx;
+    ngx_http_ssi_block_t      *bl;
     ngx_http_ssi_param_t      *prm;
     ngx_http_ssi_command_t    *cmd;
     ngx_http_ssi_loc_conf_t   *slcf;
@@ -510,6 +539,47 @@
                     ctx->last_out = &cl->next;
 
                 } else {
+                    if (ctx->block
+                        && ctx->saved + (ctx->copy_end - ctx->copy_start))
+                    {
+                        b = ngx_create_temp_buf(r->pool,
+                               ctx->saved + (ctx->copy_end - ctx->copy_start));
+
+                        if (b == NULL) {
+                            return NGX_ERROR;
+                        }
+
+                        if (ctx->saved) {
+                            b->last = ngx_cpymem(b->pos, ngx_http_ssi_string,
+                                                 ctx->saved);
+                        }
+
+                        b->last = ngx_cpymem(b->last, ctx->copy_start,
+                                             ctx->copy_end - ctx->copy_start);
+
+                        cl = ngx_alloc_chain_link(r->pool);
+                        if (cl == NULL) {
+                            return NGX_ERROR;
+                        }
+
+                        cl->buf = b;
+                        cl->next = NULL;
+
+                        b = NULL;
+
+                        mctx = ngx_http_get_module_ctx(r->main,
+                                                   ngx_http_ssi_filter_module);
+                        bl = mctx->blocks->elts;
+                        for (ll = &bl[mctx->blocks->nelts - 1].bufs;
+                             *ll;
+                             ll = &(*ll)->next)
+                        {
+                            /* void */
+                        }
+
+                        *ll = cl;
+                    }
+
                     ctx->saved = 0;
                 }
             }
@@ -559,8 +629,79 @@
                     goto ssi_error;
                 }
 
-                if (!ctx->output && cmd->conditional == 0) {
-                    continue;
+                if (!ctx->output && !cmd->block) {
+
+                    if (ctx->block) {
+
+                        /* reconstruct the SSI command text */
+
+                        len = 5 + ctx->command.len + 4;
+
+                        param = ctx->params.elts;
+                        for (i = 0; i < ctx->params.nelts; i++) {
+                            len += 1 + param[i].key.len + 2
+                                + param[i].value.len + 1;
+                        }
+
+                        b = ngx_create_temp_buf(r->pool, len);
+
+                        if (b == NULL) {
+                            return NGX_ERROR;
+                        }
+
+                        cl = ngx_alloc_chain_link(r->pool);
+                        if (cl == NULL) {
+                            return NGX_ERROR;
+                        }
+
+                        cl->buf = b;
+                        cl->next = NULL;
+
+                        *b->last++ = '<';
+                        *b->last++ = '!';
+                        *b->last++ = '-';
+                        *b->last++ = '-';
+                        *b->last++ = '#';
+
+                        b->last = ngx_cpymem(b->last, ctx->command.data,
+                                             ctx->command.len);
+
+                        for (i = 0; i < ctx->params.nelts; i++) {
+                            *b->last++ = ' ';
+                            b->last = ngx_cpymem(b->last, param[i].key.data,
+                                                 param[i].key.len);
+                            *b->last++ = '=';
+                            *b->last++ = '"';
+                            b->last = ngx_cpymem(b->last, param[i].value.data,
+                                                 param[i].value.len);
+                            *b->last++ = '"';
+                        }
+
+                        *b->last++ = ' ';
+                        *b->last++ = '-';
+                        *b->last++ = '-';
+                        *b->last++ = '>';
+
+                        mctx = ngx_http_get_module_ctx(r->main,
+                                                   ngx_http_ssi_filter_module);
+                        bl = mctx->blocks->elts;
+                        for (ll = &bl[mctx->blocks->nelts - 1].bufs;
+                             *ll;
+                             ll = &(*ll)->next)
+                        {
+                            /* void */
+                        }
+
+                        *ll = cl;
+
+                        b = NULL;
+
+                        continue;
+                    }
+
+                    if (cmd->conditional == 0) {
+                        continue;
+                    }
                 }
 
                 if (ctx->params.nelts > NGX_HTTP_SSI_MAX_PARAMS) {
@@ -1382,8 +1523,12 @@
 
     ctx = ngx_http_get_module_ctx(r->main, ngx_http_ssi_filter_module);
 
-    var = ctx->variables.elts;
-    for (i = 0; i < ctx->variables.nelts; i++) {
+    if (ctx->variables == NULL) {
+        return NULL;
+    }
+
+    var = ctx->variables->elts;
+    for (i = 0; i < ctx->variables->nelts; i++) {
         if (name->len != var[i].name.len) {
             continue;
         }
@@ -1663,13 +1808,18 @@
 ngx_http_ssi_include(ngx_http_request_t *r, ngx_http_ssi_ctx_t *ctx,
     ngx_str_t **params)
 {
-    ngx_int_t    rc;
-    ngx_str_t   *uri, *file, *wait, args;
-    ngx_uint_t   flags;
+    ngx_int_t              rc;
+    ngx_str_t             *uri, *file, *wait, *stub, args;
+    ngx_buf_t             *b;
+    ngx_uint_t             flags, i;
+    ngx_chain_t           *out, *cl, *tl, **ll;
+    ngx_http_ssi_ctx_t    *mctx;
+    ngx_http_ssi_block_t  *bl;
 
     uri = params[NGX_HTTP_SSI_INCLUDE_VIRTUAL];
     file = params[NGX_HTTP_SSI_INCLUDE_FILE];
     wait = params[NGX_HTTP_SSI_INCLUDE_WAIT];
+    stub = params[NGX_HTTP_SSI_INCLUDE_STUB];
 
     if (uri && file) {
         ngx_log_error(NGX_LOG_ERR, r->connection->log, 0,
@@ -1687,8 +1837,7 @@
     if (wait) {
         if (uri == NULL) {
             ngx_log_error(NGX_LOG_ERR, r->connection->log, 0,
-                          "\"wait\" may not be used with file=\"%V\"",
-                          uri, file);
+                          "\"wait\" may not be used with file=\"%V\"", file);
             return NGX_HTTP_SSI_ERROR;
         }
 
@@ -1699,7 +1848,7 @@
         {
             ngx_log_error(NGX_LOG_ERR, r->connection->log, 0,
                           "invalid value \"%V\" in the \"wait\" parameter",
-                          &wait);
+                          wait);
             return NGX_HTTP_SSI_ERROR;
         }
     }
@@ -1725,7 +1874,68 @@
         return NGX_HTTP_SSI_ERROR;
     }
 
-    rc = ngx_http_subrequest(r, uri, &args, flags);
+    out = NULL;
+
+    if (stub) {
+        mctx = ngx_http_get_module_ctx(r->main, ngx_http_ssi_filter_module);
+
+        if (mctx->blocks) {
+            bl = mctx->blocks->elts;
+            for (i = 0; i < mctx->blocks->nelts; i++) {
+                if (stub->len == bl[i].name.len
+                    && ngx_strncmp(stub->data, bl[i].name.data, stub->len) == 0)
+                {
+                    goto found;
+                }
+            }
+        }
+
+        ngx_log_error(NGX_LOG_ERR, r->connection->log, 0,
+                      "\"stub\"=\"%V\" for \"include\" not found", stub);
+        return NGX_HTTP_SSI_ERROR;
+
+    found:
+
+        if (bl[i].count++) {
+
+            ll = &out;
+
+            for (tl = bl[i].bufs; tl; tl = tl->next) {
+
+                if (ctx->free) {
+                    cl = ctx->free;
+                    ctx->free = ctx->free->next;
+                    b = cl->buf;
+
+                } else {
+                    b = ngx_alloc_buf(r->pool);
+                    if (b == NULL) {
+                        return NGX_ERROR;
+                    }
+
+                    cl = ngx_alloc_chain_link(r->pool);
+                    if (cl == NULL) {
+                        return NGX_ERROR;
+                    }
+
+                    cl->buf = b;
+                }
+
+                ngx_memcpy(b, tl->buf, sizeof(ngx_buf_t));
+
+                b->pos = b->start;
+
+                *ll = cl;
+                cl->next = NULL;
+                ll = &cl->next;
+            }
+
+        } else {
+            out = bl[i].bufs;
+        }
+    }
+
+    rc = ngx_http_subrequest(r, uri, &args, out, flags);
 
     if (rc == NGX_ERROR) {
         return NGX_HTTP_SSI_ERROR;
@@ -1861,10 +2071,10 @@
 
     mctx = ngx_http_get_module_ctx(r->main, ngx_http_ssi_filter_module);
 
-    if (mctx->variables.elts == NULL) {
-        if (ngx_array_init(&mctx->variables, r->pool, 4,
-                           sizeof(ngx_http_ssi_var_t)) != NGX_OK)
-        {
+    if (mctx->variables == NULL) {
+        mctx->variables = ngx_array_create(r->pool, 4,
+                                           sizeof(ngx_http_ssi_var_t));
+        if (mctx->variables == NULL) {
             return NGX_HTTP_SSI_ERROR;
         }
     }
@@ -1893,7 +2103,7 @@
         return NGX_OK;
     }
 
-    var = ngx_array_push(&mctx->variables);
+    var = ngx_array_push(mctx->variables);
     if (var == NULL) {
         return NGX_HTTP_SSI_ERROR;
     }
@@ -2136,6 +2346,56 @@
 
 
 static ngx_int_t
+ngx_http_ssi_block(ngx_http_request_t *r, ngx_http_ssi_ctx_t *ctx,
+    ngx_str_t **params)
+{
+    ngx_http_ssi_ctx_t    *mctx;
+    ngx_http_ssi_block_t  *bl;
+
+    ngx_log_debug0(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
+                   "ssi block");
+
+    mctx = ngx_http_get_module_ctx(r->main, ngx_http_ssi_filter_module);
+
+    if (mctx->blocks == NULL) {
+        mctx->blocks = ngx_array_create(r->pool, 4,
+                                        sizeof(ngx_http_ssi_block_t));
+        if (mctx->blocks == NULL) {
+            return NGX_HTTP_SSI_ERROR;
+        }
+    }
+
+    bl = ngx_array_push(mctx->blocks);
+    if (bl == NULL) {
+        return NGX_HTTP_SSI_ERROR;
+    }
+
+    bl->name = *params[NGX_HTTP_SSI_BLOCK_NAME];
+    bl->bufs = NULL;
+    bl->count = 0;
+
+    ctx->output = 0;
+    ctx->block = 1;
+
+    return NGX_OK;
+}
+
+
+static ngx_int_t
+ngx_http_ssi_endblock(ngx_http_request_t *r, ngx_http_ssi_ctx_t *ctx,
+    ngx_str_t **params)
+{
+    ngx_log_debug0(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
+                   "ssi endblock");
+
+    ctx->output = 1;
+    ctx->block = 0;
+
+    return NGX_OK;
+}
+
+
+static ngx_int_t
 ngx_http_ssi_date_gmt_local_variable(ngx_http_request_t *r,
     ngx_http_variable_value_t *v,  uintptr_t gmt)
 {
--- a/src/http/modules/ngx_http_ssi_filter_module.h	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/modules/ngx_http_ssi_filter_module.h	Fri Jul 28 00:00:00 2006 +0400
@@ -56,9 +56,11 @@
 
     size_t                    value_len;
 
-    ngx_array_t               variables;
+    ngx_array_t              *variables;
+    ngx_array_t              *blocks;
 
     unsigned                  conditional:2;
+    unsigned                  block:1;
     unsigned                  output:1;
     unsigned                  output_chosen:1;
     unsigned                  wait:1;
@@ -88,6 +90,7 @@
     ngx_http_ssi_param_t     *params;
 
     unsigned                  conditional:2;
+    unsigned                  block:1;
     unsigned                  flush:1;
 } ngx_http_ssi_command_t;
 
--- a/src/http/modules/ngx_http_ssl_module.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/modules/ngx_http_ssl_module.c	Fri Jul 28 00:00:00 2006 +0400
@@ -85,7 +85,7 @@
       NULL },
 
     { ngx_string("ssl_verify_client"),
-      NGX_HTTP_MAIN_CONF|NGX_HTTP_SRV_CONF|NGX_CONF_1MORE,
+      NGX_HTTP_MAIN_CONF|NGX_HTTP_SRV_CONF|NGX_CONF_FLAG,
       ngx_conf_set_flag_slot,
       NGX_HTTP_SRV_CONF_OFFSET,
       offsetof(ngx_http_ssl_srv_conf_t, verify),
--- a/src/http/modules/ngx_http_stub_status_module.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/modules/ngx_http_stub_status_module.c	Fri Jul 28 00:00:00 2006 +0400
@@ -26,7 +26,7 @@
 
 
 
-ngx_http_module_t  ngx_http_stub_status_module_ctx = {
+static ngx_http_module_t  ngx_http_stub_status_module_ctx = {
     NULL,                                  /* preconfiguration */
     NULL,                                  /* postconfiguration */
 
--- a/src/http/modules/ngx_http_userid_filter_module.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/modules/ngx_http_userid_filter_module.c	Fri Jul 28 00:00:00 2006 +0400
@@ -160,7 +160,7 @@
 };
 
 
-ngx_http_module_t  ngx_http_userid_filter_module_ctx = {
+static ngx_http_module_t  ngx_http_userid_filter_module_ctx = {
     ngx_http_userid_add_variables,         /* preconfiguration */
     NULL,                                  /* postconfiguration */
 
--- a/src/http/modules/perl/nginx.xs	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/modules/perl/nginx.xs	Fri Jul 28 00:00:00 2006 +0400
@@ -199,13 +199,16 @@
     CODE:
 
     dXSTARG;
-    ngx_http_request_t  *r;
-    SV                  *key;
-    u_char              *p;
-    STRLEN               len;
-    ngx_uint_t           i;
-    ngx_list_part_t     *part;
-    ngx_table_elt_t     *header;
+    ngx_http_request_t         *r;
+    SV                         *key;
+    u_char                     *p, *lowcase_key, *cookie;
+    STRLEN                      len;
+    ssize_t                     size;
+    ngx_uint_t                  i, n, hash;
+    ngx_list_part_t            *part;
+    ngx_table_elt_t            *h, **ph;
+    ngx_http_header_t          *hh;
+    ngx_http_core_main_conf_t  *cmcf;
 
     ngx_http_perl_set_request(r);
 
@@ -217,8 +220,85 @@
 
     p = (u_char *) SvPV(key, len);
 
+    /* look up hashed headers */
+
+    lowcase_key = ngx_palloc(r->pool, len);
+    if (lowcase_key == NULL) {
+        XSRETURN_UNDEF;
+    }
+
+    hash = 0;
+    for (i = 0; i < len; i++) {
+        lowcase_key[i] = ngx_tolower(p[i]);
+        hash = ngx_hash(hash, lowcase_key[i]);
+    }
+
+    cmcf = ngx_http_get_module_main_conf(r, ngx_http_core_module);
+
+    hh = ngx_hash_find(&cmcf->headers_in_hash, hash, lowcase_key, len);
+
+    if (hh) {
+        if (hh->offset) {
+
+            ph = (ngx_table_elt_t **) ((char *) &r->headers_in + hh->offset);
+
+            if (*ph) {
+                ngx_http_perl_set_targ((*ph)->value.data, (*ph)->value.len, 0);
+
+                goto done;
+            }
+
+            XSRETURN_UNDEF;
+        }
+
+        /* Cookie */
+
+        n = r->headers_in.cookies.nelts;
+
+        if (n == 0) {
+            XSRETURN_UNDEF;
+        }
+
+        ph = r->headers_in.cookies.elts;
+
+        if (n == 1) {
+            ngx_http_perl_set_targ((*ph)->value.data, (*ph)->value.len, 0);
+
+            goto done;
+        }
+
+        size = - (ssize_t) (sizeof("; ") - 1);
+
+        for (i = 0; i < n; i++) {
+            size += ph[i]->value.len + sizeof("; ") - 1;
+        }
+
+        cookie = ngx_palloc(r->pool, size);
+        if (cookie == NULL) {
+            XSRETURN_UNDEF;
+        }
+
+        p = cookie;
+
+        for (i = 0; /* void */ ; i++) {
+            p = ngx_copy(p, ph[i]->value.data, ph[i]->value.len);
+
+            if (i == n - 1) {
+                break;
+            }
+
+            *p++ = ';'; *p++ = ' ';
+        }
+
+        ngx_http_perl_set_targ(cookie, size, 0);
+
+        goto done;
+    }
+
+    /* iterate over all headers */
+
     part = &r->headers_in.headers.part;
-    header = part->elts;
+    h = part->elts;
 
     for (i = 0; /* void */ ; i++) {
 
@@ -228,17 +308,17 @@
             }
 
             part = part->next;
-            header = part->elts;
+            h = part->elts;
             i = 0;
         }
 
-        if (len != header[i].key.len
-            || ngx_strcasecmp(p, header[i].key.data) != 0)
+        if (len != h[i].key.len
+            || ngx_strcasecmp(p, h[i].key.data) != 0)
         {
             continue;
         }
 
-        ngx_http_perl_set_targ(header[i].value.data, header[i].value.len, 0);
+        ngx_http_perl_set_targ(h[i].value.data, h[i].value.len, 0);
 
         goto done;
     }
--- a/src/http/modules/perl/ngx_http_perl_module.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/modules/perl/ngx_http_perl_module.c	Fri Jul 28 00:00:00 2006 +0400
@@ -170,7 +170,7 @@
 };
 
 static ngx_http_ssi_command_t  ngx_http_perl_ssi_command = {
-    ngx_string("perl"), ngx_http_perl_ssi, ngx_http_perl_ssi_params, 0, 1
+    ngx_string("perl"), ngx_http_perl_ssi, ngx_http_perl_ssi_params, 0, 0, 1
 };
 
 #endif
--- a/src/http/ngx_http.h	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/ngx_http.h	Fri Jul 28 00:00:00 2006 +0400
@@ -84,9 +84,6 @@
 
 ngx_int_t ngx_http_send_special(ngx_http_request_t *r, ngx_uint_t flags);
 
-u_char * ngx_http_log_error_info(ngx_http_request_t *r, u_char *buf,
-    size_t len);
-
 
 ngx_int_t ngx_http_read_client_request_body(ngx_http_request_t *r,
     ngx_http_client_body_handler_pt post_handler);
--- a/src/http/ngx_http_copy_filter_module.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/ngx_http_copy_filter_module.c	Fri Jul 28 00:00:00 2006 +0400
@@ -104,6 +104,7 @@
         ctx->output_filter = (ngx_output_chain_filter_pt) ngx_http_next_filter;
         ctx->filter_ctx = r;
 
+        r->request_output = 1;
     }
 
     rc = ngx_output_chain(ctx, in);
--- a/src/http/ngx_http_core_module.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/ngx_http_core_module.c	Fri Jul 28 00:00:00 2006 +0400
@@ -426,7 +426,7 @@
 };
 
 
-ngx_http_module_t  ngx_http_core_module_ctx = {
+static ngx_http_module_t  ngx_http_core_module_ctx = {
     ngx_http_core_preconfiguration,        /* preconfiguration */
     NULL,                                  /* postconfiguration */
 
@@ -1071,13 +1071,19 @@
         last = ngx_copy(path->data, clcf->root.data, clcf->root.len);
 
     } else {
-        last = ngx_http_script_run(r, path, clcf->root_lengths->elts, reserved,
-                                   clcf->root_values->elts);
-        if (last == NULL) {
+        if (ngx_http_script_run(r, path, clcf->root_lengths->elts, reserved,
+                               clcf->root_values->elts)
+            == NULL)
+        {
+            return NULL;
+        }
+
+        if (ngx_conf_full_name((ngx_cycle_t *) ngx_cycle, path) == NGX_ERROR) {
             return NULL;
         }
 
         r->root_length = path->len - reserved;
+        last = path->data + r->root_length;
     }
 
     last = ngx_cpystrn(last, r->uri.data + alias, r->uri.len - alias + 1);
@@ -1158,7 +1164,7 @@
 
 ngx_int_t
 ngx_http_subrequest(ngx_http_request_t *r,
-    ngx_str_t *uri, ngx_str_t *args, ngx_uint_t flags)
+    ngx_str_t *uri, ngx_str_t *args, ngx_chain_t *out, ngx_uint_t flags)
 {
     ngx_connection_t              *c;
     ngx_http_request_t            *sr;
@@ -1239,6 +1245,7 @@
         return NGX_ERROR;
     }
 
+    sr->out = out;
     sr->main = r->main;
     sr->parent = r;
     sr->read_event_handler = ngx_http_request_empty_handler;
@@ -2527,8 +2534,10 @@
         lcf->root.len--;
     }
 
-    if (ngx_conf_full_name(cf->cycle, &lcf->root) == NGX_ERROR) {
-        return NGX_CONF_ERROR;
+    if (lcf->root.data[0] != '$') {
+        if (ngx_conf_full_name(cf->cycle, &lcf->root) == NGX_ERROR) {
+            return NGX_CONF_ERROR;
+        }
     }
 
     n = ngx_http_script_variables_count(&lcf->root);
--- a/src/http/ngx_http_core_module.h	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/ngx_http_core_module.h	Fri Jul 28 00:00:00 2006 +0400
@@ -267,7 +267,7 @@
 ngx_int_t ngx_http_auth_basic_user(ngx_http_request_t *r);
 
 ngx_int_t ngx_http_subrequest(ngx_http_request_t *r,
-    ngx_str_t *uri, ngx_str_t *args, ngx_uint_t flags);
+    ngx_str_t *uri, ngx_str_t *args, ngx_chain_t *out, ngx_uint_t flags);
 ngx_int_t ngx_http_internal_redirect(ngx_http_request_t *r,
     ngx_str_t *uri, ngx_str_t *args);
 
@@ -283,7 +283,6 @@
 ngx_int_t ngx_http_write_filter(ngx_http_request_t *r, ngx_chain_t *chain);
 
 
-extern ngx_http_module_t  ngx_http_core_module_ctx;
 extern ngx_module_t  ngx_http_core_module;
 
 extern ngx_uint_t ngx_http_max_module;
--- a/src/http/ngx_http_header_filter_module.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/ngx_http_header_filter_module.c	Fri Jul 28 00:00:00 2006 +0400
@@ -159,6 +159,8 @@
     ngx_table_elt_t           *header;
     ngx_http_core_loc_conf_t  *clcf;
 
+    r->header_sent = 1;
+
     if (r != r->main) {
         return NGX_OK;
     }
--- a/src/http/ngx_http_parse.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/ngx_http_parse.c	Fri Jul 28 00:00:00 2006 +0400
@@ -969,6 +969,8 @@
 #endif
 
         case sw_quoted:
+            r->quoted_uri = 1;
+
             if (ch >= '0' && ch <= '9') {
                 decoded = (u_char) (ch - '0');
                 state = sw_quoted_second;
--- a/src/http/ngx_http_postpone_filter_module.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/ngx_http_postpone_filter_module.c	Fri Jul 28 00:00:00 2006 +0400
@@ -127,7 +127,6 @@
         || (r->connection->buffered
             & (NGX_HTTP_LOWLEVEL_BUFFERED|NGX_LOWLEVEL_BUFFERED)))
     {
-
         ngx_log_debug2(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
                        "http postpone filter out \"%V?%V\"", &r->uri, &r->args);
 
--- a/src/http/ngx_http_request.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/ngx_http_request.c	Fri Jul 28 00:00:00 2006 +0400
@@ -853,7 +853,7 @@
 
             } else {
                 for (i = 0; i < h->key.len; i++) {
-                    h->lowcase_key[i] = ngx_tolower(h->lowcase_key[i]);
+                    h->lowcase_key[i] = ngx_tolower(h->key.data[i]);
                 }
             }
 
@@ -1459,6 +1459,28 @@
                    "http finalize request: %d, \"%V?%V\"",
                    rc, &r->uri, &r->args);
 
+    if (r != r->main
+        && rc != NGX_ERROR
+        && !r->connection->error
+        && !r->request_output
+        && r->out)
+    {
+        if (!r->header_sent) {
+            rc = ngx_http_set_content_type(r);
+
+            if (rc == NGX_OK) {
+                rc = ngx_http_send_header(r);
+
+                if (rc != NGX_ERROR) {
+                    rc = ngx_http_output_filter(r, r->out);
+                }
+            }
+
+        } else {
+            rc = ngx_http_output_filter(r, r->out);
+        }
+    }
+
     if (rc == NGX_ERROR
         || rc == NGX_HTTP_REQUEST_TIME_OUT
         || r->connection->error)
@@ -2435,15 +2457,6 @@
         buf = p;
     }
 
-    return ngx_http_log_error_info(r, buf, len);
-}
-
-
-u_char *
-ngx_http_log_error_info(ngx_http_request_t *r, u_char *buf, size_t len)
-{
-    u_char  *p;
-
     if (r->headers_in.host) {
         p = ngx_snprintf(buf, len, ", host: \"%V\"",
                          &r->headers_in.host->value);
--- a/src/http/ngx_http_request.h	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/ngx_http_request.h	Fri Jul 28 00:00:00 2006 +0400
@@ -437,6 +437,8 @@
     unsigned                          internal:1;
     unsigned                          post_action:1;
     unsigned                          request_complete:1;
+    unsigned                          request_output:1;
+    unsigned                          header_sent:1;
     unsigned                          done:1;
     unsigned                          utf8:1;
 
--- a/src/http/ngx_http_request_body.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/ngx_http_request_body.c	Fri Jul 28 00:00:00 2006 +0400
@@ -92,6 +92,8 @@
         rb->bufs->buf = b;
         rb->bufs->next = NULL;
 
+        rb->buf = b;
+
         if ((off_t) preread >= r->headers_in.content_length_n) {
 
             /* the whole request body was pre-read */
@@ -124,8 +126,6 @@
 
             /* the whole request body may be placed in r->header_in */
 
-            rb->buf = b;
-
             r->read_event_handler = ngx_http_read_client_request_body_handler;
 
             return ngx_http_do_read_client_request_body(r);
--- a/src/http/ngx_http_upstream.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/ngx_http_upstream.c	Fri Jul 28 00:00:00 2006 +0400
@@ -1394,6 +1394,7 @@
     if (u->cachable) {
         p->temp_file->persistent = 1;
     } else {
+        p->temp_file->log_level = NGX_LOG_WARN;
         p->temp_file->warn = "an upstream response is buffered "
                              "to a temporary file";
     }
--- a/src/http/ngx_http_variables.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/ngx_http_variables.c	Fri Jul 28 00:00:00 2006 +0400
@@ -523,15 +523,17 @@
 ngx_http_variable_headers(ngx_http_request_t *r, ngx_http_variable_value_t *v,
     uintptr_t data)
 {
-    size_t             len;
+    ssize_t            len;
     u_char            *p;
-    ngx_uint_t         i;
+    ngx_uint_t         i, n;
     ngx_array_t       *a;
     ngx_table_elt_t  **h;
 
     a = (ngx_array_t *) ((char *) r + data);
 
-    if (a->nelts == 0) {
+    n = a->nelts;
+
+    if (n == 0) {
         v->not_found = 1;
         return NGX_OK;
     }
@@ -542,16 +544,16 @@
 
     h = a->elts;
 
-    if (a->nelts == 1) {
+    if (n == 1) {
         v->len = (*h)->value.len;
         v->data = (*h)->value.data;
 
         return NGX_OK;
     }
 
-    len = (size_t) - (ssize_t) (sizeof("; ") - 1);
+    len = - (ssize_t) (sizeof("; ") - 1);
 
-    for (i = 0; i < a->nelts; i++) {
+    for (i = 0; i < n; i++) {
         len += h[i]->value.len + sizeof("; ") - 1;
     }
 
@@ -566,7 +568,7 @@
     for (i = 0; /* void */ ; i++) {
         p = ngx_copy(p, h[i]->value.data, h[i]->value.len);
 
-        if (i == a->nelts - 1) {
+        if (i == n - 1) {
             break;
         }
 
--- a/src/http/ngx_http_write_filter_module.c	Tue Jul 11 00:00:00 2006 +0400
+++ b/src/http/ngx_http_write_filter_module.c	Fri Jul 28 00:00:00 2006 +0400
@@ -13,7 +13,7 @@
 static ngx_int_t ngx_http_write_filter_init(ngx_cycle_t *cycle);
 
 
-ngx_http_module_t  ngx_http_write_filter_module_ctx = {
+static ngx_http_module_t  ngx_http_write_filter_module_ctx = {
     NULL,                                  /* preconfiguration */
     NULL,                                  /* postconfiguration */
 
@@ -69,7 +69,7 @@
     for (cl = r->out; cl; cl = cl->next) {
         ll = &cl->next;
 
-        ngx_log_debug7(NGX_LOG_DEBUG_EVENT, r->connection->log, 0,
+        ngx_log_debug7(NGX_LOG_DEBUG_EVENT, c->log, 0,
                        "write old buf t:%d f:%d %p, pos %p, size: %z "
                        "file: %O, size: %z",
                        cl->buf->temporary, cl->buf->in_file,
@@ -80,7 +80,7 @@
 
 #if 1
         if (ngx_buf_size(cl->buf) == 0 && !ngx_buf_special(cl->buf)) {
-            ngx_log_error(NGX_LOG_ALERT, r->connection->log, 0,
+            ngx_log_error(NGX_LOG_ALERT, c->log, 0,
                           "zero size buf in writer "
                           "t:%d r:%d f:%d %p %p-%p %p %O-%O",
                           cl->buf->temporary,
@@ -121,7 +121,7 @@
         *ll = cl;
         ll = &cl->next;
 
-        ngx_log_debug7(NGX_LOG_DEBUG_EVENT, r->connection->log, 0,
+        ngx_log_debug7(NGX_LOG_DEBUG_EVENT, c->log, 0,
                        "write new buf t:%d f:%d %p, pos %p, size: %z "
                        "file: %O, size: %z",
                        cl->buf->temporary, cl->buf->in_file,
@@ -132,7 +132,7 @@
 
 #if 1
         if (ngx_buf_size(cl->buf) == 0 && !ngx_buf_special(cl->buf)) {
-            ngx_log_error(NGX_LOG_ALERT, r->connection->log, 0,
+            ngx_log_error(NGX_LOG_ALERT, c->log, 0,
                           "zero size buf in writer "
                           "t:%d r:%d f:%d %p %p-%p %p %O-%O",
                           cl->buf->temporary,
@@ -201,7 +201,7 @@
             return NGX_OK;
         }
 
-        ngx_log_error(NGX_LOG_ALERT, r->connection->log, 0,
+        ngx_log_error(NGX_LOG_ALERT, c->log, 0,
                       "the http output chain is empty");
 
         ngx_debug_point();
@@ -214,8 +214,8 @@
 
         if (to_send <= 0) {
             c->write->delayed = 1;
-            ngx_add_timer(r->connection->write,
-                       (ngx_msec_t) (- to_send * 1000 / r->limit_rate + 1));
+            ngx_add_timer(c->write,
+                          (ngx_msec_t) (- to_send * 1000 / r->limit_rate + 1));
 
             c->buffered |= NGX_HTTP_WRITE_BUFFERED;
 
@@ -244,8 +244,7 @@
     if (to_send) {
         sent = c->sent - sent;
         c->write->delayed = 1;
-        ngx_add_timer(r->connection->write,
-                      (ngx_msec_t) (sent * 1000 / r->limit_rate + 1));
+        ngx_add_timer(c->write, (ngx_msec_t) (sent * 1000 / r->limit_rate + 1));
     }
 
     for (cl = r->out; cl && cl != chain; /* void */) {