1254721Semaste//===-- WatchpointOptions.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// C Includes 11254721Semaste// C++ Includes 12254721Semaste// Other libraries and framework includes 13254721Semaste// Project includes 14296417Sdim#include "lldb/Breakpoint/WatchpointOptions.h" 15296417Sdim 16254721Semaste#include "lldb/Core/Stream.h" 17254721Semaste#include "lldb/Core/StringList.h" 18254721Semaste#include "lldb/Core/Value.h" 19254721Semaste#include "lldb/Breakpoint/StoppointCallbackContext.h" 20254721Semaste#include "lldb/Target/Process.h" 21254721Semaste#include "lldb/Target/Target.h" 22254721Semaste#include "lldb/Target/ThreadSpec.h" 23254721Semaste 24254721Semasteusing namespace lldb; 25254721Semasteusing namespace lldb_private; 26254721Semaste 27254721Semastebool 28254721SemasteWatchpointOptions::NullCallback (void *baton, StoppointCallbackContext *context, lldb::user_id_t watch_id) 29254721Semaste{ 30254721Semaste return true; 31254721Semaste} 32254721Semaste 33254721Semaste//---------------------------------------------------------------------- 34254721Semaste// WatchpointOptions constructor 35254721Semaste//---------------------------------------------------------------------- 36254721SemasteWatchpointOptions::WatchpointOptions() : 37254721Semaste m_callback (WatchpointOptions::NullCallback), 38254721Semaste m_callback_baton_sp (), 39254721Semaste m_callback_is_synchronous (false), 40254721Semaste m_thread_spec_ap () 41254721Semaste{ 42254721Semaste} 43254721Semaste 44254721Semaste//---------------------------------------------------------------------- 45254721Semaste// WatchpointOptions copy constructor 46254721Semaste//---------------------------------------------------------------------- 47254721SemasteWatchpointOptions::WatchpointOptions(const WatchpointOptions& rhs) : 48254721Semaste m_callback (rhs.m_callback), 49254721Semaste m_callback_baton_sp (rhs.m_callback_baton_sp), 50254721Semaste m_callback_is_synchronous (rhs.m_callback_is_synchronous), 51254721Semaste m_thread_spec_ap () 52254721Semaste{ 53296417Sdim if (rhs.m_thread_spec_ap.get() != nullptr) 54254721Semaste m_thread_spec_ap.reset (new ThreadSpec(*rhs.m_thread_spec_ap.get())); 55254721Semaste} 56254721Semaste 57254721Semaste//---------------------------------------------------------------------- 58254721Semaste// WatchpointOptions assignment operator 59254721Semaste//---------------------------------------------------------------------- 60254721Semasteconst WatchpointOptions& 61254721SemasteWatchpointOptions::operator=(const WatchpointOptions& rhs) 62254721Semaste{ 63254721Semaste m_callback = rhs.m_callback; 64254721Semaste m_callback_baton_sp = rhs.m_callback_baton_sp; 65254721Semaste m_callback_is_synchronous = rhs.m_callback_is_synchronous; 66296417Sdim if (rhs.m_thread_spec_ap.get() != nullptr) 67254721Semaste m_thread_spec_ap.reset(new ThreadSpec(*rhs.m_thread_spec_ap.get())); 68254721Semaste return *this; 69254721Semaste} 70254721Semaste 71254721SemasteWatchpointOptions * 72254721SemasteWatchpointOptions::CopyOptionsNoCallback (WatchpointOptions &orig) 73254721Semaste{ 74254721Semaste WatchpointHitCallback orig_callback = orig.m_callback; 75254721Semaste lldb::BatonSP orig_callback_baton_sp = orig.m_callback_baton_sp; 76254721Semaste bool orig_is_sync = orig.m_callback_is_synchronous; 77254721Semaste 78254721Semaste orig.ClearCallback(); 79254721Semaste WatchpointOptions *ret_val = new WatchpointOptions(orig); 80254721Semaste 81254721Semaste orig.SetCallback (orig_callback, orig_callback_baton_sp, orig_is_sync); 82254721Semaste 83254721Semaste return ret_val; 84254721Semaste} 85254721Semaste 86254721Semaste//---------------------------------------------------------------------- 87254721Semaste// Destructor 88254721Semaste//---------------------------------------------------------------------- 89296417SdimWatchpointOptions::~WatchpointOptions() = default; 90254721Semaste 91254721Semaste//------------------------------------------------------------------ 92254721Semaste// Callbacks 93254721Semaste//------------------------------------------------------------------ 94254721Semastevoid 95254721SemasteWatchpointOptions::SetCallback (WatchpointHitCallback callback, const BatonSP &callback_baton_sp, bool callback_is_synchronous) 96254721Semaste{ 97254721Semaste m_callback_is_synchronous = callback_is_synchronous; 98254721Semaste m_callback = callback; 99254721Semaste m_callback_baton_sp = callback_baton_sp; 100254721Semaste} 101254721Semaste 102254721Semastevoid 103254721SemasteWatchpointOptions::ClearCallback () 104254721Semaste{ 105254721Semaste m_callback = WatchpointOptions::NullCallback; 106254721Semaste m_callback_is_synchronous = false; 107254721Semaste m_callback_baton_sp.reset(); 108254721Semaste} 109254721Semaste 110254721SemasteBaton * 111254721SemasteWatchpointOptions::GetBaton () 112254721Semaste{ 113254721Semaste return m_callback_baton_sp.get(); 114254721Semaste} 115254721Semaste 116254721Semasteconst Baton * 117254721SemasteWatchpointOptions::GetBaton () const 118254721Semaste{ 119254721Semaste return m_callback_baton_sp.get(); 120254721Semaste} 121254721Semaste 122254721Semastebool 123254721SemasteWatchpointOptions::InvokeCallback (StoppointCallbackContext *context, 124254721Semaste lldb::user_id_t watch_id) 125254721Semaste{ 126254721Semaste if (m_callback && context->is_synchronous == IsCallbackSynchronous()) 127254721Semaste { 128296417Sdim return m_callback(m_callback_baton_sp ? m_callback_baton_sp->m_data : nullptr, 129296417Sdim context, 130296417Sdim watch_id); 131254721Semaste } 132254721Semaste else 133254721Semaste return true; 134254721Semaste} 135254721Semaste 136254721Semastebool 137254721SemasteWatchpointOptions::HasCallback () 138254721Semaste{ 139254721Semaste return m_callback != WatchpointOptions::NullCallback; 140254721Semaste} 141254721Semaste 142254721Semasteconst ThreadSpec * 143254721SemasteWatchpointOptions::GetThreadSpecNoCreate () const 144254721Semaste{ 145254721Semaste return m_thread_spec_ap.get(); 146254721Semaste} 147254721Semaste 148254721SemasteThreadSpec * 149254721SemasteWatchpointOptions::GetThreadSpec () 150254721Semaste{ 151296417Sdim if (m_thread_spec_ap.get() == nullptr) 152254721Semaste m_thread_spec_ap.reset (new ThreadSpec()); 153254721Semaste 154254721Semaste return m_thread_spec_ap.get(); 155254721Semaste} 156254721Semaste 157254721Semastevoid 158254721SemasteWatchpointOptions::SetThreadID (lldb::tid_t thread_id) 159254721Semaste{ 160254721Semaste GetThreadSpec()->SetTID(thread_id); 161254721Semaste} 162254721Semaste 163254721Semastevoid 164254721SemasteWatchpointOptions::GetCallbackDescription (Stream *s, lldb::DescriptionLevel level) const 165254721Semaste{ 166254721Semaste if (m_callback_baton_sp.get()) 167254721Semaste { 168254721Semaste s->EOL(); 169254721Semaste m_callback_baton_sp->GetDescription (s, level); 170254721Semaste } 171254721Semaste} 172296417Sdim 173254721Semastevoid 174254721SemasteWatchpointOptions::GetDescription (Stream *s, lldb::DescriptionLevel level) const 175254721Semaste{ 176254721Semaste // Figure out if there are any options not at their default value, and only print 177254721Semaste // anything if there are: 178254721Semaste 179296417Sdim if ((GetThreadSpecNoCreate() != nullptr && GetThreadSpecNoCreate()->HasSpecification ())) 180254721Semaste { 181254721Semaste if (level == lldb::eDescriptionLevelVerbose) 182254721Semaste { 183254721Semaste s->EOL (); 184254721Semaste s->IndentMore(); 185254721Semaste s->Indent(); 186254721Semaste s->PutCString("Watchpoint Options:\n"); 187254721Semaste s->IndentMore(); 188254721Semaste s->Indent(); 189254721Semaste } 190254721Semaste else 191254721Semaste s->PutCString(" Options: "); 192254721Semaste 193254721Semaste if (m_thread_spec_ap.get()) 194254721Semaste m_thread_spec_ap->GetDescription (s, level); 195254721Semaste else if (level == eDescriptionLevelBrief) 196254721Semaste s->PutCString ("thread spec: no "); 197254721Semaste if (level == lldb::eDescriptionLevelFull) 198254721Semaste { 199254721Semaste s->IndentLess(); 200254721Semaste s->IndentMore(); 201254721Semaste } 202254721Semaste } 203254721Semaste 204254721Semaste GetCallbackDescription(s, level); 205254721Semaste} 206254721Semaste 207254721Semastevoid 208254721SemasteWatchpointOptions::CommandBaton::GetDescription (Stream *s, lldb::DescriptionLevel level) const 209254721Semaste{ 210254721Semaste CommandData *data = (CommandData *)m_data; 211254721Semaste 212254721Semaste if (level == eDescriptionLevelBrief) 213254721Semaste { 214254721Semaste s->Printf (", commands = %s", (data && data->user_source.GetSize() > 0) ? "yes" : "no"); 215254721Semaste return; 216254721Semaste } 217254721Semaste 218254721Semaste s->IndentMore (); 219254721Semaste s->Indent("watchpoint commands:\n"); 220254721Semaste 221254721Semaste s->IndentMore (); 222254721Semaste if (data && data->user_source.GetSize() > 0) 223254721Semaste { 224254721Semaste const size_t num_strings = data->user_source.GetSize(); 225254721Semaste for (size_t i = 0; i < num_strings; ++i) 226254721Semaste { 227254721Semaste s->Indent(data->user_source.GetStringAtIndex(i)); 228254721Semaste s->EOL(); 229254721Semaste } 230254721Semaste } 231254721Semaste else 232254721Semaste { 233254721Semaste s->PutCString ("No commands.\n"); 234254721Semaste } 235254721Semaste s->IndentLess (); 236254721Semaste s->IndentLess (); 237254721Semaste} 238