Date: Fri, 7 May 2010 04:21:46 GMT From: Garrett Cooper <gcooper@FreeBSD.org> To: Perforce Change Reviews <perforce@FreeBSD.org> Subject: PERFORCE change 177875 for review Message-ID: <201005070421.o474LkR4029107@repoman.freebsd.org>
next in thread | raw e-mail | index | archive | help
http://p4web.freebsd.org/@@177875?ac=10 Change 177875 by gcooper@gcooper-bayonetta on 2010/05/07 04:20:47 Add code to avoid race conditions with archive_read_filename by using archive_read_fd as recommended by kientzle@. Affected files ... .. //depot/projects/soc2007/gcooper-pkg_install-enhancements-simplified/usr.sbin/pkg_install/lib/file.c#13 edit Differences ... ==== //depot/projects/soc2007/gcooper-pkg_install-enhancements-simplified/usr.sbin/pkg_install/lib/file.c#13 (text+ko) ==== @@ -26,6 +26,7 @@ #include <archive.h> #include <archive_entry.h> #include <err.h> +#include <errno.h> #include <fnmatch.h> #include <pwd.h> #include <time.h> @@ -375,7 +376,7 @@ FILE *fd = NULL; /* int fd = -1; */ - int r; + int archive_fd = -1, r; if (pkg == NULL || strcmp(pkg, "-") == 0) pkg_name_humanized = "(stdin)"; @@ -390,8 +391,21 @@ archive_read_support_compression_all(archive); archive_read_support_format_tar(archive); + /* + * Avoid potential race conditions with archive_read_open_filename(3), + * by opening the file beforehand. + */ + if (pkg == NULL) + archive_fd = fileno(stdin); + else + archive_fd = open(pkg, O_RDONLY); + /* The initial open failed */ - if (archive_read_open_filename(archive, pkg, + if (archive_fd == -1) + warn("%s: unable to open the package from %s", + __func__, pkg_name_humanized); + /* archive(3) failed to open the file. */ + else if (archive_read_open_fd(archive, archive_fd, ARCHIVE_DEFAULT_BYTES_PER_BLOCK) != ARCHIVE_OK) { error = archive_error_string(archive); @@ -438,6 +452,10 @@ archive_read_finish(archive); + /* Close any open descriptors. */ + if (0 <= archive_fd) + close(archive_fd); + return fd; } @@ -459,7 +477,7 @@ const char *entry_pathname = NULL; const char *error = NULL; const char *pkg_name_humanized; - int r; + int archive_fd = -1, r, serrno; if (file_expr == NULL || strcmp("*", file_expr) == 0) extract_whole_archive = TRUE; @@ -483,8 +501,20 @@ archive_read_support_compression_all(archive); archive_read_support_format_tar(archive); + /* + * Avoid potential race conditions with archive_read_open_filename(3), + * by opening the file beforehand. + */ + if (pkg == NULL) + archive_fd = fileno(stdin); + else + archive_fd = open(pkg, O_RDONLY); + /* The initial open failed */ - if (archive_read_open_filename(archive, pkg, + if (archive_fd == -1) + warn("%s: unable to open the package from %s", + __func__, pkg_name_humanized); + else if (archive_read_open_fd(archive, archive_fd, ARCHIVE_DEFAULT_BYTES_PER_BLOCK) != ARCHIVE_OK) { error = archive_error_string(archive); @@ -523,9 +553,14 @@ } + serrno = errno; archive_read_finish(archive); - return (error == NULL ? 0 : 1); + /* Close any open descriptors. */ + if (0 <= archive_fd) + close(archive_fd); + + return (error == NULL && errno == 0 ? 0 : 1); }
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201005070421.o474LkR4029107>