xref: /llvm-project/lldb/source/Target/ThreadPlanCallFunction.cpp (revision 956761adb0ffdf6be50018aea1fb804ecb2da9f2)
1 //===-- ThreadPlanCallFunction.cpp ------------------------------*- C++ -*-===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8 
9 #include "lldb/Target/ThreadPlanCallFunction.h"
10 #include "lldb/Breakpoint/Breakpoint.h"
11 #include "lldb/Breakpoint/BreakpointLocation.h"
12 #include "lldb/Core/Address.h"
13 #include "lldb/Core/DumpRegisterValue.h"
14 #include "lldb/Core/Module.h"
15 #include "lldb/Symbol/ObjectFile.h"
16 #include "lldb/Target/ABI.h"
17 #include "lldb/Target/LanguageRuntime.h"
18 #include "lldb/Target/Process.h"
19 #include "lldb/Target/RegisterContext.h"
20 #include "lldb/Target/StopInfo.h"
21 #include "lldb/Target/Target.h"
22 #include "lldb/Target/Thread.h"
23 #include "lldb/Target/ThreadPlanRunToAddress.h"
24 #include "lldb/Utility/Log.h"
25 #include "lldb/Utility/Stream.h"
26 
27 #include <memory>
28 
29 using namespace lldb;
30 using namespace lldb_private;
31 
32 // ThreadPlanCallFunction: Plan to call a single function
33 bool ThreadPlanCallFunction::ConstructorSetup(
34     Thread &thread, ABI *&abi, lldb::addr_t &start_load_addr,
35     lldb::addr_t &function_load_addr) {
36   SetIsMasterPlan(true);
37   SetOkayToDiscard(false);
38   SetPrivate(true);
39 
40   ProcessSP process_sp(thread.GetProcess());
41   if (!process_sp)
42     return false;
43 
44   abi = process_sp->GetABI().get();
45 
46   if (!abi)
47     return false;
48 
49   Log *log(lldb_private::GetLogIfAnyCategoriesSet(LIBLLDB_LOG_STEP));
50 
51   SetBreakpoints();
52 
53   m_function_sp = thread.GetRegisterContext()->GetSP() - abi->GetRedZoneSize();
54   // If we can't read memory at the point of the process where we are planning
55   // to put our function, we're not going to get any further...
56   Status error;
57   process_sp->ReadUnsignedIntegerFromMemory(m_function_sp, 4, 0, error);
58   if (!error.Success()) {
59     m_constructor_errors.Printf(
60         "Trying to put the stack in unreadable memory at: 0x%" PRIx64 ".",
61         m_function_sp);
62     if (log)
63       log->Printf("ThreadPlanCallFunction(%p): %s.", static_cast<void *>(this),
64                   m_constructor_errors.GetData());
65     return false;
66   }
67 
68   m_start_addr = GetTarget().GetEntryPointAddress(error);
69 
70   if (log && error.Fail()) {
71     m_constructor_errors.Printf("%s", error.AsCString());
72     log->Printf("ThreadPlanCallFunction(%p): %s.", static_cast<void *>(this),
73                  m_constructor_errors.GetData());
74     return false;
75   }
76 
77   if (!m_start_addr.IsValid()) {
78     return false;
79   }
80 
81   start_load_addr = m_start_addr.GetLoadAddress(&GetTarget());
82 
83   // Checkpoint the thread state so we can restore it later.
84   if (log && log->GetVerbose())
85     ReportRegisterState("About to checkpoint thread before function call.  "
86                         "Original register state was:");
87 
88   if (!thread.CheckpointThreadState(m_stored_thread_state)) {
89     m_constructor_errors.Printf("Setting up ThreadPlanCallFunction, failed to "
90                                 "checkpoint thread state.");
91     if (log)
92       log->Printf("ThreadPlanCallFunction(%p): %s.", static_cast<void *>(this),
93                   m_constructor_errors.GetData());
94     return false;
95   }
96   function_load_addr = m_function_addr.GetLoadAddress(&GetTarget());
97 
98   return true;
99 }
100 
101 ThreadPlanCallFunction::ThreadPlanCallFunction(
102     Thread &thread, const Address &function, const CompilerType &return_type,
103     llvm::ArrayRef<addr_t> args, const EvaluateExpressionOptions &options)
104     : ThreadPlan(ThreadPlan::eKindCallFunction, "Call function plan", thread,
105                  eVoteNoOpinion, eVoteNoOpinion),
106       m_valid(false), m_stop_other_threads(options.GetStopOthers()),
107       m_unwind_on_error(options.DoesUnwindOnError()),
108       m_ignore_breakpoints(options.DoesIgnoreBreakpoints()),
109       m_debug_execution(options.GetDebug()),
110       m_trap_exceptions(options.GetTrapExceptions()), m_function_addr(function),
111       m_function_sp(0), m_takedown_done(false),
112       m_should_clear_objc_exception_bp(false),
113       m_should_clear_cxx_exception_bp(false),
114       m_stop_address(LLDB_INVALID_ADDRESS), m_return_type(return_type) {
115   lldb::addr_t start_load_addr = LLDB_INVALID_ADDRESS;
116   lldb::addr_t function_load_addr = LLDB_INVALID_ADDRESS;
117   ABI *abi = nullptr;
118 
119   if (!ConstructorSetup(thread, abi, start_load_addr, function_load_addr))
120     return;
121 
122   if (!abi->PrepareTrivialCall(thread, m_function_sp, function_load_addr,
123                                start_load_addr, args))
124     return;
125 
126   ReportRegisterState("Function call was set up.  Register state was:");
127 
128   m_valid = true;
129 }
130 
131 ThreadPlanCallFunction::ThreadPlanCallFunction(
132     Thread &thread, const Address &function,
133     const EvaluateExpressionOptions &options)
134     : ThreadPlan(ThreadPlan::eKindCallFunction, "Call function plan", thread,
135                  eVoteNoOpinion, eVoteNoOpinion),
136       m_valid(false), m_stop_other_threads(options.GetStopOthers()),
137       m_unwind_on_error(options.DoesUnwindOnError()),
138       m_ignore_breakpoints(options.DoesIgnoreBreakpoints()),
139       m_debug_execution(options.GetDebug()),
140       m_trap_exceptions(options.GetTrapExceptions()), m_function_addr(function),
141       m_function_sp(0), m_takedown_done(false),
142       m_should_clear_objc_exception_bp(false),
143       m_should_clear_cxx_exception_bp(false),
144       m_stop_address(LLDB_INVALID_ADDRESS), m_return_type(CompilerType()) {}
145 
146 ThreadPlanCallFunction::~ThreadPlanCallFunction() {
147   DoTakedown(PlanSucceeded());
148 }
149 
150 void ThreadPlanCallFunction::ReportRegisterState(const char *message) {
151   Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_STEP));
152   if (log && log->GetVerbose()) {
153     StreamString strm;
154     RegisterContext *reg_ctx = m_thread.GetRegisterContext().get();
155 
156     log->PutCString(message);
157 
158     RegisterValue reg_value;
159 
160     for (uint32_t reg_idx = 0, num_registers = reg_ctx->GetRegisterCount();
161          reg_idx < num_registers; ++reg_idx) {
162       const RegisterInfo *reg_info = reg_ctx->GetRegisterInfoAtIndex(reg_idx);
163       if (reg_ctx->ReadRegister(reg_info, reg_value)) {
164         DumpRegisterValue(reg_value, &strm, reg_info, true, false,
165                           eFormatDefault);
166         strm.EOL();
167       }
168     }
169     log->PutString(strm.GetString());
170   }
171 }
172 
173 void ThreadPlanCallFunction::DoTakedown(bool success) {
174   Log *log(lldb_private::GetLogIfAnyCategoriesSet(LIBLLDB_LOG_STEP));
175 
176   if (!m_valid) {
177     // Don't call DoTakedown if we were never valid to begin with.
178     if (log)
179       log->Printf("ThreadPlanCallFunction(%p): Log called on "
180                   "ThreadPlanCallFunction that was never valid.",
181                   static_cast<void *>(this));
182     return;
183   }
184 
185   if (!m_takedown_done) {
186     if (success) {
187       SetReturnValue();
188     }
189     if (log)
190       log->Printf("ThreadPlanCallFunction(%p): DoTakedown called for thread "
191                   "0x%4.4" PRIx64 ", m_valid: %d complete: %d.\n",
192                   static_cast<void *>(this), m_thread.GetID(), m_valid,
193                   IsPlanComplete());
194     m_takedown_done = true;
195     m_stop_address =
196         m_thread.GetStackFrameAtIndex(0)->GetRegisterContext()->GetPC();
197     m_real_stop_info_sp = GetPrivateStopInfo();
198     if (!m_thread.RestoreRegisterStateFromCheckpoint(m_stored_thread_state)) {
199       if (log)
200         log->Printf("ThreadPlanCallFunction(%p): DoTakedown failed to restore "
201                     "register state",
202                     static_cast<void *>(this));
203     }
204     SetPlanComplete(success);
205     ClearBreakpoints();
206     if (log && log->GetVerbose())
207       ReportRegisterState("Restoring thread state after function call.  "
208                           "Restored register state:");
209   } else {
210     if (log)
211       log->Printf("ThreadPlanCallFunction(%p): DoTakedown called as no-op for "
212                   "thread 0x%4.4" PRIx64 ", m_valid: %d complete: %d.\n",
213                   static_cast<void *>(this), m_thread.GetID(), m_valid,
214                   IsPlanComplete());
215   }
216 }
217 
218 void ThreadPlanCallFunction::WillPop() { DoTakedown(PlanSucceeded()); }
219 
220 void ThreadPlanCallFunction::GetDescription(Stream *s, DescriptionLevel level) {
221   if (level == eDescriptionLevelBrief) {
222     s->Printf("Function call thread plan");
223   } else {
224     TargetSP target_sp(m_thread.CalculateTarget());
225     s->Printf("Thread plan to call 0x%" PRIx64,
226               m_function_addr.GetLoadAddress(target_sp.get()));
227   }
228 }
229 
230 bool ThreadPlanCallFunction::ValidatePlan(Stream *error) {
231   if (!m_valid) {
232     if (error) {
233       if (m_constructor_errors.GetSize() > 0)
234         error->PutCString(m_constructor_errors.GetString());
235       else
236         error->PutCString("Unknown error");
237     }
238     return false;
239   }
240 
241   return true;
242 }
243 
244 Vote ThreadPlanCallFunction::ShouldReportStop(Event *event_ptr) {
245   if (m_takedown_done || IsPlanComplete())
246     return eVoteYes;
247   else
248     return ThreadPlan::ShouldReportStop(event_ptr);
249 }
250 
251 bool ThreadPlanCallFunction::DoPlanExplainsStop(Event *event_ptr) {
252   Log *log(lldb_private::GetLogIfAnyCategoriesSet(LIBLLDB_LOG_STEP |
253                                                   LIBLLDB_LOG_PROCESS));
254   m_real_stop_info_sp = GetPrivateStopInfo();
255 
256   // If our subplan knows why we stopped, even if it's done (which would
257   // forward the question to us) we answer yes.
258   if (m_subplan_sp && m_subplan_sp->PlanExplainsStop(event_ptr)) {
259     SetPlanComplete();
260     return true;
261   }
262 
263   // Check if the breakpoint is one of ours.
264 
265   StopReason stop_reason;
266   if (!m_real_stop_info_sp)
267     stop_reason = eStopReasonNone;
268   else
269     stop_reason = m_real_stop_info_sp->GetStopReason();
270   if (log)
271     log->Printf(
272         "ThreadPlanCallFunction::PlanExplainsStop: Got stop reason - %s.",
273         Thread::StopReasonAsCString(stop_reason));
274 
275   if (stop_reason == eStopReasonBreakpoint && BreakpointsExplainStop())
276     return true;
277 
278   // One more quirk here.  If this event was from Halt interrupting the target,
279   // then we should not consider ourselves complete.  Return true to
280   // acknowledge the stop.
281   if (Process::ProcessEventData::GetInterruptedFromEvent(event_ptr)) {
282     if (log)
283       log->Printf("ThreadPlanCallFunction::PlanExplainsStop: The event is an "
284                   "Interrupt, returning true.");
285     return true;
286   }
287   // We control breakpoints separately from other "stop reasons."  So first,
288   // check the case where we stopped for an internal breakpoint, in that case,
289   // continue on. If it is not an internal breakpoint, consult
290   // m_ignore_breakpoints.
291 
292   if (stop_reason == eStopReasonBreakpoint) {
293     ProcessSP process_sp(m_thread.CalculateProcess());
294     uint64_t break_site_id = m_real_stop_info_sp->GetValue();
295     BreakpointSiteSP bp_site_sp;
296     if (process_sp)
297       bp_site_sp = process_sp->GetBreakpointSiteList().FindByID(break_site_id);
298     if (bp_site_sp) {
299       uint32_t num_owners = bp_site_sp->GetNumberOfOwners();
300       bool is_internal = true;
301       for (uint32_t i = 0; i < num_owners; i++) {
302         Breakpoint &bp = bp_site_sp->GetOwnerAtIndex(i)->GetBreakpoint();
303         if (log)
304           log->Printf("ThreadPlanCallFunction::PlanExplainsStop: hit "
305                       "breakpoint %d while calling function",
306                       bp.GetID());
307 
308         if (!bp.IsInternal()) {
309           is_internal = false;
310           break;
311         }
312       }
313       if (is_internal) {
314         if (log)
315           log->Printf("ThreadPlanCallFunction::PlanExplainsStop hit an "
316                       "internal breakpoint, not stopping.");
317         return false;
318       }
319     }
320 
321     if (m_ignore_breakpoints) {
322       if (log)
323         log->Printf("ThreadPlanCallFunction::PlanExplainsStop: we are ignoring "
324                     "breakpoints, overriding breakpoint stop info ShouldStop, "
325                     "returning true");
326       m_real_stop_info_sp->OverrideShouldStop(false);
327       return true;
328     } else {
329       if (log)
330         log->Printf("ThreadPlanCallFunction::PlanExplainsStop: we are not "
331                     "ignoring breakpoints, overriding breakpoint stop info "
332                     "ShouldStop, returning true");
333       m_real_stop_info_sp->OverrideShouldStop(true);
334       return false;
335     }
336   } else if (!m_unwind_on_error) {
337     // If we don't want to discard this plan, than any stop we don't understand
338     // should be propagated up the stack.
339     return false;
340   } else {
341     // If the subplan is running, any crashes are attributable to us. If we
342     // want to discard the plan, then we say we explain the stop but if we are
343     // going to be discarded, let whoever is above us explain the stop. But
344     // don't discard the plan if the stop would restart itself (for instance if
345     // it is a signal that is set not to stop.  Check that here first.  We just
346     // say we explain the stop but aren't done and everything will continue on
347     // from there.
348 
349     if (m_real_stop_info_sp &&
350         m_real_stop_info_sp->ShouldStopSynchronous(event_ptr)) {
351       SetPlanComplete(false);
352       return m_subplan_sp ? m_unwind_on_error : false;
353     } else
354       return true;
355   }
356 }
357 
358 bool ThreadPlanCallFunction::ShouldStop(Event *event_ptr) {
359   // We do some computation in DoPlanExplainsStop that may or may not set the
360   // plan as complete. We need to do that here to make sure our state is
361   // correct.
362   DoPlanExplainsStop(event_ptr);
363 
364   if (IsPlanComplete()) {
365     ReportRegisterState("Function completed.  Register state was:");
366     return true;
367   } else {
368     return false;
369   }
370 }
371 
372 bool ThreadPlanCallFunction::StopOthers() { return m_stop_other_threads; }
373 
374 StateType ThreadPlanCallFunction::GetPlanRunState() { return eStateRunning; }
375 
376 void ThreadPlanCallFunction::DidPush() {
377   //#define SINGLE_STEP_EXPRESSIONS
378 
379   // Now set the thread state to "no reason" so we don't run with whatever
380   // signal was outstanding... Wait till the plan is pushed so we aren't
381   // changing the stop info till we're about to run.
382 
383   GetThread().SetStopInfoToNothing();
384 
385 #ifndef SINGLE_STEP_EXPRESSIONS
386   m_subplan_sp = std::make_shared<ThreadPlanRunToAddress>(
387       m_thread, m_start_addr, m_stop_other_threads);
388 
389   m_thread.QueueThreadPlan(m_subplan_sp, false);
390   m_subplan_sp->SetPrivate(true);
391 #endif
392 }
393 
394 bool ThreadPlanCallFunction::WillStop() { return true; }
395 
396 bool ThreadPlanCallFunction::MischiefManaged() {
397   Log *log(lldb_private::GetLogIfAllCategoriesSet(LIBLLDB_LOG_STEP));
398 
399   if (IsPlanComplete()) {
400     if (log)
401       log->Printf("ThreadPlanCallFunction(%p): Completed call function plan.",
402                   static_cast<void *>(this));
403 
404     ThreadPlan::MischiefManaged();
405     return true;
406   } else {
407     return false;
408   }
409 }
410 
411 void ThreadPlanCallFunction::SetBreakpoints() {
412   ProcessSP process_sp(m_thread.CalculateProcess());
413   if (m_trap_exceptions && process_sp) {
414     m_cxx_language_runtime =
415         process_sp->GetLanguageRuntime(eLanguageTypeC_plus_plus);
416     m_objc_language_runtime = process_sp->GetLanguageRuntime(eLanguageTypeObjC);
417 
418     if (m_cxx_language_runtime) {
419       m_should_clear_cxx_exception_bp =
420           !m_cxx_language_runtime->ExceptionBreakpointsAreSet();
421       m_cxx_language_runtime->SetExceptionBreakpoints();
422     }
423     if (m_objc_language_runtime) {
424       m_should_clear_objc_exception_bp =
425           !m_objc_language_runtime->ExceptionBreakpointsAreSet();
426       m_objc_language_runtime->SetExceptionBreakpoints();
427     }
428   }
429 }
430 
431 void ThreadPlanCallFunction::ClearBreakpoints() {
432   if (m_trap_exceptions) {
433     if (m_cxx_language_runtime && m_should_clear_cxx_exception_bp)
434       m_cxx_language_runtime->ClearExceptionBreakpoints();
435     if (m_objc_language_runtime && m_should_clear_objc_exception_bp)
436       m_objc_language_runtime->ClearExceptionBreakpoints();
437   }
438 }
439 
440 bool ThreadPlanCallFunction::BreakpointsExplainStop() {
441   StopInfoSP stop_info_sp = GetPrivateStopInfo();
442 
443   if (m_trap_exceptions) {
444     if ((m_cxx_language_runtime &&
445          m_cxx_language_runtime->ExceptionBreakpointsExplainStop(
446              stop_info_sp)) ||
447         (m_objc_language_runtime &&
448          m_objc_language_runtime->ExceptionBreakpointsExplainStop(
449              stop_info_sp))) {
450       Log *log(lldb_private::GetLogIfAnyCategoriesSet(LIBLLDB_LOG_STEP));
451       if (log)
452         log->Printf("ThreadPlanCallFunction::BreakpointsExplainStop - Hit an "
453                     "exception breakpoint, setting plan complete.");
454 
455       SetPlanComplete(false);
456 
457       // If the user has set the ObjC language breakpoint, it would normally
458       // get priority over our internal catcher breakpoint, but in this case we
459       // can't let that happen, so force the ShouldStop here.
460       stop_info_sp->OverrideShouldStop(true);
461       return true;
462     }
463   }
464 
465   return false;
466 }
467 
468 void ThreadPlanCallFunction::SetStopOthers(bool new_value) {
469   m_subplan_sp->SetStopOthers(new_value);
470 }
471 
472 bool ThreadPlanCallFunction::RestoreThreadState() {
473   return GetThread().RestoreThreadStateFromCheckpoint(m_stored_thread_state);
474 }
475 
476 void ThreadPlanCallFunction::SetReturnValue() {
477   ProcessSP process_sp(m_thread.GetProcess());
478   const ABI *abi = process_sp ? process_sp->GetABI().get() : nullptr;
479   if (abi && m_return_type.IsValid()) {
480     const bool persistent = false;
481     m_return_valobj_sp =
482         abi->GetReturnValueObject(m_thread, m_return_type, persistent);
483   }
484 }
485