1254721Semaste//===-- POSIXThread.cpp -----------------------------------------*- C++ -*-===//
2254721Semaste//
3254721Semaste//                     The LLVM Compiler Infrastructure
4254721Semaste//
5254721Semaste// This file is distributed under the University of Illinois Open Source
6254721Semaste// License. See LICENSE.TXT for details.
7254721Semaste//
8254721Semaste//===----------------------------------------------------------------------===//
9254721Semaste
10254721Semaste#include "lldb/lldb-python.h"
11254721Semaste
12254721Semaste// C Includes
13254721Semaste#include <errno.h>
14254721Semaste
15254721Semaste// C++ Includes
16254721Semaste// Other libraries and framework includes
17254721Semaste// Project includes
18254721Semaste#include "lldb/Breakpoint/Watchpoint.h"
19254721Semaste#include "lldb/Breakpoint/BreakpointLocation.h"
20254721Semaste#include "lldb/Core/Debugger.h"
21254721Semaste#include "lldb/Core/State.h"
22254721Semaste#include "lldb/Host/Host.h"
23254721Semaste#include "lldb/Target/Process.h"
24254721Semaste#include "lldb/Target/StopInfo.h"
25254721Semaste#include "lldb/Target/Target.h"
26254721Semaste#include "lldb/Target/ThreadSpec.h"
27254721Semaste#include "POSIXStopInfo.h"
28254721Semaste#include "POSIXThread.h"
29254721Semaste#include "ProcessPOSIX.h"
30254721Semaste#include "ProcessPOSIXLog.h"
31254721Semaste#include "ProcessMonitor.h"
32263363Semaste#include "RegisterContextPOSIXProcessMonitor_mips64.h"
33263363Semaste#include "RegisterContextPOSIXProcessMonitor_x86.h"
34263363Semaste#include "RegisterContextLinux_i386.h"
35254721Semaste#include "RegisterContextLinux_x86_64.h"
36263363Semaste#include "RegisterContextFreeBSD_i386.h"
37263363Semaste#include "RegisterContextFreeBSD_mips64.h"
38254721Semaste#include "RegisterContextFreeBSD_x86_64.h"
39254721Semaste
40254721Semaste#include "UnwindLLDB.h"
41254721Semaste
42254721Semasteusing namespace lldb;
43254721Semasteusing namespace lldb_private;
44254721Semaste
45254721Semaste
46254721SemastePOSIXThread::POSIXThread(Process &process, lldb::tid_t tid)
47254721Semaste    : Thread(process, tid),
48254721Semaste      m_frame_ap (),
49254721Semaste      m_breakpoint (),
50254721Semaste      m_thread_name_valid (false),
51263363Semaste      m_thread_name (),
52263363Semaste      m_posix_thread(NULL)
53254721Semaste{
54254721Semaste    Log *log (ProcessPOSIXLog::GetLogIfAllCategoriesSet (POSIX_LOG_THREAD));
55254721Semaste    if (log && log->GetMask().Test(POSIX_LOG_VERBOSE))
56254721Semaste        log->Printf ("POSIXThread::%s (tid = %" PRIi64 ")", __FUNCTION__, tid);
57254721Semaste
58254721Semaste    // Set the current watchpoints for this thread.
59254721Semaste    Target &target = GetProcess()->GetTarget();
60254721Semaste    const WatchpointList &wp_list = target.GetWatchpointList();
61254721Semaste    size_t wp_size = wp_list.GetSize();
62254721Semaste
63254721Semaste    for (uint32_t wp_idx = 0; wp_idx < wp_size; wp_idx++)
64254721Semaste    {
65254721Semaste        lldb::WatchpointSP wp = wp_list.GetByIndex(wp_idx);
66254721Semaste        if (wp.get() && wp->IsEnabled())
67254721Semaste        {
68269024Semaste            // This watchpoint as been enabled; obviously this "new" thread
69269024Semaste            // has been created since that watchpoint was enabled.  Since
70269024Semaste            // the POSIXBreakpointProtocol has yet to be initialized, its
71269024Semaste            // m_watchpoints_initialized member will be FALSE.  Attempting to
72269024Semaste            // read the debug status register to determine if a watchpoint
73269024Semaste            // has been hit would result in the zeroing of that register.
74269024Semaste            // Since the active debug registers would have been cloned when
75269024Semaste            // this thread was created, simply force the m_watchpoints_initized
76269024Semaste            // member to TRUE and avoid resetting dr6 and dr7.
77269024Semaste            GetPOSIXBreakpointProtocol()->ForceWatchpointsInitialized();
78254721Semaste        }
79254721Semaste    }
80254721Semaste}
81254721Semaste
82254721SemastePOSIXThread::~POSIXThread()
83254721Semaste{
84254721Semaste    DestroyThread();
85254721Semaste}
86254721Semaste
87254721SemasteProcessMonitor &
88254721SemastePOSIXThread::GetMonitor()
89254721Semaste{
90254721Semaste    ProcessSP base = GetProcess();
91254721Semaste    ProcessPOSIX &process = static_cast<ProcessPOSIX&>(*base);
92254721Semaste    return process.GetMonitor();
93254721Semaste}
94254721Semaste
95263368Semaste// Overridden by FreeBSDThread; this is used only on Linux.
96254721Semastevoid
97254721SemastePOSIXThread::RefreshStateAfterStop()
98254721Semaste{
99254721Semaste    // Invalidate all registers in our register context. We don't set "force" to
100254721Semaste    // true because the stop reply packet might have had some register values
101254721Semaste    // that were expedited and these will already be copied into the register
102254721Semaste    // context by the time this function gets called. The KDPRegisterContext
103254721Semaste    // class has been made smart enough to detect when it needs to invalidate
104254721Semaste    // which registers are valid by putting hooks in the register read and
105254721Semaste    // register supply functions where they check the process stop ID and do
106254721Semaste    // the right thing.
107254721Semaste    //if (StateIsStoppedState(GetState())
108254721Semaste    {
109254721Semaste        const bool force = false;
110254721Semaste        GetRegisterContext()->InvalidateIfNeeded (force);
111254721Semaste    }
112254721Semaste    // FIXME: This should probably happen somewhere else.
113254721Semaste    SetResumeState(eStateRunning);
114254721Semaste    Log *log (ProcessPOSIXLog::GetLogIfAllCategoriesSet (POSIX_LOG_THREAD));
115254721Semaste    if (log)
116254721Semaste        log->Printf ("POSIXThread::%s (tid = %" PRIi64 ") setting thread resume state to running", __FUNCTION__, GetID());
117254721Semaste}
118254721Semaste
119254721Semasteconst char *
120254721SemastePOSIXThread::GetInfo()
121254721Semaste{
122254721Semaste    return NULL;
123254721Semaste}
124254721Semaste
125254721Semastevoid
126254721SemastePOSIXThread::SetName (const char *name)
127254721Semaste{
128254721Semaste    m_thread_name_valid = (name && name[0]);
129254721Semaste    if (m_thread_name_valid)
130254721Semaste        m_thread_name.assign (name);
131254721Semaste    else
132254721Semaste        m_thread_name.clear();
133254721Semaste}
134254721Semaste
135254721Semasteconst char *
136254721SemastePOSIXThread::GetName ()
137254721Semaste{
138254721Semaste    if (!m_thread_name_valid)
139254721Semaste    {
140254721Semaste        SetName(Host::GetThreadName(GetProcess()->GetID(), GetID()).c_str());
141254721Semaste        m_thread_name_valid = true;
142254721Semaste    }
143254721Semaste
144254721Semaste    if (m_thread_name.empty())
145254721Semaste        return NULL;
146254721Semaste    return m_thread_name.c_str();
147254721Semaste}
148254721Semaste
149254721Semastelldb::RegisterContextSP
150254721SemastePOSIXThread::GetRegisterContext()
151254721Semaste{
152254721Semaste    if (!m_reg_context_sp)
153254721Semaste    {
154263363Semaste        m_posix_thread = NULL;
155254721Semaste
156263363Semaste        RegisterInfoInterface *reg_interface = NULL;
157263363Semaste        const ArchSpec &target_arch = GetProcess()->GetTarget().GetArchitecture();
158263363Semaste
159263363Semaste        switch (target_arch.GetCore())
160254721Semaste        {
161263363Semaste            case ArchSpec::eCore_mips64:
162263363Semaste            {
163263363Semaste                switch (target_arch.GetTriple().getOS())
164263363Semaste                {
165263363Semaste                    case llvm::Triple::FreeBSD:
166263363Semaste                        reg_interface = new RegisterContextFreeBSD_mips64(target_arch);
167263363Semaste                        break;
168263363Semaste                    default:
169263363Semaste                        assert(false && "OS not supported");
170263363Semaste                        break;
171263363Semaste                }
172254721Semaste
173263363Semaste                if (reg_interface)
174263363Semaste                {
175263363Semaste                    RegisterContextPOSIXProcessMonitor_mips64 *reg_ctx = new RegisterContextPOSIXProcessMonitor_mips64(*this, 0, reg_interface);
176263363Semaste                    m_posix_thread = reg_ctx;
177263363Semaste                    m_reg_context_sp.reset(reg_ctx);
178263363Semaste                }
179263363Semaste                break;
180263363Semaste            }
181263363Semaste
182263363Semaste            case ArchSpec::eCore_x86_32_i386:
183263363Semaste            case ArchSpec::eCore_x86_32_i486:
184263363Semaste            case ArchSpec::eCore_x86_32_i486sx:
185263363Semaste            case ArchSpec::eCore_x86_64_x86_64:
186254721Semaste            {
187263363Semaste                switch (target_arch.GetTriple().getOS())
188263363Semaste                {
189263363Semaste                    case llvm::Triple::FreeBSD:
190263363Semaste                        reg_interface = new RegisterContextFreeBSD_x86_64(target_arch);
191263363Semaste                        break;
192263363Semaste                    case llvm::Triple::Linux:
193263363Semaste                        reg_interface = new RegisterContextLinux_x86_64(target_arch);
194263363Semaste                        break;
195263363Semaste                    default:
196263363Semaste                        assert(false && "OS not supported");
197263363Semaste                        break;
198263363Semaste                }
199263363Semaste
200263363Semaste                if (reg_interface)
201263363Semaste                {
202263363Semaste                    RegisterContextPOSIXProcessMonitor_x86_64 *reg_ctx = new RegisterContextPOSIXProcessMonitor_x86_64(*this, 0, reg_interface);
203263363Semaste                    m_posix_thread = reg_ctx;
204263363Semaste                    m_reg_context_sp.reset(reg_ctx);
205263363Semaste                }
206263363Semaste                break;
207254721Semaste            }
208263363Semaste
209263363Semaste            default:
210263363Semaste                assert(false && "CPU type not supported!");
211263363Semaste                break;
212254721Semaste        }
213254721Semaste    }
214254721Semaste    return m_reg_context_sp;
215254721Semaste}
216254721Semaste
217254721Semastelldb::RegisterContextSP
218254721SemastePOSIXThread::CreateRegisterContextForFrame(lldb_private::StackFrame *frame)
219254721Semaste{
220254721Semaste    lldb::RegisterContextSP reg_ctx_sp;
221254721Semaste    uint32_t concrete_frame_idx = 0;
222254721Semaste
223254721Semaste    Log *log (ProcessPOSIXLog::GetLogIfAllCategoriesSet (POSIX_LOG_THREAD));
224254721Semaste    if (log && log->GetMask().Test(POSIX_LOG_VERBOSE))
225254721Semaste        log->Printf ("POSIXThread::%s ()", __FUNCTION__);
226254721Semaste
227254721Semaste    if (frame)
228254721Semaste        concrete_frame_idx = frame->GetConcreteFrameIndex();
229254721Semaste
230254721Semaste    if (concrete_frame_idx == 0)
231254721Semaste        reg_ctx_sp = GetRegisterContext();
232254721Semaste    else
233254721Semaste    {
234254721Semaste        assert(GetUnwinder());
235254721Semaste        reg_ctx_sp = GetUnwinder()->CreateRegisterContextForFrame(frame);
236254721Semaste    }
237254721Semaste
238254721Semaste    return reg_ctx_sp;
239254721Semaste}
240254721Semaste
241263363Semastelldb::addr_t
242263363SemastePOSIXThread::GetThreadPointer ()
243263363Semaste{
244263363Semaste    ProcessMonitor &monitor = GetMonitor();
245263363Semaste    addr_t addr;
246263363Semaste    if (monitor.ReadThreadPointer (GetID(), addr))
247263363Semaste        return addr;
248263363Semaste    else
249263363Semaste        return LLDB_INVALID_ADDRESS;
250263363Semaste}
251263363Semaste
252254721Semastebool
253254721SemastePOSIXThread::CalculateStopInfo()
254254721Semaste{
255254721Semaste    SetStopInfo (m_stop_info_sp);
256254721Semaste    return true;
257254721Semaste}
258254721Semaste
259254721SemasteUnwind *
260254721SemastePOSIXThread::GetUnwinder()
261254721Semaste{
262254721Semaste    if (m_unwinder_ap.get() == NULL)
263254721Semaste        m_unwinder_ap.reset(new UnwindLLDB(*this));
264254721Semaste
265254721Semaste    return m_unwinder_ap.get();
266254721Semaste}
267254721Semaste
268263368Semaste// Overridden by FreeBSDThread; this is used only on Linux.
269254721Semastevoid
270254721SemastePOSIXThread::WillResume(lldb::StateType resume_state)
271254721Semaste{
272254721Semaste    Log *log (ProcessPOSIXLog::GetLogIfAllCategoriesSet (POSIX_LOG_THREAD));
273254721Semaste    if (log)
274254721Semaste        log->Printf ("POSIXThread::%s (tid = %" PRIi64 ") setting thread resume state to %s", __FUNCTION__, GetID(), StateAsCString(resume_state));
275254721Semaste    // TODO: the line below shouldn't really be done, but
276254721Semaste    // the POSIXThread might rely on this so I will leave this in for now
277254721Semaste    SetResumeState(resume_state);
278254721Semaste}
279254721Semaste
280254721Semastevoid
281254721SemastePOSIXThread::DidStop()
282254721Semaste{
283254721Semaste    // Don't set the thread state to stopped unless we really stopped.
284254721Semaste}
285254721Semaste
286269024Semastebool
287269024SemastePOSIXThread::Resume()
288269024Semaste{
289269024Semaste    lldb::StateType resume_state = GetResumeState();
290269024Semaste    ProcessMonitor &monitor = GetMonitor();
291269024Semaste    bool status;
292269024Semaste
293269024Semaste    Log *log (ProcessPOSIXLog::GetLogIfAllCategoriesSet (POSIX_LOG_THREAD));
294269024Semaste    if (log)
295269024Semaste        log->Printf ("POSIXThread::%s (), resume_state = %s", __FUNCTION__,
296269024Semaste                         StateAsCString(resume_state));
297269024Semaste
298269024Semaste    switch (resume_state)
299269024Semaste    {
300269024Semaste    default:
301269024Semaste        assert(false && "Unexpected state for resume!");
302269024Semaste        status = false;
303269024Semaste        break;
304269024Semaste
305269024Semaste    case lldb::eStateRunning:
306269024Semaste        SetState(resume_state);
307269024Semaste        status = monitor.Resume(GetID(), GetResumeSignal());
308269024Semaste        break;
309269024Semaste
310269024Semaste    case lldb::eStateStepping:
311269024Semaste        SetState(resume_state);
312269024Semaste        status = monitor.SingleStep(GetID(), GetResumeSignal());
313269024Semaste        break;
314269024Semaste    case lldb::eStateStopped:
315269024Semaste    case lldb::eStateSuspended:
316269024Semaste        status = true;
317269024Semaste        break;
318269024Semaste    }
319269024Semaste
320269024Semaste    return status;
321269024Semaste}
322269024Semaste
323254721Semastevoid
324254721SemastePOSIXThread::Notify(const ProcessMessage &message)
325254721Semaste{
326254721Semaste    Log *log (ProcessPOSIXLog::GetLogIfAllCategoriesSet (POSIX_LOG_THREAD));
327254721Semaste    if (log)
328254721Semaste        log->Printf ("POSIXThread::%s () message kind = '%s' for tid %" PRIu64,
329254721Semaste                     __FUNCTION__, message.PrintKind(), GetID());
330254721Semaste
331254721Semaste    switch (message.GetKind())
332254721Semaste    {
333254721Semaste    default:
334254721Semaste        assert(false && "Unexpected message kind!");
335254721Semaste        break;
336254721Semaste
337254721Semaste    case ProcessMessage::eExitMessage:
338254721Semaste        // Nothing to be done.
339254721Semaste        break;
340254721Semaste
341254721Semaste    case ProcessMessage::eLimboMessage:
342254721Semaste        LimboNotify(message);
343254721Semaste        break;
344254721Semaste
345254721Semaste    case ProcessMessage::eSignalMessage:
346254721Semaste        SignalNotify(message);
347254721Semaste        break;
348254721Semaste
349254721Semaste    case ProcessMessage::eSignalDeliveredMessage:
350254721Semaste        SignalDeliveredNotify(message);
351254721Semaste        break;
352254721Semaste
353254721Semaste    case ProcessMessage::eTraceMessage:
354254721Semaste        TraceNotify(message);
355254721Semaste        break;
356254721Semaste
357254721Semaste    case ProcessMessage::eBreakpointMessage:
358254721Semaste        BreakNotify(message);
359254721Semaste        break;
360254721Semaste
361254721Semaste    case ProcessMessage::eWatchpointMessage:
362254721Semaste        WatchNotify(message);
363254721Semaste        break;
364254721Semaste
365254721Semaste    case ProcessMessage::eCrashMessage:
366254721Semaste        CrashNotify(message);
367254721Semaste        break;
368254721Semaste
369254721Semaste    case ProcessMessage::eNewThreadMessage:
370254721Semaste        ThreadNotify(message);
371254721Semaste        break;
372263363Semaste
373263363Semaste    case ProcessMessage::eExecMessage:
374263363Semaste        ExecNotify(message);
375263363Semaste        break;
376254721Semaste    }
377254721Semaste}
378254721Semaste
379254721Semastebool
380254721SemastePOSIXThread::EnableHardwareWatchpoint(Watchpoint *wp)
381254721Semaste{
382254721Semaste    bool wp_set = false;
383254721Semaste    if (wp)
384254721Semaste    {
385254721Semaste        addr_t wp_addr = wp->GetLoadAddress();
386254721Semaste        size_t wp_size = wp->GetByteSize();
387254721Semaste        bool wp_read = wp->WatchpointRead();
388254721Semaste        bool wp_write = wp->WatchpointWrite();
389254721Semaste        uint32_t wp_hw_index = wp->GetHardwareIndex();
390263363Semaste        POSIXBreakpointProtocol* reg_ctx = GetPOSIXBreakpointProtocol();
391254721Semaste        if (reg_ctx)
392254721Semaste            wp_set = reg_ctx->SetHardwareWatchpointWithIndex(wp_addr, wp_size,
393254721Semaste                                                             wp_read, wp_write,
394254721Semaste                                                             wp_hw_index);
395254721Semaste    }
396254721Semaste    return wp_set;
397254721Semaste}
398254721Semaste
399254721Semastebool
400254721SemastePOSIXThread::DisableHardwareWatchpoint(Watchpoint *wp)
401254721Semaste{
402254721Semaste    bool result = false;
403254721Semaste    if (wp)
404254721Semaste    {
405254721Semaste        lldb::RegisterContextSP reg_ctx_sp = GetRegisterContext();
406254721Semaste        if (reg_ctx_sp.get())
407254721Semaste            result = reg_ctx_sp->ClearHardwareWatchpoint(wp->GetHardwareIndex());
408254721Semaste    }
409254721Semaste    return result;
410254721Semaste}
411254721Semaste
412254721Semasteuint32_t
413254721SemastePOSIXThread::NumSupportedHardwareWatchpoints()
414254721Semaste{
415254721Semaste    lldb::RegisterContextSP reg_ctx_sp = GetRegisterContext();
416254721Semaste    if (reg_ctx_sp.get())
417254721Semaste        return reg_ctx_sp->NumSupportedHardwareWatchpoints();
418254721Semaste    return 0;
419254721Semaste}
420254721Semaste
421254721Semasteuint32_t
422254721SemastePOSIXThread::FindVacantWatchpointIndex()
423254721Semaste{
424254721Semaste    uint32_t hw_index = LLDB_INVALID_INDEX32;
425254721Semaste    uint32_t num_hw_wps = NumSupportedHardwareWatchpoints();
426254721Semaste    uint32_t wp_idx;
427263363Semaste    POSIXBreakpointProtocol* reg_ctx = GetPOSIXBreakpointProtocol();
428254721Semaste    if (reg_ctx)
429254721Semaste    {
430254721Semaste        for (wp_idx = 0; wp_idx < num_hw_wps; wp_idx++)
431254721Semaste        {
432254721Semaste            if (reg_ctx->IsWatchpointVacant(wp_idx))
433254721Semaste            {
434254721Semaste                hw_index = wp_idx;
435254721Semaste                break;
436254721Semaste            }
437254721Semaste        }
438254721Semaste    }
439254721Semaste    return hw_index;
440254721Semaste}
441254721Semaste
442254721Semastevoid
443254721SemastePOSIXThread::BreakNotify(const ProcessMessage &message)
444254721Semaste{
445254721Semaste    bool status;
446254721Semaste    Log *log (ProcessPOSIXLog::GetLogIfAllCategoriesSet (POSIX_LOG_THREAD));
447254721Semaste
448254721Semaste    assert(GetRegisterContext());
449263363Semaste    status = GetPOSIXBreakpointProtocol()->UpdateAfterBreakpoint();
450254721Semaste    assert(status && "Breakpoint update failed!");
451254721Semaste
452254721Semaste    // With our register state restored, resolve the breakpoint object
453254721Semaste    // corresponding to our current PC.
454254721Semaste    assert(GetRegisterContext());
455254721Semaste    lldb::addr_t pc = GetRegisterContext()->GetPC();
456254721Semaste    if (log)
457254721Semaste        log->Printf ("POSIXThread::%s () PC=0x%8.8" PRIx64, __FUNCTION__, pc);
458254721Semaste    lldb::BreakpointSiteSP bp_site(GetProcess()->GetBreakpointSiteList().FindByAddress(pc));
459254721Semaste
460254721Semaste    // If the breakpoint is for this thread, then we'll report the hit, but if it is for another thread,
461263363Semaste    // we create a stop reason with should_stop=false.  If there is no breakpoint location, then report
462263363Semaste    // an invalid stop reason. We don't need to worry about stepping over the breakpoint here, that will
463263363Semaste    // be taken care of when the thread resumes and notices that there's a breakpoint under the pc.
464263363Semaste    if (bp_site)
465254721Semaste    {
466254721Semaste        lldb::break_id_t bp_id = bp_site->GetID();
467263363Semaste        if (bp_site->ValidForThisThread(this))
468254721Semaste            SetStopInfo (StopInfo::CreateStopReasonWithBreakpointSiteID(*this, bp_id));
469254721Semaste        else
470254721Semaste        {
471263363Semaste            const bool should_stop = false;
472263363Semaste            SetStopInfo (StopInfo::CreateStopReasonWithBreakpointSiteID(*this, bp_id, should_stop));
473254721Semaste        }
474254721Semaste    }
475263363Semaste    else
476263363Semaste        SetStopInfo(StopInfoSP());
477254721Semaste}
478254721Semaste
479254721Semastevoid
480254721SemastePOSIXThread::WatchNotify(const ProcessMessage &message)
481254721Semaste{
482254721Semaste    Log *log (ProcessPOSIXLog::GetLogIfAllCategoriesSet (POSIX_LOG_THREAD));
483254721Semaste
484254721Semaste    lldb::addr_t halt_addr = message.GetHWAddress();
485254721Semaste    if (log)
486254721Semaste        log->Printf ("POSIXThread::%s () Hardware Watchpoint Address = 0x%8.8"
487254721Semaste                     PRIx64, __FUNCTION__, halt_addr);
488254721Semaste
489263363Semaste    POSIXBreakpointProtocol* reg_ctx = GetPOSIXBreakpointProtocol();
490254721Semaste    if (reg_ctx)
491254721Semaste    {
492254721Semaste        uint32_t num_hw_wps = reg_ctx->NumSupportedHardwareWatchpoints();
493254721Semaste        uint32_t wp_idx;
494254721Semaste        for (wp_idx = 0; wp_idx < num_hw_wps; wp_idx++)
495254721Semaste        {
496254721Semaste            if (reg_ctx->IsWatchpointHit(wp_idx))
497254721Semaste            {
498254721Semaste                // Clear the watchpoint hit here
499254721Semaste                reg_ctx->ClearWatchpointHits();
500254721Semaste                break;
501254721Semaste            }
502254721Semaste        }
503254721Semaste
504254721Semaste        if (wp_idx == num_hw_wps)
505254721Semaste            return;
506254721Semaste
507254721Semaste        Target &target = GetProcess()->GetTarget();
508254721Semaste        lldb::addr_t wp_monitor_addr = reg_ctx->GetWatchpointAddress(wp_idx);
509254721Semaste        const WatchpointList &wp_list = target.GetWatchpointList();
510254721Semaste        lldb::WatchpointSP wp_sp = wp_list.FindByAddress(wp_monitor_addr);
511254721Semaste
512254721Semaste        assert(wp_sp.get() && "No watchpoint found");
513254721Semaste        SetStopInfo (StopInfo::CreateStopReasonWithWatchpointID(*this,
514254721Semaste                                                                wp_sp->GetID()));
515254721Semaste    }
516254721Semaste}
517254721Semaste
518254721Semastevoid
519254721SemastePOSIXThread::TraceNotify(const ProcessMessage &message)
520254721Semaste{
521269024Semaste    POSIXBreakpointProtocol* reg_ctx = GetPOSIXBreakpointProtocol();
522269024Semaste    if (reg_ctx)
523269024Semaste    {
524269024Semaste        uint32_t num_hw_wps = reg_ctx->NumSupportedHardwareWatchpoints();
525269024Semaste        uint32_t wp_idx;
526269024Semaste        for (wp_idx = 0; wp_idx < num_hw_wps; wp_idx++)
527269024Semaste        {
528269024Semaste            if (reg_ctx->IsWatchpointHit(wp_idx))
529269024Semaste            {
530269024Semaste                WatchNotify(message);
531269024Semaste                return;
532269024Semaste            }
533269024Semaste        }
534269024Semaste    }
535269024Semaste
536254721Semaste    SetStopInfo (StopInfo::CreateStopReasonToTrace(*this));
537254721Semaste}
538254721Semaste
539254721Semastevoid
540254721SemastePOSIXThread::LimboNotify(const ProcessMessage &message)
541254721Semaste{
542254721Semaste    SetStopInfo (lldb::StopInfoSP(new POSIXLimboStopInfo(*this)));
543254721Semaste}
544254721Semaste
545254721Semastevoid
546254721SemastePOSIXThread::SignalNotify(const ProcessMessage &message)
547254721Semaste{
548254721Semaste    int signo = message.GetSignal();
549254721Semaste
550254721Semaste    SetStopInfo (StopInfo::CreateStopReasonWithSignal(*this, signo));
551254721Semaste    SetResumeSignal(signo);
552254721Semaste}
553254721Semaste
554254721Semastevoid
555254721SemastePOSIXThread::SignalDeliveredNotify(const ProcessMessage &message)
556254721Semaste{
557254721Semaste    int signo = message.GetSignal();
558254721Semaste
559254721Semaste    SetStopInfo (StopInfo::CreateStopReasonWithSignal(*this, signo));
560254721Semaste    SetResumeSignal(signo);
561254721Semaste}
562254721Semaste
563254721Semastevoid
564254721SemastePOSIXThread::CrashNotify(const ProcessMessage &message)
565254721Semaste{
566254721Semaste    // FIXME: Update stop reason as per bugzilla 14598
567254721Semaste    int signo = message.GetSignal();
568254721Semaste
569254721Semaste    assert(message.GetKind() == ProcessMessage::eCrashMessage);
570254721Semaste
571254721Semaste    Log *log (ProcessPOSIXLog::GetLogIfAllCategoriesSet (POSIX_LOG_THREAD));
572254721Semaste    if (log)
573254721Semaste        log->Printf ("POSIXThread::%s () signo = %i, reason = '%s'",
574254721Semaste                     __FUNCTION__, signo, message.PrintCrashReason());
575254721Semaste
576254721Semaste    SetStopInfo (lldb::StopInfoSP(new POSIXCrashStopInfo(*this, signo,
577254721Semaste                                                         message.GetCrashReason(),
578254721Semaste                                                         message.GetFaultAddress())));
579254721Semaste    SetResumeSignal(signo);
580254721Semaste}
581254721Semaste
582254721Semastevoid
583254721SemastePOSIXThread::ThreadNotify(const ProcessMessage &message)
584254721Semaste{
585254721Semaste    SetStopInfo (lldb::StopInfoSP(new POSIXNewThreadStopInfo(*this)));
586254721Semaste}
587254721Semaste
588254721Semasteunsigned
589254721SemastePOSIXThread::GetRegisterIndexFromOffset(unsigned offset)
590254721Semaste{
591254721Semaste    unsigned reg = LLDB_INVALID_REGNUM;
592254721Semaste    ArchSpec arch = Host::GetArchitecture();
593254721Semaste
594254721Semaste    switch (arch.GetCore())
595254721Semaste    {
596254721Semaste    default:
597254721Semaste        llvm_unreachable("CPU type not supported!");
598254721Semaste        break;
599254721Semaste
600263363Semaste    case ArchSpec::eCore_mips64:
601254721Semaste    case ArchSpec::eCore_x86_32_i386:
602254721Semaste    case ArchSpec::eCore_x86_32_i486:
603254721Semaste    case ArchSpec::eCore_x86_32_i486sx:
604254721Semaste    case ArchSpec::eCore_x86_64_x86_64:
605254721Semaste        {
606263363Semaste            POSIXBreakpointProtocol* reg_ctx = GetPOSIXBreakpointProtocol();
607263363Semaste            reg = reg_ctx->GetRegisterIndexFromOffset(offset);
608254721Semaste        }
609254721Semaste        break;
610254721Semaste    }
611254721Semaste    return reg;
612254721Semaste}
613254721Semaste
614263363Semastevoid
615263363SemastePOSIXThread::ExecNotify(const ProcessMessage &message)
616263363Semaste{
617263363Semaste    SetStopInfo (StopInfo::CreateStopReasonWithExec(*this));
618263363Semaste}
619263363Semaste
620254721Semasteconst char *
621254721SemastePOSIXThread::GetRegisterName(unsigned reg)
622254721Semaste{
623254721Semaste    const char * name = nullptr;
624254721Semaste    ArchSpec arch = Host::GetArchitecture();
625254721Semaste
626254721Semaste    switch (arch.GetCore())
627254721Semaste    {
628254721Semaste    default:
629254721Semaste        assert(false && "CPU type not supported!");
630254721Semaste        break;
631254721Semaste
632263363Semaste    case ArchSpec::eCore_mips64:
633254721Semaste    case ArchSpec::eCore_x86_32_i386:
634254721Semaste    case ArchSpec::eCore_x86_32_i486:
635254721Semaste    case ArchSpec::eCore_x86_32_i486sx:
636254721Semaste    case ArchSpec::eCore_x86_64_x86_64:
637254721Semaste        name = GetRegisterContext()->GetRegisterName(reg);
638254721Semaste        break;
639254721Semaste    }
640254721Semaste    return name;
641254721Semaste}
642254721Semaste
643254721Semasteconst char *
644254721SemastePOSIXThread::GetRegisterNameFromOffset(unsigned offset)
645254721Semaste{
646254721Semaste    return GetRegisterName(GetRegisterIndexFromOffset(offset));
647254721Semaste}
648254721Semaste
649