| Index: src/ia32/codegen-ia32.cc
|
| ===================================================================
|
| --- src/ia32/codegen-ia32.cc (revision 4383)
|
| +++ src/ia32/codegen-ia32.cc (working copy)
|
| @@ -6438,7 +6438,7 @@
|
| Label slow_allocate_heapnumber;
|
| Label heapnumber_allocated;
|
|
|
| - __ AllocateHeapNumber(eax, ebx, ecx, &slow_allocate_heapnumber);
|
| + __ AllocateHeapNumber(edi, ebx, ecx, &slow_allocate_heapnumber);
|
| __ jmp(&heapnumber_allocated);
|
|
|
| __ bind(&slow_allocate_heapnumber);
|
| @@ -6447,14 +6447,39 @@
|
| // -0.0. A new, distinct heap number is returned each time.
|
| __ push(Immediate(Smi::FromInt(0)));
|
| __ CallRuntime(Runtime::kNumberUnaryMinus, 1);
|
| + __ mov(edi, eax);
|
|
|
| __ bind(&heapnumber_allocated);
|
|
|
| - __ PrepareCallCFunction(1, ebx);
|
| - __ mov(Operand(esp, 0), eax);
|
| - __ CallCFunction(ExternalReference::fill_heap_number_with_random_function(),
|
| - 1);
|
| + __ PrepareCallCFunction(0, ebx);
|
| + __ CallCFunction(ExternalReference::random_uint32_function(), 0);
|
|
|
| + // Convert 32 random bits in eax to 0.(32 random bits) in a double
|
| + // by computing:
|
| + // ( 1.(20 0s)(32 random bits) x 2^20 ) - (1.0 x 2^20)).
|
| + // This is implemented on both SSE2 and FPU.
|
| + if (CpuFeatures::IsSupported(SSE2)) {
|
| + CpuFeatures::Scope fscope(SSE2);
|
| + __ mov(ebx, Immediate(0x49800000)); // 1.0 x 2^20 as single.
|
| + __ movd(xmm1, Operand(ebx));
|
| + __ movd(xmm0, Operand(eax));
|
| + __ cvtss2sd(xmm1, xmm1);
|
| + __ pxor(xmm0, xmm1);
|
| + __ subsd(xmm0, xmm1);
|
| + __ movdbl(FieldOperand(edi, HeapNumber::kValueOffset), xmm0);
|
| + } else {
|
| + // 0x4130000000000000 is 1.0 x 2^20 as a double.
|
| + __ mov(FieldOperand(edi, HeapNumber::kExponentOffset),
|
| + Immediate(0x41300000));
|
| + __ mov(FieldOperand(edi, HeapNumber::kMantissaOffset), eax);
|
| + __ fld_d(FieldOperand(edi, HeapNumber::kValueOffset));
|
| + __ mov(FieldOperand(edi, HeapNumber::kMantissaOffset), Immediate(0));
|
| + __ fld_d(FieldOperand(edi, HeapNumber::kValueOffset));
|
| + __ fsubp(1);
|
| + __ fstp_d(FieldOperand(edi, HeapNumber::kValueOffset));
|
| + }
|
| + __ mov(eax, edi);
|
| +
|
| Result result = allocator_->Allocate(eax);
|
| frame_->Push(&result);
|
| }
|
|
|