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

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

Issue 146077: Removed static type inference and add a dynamic test for string addition. (Closed)
Patch Set: And it lints too. Created 11 years, 6 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
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 63 matching lines...) Expand 10 before | Expand all | Expand 10 after
74 74
75 // A list of pointers to frame elements in the entry frame. NULL 75 // A list of pointers to frame elements in the entry frame. NULL
76 // indicates that the element has not yet been determined. 76 // indicates that the element has not yet been determined.
77 int length = initial_frame->element_count(); 77 int length = initial_frame->element_count();
78 ZoneList<FrameElement*> elements(length); 78 ZoneList<FrameElement*> elements(length);
79 79
80 // Initially populate the list of elements based on the initial 80 // Initially populate the list of elements based on the initial
81 // frame. 81 // frame.
82 for (int i = 0; i < length; i++) { 82 for (int i = 0; i < length; i++) {
83 FrameElement element = initial_frame->elements_[i]; 83 FrameElement element = initial_frame->elements_[i];
84 // We do not allow copies or constants in bidirectional frames. All 84 // We do not allow copies or constants in bidirectional frames.
85 // elements above the water mark on bidirectional frames have
86 // unknown static types.
87 if (direction_ == BIDIRECTIONAL) { 85 if (direction_ == BIDIRECTIONAL) {
88 if (element.is_constant() || element.is_copy()) { 86 if (element.is_constant() || element.is_copy()) {
89 elements.Add(NULL); 87 elements.Add(NULL);
90 continue; 88 continue;
91 } 89 }
92 // It's safe to change the static type on the initial frame
93 // element, see comment in JumpTarget::Combine.
94 initial_frame->elements_[i].set_static_type(StaticType::unknown());
95 } 90 }
96 elements.Add(&initial_frame->elements_[i]); 91 elements.Add(&initial_frame->elements_[i]);
97 } 92 }
98 93
99 // Compute elements based on the other reaching frames. 94 // Compute elements based on the other reaching frames.
100 if (reaching_frames_.length() > 1) { 95 if (reaching_frames_.length() > 1) {
101 for (int i = 0; i < length; i++) { 96 for (int i = 0; i < length; i++) {
102 FrameElement* element = elements[i]; 97 FrameElement* element = elements[i];
103 for (int j = 1; j < reaching_frames_.length(); j++) { 98 for (int j = 1; j < reaching_frames_.length(); j++) {
104 // Element computation is monotonic: new information will not 99 // Element computation is monotonic: new information will not
(...skipping 30 matching lines...) Expand all
135 entry_frame_->elements_.Add(*target); 130 entry_frame_->elements_.Add(*target);
136 InitializeEntryElement(index, target); 131 InitializeEntryElement(index, target);
137 } 132 }
138 } 133 }
139 134
140 // Allocate any still-undetermined frame elements to registers or 135 // Allocate any still-undetermined frame elements to registers or
141 // memory, from the top down. 136 // memory, from the top down.
142 for (int i = length - 1; i >= 0; i--) { 137 for (int i = length - 1; i >= 0; i--) {
143 if (elements[i] == NULL) { 138 if (elements[i] == NULL) {
144 // Loop over all the reaching frames to check whether the element 139 // Loop over all the reaching frames to check whether the element
145 // is synced on all frames, to count the registers it occupies, 140 // is synced on all frames and to count the registers it occupies.
146 // and to compute a merged static type.
147 bool is_synced = true; 141 bool is_synced = true;
148 RegisterFile candidate_registers; 142 RegisterFile candidate_registers;
149 int best_count = kMinInt; 143 int best_count = kMinInt;
150 int best_reg_num = RegisterAllocator::kInvalidRegister; 144 int best_reg_num = RegisterAllocator::kInvalidRegister;
151 145
152 StaticType type; // Initially invalid.
153 if (direction_ != BIDIRECTIONAL) {
154 type = reaching_frames_[0]->elements_[i].static_type();
155 }
156
157 for (int j = 0; j < reaching_frames_.length(); j++) { 146 for (int j = 0; j < reaching_frames_.length(); j++) {
158 FrameElement element = reaching_frames_[j]->elements_[i]; 147 FrameElement element = reaching_frames_[j]->elements_[i];
159 is_synced = is_synced && element.is_synced(); 148 is_synced = is_synced && element.is_synced();
160 if (element.is_register() && !entry_frame_->is_used(element.reg())) { 149 if (element.is_register() && !entry_frame_->is_used(element.reg())) {
161 // Count the register occurrence and remember it if better 150 // Count the register occurrence and remember it if better
162 // than the previous best. 151 // than the previous best.
163 int num = RegisterAllocator::ToNumber(element.reg()); 152 int num = RegisterAllocator::ToNumber(element.reg());
164 candidate_registers.Use(num); 153 candidate_registers.Use(num);
165 if (candidate_registers.count(num) > best_count) { 154 if (candidate_registers.count(num) > best_count) {
166 best_count = candidate_registers.count(num); 155 best_count = candidate_registers.count(num);
167 best_reg_num = num; 156 best_reg_num = num;
168 } 157 }
169 } 158 }
170 type = type.merge(element.static_type());
171 } 159 }
172 160
173 // If the value is synced on all frames, put it in memory. This 161 // If the value is synced on all frames, put it in memory. This
174 // costs nothing at the merge code but will incur a 162 // costs nothing at the merge code but will incur a
175 // memory-to-register move when the value is needed later. 163 // memory-to-register move when the value is needed later.
176 if (is_synced) { 164 if (is_synced) {
177 // Already recorded as a memory element. 165 // Already recorded as a memory element.
178 entry_frame_->elements_[i].set_static_type(type);
179 continue; 166 continue;
180 } 167 }
181 168
182 // Try to put it in a register. If there was no best choice 169 // Try to put it in a register. If there was no best choice
183 // consider any free register. 170 // consider any free register.
184 if (best_reg_num == RegisterAllocator::kInvalidRegister) { 171 if (best_reg_num == RegisterAllocator::kInvalidRegister) {
185 for (int j = 0; j < RegisterAllocator::kNumRegisters; j++) { 172 for (int j = 0; j < RegisterAllocator::kNumRegisters; j++) {
186 if (!entry_frame_->is_used(j)) { 173 if (!entry_frame_->is_used(j)) {
187 best_reg_num = j; 174 best_reg_num = j;
188 break; 175 break;
189 } 176 }
190 } 177 }
191 } 178 }
192 179
193 if (best_reg_num == RegisterAllocator::kInvalidRegister) { 180 if (best_reg_num != RegisterAllocator::kInvalidRegister) {
194 // If there was no register found, the element is already
195 // recorded as in memory.
196 entry_frame_->elements_[i].set_static_type(type);
197 } else {
198 // If there was a register choice, use it. Preserve the copied 181 // If there was a register choice, use it. Preserve the copied
199 // flag on the element. Set the static type as computed. 182 // flag on the element.
200 bool is_copied = entry_frame_->elements_[i].is_copied(); 183 bool is_copied = entry_frame_->elements_[i].is_copied();
201 Register reg = RegisterAllocator::ToRegister(best_reg_num); 184 Register reg = RegisterAllocator::ToRegister(best_reg_num);
202 entry_frame_->elements_[i] = 185 entry_frame_->elements_[i] =
203 FrameElement::RegisterElement(reg, 186 FrameElement::RegisterElement(reg,
204 FrameElement::NOT_SYNCED); 187 FrameElement::NOT_SYNCED);
205 if (is_copied) entry_frame_->elements_[i].set_copied(); 188 if (is_copied) entry_frame_->elements_[i].set_copied();
206 entry_frame_->elements_[i].set_static_type(type);
207 entry_frame_->set_register_location(reg, i); 189 entry_frame_->set_register_location(reg, i);
208 } 190 }
209 } 191 }
210 } 192 }
211 193
212 // The stack pointer is at the highest synced element or the base of 194 // The stack pointer is at the highest synced element or the base of
213 // the expression stack. 195 // the expression stack.
214 int stack_pointer = length - 1; 196 int stack_pointer = length - 1;
215 while (stack_pointer >= entry_frame_->expression_base_index() && 197 while (stack_pointer >= entry_frame_->expression_base_index() &&
216 !entry_frame_->elements_[stack_pointer].is_synced()) { 198 !entry_frame_->elements_[stack_pointer].is_synced()) {
(...skipping 236 matching lines...) Expand 10 before | Expand all | Expand 10 after
453 temp.CopyTo(this); 435 temp.CopyTo(this);
454 temp.Unuse(); 436 temp.Unuse();
455 437
456 #ifdef DEBUG 438 #ifdef DEBUG
457 is_shadowing_ = false; 439 is_shadowing_ = false;
458 #endif 440 #endif
459 } 441 }
460 442
461 443
462 } } // namespace v8::internal 444 } } // namespace v8::internal
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698