PERFORCE change 177875 for review

Garrett Cooper gcooper at FreeBSD.org
Fri May 7 04:21:46 UTC 2010


http://p4web.freebsd.org/@@177875?ac=10

Change 177875 by gcooper at 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 at .

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);
 
 }
 


More information about the p4-projects mailing list