================ @@ -44,6 +47,112 @@ using namespace llvm; // option descriptors for getopt_long_only() +#ifdef _WIN32 +typedef pipe_t fd_t; +const fd_t kInvalidSharedFD = LLDB_INVALID_PIPE; +#else +typedef NativeSocket fd_t; +const fd_t kInvalidSharedFD = Socket::kInvalidSocketValue; +#endif + +class SharedSocket { +public: + // Used by the parent process. + SharedSocket(Connection *conn, Status &error) { + m_fd = kInvalidSharedFD; + + const Socket *socket = + static_cast<const Socket *>(conn->GetReadObject().get()); + if (socket == nullptr) { + error = Status("invalid conn socket"); + return; + } + +#ifdef _WIN32 + m_socket = socket->GetNativeSocket(); + + // Create a pipe to transfer WSAPROTOCOL_INFO to the child process. + error = m_socket_pipe.CreateNew(true); + if (error.Fail()) + return; + + m_fd = m_socket_pipe.GetReadPipe(); +#else + m_fd = socket->GetNativeSocket(); + error = Status(); +#endif + } + + // Used by the child process. + SharedSocket(fd_t fd) : m_fd(fd) {} + + fd_t GetSendableFD() { return m_fd; } + + Status CompleteSending(lldb::pid_t child_pid) { +#ifdef _WIN32 + // Transfer WSAPROTOCOL_INFO to the child process. + m_socket_pipe.CloseReadFileDescriptor(); + + WSAPROTOCOL_INFO protocol_info; + if (::WSADuplicateSocket(m_socket, child_pid, &protocol_info) == + SOCKET_ERROR) { + int last_error = ::WSAGetLastError(); + return Status("WSADuplicateSocket() failed, error: %d", last_error); + } + + size_t num_bytes; + Status error = + m_socket_pipe.WriteWithTimeout(&protocol_info, sizeof(protocol_info), + std::chrono::seconds(10), num_bytes); + if (error.Fail()) + return error; + if (num_bytes != sizeof(protocol_info)) + return Status("WriteWithTimeout(WSAPROTOCOL_INFO) failed: %d bytes", + num_bytes); +#endif + return Status(); + } + + Status GetNativeSocket(NativeSocket &socket) { ---------------- labath wrote:
I think this would be better off as a static function -- it's not using any of the members except m_fd, which could just as easily be a function argument, and it's duplicating the Pipe and NativeSocket members as local vars. I can also imagine with a proper member function version of it, but then I think should reuse the members in the class. For example, by putting most of this work into the constructor, where it will initialize the m_pipe member and use it to receive the NativeSocket. `GetNativeSocket` could then be a plain getter (?) https://github.com/llvm/llvm-project/pull/101283 _______________________________________________ lldb-commits mailing list lldb-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/lldb-commits