xf86-video-intel: tools/backlight_helper.c

Chris Wilson ickle at kemper.freedesktop.org
Thu Jul 17 08:18:46 PDT 2014


 tools/backlight_helper.c |   56 +++++++++++++++++++++++++++++------------------
 1 file changed, 35 insertions(+), 21 deletions(-)

New commits:
commit 3140d72826b5227f7f7ac9a428faa4bcfd4b377b
Author: Chris Wilson <chris at chris-wilson.co.uk>
Date:   Thu Jul 17 16:14:16 2014 +0100

    backlight: Prevent dereference of potential NULL argv
    
    Adam Sampson spotted that
    
    "It's possible (but not very sensible) to exec a program with an empty
    argument list, so argv[0] is not necessarily a valid pointer. For
    example:
    
    $ cat exec0.c
    
    int main(int argc, char *argv[]) {
        char *empty[1] = { NULL };
        execvp(argv[1], empty);
        perror("execvp");
        return 1;
    }
    $ ./exec0 /usr/libexec/xf86-video-intel-backlight-helper
    Usage: (null) <iface>
    "
    
    He sensibly suggested that we hardcode the program name to avoid the
    NULL dereference. Being the paranoid type, we should also be careful not
    to write to any file descriptors outside of our control (i.e. stderr),
    so disable the messages unless we are debugging.
    
    Reported-by: Adam Sampson
    Signed-off-by: Chris Wilson <chris at chris-wilson.co.uk>

diff --git a/tools/backlight_helper.c b/tools/backlight_helper.c
index 24958ec..8b2667d 100644
--- a/tools/backlight_helper.c
+++ b/tools/backlight_helper.c
@@ -1,43 +1,57 @@
 #include <stdio.h>
 #include <string.h>
+#include <stdarg.h>
+#include <stdlib.h>
 #include <fcntl.h>
 #include <unistd.h>
+#include <errno.h>
 
 #include <sys/types.h>
 #include <sys/stat.h>
 
+#define DBG 0
+
+#if defined(__GNUC__) && (__GNUC__ > 3)
+__attribute__((format(printf, 1, 2), noreturn))
+#endif
+static void die(const char *format, ...)
+{
+	if (DBG) {
+		va_list args;
+
+		va_start(args, format);
+		vfprintf(stderr, format, args);
+		va_end(args);
+	}
+
+	exit(1);
+}
+
 int main(int argc, char *argv[])
 {
 	struct stat st;
 	char buf[1024];
 	int len, fd;
 
-	if (argc != 2) {
-		fprintf(stderr, "Usage: %s <iface>\n", argv[0]);
-		return 1;
-	}
+	if (argc != 2)
+		die("Usage: xf86-video-intel-backlight-helper <iface>\n");
+
+	if (strchr(argv[1], '/') != NULL)
+		die("Invalid interface '%s': contains '/'\n", argv[1]);
+
+	if (snprintf(buf, sizeof(buf),
+		     "/sys/class/backlight/%s/brightness",
+		     argv[1]) >= sizeof(buf))
+		die("Invalid interface '%s': name too long\n", argv[1]);
 
-	if (strchr(argv[1], '/') != NULL) {
-		fprintf(stderr, "Invalid interface name\n");
-		return 1;
-	}
-	if (snprintf(buf, sizeof(buf), "/sys/class/backlight/%s/brightness",
-		argv[1]) >= sizeof(buf)) {
-		fprintf(stderr, "Interface name is too long\n");
-		return 1;
-	}
 	fd = open(buf, O_RDWR);
-	if (fd < 0 || fstat(fd, &st) || major(st.st_dev)) {
-		fprintf(stderr, "Cannot access backlight interface '%s'\n", argv[1]);
-		return 1;
-	}
+	if (fd < 0 || fstat(fd, &st) || major(st.st_dev))
+		die("Invalid interface '%s': unknown backlight file\n", argv[1]);
 
 	while (fgets(buf, sizeof(buf), stdin)) {
 		len = strlen(buf);
-		if (write(fd, buf, len) != len) {
-			fprintf(stderr, "Failed to update backlight interface '%s'\n", argv[1]);
-			return 2;
-		}
+		if (write(fd, buf, len) != len)
+			die("Failed to update backlight interface '%s': errno=%d\n", argv[1], errno);
 	}
 
 	return 0;


More information about the xorg-commit mailing list