| OLD | NEW | 
|---|
| 1 // Copyright 2013 the V8 project authors. All rights reserved. | 1 // Copyright 2013 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 464 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 475 | 475 | 
| 476 Operand LCodeGen::ToOperand(LOperand* op) const { | 476 Operand LCodeGen::ToOperand(LOperand* op) const { | 
| 477   // Does not handle registers. In X64 assembler, plain registers are not | 477   // Does not handle registers. In X64 assembler, plain registers are not | 
| 478   // representable as an Operand. | 478   // representable as an Operand. | 
| 479   ASSERT(op->IsStackSlot() || op->IsDoubleStackSlot()); | 479   ASSERT(op->IsStackSlot() || op->IsDoubleStackSlot()); | 
| 480   return Operand(rbp, StackSlotOffset(op->index())); | 480   return Operand(rbp, StackSlotOffset(op->index())); | 
| 481 } | 481 } | 
| 482 | 482 | 
| 483 | 483 | 
| 484 void LCodeGen::WriteTranslation(LEnvironment* environment, | 484 void LCodeGen::WriteTranslation(LEnvironment* environment, | 
| 485                                 Translation* translation, | 485                                 Translation* translation) { | 
| 486                                 int* pushed_arguments_index, |  | 
| 487                                 int* pushed_arguments_count) { |  | 
| 488   if (environment == NULL) return; | 486   if (environment == NULL) return; | 
| 489 | 487 | 
| 490   // The translation includes one command per value in the environment. | 488   // The translation includes one command per value in the environment. | 
| 491   int translation_size = environment->values()->length(); | 489   int translation_size = environment->translation_size(); | 
| 492   // The output frame height does not include the parameters. | 490   // The output frame height does not include the parameters. | 
| 493   int height = translation_size - environment->parameter_count(); | 491   int height = translation_size - environment->parameter_count(); | 
| 494 | 492 | 
| 495   // Function parameters are arguments to the outermost environment. The | 493   WriteTranslation(environment->outer(), translation); | 
| 496   // arguments index points to the first element of a sequence of tagged |  | 
| 497   // values on the stack that represent the arguments. This needs to be |  | 
| 498   // kept in sync with the LArgumentsElements implementation. |  | 
| 499   *pushed_arguments_index = -environment->parameter_count(); |  | 
| 500   *pushed_arguments_count = environment->parameter_count(); |  | 
| 501 |  | 
| 502   WriteTranslation(environment->outer(), |  | 
| 503                    translation, |  | 
| 504                    pushed_arguments_index, |  | 
| 505                    pushed_arguments_count); |  | 
| 506   bool has_closure_id = !info()->closure().is_null() && | 494   bool has_closure_id = !info()->closure().is_null() && | 
| 507       !info()->closure().is_identical_to(environment->closure()); | 495       !info()->closure().is_identical_to(environment->closure()); | 
| 508   int closure_id = has_closure_id | 496   int closure_id = has_closure_id | 
| 509       ? DefineDeoptimizationLiteral(environment->closure()) | 497       ? DefineDeoptimizationLiteral(environment->closure()) | 
| 510       : Translation::kSelfLiteralId; | 498       : Translation::kSelfLiteralId; | 
| 511 | 499 | 
| 512   switch (environment->frame_type()) { | 500   switch (environment->frame_type()) { | 
| 513     case JS_FUNCTION: | 501     case JS_FUNCTION: | 
| 514       translation->BeginJSFrame(environment->ast_id(), closure_id, height); | 502       translation->BeginJSFrame(environment->ast_id(), closure_id, height); | 
| 515       break; | 503       break; | 
| (...skipping 11 matching lines...) Expand all  Loading... | 
| 527       translation->BeginSetterStubFrame(closure_id); | 515       translation->BeginSetterStubFrame(closure_id); | 
| 528       break; | 516       break; | 
| 529     case ARGUMENTS_ADAPTOR: | 517     case ARGUMENTS_ADAPTOR: | 
| 530       translation->BeginArgumentsAdaptorFrame(closure_id, translation_size); | 518       translation->BeginArgumentsAdaptorFrame(closure_id, translation_size); | 
| 531       break; | 519       break; | 
| 532     case STUB: | 520     case STUB: | 
| 533       translation->BeginCompiledStubFrame(); | 521       translation->BeginCompiledStubFrame(); | 
| 534       break; | 522       break; | 
| 535   } | 523   } | 
| 536 | 524 | 
| 537   // Inlined frames which push their arguments cause the index to be |  | 
| 538   // bumped and another stack area to be used for materialization, |  | 
| 539   // otherwise actual argument values are unknown for inlined frames. |  | 
| 540   bool arguments_known = true; |  | 
| 541   int arguments_index = *pushed_arguments_index; |  | 
| 542   int arguments_count = *pushed_arguments_count; |  | 
| 543   if (environment->entry() != NULL) { |  | 
| 544     arguments_known = environment->entry()->arguments_pushed(); |  | 
| 545     arguments_index = arguments_index < 0 |  | 
| 546         ? GetStackSlotCount() : arguments_index + arguments_count; |  | 
| 547     arguments_count = environment->entry()->arguments_count() + 1; |  | 
| 548     if (environment->entry()->arguments_pushed()) { |  | 
| 549       *pushed_arguments_index = arguments_index; |  | 
| 550       *pushed_arguments_count = arguments_count; |  | 
| 551     } |  | 
| 552   } |  | 
| 553 |  | 
| 554   for (int i = 0; i < translation_size; ++i) { | 525   for (int i = 0; i < translation_size; ++i) { | 
| 555     LOperand* value = environment->values()->at(i); | 526     LOperand* value = environment->values()->at(i); | 
| 556     // spilled_registers_ and spilled_double_registers_ are either | 527     // spilled_registers_ and spilled_double_registers_ are either | 
| 557     // both NULL or both set. | 528     // both NULL or both set. | 
| 558     if (environment->spilled_registers() != NULL && value != NULL) { | 529     if (environment->spilled_registers() != NULL && value != NULL) { | 
| 559       if (value->IsRegister() && | 530       if (value->IsRegister() && | 
| 560           environment->spilled_registers()[value->index()] != NULL) { | 531           environment->spilled_registers()[value->index()] != NULL) { | 
| 561         translation->MarkDuplicate(); | 532         translation->MarkDuplicate(); | 
| 562         AddToTranslation(translation, | 533         AddToTranslation(translation, | 
| 563                          environment->spilled_registers()[value->index()], | 534                          environment->spilled_registers()[value->index()], | 
| 564                          environment->HasTaggedValueAt(i), | 535                          environment->HasTaggedValueAt(i), | 
| 565                          environment->HasUint32ValueAt(i), | 536                          environment->HasUint32ValueAt(i)); | 
| 566                          arguments_known, |  | 
| 567                          arguments_index, |  | 
| 568                          arguments_count); |  | 
| 569       } else if ( | 537       } else if ( | 
| 570           value->IsDoubleRegister() && | 538           value->IsDoubleRegister() && | 
| 571           environment->spilled_double_registers()[value->index()] != NULL) { | 539           environment->spilled_double_registers()[value->index()] != NULL) { | 
| 572         translation->MarkDuplicate(); | 540         translation->MarkDuplicate(); | 
| 573         AddToTranslation( | 541         AddToTranslation( | 
| 574             translation, | 542             translation, | 
| 575             environment->spilled_double_registers()[value->index()], | 543             environment->spilled_double_registers()[value->index()], | 
| 576             false, | 544             false, | 
| 577             false, | 545             false); | 
| 578             arguments_known, |  | 
| 579             arguments_index, |  | 
| 580             arguments_count); |  | 
| 581       } | 546       } | 
| 582     } | 547     } | 
| 583 | 548 | 
|  | 549     // TODO(mstarzinger): Introduce marker operands to indicate that this value | 
|  | 550     // is not present and must be reconstructed from the deoptimizer. Currently | 
|  | 551     // this is only used for the arguments object. | 
|  | 552     if (value == NULL) { | 
|  | 553       int arguments_count = environment->values()->length() - translation_size; | 
|  | 554       translation->BeginArgumentsObject(arguments_count); | 
|  | 555       for (int i = 0; i < arguments_count; ++i) { | 
|  | 556         LOperand* value = environment->values()->at(translation_size + i); | 
|  | 557         ASSERT(environment->spilled_registers() == NULL || | 
|  | 558                !value->IsRegister() || | 
|  | 559                environment->spilled_registers()[value->index()] == NULL); | 
|  | 560         ASSERT(environment->spilled_registers() == NULL || | 
|  | 561                !value->IsDoubleRegister() || | 
|  | 562                environment->spilled_double_registers()[value->index()] == NULL); | 
|  | 563         AddToTranslation(translation, | 
|  | 564                          value, | 
|  | 565                          environment->HasTaggedValueAt(translation_size + i), | 
|  | 566                          environment->HasUint32ValueAt(translation_size + i)); | 
|  | 567       } | 
|  | 568       continue; | 
|  | 569     } | 
|  | 570 | 
| 584     AddToTranslation(translation, | 571     AddToTranslation(translation, | 
| 585                      value, | 572                      value, | 
| 586                      environment->HasTaggedValueAt(i), | 573                      environment->HasTaggedValueAt(i), | 
| 587                      environment->HasUint32ValueAt(i), | 574                      environment->HasUint32ValueAt(i)); | 
| 588                      arguments_known, |  | 
| 589                      arguments_index, |  | 
| 590                      arguments_count); |  | 
| 591   } | 575   } | 
| 592 } | 576 } | 
| 593 | 577 | 
| 594 | 578 | 
| 595 void LCodeGen::AddToTranslation(Translation* translation, | 579 void LCodeGen::AddToTranslation(Translation* translation, | 
| 596                                 LOperand* op, | 580                                 LOperand* op, | 
| 597                                 bool is_tagged, | 581                                 bool is_tagged, | 
| 598                                 bool is_uint32, | 582                                 bool is_uint32) { | 
| 599                                 bool arguments_known, | 583   if (op->IsStackSlot()) { | 
| 600                                 int arguments_index, |  | 
| 601                                 int arguments_count) { |  | 
| 602   if (op == NULL) { |  | 
| 603     // TODO(twuerthinger): Introduce marker operands to indicate that this value |  | 
| 604     // is not present and must be reconstructed from the deoptimizer. Currently |  | 
| 605     // this is only used for the arguments object. |  | 
| 606     translation->StoreArgumentsObject( |  | 
| 607         arguments_known, arguments_index, arguments_count); |  | 
| 608   } else if (op->IsStackSlot()) { |  | 
| 609     if (is_tagged) { | 584     if (is_tagged) { | 
| 610       translation->StoreStackSlot(op->index()); | 585       translation->StoreStackSlot(op->index()); | 
| 611     } else if (is_uint32) { | 586     } else if (is_uint32) { | 
| 612       translation->StoreUint32StackSlot(op->index()); | 587       translation->StoreUint32StackSlot(op->index()); | 
| 613     } else { | 588     } else { | 
| 614       translation->StoreInt32StackSlot(op->index()); | 589       translation->StoreInt32StackSlot(op->index()); | 
| 615     } | 590     } | 
| 616   } else if (op->IsDoubleStackSlot()) { | 591   } else if (op->IsDoubleStackSlot()) { | 
| 617     translation->StoreDoubleStackSlot(op->index()); | 592     translation->StoreDoubleStackSlot(op->index()); | 
| 618   } else if (op->IsArgument()) { | 593   } else if (op->IsArgument()) { | 
| (...skipping 84 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 703     // 0 ..................................................... size-1 | 678     // 0 ..................................................... size-1 | 
| 704     // [parameters] [locals] [expression stack including arguments] | 679     // [parameters] [locals] [expression stack including arguments] | 
| 705 | 680 | 
| 706     // Layout of the translation: | 681     // Layout of the translation: | 
| 707     // 0 ........................................................ size - 1 + 4 | 682     // 0 ........................................................ size - 1 + 4 | 
| 708     // [expression stack including arguments] [locals] [4 words] [parameters] | 683     // [expression stack including arguments] [locals] [4 words] [parameters] | 
| 709     // |>------------  translation_size ------------<| | 684     // |>------------  translation_size ------------<| | 
| 710 | 685 | 
| 711     int frame_count = 0; | 686     int frame_count = 0; | 
| 712     int jsframe_count = 0; | 687     int jsframe_count = 0; | 
| 713     int args_index = 0; |  | 
| 714     int args_count = 0; |  | 
| 715     for (LEnvironment* e = environment; e != NULL; e = e->outer()) { | 688     for (LEnvironment* e = environment; e != NULL; e = e->outer()) { | 
| 716       ++frame_count; | 689       ++frame_count; | 
| 717       if (e->frame_type() == JS_FUNCTION) { | 690       if (e->frame_type() == JS_FUNCTION) { | 
| 718         ++jsframe_count; | 691         ++jsframe_count; | 
| 719       } | 692       } | 
| 720     } | 693     } | 
| 721     Translation translation(&translations_, frame_count, jsframe_count, zone()); | 694     Translation translation(&translations_, frame_count, jsframe_count, zone()); | 
| 722     WriteTranslation(environment, &translation, &args_index, &args_count); | 695     WriteTranslation(environment, &translation); | 
| 723     int deoptimization_index = deoptimizations_.length(); | 696     int deoptimization_index = deoptimizations_.length(); | 
| 724     int pc_offset = masm()->pc_offset(); | 697     int pc_offset = masm()->pc_offset(); | 
| 725     environment->Register(deoptimization_index, | 698     environment->Register(deoptimization_index, | 
| 726                           translation.index(), | 699                           translation.index(), | 
| 727                           (mode == Safepoint::kLazyDeopt) ? pc_offset : -1); | 700                           (mode == Safepoint::kLazyDeopt) ? pc_offset : -1); | 
| 728     deoptimizations_.Add(environment, environment->zone()); | 701     deoptimizations_.Add(environment, environment->zone()); | 
| 729   } | 702   } | 
| 730 } | 703 } | 
| 731 | 704 | 
| 732 | 705 | 
| (...skipping 4901 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
| 5634                                FixedArray::kHeaderSize - kPointerSize)); | 5607                                FixedArray::kHeaderSize - kPointerSize)); | 
| 5635   __ bind(&done); | 5608   __ bind(&done); | 
| 5636 } | 5609 } | 
| 5637 | 5610 | 
| 5638 | 5611 | 
| 5639 #undef __ | 5612 #undef __ | 
| 5640 | 5613 | 
| 5641 } }  // namespace v8::internal | 5614 } }  // namespace v8::internal | 
| 5642 | 5615 | 
| 5643 #endif  // V8_TARGET_ARCH_X64 | 5616 #endif  // V8_TARGET_ARCH_X64 | 
| OLD | NEW | 
|---|