Mercurial > hg > nginx-vendor-current
comparison src/core/ngx_open_file_cache.c @ 662:e5fa0a4a7d27 NGINX_1_1_15
nginx 1.1.15
*) Feature: the "disable_symlinks" directive.
*) Feature: the "proxy_cookie_domain" and "proxy_cookie_path"
directives.
*) Bugfix: nginx might log incorrect error "upstream prematurely closed
connection" instead of correct "upstream sent too big header" one.
Thanks to Feibo Li.
*) Bugfix: nginx could not be built with the ngx_http_perl_module if the
--with-openssl option was used.
*) Bugfix: internal redirects to named locations were not limited.
*) Bugfix: calling $r->flush() multiple times might cause errors in the
ngx_http_gzip_filter_module.
*) Bugfix: temporary files might be not removed if the "proxy_store"
directive were used with SSI includes.
*) Bugfix: in some cases non-cacheable variables (such as the $args
variable) returned old empty cached value.
*) Bugfix: a segmentation fault might occur in a worker process if too
many SSI subrequests were issued simultaneously; the bug had appeared
in 0.7.25.
author | Igor Sysoev <http://sysoev.ru> |
---|---|
date | Wed, 15 Feb 2012 00:00:00 +0400 |
parents | d0f7a625f27c |
children | f5b859b2f097 |
comparison
equal
deleted
inserted
replaced
661:b49c1751031c | 662:e5fa0a4a7d27 |
---|---|
20 | 20 |
21 #define NGX_MIN_READ_AHEAD (128 * 1024) | 21 #define NGX_MIN_READ_AHEAD (128 * 1024) |
22 | 22 |
23 | 23 |
24 static void ngx_open_file_cache_cleanup(void *data); | 24 static void ngx_open_file_cache_cleanup(void *data); |
25 static ngx_int_t ngx_open_and_stat_file(u_char *name, ngx_open_file_info_t *of, | 25 #if (NGX_HAVE_OPENAT) |
26 ngx_log_t *log); | 26 static ngx_fd_t ngx_openat_file_owner(ngx_fd_t at_fd, const u_char *name, |
27 ngx_int_t mode, ngx_int_t create, ngx_int_t access, ngx_log_t *log); | |
28 #endif | |
29 static ngx_fd_t ngx_open_file_wrapper(ngx_str_t *name, | |
30 ngx_open_file_info_t *of, ngx_int_t mode, ngx_int_t create, | |
31 ngx_int_t access, ngx_log_t *log); | |
32 static ngx_int_t ngx_file_info_wrapper(ngx_str_t *name, | |
33 ngx_open_file_info_t *of, ngx_file_info_t *fi, ngx_log_t *log); | |
34 static ngx_int_t ngx_open_and_stat_file(ngx_str_t *name, | |
35 ngx_open_file_info_t *of, ngx_log_t *log); | |
27 static void ngx_open_file_add_event(ngx_open_file_cache_t *cache, | 36 static void ngx_open_file_add_event(ngx_open_file_cache_t *cache, |
28 ngx_cached_open_file_t *file, ngx_open_file_info_t *of, ngx_log_t *log); | 37 ngx_cached_open_file_t *file, ngx_open_file_info_t *of, ngx_log_t *log); |
29 static void ngx_open_file_cleanup(void *data); | 38 static void ngx_open_file_cleanup(void *data); |
30 static void ngx_close_cached_file(ngx_open_file_cache_t *cache, | 39 static void ngx_close_cached_file(ngx_open_file_cache_t *cache, |
31 ngx_cached_open_file_t *file, ngx_uint_t min_uses, ngx_log_t *log); | 40 ngx_cached_open_file_t *file, ngx_uint_t min_uses, ngx_log_t *log); |
145 | 154 |
146 if (cache == NULL) { | 155 if (cache == NULL) { |
147 | 156 |
148 if (of->test_only) { | 157 if (of->test_only) { |
149 | 158 |
150 if (ngx_file_info(name->data, &fi) == NGX_FILE_ERROR) { | 159 if (ngx_file_info_wrapper(name, of, &fi, pool->log) |
151 of->err = ngx_errno; | 160 == NGX_FILE_ERROR) |
152 of->failed = ngx_file_info_n; | 161 { |
153 return NGX_ERROR; | 162 return NGX_ERROR; |
154 } | 163 } |
155 | 164 |
156 of->uniq = ngx_file_uniq(&fi); | 165 of->uniq = ngx_file_uniq(&fi); |
157 of->mtime = ngx_file_mtime(&fi); | 166 of->mtime = ngx_file_mtime(&fi); |
168 cln = ngx_pool_cleanup_add(pool, sizeof(ngx_pool_cleanup_file_t)); | 177 cln = ngx_pool_cleanup_add(pool, sizeof(ngx_pool_cleanup_file_t)); |
169 if (cln == NULL) { | 178 if (cln == NULL) { |
170 return NGX_ERROR; | 179 return NGX_ERROR; |
171 } | 180 } |
172 | 181 |
173 rc = ngx_open_and_stat_file(name->data, of, pool->log); | 182 rc = ngx_open_and_stat_file(name, of, pool->log); |
174 | 183 |
175 if (rc == NGX_OK && !of->is_dir) { | 184 if (rc == NGX_OK && !of->is_dir) { |
176 cln->handler = ngx_pool_cleanup_file; | 185 cln->handler = ngx_pool_cleanup_file; |
177 clnf = cln->data; | 186 clnf = cln->data; |
178 | 187 |
203 | 212 |
204 if (file->fd == NGX_INVALID_FILE && file->err == 0 && !file->is_dir) { | 213 if (file->fd == NGX_INVALID_FILE && file->err == 0 && !file->is_dir) { |
205 | 214 |
206 /* file was not used often enough to keep open */ | 215 /* file was not used often enough to keep open */ |
207 | 216 |
208 rc = ngx_open_and_stat_file(name->data, of, pool->log); | 217 rc = ngx_open_and_stat_file(name, of, pool->log); |
209 | 218 |
210 if (rc != NGX_OK && (of->err == 0 || !of->errors)) { | 219 if (rc != NGX_OK && (of->err == 0 || !of->errors)) { |
211 goto failed; | 220 goto failed; |
212 } | 221 } |
213 | 222 |
215 } | 224 } |
216 | 225 |
217 if (file->use_event | 226 if (file->use_event |
218 || (file->event == NULL | 227 || (file->event == NULL |
219 && (of->uniq == 0 || of->uniq == file->uniq) | 228 && (of->uniq == 0 || of->uniq == file->uniq) |
220 && now - file->created < of->valid)) | 229 && now - file->created < of->valid |
230 #if (NGX_HAVE_OPENAT) | |
231 && of->disable_symlinks == file->disable_symlinks | |
232 #endif | |
233 )) | |
221 { | 234 { |
222 if (file->err == 0) { | 235 if (file->err == 0) { |
223 | 236 |
224 of->fd = file->fd; | 237 of->fd = file->fd; |
225 of->uniq = file->uniq; | 238 of->uniq = file->uniq; |
237 ngx_open_file_add_event(cache, file, of, pool->log); | 250 ngx_open_file_add_event(cache, file, of, pool->log); |
238 } | 251 } |
239 | 252 |
240 } else { | 253 } else { |
241 of->err = file->err; | 254 of->err = file->err; |
255 #if (NGX_HAVE_OPENAT) | |
256 of->failed = file->disable_symlinks ? ngx_openat_file_n | |
257 : ngx_open_file_n; | |
258 #else | |
242 of->failed = ngx_open_file_n; | 259 of->failed = ngx_open_file_n; |
260 #endif | |
243 } | 261 } |
244 | 262 |
245 goto found; | 263 goto found; |
246 } | 264 } |
247 | 265 |
261 } | 279 } |
262 | 280 |
263 of->fd = file->fd; | 281 of->fd = file->fd; |
264 of->uniq = file->uniq; | 282 of->uniq = file->uniq; |
265 | 283 |
266 rc = ngx_open_and_stat_file(name->data, of, pool->log); | 284 rc = ngx_open_and_stat_file(name, of, pool->log); |
267 | 285 |
268 if (rc != NGX_OK && (of->err == 0 || !of->errors)) { | 286 if (rc != NGX_OK && (of->err == 0 || !of->errors)) { |
269 goto failed; | 287 goto failed; |
270 } | 288 } |
271 | 289 |
309 | 327 |
310 ngx_open_file_del_event(file); | 328 ngx_open_file_del_event(file); |
311 | 329 |
312 if (ngx_close_file(file->fd) == NGX_FILE_ERROR) { | 330 if (ngx_close_file(file->fd) == NGX_FILE_ERROR) { |
313 ngx_log_error(NGX_LOG_ALERT, pool->log, ngx_errno, | 331 ngx_log_error(NGX_LOG_ALERT, pool->log, ngx_errno, |
314 ngx_close_file_n " \"%s\" failed", | 332 ngx_close_file_n " \"%V\" failed", name); |
315 name->data); | |
316 } | 333 } |
317 | 334 |
318 goto add_event; | 335 goto add_event; |
319 } | 336 } |
320 | 337 |
327 goto create; | 344 goto create; |
328 } | 345 } |
329 | 346 |
330 /* not found */ | 347 /* not found */ |
331 | 348 |
332 rc = ngx_open_and_stat_file(name->data, of, pool->log); | 349 rc = ngx_open_and_stat_file(name, of, pool->log); |
333 | 350 |
334 if (rc != NGX_OK && (of->err == 0 || !of->errors)) { | 351 if (rc != NGX_OK && (of->err == 0 || !of->errors)) { |
335 goto failed; | 352 goto failed; |
336 } | 353 } |
337 | 354 |
374 | 391 |
375 update: | 392 update: |
376 | 393 |
377 file->fd = of->fd; | 394 file->fd = of->fd; |
378 file->err = of->err; | 395 file->err = of->err; |
396 #if (NGX_HAVE_OPENAT) | |
397 file->disable_symlinks = of->disable_symlinks; | |
398 #endif | |
379 | 399 |
380 if (of->err == 0) { | 400 if (of->err == 0) { |
381 file->uniq = of->uniq; | 401 file->uniq = of->uniq; |
382 file->mtime = of->mtime; | 402 file->mtime = of->mtime; |
383 file->size = of->size; | 403 file->size = of->size; |
450 } | 470 } |
451 | 471 |
452 if (of->fd != NGX_INVALID_FILE) { | 472 if (of->fd != NGX_INVALID_FILE) { |
453 if (ngx_close_file(of->fd) == NGX_FILE_ERROR) { | 473 if (ngx_close_file(of->fd) == NGX_FILE_ERROR) { |
454 ngx_log_error(NGX_LOG_ALERT, pool->log, ngx_errno, | 474 ngx_log_error(NGX_LOG_ALERT, pool->log, ngx_errno, |
455 ngx_close_file_n " \"%s\" failed", name->data); | 475 ngx_close_file_n " \"%V\" failed", name); |
456 } | 476 } |
457 } | 477 } |
458 | 478 |
459 return NGX_ERROR; | 479 return NGX_ERROR; |
460 } | 480 } |
461 | 481 |
462 | 482 |
483 #if (NGX_HAVE_OPENAT) | |
484 | |
485 static ngx_fd_t | |
486 ngx_openat_file_owner(ngx_fd_t at_fd, const u_char *name, | |
487 ngx_int_t mode, ngx_int_t create, ngx_int_t access, ngx_log_t *log) | |
488 { | |
489 ngx_fd_t fd; | |
490 ngx_err_t err; | |
491 ngx_file_info_t fi, atfi; | |
492 | |
493 /* | |
494 * To allow symlinks with the same owner, use openat() (followed | |
495 * by fstat()) and fstatat(AT_SYMLINK_NOFOLLOW), and then compare | |
496 * uids between fstat() and fstatat(). | |
497 * | |
498 * As there is a race between openat() and fstatat() we don't | |
499 * know if openat() in fact opened symlink or not. Therefore, | |
500 * we have to compare uids even if fstatat() reports the opened | |
501 * component isn't a symlink (as we don't know whether it was | |
502 * symlink during openat() or not). | |
503 */ | |
504 | |
505 fd = ngx_openat_file(at_fd, name, mode, create, access); | |
506 | |
507 if (fd == NGX_FILE_ERROR) { | |
508 return NGX_FILE_ERROR; | |
509 } | |
510 | |
511 if (ngx_file_at_info(at_fd, name, &atfi, AT_SYMLINK_NOFOLLOW) | |
512 == NGX_FILE_ERROR) | |
513 { | |
514 err = ngx_errno; | |
515 goto failed; | |
516 } | |
517 | |
518 if (ngx_fd_info(fd, &fi) == NGX_FILE_ERROR) { | |
519 err = ngx_errno; | |
520 goto failed; | |
521 } | |
522 | |
523 if (fi.st_uid != atfi.st_uid) { | |
524 err = NGX_ELOOP; | |
525 goto failed; | |
526 } | |
527 | |
528 return fd; | |
529 | |
530 failed: | |
531 | |
532 if (ngx_close_file(fd) == NGX_FILE_ERROR) { | |
533 ngx_log_error(NGX_LOG_ALERT, log, ngx_errno, | |
534 ngx_close_file_n " \"%V\" failed", name); | |
535 } | |
536 | |
537 ngx_set_errno(err); | |
538 | |
539 return NGX_INVALID_FILE; | |
540 } | |
541 | |
542 #endif | |
543 | |
544 | |
545 static ngx_fd_t | |
546 ngx_open_file_wrapper(ngx_str_t *name, ngx_open_file_info_t *of, | |
547 ngx_int_t mode, ngx_int_t create, ngx_int_t access, ngx_log_t *log) | |
548 { | |
549 ngx_fd_t fd; | |
550 | |
551 #if !(NGX_HAVE_OPENAT) | |
552 | |
553 fd = ngx_open_file(name->data, mode, create, access); | |
554 | |
555 if (fd == NGX_INVALID_FILE) { | |
556 of->err = ngx_errno; | |
557 of->failed = ngx_open_file_n; | |
558 return NGX_INVALID_FILE; | |
559 } | |
560 | |
561 return fd; | |
562 | |
563 #else | |
564 | |
565 u_char *p, *cp, *end; | |
566 ngx_fd_t at_fd; | |
567 ngx_str_t at_name; | |
568 ngx_file_info_t fi; | |
569 | |
570 if (of->disable_symlinks == NGX_DISABLE_SYMLINKS_OFF) { | |
571 fd = ngx_open_file(name->data, mode, create, access); | |
572 | |
573 if (fd == NGX_INVALID_FILE) { | |
574 of->err = ngx_errno; | |
575 of->failed = ngx_open_file_n; | |
576 return NGX_INVALID_FILE; | |
577 } | |
578 | |
579 return fd; | |
580 } | |
581 | |
582 p = name->data; | |
583 end = p + name->len; | |
584 | |
585 at_fd = AT_FDCWD; | |
586 at_name = *name; | |
587 | |
588 if (p[0] == '/') { | |
589 at_fd = ngx_openat_file(at_fd, "/", | |
590 NGX_FILE_RDONLY|NGX_FILE_NONBLOCK, | |
591 NGX_FILE_OPEN, 0); | |
592 | |
593 if (at_fd == NGX_FILE_ERROR) { | |
594 of->err = ngx_errno; | |
595 of->failed = ngx_openat_file_n; | |
596 return NGX_FILE_ERROR; | |
597 } | |
598 | |
599 at_name.len = 1; | |
600 p++; | |
601 } | |
602 | |
603 for ( ;; ) { | |
604 cp = ngx_strlchr(p, end, '/'); | |
605 if (cp == NULL) { | |
606 break; | |
607 } | |
608 | |
609 if (cp == p) { | |
610 p++; | |
611 continue; | |
612 } | |
613 | |
614 *cp = '\0'; | |
615 | |
616 if (of->disable_symlinks == NGX_DISABLE_SYMLINKS_NOTOWNER) { | |
617 fd = ngx_openat_file_owner(at_fd, p, | |
618 NGX_FILE_RDONLY|NGX_FILE_NONBLOCK, | |
619 NGX_FILE_OPEN, 0, log); | |
620 | |
621 } else { | |
622 fd = ngx_openat_file(at_fd, p, | |
623 NGX_FILE_RDONLY|NGX_FILE_NONBLOCK|NGX_FILE_NOFOLLOW, | |
624 NGX_FILE_OPEN, 0); | |
625 } | |
626 | |
627 *cp = '/'; | |
628 | |
629 if (fd == NGX_INVALID_FILE) { | |
630 of->err = ngx_errno; | |
631 of->failed = ngx_openat_file_n; | |
632 goto failed; | |
633 } | |
634 | |
635 if (at_fd != AT_FDCWD && ngx_close_file(at_fd) == NGX_FILE_ERROR) { | |
636 ngx_log_error(NGX_LOG_ALERT, log, ngx_errno, | |
637 ngx_close_file_n " \"%V\" failed", at_name); | |
638 } | |
639 | |
640 p = cp + 1; | |
641 at_fd = fd; | |
642 at_name.len = cp - at_name.data; | |
643 } | |
644 | |
645 if (p == end && at_fd != AT_FDCWD) { | |
646 | |
647 /* | |
648 * If pathname ends with a trailing slash, check if last path | |
649 * component is a directory; if not, fail with ENOTDIR as per | |
650 * POSIX. | |
651 * | |
652 * We use separate check instead of O_DIRECTORY in the loop above, | |
653 * as O_DIRECTORY doesn't work on FreeBSD 8. | |
654 * | |
655 * Note this returns already opened file descriptor, with different | |
656 * mode/create/access. This is believed to be safe as we don't | |
657 * use this codepath to create directories. | |
658 */ | |
659 | |
660 if (ngx_fd_info(at_fd, &fi) == NGX_FILE_ERROR) { | |
661 of->err = ngx_errno; | |
662 of->failed = ngx_fd_info_n; | |
663 fd = NGX_INVALID_FILE; | |
664 | |
665 goto failed; | |
666 } | |
667 | |
668 if (ngx_is_dir(&fi)) { | |
669 return at_fd; | |
670 } | |
671 | |
672 of->err = ENOTDIR; | |
673 of->failed = ngx_openat_file_n; | |
674 fd = NGX_INVALID_FILE; | |
675 | |
676 goto failed; | |
677 } | |
678 | |
679 if (of->disable_symlinks == NGX_DISABLE_SYMLINKS_NOTOWNER) { | |
680 fd = ngx_openat_file_owner(at_fd, p, mode, create, access, log); | |
681 | |
682 } else { | |
683 fd = ngx_openat_file(at_fd, p, mode|NGX_FILE_NOFOLLOW, create, access); | |
684 } | |
685 | |
686 if (fd == NGX_INVALID_FILE) { | |
687 of->err = ngx_errno; | |
688 of->failed = ngx_openat_file_n; | |
689 } | |
690 | |
691 failed: | |
692 | |
693 if (at_fd != AT_FDCWD && ngx_close_file(at_fd) == NGX_FILE_ERROR) { | |
694 ngx_log_error(NGX_LOG_ALERT, log, ngx_errno, | |
695 ngx_close_file_n " \"%V\" failed", at_name); | |
696 } | |
697 | |
698 return fd; | |
699 #endif | |
700 } | |
701 | |
702 | |
463 static ngx_int_t | 703 static ngx_int_t |
464 ngx_open_and_stat_file(u_char *name, ngx_open_file_info_t *of, ngx_log_t *log) | 704 ngx_file_info_wrapper(ngx_str_t *name, ngx_open_file_info_t *of, |
705 ngx_file_info_t *fi, ngx_log_t *log) | |
706 { | |
707 ngx_int_t rc; | |
708 | |
709 #if !(NGX_HAVE_OPENAT) | |
710 | |
711 rc = ngx_file_info(name->data, fi); | |
712 | |
713 if (rc == NGX_FILE_ERROR) { | |
714 of->err = ngx_errno; | |
715 of->failed = ngx_file_info_n; | |
716 return NGX_FILE_ERROR; | |
717 } | |
718 | |
719 return rc; | |
720 | |
721 #else | |
722 | |
723 ngx_fd_t fd; | |
724 | |
725 if (of->disable_symlinks == NGX_DISABLE_SYMLINKS_OFF) { | |
726 | |
727 rc = ngx_file_info(name->data, fi); | |
728 | |
729 if (rc == NGX_FILE_ERROR) { | |
730 of->err = ngx_errno; | |
731 of->failed = ngx_file_info_n; | |
732 return NGX_FILE_ERROR; | |
733 } | |
734 | |
735 return rc; | |
736 } | |
737 | |
738 fd = ngx_open_file_wrapper(name, of, NGX_FILE_RDONLY|NGX_FILE_NONBLOCK, | |
739 NGX_FILE_OPEN, 0, log); | |
740 | |
741 if (fd == NGX_INVALID_FILE) { | |
742 return NGX_FILE_ERROR; | |
743 } | |
744 | |
745 rc = ngx_fd_info(fd, fi); | |
746 | |
747 if (rc == NGX_FILE_ERROR) { | |
748 of->err = ngx_errno; | |
749 of->failed = ngx_fd_info_n; | |
750 } | |
751 | |
752 if (ngx_close_file(fd) == NGX_FILE_ERROR) { | |
753 ngx_log_error(NGX_LOG_ALERT, log, ngx_errno, | |
754 ngx_close_file_n " \"%V\" failed", name); | |
755 } | |
756 | |
757 return rc; | |
758 #endif | |
759 } | |
760 | |
761 | |
762 static ngx_int_t | |
763 ngx_open_and_stat_file(ngx_str_t *name, ngx_open_file_info_t *of, | |
764 ngx_log_t *log) | |
465 { | 765 { |
466 ngx_fd_t fd; | 766 ngx_fd_t fd; |
467 ngx_file_info_t fi; | 767 ngx_file_info_t fi; |
468 | 768 |
469 if (of->fd != NGX_INVALID_FILE) { | 769 if (of->fd != NGX_INVALID_FILE) { |
470 | 770 |
471 if (ngx_file_info(name, &fi) == NGX_FILE_ERROR) { | 771 if (ngx_file_info_wrapper(name, of, &fi, log) == NGX_FILE_ERROR) { |
472 of->failed = ngx_file_info_n; | 772 of->fd = NGX_INVALID_FILE; |
473 goto failed; | 773 return NGX_ERROR; |
474 } | 774 } |
475 | 775 |
476 if (of->uniq == ngx_file_uniq(&fi)) { | 776 if (of->uniq == ngx_file_uniq(&fi)) { |
477 goto done; | 777 goto done; |
478 } | 778 } |
479 | 779 |
480 } else if (of->test_dir) { | 780 } else if (of->test_dir) { |
481 | 781 |
482 if (ngx_file_info(name, &fi) == NGX_FILE_ERROR) { | 782 if (ngx_file_info_wrapper(name, of, &fi, log) == NGX_FILE_ERROR) { |
483 of->failed = ngx_file_info_n; | 783 of->fd = NGX_INVALID_FILE; |
484 goto failed; | 784 return NGX_ERROR; |
485 } | 785 } |
486 | 786 |
487 if (ngx_is_dir(&fi)) { | 787 if (ngx_is_dir(&fi)) { |
488 goto done; | 788 goto done; |
489 } | 789 } |
494 /* | 794 /* |
495 * Use non-blocking open() not to hang on FIFO files, etc. | 795 * Use non-blocking open() not to hang on FIFO files, etc. |
496 * This flag has no effect on a regular files. | 796 * This flag has no effect on a regular files. |
497 */ | 797 */ |
498 | 798 |
499 fd = ngx_open_file(name, NGX_FILE_RDONLY|NGX_FILE_NONBLOCK, | 799 fd = ngx_open_file_wrapper(name, of, NGX_FILE_RDONLY|NGX_FILE_NONBLOCK, |
500 NGX_FILE_OPEN, 0); | 800 NGX_FILE_OPEN, 0, log); |
501 | 801 |
502 } else { | 802 } else { |
503 fd = ngx_open_file(name, NGX_FILE_APPEND, NGX_FILE_CREATE_OR_OPEN, | 803 fd = ngx_open_file_wrapper(name, of, NGX_FILE_APPEND, |
504 NGX_FILE_DEFAULT_ACCESS); | 804 NGX_FILE_CREATE_OR_OPEN, |
805 NGX_FILE_DEFAULT_ACCESS, log); | |
505 } | 806 } |
506 | 807 |
507 if (fd == NGX_INVALID_FILE) { | 808 if (fd == NGX_INVALID_FILE) { |
508 of->failed = ngx_open_file_n; | 809 of->fd = NGX_INVALID_FILE; |
509 goto failed; | 810 return NGX_ERROR; |
510 } | 811 } |
511 | 812 |
512 if (ngx_fd_info(fd, &fi) == NGX_FILE_ERROR) { | 813 if (ngx_fd_info(fd, &fi) == NGX_FILE_ERROR) { |
513 ngx_log_error(NGX_LOG_CRIT, log, ngx_errno, | 814 ngx_log_error(NGX_LOG_CRIT, log, ngx_errno, |
514 ngx_fd_info_n " \"%s\" failed", name); | 815 ngx_fd_info_n " \"%V\" failed", name); |
515 | 816 |
516 if (ngx_close_file(fd) == NGX_FILE_ERROR) { | 817 if (ngx_close_file(fd) == NGX_FILE_ERROR) { |
517 ngx_log_error(NGX_LOG_ALERT, log, ngx_errno, | 818 ngx_log_error(NGX_LOG_ALERT, log, ngx_errno, |
518 ngx_close_file_n " \"%s\" failed", name); | 819 ngx_close_file_n " \"%V\" failed", name); |
519 } | 820 } |
520 | 821 |
521 of->fd = NGX_INVALID_FILE; | 822 of->fd = NGX_INVALID_FILE; |
522 | 823 |
523 return NGX_ERROR; | 824 return NGX_ERROR; |
524 } | 825 } |
525 | 826 |
526 if (ngx_is_dir(&fi)) { | 827 if (ngx_is_dir(&fi)) { |
527 if (ngx_close_file(fd) == NGX_FILE_ERROR) { | 828 if (ngx_close_file(fd) == NGX_FILE_ERROR) { |
528 ngx_log_error(NGX_LOG_ALERT, log, ngx_errno, | 829 ngx_log_error(NGX_LOG_ALERT, log, ngx_errno, |
529 ngx_close_file_n " \"%s\" failed", name); | 830 ngx_close_file_n " \"%V\" failed", name); |
530 } | 831 } |
531 | 832 |
532 of->fd = NGX_INVALID_FILE; | 833 of->fd = NGX_INVALID_FILE; |
533 | 834 |
534 } else { | 835 } else { |
535 of->fd = fd; | 836 of->fd = fd; |
536 | 837 |
537 if (of->read_ahead && ngx_file_size(&fi) > NGX_MIN_READ_AHEAD) { | 838 if (of->read_ahead && ngx_file_size(&fi) > NGX_MIN_READ_AHEAD) { |
538 if (ngx_read_ahead(fd, of->read_ahead) == NGX_ERROR) { | 839 if (ngx_read_ahead(fd, of->read_ahead) == NGX_ERROR) { |
539 ngx_log_error(NGX_LOG_ALERT, log, ngx_errno, | 840 ngx_log_error(NGX_LOG_ALERT, log, ngx_errno, |
540 ngx_read_ahead_n " \"%s\" failed", name); | 841 ngx_read_ahead_n " \"%V\" failed", name); |
541 } | 842 } |
542 } | 843 } |
543 | 844 |
544 if (of->directio <= ngx_file_size(&fi)) { | 845 if (of->directio <= ngx_file_size(&fi)) { |
545 if (ngx_directio_on(fd) == NGX_FILE_ERROR) { | 846 if (ngx_directio_on(fd) == NGX_FILE_ERROR) { |
546 ngx_log_error(NGX_LOG_ALERT, log, ngx_errno, | 847 ngx_log_error(NGX_LOG_ALERT, log, ngx_errno, |
547 ngx_directio_on_n " \"%s\" failed", name); | 848 ngx_directio_on_n " \"%V\" failed", name); |
548 | 849 |
549 } else { | 850 } else { |
550 of->is_directio = 1; | 851 of->is_directio = 1; |
551 } | 852 } |
552 } | 853 } |
562 of->is_file = ngx_is_file(&fi); | 863 of->is_file = ngx_is_file(&fi); |
563 of->is_link = ngx_is_link(&fi); | 864 of->is_link = ngx_is_link(&fi); |
564 of->is_exec = ngx_is_exec(&fi); | 865 of->is_exec = ngx_is_exec(&fi); |
565 | 866 |
566 return NGX_OK; | 867 return NGX_OK; |
567 | |
568 failed: | |
569 | |
570 of->fd = NGX_INVALID_FILE; | |
571 of->err = ngx_errno; | |
572 | |
573 return NGX_ERROR; | |
574 } | 868 } |
575 | 869 |
576 | 870 |
577 /* | 871 /* |
578 * we ignore any possible event setting error and | 872 * we ignore any possible event setting error and |