1 : // Copyright 2012 Google Inc.
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 : // Implements HeapProxy, a class that wraps Win32 heap allocations but adds
16 : // heap/tail redzones.
17 : #ifndef SYZYGY_AGENT_ASAN_ASAN_HEAP_H_
18 : #define SYZYGY_AGENT_ASAN_ASAN_HEAP_H_
19 :
20 : #include <windows.h>
21 :
22 : #include "base/synchronization/lock.h"
23 :
24 m : namespace agent {
25 m : namespace asan {
26 :
27 : // Makes like a Win32 heap manager heap, but adds a redzone before and after
28 : // each allocation and maintains a quarantine list of freed blocks.
29 m : class HeapProxy {
30 m : public:
31 m : HeapProxy();
32 m : ~HeapProxy();
33 :
34 : // @name Cast to/from HANDLE.
35 : // @{
36 m : static HANDLE ToHandle(HeapProxy* proxy);
37 m : static HeapProxy* FromHandle(HANDLE heap);
38 : // @}
39 :
40 : // @name Heap interface.
41 : // @{
42 m : bool Create(DWORD options,
43 m : size_t initial_size,
44 m : size_t maximum_size);
45 m : bool Destroy();
46 m : void* Alloc(DWORD flags, size_t bytes);
47 m : void* ReAlloc(DWORD flags, void* mem, size_t bytes);
48 m : bool Free(DWORD flags, void* mem);
49 m : size_t Size(DWORD flags, const void* mem);
50 m : bool Validate(DWORD flags, const void* mem);
51 m : size_t Compact(DWORD flags);
52 m : bool Lock();
53 m : bool Unlock();
54 m : bool Walk(PROCESS_HEAP_ENTRY* entry);
55 m : bool SetInformation(HEAP_INFORMATION_CLASS info_class,
56 m : void* info,
57 m : size_t info_length);
58 m : bool QueryInformation(HEAP_INFORMATION_CLASS info_class,
59 m : void* info,
60 m : size_t info_length,
61 m : unsigned long* return_length);
62 : // @}
63 :
64 m : private:
65 : // Every allocated block starts with a BlockHeader.
66 m : struct BlockHeader {
67 m : size_t size;
68 m : };
69 :
70 : // Free blocks are linked together.
71 m : struct FreeBlockHeader : public BlockHeader {
72 m : FreeBlockHeader* next;
73 m : };
74 :
75 : // Quarantines @p block and flushes quarantine overage.
76 m : void QuarantineBlock(BlockHeader* block);
77 :
78 : // Calculates the underlying allocation size for a requested
79 : // allocation of @p bytes.
80 m : static size_t GetAllocSize(size_t bytes);
81 :
82 : // Returns the block header for an alloc.
83 m : static BlockHeader* ToBlock(const void* alloc);
84 :
85 : // Returns alloc for a block.
86 m : static uint8* ToAlloc(BlockHeader* block);
87 :
88 : // Contains the underlying heap we delegate to.
89 m : HANDLE heap_;
90 :
91 m : base::Lock lock_;
92 : // Points to the head of the quarantine queue.
93 m : FreeBlockHeader* head_; // Under lock_.
94 : // Points to the tail of the quarantine queue.
95 m : FreeBlockHeader* tail_; // Under lock_.
96 : // Total size of blocks in quarantine.
97 m : size_t quarantine_size_; // Under lock_.
98 m : };
99 :
100 m : } // namespace asan
101 m : } // namespace agent
102 :
103 : #endif // SYZYGY_AGENT_ASAN_ASAN_HEAP_H_
|