Revision: 18360
Author: [email protected]
Date: Wed Dec 18 17:53:50 2013 UTC
Log: HStoreNamedField for Smis optimized for x64
[email protected]
Review URL: https://codereview.chromium.org/108413003
http://code.google.com/p/v8/source/detail?r=18360
Modified:
/branches/bleeding_edge/src/hydrogen-instructions.h
/branches/bleeding_edge/src/hydrogen.cc
/branches/bleeding_edge/src/objects-inl.h
/branches/bleeding_edge/src/x64/lithium-codegen-x64.cc
/branches/bleeding_edge/src/x64/lithium-x64.cc
=======================================
--- /branches/bleeding_edge/src/hydrogen-instructions.h Wed Dec 18 17:40:53
2013 UTC
+++ /branches/bleeding_edge/src/hydrogen-instructions.h Wed Dec 18 17:53:50
2013 UTC
@@ -6503,10 +6503,20 @@
};
+// Indicates whether the store is a store to an entry that was previously
+// initialized or not.
+enum StoreFieldOrKeyedMode {
+ INITIALIZING_STORE,
+ STORE_TO_INITIALIZED_ENTRY
+};
+
+
class HStoreNamedField V8_FINAL : public HTemplateInstruction<3> {
public:
DECLARE_INSTRUCTION_FACTORY_P3(HStoreNamedField, HValue*,
HObjectAccess, HValue*);
+ DECLARE_INSTRUCTION_FACTORY_P4(HStoreNamedField, HValue*,
+ HObjectAccess, HValue*,
StoreFieldOrKeyedMode);
DECLARE_CONCRETE_INSTRUCTION(StoreNamedField)
@@ -6527,8 +6537,12 @@
field_representation().IsUInteger16() ||
field_representation().IsInteger32()) {
return Representation::Integer32();
- } else if (field_representation().IsDouble() ||
- field_representation().IsSmi()) {
+ } else if (field_representation().IsDouble()) {
+ return field_representation();
+ } else if (field_representation().IsSmi()) {
+ if (SmiValuesAre32Bits() && store_mode_ ==
STORE_TO_INITIALIZED_ENTRY) {
+ return Representation::Integer32();
+ }
return field_representation();
} else if (field_representation().IsExternal()) {
return Representation::External();
@@ -6555,6 +6569,7 @@
HObjectAccess access() const { return access_; }
HValue* new_space_dominator() const { return new_space_dominator_; }
bool has_transition() const { return has_transition_; }
+ StoreFieldOrKeyedMode store_mode() const { return store_mode_; }
Handle<Map> transition_map() const {
if (has_transition()) {
@@ -6605,11 +6620,13 @@
private:
HStoreNamedField(HValue* obj,
HObjectAccess access,
- HValue* val)
+ HValue* val,
+ StoreFieldOrKeyedMode store_mode = INITIALIZING_STORE)
: access_(access),
new_space_dominator_(NULL),
write_barrier_mode_(UPDATE_WRITE_BARRIER),
- has_transition_(false) {
+ has_transition_(false),
+ store_mode_(store_mode) {
SetOperandAt(0, obj);
SetOperandAt(1, val);
SetOperandAt(2, obj);
@@ -6620,6 +6637,7 @@
HValue* new_space_dominator_;
WriteBarrierMode write_barrier_mode_ : 1;
bool has_transition_ : 1;
+ StoreFieldOrKeyedMode store_mode_ : 1;
};
=======================================
--- /branches/bleeding_edge/src/hydrogen.cc Wed Dec 18 17:18:23 2013 UTC
+++ /branches/bleeding_edge/src/hydrogen.cc Wed Dec 18 17:53:50 2013 UTC
@@ -5206,9 +5206,9 @@
}
} else {
// This is a normal store.
- instr = New<HStoreNamedField>(checked_object->ActualValue(),
- field_access,
- value);
+ instr = New<HStoreNamedField>(
+ checked_object->ActualValue(), field_access, value,
+ transition_to_field ? INITIALIZING_STORE :
STORE_TO_INITIALIZED_ENTRY);
}
if (transition_to_field) {
@@ -9441,7 +9441,7 @@
Add<HStoreNamedField>(object, access, result);
} else {
Representation representation = details.representation();
- HInstruction* value_instruction = Add<HConstant>(value);
+ HInstruction* value_instruction;
if (representation.IsDouble()) {
// Allocate a HeapNumber box and store the value into it.
@@ -9456,8 +9456,12 @@
AddStoreMapConstant(double_box,
isolate()->factory()->heap_number_map());
Add<HStoreNamedField>(double_box,
HObjectAccess::ForHeapNumberValue(),
- value_instruction);
+ Add<HConstant>(value));
value_instruction = double_box;
+ } else if (representation.IsSmi() && value->IsUninitialized()) {
+ value_instruction = graph()->GetConstant0();
+ } else {
+ value_instruction = Add<HConstant>(value);
}
Add<HStoreNamedField>(object, access, value_instruction);
=======================================
--- /branches/bleeding_edge/src/objects-inl.h Wed Dec 18 10:30:31 2013 UTC
+++ /branches/bleeding_edge/src/objects-inl.h Wed Dec 18 17:53:50 2013 UTC
@@ -267,6 +267,9 @@
MaybeObject* Object::AllocateNewStorageFor(Heap* heap,
Representation representation) {
+ if (FLAG_track_fields && representation.IsSmi() && IsUninitialized()) {
+ return Smi::FromInt(0);
+ }
if (!FLAG_track_double_fields) return this;
if (!representation.IsDouble()) return this;
if (IsUninitialized()) {
=======================================
--- /branches/bleeding_edge/src/x64/lithium-codegen-x64.cc Wed Dec 18
17:40:53 2013 UTC
+++ /branches/bleeding_edge/src/x64/lithium-codegen-x64.cc Wed Dec 18
17:53:50 2013 UTC
@@ -3938,13 +3938,14 @@
void LCodeGen::DoStoreNamedField(LStoreNamedField* instr) {
+ HStoreNamedField* hinstr = instr->hydrogen();
Representation representation = instr->representation();
- HObjectAccess access = instr->hydrogen()->access();
+ HObjectAccess access = hinstr->access();
int offset = access.offset();
if (access.IsExternalMemory()) {
- ASSERT(!instr->hydrogen()->NeedsWriteBarrier());
+ ASSERT(!hinstr->NeedsWriteBarrier());
Register value = ToRegister(instr->value());
if (instr->object()->IsConstantOperand()) {
ASSERT(value.is(rax));
@@ -3964,7 +3965,8 @@
if (FLAG_track_fields && representation.IsSmi()) {
if (instr->value()->IsConstantOperand()) {
LConstantOperand* operand_value =
LConstantOperand::cast(instr->value());
- if (!IsSmiConstant(operand_value)) {
+ if (!IsInteger32Constant(operand_value) &&
+ !IsSmiConstant(operand_value)) {
DeoptimizeIf(no_condition, instr->environment());
}
}
@@ -3975,7 +3977,7 @@
DeoptimizeIf(no_condition, instr->environment());
}
} else {
- if (!instr->hydrogen()->value()->type().IsHeapObject()) {
+ if (!hinstr->value()->type().IsHeapObject()) {
Register value = ToRegister(instr->value());
Condition cc = masm()->CheckSmi(value);
DeoptimizeIf(cc, instr->environment());
@@ -3984,14 +3986,14 @@
} else if (FLAG_track_double_fields && representation.IsDouble()) {
ASSERT(transition.is_null());
ASSERT(access.IsInobject());
- ASSERT(!instr->hydrogen()->NeedsWriteBarrier());
+ ASSERT(!hinstr->NeedsWriteBarrier());
XMMRegister value = ToDoubleRegister(instr->value());
__ movsd(FieldOperand(object, offset), value);
return;
}
if (!transition.is_null()) {
- if (!instr->hydrogen()->NeedsWriteBarrierForMap()) {
+ if (!hinstr->NeedsWriteBarrierForMap()) {
__ Move(FieldOperand(object, HeapObject::kMapOffset), transition);
} else {
Register temp = ToRegister(instr->temp());
@@ -4009,9 +4011,8 @@
}
// Do the store.
- SmiCheck check_needed =
- instr->hydrogen()->value()->IsHeapObject()
- ? OMIT_SMI_CHECK : INLINE_SMI_CHECK;
+ SmiCheck check_needed = hinstr->value()->IsHeapObject()
+ ? OMIT_SMI_CHECK : INLINE_SMI_CHECK;
Register write_register = object;
if (!access.IsInobject()) {
@@ -4019,26 +4020,41 @@
__ movq(write_register, FieldOperand(object,
JSObject::kPropertiesOffset));
}
- if (instr->value()->IsConstantOperand()) {
+ if (representation.IsSmi() &&
+ hinstr->value()->representation().IsInteger32()) {
+ ASSERT(hinstr->store_mode() == STORE_TO_INITIALIZED_ENTRY);
+ // Store int value directly to upper half of the smi.
+ STATIC_ASSERT(kSmiTag == 0);
+ STATIC_ASSERT(kSmiTagSize + kSmiShiftSize == 32);
+ offset += kPointerSize / 2;
+ representation = Representation::Integer32();
+ }
+
+ Operand operand = FieldOperand(write_register, offset);
+
+ if (instr->value()->IsRegister()) {
+ Register value = ToRegister(instr->value());
+ __ Store(operand, value, representation);
+ } else {
LConstantOperand* operand_value =
LConstantOperand::cast(instr->value());
- if (operand_value->IsRegister()) {
- Register value = ToRegister(operand_value);
- __ Store(FieldOperand(write_register, offset), value,
representation);
- } else if (representation.IsInteger32()) {
+ if (IsInteger32Constant(operand_value)) {
+ ASSERT(!hinstr->NeedsWriteBarrier());
int32_t value = ToInteger32(operand_value);
- ASSERT(!instr->hydrogen()->NeedsWriteBarrier());
- __ movl(FieldOperand(write_register, offset), Immediate(value));
+ if (representation.IsSmi()) {
+ __ Move(operand, Smi::FromInt(value));
+
+ } else {
+ __ movl(operand, Immediate(value));
+ }
+
} else {
Handle<Object> handle_value = ToHandle(operand_value);
- ASSERT(!instr->hydrogen()->NeedsWriteBarrier());
- __ Move(FieldOperand(write_register, offset), handle_value);
+ ASSERT(!hinstr->NeedsWriteBarrier());
+ __ Move(operand, handle_value);
}
- } else {
- Register value = ToRegister(instr->value());
- __ Store(FieldOperand(write_register, offset), value, representation);
}
- if (instr->hydrogen()->NeedsWriteBarrier()) {
+ if (hinstr->NeedsWriteBarrier()) {
Register value = ToRegister(instr->value());
Register temp = access.IsInobject() ? ToRegister(instr->temp()) :
object;
// Update the write barrier for the object for in-object properties.
=======================================
--- /branches/bleeding_edge/src/x64/lithium-x64.cc Wed Dec 18 10:40:26 2013
UTC
+++ /branches/bleeding_edge/src/x64/lithium-x64.cc Wed Dec 18 17:53:50 2013
UTC
@@ -2296,7 +2296,7 @@
} else if (can_be_constant) {
val = UseRegisterOrConstant(instr->value());
} else if (FLAG_track_fields && instr->field_representation().IsSmi()) {
- val = UseTempRegister(instr->value());
+ val = UseRegister(instr->value());
} else if (FLAG_track_double_fields &&
instr->field_representation().IsDouble()) {
val = UseRegisterAtStart(instr->value());
--
--
v8-dev mailing list
[email protected]
http://groups.google.com/group/v8-dev
---
You received this message because you are subscribed to the Google Groups "v8-dev" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to [email protected].
For more options, visit https://groups.google.com/groups/opt_out.