OLD | NEW |
1 // Copyright 2013 the V8 project authors. All rights reserved. | 1 // Copyright 2013 the V8 project authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "src/compiler/code-generator.h" | 5 #include "src/compiler/code-generator.h" |
6 | 6 |
7 #include "src/compiler/code-generator-impl.h" | 7 #include "src/compiler/code-generator-impl.h" |
8 #include "src/compiler/linkage.h" | 8 #include "src/compiler/linkage.h" |
9 #include "src/compiler/pipeline.h" | 9 #include "src/compiler/pipeline.h" |
10 | 10 |
(...skipping 215 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
226 for (int i = 0; i < patch_count; ++i) { | 226 for (int i = 0; i < patch_count; ++i) { |
227 LazyDeoptimizationEntry entry = lazy_deoptimization_entries_[i]; | 227 LazyDeoptimizationEntry entry = lazy_deoptimization_entries_[i]; |
228 data->SetReturnAddressPc(i, Smi::FromInt(entry.position_after_call())); | 228 data->SetReturnAddressPc(i, Smi::FromInt(entry.position_after_call())); |
229 data->SetPatchedAddressPc(i, Smi::FromInt(entry.deoptimization()->pos())); | 229 data->SetPatchedAddressPc(i, Smi::FromInt(entry.deoptimization()->pos())); |
230 } | 230 } |
231 | 231 |
232 code_object->set_deoptimization_data(*data); | 232 code_object->set_deoptimization_data(*data); |
233 } | 233 } |
234 | 234 |
235 | 235 |
| 236 void CodeGenerator::AddSafepointAndDeopt(Instruction* instr) { |
| 237 CallDescriptor::DeoptimizationSupport deopt = |
| 238 static_cast<CallDescriptor::DeoptimizationSupport>( |
| 239 MiscField::decode(instr->opcode())); |
| 240 |
| 241 if ((deopt & CallDescriptor::kLazyDeoptimization) != 0) { |
| 242 RecordLazyDeoptimizationEntry(instr); |
| 243 } |
| 244 |
| 245 bool needs_frame_state = (deopt & CallDescriptor::kNeedsFrameState) != 0; |
| 246 |
| 247 RecordSafepoint( |
| 248 instr->pointer_map(), Safepoint::kSimple, 0, |
| 249 needs_frame_state ? Safepoint::kLazyDeopt : Safepoint::kNoLazyDeopt); |
| 250 |
| 251 if ((deopt & CallDescriptor::kNeedsFrameState) != 0) { |
| 252 // If the frame state is present, it starts at argument 1 |
| 253 // (just after the code address). |
| 254 InstructionOperandConverter converter(this, instr); |
| 255 // Argument 1 is deoptimization id. |
| 256 int deoptimization_id = converter.ToConstant(instr->InputAt(1)).ToInt32(); |
| 257 // The actual frame state values start with argument 2. |
| 258 BuildTranslation(instr, 2, deoptimization_id); |
| 259 safepoints()->RecordLazyDeoptimizationIndex(deoptimization_id); |
| 260 } |
| 261 } |
| 262 |
| 263 |
236 void CodeGenerator::RecordLazyDeoptimizationEntry(Instruction* instr) { | 264 void CodeGenerator::RecordLazyDeoptimizationEntry(Instruction* instr) { |
237 InstructionOperandConverter i(this, instr); | 265 InstructionOperandConverter i(this, instr); |
238 | 266 |
239 Label after_call; | 267 Label after_call; |
240 masm()->bind(&after_call); | 268 masm()->bind(&after_call); |
241 | 269 |
242 // The continuation and deoptimization are the last two inputs: | 270 // The continuation and deoptimization are the last two inputs: |
243 BasicBlock* cont_block = | 271 BasicBlock* cont_block = |
244 i.InputBlock(static_cast<int>(instr->InputCount()) - 2); | 272 i.InputBlock(static_cast<int>(instr->InputCount()) - 2); |
245 BasicBlock* deopt_block = | 273 BasicBlock* deopt_block = |
(...skipping 11 matching lines...) Expand all Loading... |
257 int result = static_cast<int>(deoptimization_literals_.size()); | 285 int result = static_cast<int>(deoptimization_literals_.size()); |
258 for (unsigned i = 0; i < deoptimization_literals_.size(); ++i) { | 286 for (unsigned i = 0; i < deoptimization_literals_.size(); ++i) { |
259 if (deoptimization_literals_[i].is_identical_to(literal)) return i; | 287 if (deoptimization_literals_[i].is_identical_to(literal)) return i; |
260 } | 288 } |
261 deoptimization_literals_.push_back(literal); | 289 deoptimization_literals_.push_back(literal); |
262 return result; | 290 return result; |
263 } | 291 } |
264 | 292 |
265 | 293 |
266 void CodeGenerator::BuildTranslation(Instruction* instr, | 294 void CodeGenerator::BuildTranslation(Instruction* instr, |
| 295 int first_argument_index, |
267 int deoptimization_id) { | 296 int deoptimization_id) { |
268 // We should build translation only once. | 297 // We should build translation only once. |
269 DCHECK_EQ(NULL, deoptimization_states_[deoptimization_id]); | 298 DCHECK_EQ(NULL, deoptimization_states_[deoptimization_id]); |
270 | 299 |
271 FrameStateDescriptor* descriptor = | 300 FrameStateDescriptor* descriptor = |
272 code()->GetDeoptimizationEntry(deoptimization_id); | 301 code()->GetDeoptimizationEntry(deoptimization_id); |
273 Translation translation(&translations_, 1, 1, zone()); | 302 Translation translation(&translations_, 1, 1, zone()); |
274 translation.BeginJSFrame(descriptor->bailout_id(), | 303 translation.BeginJSFrame(descriptor->bailout_id(), |
275 Translation::kSelfLiteralId, | 304 Translation::kSelfLiteralId, |
276 descriptor->size() - descriptor->parameters_count()); | 305 descriptor->size() - descriptor->parameters_count()); |
277 | 306 |
278 for (int i = 0; i < descriptor->size(); i++) { | 307 for (int i = 0; i < descriptor->size(); i++) { |
279 AddTranslationForOperand(&translation, instr, instr->InputAt(i)); | 308 AddTranslationForOperand(&translation, instr, |
| 309 instr->InputAt(i + first_argument_index)); |
280 } | 310 } |
281 | 311 |
282 deoptimization_states_[deoptimization_id] = | 312 deoptimization_states_[deoptimization_id] = |
283 new (zone()) DeoptimizationState(translation.index()); | 313 new (zone()) DeoptimizationState(translation.index()); |
284 } | 314 } |
285 | 315 |
286 | 316 |
287 void CodeGenerator::AddTranslationForOperand(Translation* translation, | 317 void CodeGenerator::AddTranslationForOperand(Translation* translation, |
288 Instruction* instr, | 318 Instruction* instr, |
289 InstructionOperand* op) { | 319 InstructionOperand* op) { |
(...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
360 } | 390 } |
361 | 391 |
362 | 392 |
363 void CodeGenerator::AddNopForSmiCodeInlining() { UNIMPLEMENTED(); } | 393 void CodeGenerator::AddNopForSmiCodeInlining() { UNIMPLEMENTED(); } |
364 | 394 |
365 #endif // !V8_TURBOFAN_BACKEND | 395 #endif // !V8_TURBOFAN_BACKEND |
366 | 396 |
367 } // namespace compiler | 397 } // namespace compiler |
368 } // namespace internal | 398 } // namespace internal |
369 } // namespace v8 | 399 } // namespace v8 |
OLD | NEW |