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

Side by Side Diff: src/jump-target.cc

Issue 114018: Simplify JumpTarget::ComputeEntryFrame. Eliminate a separate pass... (Closed) Base URL: http://v8.googlecode.com/svn/branches/bleeding_edge/
Patch Set: Created 11 years, 7 months 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/ia32/register-allocator-ia32.cc ('k') | src/register-allocator.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 2009 the V8 project authors. All rights reserved. 1 // Copyright 2009 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 171 matching lines...) Expand 10 before | Expand all | Expand 10 after
182 182
183 // Element computation is monotonic: new information will not 183 // Element computation is monotonic: new information will not
184 // change our decision about undetermined or invalid elements. 184 // change our decision about undetermined or invalid elements.
185 if (element == NULL || !element->is_valid()) break; 185 if (element == NULL || !element->is_valid()) break;
186 186
187 elements[i] = Combine(element, &reaching_frames_[j]->elements_[i]); 187 elements[i] = Combine(element, &reaching_frames_[j]->elements_[i]);
188 } 188 }
189 } 189 }
190 } 190 }
191 191
192 // Compute the registers already reserved by values in the frame. 192 // Build the new frame. Initially it has memory elements for the
193 // Count the reserved registers to avoid using them. 193 // parameters and some platform-dependent elements (e.g., return
194 RegisterFile frame_registers = RegisterAllocator::Reserved(); 194 // address). Fill those in first.
William Hesse 2009/05/11 13:47:34 The new frame does not "have" memory elements for
Kevin Millikin (Chromium) 2009/05/11 13:57:15 Replaced with: // Build the new frame. A freshl
195 for (int i = 0; i < length; i++) { 195 entry_frame_ = new VirtualFrame(cgen_);
196 FrameElement* element = elements[i]; 196 int index = 0;
197 if (element != NULL && element->is_register()) { 197 for (; index < entry_frame_->elements_.length(); index++) {
198 frame_registers.Use(element->reg()); 198 // If the element is determined, set it now and count registers.
199 // Undetermined elements are initially recorded as if in memory.
200 if (elements[index] != NULL) {
201 entry_frame_->elements_[index] = *elements[index];
202 if (elements[index]->is_register()) {
203 entry_frame_->register_locations_[elements[index]->reg().code()] =
204 index;
205 }
206 }
207 }
208 // Fill in the rest of the frame with new elements.
209 for (; index < length; index++) {
210 if (elements[index] == NULL) {
211 entry_frame_->elements_.Add(FrameElement::MemoryElement());
212 } else {
213 entry_frame_->elements_.Add(*elements[index]);
214 if (elements[index]->is_register()) {
215 entry_frame_->register_locations_[elements[index]->reg().code()] =
216 index;
217 }
199 } 218 }
200 } 219 }
201 220
202 // Build the new frame. The frame already has memory elements for 221 // Allocate any still-undetermined frame elements to registers or
203 // the parameters (including the receiver) and the return address. 222 // memory, from the top down.
204 // We will fill it up with memory elements.
205 entry_frame_ = new VirtualFrame(cgen_);
206 while (entry_frame_->elements_.length() < length) {
207 entry_frame_->elements_.Add(FrameElement::MemoryElement());
208 }
209
210
211 // Copy the already-determined frame elements to the entry frame,
212 // and allocate any still-undetermined frame elements to registers
213 // or memory, from the top down.
214 for (int i = length - 1; i >= 0; i--) { 223 for (int i = length - 1; i >= 0; i--) {
215 if (elements[i] == NULL) { 224 if (elements[i] == NULL) {
216 // If the value is synced on all frames, put it in memory. This 225 // If the value is synced on all frames, put it in memory. This
217 // costs nothing at the merge code but will incur a 226 // costs nothing at the merge code but will incur a
218 // memory-to-register move when the value is needed later. 227 // memory-to-register move when the value is needed later.
219 bool is_synced = true; 228 bool is_synced = true;
220 for (int j = 0; is_synced && j < reaching_frames_.length(); j++) { 229 for (int j = 0; is_synced && j < reaching_frames_.length(); j++) {
221 is_synced = reaching_frames_[j]->elements_[i].is_synced(); 230 is_synced = reaching_frames_[j]->elements_[i].is_synced();
222 } 231 }
223 232
224 // There is nothing to be done if the elements are all synced. 233 // There is nothing to be done if the elements are all synced.
225 // It is already recorded as a memory element. 234 // It is already recorded as a memory element.
226 if (is_synced) continue; 235 if (is_synced) continue;
227 236
228 // Choose an available register. Prefer ones that the element 237 // Choose an available register. Prefer ones that the element
229 // is already occupying on some reaching frame. 238 // is already occupying on some reaching frame.
230 RegisterFile candidate_registers; 239 RegisterFile candidate_registers;
231 int max_count = kMinInt; 240 int max_count = kMinInt;
232 int best_reg_code = no_reg.code_; 241 int best_reg_code = no_reg.code_;
233 242
234 for (int j = 0; j < reaching_frames_.length(); j++) { 243 for (int j = 0; j < reaching_frames_.length(); j++) {
235 FrameElement element = reaching_frames_[j]->elements_[i]; 244 FrameElement element = reaching_frames_[j]->elements_[i];
236 if (element.is_register() && 245 if (element.is_register() &&
237 !frame_registers.is_used(element.reg())) { 246 !entry_frame_->is_used(element.reg())) {
238 candidate_registers.Use(element.reg()); 247 candidate_registers.Use(element.reg());
239 if (candidate_registers.count(element.reg()) > max_count) { 248 if (candidate_registers.count(element.reg()) > max_count) {
240 max_count = candidate_registers.count(element.reg()); 249 max_count = candidate_registers.count(element.reg());
241 best_reg_code = element.reg().code(); 250 best_reg_code = element.reg().code();
242 } 251 }
243 } 252 }
244 } 253 }
245 // If there was no preferred choice consider any free register. 254 // If there was no preferred choice consider any free register.
246 if (best_reg_code == no_reg.code_) { 255 if (best_reg_code == no_reg.code_) {
247 for (int j = 0; j < kNumRegisters; j++) { 256 for (int j = 0; j < kNumRegisters; j++) {
248 if (!frame_registers.is_used(j)) { 257 if (!entry_frame_->is_used(j) && !RegisterAllocator::IsReserved(j)) {
249 best_reg_code = j; 258 best_reg_code = j;
250 break; 259 break;
251 } 260 }
252 } 261 }
253 } 262 }
254 263
255 // If there was a register choice, use it. If not do nothing 264 // If there was a register choice, use it. If not do nothing
256 // (the element is already recorded as in memory) 265 // (the element is already recorded as in memory)
257 if (best_reg_code != no_reg.code_) { 266 if (best_reg_code != no_reg.code_) {
258 Register reg = { best_reg_code }; 267 Register reg = { best_reg_code };
259 frame_registers.Use(reg);
260 entry_frame_->elements_[i] = 268 entry_frame_->elements_[i] =
261 FrameElement::RegisterElement(reg, 269 FrameElement::RegisterElement(reg,
262 FrameElement::NOT_SYNCED); 270 FrameElement::NOT_SYNCED);
271 entry_frame_->register_locations_[best_reg_code] = i;
263 } 272 }
264 } else {
265 // The element is already determined.
266 entry_frame_->elements_[i] = *elements[i];
267 } 273 }
268 } 274 }
269 275
270 // Set the copied flags in the frame to be exact. This assumes that 276 // Set the copied flags in the frame to be exact. This assumes that
271 // the backing store of copies is always lower in the frame. 277 // the backing store of copies is always lower in the frame.
272 // Set the register locations to their index in the frame.
273 for (int i = 0; i < length; i++) { 278 for (int i = 0; i < length; i++) {
274 FrameElement* current = &entry_frame_->elements_[i]; 279 FrameElement* current = &entry_frame_->elements_[i];
275 current->clear_copied(); 280 current->clear_copied();
276 if (current->is_copy()) { 281 if (current->is_copy()) {
277 entry_frame_->elements_[current->index()].set_copied(); 282 entry_frame_->elements_[current->index()].set_copied();
278 } else if (current->is_register()) {
279 entry_frame_->register_locations_[current->reg().code()] = i;
280 } 283 }
281 284
282 if (direction_ == BIDIRECTIONAL && i >= high_water_mark) { 285 if (direction_ == BIDIRECTIONAL && i >= high_water_mark) {
283 current->set_static_type(StaticType::unknown()); 286 current->set_static_type(StaticType::unknown());
284 } else { 287 } else {
285 StaticType merged_type = reaching_frames_[0]->elements_[i].static_type(); 288 StaticType merged_type = reaching_frames_[0]->elements_[i].static_type();
286 for (int j = 1, n = reaching_frames_.length(); 289 for (int j = 1, n = reaching_frames_.length();
287 !merged_type.is_unknown() && j < n; 290 !merged_type.is_unknown() && j < n;
288 j++) { 291 j++) {
289 merged_type = 292 merged_type =
(...skipping 432 matching lines...) Expand 10 before | Expand all | Expand 10 after
722 temp.CopyTo(this); 725 temp.CopyTo(this);
723 temp.Reset(); // So the destructor does not deallocate virtual frames. 726 temp.Reset(); // So the destructor does not deallocate virtual frames.
724 727
725 #ifdef DEBUG 728 #ifdef DEBUG
726 is_shadowing_ = false; 729 is_shadowing_ = false;
727 #endif 730 #endif
728 } 731 }
729 732
730 733
731 } } // namespace v8::internal 734 } } // namespace v8::internal
OLDNEW
« no previous file with comments | « src/ia32/register-allocator-ia32.cc ('k') | src/register-allocator.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698