base: Give more information when setting up asynchronous IO fails.
authorGabe Black <gabeblack@google.com>
Mon, 31 Jul 2017 22:31:38 +0000 (15:31 -0700)
committerGabe Black <gabeblack@google.com>
Wed, 2 Aug 2017 20:42:13 +0000 (20:42 +0000)
When asynchronous IO fails, gem5 currently just says it failed and quits, and
doesn't give any more information about which step failed, or what
specifically about it failed.

This change adds two helpers which will attempt the fcntl, check for error
conditions, and in the event of a failure, include a message describing the
error code and what the arguments to fcntl were.

Change-Id: I316478172ab2aefd3788279dbc12744791385cd5
Reviewed-on: https://gem5-review.googlesource.com/4320
Reviewed-by: Andreas Sandberg <andreas.sandberg@arm.com>
Maintainer: Gabe Black <gabeblack@google.com>

src/base/pollevent.cc

index 30edb65b656ae068984a9a8f54e4b3ecdf138854..79814e077dfb87768dfb4dc37832e5d436f57aaf 100644 (file)
@@ -41,7 +41,9 @@
 #include <fcntl.h>
 #include <unistd.h>
 
+#include <cerrno>
 #include <csignal>
+#include <cstring>
 
 #include "base/misc.hh"
 #include "base/types.hh"
@@ -200,25 +202,43 @@ PollQueue::service()
     }
 }
 
+template <class ArgT>
+static int fcntlHelper(int fd, int cmd, ArgT arg)
+{
+    int retval = fcntl(fd, cmd, arg);
+    if (retval == -1) {
+        char *errstr = strerror(errno);
+        panic("fcntl(%d, %d, %s): \"%s\" when setting up async IO.\n",
+              errstr, fd, cmd, arg);
+    }
+    return retval;
+}
+
+static int fcntlHelper(int fd, int cmd)
+{
+    int retval = fcntl(fd, cmd);
+    if (retval == -1) {
+        char *errstr = strerror(errno);
+        panic("fcntl(%d, %d): \"%s\" when setting up async IO.\n",
+              errstr, fd, cmd);
+    }
+    return retval;
+}
+
 void
 PollQueue::setupAsyncIO(int fd, bool set)
 {
-    int flags = fcntl(fd, F_GETFL);
-    if (flags == -1)
-        panic("Could not set up async IO");
+    int flags = fcntlHelper(fd, F_GETFL);
 
     if (set)
         flags |= FASYNC;
     else
         flags &= ~(FASYNC);
 
-    if (set) {
-      if (fcntl(fd, F_SETOWN, getpid()) == -1)
-        panic("Could not set up async IO");
-    }
+    if (set)
+        fcntlHelper(fd, F_SETOWN, getpid());
 
-    if (fcntl(fd, F_SETFL, flags) == -1)
-        panic("Could not set up async IO");
+    fcntlHelper(fd, F_SETFL, flags);
 
     // The file descriptor might already have events pending. We won't
     // see them if they occurred before we set the FASYNC