asmith created this revision.
asmith added reviewers: zturner, llvm-commits.
Herald added subscribers: lldb-commits, abidh, mgorny, srhines.

This is intended as a first step to make lldb-server work on Windows. Follow-up 
changes to implement remote capabilities in PlatformWindows, launch gdbserver, 
launch/attach processes using Windows APIs etc will come in separate revisions.

The changes in this commit include the following:

- #ifdef what's not supported on Windows, for example signals
- Add a dummy 'waitpid' to the Windows PosixApi along with some definitions 
that are needed for compilation.
- Setup WSAsocket connection in SystemInitializerLLGS::Initialize.
- Add a namespace to static function 'terminate()' in lldb-server.cpp because 
its ambiguous with a Windows API.
- Better error handling in SocketAddress::GetAddressInfo.
- Clear the string before calling llvm::convertWideToUTF8 to avoid an 
unexpected assertion.


Repository:
  rLLDB LLDB

https://reviews.llvm.org/D56233

Files:
  cmake/modules/LLDBConfig.cmake
  include/lldb/Host/windows/PosixApi.h
  include/lldb/Target/Platform.h
  source/Host/common/SocketAddress.cpp
  source/Host/windows/HostInfoWindows.cpp
  source/Plugins/Process/gdb-remote/GDBRemoteCommunication.cpp
  tools/lldb-server/SystemInitializerLLGS.cpp
  tools/lldb-server/lldb-gdbserver.cpp
  tools/lldb-server/lldb-platform.cpp
  tools/lldb-server/lldb-server.cpp

Index: tools/lldb-server/lldb-server.cpp
===================================================================
--- tools/lldb-server/lldb-server.cpp
+++ tools/lldb-server/lldb-server.cpp
@@ -37,13 +37,15 @@
 int main_gdbserver(int argc, char *argv[]);
 int main_platform(int argc, char *argv[]);
 
-static void initialize() {
+namespace llsvr {
+void initialize() {
   if (auto e = g_debugger_lifetime->Initialize(
           llvm::make_unique<SystemInitializerLLGS>(), {}, nullptr))
     llvm::consumeError(std::move(e));
 }
 
-static void terminate() { g_debugger_lifetime->Terminate(); }
+void terminate() { g_debugger_lifetime->Terminate(); }
+} // namespace llsvr
 
 //----------------------------------------------------------------------
 // main
@@ -62,14 +64,14 @@
 
   switch (argv[1][0]) {
   case 'g':
-    initialize();
+    llsvr::initialize();
     main_gdbserver(argc, argv);
-    terminate();
+    llsvr::terminate();
     break;
   case 'p':
-    initialize();
+    llsvr::initialize();
     main_platform(argc, argv);
-    terminate();
+    llsvr::terminate();
     break;
   case 'v':
     fprintf(stderr, "%s\n", lldb_private::GetVersion());
Index: tools/lldb-server/lldb-platform.cpp
===================================================================
--- tools/lldb-server/lldb-platform.cpp
+++ tools/lldb-server/lldb-platform.cpp
@@ -16,8 +16,9 @@
 #include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
+#if !defined(_WIN32)
 #include <sys/wait.h>
-
+#endif
 #include <fstream>
 
 #include "llvm/Support/FileSystem.h"
@@ -74,6 +75,7 @@
 // Watch for signals
 //----------------------------------------------------------------------
 static void signal_handler(int signo) {
+#if !defined(_WIN32)
   switch (signo) {
   case SIGHUP:
     // Use SIGINT first, if that does not work, use SIGHUP as a last resort.
@@ -85,6 +87,7 @@
     abort();
     break;
   }
+#endif
 }
 
 static void display_usage(const char *progname, const char *subcommand) {
@@ -138,8 +141,10 @@
   const char *subcommand = argv[1];
   argc--;
   argv++;
+#if !defined(_WIN32)
   signal(SIGPIPE, SIG_IGN);
   signal(SIGHUP, signal_handler);
+#endif
   int long_option_index = 0;
   Status error;
   std::string listen_host_port;
Index: tools/lldb-server/lldb-gdbserver.cpp
===================================================================
--- tools/lldb-server/lldb-gdbserver.cpp
+++ tools/lldb-server/lldb-gdbserver.cpp
@@ -525,7 +525,7 @@
     handle_launch(gdb_server, argc, argv);
 
   // Print version info.
-  printf("%s-%s", LLGS_PROGRAM_NAME, LLGS_VERSION_STR);
+  printf("%s-%s\n", LLGS_PROGRAM_NAME, LLGS_VERSION_STR);
 
   ConnectToRemote(mainloop, gdb_server, reverse_connect, host_and_port,
                   progname, subcommand, named_pipe_path.c_str(),
Index: tools/lldb-server/SystemInitializerLLGS.cpp
===================================================================
--- tools/lldb-server/SystemInitializerLLGS.cpp
+++ tools/lldb-server/SystemInitializerLLGS.cpp
@@ -13,6 +13,9 @@
 #include "Plugins/ObjectFile/Mach-O/ObjectFileMachO.h"
 using HostObjectFile = ObjectFileMachO;
 #elif defined(_WIN32)
+#include "lldb/Host/windows/windows.h"
+#include <winsock2.h>
+
 #include "Plugins/ObjectFile/PECOFF/ObjectFilePECOFF.h"
 using HostObjectFile = ObjectFilePECOFF;
 #else
@@ -22,6 +25,8 @@
 
 using namespace lldb_private;
 
+static uint32_t g_ref_count = 0;
+
 llvm::Error
 SystemInitializerLLGS::Initialize(const InitializerOptions &options) {
   if (auto e = SystemInitializerCommon::Initialize(options))
@@ -29,10 +34,31 @@
 
   HostObjectFile::Initialize();
 
+#if defined(_WIN32)
+  if (g_ref_count++ == 0) {
+    // Require Windows Sockets version 2.2.
+    auto wVersion = MAKEWORD(2, 2);
+    WSADATA wsaData;
+    auto err = WSAStartup(wVersion, &wsaData);
+    if (err == 0) {
+      // Check if the WinSock verison is what we expect.
+      if (wsaData.wVersion < wVersion) {
+        g_ref_count = 0;
+        WSACleanup();
+      }
+    } else
+      g_ref_count = 0;
+  }
+#endif
+
   return llvm::Error::success();
 }
 
 void SystemInitializerLLGS::Terminate() {
+#if defined(_WIN32)
+  if (g_ref_count && --g_ref_count == 0)
+    WSACleanup();
+#endif
   HostObjectFile::Terminate();
   SystemInitializerCommon::Terminate();
 }
Index: source/Plugins/Process/gdb-remote/GDBRemoteCommunication.cpp
===================================================================
--- source/Plugins/Process/gdb-remote/GDBRemoteCommunication.cpp
+++ source/Plugins/Process/gdb-remote/GDBRemoteCommunication.cpp
@@ -38,6 +38,8 @@
 
 #if defined(__APPLE__)
 #define DEBUGSERVER_BASENAME "debugserver"
+#elif defined(_WIN32)
+#define DEBUGSERVER_BASENAME "lldb-server.exe"
 #else
 #define DEBUGSERVER_BASENAME "lldb-server"
 #endif
Index: source/Host/windows/HostInfoWindows.cpp
===================================================================
--- source/Host/windows/HostInfoWindows.cpp
+++ source/Host/windows/HostInfoWindows.cpp
@@ -82,6 +82,7 @@
   if (!::GetComputerNameW(buffer, &dwSize))
     return false;
 
+  s.clear();
   return llvm::convertWideToUTF8(buffer, s);
 }
 
Index: source/Host/common/SocketAddress.cpp
===================================================================
--- source/Host/common/SocketAddress.cpp
+++ source/Host/common/SocketAddress.cpp
@@ -8,7 +8,7 @@
 //===----------------------------------------------------------------------===//
 //
 // Note: This file is used on Darwin by debugserver, so it needs to remain as
-//       self contained as possible, and devoid of references to LLVM unless 
+//       self contained as possible, and devoid of references to LLVM unless
 //       there is compelling reason.
 //
 //===----------------------------------------------------------------------===//
@@ -29,6 +29,7 @@
 #include <string.h>
 
 #include "lldb/Host/PosixApi.h"
+#include "lldb/Utility/Status.h"
 
 // WindowsXP needs an inet_ntop implementation
 #ifdef _WIN32
@@ -256,6 +257,15 @@
          service_ptr = service_ptr->ai_next) {
       addr_list.emplace_back(SocketAddress(service_ptr));
     }
+  } else if (err) {
+    // Consume the error here.
+    Status error;
+#ifdef _WIN32
+    error.SetError(err, lldb::eErrorTypeWin32);
+#else
+    error.SetError(err, lldb::eErrorTypePOSIX);
+#endif
+    printf("SocketAddress::GetAddressInfo - %s\n", error.AsCString());
   }
 
   if (service_info_list)
Index: include/lldb/Target/Platform.h
===================================================================
--- include/lldb/Target/Platform.h
+++ include/lldb/Target/Platform.h
@@ -579,7 +579,7 @@
   virtual uint64_t WriteFile(lldb::user_id_t fd, uint64_t offset,
                              const void *src, uint64_t src_len, Status &error) {
     error.SetErrorStringWithFormat(
-        "Platform::ReadFile() is not supported in the %s platform",
+        "Platform::WriteFile() is not supported in the %s platform",
         GetName().GetCString());
     return -1;
   }
Index: include/lldb/Host/windows/PosixApi.h
===================================================================
--- include/lldb/Host/windows/PosixApi.h
+++ include/lldb/Host/windows/PosixApi.h
@@ -75,6 +75,9 @@
 
 #endif // _MSC_VER
 
+#define WNOHANG 1
+#define WUNTRACED 2
+
 // Various useful posix functions that are not present in Windows.  We provide
 // custom implementations.
 int vasprintf(char **ret, const char *fmt, va_list ap);
@@ -102,4 +105,8 @@
 inline pid_t fork(void) { LLVM_BUILTIN_UNREACHABLE; }
 inline pid_t setsid(void) { LLVM_BUILTIN_UNREACHABLE; }
 
+inline pid_t waitpid(pid_t pid, int *status, int options) {
+  // To be implemented.
+  return pid_t(-1);
+}
 #endif
Index: cmake/modules/LLDBConfig.cmake
===================================================================
--- cmake/modules/LLDBConfig.cmake
+++ cmake/modules/LLDBConfig.cmake
@@ -366,7 +366,7 @@
 
 # Figure out if lldb could use lldb-server.  If so, then we'll
 # ensure we build lldb-server when an lldb target is being built.
-if (CMAKE_SYSTEM_NAME MATCHES "Android|Darwin|FreeBSD|Linux|NetBSD")
+if (CMAKE_SYSTEM_NAME MATCHES "Android|Darwin|FreeBSD|Linux|NetBSD|Windows")
     set(LLDB_CAN_USE_LLDB_SERVER 1)
 else()
     set(LLDB_CAN_USE_LLDB_SERVER 0)
_______________________________________________
lldb-commits mailing list
lldb-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits

Reply via email to