Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(90)

Unified Diff: src/compiler/effect-control-linearizer.cc

Issue 2763533002: [WIP] JSForInLowering and JSForInHasOwnProperty.
Patch Set: Hack around the issue with indices not being available always. Created 3 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « src/compiler/effect-control-linearizer.h ('k') | src/compiler/js-call-reducer.h » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: src/compiler/effect-control-linearizer.cc
diff --git a/src/compiler/effect-control-linearizer.cc b/src/compiler/effect-control-linearizer.cc
index 27da109b500a56e7fea89a5949a447ff9adacda8..b734255efac41bf7de8842c7b0d91c0849f5e259 100644
--- a/src/compiler/effect-control-linearizer.cc
+++ b/src/compiler/effect-control-linearizer.cc
@@ -791,6 +791,9 @@ bool EffectControlLinearizer::TryWireInStateEffect(Node* node,
case IrOpcode::kTransitionElementsKind:
LowerTransitionElementsKind(node);
break;
+ case IrOpcode::kLoadFieldByIndex:
+ result = LowerLoadFieldByIndex(node);
+ break;
case IrOpcode::kLoadTypedElement:
result = LowerLoadTypedElement(node);
break;
@@ -2554,6 +2557,107 @@ void EffectControlLinearizer::LowerTransitionElementsKind(Node* node) {
__ Bind(&done);
}
+Node* EffectControlLinearizer::LowerLoadFieldByIndex(Node* node) {
+ Node* object = node->InputAt(0);
+ Node* index = node->InputAt(1);
+ Node* zero = __ IntPtrConstant(0);
+ Node* one = __ IntPtrConstant(1);
+
+ // Sign-extend the {index} on 64-bit architectures.
+ if (machine()->Is64()) {
+ index = __ ChangeInt32ToInt64(index);
+ }
+
+ auto if_double = __ MakeDeferredLabel<1>();
+ auto done = __ MakeLabel<3>(MachineRepresentation::kTagged);
+
+ // Check if field is a mutable double field.
+ __ GotoUnless(__ WordEqual(__ WordAnd(index, one), zero), &if_double);
+
+ // The field is a proper Tagged field on {object}. The {index} is shifted
+ // to the left by one in the code below.
+ {
+ // Check if field is in-object or out-of-object.
+ auto if_outofobject = __ MakeLabel<1>();
+ __ GotoIf(__ IntLessThan(index, zero), &if_outofobject);
+
+ // The field is located in the {object} itself.
+ {
+ Node* offset =
+ __ IntAdd(__ WordShl(index, __ IntPtrConstant(kPointerSizeLog2 - 1)),
+ __ IntPtrConstant(JSObject::kHeaderSize - kHeapObjectTag));
+ Node* result = __ Load(MachineType::AnyTagged(), object, offset);
+ __ Goto(&done, result);
+ }
+
+ // The field is located in the properties backing store of {object}.
+ // The {index} is equal to the negated out of property index plus 1.
+ __ Bind(&if_outofobject);
+ {
+ Node* properties =
+ __ LoadField(AccessBuilder::ForJSObjectProperties(), object);
+ Node* offset =
+ __ IntAdd(__ WordShl(__ IntSub(zero, index),
+ __ IntPtrConstant(kPointerSizeLog2 - 1)),
+ __ IntPtrConstant((FixedArray::kHeaderSize - kPointerSize) -
+ kHeapObjectTag));
+ Node* result = __ Load(MachineType::AnyTagged(), properties, offset);
+ __ Goto(&done, result);
+ }
+ }
+
+ // The field is a Double field, either unboxed in the object on 64-bit
+ // architectures, or as MutableHeapNumber.
+ __ Bind(&if_double);
+ {
+ auto done_double = __ MakeLabel<2>(MachineRepresentation::kFloat64);
+
+ index = __ WordSar(index, one);
+
+ // Check if field is in-object or out-of-object.
+ auto if_outofobject = __ MakeLabel<1>();
+ __ GotoIf(__ IntLessThan(index, zero), &if_outofobject);
+
+ // The field is located in the {object} itself.
+ {
+ Node* offset =
+ __ IntAdd(__ WordShl(index, __ IntPtrConstant(kPointerSizeLog2)),
+ __ IntPtrConstant(JSObject::kHeaderSize - kHeapObjectTag));
+ if (FLAG_unbox_double_fields) {
+ Node* result = __ Load(MachineType::Float64(), object, offset);
+ __ Goto(&done_double, result);
+ } else {
+ Node* result = __ Load(MachineType::AnyTagged(), object, offset);
+ result = __ LoadField(AccessBuilder::ForHeapNumberValue(), result);
+ __ Goto(&done_double, result);
+ }
+ }
+
+ __ Bind(&if_outofobject);
+ {
+ Node* properties =
+ __ LoadField(AccessBuilder::ForJSObjectProperties(), object);
+ Node* offset =
+ __ IntAdd(__ WordShl(__ IntSub(zero, index),
+ __ IntPtrConstant(kPointerSizeLog2)),
+ __ IntPtrConstant((FixedArray::kHeaderSize - kPointerSize) -
+ kHeapObjectTag));
+ Node* result = __ Load(MachineType::AnyTagged(), properties, offset);
+ result = __ LoadField(AccessBuilder::ForHeapNumberValue(), result);
+ __ Goto(&done_double, result);
+ }
+
+ __ Bind(&done_double);
+ {
+ Node* result = AllocateHeapNumberWithValue(done_double.PhiAt(0));
+ __ Goto(&done, result);
+ }
+ }
+
+ __ Bind(&done);
+ return done.PhiAt(0);
+}
+
Node* EffectControlLinearizer::LowerLoadTypedElement(Node* node) {
ExternalArrayType array_type = ExternalArrayTypeOf(node->op());
Node* buffer = node->InputAt(0);
« no previous file with comments | « src/compiler/effect-control-linearizer.h ('k') | src/compiler/js-call-reducer.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698