bmalloc
[WebKit-https.git] / Source / bmalloc / bmalloc / Page.h
1 /*
2  * Copyright (C) 2014 Apple Inc. All rights reserved.
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions
6  * are met:
7  * 1. Redistributions of source code must retain the above copyright
8  *    notice, this list of conditions and the following disclaimer.
9  * 2. Redistributions in binary form must reproduce the above copyright
10  *    notice, this list of conditions and the following disclaimer in the
11  *    documentation and/or other materials provided with the distribution.
12  *
13  * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
14  * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
15  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
16  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL APPLE INC. OR
17  * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
18  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
19  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
20  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
21  * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
22  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
23  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 
24  */
25
26 #ifndef Page_h
27 #define Page_h
28
29 #include "BAssert.h"
30 #include "Mutex.h"
31 #include "VMAllocate.h"
32 #include <mutex>
33
34 namespace bmalloc {
35
36 template<typename Traits>
37 class Page {
38 public:
39     typedef typename Traits::Chunk Chunk;
40     typedef typename Traits::Line Line;
41     static const size_t lineSize = Traits::lineSize;
42
43     static const unsigned char maxRefCount = std::numeric_limits<unsigned char>::max();
44     static_assert(vmPageSize / lineSize < maxRefCount, "maximum line count must fit in Page");
45     
46     static Page* get(Line*);
47
48     void ref(std::lock_guard<Mutex>&);
49     bool deref();
50     unsigned refCount(std::lock_guard<Mutex>&);
51     
52     Line* begin();
53     Line* end();
54
55 private:
56     unsigned char m_refCount;
57 };
58
59 template<typename Traits>
60 inline void Page<Traits>::ref(std::lock_guard<Mutex>&)
61 {
62     ASSERT(m_refCount < maxRefCount);
63     ++m_refCount;
64 }
65
66 template<typename Traits>
67 inline bool Page<Traits>::deref()
68 {
69     ASSERT(m_refCount);
70     --m_refCount;
71     return !m_refCount;
72 }
73
74 template<typename Traits>
75 inline unsigned Page<Traits>::refCount(std::lock_guard<Mutex>&)
76 {
77     return m_refCount;
78 }
79
80 template<typename Traits>
81 inline auto Page<Traits>::get(Line* line) -> Page*
82 {
83     Chunk* chunk = Chunk::get(line);
84     size_t lineNumber = line - chunk->lines();
85     size_t pageNumber = lineNumber * lineSize / vmPageSize;
86     return &chunk->pages()[pageNumber];
87 }
88
89 template<typename Traits>
90 inline auto Page<Traits>::begin() -> Line*
91 {
92     Chunk* chunk = Chunk::get(this);
93     size_t pageNumber = this - chunk->pages();
94     size_t lineNumber = pageNumber * vmPageSize / lineSize;
95     return &chunk->lines()[lineNumber];
96 }
97
98 template<typename Traits>
99 inline auto Page<Traits>::end() -> Line*
100 {
101     return begin() + vmPageSize / lineSize;
102 }
103
104 } // namespace bmalloc
105
106 #endif // Page_h