Add OnError support to EPoll

This enables rawrtc support.

Change-Id: Id1d346982a19260e323de76a8d1ee021723ae20d
diff --git a/aos/events/epoll.cc b/aos/events/epoll.cc
index 978909e..1c4427b 100644
--- a/aos/events/epoll.cc
+++ b/aos/events/epoll.cc
@@ -119,6 +119,11 @@
         << ": No handler registered for output events on " << event_data->fd;
     event_data->out_fn();
   }
+  if (event.events & kErrorEvents) {
+    CHECK(event_data->err_fn)
+        << ": No handler registered for error events on " << event_data->fd;
+    event_data->err_fn();
+  }
   return true;
 }
 
@@ -136,6 +141,18 @@
   DoEpollCtl(event_data, event_data->events | kInEvents);
 }
 
+void EPoll::OnError(int fd, ::std::function<void()> function) {
+  EventData *event_data = GetEventData(fd);
+  if (event_data == nullptr) {
+    fns_.emplace_back(std::make_unique<EventData>(fd));
+    event_data = fns_.back().get();
+  } else {
+    CHECK(!event_data->err_fn) << ": Duplicate in functions for " << fd;
+  }
+  event_data->err_fn = ::std::move(function);
+  DoEpollCtl(event_data, event_data->events | kErrorEvents);
+}
+
 void EPoll::OnWriteable(int fd, ::std::function<void()> function) {
   EventData *event_data = GetEventData(fd);
   if (event_data == nullptr) {
diff --git a/aos/events/epoll.h b/aos/events/epoll.h
index 71f58bb..4bcedf1 100644
--- a/aos/events/epoll.h
+++ b/aos/events/epoll.h
@@ -75,6 +75,10 @@
   // Only one function may be registered for readability on each fd.
   void OnReadable(int fd, ::std::function<void()> function);
 
+  // Registers a function to be called if the fd reports an error.
+  // Only one function may be registered for errors on each fd.
+  void OnError(int fd, ::std::function<void()> function);
+
   // Registers a function to be called if the fd becomes writeable.
   // Only one function may be registered for writability on each fd.
   void OnWriteable(int fd, ::std::function<void()> function);
@@ -108,7 +112,7 @@
 
     const int fd;
     uint32_t events = 0;
-    ::std::function<void()> in_fn, out_fn;
+    std::function<void()> in_fn, out_fn, err_fn;
   };
 
   void EnableEvents(int fd, uint32_t events);
@@ -122,6 +126,7 @@
   // with input.
   static constexpr uint32_t kInEvents = EPOLLIN | EPOLLPRI;
   static constexpr uint32_t kOutEvents = EPOLLOUT;
+  static constexpr uint32_t kErrorEvents = EPOLLERR;
 
   ::std::atomic<bool> run_{true};