comparison src/http/modules/ngx_http_ssi_filter_module.c @ 665:0b460e61bdcd default tip

Merge with nginx 1.0.0.
author Maxim Dounin <mdounin@mdounin.ru>
date Mon, 25 Apr 2011 04:22:17 +0400
parents b4dcae568a2a
children
comparison
equal deleted inserted replaced
572:06419a2298a9 665:0b460e61bdcd
12 12
13 #define NGX_HTTP_SSI_DATE_LEN 2048 13 #define NGX_HTTP_SSI_DATE_LEN 2048
14 14
15 #define NGX_HTTP_SSI_ADD_PREFIX 1 15 #define NGX_HTTP_SSI_ADD_PREFIX 1
16 #define NGX_HTTP_SSI_ADD_ZERO 2 16 #define NGX_HTTP_SSI_ADD_ZERO 2
17 #define NGX_HTTP_SSI_EXPR_TEST 4
18 17
19 18
20 typedef struct { 19 typedef struct {
21 ngx_flag_t enable; 20 ngx_flag_t enable;
22 ngx_flag_t silent_errors; 21 ngx_flag_t silent_errors;
69 } ngx_http_ssi_state_e; 68 } ngx_http_ssi_state_e;
70 69
71 70
72 static ngx_int_t ngx_http_ssi_output(ngx_http_request_t *r, 71 static ngx_int_t ngx_http_ssi_output(ngx_http_request_t *r,
73 ngx_http_ssi_ctx_t *ctx); 72 ngx_http_ssi_ctx_t *ctx);
73 static void ngx_http_ssi_buffered(ngx_http_request_t *r,
74 ngx_http_ssi_ctx_t *ctx);
74 static ngx_int_t ngx_http_ssi_parse(ngx_http_request_t *r, 75 static ngx_int_t ngx_http_ssi_parse(ngx_http_request_t *r,
75 ngx_http_ssi_ctx_t *ctx); 76 ngx_http_ssi_ctx_t *ctx);
76 static ngx_str_t *ngx_http_ssi_get_variable(ngx_http_request_t *r, 77 static ngx_str_t *ngx_http_ssi_get_variable(ngx_http_request_t *r,
77 ngx_str_t *name, ngx_uint_t key); 78 ngx_str_t *name, ngx_uint_t key);
78 static ngx_int_t ngx_http_ssi_evaluate_string(ngx_http_request_t *r, 79 static ngx_int_t ngx_http_ssi_evaluate_string(ngx_http_request_t *r,
345 ctx->params.elts = ctx->params_array; 346 ctx->params.elts = ctx->params_array;
346 ctx->params.size = sizeof(ngx_table_elt_t); 347 ctx->params.size = sizeof(ngx_table_elt_t);
347 ctx->params.nalloc = NGX_HTTP_SSI_PARAMS_N; 348 ctx->params.nalloc = NGX_HTTP_SSI_PARAMS_N;
348 ctx->params.pool = r->pool; 349 ctx->params.pool = r->pool;
349 350
350 ctx->timefmt.len = sizeof("%A, %d-%b-%Y %H:%M:%S %Z") - 1; 351 ngx_str_set(&ctx->timefmt, "%A, %d-%b-%Y %H:%M:%S %Z");
351 ctx->timefmt.data = (u_char *) "%A, %d-%b-%Y %H:%M:%S %Z"; 352 ngx_str_set(&ctx->errmsg,
352 353 "[an error occurred while processing the directive]");
353 ctx->errmsg.len =
354 sizeof("[an error occurred while processing the directive]") - 1;
355 ctx->errmsg.data = (u_char *)
356 "[an error occurred while processing the directive]";
357 354
358 r->filter_need_in_memory = 1; 355 r->filter_need_in_memory = 1;
359 356
360 if (r == r->main) { 357 if (r == r->main) {
361 ngx_http_clear_content_length(r); 358 ngx_http_clear_content_length(r);
434 431
435 slcf = ngx_http_get_module_loc_conf(r, ngx_http_ssi_filter_module); 432 slcf = ngx_http_get_module_loc_conf(r, ngx_http_ssi_filter_module);
436 433
437 while (ctx->in || ctx->buf) { 434 while (ctx->in || ctx->buf) {
438 435
439 if (ctx->buf == NULL ){ 436 if (ctx->buf == NULL) {
440 ctx->buf = ctx->in->buf; 437 ctx->buf = ctx->in->buf;
441 ctx->in = ctx->in->next; 438 ctx->in = ctx->in->next;
442 ctx->pos = ctx->buf->pos; 439 ctx->pos = ctx->buf->pos;
443 } 440 }
444 441
796 if (rc == NGX_OK) { 793 if (rc == NGX_OK) {
797 continue; 794 continue;
798 } 795 }
799 796
800 if (rc == NGX_DONE || rc == NGX_AGAIN || rc == NGX_ERROR) { 797 if (rc == NGX_DONE || rc == NGX_AGAIN || rc == NGX_ERROR) {
798 ngx_http_ssi_buffered(r, ctx);
801 return rc; 799 return rc;
802 } 800 }
803 } 801 }
804 802
805 803
948 cl->next = ctx->free; 946 cl->next = ctx->free;
949 ctx->free = cl; 947 ctx->free = cl;
950 } 948 }
951 } 949 }
952 950
951 ngx_http_ssi_buffered(r, ctx);
952
953 return rc;
954 }
955
956
957 static void
958 ngx_http_ssi_buffered(ngx_http_request_t *r, ngx_http_ssi_ctx_t *ctx)
959 {
953 if (ctx->in || ctx->buf) { 960 if (ctx->in || ctx->buf) {
954 r->buffered |= NGX_HTTP_SSI_BUFFERED; 961 r->buffered |= NGX_HTTP_SSI_BUFFERED;
955 962
956 } else { 963 } else {
957 r->buffered &= ~NGX_HTTP_SSI_BUFFERED; 964 r->buffered &= ~NGX_HTTP_SSI_BUFFERED;
958 } 965 }
959
960 return rc;
961 } 966 }
962 967
963 968
964 static ngx_int_t 969 static ngx_int_t
965 ngx_http_ssi_parse(ngx_http_request_t *r, ngx_http_ssi_ctx_t *ctx) 970 ngx_http_ssi_parse(ngx_http_request_t *r, ngx_http_ssi_ctx_t *ctx)
1699 key = ngx_hash_strlow(var.data, var.data, var.len); 1704 key = ngx_hash_strlow(var.data, var.data, var.len);
1700 1705
1701 val = ngx_http_ssi_get_variable(r, &var, key); 1706 val = ngx_http_ssi_get_variable(r, &var, key);
1702 1707
1703 if (val == NULL) { 1708 if (val == NULL) {
1704 vv = ngx_http_get_variable(r, &var, key, 1709 vv = ngx_http_get_variable(r, &var, key);
1705 flags & NGX_HTTP_SSI_EXPR_TEST);
1706 if (vv == NULL) { 1710 if (vv == NULL) {
1707 return NGX_ERROR; 1711 return NGX_ERROR;
1708 } 1712 }
1709 1713
1710 if (vv->not_found) { 1714 if (vv->not_found) {
1896 1900
1897 ngx_unescape_uri(&dst, &src, uri->len, NGX_UNESCAPE_URI); 1901 ngx_unescape_uri(&dst, &src, uri->len, NGX_UNESCAPE_URI);
1898 1902
1899 len = (uri->data + uri->len) - src; 1903 len = (uri->data + uri->len) - src;
1900 if (len) { 1904 if (len) {
1901 dst = ngx_copy(dst, src, len); 1905 dst = ngx_movemem(dst, src, len);
1902 } 1906 }
1903 1907
1904 uri->len = dst - uri->data; 1908 uri->len = dst - uri->data;
1905 1909
1906 ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0, 1910 ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
1907 "ssi include: \"%V\"", uri); 1911 "ssi include: \"%V\"", uri);
1908 1912
1909 args.len = 0; 1913 ngx_str_null(&args);
1910 args.data = NULL; 1914 flags = NGX_HTTP_LOG_UNSAFE;
1911 flags = 0;
1912 1915
1913 if (ngx_http_parse_unsafe_uri(r, uri, &args, &flags) != NGX_OK) { 1916 if (ngx_http_parse_unsafe_uri(r, uri, &args, &flags) != NGX_OK) {
1914 return NGX_HTTP_SSI_ERROR; 1917 return NGX_HTTP_SSI_ERROR;
1915 } 1918 }
1916 1919
2059 "ssi stub output: \"%V?%V\"", &r->uri, &r->args); 2062 "ssi stub output: \"%V?%V\"", &r->uri, &r->args);
2060 2063
2061 out = data; 2064 out = data;
2062 2065
2063 if (!r->header_sent) { 2066 if (!r->header_sent) {
2064 if (ngx_http_set_content_type(r) != NGX_OK) { 2067 r->headers_out.content_type_len =
2065 return NGX_ERROR; 2068 r->parent->headers_out.content_type_len;
2066 } 2069 r->headers_out.content_type = r->parent->headers_out.content_type;
2067 2070
2068 if (ngx_http_send_header(r) == NGX_ERROR) { 2071 if (ngx_http_send_header(r) == NGX_ERROR) {
2069 return NGX_ERROR; 2072 return NGX_ERROR;
2070 } 2073 }
2071 } 2074 }
2108 key = ngx_hash_strlow(var->data, var->data, var->len); 2111 key = ngx_hash_strlow(var->data, var->data, var->len);
2109 2112
2110 value = ngx_http_ssi_get_variable(r, var, key); 2113 value = ngx_http_ssi_get_variable(r, var, key);
2111 2114
2112 if (value == NULL) { 2115 if (value == NULL) {
2113 vv = ngx_http_get_variable(r, var, key, 1); 2116 vv = ngx_http_get_variable(r, var, key);
2114 2117
2115 if (vv == NULL) { 2118 if (vv == NULL) {
2116 return NGX_HTTP_SSI_ERROR; 2119 return NGX_HTTP_SSI_ERROR;
2117 } 2120 }
2118 2121
2159 "unknown encoding \"%V\" in the \"echo\" command", 2162 "unknown encoding \"%V\" in the \"echo\" command",
2160 enc); 2163 enc);
2161 } 2164 }
2162 } 2165 }
2163 2166
2167 p = value->data;
2168
2164 switch (ctx->encoding) { 2169 switch (ctx->encoding) {
2165
2166 case NGX_HTTP_SSI_NO_ENCODING:
2167 break;
2168 2170
2169 case NGX_HTTP_SSI_URL_ENCODING: 2171 case NGX_HTTP_SSI_URL_ENCODING:
2170 len = 2 * ngx_escape_uri(NULL, value->data, value->len, 2172 len = 2 * ngx_escape_uri(NULL, value->data, value->len,
2171 NGX_ESCAPE_HTML); 2173 NGX_ESCAPE_HTML);
2172 2174
2175 if (p == NULL) { 2177 if (p == NULL) {
2176 return NGX_HTTP_SSI_ERROR; 2178 return NGX_HTTP_SSI_ERROR;
2177 } 2179 }
2178 2180
2179 (void) ngx_escape_uri(p, value->data, value->len, NGX_ESCAPE_HTML); 2181 (void) ngx_escape_uri(p, value->data, value->len, NGX_ESCAPE_HTML);
2180 2182 }
2181 value->len += len; 2183
2182 value->data = p; 2184 len += value->len;
2183 }
2184
2185 break; 2185 break;
2186 2186
2187 case NGX_HTTP_SSI_ENTITY_ENCODING: 2187 case NGX_HTTP_SSI_ENTITY_ENCODING:
2188 len = ngx_escape_html(NULL, value->data, value->len); 2188 len = ngx_escape_html(NULL, value->data, value->len);
2189 2189
2192 if (p == NULL) { 2192 if (p == NULL) {
2193 return NGX_HTTP_SSI_ERROR; 2193 return NGX_HTTP_SSI_ERROR;
2194 } 2194 }
2195 2195
2196 (void) ngx_escape_html(p, value->data, value->len); 2196 (void) ngx_escape_html(p, value->data, value->len);
2197 2197 }
2198 value->len += len; 2198
2199 value->data = p; 2199 len += value->len;
2200 } 2200 break;
2201 2201
2202 default: /* NGX_HTTP_SSI_NO_ENCODING */
2203 len = value->len;
2202 break; 2204 break;
2203 } 2205 }
2204 2206
2205 b = ngx_calloc_buf(r->pool); 2207 b = ngx_calloc_buf(r->pool);
2206 if (b == NULL) { 2208 if (b == NULL) {
2211 if (cl == NULL) { 2213 if (cl == NULL) {
2212 return NGX_HTTP_SSI_ERROR; 2214 return NGX_HTTP_SSI_ERROR;
2213 } 2215 }
2214 2216
2215 b->memory = 1; 2217 b->memory = 1;
2216 b->pos = value->data; 2218 b->pos = p;
2217 b->last = value->data + value->len; 2219 b->last = p + len;
2218 2220
2219 cl->buf = b; 2221 cl->buf = b;
2220 cl->next = NULL; 2222 cl->next = NULL;
2221 *ctx->last_out = cl; 2223 *ctx->last_out = cl;
2222 ctx->last_out = &cl->next; 2224 ctx->last_out = &cl->next;
2360 2362
2361 while (p < last && *p == ' ') { 2363 while (p < last && *p == ' ') {
2362 p++; 2364 p++;
2363 } 2365 }
2364 2366
2365 flags = (p == last) ? NGX_HTTP_SSI_EXPR_TEST : 0; 2367 flags = 0;
2366 2368
2367 ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0, 2369 ngx_log_debug1(NGX_LOG_DEBUG_HTTP, r->connection->log, 0,
2368 "left: \"%V\"", &left); 2370 "left: \"%V\"", &left);
2369 2371
2370 rc = ngx_http_ssi_evaluate_string(r, ctx, &left, flags); 2372 rc = ngx_http_ssi_evaluate_string(r, ctx, &left, flags);
2448 rc = ngx_strncmp(left.data, right.data, right.len); 2450 rc = ngx_strncmp(left.data, right.data, right.len);
2449 } 2451 }
2450 2452
2451 } else { 2453 } else {
2452 #if (NGX_PCRE) 2454 #if (NGX_PCRE)
2453 ngx_str_t err; 2455 ngx_regex_compile_t rgc;
2454 ngx_regex_t *regex; 2456 u_char errstr[NGX_MAX_CONF_ERRSTR];
2455 u_char errstr[NGX_MAX_CONF_ERRSTR];
2456
2457 err.len = NGX_MAX_CONF_ERRSTR;
2458 err.data = errstr;
2459 2457
2460 right.data[right.len] = '\0'; 2458 right.data[right.len] = '\0';
2461 2459
2462 regex = ngx_regex_compile(&right, 0, r->pool, &err); 2460 ngx_memzero(&rgc, sizeof(ngx_regex_compile_t));
2463 2461
2464 if (regex == NULL) { 2462 rgc.pattern = right;
2465 ngx_log_error(NGX_LOG_ERR, r->connection->log, 0, "%s", err.data); 2463 rgc.pool = r->pool;
2464 rgc.err.len = NGX_MAX_CONF_ERRSTR;
2465 rgc.err.data = errstr;
2466
2467 if (ngx_regex_compile(&rgc) != NGX_OK) {
2468 ngx_log_error(NGX_LOG_ERR, r->connection->log, 0, "%V", &rgc.err);
2466 return NGX_HTTP_SSI_ERROR; 2469 return NGX_HTTP_SSI_ERROR;
2467 } 2470 }
2468 2471
2469 rc = ngx_regex_exec(regex, &left, NULL, 0); 2472 rc = ngx_regex_exec(rgc.regex, &left, NULL, 0);
2470 2473
2471 if (rc != NGX_REGEX_NO_MATCHED && rc < 0) { 2474 if (rc < NGX_REGEX_NO_MATCHED) {
2472 ngx_log_error(NGX_LOG_ALERT, r->connection->log, 0, 2475 ngx_log_error(NGX_LOG_ALERT, r->connection->log, 0,
2473 ngx_regex_exec_n " failed: %d on \"%V\" using \"%V\"", 2476 ngx_regex_exec_n " failed: %i on \"%V\" using \"%V\"",
2474 rc, &left, &right); 2477 rc, &left, &right);
2475 return NGX_HTTP_SSI_ERROR; 2478 return NGX_HTTP_SSI_ERROR;
2476 } 2479 }
2477 #else 2480 #else
2478 ngx_log_error(NGX_LOG_ALERT, r->connection->log, 0, 2481 ngx_log_error(NGX_LOG_ALERT, r->connection->log, 0,
2612 v->data = ngx_pnalloc(r->pool, NGX_TIME_T_LEN); 2615 v->data = ngx_pnalloc(r->pool, NGX_TIME_T_LEN);
2613 if (v->data == NULL) { 2616 if (v->data == NULL) {
2614 return NGX_ERROR; 2617 return NGX_ERROR;
2615 } 2618 }
2616 2619
2617 v->len = ngx_sprintf(v->data, "%T", tp->sec + (gmt ? 0 : tp->gmtoff)) 2620 v->len = ngx_sprintf(v->data, "%T", tp->sec) - v->data;
2618 - v->data;
2619 2621
2620 return NGX_OK; 2622 return NGX_OK;
2621 } 2623 }
2622 2624
2623 if (gmt) { 2625 if (gmt) {
2770 prev->ignore_recycled_buffers, 0); 2772 prev->ignore_recycled_buffers, 0);
2771 2773
2772 ngx_conf_merge_size_value(conf->min_file_chunk, prev->min_file_chunk, 1024); 2774 ngx_conf_merge_size_value(conf->min_file_chunk, prev->min_file_chunk, 1024);
2773 ngx_conf_merge_size_value(conf->value_len, prev->value_len, 256); 2775 ngx_conf_merge_size_value(conf->value_len, prev->value_len, 256);
2774 2776
2775 if (ngx_http_merge_types(cf, conf->types_keys, &conf->types, 2777 if (ngx_http_merge_types(cf, &conf->types_keys, &conf->types,
2776 prev->types_keys, &prev->types, 2778 &prev->types_keys, &prev->types,
2777 ngx_http_html_default_types) 2779 ngx_http_html_default_types)
2778 != NGX_OK) 2780 != NGX_OK)
2779 { 2781 {
2780 return NGX_CONF_ERROR; 2782 return NGX_CONF_ERROR;
2781 } 2783 }