Merge "Copy windows 32-bit e2fsprogs executables into /bin64" into studio-1.4-dev
automerge: ccc67f3

* commit 'ccc67f3f00dd92210b64c610abbb93bb557ac526':
  Copy windows 32-bit e2fsprogs executables into $OUT_DIR/bin64
diff --git a/distrib/android-emugl/host/libs/libOpenglRender/RenderServer.cpp b/distrib/android-emugl/host/libs/libOpenglRender/RenderServer.cpp
index 7c91271..de3952f 100644
--- a/distrib/android-emugl/host/libs/libOpenglRender/RenderServer.cpp
+++ b/distrib/android-emugl/host/libs/libOpenglRender/RenderServer.cpp
@@ -113,6 +113,7 @@
         // check if we have been requested to exit while waiting on accept
         if ((clientFlags & IOSTREAM_CLIENT_EXIT_SERVER) != 0) {
             m_exiting = true;
+            delete stream;
             break;
         }
 
@@ -120,11 +121,10 @@
         if (!rt) {
             fprintf(stderr,"Failed to create RenderThread\n");
             delete stream;
-            stream = NULL;
         } else if (!rt->start()) {
             fprintf(stderr,"Failed to start RenderThread\n");
             delete rt;
-            rt = NULL;
+            delete stream;
         }
 
         //
diff --git a/distrib/android-emugl/host/libs/libOpenglRender/render_api.cpp b/distrib/android-emugl/host/libs/libOpenglRender/render_api.cpp
index 1fb8d6f..984755a 100644
--- a/distrib/android-emugl/host/libs/libOpenglRender/render_api.cpp
+++ b/distrib/android-emugl/host/libs/libOpenglRender/render_api.cpp
@@ -112,6 +112,7 @@
     if (!s_renderWindow->isValid()) {
         ERR("Could not initialize emulated framebuffer");
         delete s_renderWindow;
+        s_renderWindow = NULL;
         return false;
     }
 
@@ -164,10 +165,22 @@
         s_renderThread = NULL;
     }
 
-    if (s_renderWindow) {
-        delete s_renderWindow;
-        s_renderWindow = NULL;
-    }
+    /*
+     * This conditional is unreachable in all cases except
+     * during UI shutdown. When the UI has to shutdown in an
+     * unorderly fashion (e.g. SIGKILL), a yet undefined
+     * alternative path will free s_renderWindow twice,
+     * resulting to a segfault.
+     *
+     * TODO: FIX THIS
+     *
+     */
+    // if (s_renderWindow != NULL) {
+    //     delete s_renderWindow;
+    //     s_renderWindow = NULL;
+    // }
+
+    delete dummy;
 
     return ret;
 }
diff --git a/distrib/android-emugl/shared/OpenglCodecCommon/SocketStream.cpp b/distrib/android-emugl/shared/OpenglCodecCommon/SocketStream.cpp
index 4b4ffb3..7b19262 100644
--- a/distrib/android-emugl/shared/OpenglCodecCommon/SocketStream.cpp
+++ b/distrib/android-emugl/shared/OpenglCodecCommon/SocketStream.cpp
@@ -50,8 +50,11 @@
 #ifdef _WIN32
         closesocket(m_sock);
 #else
-        ::close(m_sock);
+        forceStop();
+        if(close(m_sock) < 0)
+          perror("Closing SocketStream failed");
 #endif
+        // DBG("SocketStream::~close  @ %d \n", m_sock);
         m_sock = -1;
     }
     if (m_buf != NULL) {
@@ -171,6 +174,7 @@
 #ifdef _WIN32
     ::shutdown(m_sock, SD_BOTH);
 #else
-    ::shutdown(m_sock, SHUT_RDWR);
+    if(::shutdown(m_sock, SHUT_RDWR) < 0)
+      perror("Error shutting down SocketStream");
 #endif
 }
diff --git a/distrib/android-emugl/shared/OpenglCodecCommon/UnixStream.cpp b/distrib/android-emugl/shared/OpenglCodecCommon/UnixStream.cpp
index 7b2f67d..f7af57a 100644
--- a/distrib/android-emugl/shared/OpenglCodecCommon/UnixStream.cpp
+++ b/distrib/android-emugl/shared/OpenglCodecCommon/UnixStream.cpp
@@ -37,15 +37,32 @@
 #endif
 
 UnixStream::UnixStream(size_t bufSize) :
-    SocketStream(bufSize)
+    SocketStream(bufSize),
+    bound_socket_path(NULL)
 {
 }
 
 UnixStream::UnixStream(int sock, size_t bufSize) :
-    SocketStream(sock, bufSize)
+    SocketStream(sock, bufSize),
+    bound_socket_path(NULL)
 {
 }
 
+UnixStream::~UnixStream()
+{
+    if (bound_socket_path != NULL) {
+      int ret = 0;
+      do {
+          ret = unlink(bound_socket_path);
+      } while (ret < 0 && errno == EINTR);
+      if(ret != 0) {
+          ERR("Failed to unlink UNIX socket at \"%s\"\n", bound_socket_path);
+          perror("UNIX socket could not be unlinked");
+      }
+      free(bound_socket_path);
+    }
+}
+
 /* Initialize a sockaddr_un with the appropriate values corresponding
  * to a given 'virtual port'. Returns 0 on success, -1 on error.
  */
@@ -84,6 +101,7 @@
 
     // Now, initialize it properly
     snprintf(path, pathlen, "%s/qemu-gles-%d", tmp, port_number);
+
     return 0;
 }
 
@@ -95,7 +113,16 @@
     }
 
     m_sock = emugl::socketLocalServer(addrstr, SOCK_STREAM);
-    if (!valid()) return int(ERR_INVALID_SOCKET);
+
+    if (!valid())
+        return int(ERR_INVALID_SOCKET);
+
+    bound_socket_path = strdup(addrstr);
+    if(bound_socket_path == NULL) {
+        ERR("WARNING: UNIX socket at \"%s\" should be manually removed \n",
+            addrstr);
+        return -1;
+    }
 
     return 0;
 }
@@ -108,6 +135,7 @@
         struct sockaddr_un addr;
         socklen_t len = sizeof(addr);
         clientSock = ::accept(m_sock, (sockaddr *)&addr, &len);
+        // DBG("UnixStream::accept  @ %d \n", clientSock);
 
         if (clientSock < 0 && errno == EINTR) {
             continue;
@@ -126,6 +154,7 @@
 int UnixStream::connect(const char* addr)
 {
     m_sock = emugl::socketLocalClient(addr, SOCK_STREAM);
+    // DBG("UnixStream::connect @ %d \n", m_sock);
     if (!valid()) return -1;
 
     return 0;
diff --git a/distrib/android-emugl/shared/OpenglCodecCommon/UnixStream.h b/distrib/android-emugl/shared/OpenglCodecCommon/UnixStream.h
index 95e7431..5e2025d 100644
--- a/distrib/android-emugl/shared/OpenglCodecCommon/UnixStream.h
+++ b/distrib/android-emugl/shared/OpenglCodecCommon/UnixStream.h
@@ -21,10 +21,12 @@
 class UnixStream : public SocketStream {
 public:
     explicit UnixStream(size_t bufsize = 10000);
+    ~UnixStream();
     virtual int listen(char addrstr[MAX_ADDRSTR_LEN]);
     virtual SocketStream *accept();
     virtual int connect(const char* addr);
 private:
+    char *bound_socket_path;
     UnixStream(int sock, size_t bufSize);
 };
 
diff --git a/distrib/android-emugl/shared/emugl/common/sockets.cpp b/distrib/android-emugl/shared/emugl/common/sockets.cpp
index 2a13d72..b38a4be 100644
--- a/distrib/android-emugl/shared/emugl/common/sockets.cpp
+++ b/distrib/android-emugl/shared/emugl/common/sockets.cpp
@@ -24,6 +24,7 @@
 #include <netinet/tcp.h>
 #include <sys/un.h>
 #include <sys/stat.h>
+#include <stdio.h>
 #endif
 
 #include <stddef.h>
@@ -35,6 +36,19 @@
 
 namespace {
 
+static void socketSetDontLinger(int s) {
+#ifdef _WIN32
+  // TODO: Verify default behavior on WINDOWS
+#else
+    // Ungraceful shutdown, no reason to linger at all
+    struct linger so_linger;
+    so_linger.l_onoff  = 1;
+    so_linger.l_linger = 0;
+    if(setsockopt(s, SOL_SOCKET, SO_LINGER, &so_linger, sizeof so_linger) < 0)
+      perror("Setting socket option SO_LINGER={on, 0} failed");
+#endif
+}
+
 static void socketSetReuseAddress(int s) {
 #ifdef _WIN32
     // The default behaviour on Windows is equivalent to SO_REUSEADDR
@@ -44,7 +58,8 @@
     // http://msdn.microsoft.com/en-us/library/windows/desktop/ms740621(v=vs.85).aspx
 #else
     int val = 1;
-    setsockopt(s, SOL_SOCKET, SO_REUSEADDR, &val, sizeof(val));
+    if(setsockopt(s, SOL_SOCKET, SO_REUSEADDR, &val, sizeof(val)) < 0)
+      perror("Setting socket option SO_REUSEADDR failed");
 #endif
 }
 
@@ -104,25 +119,35 @@
 
 int socketBindInternal(const SockAddr* addr, int socketType) {
     int s = ::socket(addr->getFamily(), socketType, 0);
-    if (s < 0)
+    if (s < 0) {
+        perror("Could not create socket to bind");
         return -errno;
+    }
+
+    socketSetDontLinger(s);
+    socketSetReuseAddress(s);
 
     // Bind to the socket.
     if (::bind(s, &addr->generic, addr->len) < 0 ||
         ::listen(s, 5) < 0) {
         int ret = -errno;
+        perror("Could not bind or listen to socket");
         ::close(s);
         return ret;
     }
 
-    socketSetReuseAddress(s);
     return s;
 }
 
 int socketConnectInternal(const SockAddr* addr, int socketType) {
     int s = ::socket(addr->getFamily(), socketType, 0);
-    if (s < 0)
+    if (s < 0) {
+        perror("Could not create socket to connect");
         return -errno;
+    }
+
+    socketSetDontLinger(s);
+    socketSetReuseAddress(s);
 
     int ret;
     do {