Modified local spawning in debugserver processes to use a new --reverse-connect option so that debugserver actually connects back to LLDB instead of LLDB connecting to debugserver.

This gets rid of our hacky "get_random_port()" which would grab a random port and tell debugserver to open that port. Now LLDB creates, binds, listens and accepts a connection by binding to port zero and sending the correctly bound port down as the host:port to connect back to.

Fixed the "ConnectionFileDescriptor" to be able to correctly listen for connections from a specified host, localhost, or any host. Prior to this fix "listen://" only accepted the following format:

listen://<port>

But now it can accept:

listen://<port>         // Listen for connection from localhost on port <port>
listen://<host>:<port>  // Listen for connection from <host> and <port>    
listen://*:<port>       // Listen for connection from any host on port <port>

llvm-svn: 196547
diff --git a/lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp b/lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp
index 4527897..c6dc6cf 100644
--- a/lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp
+++ b/lldb/source/Plugins/Process/gdb-remote/ProcessGDBRemote.cpp
@@ -845,31 +845,35 @@
 ProcessGDBRemote::ConnectToDebugserver (const char *connect_url)
 {
     Error error;
-    // Sleep and wait a bit for debugserver to start to listen...
-    std::unique_ptr<ConnectionFileDescriptor> conn_ap(new ConnectionFileDescriptor());
-    if (conn_ap.get())
+    // Only connect if we have a valid connect URL
+    
+    if (connect_url && connect_url[0])
     {
-        const uint32_t max_retry_count = 50;
-        uint32_t retry_count = 0;
-        while (!m_gdb_comm.IsConnected())
+        std::unique_ptr<ConnectionFileDescriptor> conn_ap(new ConnectionFileDescriptor());
+        if (conn_ap.get())
         {
-            if (conn_ap->Connect(connect_url, &error) == eConnectionStatusSuccess)
+            const uint32_t max_retry_count = 50;
+            uint32_t retry_count = 0;
+            while (!m_gdb_comm.IsConnected())
             {
-                m_gdb_comm.SetConnection (conn_ap.release());
-                break;
-            }
-            else if (error.WasInterrupted())
-            {
-                // If we were interrupted, don't keep retrying.
-                break;
-            }
-            
-            retry_count++;
-            
-            if (retry_count >= max_retry_count)
-                break;
+                if (conn_ap->Connect(connect_url, &error) == eConnectionStatusSuccess)
+                {
+                    m_gdb_comm.SetConnection (conn_ap.release());
+                    break;
+                }
+                else if (error.WasInterrupted())
+                {
+                    // If we were interrupted, don't keep retrying.
+                    break;
+                }
+                
+                retry_count++;
+                
+                if (retry_count >= max_retry_count)
+                    break;
 
-            usleep (100000);
+                usleep (100000);
+            }
         }
     }
 
@@ -2501,9 +2505,9 @@
         debugserver_launch_info.SetMonitorProcessCallback (MonitorDebugserverProcess, this, false);
         debugserver_launch_info.SetUserID(process_info.GetUserID());
 
-        error = GDBRemoteCommunication::StartDebugserverProcess ("localhost:0",
-                                                                 debugserver_launch_info,
-                                                                 port);
+        error = m_gdb_comm.StartDebugserverProcess (NULL,
+                                                    debugserver_launch_info,
+                                                    port);
 
         if (error.Success ())
             m_debugserver_pid = debugserver_launch_info.GetProcessID();
@@ -2522,10 +2526,17 @@
             return error;
         }
         
-        char connect_url[128];
-        snprintf (connect_url, sizeof(connect_url), "connect://localhost:%u", port);
-        
-        error = ConnectToDebugserver (connect_url);
+        if (m_gdb_comm.IsConnected())
+        {
+            // Finish the connection process by doing the handshake without connecting (send NULL URL)
+            ConnectToDebugserver (NULL);
+        }
+        else
+        {
+            char connect_url[128];
+            snprintf (connect_url, sizeof(connect_url), "connect://localhost:%u", port);
+            error = ConnectToDebugserver (connect_url);
+        }
 
     }
     return error;