1 // Copyright 2019 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 #ifndef BASE_PROFILER_SUSPENDABLE_THREAD_DELEGATE_H_
6 #define BASE_PROFILER_SUSPENDABLE_THREAD_DELEGATE_H_
7 
8 #include <vector>
9 
10 #include "base/base_export.h"
11 #include "base/profiler/register_context.h"
12 #include "base/profiler/thread_delegate.h"
13 
14 namespace base {
15 
16 // Platform-specific thread and stack manipulation delegate, for use by the
17 // platform-independent stack copying/walking implementation in
18 // StackSamplerImpl for suspension-based stack copying.
19 //
20 // IMPORTANT NOTE: Most methods in this interface are invoked while the target
21 // thread is suspended so must not do any allocation from the heap, including
22 // indirectly via use of DCHECK/CHECK or other logging statements. Otherwise the
23 // implementation can deadlock on heap locks acquired by the target thread
24 // before it was suspended. These functions are commented with "NO HEAP
25 // ALLOCATIONS".
26 class BASE_EXPORT SuspendableThreadDelegate : public ThreadDelegate {
27  public:
28   // Implementations of this interface should suspend the thread for the
29   // object's lifetime. NO HEAP ALLOCATIONS between the time the thread is
30   // suspended and resumed.
31   class BASE_EXPORT ScopedSuspendThread {
32    public:
33     ScopedSuspendThread() = default;
34     virtual ~ScopedSuspendThread() = default;
35 
36     ScopedSuspendThread(const ScopedSuspendThread&) = delete;
37     ScopedSuspendThread& operator=(const ScopedSuspendThread&) = delete;
38 
39     virtual bool WasSuccessful() const = 0;
40   };
41 
42   SuspendableThreadDelegate() = default;
43 
44   // Creates an object that holds the thread suspended for its lifetime.
45   virtual std::unique_ptr<ScopedSuspendThread> CreateScopedSuspendThread() = 0;
46 
47   // Gets the register context for the thread.
48   // NO HEAP ALLOCATIONS.
49   virtual bool GetThreadContext(RegisterContext* thread_context) = 0;
50 
51   // Returns true if the thread's stack can be copied, where the bottom address
52   // of the thread is at |stack_pointer|.
53   // NO HEAP ALLOCATIONS.
54   virtual bool CanCopyStack(uintptr_t stack_pointer) = 0;
55 };
56 
57 }  // namespace base
58 
59 #endif  // BASE_PROFILER_SUSPENDABLE_THREAD_DELEGATE_H_
60