Skip site navigation (1)Skip section navigation (2)
Date:      Wed, 27 Dec 2017 18:30:24 +0000 (UTC)
From:      Warner Losh <imp@FreeBSD.org>
To:        src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org
Subject:   svn commit: r327241 - head/usr.sbin/devmatch
Message-ID:  <201712271830.vBRIUOFM036151@repo.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: imp
Date: Wed Dec 27 18:30:24 2017
New Revision: 327241
URL: https://svnweb.freebsd.org/changeset/base/327241

Log:
  Fix a bunch of issues (and a few non-issues but appeasement is easier
  than arguing) Coverity found:
  
  o Use open + fstat rather than stat + open to avoid any races for a
    file that's static for the life of the system. This will prevent any
    problems should someone insert a new device while installing a
    kernel in the future.
  o Use strlcpy instead of strcpy as a failsafe to knowing that the
    strings can't possibly be larger than the buffer due to data
    source limits (though in the future these limits might be more
    dynamic).
  o If we can't find the hints file, return rather than dereference
    a NULL pointer.
  o Check for lastmod before calling strcmp in case a PNP entry
    comes before a module entry. That's not allowed, but within the
    realm of crazy things programmers do.
  o Free lastmod before exiting search_hints() to avoid a leak.
  
  CID: 1383971, 1383970, 1383969, 1383965, 1383963, 1383960

Modified:
  head/usr.sbin/devmatch/devmatch.c

Modified: head/usr.sbin/devmatch/devmatch.c
==============================================================================
--- head/usr.sbin/devmatch/devmatch.c	Wed Dec 27 18:22:02 2017	(r327240)
+++ head/usr.sbin/devmatch/devmatch.c	Wed Dec 27 18:30:24 2017	(r327241)
@@ -31,6 +31,7 @@ __FBSDID("$FreeBSD$");
 #include <ctype.h>
 #include <devinfo.h>
 #include <err.h>
+#include <errno.h>
 #include <fcntl.h>
 #include <getopt.h>
 #include <stdio.h>
@@ -78,14 +79,17 @@ read_linker_hints(void)
 	p = modpath;
 	while ((q = strsep(&p, ";")) != NULL) {
 		snprintf(fn, sizeof(fn), "%s/linker.hints", q);
-		if (stat(fn, &sb) != 0)
-			continue;
+		fd = open(fn, O_RDONLY);
+		if (fd < 0) {
+			if (errno == ENOENT)
+				continue;
+			err(1, "Can't open %s for reading", fn);
+		}
+		if (fstat(fd, &sb) != 0)
+			err(1, "Can't fstat %s\n", fn);
 		hints = malloc(sb.st_size);
 		if (hints == NULL)
 			err(1, "not enough space to read hints file of %ju bytes", (uintmax_t)sb.st_size);
-		fd = open(fn, O_RDONLY);
-		if (fd < 0)
-			err(1, "Can't open %s for reading", fn);
 		if (read(fd, hints, sb.st_size) != sb.st_size)
 			err(1, "Can't read in %ju bytes from %s", (uintmax_t)sb.st_size, fn);
 		close(fd);
@@ -95,6 +99,7 @@ read_linker_hints(void)
 		warnx("Can't read linker hints file.");
 		free(hints);
 		hints = NULL;
+		return;
 	}
 	if (*(int *)(intptr_t)hints != LINKER_HINTS_VERSION) {
 		warnx("Linker hints version %d doesn't match expected %d.",
@@ -144,12 +149,12 @@ pnpval_as_int(const char *val, const char *pnpinfo)
 	cp = strchr(val, ';');
 	key[0] = ' ';
 	if (cp == NULL)
-		strcpy(key + 1, val);
+		strlcpy(key + 1, val, sizeof(key) - 1);
 	else {
 		memcpy(key + 1, val, cp - val);
 		key[cp - val + 1] = '\0';
 	}
-	strcat(key, "=");
+	strlcat(key, "=", sizeof(key));
 	if (strncmp(key + 1, pnpinfo, strlen(key + 1)) == 0)
 		rv = strtol(pnpinfo + strlen(key + 1), NULL, 0);
 	else {
@@ -241,7 +246,7 @@ search_hints(const char *bus, const char *dev, const c
 				printf("Module %s in %s\n", val1, val2);
 			break;
 		case MDT_PNP_INFO:
-			if (!dump_flag && !unbound_flag && strcmp(lastmod, "kernel") == 0)
+			if (!dump_flag && !unbound_flag && lastmod && strcmp(lastmod, "kernel") == 0)
 				break;
 			getstr(&ptr, val1);
 			getstr(&ptr, val2);
@@ -343,6 +348,7 @@ search_hints(const char *bus, const char *dev, const c
 			printf(" -------------------------");
 		printf("\n");
 	}
+	free(lastmod);
 }
 
 static int



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201712271830.vBRIUOFM036151>