Author: cbieneman
Date: Wed Apr 12 16:56:29 2017
New Revision: 300111

URL: http://llvm.org/viewvc/llvm-project?rev=300111&view=rev
Log:
Support Unit Testing debugserver

Summary:
This patch refactors the CMake build system's support for building debugserver 
to allow us to build the majority of debugserver's sources into the 
debugserverCommon library which can then be reused by unit tests.

The first unit test I've written tests debug server's ability to accept 
incoming connections from LLDB. The test forks the process, and one side 
creates a listening socket using debugserver's socket API, the other side 
creates a transmitting socket using LLDB's TCPSocket class.

I have no clue where to even start getting this connected into the LLDB Xcode 
project, so for now these tests are CMake-only.

Reviewers: zturner, labath, jasonmolenda

Subscribers: lldb-commits, mgorny

Differential Revision: https://reviews.llvm.org/D31357

Added:
    lldb/trunk/unittests/debugserver/
    lldb/trunk/unittests/debugserver/CMakeLists.txt
    lldb/trunk/unittests/debugserver/RNBSocketTest.cpp
    lldb/trunk/unittests/debugserver/debugserver_LogCallback.cpp
Modified:
    lldb/trunk/tools/debugserver/source/CMakeLists.txt
    lldb/trunk/tools/debugserver/source/MacOSX/CMakeLists.txt
    lldb/trunk/unittests/CMakeLists.txt

Modified: lldb/trunk/tools/debugserver/source/CMakeLists.txt
URL: 
http://llvm.org/viewvc/llvm-project/lldb/trunk/tools/debugserver/source/CMakeLists.txt?rev=300111&r1=300110&r2=300111&view=diff
==============================================================================
--- lldb/trunk/tools/debugserver/source/CMakeLists.txt (original)
+++ lldb/trunk/tools/debugserver/source/CMakeLists.txt Wed Apr 12 16:56:29 2017
@@ -2,12 +2,10 @@ include_directories(${CMAKE_CURRENT_BINA
 include_directories(${LLDB_SOURCE_DIR}/source)
 include_directories(MacOSX/DarwinLog)
 
-if (CMAKE_SYSTEM_NAME MATCHES "Darwin")
-  include_directories(MacOSX)
-  #include_directories(${CMAKE_CURRENT_BINARY_DIR}/MacOSX)
+include_directories(MacOSX)
+#include_directories(${CMAKE_CURRENT_BINARY_DIR}/MacOSX)
 
-  set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -stdlib=libc++ 
-Wl,-sectcreate,__TEXT,__info_plist,${CMAKE_CURRENT_SOURCE_DIR}/../resources/lldb-debugserver-Info.plist")
-endif()
+set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -stdlib=libc++ 
-Wl,-sectcreate,__TEXT,__info_plist,${CMAKE_CURRENT_SOURCE_DIR}/../resources/lldb-debugserver-Info.plist")
 
 check_cxx_compiler_flag("-Wno-gnu-zero-variadic-macro-arguments"
                         CXX_SUPPORTS_NO_GNU_ZERO_VARIADIC_MACRO_ARGUMENTS)
@@ -27,19 +25,31 @@ if (CXX_SUPPORTS_NO_EXTENDED_OFFSETOF)
   set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -Wno-extended-offsetof")
 endif ()
 
-if (NOT CMAKE_SYSTEM_NAME MATCHES "Darwin")
-  add_definitions(
-    -DDEBUGSERVER_VERSION_STR="${LLDB_VERSION}"
-    )
-endif ()
+find_library(COCOA_LIBRARY Cocoa)
+add_subdirectory(MacOSX)
 
-if (CMAKE_SYSTEM_NAME MATCHES "Darwin")
-  find_library(COCOA_LIBRARY Cocoa)
-  add_subdirectory(MacOSX)
-endif()
+set(generated_mach_interfaces
+  ${CMAKE_CURRENT_BINARY_DIR}/mach_exc.h
+  ${CMAKE_CURRENT_BINARY_DIR}/mach_excServer.c
+  ${CMAKE_CURRENT_BINARY_DIR}/mach_excUser.c
+  )
+add_custom_command(OUTPUT ${generated_mach_interfaces}
+  COMMAND mig ${CMAKE_CURRENT_SOURCE_DIR}/MacOSX/dbgnub-mig.defs
+  DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/MacOSX/dbgnub-mig.defs
+  )
 
-add_lldb_library(lldbDebugserverCommon
-  debugserver.cpp
+set(DEBUGSERVER_VERS_GENERATED_FILE 
${CMAKE_CURRENT_BINARY_DIR}/debugserver_vers.c)
+set_source_files_properties(${DEBUGSERVER_VERS_GENERATED_FILE} PROPERTIES 
GENERATED 1)
+
+add_custom_command(OUTPUT ${DEBUGSERVER_VERS_GENERATED_FILE}
+  COMMAND ${LLDB_SOURCE_DIR}/scripts/generate-vers.pl
+          ${LLDB_SOURCE_DIR}/lldb.xcodeproj/project.pbxproj debugserver
+          > ${DEBUGSERVER_VERS_GENERATED_FILE}
+  DEPENDS ${LLDB_SOURCE_DIR}/scripts/generate-vers.pl
+          ${LLDB_SOURCE_DIR}/lldb.xcodeproj/project.pbxproj
+  )
+
+set(lldbDebugserverCommonSources
   DNBArch.cpp
   DNBBreakpoint.cpp
   DNB.cpp
@@ -63,12 +73,53 @@ add_lldb_library(lldbDebugserverCommon
   RNBSocket.cpp
   SysSignal.cpp
   TTYState.cpp
+  
+  MacOSX/CFBundle.cpp
+  MacOSX/CFString.cpp
+  MacOSX/Genealogy.cpp
+  MacOSX/MachException.cpp
+  MacOSX/MachProcess.mm
+  MacOSX/MachTask.mm
+  MacOSX/MachThread.cpp
+  MacOSX/MachThreadList.cpp
+  MacOSX/MachVMMemory.cpp
+  MacOSX/MachVMRegion.cpp
+  MacOSX/OsLogger.cpp
+  ${generated_mach_interfaces}
+  ${DEBUGSERVER_VERS_GENERATED_FILE})
+
+add_library(lldbDebugserverCommon ${lldbDebugserverCommonSources})
+
+target_link_libraries(lldbDebugserverCommon
+                      INTERFACE ${COCOA_LIBRARY}
+                      lldbDebugserverMacOSX_I386
+                      lldbDebugserverMacOSX_X86_64
+                      lldbDebugserverMacOSX_DarwinLog)
+
+set(LLVM_OPTIONAL_SOURCES ${lldbDebugserverCommonSources})
+add_lldb_tool(debugserver INCLUDE_IN_FRAMEWORK
+  debugserver.cpp
 
   LINK_LIBS
-    lldbHost
-    ${COCOA_LIBRARY}
+    lldbDebugserverCommon
   )
 
+set(LLDB_CODESIGN_IDENTITY "lldb_codesign"
+  CACHE STRING "Identity used for code signing. Set to empty string to skip 
the signing step.")
+if (NOT ("${LLDB_CODESIGN_IDENTITY}" STREQUAL ""))
+  execute_process(
+    COMMAND xcrun -f codesign_allocate
+    OUTPUT_STRIP_TRAILING_WHITESPACE
+    OUTPUT_VARIABLE CODESIGN_ALLOCATE
+    )
+  add_custom_command(TARGET debugserver
+    POST_BUILD
+    COMMAND ${CMAKE_COMMAND} -E env CODESIGN_ALLOCATE=${CODESIGN_ALLOCATE}
+            codesign --force --sign ${LLDB_CODESIGN_IDENTITY}
+            $<TARGET_FILE:debugserver>
+    WORKING_DIRECTORY ${CMAKE_BINARY_DIR}/bin
+  )
+endif()
 
 
 

Modified: lldb/trunk/tools/debugserver/source/MacOSX/CMakeLists.txt
URL: 
http://llvm.org/viewvc/llvm-project/lldb/trunk/tools/debugserver/source/MacOSX/CMakeLists.txt?rev=300111&r1=300110&r2=300111&view=diff
==============================================================================
--- lldb/trunk/tools/debugserver/source/MacOSX/CMakeLists.txt (original)
+++ lldb/trunk/tools/debugserver/source/MacOSX/CMakeLists.txt Wed Apr 12 
16:56:29 2017
@@ -6,70 +6,3 @@ add_subdirectory(x86_64)
 add_subdirectory(DarwinLog)
 
 include_directories(..)
-
-set(generated_mach_interfaces
-  ${CMAKE_CURRENT_BINARY_DIR}/mach_exc.h
-  ${CMAKE_CURRENT_BINARY_DIR}/mach_excServer.c
-  ${CMAKE_CURRENT_BINARY_DIR}/mach_excUser.c
-  )
-add_custom_command(OUTPUT ${generated_mach_interfaces}
-  COMMAND mig ${CMAKE_CURRENT_SOURCE_DIR}/dbgnub-mig.defs
-  DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/dbgnub-mig.defs
-  )
-
-set(DEBUGSERVER_VERS_GENERATED_FILE 
${CMAKE_CURRENT_BINARY_DIR}/debugserver_vers.c)
-set_source_files_properties(${DEBUGSERVER_VERS_GENERATED_FILE} PROPERTIES 
GENERATED 1)
-
-add_custom_command(OUTPUT ${DEBUGSERVER_VERS_GENERATED_FILE}
-  COMMAND ${LLDB_SOURCE_DIR}/scripts/generate-vers.pl
-          ${LLDB_SOURCE_DIR}/lldb.xcodeproj/project.pbxproj debugserver
-          > ${DEBUGSERVER_VERS_GENERATED_FILE}
-  DEPENDS ${LLDB_SOURCE_DIR}/scripts/generate-vers.pl
-          ${LLDB_SOURCE_DIR}/lldb.xcodeproj/project.pbxproj
-  )
-
-add_lldb_tool(debugserver INCLUDE_IN_FRAMEWORK
-  CFBundle.cpp
-  CFString.cpp
-  Genealogy.cpp
-  MachException.cpp
-  MachProcess.mm
-  MachTask.mm
-  MachThread.cpp
-  MachThreadList.cpp
-  MachVMMemory.cpp
-  MachVMRegion.cpp
-  OsLogger.cpp
-  ${generated_mach_interfaces}
-  ${DEBUGSERVER_VERS_GENERATED_FILE}
-
-  LINK_LIBS
-    lldbDebugserverCommon
-    lldbDebugserverMacOSX_I386
-    lldbDebugserverMacOSX_X86_64
-    lldbDebugserverMacOSX_DarwinLog
-  )
-
-set_source_files_properties(
-  HasAVX.s
-  # Necessary since compilation will fail with stand-alone assembler
-  PROPERTIES LANGUAGE C COMPILE_FLAGS "-x assembler-with-cpp"
-  )
-
-set(LLDB_CODESIGN_IDENTITY "lldb_codesign"
-  CACHE STRING "Identity used for code signing. Set to empty string to skip 
the signing step.")
-if (NOT ("${LLDB_CODESIGN_IDENTITY}" STREQUAL ""))
-  execute_process(
-    COMMAND xcrun -f codesign_allocate
-    OUTPUT_STRIP_TRAILING_WHITESPACE
-    OUTPUT_VARIABLE CODESIGN_ALLOCATE
-    )
-  add_custom_command(TARGET debugserver
-    POST_BUILD
-    # Note: --entitlements option removed (see comment above).
-    COMMAND ${CMAKE_COMMAND} -E env CODESIGN_ALLOCATE=${CODESIGN_ALLOCATE}
-            codesign --force --sign ${LLDB_CODESIGN_IDENTITY}
-            $<TARGET_FILE:debugserver>
-    WORKING_DIRECTORY ${CMAKE_BINARY_DIR}/bin
-  )
-endif()

Modified: lldb/trunk/unittests/CMakeLists.txt
URL: 
http://llvm.org/viewvc/llvm-project/lldb/trunk/unittests/CMakeLists.txt?rev=300111&r1=300110&r2=300111&view=diff
==============================================================================
--- lldb/trunk/unittests/CMakeLists.txt (original)
+++ lldb/trunk/unittests/CMakeLists.txt Wed Apr 12 16:56:29 2017
@@ -70,3 +70,7 @@ add_subdirectory(SymbolFile)
 add_subdirectory(Target)
 add_subdirectory(UnwindAssembly)
 add_subdirectory(Utility)
+
+if(LLDB_CAN_USE_DEBUGSERVER)
+  add_subdirectory(debugserver)
+endif()
\ No newline at end of file

Added: lldb/trunk/unittests/debugserver/CMakeLists.txt
URL: 
http://llvm.org/viewvc/llvm-project/lldb/trunk/unittests/debugserver/CMakeLists.txt?rev=300111&view=auto
==============================================================================
--- lldb/trunk/unittests/debugserver/CMakeLists.txt (added)
+++ lldb/trunk/unittests/debugserver/CMakeLists.txt Wed Apr 12 16:56:29 2017
@@ -0,0 +1,19 @@
+# Note: debugserver is a Darwin-only implementation of a remote debugging
+# server. It is not intended to be used on other platforms. The tests are here
+# because using the LLDB Host API is convienent and allows testing of both 
parts
+# of the debugserver communication path. If you are looking for a non-darwin
+# remote debugging server, please use lldb-server.
+
+include_directories(${LLDB_SOURCE_DIR}/tools/debugserver/source
+                    ${LLDB_SOURCE_DIR}/tools/debugserver/source/MacOSX)
+
+add_lldb_unittest(debugserverTests
+  RNBSocketTest.cpp
+  debugserver_LogCallback.cpp
+
+  LINK_LIBS
+    lldbDebugserverCommon
+    lldbHost
+  LINK_COMPONENTS
+    Support
+  )

Added: lldb/trunk/unittests/debugserver/RNBSocketTest.cpp
URL: 
http://llvm.org/viewvc/llvm-project/lldb/trunk/unittests/debugserver/RNBSocketTest.cpp?rev=300111&view=auto
==============================================================================
--- lldb/trunk/unittests/debugserver/RNBSocketTest.cpp (added)
+++ lldb/trunk/unittests/debugserver/RNBSocketTest.cpp Wed Apr 12 16:56:29 2017
@@ -0,0 +1,133 @@
+//===-- RNBSocketTest.cpp ---------------------------------------*- C++ 
-*-===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#include "gtest/gtest.h"
+
+#include <arpa/inet.h>
+#include <sys/sysctl.h>
+#include <unistd.h>
+
+#include "RNBDefs.h"
+#include "RNBSocket.h"
+#include "lldb/Host/Socket.h"
+#include "lldb/Host/StringConvert.h"
+#include "lldb/Host/common/TCPSocket.h"
+
+using namespace lldb_private;
+
+std::string hello = "Hello, world!";
+std::string goodbye = "Goodbye!";
+
+static void ServerCallbackv4(const void *baton, in_port_t port) {
+  auto child_pid = fork();
+  if (child_pid == 0) {
+    Socket *client_socket;
+    char addr_buffer[256];
+    sprintf(addr_buffer, "%s:%d", baton, port);
+    Error err = Socket::TcpConnect(addr_buffer, false, client_socket);
+    if (err.Fail())
+      abort();
+    char buffer[32];
+    size_t read_size = 32;
+    err = client_socket->Read((void *)&buffer[0], read_size);
+    if (err.Fail())
+      abort();
+    std::string Recv(&buffer[0], read_size);
+    if (Recv != hello)
+      abort();
+    size_t write_size = goodbye.length();
+    err = client_socket->Write(goodbye.c_str(), write_size);
+    if (err.Fail())
+      abort();
+    if (write_size != goodbye.length())
+      abort();
+    delete client_socket;
+    exit(0);
+  }
+}
+
+void TestSocketListen(const char *addr) {
+  RNBSocket server_socket;
+  auto result =
+      server_socket.Listen(addr, 0, ServerCallbackv4, (const void *)addr);
+  ASSERT_TRUE(result == rnb_success);
+  result = server_socket.Write(hello.c_str(), hello.length());
+  ASSERT_TRUE(result == rnb_success);
+  std::string bye;
+  result = server_socket.Read(bye);
+  ASSERT_TRUE(result == rnb_success);
+  ASSERT_EQ(bye, goodbye);
+
+  int exit_status;
+  wait(&exit_status);
+  ASSERT_EQ(exit_status, 0);
+}
+
+TEST(RNBSocket, LoopBackListenIPv4) { TestSocketListen("127.0.0.1"); }
+
+void TestSocketConnect(const char *addr) {
+  char addr_wrap[256];
+  sprintf(addr_wrap, "%s:0", addr);
+
+  Socket *server_socket;
+  Predicate<uint16_t> port_predicate;
+  port_predicate.SetValue(0, eBroadcastNever);
+  Error err =
+      Socket::TcpListen(addr_wrap, false, server_socket, &port_predicate);
+  ASSERT_FALSE(err.Fail());
+
+  auto port = ((TCPSocket *)server_socket)->GetLocalPortNumber();
+  auto child_pid = fork();
+  if (child_pid != 0) {
+    RNBSocket client_socket;
+    auto result = client_socket.Connect(addr, port);
+    ASSERT_TRUE(result == rnb_success);
+    result = client_socket.Write(hello.c_str(), hello.length());
+    ASSERT_TRUE(result == rnb_success);
+    std::string bye;
+    result = client_socket.Read(bye);
+    ASSERT_TRUE(result == rnb_success);
+    ASSERT_EQ(bye, goodbye);
+  } else {
+    Socket *connected_socket;
+    err = server_socket->Accept(addr_wrap, false, connected_socket);
+    if (err.Fail()) {
+      llvm::errs() << err.AsCString();
+      abort();
+    }
+    char buffer[32];
+    size_t read_size = 32;
+    err = connected_socket->Read((void *)&buffer[0], read_size);
+    if (err.Fail()) {
+      llvm::errs() << err.AsCString();
+      abort();
+    }
+    std::string Recv(&buffer[0], read_size);
+    if (Recv != hello) {
+      llvm::errs() << err.AsCString();
+      abort();
+    }
+    size_t write_size = goodbye.length();
+    err = connected_socket->Write(goodbye.c_str(), write_size);
+    if (err.Fail()) {
+      llvm::errs() << err.AsCString();
+      abort();
+    }
+    if (write_size != goodbye.length()) {
+      llvm::errs() << err.AsCString();
+      abort();
+    }
+    exit(0);
+  }
+  int exit_status;
+  wait(&exit_status);
+  ASSERT_EQ(exit_status, 0);
+}
+
+TEST(RNBSocket, LoopBackConnectIPv4) { TestSocketConnect("127.0.0.1"); }

Added: lldb/trunk/unittests/debugserver/debugserver_LogCallback.cpp
URL: 
http://llvm.org/viewvc/llvm-project/lldb/trunk/unittests/debugserver/debugserver_LogCallback.cpp?rev=300111&view=auto
==============================================================================
--- lldb/trunk/unittests/debugserver/debugserver_LogCallback.cpp (added)
+++ lldb/trunk/unittests/debugserver/debugserver_LogCallback.cpp Wed Apr 12 
16:56:29 2017
@@ -0,0 +1,20 @@
+//===-- debugserver_LogCallback.cpp -----------------------------*- C++ 
-*-===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+//------------------------------------------------------------------------------
+// this function is defined in debugserver.cpp, but is needed to link the
+// debugserver Common library. It is for logging only, so it is left
+// unimplemented here.
+//------------------------------------------------------------------------------
+
+#include <stdint.h>
+#include <stdarg.h>
+
+void FileLogCallback(void *baton, uint32_t flags, const char *format,
+                     va_list args) {}


_______________________________________________
lldb-commits mailing list
lldb-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits

Reply via email to