Add enumeration to specify if smi check needed
R==ager@chromium.org BUG=none TEST=none Review URL: http://codereview.chromium.org/7039004 git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@7914 ce2b1a6d-e550-0410-aec6-3dcde31c8c00
This commit is contained in:
parent
0eca2b4fc1
commit
ecc25bfb47
@ -1369,7 +1369,7 @@ void NumberToStringStub::GenerateLookupNumberStringCache(MacroAssembler* masm,
|
||||
scratch1,
|
||||
Heap::kHeapNumberMapRootIndex,
|
||||
not_found,
|
||||
true);
|
||||
DONT_DO_SMI_CHECK);
|
||||
|
||||
STATIC_ASSERT(8 == kDoubleSize);
|
||||
__ add(scratch1,
|
||||
@ -3021,7 +3021,7 @@ void TranscendentalCacheStub::Generate(MacroAssembler* masm) {
|
||||
r1,
|
||||
Heap::kHeapNumberMapRootIndex,
|
||||
&calculate,
|
||||
true);
|
||||
DONT_DO_SMI_CHECK);
|
||||
// Input is a HeapNumber. Load it to a double register and store the
|
||||
// low and high words into r2, r3.
|
||||
__ vldr(d0, FieldMemOperand(r0, HeapNumber::kValueOffset));
|
||||
@ -4693,7 +4693,7 @@ void StringCharCodeAtGenerator::GenerateSlow(
|
||||
scratch_,
|
||||
Heap::kHeapNumberMapRootIndex,
|
||||
index_not_number_,
|
||||
true);
|
||||
DONT_DO_SMI_CHECK);
|
||||
call_helper.BeforeCall(masm);
|
||||
__ Push(object_, index_);
|
||||
__ push(index_); // Consumed by runtime conversion function.
|
||||
|
@ -1655,8 +1655,8 @@ void MacroAssembler::CheckMap(Register obj,
|
||||
Register scratch,
|
||||
Handle<Map> map,
|
||||
Label* fail,
|
||||
bool is_heap_object) {
|
||||
if (!is_heap_object) {
|
||||
SmiCheckType smi_check_type) {
|
||||
if (smi_check_type == DO_SMI_CHECK) {
|
||||
JumpIfSmi(obj, fail);
|
||||
}
|
||||
ldr(scratch, FieldMemOperand(obj, HeapObject::kMapOffset));
|
||||
@ -1670,8 +1670,8 @@ void MacroAssembler::CheckMap(Register obj,
|
||||
Register scratch,
|
||||
Heap::RootListIndex index,
|
||||
Label* fail,
|
||||
bool is_heap_object) {
|
||||
if (!is_heap_object) {
|
||||
SmiCheckType smi_check_type) {
|
||||
if (smi_check_type == DO_SMI_CHECK) {
|
||||
JumpIfSmi(obj, fail);
|
||||
}
|
||||
ldr(scratch, FieldMemOperand(obj, HeapObject::kMapOffset));
|
||||
@ -2521,7 +2521,7 @@ void MacroAssembler::LoadGlobalFunctionInitialMap(Register function,
|
||||
ldr(map, FieldMemOperand(function, JSFunction::kPrototypeOrInitialMapOffset));
|
||||
if (emit_debug_code()) {
|
||||
Label ok, fail;
|
||||
CheckMap(map, scratch, Heap::kMetaMapRootIndex, &fail, false);
|
||||
CheckMap(map, scratch, Heap::kMetaMapRootIndex, &fail, DO_SMI_CHECK);
|
||||
b(&ok);
|
||||
bind(&fail);
|
||||
Abort("Global functions must have initial map");
|
||||
|
@ -29,6 +29,7 @@
|
||||
#define V8_ARM_MACRO_ASSEMBLER_ARM_H_
|
||||
|
||||
#include "assembler.h"
|
||||
#include "v8globals.h"
|
||||
|
||||
namespace v8 {
|
||||
namespace internal {
|
||||
@ -575,13 +576,13 @@ class MacroAssembler: public Assembler {
|
||||
Register scratch,
|
||||
Handle<Map> map,
|
||||
Label* fail,
|
||||
bool is_heap_object);
|
||||
SmiCheckType smi_check_type);
|
||||
|
||||
void CheckMap(Register obj,
|
||||
Register scratch,
|
||||
Heap::RootListIndex index,
|
||||
Label* fail,
|
||||
bool is_heap_object);
|
||||
SmiCheckType smi_check_type);
|
||||
|
||||
|
||||
// Compare the object in a register to a value from the root list.
|
||||
|
@ -1550,8 +1550,11 @@ MaybeObject* CallStubCompiler::CompileArrayPushCall(Object* object,
|
||||
__ ldr(elements, FieldMemOperand(receiver, JSArray::kElementsOffset));
|
||||
|
||||
// Check that the elements are in fast mode and writable.
|
||||
__ CheckMap(elements, r0,
|
||||
Heap::kFixedArrayMapRootIndex, &call_builtin, true);
|
||||
__ CheckMap(elements,
|
||||
r0,
|
||||
Heap::kFixedArrayMapRootIndex,
|
||||
&call_builtin,
|
||||
DONT_DO_SMI_CHECK);
|
||||
|
||||
if (argc == 1) { // Otherwise fall through to call the builtin.
|
||||
Label exit, with_write_barrier, attempt_to_grow_elements;
|
||||
@ -1700,7 +1703,11 @@ MaybeObject* CallStubCompiler::CompileArrayPopCall(Object* object,
|
||||
__ ldr(elements, FieldMemOperand(receiver, JSArray::kElementsOffset));
|
||||
|
||||
// Check that the elements are in fast mode and writable.
|
||||
__ CheckMap(elements, r0, Heap::kFixedArrayMapRootIndex, &call_builtin, true);
|
||||
__ CheckMap(elements,
|
||||
r0,
|
||||
Heap::kFixedArrayMapRootIndex,
|
||||
&call_builtin,
|
||||
DONT_DO_SMI_CHECK);
|
||||
|
||||
// Get the array's length into r4 and calculate new length.
|
||||
__ ldr(r4, FieldMemOperand(receiver, JSArray::kLengthOffset));
|
||||
@ -2042,7 +2049,7 @@ MaybeObject* CallStubCompiler::CompileMathFloorCall(Object* object,
|
||||
__ Drop(argc + 1, eq);
|
||||
__ Ret(eq);
|
||||
|
||||
__ CheckMap(r0, r1, Heap::kHeapNumberMapRootIndex, &slow, true);
|
||||
__ CheckMap(r0, r1, Heap::kHeapNumberMapRootIndex, &slow, DONT_DO_SMI_CHECK);
|
||||
|
||||
Label wont_fit_smi, no_vfp_exception, restore_fpscr_and_return;
|
||||
|
||||
@ -2203,7 +2210,7 @@ MaybeObject* CallStubCompiler::CompileMathAbsCall(Object* object,
|
||||
// Check if the argument is a heap number and load its exponent and
|
||||
// sign.
|
||||
__ bind(¬_smi);
|
||||
__ CheckMap(r0, r1, Heap::kHeapNumberMapRootIndex, &slow, true);
|
||||
__ CheckMap(r0, r1, Heap::kHeapNumberMapRootIndex, &slow, DONT_DO_SMI_CHECK);
|
||||
__ ldr(r1, FieldMemOperand(r0, HeapNumber::kExponentOffset));
|
||||
|
||||
// Check the sign of the argument. If the argument is positive,
|
||||
|
@ -4672,7 +4672,7 @@ void StringCharCodeAtGenerator::GenerateSlow(
|
||||
__ CheckMap(index_,
|
||||
masm->isolate()->factory()->heap_number_map(),
|
||||
index_not_number_,
|
||||
true);
|
||||
DONT_DO_SMI_CHECK);
|
||||
call_helper.BeforeCall(masm);
|
||||
__ push(object_);
|
||||
__ push(index_);
|
||||
|
@ -93,7 +93,7 @@ static void GenerateStringDictionaryReceiverCheck(MacroAssembler* masm,
|
||||
__ j(not_zero, miss);
|
||||
|
||||
__ mov(r0, FieldOperand(receiver, JSObject::kPropertiesOffset));
|
||||
__ CheckMap(r0, FACTORY->hash_table_map(), miss, true);
|
||||
__ CheckMap(r0, FACTORY->hash_table_map(), miss, DONT_DO_SMI_CHECK);
|
||||
}
|
||||
|
||||
|
||||
@ -414,7 +414,10 @@ static void GenerateFastArrayLoad(MacroAssembler* masm,
|
||||
__ mov(scratch, FieldOperand(receiver, JSObject::kElementsOffset));
|
||||
if (not_fast_array != NULL) {
|
||||
// Check that the object is in fast mode and writable.
|
||||
__ CheckMap(scratch, FACTORY->fixed_array_map(), not_fast_array, true);
|
||||
__ CheckMap(scratch,
|
||||
FACTORY->fixed_array_map(),
|
||||
not_fast_array,
|
||||
DONT_DO_SMI_CHECK);
|
||||
} else {
|
||||
__ AssertFastElements(scratch);
|
||||
}
|
||||
@ -509,7 +512,10 @@ void KeyedLoadIC::GenerateGeneric(MacroAssembler* masm) {
|
||||
// ebx: untagged index
|
||||
// eax: key
|
||||
// ecx: elements
|
||||
__ CheckMap(ecx, isolate->factory()->hash_table_map(), &slow, true);
|
||||
__ CheckMap(ecx,
|
||||
isolate->factory()->hash_table_map(),
|
||||
&slow,
|
||||
DONT_DO_SMI_CHECK);
|
||||
Label slow_pop_receiver;
|
||||
// Push receiver on the stack to free up a register for the dictionary
|
||||
// probing.
|
||||
@ -731,7 +737,7 @@ void KeyedStoreIC::GenerateGeneric(MacroAssembler* masm,
|
||||
// ecx: key (a smi)
|
||||
__ mov(edi, FieldOperand(edx, JSObject::kElementsOffset));
|
||||
// Check that the object is in fast mode and writable.
|
||||
__ CheckMap(edi, FACTORY->fixed_array_map(), &slow, true);
|
||||
__ CheckMap(edi, FACTORY->fixed_array_map(), &slow, DONT_DO_SMI_CHECK);
|
||||
__ cmp(ecx, FieldOperand(edi, FixedArray::kLengthOffset));
|
||||
__ j(below, &fast);
|
||||
|
||||
@ -765,7 +771,7 @@ void KeyedStoreIC::GenerateGeneric(MacroAssembler* masm,
|
||||
// edx: receiver, a JSArray
|
||||
// ecx: key, a smi.
|
||||
__ mov(edi, FieldOperand(edx, JSObject::kElementsOffset));
|
||||
__ CheckMap(edi, FACTORY->fixed_array_map(), &slow, true);
|
||||
__ CheckMap(edi, FACTORY->fixed_array_map(), &slow, DONT_DO_SMI_CHECK);
|
||||
|
||||
// Check the key against the length in the array, compute the
|
||||
// address to store into and fall through to fast case.
|
||||
@ -1049,7 +1055,10 @@ void KeyedCallIC::GenerateMegamorphic(MacroAssembler* masm, int argc) {
|
||||
// eax: elements
|
||||
// ecx: smi key
|
||||
// Check whether the elements is a number dictionary.
|
||||
__ CheckMap(eax, isolate->factory()->hash_table_map(), &slow_load, true);
|
||||
__ CheckMap(eax,
|
||||
isolate->factory()->hash_table_map(),
|
||||
&slow_load,
|
||||
DONT_DO_SMI_CHECK);
|
||||
__ mov(ebx, ecx);
|
||||
__ SmiUntag(ebx);
|
||||
// ebx: untagged index
|
||||
@ -1090,7 +1099,7 @@ void KeyedCallIC::GenerateMegamorphic(MacroAssembler* masm, int argc) {
|
||||
__ CheckMap(ebx,
|
||||
isolate->factory()->hash_table_map(),
|
||||
&lookup_monomorphic_cache,
|
||||
true);
|
||||
DONT_DO_SMI_CHECK);
|
||||
|
||||
GenerateDictionaryLoad(masm, &slow_load, ebx, ecx, eax, edi, edi);
|
||||
__ IncrementCounter(counters->keyed_call_generic_lookup_dict(), 1);
|
||||
|
@ -277,10 +277,9 @@ void MacroAssembler::CmpInstanceType(Register map, InstanceType type) {
|
||||
void MacroAssembler::CheckMap(Register obj,
|
||||
Handle<Map> map,
|
||||
Label* fail,
|
||||
bool is_heap_object) {
|
||||
if (!is_heap_object) {
|
||||
test(obj, Immediate(kSmiTagMask));
|
||||
j(zero, fail);
|
||||
SmiCheckType smi_check_type) {
|
||||
if (smi_check_type == DONT_DO_SMI_CHECK) {
|
||||
JumpIfSmi(obj, fail);
|
||||
}
|
||||
cmp(FieldOperand(obj, HeapObject::kMapOffset), Immediate(map));
|
||||
j(not_equal, fail);
|
||||
@ -1742,7 +1741,7 @@ void MacroAssembler::LoadGlobalFunctionInitialMap(Register function,
|
||||
mov(map, FieldOperand(function, JSFunction::kPrototypeOrInitialMapOffset));
|
||||
if (emit_debug_code()) {
|
||||
Label ok, fail;
|
||||
CheckMap(map, isolate()->factory()->meta_map(), &fail, false);
|
||||
CheckMap(map, isolate()->factory()->meta_map(), &fail, DO_SMI_CHECK);
|
||||
jmp(&ok);
|
||||
bind(&fail);
|
||||
Abort("Global functions must have initial map");
|
||||
|
@ -29,6 +29,7 @@
|
||||
#define V8_IA32_MACRO_ASSEMBLER_IA32_H_
|
||||
|
||||
#include "assembler.h"
|
||||
#include "v8globals.h"
|
||||
|
||||
namespace v8 {
|
||||
namespace internal {
|
||||
@ -211,7 +212,7 @@ class MacroAssembler: public Assembler {
|
||||
void CheckMap(Register obj,
|
||||
Handle<Map> map,
|
||||
Label* fail,
|
||||
bool is_heap_object);
|
||||
SmiCheckType smi_check_type);
|
||||
|
||||
// Check if the object in register heap_object is a string. Afterwards the
|
||||
// register map contains the object map and the register instance_type
|
||||
|
@ -1924,7 +1924,7 @@ MaybeObject* CallStubCompiler::CompileMathFloorCall(Object* object,
|
||||
|
||||
// Check if the argument is a heap number and load its value into xmm0.
|
||||
Label slow;
|
||||
__ CheckMap(eax, factory()->heap_number_map(), &slow, true);
|
||||
__ CheckMap(eax, factory()->heap_number_map(), &slow, DONT_DO_SMI_CHECK);
|
||||
__ movdbl(xmm0, FieldOperand(eax, HeapNumber::kValueOffset));
|
||||
|
||||
// Check if the argument is strictly positive. Note this also
|
||||
@ -2068,7 +2068,7 @@ MaybeObject* CallStubCompiler::CompileMathAbsCall(Object* object,
|
||||
// Check if the argument is a heap number and load its exponent and
|
||||
// sign into ebx.
|
||||
__ bind(¬_smi);
|
||||
__ CheckMap(eax, factory()->heap_number_map(), &slow, true);
|
||||
__ CheckMap(eax, factory()->heap_number_map(), &slow, DONT_DO_SMI_CHECK);
|
||||
__ mov(ebx, FieldOperand(eax, HeapNumber::kExponentOffset));
|
||||
|
||||
// Check the sign of the argument. If the argument is positive,
|
||||
@ -3322,7 +3322,7 @@ MaybeObject* ExternalArrayStubCompiler::CompileKeyedLoadStub(
|
||||
__ j(not_zero, &slow);
|
||||
|
||||
// Check that the map matches.
|
||||
__ CheckMap(edx, Handle<Map>(receiver->map()), &slow, false);
|
||||
__ CheckMap(edx, Handle<Map>(receiver->map()), &slow, DO_SMI_CHECK);
|
||||
__ mov(ebx, FieldOperand(edx, JSObject::kElementsOffset));
|
||||
|
||||
// eax: key, known to be a smi.
|
||||
@ -3476,7 +3476,7 @@ MaybeObject* ExternalArrayStubCompiler::CompileKeyedStoreStub(
|
||||
__ j(zero, &slow);
|
||||
|
||||
// Check that the map matches.
|
||||
__ CheckMap(edx, Handle<Map>(receiver->map()), &slow, false);
|
||||
__ CheckMap(edx, Handle<Map>(receiver->map()), &slow, DO_SMI_CHECK);
|
||||
|
||||
// Check that the key is a smi.
|
||||
__ test(ecx, Immediate(kSmiTagMask));
|
||||
|
@ -1,4 +1,4 @@
|
||||
// Copyright 2010 the V8 project authors. All rights reserved.
|
||||
// Copyright 2011 the V8 project authors. All rights reserved.
|
||||
// Redistribution and use in source and binary forms, with or without
|
||||
// modification, are permitted provided that the following conditions are
|
||||
// met:
|
||||
@ -482,6 +482,14 @@ enum StrictModeFlag {
|
||||
kInvalidStrictFlag
|
||||
};
|
||||
|
||||
|
||||
// Used to specify if a macro instruction must perform a smi check on tagged
|
||||
// values.
|
||||
enum SmiCheckType {
|
||||
DONT_DO_SMI_CHECK = 0,
|
||||
DO_SMI_CHECK
|
||||
};
|
||||
|
||||
} } // namespace v8::internal
|
||||
|
||||
#endif // V8_V8GLOBALS_H_
|
||||
|
@ -2551,7 +2551,10 @@ void NumberToStringStub::GenerateLookupNumberStringCache(MacroAssembler* masm,
|
||||
Factory* factory = masm->isolate()->factory();
|
||||
if (!object_is_smi) {
|
||||
__ JumpIfSmi(object, &is_smi);
|
||||
__ CheckMap(object, factory->heap_number_map(), not_found, true);
|
||||
__ CheckMap(object,
|
||||
factory->heap_number_map(),
|
||||
not_found,
|
||||
DONT_DO_SMI_CHECK);
|
||||
|
||||
STATIC_ASSERT(8 == kDoubleSize);
|
||||
__ movl(scratch, FieldOperand(object, HeapNumber::kValueOffset + 4));
|
||||
@ -3680,7 +3683,10 @@ void StringCharCodeAtGenerator::GenerateSlow(
|
||||
// Index is not a smi.
|
||||
__ bind(&index_not_smi_);
|
||||
// If index is a heap number, try converting it to an integer.
|
||||
__ CheckMap(index_, factory->heap_number_map(), index_not_number_, true);
|
||||
__ CheckMap(index_,
|
||||
factory->heap_number_map(),
|
||||
index_not_number_,
|
||||
DONT_DO_SMI_CHECK);
|
||||
call_helper.BeforeCall(masm);
|
||||
__ push(object_);
|
||||
__ push(index_);
|
||||
|
@ -2561,8 +2561,8 @@ void MacroAssembler::CmpInstanceType(Register map, InstanceType type) {
|
||||
void MacroAssembler::CheckMap(Register obj,
|
||||
Handle<Map> map,
|
||||
Label* fail,
|
||||
bool is_heap_object) {
|
||||
if (!is_heap_object) {
|
||||
SmiCheckType smi_check_type) {
|
||||
if (smi_check_type == DO_SMI_CHECK) {
|
||||
JumpIfSmi(obj, fail);
|
||||
}
|
||||
Cmp(FieldOperand(obj, HeapObject::kMapOffset), map);
|
||||
@ -3602,7 +3602,7 @@ void MacroAssembler::LoadGlobalFunctionInitialMap(Register function,
|
||||
movq(map, FieldOperand(function, JSFunction::kPrototypeOrInitialMapOffset));
|
||||
if (emit_debug_code()) {
|
||||
Label ok, fail;
|
||||
CheckMap(map, isolate()->factory()->meta_map(), &fail, false);
|
||||
CheckMap(map, isolate()->factory()->meta_map(), &fail, DO_SMI_CHECK);
|
||||
jmp(&ok);
|
||||
bind(&fail);
|
||||
Abort("Global functions must have initial map");
|
||||
|
@ -29,6 +29,7 @@
|
||||
#define V8_X64_MACRO_ASSEMBLER_X64_H_
|
||||
|
||||
#include "assembler.h"
|
||||
#include "v8globals.h"
|
||||
|
||||
namespace v8 {
|
||||
namespace internal {
|
||||
@ -749,7 +750,7 @@ class MacroAssembler: public Assembler {
|
||||
void CheckMap(Register obj,
|
||||
Handle<Map> map,
|
||||
Label* fail,
|
||||
bool is_heap_object);
|
||||
SmiCheckType smi_check_type);
|
||||
|
||||
// Check if the object in register heap_object is a string. Afterwards the
|
||||
// register map contains the object map and the register instance_type
|
||||
|
@ -1905,7 +1905,7 @@ MaybeObject* CallStubCompiler::CompileMathAbsCall(Object* object,
|
||||
|
||||
// Check if the argument is a heap number and load its value.
|
||||
__ bind(¬_smi);
|
||||
__ CheckMap(rax, factory()->heap_number_map(), &slow, true);
|
||||
__ CheckMap(rax, factory()->heap_number_map(), &slow, DONT_DO_SMI_CHECK);
|
||||
__ movq(rbx, FieldOperand(rax, HeapNumber::kValueOffset));
|
||||
|
||||
// Check the sign of the argument. If the argument is positive,
|
||||
@ -3137,7 +3137,7 @@ MaybeObject* ExternalArrayStubCompiler::CompileKeyedLoadStub(
|
||||
__ JumpIfNotSmi(rax, &slow);
|
||||
|
||||
// Check that the map matches.
|
||||
__ CheckMap(rdx, Handle<Map>(receiver->map()), &slow, false);
|
||||
__ CheckMap(rdx, Handle<Map>(receiver->map()), &slow, DO_SMI_CHECK);
|
||||
__ movq(rbx, FieldOperand(rdx, JSObject::kElementsOffset));
|
||||
|
||||
// Check that the index is in range.
|
||||
@ -3267,7 +3267,7 @@ MaybeObject* ExternalArrayStubCompiler::CompileKeyedStoreStub(
|
||||
__ JumpIfSmi(rdx, &slow);
|
||||
|
||||
// Check that the map matches.
|
||||
__ CheckMap(rdx, Handle<Map>(receiver->map()), &slow, false);
|
||||
__ CheckMap(rdx, Handle<Map>(receiver->map()), &slow, DO_SMI_CHECK);
|
||||
__ movq(rbx, FieldOperand(rdx, JSObject::kElementsOffset));
|
||||
|
||||
// Check that the key is a smi.
|
||||
|
Loading…
Reference in New Issue
Block a user