Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(605)

Side by Side Diff: src/zone.cc

Issue 435003: Patch for allowing several V8 instances in process:... (Closed) Base URL: http://v8.googlecode.com/svn/branches/bleeding_edge/
Patch Set: '' Created 11 years ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « src/zone.h ('k') | src/zone-inl.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2006-2008 the V8 project authors. All rights reserved. 1 // Copyright 2006-2008 the V8 project authors. All rights reserved.
2 // Redistribution and use in source and binary forms, with or without 2 // Redistribution and use in source and binary forms, with or without
3 // modification, are permitted provided that the following conditions are 3 // modification, are permitted provided that the following conditions are
4 // met: 4 // met:
5 // 5 //
6 // * Redistributions of source code must retain the above copyright 6 // * Redistributions of source code must retain the above copyright
7 // notice, this list of conditions and the following disclaimer. 7 // notice, this list of conditions and the following disclaimer.
8 // * Redistributions in binary form must reproduce the above 8 // * Redistributions in binary form must reproduce the above
9 // copyright notice, this list of conditions and the following 9 // copyright notice, this list of conditions and the following
10 // disclaimer in the documentation and/or other materials provided 10 // disclaimer in the documentation and/or other materials provided
(...skipping 14 matching lines...) Expand all
25 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 25 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
26 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 26 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 27
28 #include "v8.h" 28 #include "v8.h"
29 29
30 #include "zone-inl.h" 30 #include "zone-inl.h"
31 31
32 namespace v8 { 32 namespace v8 {
33 namespace internal { 33 namespace internal {
34 34
35 35 ZoneData::ZoneData():position_(0), limit_(0), zone_excess_limit_(256 * MB),
36 Address Zone::position_ = 0; 36 segment_bytes_allocated_(0), allow_allocation_(true), nesting_(0),
37 Address Zone::limit_ = 0; 37 head_(NULL), bytes_allocated_(0) {
38 int Zone::zone_excess_limit_ = 256 * MB; 38 }
39 int Zone::segment_bytes_allocated_ = 0;
40
41 bool AssertNoZoneAllocation::allow_allocation_ = true;
42
43 int ZoneScope::nesting_ = 0;
44 39
45 // Segments represent chunks of memory: They have starting address 40 // Segments represent chunks of memory: They have starting address
46 // (encoded in the this pointer) and a size in bytes. Segments are 41 // (encoded in the this pointer) and a size in bytes. Segments are
47 // chained together forming a LIFO structure with the newest segment 42 // chained together forming a LIFO structure with the newest segment
48 // available as Segment::head(). Segments are allocated using malloc() 43 // available as Segment::head(). Segments are allocated using malloc()
49 // and de-allocated using free(). 44 // and de-allocated using free().
50 45
51 class Segment { 46 class Segment {
52 public: 47 public:
53 Segment* next() const { return next_; } 48 Segment* next() const { return next_; }
54 void clear_next() { next_ = NULL; } 49 void clear_next() { next_ = NULL; }
55 50
56 int size() const { return size_; } 51 int size() const { return size_; }
57 int capacity() const { return size_ - sizeof(Segment); } 52 int capacity() const { return size_ - sizeof(Segment); }
58 53
59 Address start() const { return address(sizeof(Segment)); } 54 Address start() const { return address(sizeof(Segment)); }
60 Address end() const { return address(size_); } 55 Address end() const { return address(size_); }
61 56
62 static Segment* head() { return head_; } 57 static Segment* head() { return v8_context()->zone_data_.head_; }
63 static void set_head(Segment* head) { head_ = head; } 58 static void set_head(Segment* head) { v8_context()->zone_data_.head_ = head; }
64 59
65 // Creates a new segment, sets it size, and pushes it to the front 60 // Creates a new segment, sets it size, and pushes it to the front
66 // of the segment chain. Returns the new segment. 61 // of the segment chain. Returns the new segment.
67 static Segment* New(int size) { 62 static Segment* New(int size) {
68 Segment* result = reinterpret_cast<Segment*>(Malloced::New(size)); 63 Segment* result = reinterpret_cast<Segment*>(Malloced::New(size));
69 Zone::adjust_segment_bytes_allocated(size); 64 Zone::adjust_segment_bytes_allocated(size);
70 if (result != NULL) { 65 if (result != NULL) {
71 result->next_ = head_; 66 ZoneData& zone_data = v8_context()->zone_data_;
67 result->next_ = zone_data.head_;
72 result->size_ = size; 68 result->size_ = size;
73 head_ = result; 69 zone_data.head_ = result;
74 } 70 }
75 return result; 71 return result;
76 } 72 }
77 73
78 // Deletes the given segment. Does not touch the segment chain. 74 // Deletes the given segment. Does not touch the segment chain.
79 static void Delete(Segment* segment, int size) { 75 static void Delete(Segment* segment, int size) {
80 Zone::adjust_segment_bytes_allocated(-size); 76 Zone::adjust_segment_bytes_allocated(-size);
81 Malloced::Delete(segment); 77 Malloced::Delete(segment);
82 } 78 }
83 79
84 static int bytes_allocated() { return bytes_allocated_; } 80 static int bytes_allocated() {
81 return v8_context()->zone_data_.bytes_allocated_;
82 }
85 83
86 private: 84 private:
87 // Computes the address of the nth byte in this segment. 85 // Computes the address of the nth byte in this segment.
88 Address address(int n) const { 86 Address address(int n) const {
89 return Address(this) + n; 87 return Address(this) + n;
90 } 88 }
91 89
92 static Segment* head_;
93 static int bytes_allocated_;
94 Segment* next_; 90 Segment* next_;
95 int size_; 91 int size_;
96 }; 92 };
97 93
98
99 Segment* Segment::head_ = NULL;
100 int Segment::bytes_allocated_ = 0;
101
102
103 void Zone::DeleteAll() { 94 void Zone::DeleteAll() {
104 #ifdef DEBUG 95 #ifdef DEBUG
105 // Constant byte value used for zapping dead memory in debug mode. 96 // Constant byte value used for zapping dead memory in debug mode.
106 static const unsigned char kZapDeadByte = 0xcd; 97 static const unsigned char kZapDeadByte = 0xcd;
107 #endif 98 #endif
108 99
109 // Find a segment with a suitable size to keep around. 100 // Find a segment with a suitable size to keep around.
110 Segment* keep = Segment::head(); 101 Segment* keep = Segment::head();
111 while (keep != NULL && keep->size() > kMaximumKeptSegmentSize) { 102 while (keep != NULL && keep->size() > kMaximumKeptSegmentSize) {
112 keep = keep->next(); 103 keep = keep->next();
(...skipping 11 matching lines...) Expand all
124 int size = current->size(); 115 int size = current->size();
125 #ifdef DEBUG 116 #ifdef DEBUG
126 // Zap the entire current segment (including the header). 117 // Zap the entire current segment (including the header).
127 memset(current, kZapDeadByte, size); 118 memset(current, kZapDeadByte, size);
128 #endif 119 #endif
129 Segment::Delete(current, size); 120 Segment::Delete(current, size);
130 } 121 }
131 current = next; 122 current = next;
132 } 123 }
133 124
125 ZoneData& zone_data = v8_context()->zone_data_;
134 // If we have found a segment we want to keep, we must recompute the 126 // If we have found a segment we want to keep, we must recompute the
135 // variables 'position' and 'limit' to prepare for future allocate 127 // variables 'position' and 'limit' to prepare for future allocate
136 // attempts. Otherwise, we must clear the position and limit to 128 // attempts. Otherwise, we must clear the position and limit to
137 // force a new segment to be allocated on demand. 129 // force a new segment to be allocated on demand.
138 if (keep != NULL) { 130 if (keep != NULL) {
139 Address start = keep->start(); 131 Address start = keep->start();
140 position_ = RoundUp(start, kAlignment); 132 zone_data.position_ = RoundUp(start, kAlignment);
141 limit_ = keep->end(); 133 zone_data.limit_ = keep->end();
142 #ifdef DEBUG 134 #ifdef DEBUG
143 // Zap the contents of the kept segment (but not the header). 135 // Zap the contents of the kept segment (but not the header).
144 memset(start, kZapDeadByte, keep->capacity()); 136 memset(start, kZapDeadByte, keep->capacity());
145 #endif 137 #endif
146 } else { 138 } else {
147 position_ = limit_ = 0; 139 zone_data.position_ = zone_data.limit_ = 0;
148 } 140 }
149 141
150 // Update the head segment to be the kept segment (if any). 142 // Update the head segment to be the kept segment (if any).
151 Segment::set_head(keep); 143 Segment::set_head(keep);
152 } 144 }
153 145
154 146
155 Address Zone::NewExpand(int size) { 147 Address Zone::NewExpand(int size) {
148 ZoneData& zone_data = v8_context()->zone_data_;
156 // Make sure the requested size is already properly aligned and that 149 // Make sure the requested size is already properly aligned and that
157 // there isn't enough room in the Zone to satisfy the request. 150 // there isn't enough room in the Zone to satisfy the request.
158 ASSERT(size == RoundDown(size, kAlignment)); 151 ASSERT(size == RoundDown(size, kAlignment));
159 ASSERT(position_ + size > limit_); 152 ASSERT(zone_data.position_ + size > zone_data.limit_);
160 153
161 // Compute the new segment size. We use a 'high water mark' 154 // Compute the new segment size. We use a 'high water mark'
162 // strategy, where we increase the segment size every time we expand 155 // strategy, where we increase the segment size every time we expand
163 // except that we employ a maximum segment size when we delete. This 156 // except that we employ a maximum segment size when we delete. This
164 // is to avoid excessive malloc() and free() overhead. 157 // is to avoid excessive malloc() and free() overhead.
165 Segment* head = Segment::head(); 158 Segment* head = Segment::head();
166 int old_size = (head == NULL) ? 0 : head->size(); 159 int old_size = (head == NULL) ? 0 : head->size();
167 static const int kSegmentOverhead = sizeof(Segment) + kAlignment; 160 static const int kSegmentOverhead = sizeof(Segment) + kAlignment;
168 int new_size = kSegmentOverhead + size + (old_size << 1); 161 int new_size = kSegmentOverhead + size + (old_size << 1);
169 if (new_size < kMinimumSegmentSize) { 162 if (new_size < kMinimumSegmentSize) {
170 new_size = kMinimumSegmentSize; 163 new_size = kMinimumSegmentSize;
171 } else if (new_size > kMaximumSegmentSize) { 164 } else if (new_size > kMaximumSegmentSize) {
172 // Limit the size of new segments to avoid growing the segment size 165 // Limit the size of new segments to avoid growing the segment size
173 // exponentially, thus putting pressure on contiguous virtual address space. 166 // exponentially, thus putting pressure on contiguous virtual address space.
174 // All the while making sure to allocate a segment large enough to hold the 167 // All the while making sure to allocate a segment large enough to hold the
175 // requested size. 168 // requested size.
176 new_size = Max(kSegmentOverhead + size, kMaximumSegmentSize); 169 new_size = Max(kSegmentOverhead + size, kMaximumSegmentSize);
177 } 170 }
178 Segment* segment = Segment::New(new_size); 171 Segment* segment = Segment::New(new_size);
179 if (segment == NULL) { 172 if (segment == NULL) {
180 V8::FatalProcessOutOfMemory("Zone"); 173 V8::FatalProcessOutOfMemory("Zone");
181 return NULL; 174 return NULL;
182 } 175 }
183 176
184 // Recompute 'top' and 'limit' based on the new segment. 177 // Recompute 'top' and 'limit' based on the new segment.
185 Address result = RoundUp(segment->start(), kAlignment); 178 Address result = RoundUp(segment->start(), kAlignment);
186 position_ = result + size; 179 zone_data.position_ = result + size;
187 limit_ = segment->end(); 180 zone_data.limit_ = segment->end();
188 ASSERT(position_ <= limit_); 181 ASSERT(zone_data.position_ <= zone_data.limit_);
189 return result; 182 return result;
190 } 183 }
191 184
192 185
193 } } // namespace v8::internal 186 } } // namespace v8::internal
OLDNEW
« no previous file with comments | « src/zone.h ('k') | src/zone-inl.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698