blob: 557fb95df6967ccc9290bc928f7521df4ffbc966 [file] [log] [blame]
Chris Lattner30fdc8d2010-06-08 16:52:24 +00001//===-- Communication.cpp ---------------------------------------*- C++ -*-===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9
10// C Includes
11// C++ Includes
Eugene Zelenko896ddd02016-03-02 01:09:03 +000012#include <cstring>
13
Chris Lattner30fdc8d2010-06-08 16:52:24 +000014// Other libraries and framework includes
15// Project includes
Chris Lattner30fdc8d2010-06-08 16:52:24 +000016#include "lldb/Core/Communication.h"
17#include "lldb/Core/Connection.h"
Jim Ingham583bbb12016-03-07 21:50:25 +000018#include "lldb/Core/Listener.h"
Chris Lattner30fdc8d2010-06-08 16:52:24 +000019#include "lldb/Core/Log.h"
20#include "lldb/Core/Timer.h"
21#include "lldb/Core/Event.h"
Greg Clayton7fb56d02011-02-01 01:31:41 +000022#include "lldb/Host/Host.h"
Zachary Turner39de3112014-09-09 20:54:56 +000023#include "lldb/Host/HostThread.h"
24#include "lldb/Host/ThreadLauncher.h"
Chris Lattner30fdc8d2010-06-08 16:52:24 +000025
26using namespace lldb;
27using namespace lldb_private;
28
Jim Ingham4bddaeb2012-02-16 06:50:00 +000029ConstString &
30Communication::GetStaticBroadcasterClass ()
31{
32 static ConstString class_name ("lldb.communication");
33 return class_name;
34}
35
Greg Claytond46c87a2010-12-04 02:39:47 +000036Communication::Communication(const char *name) :
Eugene Zelenko896ddd02016-03-02 01:09:03 +000037 Broadcaster(nullptr, name),
38 m_connection_sp(),
39 m_read_thread_enabled(false),
40 m_read_thread_did_exit(false),
Chris Lattner30fdc8d2010-06-08 16:52:24 +000041 m_bytes(),
Eugene Zelenko896ddd02016-03-02 01:09:03 +000042 m_bytes_mutex(Mutex::eMutexTypeRecursive),
43 m_write_mutex(Mutex::eMutexTypeNormal),
44 m_synchronize_mutex(Mutex::eMutexTypeNormal),
45 m_callback(nullptr),
46 m_callback_baton(nullptr),
47 m_close_on_eof(true)
Chris Lattner30fdc8d2010-06-08 16:52:24 +000048
49{
50 lldb_private::LogIfAnyCategoriesSet (LIBLLDB_LOG_OBJECT | LIBLLDB_LOG_COMMUNICATION,
51 "%p Communication::Communication (name = %s)",
52 this, name);
Greg Clayton95bf0fd2011-04-01 00:29:43 +000053
54 SetEventName (eBroadcastBitDisconnected, "disconnected");
55 SetEventName (eBroadcastBitReadThreadGotBytes, "got bytes");
56 SetEventName (eBroadcastBitReadThreadDidExit, "read thread did exit");
57 SetEventName (eBroadcastBitReadThreadShouldExit, "read thread should exit");
58 SetEventName (eBroadcastBitPacketAvailable, "packet available");
Pavel Labath3f5df532015-03-12 10:12:41 +000059 SetEventName (eBroadcastBitNoMorePendingInput, "no more pending input");
Jim Ingham4bddaeb2012-02-16 06:50:00 +000060
61 CheckInWithManager();
Chris Lattner30fdc8d2010-06-08 16:52:24 +000062}
63
Chris Lattner30fdc8d2010-06-08 16:52:24 +000064Communication::~Communication()
65{
66 lldb_private::LogIfAnyCategoriesSet (LIBLLDB_LOG_OBJECT | LIBLLDB_LOG_COMMUNICATION,
67 "%p Communication::~Communication (name = %s)",
Jim Ingham583bbb12016-03-07 21:50:25 +000068 this, GetBroadcasterName().AsCString());
Chris Lattner30fdc8d2010-06-08 16:52:24 +000069 Clear();
70}
71
72void
73Communication::Clear()
74{
Eugene Zelenko896ddd02016-03-02 01:09:03 +000075 SetReadThreadBytesReceivedCallback(nullptr, nullptr);
76 Disconnect(nullptr);
77 StopReadThread(nullptr);
Chris Lattner30fdc8d2010-06-08 16:52:24 +000078}
79
80ConnectionStatus
Chris Lattner30fdc8d2010-06-08 16:52:24 +000081Communication::Connect (const char *url, Error *error_ptr)
82{
83 Clear();
84
85 lldb_private::LogIfAnyCategoriesSet (LIBLLDB_LOG_COMMUNICATION, "%p Communication::Connect (url = %s)", this, url);
86
Greg Clayton8b2fe6d2010-12-14 02:59:59 +000087 lldb::ConnectionSP connection_sp (m_connection_sp);
Eugene Zelenko896ddd02016-03-02 01:09:03 +000088 if (connection_sp)
Greg Clayton8b2fe6d2010-12-14 02:59:59 +000089 return connection_sp->Connect (url, error_ptr);
Chris Lattner30fdc8d2010-06-08 16:52:24 +000090 if (error_ptr)
91 error_ptr->SetErrorString("Invalid connection.");
92 return eConnectionStatusNoConnection;
93}
94
95ConnectionStatus
96Communication::Disconnect (Error *error_ptr)
97{
98 lldb_private::LogIfAnyCategoriesSet (LIBLLDB_LOG_COMMUNICATION, "%p Communication::Disconnect ()", this);
99
Greg Clayton8b2fe6d2010-12-14 02:59:59 +0000100 lldb::ConnectionSP connection_sp (m_connection_sp);
Eugene Zelenko896ddd02016-03-02 01:09:03 +0000101 if (connection_sp)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000102 {
Greg Clayton8b2fe6d2010-12-14 02:59:59 +0000103 ConnectionStatus status = connection_sp->Disconnect (error_ptr);
104 // We currently don't protect connection_sp with any mutex for
Greg Claytonbfae66a2010-12-12 21:50:57 +0000105 // multi-threaded environments. So lets not nuke our connection class
106 // without putting some multi-threaded protections in. We also probably
107 // don't want to pay for the overhead it might cause if every time we
108 // access the connection we have to take a lock.
109 //
Greg Claytone01e07b2013-04-18 18:10:51 +0000110 // This unique pointer will cleanup after itself when this object goes away,
Greg Claytonbfae66a2010-12-12 21:50:57 +0000111 // so there is no need to currently have it destroy itself immediately
112 // upon disconnnect.
Greg Clayton8b2fe6d2010-12-14 02:59:59 +0000113 //connection_sp.reset();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000114 return status;
115 }
116 return eConnectionStatusNoConnection;
117}
118
119bool
120Communication::IsConnected () const
121{
Eugene Zelenko896ddd02016-03-02 01:09:03 +0000122 lldb::ConnectionSP connection_sp(m_connection_sp);
123 return (connection_sp ? connection_sp->IsConnected() : false);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000124}
125
126bool
127Communication::HasConnection () const
128{
Eugene Zelenko896ddd02016-03-02 01:09:03 +0000129 return m_connection_sp.get() != nullptr;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000130}
131
132size_t
133Communication::Read (void *dst, size_t dst_len, uint32_t timeout_usec, ConnectionStatus &status, Error *error_ptr)
134{
135 lldb_private::LogIfAnyCategoriesSet (LIBLLDB_LOG_COMMUNICATION,
Daniel Malead01b2952012-11-29 21:49:15 +0000136 "%p Communication::Read (dst = %p, dst_len = %" PRIu64 ", timeout = %u usec) connection = %p",
Greg Clayton8b2fe6d2010-12-14 02:59:59 +0000137 this,
138 dst,
Greg Clayton43e0af02012-09-18 18:04:04 +0000139 (uint64_t)dst_len,
Greg Clayton8b2fe6d2010-12-14 02:59:59 +0000140 timeout_usec,
141 m_connection_sp.get());
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000142
Stephen Wilsona08cfb12011-01-12 04:22:54 +0000143 if (m_read_thread_enabled)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000144 {
145 // We have a dedicated read thread that is getting data for us
146 size_t cached_bytes = GetCachedBytes (dst, dst_len);
147 if (cached_bytes > 0 || timeout_usec == 0)
148 {
149 status = eConnectionStatusSuccess;
150 return cached_bytes;
151 }
152
Eugene Zelenko896ddd02016-03-02 01:09:03 +0000153 if (!m_connection_sp)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000154 {
155 if (error_ptr)
156 error_ptr->SetErrorString("Invalid connection.");
157 status = eConnectionStatusNoConnection;
158 return 0;
159 }
160 // Set the timeout appropriately
161 TimeValue timeout_time;
162 if (timeout_usec != UINT32_MAX)
163 {
164 timeout_time = TimeValue::Now();
165 timeout_time.OffsetWithMicroSeconds (timeout_usec);
166 }
167
Jim Ingham583bbb12016-03-07 21:50:25 +0000168 ListenerSP listener_sp(Listener::MakeListener("Communication::Read"));
169 listener_sp->StartListeningForEvents (this, eBroadcastBitReadThreadGotBytes | eBroadcastBitReadThreadDidExit);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000170 EventSP event_sp;
Jim Ingham583bbb12016-03-07 21:50:25 +0000171 while (listener_sp->WaitForEvent (timeout_time.IsValid() ? &timeout_time : nullptr, event_sp))
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000172 {
173 const uint32_t event_type = event_sp->GetType();
174 if (event_type & eBroadcastBitReadThreadGotBytes)
175 {
176 return GetCachedBytes (dst, dst_len);
177 }
178
179 if (event_type & eBroadcastBitReadThreadDidExit)
180 {
Tamas Berghammer35856692015-04-20 09:52:47 +0000181 if (GetCloseOnEOF ())
Eugene Zelenko896ddd02016-03-02 01:09:03 +0000182 Disconnect(nullptr);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000183 break;
184 }
185 }
186 return 0;
187 }
188
189 // We aren't using a read thread, just read the data synchronously in this
190 // thread.
Greg Clayton8b2fe6d2010-12-14 02:59:59 +0000191 lldb::ConnectionSP connection_sp (m_connection_sp);
Eugene Zelenko896ddd02016-03-02 01:09:03 +0000192 if (connection_sp)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000193 {
Pavel Labathef984e72016-05-03 14:07:41 +0000194 return connection_sp->Read (dst, dst_len, timeout_usec, status, error_ptr);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000195 }
196
197 if (error_ptr)
198 error_ptr->SetErrorString("Invalid connection.");
199 status = eConnectionStatusNoConnection;
200 return 0;
201}
202
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000203size_t
204Communication::Write (const void *src, size_t src_len, ConnectionStatus &status, Error *error_ptr)
205{
Greg Clayton8b2fe6d2010-12-14 02:59:59 +0000206 lldb::ConnectionSP connection_sp (m_connection_sp);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000207
Jason Molendaccd41e52012-10-04 22:47:07 +0000208 Mutex::Locker locker(m_write_mutex);
Greg Clayton8b2fe6d2010-12-14 02:59:59 +0000209 lldb_private::LogIfAnyCategoriesSet (LIBLLDB_LOG_COMMUNICATION,
Daniel Malead01b2952012-11-29 21:49:15 +0000210 "%p Communication::Write (src = %p, src_len = %" PRIu64 ") connection = %p",
Greg Clayton8b2fe6d2010-12-14 02:59:59 +0000211 this,
212 src,
Greg Clayton43e0af02012-09-18 18:04:04 +0000213 (uint64_t)src_len,
Greg Clayton8b2fe6d2010-12-14 02:59:59 +0000214 connection_sp.get());
215
Eugene Zelenko896ddd02016-03-02 01:09:03 +0000216 if (connection_sp)
Greg Clayton8b2fe6d2010-12-14 02:59:59 +0000217 return connection_sp->Write (src, src_len, status, error_ptr);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000218
219 if (error_ptr)
220 error_ptr->SetErrorString("Invalid connection.");
221 status = eConnectionStatusNoConnection;
222 return 0;
223}
224
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000225bool
226Communication::StartReadThread (Error *error_ptr)
227{
Greg Clayton1cb64962011-03-24 04:28:38 +0000228 if (error_ptr)
229 error_ptr->Clear();
230
Zachary Turneracee96a2014-09-23 18:32:09 +0000231 if (m_read_thread.IsJoinable())
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000232 return true;
233
234 lldb_private::LogIfAnyCategoriesSet (LIBLLDB_LOG_COMMUNICATION,
235 "%p Communication::StartReadThread ()", this);
236
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000237 char thread_name[1024];
Jim Ingham583bbb12016-03-07 21:50:25 +0000238 snprintf(thread_name, sizeof(thread_name), "<lldb.comm.%s>", GetBroadcasterName().AsCString());
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000239
Greg Clayton86c3f342010-09-15 05:19:45 +0000240 m_read_thread_enabled = true;
Pavel Labath3f5df532015-03-12 10:12:41 +0000241 m_read_thread_did_exit = false;
Zachary Turner39de3112014-09-09 20:54:56 +0000242 m_read_thread = ThreadLauncher::LaunchThread(thread_name, Communication::ReadThread, this, error_ptr);
Zachary Turneracee96a2014-09-23 18:32:09 +0000243 if (!m_read_thread.IsJoinable())
Greg Clayton86c3f342010-09-15 05:19:45 +0000244 m_read_thread_enabled = false;
Greg Clayton26661bc2010-07-23 15:43:25 +0000245 return m_read_thread_enabled;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000246}
247
248bool
249Communication::StopReadThread (Error *error_ptr)
250{
Zachary Turneracee96a2014-09-23 18:32:09 +0000251 if (!m_read_thread.IsJoinable())
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000252 return true;
253
254 lldb_private::LogIfAnyCategoriesSet (LIBLLDB_LOG_COMMUNICATION,
255 "%p Communication::StopReadThread ()", this);
256
257 m_read_thread_enabled = false;
258
Eugene Zelenko896ddd02016-03-02 01:09:03 +0000259 BroadcastEvent(eBroadcastBitReadThreadShouldExit, nullptr);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000260
Zachary Turner39de3112014-09-09 20:54:56 +0000261 // error = m_read_thread.Cancel();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000262
Zachary Turner39de3112014-09-09 20:54:56 +0000263 Error error = m_read_thread.Join(nullptr);
Zachary Turner39de3112014-09-09 20:54:56 +0000264 return error.Success();
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000265}
266
Greg Clayton59042602014-01-30 18:52:57 +0000267bool
268Communication::JoinReadThread (Error *error_ptr)
269{
Zachary Turneracee96a2014-09-23 18:32:09 +0000270 if (!m_read_thread.IsJoinable())
Greg Clayton59042602014-01-30 18:52:57 +0000271 return true;
272
Zachary Turner39de3112014-09-09 20:54:56 +0000273 Error error = m_read_thread.Join(nullptr);
Zachary Turner39de3112014-09-09 20:54:56 +0000274 return error.Success();
Greg Clayton59042602014-01-30 18:52:57 +0000275}
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000276
277size_t
278Communication::GetCachedBytes (void *dst, size_t dst_len)
279{
280 Mutex::Locker locker(m_bytes_mutex);
Eugene Zelenko896ddd02016-03-02 01:09:03 +0000281 if (!m_bytes.empty())
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000282 {
Eugene Zelenko896ddd02016-03-02 01:09:03 +0000283 // If DST is nullptr and we have a thread, then return the number
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000284 // of bytes that are available so the caller can call again
Eugene Zelenko896ddd02016-03-02 01:09:03 +0000285 if (dst == nullptr)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000286 return m_bytes.size();
287
288 const size_t len = std::min<size_t>(dst_len, m_bytes.size());
289
Greg Clayton471b31c2010-07-20 22:52:08 +0000290 ::memcpy (dst, m_bytes.c_str(), len);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000291 m_bytes.erase(m_bytes.begin(), m_bytes.begin() + len);
292
293 return len;
294 }
295 return 0;
296}
297
298void
Caroline Ticeefed6132010-11-19 20:47:54 +0000299Communication::AppendBytesToCache (const uint8_t * bytes, size_t len, bool broadcast, ConnectionStatus status)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000300{
301 lldb_private::LogIfAnyCategoriesSet (LIBLLDB_LOG_COMMUNICATION,
Daniel Malead01b2952012-11-29 21:49:15 +0000302 "%p Communication::AppendBytesToCache (src = %p, src_len = %" PRIu64 ", broadcast = %i)",
Greg Clayton43e0af02012-09-18 18:04:04 +0000303 this, bytes, (uint64_t)len, broadcast);
Eugene Zelenko896ddd02016-03-02 01:09:03 +0000304 if ((bytes == nullptr || len == 0)
Caroline Tice9fd58502011-02-03 20:02:43 +0000305 && (status != lldb::eConnectionStatusEndOfFile))
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000306 return;
307 if (m_callback)
308 {
309 // If the user registered a callback, then call it and do not broadcast
310 m_callback (m_callback_baton, bytes, len);
311 }
Eugene Zelenko896ddd02016-03-02 01:09:03 +0000312 else if (bytes != nullptr && len > 0)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000313 {
314 Mutex::Locker locker(m_bytes_mutex);
315 m_bytes.append ((const char *)bytes, len);
316 if (broadcast)
317 BroadcastEventIfUnique (eBroadcastBitReadThreadGotBytes);
318 }
319}
320
321size_t
Greg Clayton73bf5db2011-06-17 01:22:15 +0000322Communication::ReadFromConnection (void *dst,
323 size_t dst_len,
324 uint32_t timeout_usec,
325 ConnectionStatus &status,
326 Error *error_ptr)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000327{
Eugene Zelenko896ddd02016-03-02 01:09:03 +0000328 lldb::ConnectionSP connection_sp(m_connection_sp);
Pavel Labathef984e72016-05-03 14:07:41 +0000329 return (connection_sp ? connection_sp->Read(dst, dst_len, timeout_usec, status, error_ptr) : 0);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000330}
331
Caroline Tice82305fc2010-12-02 18:31:56 +0000332bool
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000333Communication::ReadThreadIsRunning ()
334{
Stephen Wilsona08cfb12011-01-12 04:22:54 +0000335 return m_read_thread_enabled;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000336}
337
Virgile Bellob2f1fb22013-08-23 12:44:05 +0000338lldb::thread_result_t
339Communication::ReadThread (lldb::thread_arg_t p)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000340{
341 Communication *comm = (Communication *)p;
342
Greg Clayton5160ce52013-03-27 23:08:40 +0000343 Log *log(lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_COMMUNICATION));
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000344
345 if (log)
346 log->Printf ("%p Communication::ReadThread () thread starting...", p);
347
348 uint8_t buf[1024];
349
350 Error error;
351 ConnectionStatus status = eConnectionStatusSuccess;
352 bool done = false;
353 while (!done && comm->m_read_thread_enabled)
354 {
Peter Collingbourneba23ca02011-06-18 23:52:14 +0000355 size_t bytes_read = comm->ReadFromConnection (buf, sizeof(buf), 5 * TimeValue::MicroSecPerSec, status, &error);
Greg Clayton73bf5db2011-06-17 01:22:15 +0000356 if (bytes_read > 0)
357 comm->AppendBytesToCache (buf, bytes_read, true, status);
358 else if ((bytes_read == 0)
359 && status == eConnectionStatusEndOfFile)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000360 {
Greg Clayton73bf5db2011-06-17 01:22:15 +0000361 if (comm->GetCloseOnEOF ())
362 comm->Disconnect ();
363 comm->AppendBytesToCache (buf, bytes_read, true, status);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000364 }
365
366 switch (status)
367 {
368 case eConnectionStatusSuccess:
369 break;
370
Greg Clayton7788e5f2010-12-04 02:22:36 +0000371 case eConnectionStatusEndOfFile:
Tamas Berghammer35856692015-04-20 09:52:47 +0000372 done = true;
373 break;
Todd Fiala42628282014-08-21 17:16:26 +0000374 case eConnectionStatusError: // Check GetError() for details
375 if (error.GetType() == eErrorTypePOSIX && error.GetError() == EIO)
376 {
377 // EIO on a pipe is usually caused by remote shutdown
378 comm->Disconnect ();
379 done = true;
380 }
381 if (log)
382 error.LogIfError (log,
383 "%p Communication::ReadFromConnection () => status = %s",
384 p,
385 Communication::ConnectionStatusAsCString (status));
386 break;
Pavel Labath3f5df532015-03-12 10:12:41 +0000387 case eConnectionStatusInterrupted: // Synchronization signal from SynchronizeWithReadThread()
388 // The connection returns eConnectionStatusInterrupted only when there is no
389 // input pending to be read, so we can signal that.
390 comm->BroadcastEvent (eBroadcastBitNoMorePendingInput);
391 break;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000392 case eConnectionStatusNoConnection: // No connection
393 case eConnectionStatusLostConnection: // Lost connection while connected to a valid connection
394 done = true;
Jason Molenda62e06812016-02-16 04:14:33 +0000395 LLVM_FALLTHROUGH;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000396 case eConnectionStatusTimedOut: // Request timed out
Greg Clayton2d4edfb2010-11-06 01:53:30 +0000397 if (log)
Greg Clayton5160ce52013-03-27 23:08:40 +0000398 error.LogIfError (log,
399 "%p Communication::ReadFromConnection () => status = %s",
400 p,
401 Communication::ConnectionStatusAsCString (status));
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000402 break;
403 }
404 }
Caroline Tice20ad3c42010-10-29 21:48:37 +0000405 log = lldb_private::GetLogIfAllCategoriesSet (LIBLLDB_LOG_COMMUNICATION);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000406 if (log)
407 log->Printf ("%p Communication::ReadThread () thread exiting...", p);
408
Pavel Labath3f5df532015-03-12 10:12:41 +0000409 comm->m_read_thread_did_exit = true;
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000410 // Let clients know that this thread is exiting
Pavel Labath3f5df532015-03-12 10:12:41 +0000411 comm->BroadcastEvent (eBroadcastBitNoMorePendingInput);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000412 comm->BroadcastEvent (eBroadcastBitReadThreadDidExit);
413 return NULL;
414}
415
416void
Eugene Zelenko896ddd02016-03-02 01:09:03 +0000417Communication::SetReadThreadBytesReceivedCallback(ReadThreadBytesReceived callback,
418 void *callback_baton)
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000419{
420 m_callback = callback;
421 m_callback_baton = callback_baton;
422}
423
424void
Pavel Labath3f5df532015-03-12 10:12:41 +0000425Communication::SynchronizeWithReadThread ()
426{
427 // Only one thread can do the synchronization dance at a time.
428 Mutex::Locker locker(m_synchronize_mutex);
429
430 // First start listening for the synchronization event.
Jim Ingham583bbb12016-03-07 21:50:25 +0000431 ListenerSP listener_sp(Listener::MakeListener("Communication::SyncronizeWithReadThread"));
432 listener_sp->StartListeningForEvents(this, eBroadcastBitNoMorePendingInput);
Pavel Labath3f5df532015-03-12 10:12:41 +0000433
434 // If the thread is not running, there is no point in synchronizing.
435 if (!m_read_thread_enabled || m_read_thread_did_exit)
436 return;
437
438 // Notify the read thread.
439 m_connection_sp->InterruptRead();
440
441 // Wait for the synchronization event.
442 EventSP event_sp;
Jim Ingham583bbb12016-03-07 21:50:25 +0000443 listener_sp->WaitForEvent(nullptr, event_sp);
Pavel Labath3f5df532015-03-12 10:12:41 +0000444}
445
446void
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000447Communication::SetConnection (Connection *connection)
448{
Eugene Zelenko896ddd02016-03-02 01:09:03 +0000449 Disconnect(nullptr);
450 StopReadThread(nullptr);
Greg Clayton8b2fe6d2010-12-14 02:59:59 +0000451 m_connection_sp.reset(connection);
Chris Lattner30fdc8d2010-06-08 16:52:24 +0000452}
Caroline Ticeceb6b132010-10-26 03:11:13 +0000453
454const char *
455Communication::ConnectionStatusAsCString (lldb::ConnectionStatus status)
456{
457 switch (status)
458 {
459 case eConnectionStatusSuccess: return "success";
460 case eConnectionStatusError: return "error";
461 case eConnectionStatusTimedOut: return "timed out";
462 case eConnectionStatusNoConnection: return "no connection";
463 case eConnectionStatusLostConnection: return "lost connection";
Greg Clayton7a5388b2011-03-20 04:57:14 +0000464 case eConnectionStatusEndOfFile: return "end of file";
Greg Claytonf0066ad2014-05-02 00:45:31 +0000465 case eConnectionStatusInterrupted: return "interrupted";
Caroline Ticeceb6b132010-10-26 03:11:13 +0000466 }
467
468 static char unknown_state_string[64];
469 snprintf(unknown_state_string, sizeof (unknown_state_string), "ConnectionStatus = %i", status);
470 return unknown_state_string;
471}