diff options
Diffstat (limited to 'deps/v8/src/ia32/lithium-codegen-ia32.cc')
-rw-r--r-- | deps/v8/src/ia32/lithium-codegen-ia32.cc | 359 |
1 files changed, 119 insertions, 240 deletions
diff --git a/deps/v8/src/ia32/lithium-codegen-ia32.cc b/deps/v8/src/ia32/lithium-codegen-ia32.cc index e03f73323d..32c66a05f5 100644 --- a/deps/v8/src/ia32/lithium-codegen-ia32.cc +++ b/deps/v8/src/ia32/lithium-codegen-ia32.cc @@ -176,7 +176,6 @@ bool LCodeGen::GeneratePrologue() { __ bind(&do_not_pad); } - info()->set_prologue_offset(masm_->pc_offset()); __ push(ebp); // Caller's frame pointer. __ mov(ebp, esp); __ push(esi); // Callee's context. @@ -294,30 +293,7 @@ bool LCodeGen::GenerateBody() { } if (emit_instructions) { - if (FLAG_code_comments) { - HValue* hydrogen = instr->hydrogen_value(); - if (hydrogen != NULL) { - if (hydrogen->IsChange()) { - HValue* changed_value = HChange::cast(hydrogen)->value(); - int use_id = 0; - const char* use_mnemo = "dead"; - if (hydrogen->UseCount() >= 1) { - HValue* use_value = hydrogen->uses().value(); - use_id = use_value->id(); - use_mnemo = use_value->Mnemonic(); - } - Comment(";;; @%d: %s. <of #%d %s for #%d %s>", - current_instruction_, instr->Mnemonic(), - changed_value->id(), changed_value->Mnemonic(), - use_id, use_mnemo); - } else { - Comment(";;; @%d: %s. <#%d>", current_instruction_, - instr->Mnemonic(), hydrogen->id()); - } - } else { - Comment(";;; @%d: %s.", current_instruction_, instr->Mnemonic()); - } - } + Comment(";;; @%d: %s.", current_instruction_, instr->Mnemonic()); instr->CompileToNative(this); } } @@ -1044,43 +1020,6 @@ void LCodeGen::DoModI(LModI* instr) { void LCodeGen::DoDivI(LDivI* instr) { - if (instr->hydrogen()->HasPowerOf2Divisor()) { - Register dividend = ToRegister(instr->left()); - int32_t divisor = - HConstant::cast(instr->hydrogen()->right())->Integer32Value(); - int32_t test_value = 0; - int32_t power = 0; - - if (divisor > 0) { - test_value = divisor - 1; - power = WhichPowerOf2(divisor); - } else { - // Check for (0 / -x) that will produce negative zero. - if (instr->hydrogen()->CheckFlag(HValue::kBailoutOnMinusZero)) { - __ test(dividend, Operand(dividend)); - DeoptimizeIf(zero, instr->environment()); - } - // Check for (kMinInt / -1). - if (divisor == -1 && instr->hydrogen()->CheckFlag(HValue::kCanOverflow)) { - __ cmp(dividend, kMinInt); - DeoptimizeIf(zero, instr->environment()); - } - test_value = - divisor - 1; - power = WhichPowerOf2(-divisor); - } - - if (test_value != 0) { - // Deoptimize if remainder is not 0. - __ test(dividend, Immediate(test_value)); - DeoptimizeIf(not_zero, instr->environment()); - __ sar(dividend, power); - } - - if (divisor < 0) __ neg(dividend); - - return; - } - LOperand* right = instr->right(); ASSERT(ToRegister(instr->result()).is(eax)); ASSERT(ToRegister(instr->left()).is(eax)); @@ -1106,7 +1045,7 @@ void LCodeGen::DoDivI(LDivI* instr) { __ bind(&left_not_zero); } - // Check for (kMinInt / -1). + // Check for (-kMinInt / -1). if (instr->hydrogen()->CheckFlag(HValue::kCanOverflow)) { Label left_not_min_int; __ cmp(left_reg, kMinInt); @@ -1361,13 +1300,6 @@ void LCodeGen::DoShiftI(LShiftI* instr) { ASSERT(ToRegister(right).is(ecx)); switch (instr->op()) { - case Token::ROR: - __ ror_cl(ToRegister(left)); - if (instr->can_deopt()) { - __ test(ToRegister(left), Immediate(0x80000000)); - DeoptimizeIf(not_zero, instr->environment()); - } - break; case Token::SAR: __ sar_cl(ToRegister(left)); break; @@ -1389,14 +1321,6 @@ void LCodeGen::DoShiftI(LShiftI* instr) { int value = ToInteger32(LConstantOperand::cast(right)); uint8_t shift_count = static_cast<uint8_t>(value & 0x1F); switch (instr->op()) { - case Token::ROR: - if (shift_count == 0 && instr->can_deopt()) { - __ test(ToRegister(left), Immediate(0x80000000)); - DeoptimizeIf(not_zero, instr->environment()); - } else { - __ ror(ToRegister(left), shift_count); - } - break; case Token::SAR: if (shift_count != 0) { __ sar(ToRegister(left), shift_count); @@ -1587,15 +1511,6 @@ void LCodeGen::DoDateField(LDateField* instr) { } -void LCodeGen::DoSeqStringSetChar(LSeqStringSetChar* instr) { - SeqStringSetCharGenerator::Generate(masm(), - instr->encoding(), - ToRegister(instr->string()), - ToRegister(instr->index()), - ToRegister(instr->value())); -} - - void LCodeGen::DoBitNotI(LBitNotI* instr) { LOperand* input = instr->value(); ASSERT(input->Equals(instr->result())); @@ -2834,71 +2749,33 @@ void LCodeGen::DoAccessArgumentsAt(LAccessArgumentsAt* instr) { } -void LCodeGen::DoLoadKeyedExternalArray(LLoadKeyed* instr) { - ElementsKind elements_kind = instr->elements_kind(); - LOperand* key = instr->key(); - if (!key->IsConstantOperand() && - ExternalArrayOpRequiresTemp(instr->hydrogen()->key()->representation(), - elements_kind)) { - __ SmiUntag(ToRegister(key)); - } - Operand operand(BuildFastArrayOperand( - instr->elements(), - key, - instr->hydrogen()->key()->representation(), - elements_kind, - 0, - instr->additional_index())); - if (elements_kind == EXTERNAL_FLOAT_ELEMENTS) { - XMMRegister result(ToDoubleRegister(instr->result())); - __ movss(result, operand); - __ cvtss2sd(result, result); - } else if (elements_kind == EXTERNAL_DOUBLE_ELEMENTS) { - __ movdbl(ToDoubleRegister(instr->result()), operand); - } else { - Register result(ToRegister(instr->result())); - switch (elements_kind) { - case EXTERNAL_BYTE_ELEMENTS: - __ movsx_b(result, operand); - break; - case EXTERNAL_PIXEL_ELEMENTS: - case EXTERNAL_UNSIGNED_BYTE_ELEMENTS: - __ movzx_b(result, operand); - break; - case EXTERNAL_SHORT_ELEMENTS: - __ movsx_w(result, operand); - break; - case EXTERNAL_UNSIGNED_SHORT_ELEMENTS: - __ movzx_w(result, operand); - break; - case EXTERNAL_INT_ELEMENTS: - __ mov(result, operand); - break; - case EXTERNAL_UNSIGNED_INT_ELEMENTS: - __ mov(result, operand); - if (!instr->hydrogen()->CheckFlag(HInstruction::kUint32)) { - __ test(result, Operand(result)); - DeoptimizeIf(negative, instr->environment()); - } - break; - case EXTERNAL_FLOAT_ELEMENTS: - case EXTERNAL_DOUBLE_ELEMENTS: - case FAST_SMI_ELEMENTS: - case FAST_ELEMENTS: - case FAST_DOUBLE_ELEMENTS: - case FAST_HOLEY_SMI_ELEMENTS: - case FAST_HOLEY_ELEMENTS: - case FAST_HOLEY_DOUBLE_ELEMENTS: - case DICTIONARY_ELEMENTS: - case NON_STRICT_ARGUMENTS_ELEMENTS: - UNREACHABLE(); - break; +void LCodeGen::DoLoadKeyedFastElement(LLoadKeyedFastElement* instr) { + Register result = ToRegister(instr->result()); + + // Load the result. + __ mov(result, + BuildFastArrayOperand(instr->elements(), + instr->key(), + instr->hydrogen()->key()->representation(), + FAST_ELEMENTS, + FixedArray::kHeaderSize - kHeapObjectTag, + instr->additional_index())); + + // Check for the hole value. + if (instr->hydrogen()->RequiresHoleCheck()) { + if (IsFastSmiElementsKind(instr->hydrogen()->elements_kind())) { + __ test(result, Immediate(kSmiTagMask)); + DeoptimizeIf(not_equal, instr->environment()); + } else { + __ cmp(result, factory()->the_hole_value()); + DeoptimizeIf(equal, instr->environment()); } } } -void LCodeGen::DoLoadKeyedFixedDoubleArray(LLoadKeyed* instr) { +void LCodeGen::DoLoadKeyedFastDoubleElement( + LLoadKeyedFastDoubleElement* instr) { XMMRegister result = ToDoubleRegister(instr->result()); if (instr->hydrogen()->RequiresHoleCheck()) { @@ -2925,42 +2802,6 @@ void LCodeGen::DoLoadKeyedFixedDoubleArray(LLoadKeyed* instr) { } -void LCodeGen::DoLoadKeyedFixedArray(LLoadKeyed* instr) { - Register result = ToRegister(instr->result()); - - // Load the result. - __ mov(result, - BuildFastArrayOperand(instr->elements(), - instr->key(), - instr->hydrogen()->key()->representation(), - FAST_ELEMENTS, - FixedArray::kHeaderSize - kHeapObjectTag, - instr->additional_index())); - - // Check for the hole value. - if (instr->hydrogen()->RequiresHoleCheck()) { - if (IsFastSmiElementsKind(instr->hydrogen()->elements_kind())) { - __ test(result, Immediate(kSmiTagMask)); - DeoptimizeIf(not_equal, instr->environment()); - } else { - __ cmp(result, factory()->the_hole_value()); - DeoptimizeIf(equal, instr->environment()); - } - } -} - - -void LCodeGen::DoLoadKeyed(LLoadKeyed* instr) { - if (instr->is_external()) { - DoLoadKeyedExternalArray(instr); - } else if (instr->hydrogen()->representation().IsDouble()) { - DoLoadKeyedFixedDoubleArray(instr); - } else { - DoLoadKeyedFixedArray(instr); - } -} - - Operand LCodeGen::BuildFastArrayOperand( LOperand* elements_pointer, LOperand* key, @@ -2970,7 +2811,7 @@ Operand LCodeGen::BuildFastArrayOperand( uint32_t additional_index) { Register elements_pointer_reg = ToRegister(elements_pointer); int shift_size = ElementsKindToShiftSize(elements_kind); - // Even though the HLoad/StoreKeyed instructions force the input + // Even though the HLoad/StoreKeyedFastElement instructions force the input // representation for the key to be an integer, the input gets replaced during // bound check elimination with the index argument to the bounds check, which // can be tagged, so that case must be handled here, too. @@ -2995,6 +2836,71 @@ Operand LCodeGen::BuildFastArrayOperand( } +void LCodeGen::DoLoadKeyedSpecializedArrayElement( + LLoadKeyedSpecializedArrayElement* instr) { + ElementsKind elements_kind = instr->elements_kind(); + LOperand* key = instr->key(); + if (!key->IsConstantOperand() && + ExternalArrayOpRequiresTemp(instr->hydrogen()->key()->representation(), + elements_kind)) { + __ SmiUntag(ToRegister(key)); + } + Operand operand(BuildFastArrayOperand( + instr->external_pointer(), + key, + instr->hydrogen()->key()->representation(), + elements_kind, + 0, + instr->additional_index())); + if (elements_kind == EXTERNAL_FLOAT_ELEMENTS) { + XMMRegister result(ToDoubleRegister(instr->result())); + __ movss(result, operand); + __ cvtss2sd(result, result); + } else if (elements_kind == EXTERNAL_DOUBLE_ELEMENTS) { + __ movdbl(ToDoubleRegister(instr->result()), operand); + } else { + Register result(ToRegister(instr->result())); + switch (elements_kind) { + case EXTERNAL_BYTE_ELEMENTS: + __ movsx_b(result, operand); + break; + case EXTERNAL_PIXEL_ELEMENTS: + case EXTERNAL_UNSIGNED_BYTE_ELEMENTS: + __ movzx_b(result, operand); + break; + case EXTERNAL_SHORT_ELEMENTS: + __ movsx_w(result, operand); + break; + case EXTERNAL_UNSIGNED_SHORT_ELEMENTS: + __ movzx_w(result, operand); + break; + case EXTERNAL_INT_ELEMENTS: + __ mov(result, operand); + break; + case EXTERNAL_UNSIGNED_INT_ELEMENTS: + __ mov(result, operand); + if (!instr->hydrogen()->CheckFlag(HInstruction::kUint32)) { + __ test(result, Operand(result)); + DeoptimizeIf(negative, instr->environment()); + } + break; + case EXTERNAL_FLOAT_ELEMENTS: + case EXTERNAL_DOUBLE_ELEMENTS: + case FAST_SMI_ELEMENTS: + case FAST_ELEMENTS: + case FAST_DOUBLE_ELEMENTS: + case FAST_HOLEY_SMI_ELEMENTS: + case FAST_HOLEY_ELEMENTS: + case FAST_HOLEY_DOUBLE_ELEMENTS: + case DICTIONARY_ELEMENTS: + case NON_STRICT_ARGUMENTS_ELEMENTS: + UNREACHABLE(); + break; + } + } +} + + void LCodeGen::DoLoadKeyedGeneric(LLoadKeyedGeneric* instr) { ASSERT(ToRegister(instr->context()).is(esi)); ASSERT(ToRegister(instr->object()).is(edx)); @@ -3647,16 +3553,6 @@ void LCodeGen::DoMathLog(LUnaryMathOperation* instr) { } -void LCodeGen::DoMathExp(LMathExp* instr) { - XMMRegister input = ToDoubleRegister(instr->value()); - XMMRegister result = ToDoubleRegister(instr->result()); - Register temp1 = ToRegister(instr->temp1()); - Register temp2 = ToRegister(instr->temp2()); - - MathExpGenerator::EmitMathExp(masm(), input, result, xmm0, temp1, temp2); -} - - void LCodeGen::DoMathTan(LUnaryMathOperation* instr) { ASSERT(ToDoubleRegister(instr->result()).is(xmm1)); TranscendentalCacheStub stub(TranscendentalCache::TAN, @@ -3922,7 +3818,8 @@ void LCodeGen::DoBoundsCheck(LBoundsCheck* instr) { } -void LCodeGen::DoStoreKeyedExternalArray(LStoreKeyed* instr) { +void LCodeGen::DoStoreKeyedSpecializedArrayElement( + LStoreKeyedSpecializedArrayElement* instr) { ElementsKind elements_kind = instr->elements_kind(); LOperand* key = instr->key(); if (!key->IsConstantOperand() && @@ -3931,7 +3828,7 @@ void LCodeGen::DoStoreKeyedExternalArray(LStoreKeyed* instr) { __ SmiUntag(ToRegister(key)); } Operand operand(BuildFastArrayOperand( - instr->elements(), + instr->external_pointer(), key, instr->hydrogen()->key()->representation(), elements_kind, @@ -3975,39 +3872,13 @@ void LCodeGen::DoStoreKeyedExternalArray(LStoreKeyed* instr) { } -void LCodeGen::DoStoreKeyedFixedDoubleArray(LStoreKeyed* instr) { - XMMRegister value = ToDoubleRegister(instr->value()); - - if (instr->NeedsCanonicalization()) { - Label have_value; - - __ ucomisd(value, value); - __ j(parity_odd, &have_value); // NaN. - - ExternalReference canonical_nan_reference = - ExternalReference::address_of_canonical_non_hole_nan(); - __ movdbl(value, Operand::StaticVariable(canonical_nan_reference)); - __ bind(&have_value); - } - - Operand double_store_operand = BuildFastArrayOperand( - instr->elements(), - instr->key(), - instr->hydrogen()->key()->representation(), - FAST_DOUBLE_ELEMENTS, - FixedDoubleArray::kHeaderSize - kHeapObjectTag, - instr->additional_index()); - __ movdbl(double_store_operand, value); -} - - -void LCodeGen::DoStoreKeyedFixedArray(LStoreKeyed* instr) { +void LCodeGen::DoStoreKeyedFastElement(LStoreKeyedFastElement* instr) { Register value = ToRegister(instr->value()); - Register elements = ToRegister(instr->elements()); + Register elements = ToRegister(instr->object()); Register key = instr->key()->IsRegister() ? ToRegister(instr->key()) : no_reg; Operand operand = BuildFastArrayOperand( - instr->elements(), + instr->object(), instr->key(), instr->hydrogen()->key()->representation(), FAST_ELEMENTS, @@ -4032,15 +3903,30 @@ void LCodeGen::DoStoreKeyedFixedArray(LStoreKeyed* instr) { } -void LCodeGen::DoStoreKeyed(LStoreKeyed* instr) { - // By cases...external, fast-double, fast - if (instr->is_external()) { - DoStoreKeyedExternalArray(instr); - } else if (instr->hydrogen()->value()->representation().IsDouble()) { - DoStoreKeyedFixedDoubleArray(instr); - } else { - DoStoreKeyedFixedArray(instr); +void LCodeGen::DoStoreKeyedFastDoubleElement( + LStoreKeyedFastDoubleElement* instr) { + XMMRegister value = ToDoubleRegister(instr->value()); + + if (instr->NeedsCanonicalization()) { + Label have_value; + + __ ucomisd(value, value); + __ j(parity_odd, &have_value); // NaN. + + ExternalReference canonical_nan_reference = + ExternalReference::address_of_canonical_non_hole_nan(); + __ movdbl(value, Operand::StaticVariable(canonical_nan_reference)); + __ bind(&have_value); } + + Operand double_store_operand = BuildFastArrayOperand( + instr->elements(), + instr->key(), + instr->hydrogen()->key()->representation(), + FAST_DOUBLE_ELEMENTS, + FixedDoubleArray::kHeaderSize - kHeapObjectTag, + instr->additional_index()); + __ movdbl(double_store_operand, value); } @@ -4482,7 +4368,6 @@ void LCodeGen::DoDeferredTaggedToI(LTaggedToI* instr) { // Check for undefined. Undefined is converted to zero for truncating // conversions. __ cmp(input_reg, factory()->undefined_value()); - __ RecordComment("Deferred TaggedToI: cannot truncate"); DeoptimizeIf(not_equal, instr->environment()); __ mov(input_reg, 0); __ jmp(&done, Label::kNear); @@ -4503,7 +4388,6 @@ void LCodeGen::DoDeferredTaggedToI(LTaggedToI* instr) { __ j(less, &convert, Label::kNear); // Pop FPU stack before deoptimizing. __ fstp(0); - __ RecordComment("Deferred TaggedToI: exponent too big"); DeoptimizeIf(no_condition, instr->environment()); // Reserve space for 64 bit answer. @@ -4529,7 +4413,6 @@ void LCodeGen::DoDeferredTaggedToI(LTaggedToI* instr) { } } else { // Deoptimize if we don't have a heap number. - __ RecordComment("Deferred TaggedToI: not a heap number"); DeoptimizeIf(not_equal, instr->environment()); XMMRegister xmm_temp = ToDoubleRegister(instr->temp()); @@ -4537,16 +4420,13 @@ void LCodeGen::DoDeferredTaggedToI(LTaggedToI* instr) { __ cvttsd2si(input_reg, Operand(xmm0)); __ cvtsi2sd(xmm_temp, Operand(input_reg)); __ ucomisd(xmm0, xmm_temp); - __ RecordComment("Deferred TaggedToI: lost precision"); DeoptimizeIf(not_equal, instr->environment()); - __ RecordComment("Deferred TaggedToI: NaN"); DeoptimizeIf(parity_even, instr->environment()); // NaN. if (instr->hydrogen()->CheckFlag(HValue::kBailoutOnMinusZero)) { __ test(input_reg, Operand(input_reg)); __ j(not_zero, &done); __ movmskpd(input_reg, xmm0); __ and_(input_reg, 1); - __ RecordComment("Deferred TaggedToI: minus zero"); DeoptimizeIf(not_zero, instr->environment()); } } @@ -4876,7 +4756,6 @@ void LCodeGen::DoClampTToUint8(LClampTToUint8* instr) { void LCodeGen::DoCheckPrototypeMaps(LCheckPrototypeMaps* instr) { - ASSERT(instr->temp()->Equals(instr->result())); Register reg = ToRegister(instr->temp()); Handle<JSObject> holder = instr->holder(); |