OLD | NEW |
---|---|
(Empty) | |
1 // Copyright 2015 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 #include "base/trace_event/memory_profiler_allocation_context.h" | |
6 | |
7 #include "base/threading/thread_local_storage.h" | |
8 | |
9 namespace base { | |
10 namespace trace_event { | |
11 | |
12 subtle::Atomic32 AllocationContextTracker::capture_enabled_ = 0; | |
13 | |
14 namespace { | |
15 ThreadLocalStorage::StaticSlot g_tls_alloc_ctx_tracker = TLS_INITIALIZER; | |
16 } | |
17 | |
18 AllocationStack::AllocationStack() {} | |
19 AllocationStack::~AllocationStack() {} | |
20 | |
21 // This function is added to the TLS slot to clean up the instance when the | |
22 // thread exits. | |
23 void DestructAllocationContextTracker(void* alloc_ctx_tracker) { | |
24 delete static_cast<AllocationContextTracker*>(alloc_ctx_tracker); | |
25 } | |
26 | |
27 AllocationContextTracker* AllocationContextTracker::GetThreadLocalTracker() { | |
28 AllocationContextTracker* tracker; | |
29 | |
30 if (g_tls_alloc_ctx_tracker.initialized()) { | |
Dmitry Skiba
2015/09/29 19:00:16
Hmm, so we are setting g_tls_alloc_ctx_tracker val
Primiano Tucci (use gerrit)
2015/09/30 08:26:31
Ahh I think I see your point. Yes, looks like the
| |
31 tracker = | |
32 static_cast<AllocationContextTracker*>(g_tls_alloc_ctx_tracker.Get()); | |
33 } else { | |
34 tracker = new AllocationContextTracker(); | |
35 g_tls_alloc_ctx_tracker.Initialize(DestructAllocationContextTracker); | |
36 g_tls_alloc_ctx_tracker.Set(tracker); | |
37 } | |
38 | |
39 return tracker; | |
40 } | |
41 | |
42 AllocationContextTracker::AllocationContextTracker() {} | |
43 AllocationContextTracker::~AllocationContextTracker() {} | |
44 | |
45 // static | |
46 void AllocationContextTracker::SetCaptureEnabled(bool enabled) { | |
47 // There is no memory barrier here for performance reasons, a little lag is | |
48 // not an issue. | |
49 subtle::NoBarrier_Store(&capture_enabled_, enabled); | |
50 } | |
51 | |
52 // static | |
53 void AllocationContextTracker::PushPseudoStackFrame(StackFrame frame) { | |
54 auto tracker = AllocationContextTracker::GetThreadLocalTracker(); | |
55 tracker->pseudo_stack_.push(frame); | |
56 } | |
57 | |
58 // static | |
59 void AllocationContextTracker::PopPseudoStackFrame(StackFrame frame) { | |
60 auto tracker = AllocationContextTracker::GetThreadLocalTracker(); | |
61 DCHECK_EQ(frame, *tracker->pseudo_stack_.top()); | |
62 tracker->pseudo_stack_.pop(); | |
63 } | |
64 | |
65 // static | |
66 void AllocationContextTracker::SetContextField(const char* key, | |
67 const char* value) { | |
68 auto tracker = AllocationContextTracker::GetThreadLocalTracker(); | |
69 tracker->context_[key] = value; | |
70 } | |
71 | |
72 // static | |
73 void AllocationContextTracker::UnsetContextField(const char* key) { | |
74 auto tracker = AllocationContextTracker::GetThreadLocalTracker(); | |
75 tracker->context_.erase(key); | |
76 } | |
77 | |
78 // static | |
79 AllocationStack* AllocationContextTracker::GetPseudoStackForTesting() { | |
80 auto tracker = AllocationContextTracker::GetThreadLocalTracker(); | |
81 return &tracker->pseudo_stack_; | |
82 } | |
83 | |
84 // static | |
85 AllocationContext AllocationContextTracker::GetContext() { | |
86 // TODO(ruuda): Implement this in a follow-up CL. | |
87 return AllocationContext(); | |
88 } | |
89 | |
90 } // namespace trace_event | |
91 } // namespace base | |
OLD | NEW |