1 : // Copyright 2015 Google Inc. All Rights Reserved.
2 : //
3 : // Licensed under the Apache License, Version 2.0 (the "License");
4 : // you may not use this file except in compliance with the License.
5 : // You may obtain a copy of the License at
6 : //
7 : // http://www.apache.org/licenses/LICENSE-2.0
8 : //
9 : // Unless required by applicable law or agreed to in writing, software
10 : // distributed under the License is distributed on an "AS IS" BASIS,
11 : // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 : // See the License for the specific language governing permissions and
13 : // limitations under the License.
14 : //
15 : // Declares a backdrop class to be used with Heap events.
16 : #ifndef SYZYGY_BARD_BACKDROPS_HEAP_BACKDROP_H_
17 : #define SYZYGY_BARD_BACKDROPS_HEAP_BACKDROP_H_
18 :
19 : #include <windows.h>
20 :
21 : #include <map>
22 : #include <string>
23 :
24 : #include "base/bind.h"
25 : #include "base/callback.h"
26 : #include "base/synchronization/lock.h"
27 : #include "syzygy/bard/event.h"
28 : #include "syzygy/bard/trace_live_map.h"
29 :
30 : namespace bard {
31 : namespace backdrops {
32 :
33 : using base::Callback;
34 :
35 : // Backdrop class to be used with Heap management events. It stores the
36 : // existing heaps and objects, and maps them from and to their trace file
37 : // addresses. It also stores the total time taken to run all the commands
38 : // so far.
39 : // The class is thread safe for simultaneous access across multiple threads.
40 : class HeapBackdrop {
41 : public:
42 : using EventType = EventInterface::EventType;
43 : // @name Heap API callback signatures.
44 : // @{
45 : using HeapAllocCallback = Callback<LPVOID(HANDLE, DWORD, SIZE_T)>;
46 : using HeapCreateCallback = Callback<HANDLE(DWORD, SIZE_T, SIZE_T)>;
47 : using HeapDestroyCallback = Callback<BOOL(HANDLE)>;
48 : using HeapFreeCallback = Callback<BOOL(HANDLE, DWORD, LPVOID)>;
49 : using HeapReAllocCallback = Callback<LPVOID(HANDLE, DWORD, LPVOID, SIZE_T)>;
50 : using HeapSetInformationCallback =
51 : Callback<BOOL(HANDLE, HEAP_INFORMATION_CLASS, PVOID, SIZE_T BOOL)>;
52 : using HeapSizeCallback = Callback<SIZE_T(HANDLE, DWORD, LPCVOID)>;
53 : // @}
54 :
55 : HeapBackdrop();
56 :
57 : // @name TraceLiveMap accessors.
58 : // @{
59 E : TraceLiveMap<HANDLE>& heap_map() { return heap_map_; }
60 E : TraceLiveMap<LPVOID>& alloc_map() { return alloc_map_; }
61 :
62 : const TraceLiveMap<HANDLE>& heap_map() const { return heap_map_; }
63 : const TraceLiveMap<LPVOID>& alloc_map() const { return alloc_map_; }
64 : // @}
65 :
66 : // @name Heap API functions.
67 : // @{
68 : LPVOID HeapAlloc(HANDLE heap, DWORD flags, SIZE_T bytes);
69 : HANDLE HeapCreate(DWORD options, SIZE_T initial_size, SIZE_T maximum_size);
70 : BOOL HeapDestroy(HANDLE heap);
71 : BOOL HeapFree(HANDLE heap, DWORD flags, LPVOID mem);
72 : LPVOID HeapReAlloc(HANDLE heap, DWORD flags, LPVOID mem, SIZE_T bytes);
73 : BOOL HeapSetInformation(HANDLE heap,
74 : HEAP_INFORMATION_CLASS info_class,
75 : PVOID info,
76 : SIZE_T info_length);
77 : SIZE_T HeapSize(HANDLE heap, DWORD flags, LPCVOID mem);
78 : // @}
79 :
80 : // @name Heap API callback mutators.
81 : // @{
82 E : void set_heap_alloc(const HeapAllocCallback& heap_alloc) {
83 E : heap_alloc_ = heap_alloc;
84 E : }
85 E : void set_heap_create(const HeapCreateCallback& heap_create) {
86 E : heap_create_ = heap_create;
87 E : }
88 E : void set_heap_destroy(const HeapDestroyCallback& heap_destroy) {
89 E : heap_destroy_ = heap_destroy;
90 E : }
91 E : void set_heap_free(const HeapFreeCallback& heap_free) {
92 E : heap_free_ = heap_free;
93 E : }
94 E : void set_heap_realloc(const HeapReAllocCallback& heap_realloc) {
95 E : heap_realloc_ = heap_realloc;
96 E : }
97 : void set_heap_set_information(
98 E : const HeapSetInformationCallback& heap_set_information) {
99 E : heap_set_information_ = heap_set_information;
100 E : }
101 E : void set_heap_size(const HeapSizeCallback& heap_size) {
102 E : heap_size_ = heap_size;
103 E : }
104 : // @}
105 :
106 : // Update the total time taken by a event with type @p type.
107 : // @param type the type of the heap event.
108 : // @param time the time the heap call took to run, in cycles as
109 : // measured by rdtsc.
110 : void UpdateStats(EventType type, uint64_t time);
111 :
112 : // Exposed for unittesting.
113 : protected:
114 : // The following struct holds the statistics generated by a specific
115 : // function call: the sum of the time it takes to run and the number
116 : // of times it was called.
117 : struct Stats {
118 : uint64_t time;
119 : uint64_t calls;
120 : };
121 :
122 : // Pointers to heap API implementation that is being evaluated.
123 : HeapAllocCallback heap_alloc_;
124 : HeapCreateCallback heap_create_;
125 : HeapDestroyCallback heap_destroy_;
126 : HeapFreeCallback heap_free_;
127 : HeapReAllocCallback heap_realloc_;
128 : HeapSetInformationCallback heap_set_information_;
129 : HeapSizeCallback heap_size_;
130 :
131 : TraceLiveMap<HANDLE> heap_map_;
132 : TraceLiveMap<LPVOID> alloc_map_;
133 :
134 : std::map<EventType, struct Stats> total_stats_;
135 :
136 : base::Lock lock_;
137 :
138 : private:
139 : DISALLOW_COPY_AND_ASSIGN(HeapBackdrop);
140 : };
141 :
142 : } // namespace backdrops
143 : } // namespace bard
144 :
145 : #endif // SYZYGY_BARD_BACKDROPS_HEAP_BACKDROP_H_
|