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

Side by Side Diff: src/code-stub-assembler.cc

Issue 2497243002: [stubs] Port builtin for Array.push fast-case from Crankshaft to TF (Closed)
Patch Set: Fix GC mole Created 4 years 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 unified diff | Download patch
« no previous file with comments | « src/code-stub-assembler.h ('k') | src/code-stubs.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2016 the V8 project authors. All rights reserved. 1 // Copyright 2016 the V8 project authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 #include "src/code-stub-assembler.h" 4 #include "src/code-stub-assembler.h"
5 #include "src/code-factory.h" 5 #include "src/code-factory.h"
6 #include "src/frames-inl.h" 6 #include "src/frames-inl.h"
7 #include "src/frames.h" 7 #include "src/frames.h"
8 8
9 namespace v8 { 9 namespace v8 {
10 namespace internal { 10 namespace internal {
(...skipping 507 matching lines...) Expand 10 before | Expand all | Expand 10 after
518 518
519 Bind(&return_result); 519 Bind(&return_result);
520 return var_result.value(); 520 return var_result.value();
521 } 521 }
522 522
523 Node* CodeStubAssembler::TaggedIsSmi(Node* a) { 523 Node* CodeStubAssembler::TaggedIsSmi(Node* a) {
524 return WordEqual(WordAnd(BitcastTaggedToWord(a), IntPtrConstant(kSmiTagMask)), 524 return WordEqual(WordAnd(BitcastTaggedToWord(a), IntPtrConstant(kSmiTagMask)),
525 IntPtrConstant(0)); 525 IntPtrConstant(0));
526 } 526 }
527 527
528 Node* CodeStubAssembler::TaggedIsNotSmi(Node* a) {
529 return WordNotEqual(
530 WordAnd(BitcastTaggedToWord(a), IntPtrConstant(kSmiTagMask)),
531 IntPtrConstant(0));
532 }
533
528 Node* CodeStubAssembler::WordIsPositiveSmi(Node* a) { 534 Node* CodeStubAssembler::WordIsPositiveSmi(Node* a) {
529 return WordEqual(WordAnd(a, IntPtrConstant(kSmiTagMask | kSmiSignMask)), 535 return WordEqual(WordAnd(a, IntPtrConstant(kSmiTagMask | kSmiSignMask)),
530 IntPtrConstant(0)); 536 IntPtrConstant(0));
531 } 537 }
532 538
533 Node* CodeStubAssembler::WordIsWordAligned(Node* word) { 539 Node* CodeStubAssembler::WordIsWordAligned(Node* word) {
534 return WordEqual(IntPtrConstant(0), 540 return WordEqual(IntPtrConstant(0),
535 WordAnd(word, IntPtrConstant((1 << kPointerSizeLog2) - 1))); 541 WordAnd(word, IntPtrConstant((1 << kPointerSizeLog2) - 1)));
536 } 542 }
537 543
(...skipping 108 matching lines...) Expand 10 before | Expand all | Expand 10 after
646 652
647 void CodeStubAssembler::BranchIfJSObject(Node* object, Label* if_true, 653 void CodeStubAssembler::BranchIfJSObject(Node* object, Label* if_true,
648 Label* if_false) { 654 Label* if_false) {
649 GotoIf(TaggedIsSmi(object), if_false); 655 GotoIf(TaggedIsSmi(object), if_false);
650 STATIC_ASSERT(LAST_JS_OBJECT_TYPE == LAST_TYPE); 656 STATIC_ASSERT(LAST_JS_OBJECT_TYPE == LAST_TYPE);
651 Branch(Int32GreaterThanOrEqual(LoadInstanceType(object), 657 Branch(Int32GreaterThanOrEqual(LoadInstanceType(object),
652 Int32Constant(FIRST_JS_OBJECT_TYPE)), 658 Int32Constant(FIRST_JS_OBJECT_TYPE)),
653 if_true, if_false); 659 if_true, if_false);
654 } 660 }
655 661
656 void CodeStubAssembler::BranchIfFastJSArray(Node* object, Node* context, 662 void CodeStubAssembler::BranchIfFastJSArray(
657 Label* if_true, Label* if_false) { 663 Node* object, Node* context, CodeStubAssembler::FastJSArrayAccessMode mode,
664 Label* if_true, Label* if_false) {
658 // Bailout if receiver is a Smi. 665 // Bailout if receiver is a Smi.
659 GotoIf(TaggedIsSmi(object), if_false); 666 GotoIf(TaggedIsSmi(object), if_false);
660 667
661 Node* map = LoadMap(object); 668 Node* map = LoadMap(object);
662 669
663 // Bailout if instance type is not JS_ARRAY_TYPE. 670 // Bailout if instance type is not JS_ARRAY_TYPE.
664 GotoIf(WordNotEqual(LoadMapInstanceType(map), Int32Constant(JS_ARRAY_TYPE)), 671 GotoIf(WordNotEqual(LoadMapInstanceType(map), Int32Constant(JS_ARRAY_TYPE)),
665 if_false); 672 if_false);
666 673
667 Node* elements_kind = LoadMapElementsKind(map); 674 Node* elements_kind = LoadMapElementsKind(map);
668 675
669 // Bailout if receiver has slow elements. 676 // Bailout if receiver has slow elements.
670 GotoUnless(IsFastElementsKind(elements_kind), if_false); 677 GotoUnless(IsFastElementsKind(elements_kind), if_false);
671 678
672 // Check prototype chain if receiver does not have packed elements. 679 // Check prototype chain if receiver does not have packed elements.
673 GotoUnless(IsHoleyFastElementsKind(elements_kind), if_true); 680 if (mode == FastJSArrayAccessMode::INBOUNDS_READ) {
674 681 GotoUnless(IsHoleyFastElementsKind(elements_kind), if_true);
682 }
675 BranchIfPrototypesHaveNoElements(map, if_true, if_false); 683 BranchIfPrototypesHaveNoElements(map, if_true, if_false);
676 } 684 }
677 685
678 Node* CodeStubAssembler::AllocateRawUnaligned(Node* size_in_bytes, 686 Node* CodeStubAssembler::AllocateRawUnaligned(Node* size_in_bytes,
679 AllocationFlags flags, 687 AllocationFlags flags,
680 Node* top_address, 688 Node* top_address,
681 Node* limit_address) { 689 Node* limit_address) {
682 Node* top = Load(MachineType::Pointer(), top_address); 690 Node* top = Load(MachineType::Pointer(), top_address);
683 Node* limit = Load(MachineType::Pointer(), limit_address); 691 Node* limit = Load(MachineType::Pointer(), limit_address);
684 692
(...skipping 669 matching lines...) Expand 10 before | Expand all | Expand 10 after
1354 Node* CodeStubAssembler::StoreFixedDoubleArrayElement( 1362 Node* CodeStubAssembler::StoreFixedDoubleArrayElement(
1355 Node* object, Node* index_node, Node* value, ParameterMode parameter_mode) { 1363 Node* object, Node* index_node, Node* value, ParameterMode parameter_mode) {
1356 CSA_ASSERT(this, IsFixedDoubleArray(object)); 1364 CSA_ASSERT(this, IsFixedDoubleArray(object));
1357 Node* offset = 1365 Node* offset =
1358 ElementOffsetFromIndex(index_node, FAST_DOUBLE_ELEMENTS, parameter_mode, 1366 ElementOffsetFromIndex(index_node, FAST_DOUBLE_ELEMENTS, parameter_mode,
1359 FixedArray::kHeaderSize - kHeapObjectTag); 1367 FixedArray::kHeaderSize - kHeapObjectTag);
1360 MachineRepresentation rep = MachineRepresentation::kFloat64; 1368 MachineRepresentation rep = MachineRepresentation::kFloat64;
1361 return StoreNoWriteBarrier(rep, object, offset, value); 1369 return StoreNoWriteBarrier(rep, object, offset, value);
1362 } 1370 }
1363 1371
1372 Node* CodeStubAssembler::BuildAppendJSArray(ElementsKind kind, Node* context,
1373 Node* array,
1374 CodeStubArguments& args,
1375 Variable& arg_index,
1376 Label* bailout) {
1377 Comment("BuildAppendJSArray: %s", ElementsKindToString(kind));
1378 Label pre_bailout(this);
1379 Label success(this);
1380 Variable elements(this, MachineRepresentation::kTagged);
1381 ParameterMode mode = OptimalParameterMode();
1382 Variable length(this, OptimalParameterRepresentation());
1383 length.Bind(UntagParameter(LoadJSArrayLength(array), mode));
1384 elements.Bind(LoadElements(array));
1385 Node* capacity =
1386 UntagParameter(LoadFixedArrayBaseLength(elements.value()), mode);
1387
1388 // Resize the capacity of the fixed array if it doesn't fit.
1389 Label fits(this, &elements);
1390 Node* first = arg_index.value();
1391 Node* growth = IntPtrSubFoldConstants(args.GetLength(), first);
1392 Node* new_length = IntPtrAdd(
1393 mode == INTPTR_PARAMETERS ? growth : SmiTag(growth), length.value());
1394 GotoUnless(IntPtrGreaterThanOrEqual(new_length, capacity), &fits);
1395 Node* new_capacity = CalculateNewElementsCapacity(
1396 IntPtrAdd(new_length, IntPtrOrSmiConstant(1, mode)), mode);
1397 elements.Bind(GrowElementsCapacity(array, elements.value(), kind, kind,
1398 capacity, new_capacity, mode,
1399 &pre_bailout));
1400 Goto(&fits);
1401 Bind(&fits);
1402
1403 // Push each argument onto the end of the array now that there is enough
1404 // capacity.
1405 CodeStubAssembler::VariableList push_vars({&length, &elements}, zone());
1406 args.ForEach(
1407 push_vars,
1408 [kind, mode, &length, &elements, &pre_bailout](
1409 CodeStubAssembler* assembler, Node* arg) {
1410 if (IsFastSmiElementsKind(kind)) {
1411 assembler->GotoIf(assembler->TaggedIsNotSmi(arg), &pre_bailout);
1412 } else if (IsFastDoubleElementsKind(kind)) {
1413 assembler->GotoIfNotNumber(arg, &pre_bailout);
1414 }
1415 if (IsFastDoubleElementsKind(kind)) {
1416 Node* double_value = assembler->ChangeNumberToFloat64(arg);
1417 assembler->StoreFixedDoubleArrayElement(
1418 elements.value(), length.value(),
1419 assembler->Float64SilenceNaN(double_value), mode);
1420 } else {
1421 WriteBarrierMode barrier_mode = IsFastSmiElementsKind(kind)
1422 ? SKIP_WRITE_BARRIER
1423 : UPDATE_WRITE_BARRIER;
1424 assembler->StoreFixedArrayElement(elements.value(), length.value(),
1425 arg, barrier_mode, 0, mode);
1426 }
1427 assembler->Increment(length, 1, mode);
1428 },
1429 first, nullptr);
1430 length.Bind(TagParameter(length.value(), mode));
1431 StoreObjectFieldNoWriteBarrier(array, JSArray::kLengthOffset, length.value());
1432 Goto(&success);
1433
1434 Bind(&pre_bailout);
1435 length.Bind(TagParameter(length.value(), mode));
1436 Node* diff = SmiSub(length.value(), LoadJSArrayLength(array));
1437 StoreObjectFieldNoWriteBarrier(array, JSArray::kLengthOffset, length.value());
1438 arg_index.Bind(IntPtrAdd(arg_index.value(), SmiUntag(diff)));
1439 Goto(bailout);
1440
1441 Bind(&success);
1442 return length.value();
1443 }
1444
1364 Node* CodeStubAssembler::AllocateHeapNumber(MutableMode mode) { 1445 Node* CodeStubAssembler::AllocateHeapNumber(MutableMode mode) {
1365 Node* result = Allocate(HeapNumber::kSize, kNone); 1446 Node* result = Allocate(HeapNumber::kSize, kNone);
1366 Heap::RootListIndex heap_map_index = 1447 Heap::RootListIndex heap_map_index =
1367 mode == IMMUTABLE ? Heap::kHeapNumberMapRootIndex 1448 mode == IMMUTABLE ? Heap::kHeapNumberMapRootIndex
1368 : Heap::kMutableHeapNumberMapRootIndex; 1449 : Heap::kMutableHeapNumberMapRootIndex;
1369 Node* map = LoadRoot(heap_map_index); 1450 Node* map = LoadRoot(heap_map_index);
1370 StoreMapNoWriteBarrier(result, map); 1451 StoreMapNoWriteBarrier(result, map);
1371 return result; 1452 return result;
1372 } 1453 }
1373 1454
(...skipping 749 matching lines...) Expand 10 before | Expand all | Expand 10 after
2123 to_index_smi == from_index_smi)); 2204 to_index_smi == from_index_smi));
2124 BuildFastLoop(vars, MachineType::PointerRepresentation(), from_offset, 2205 BuildFastLoop(vars, MachineType::PointerRepresentation(), from_offset,
2125 limit_offset, 2206 limit_offset,
2126 [from_string, to_string, &current_to_offset, to_increment, type, 2207 [from_string, to_string, &current_to_offset, to_increment, type,
2127 rep, index_same](CodeStubAssembler* assembler, Node* offset) { 2208 rep, index_same](CodeStubAssembler* assembler, Node* offset) {
2128 Node* value = assembler->Load(type, from_string, offset); 2209 Node* value = assembler->Load(type, from_string, offset);
2129 assembler->StoreNoWriteBarrier( 2210 assembler->StoreNoWriteBarrier(
2130 rep, to_string, 2211 rep, to_string,
2131 index_same ? offset : current_to_offset.value(), value); 2212 index_same ? offset : current_to_offset.value(), value);
2132 if (!index_same) { 2213 if (!index_same) {
2133 current_to_offset.Bind(assembler->IntPtrAdd( 2214 assembler->Increment(current_to_offset, to_increment);
2134 current_to_offset.value(),
2135 assembler->IntPtrConstant(to_increment)));
2136 } 2215 }
2137 }, 2216 },
2138 from_increment, IndexAdvanceMode::kPost); 2217 from_increment, IndexAdvanceMode::kPost);
2139 } 2218 }
2140 2219
2141 Node* CodeStubAssembler::LoadElementAndPrepareForStore(Node* array, 2220 Node* CodeStubAssembler::LoadElementAndPrepareForStore(Node* array,
2142 Node* offset, 2221 Node* offset,
2143 ElementsKind from_kind, 2222 ElementsKind from_kind,
2144 ElementsKind to_kind, 2223 ElementsKind to_kind,
2145 Label* if_hole) { 2224 Label* if_hole) {
(...skipping 401 matching lines...) Expand 10 before | Expand all | Expand 10 after
2547 { 2626 {
2548 // The {value} is a Smi, convert it to a String. 2627 // The {value} is a Smi, convert it to a String.
2549 Callable callable = CodeFactory::NumberToString(isolate()); 2628 Callable callable = CodeFactory::NumberToString(isolate());
2550 var_value.Bind(CallStub(callable, context, value)); 2629 var_value.Bind(CallStub(callable, context, value));
2551 Goto(&if_valueisstring); 2630 Goto(&if_valueisstring);
2552 } 2631 }
2553 Bind(&if_valueisstring); 2632 Bind(&if_valueisstring);
2554 return var_value.value(); 2633 return var_value.value();
2555 } 2634 }
2556 2635
2636 Node* CodeStubAssembler::ChangeNumberToFloat64(compiler::Node* value) {
2637 Variable result(this, MachineRepresentation::kFloat64);
2638 Label smi(this);
2639 Label done(this, &result);
2640 GotoIf(TaggedIsSmi(value), &smi);
2641 result.Bind(
2642 LoadObjectField(value, HeapNumber::kValueOffset, MachineType::Float64()));
2643 Goto(&done);
2644
2645 Bind(&smi);
2646 {
2647 result.Bind(ChangeInt32ToFloat64(SmiUntag(value)));
2648 Goto(&done);
2649 }
2650
2651 Bind(&done);
2652 return result.value();
2653 }
2654
2557 Node* CodeStubAssembler::ToThisValue(Node* context, Node* value, 2655 Node* CodeStubAssembler::ToThisValue(Node* context, Node* value,
2558 PrimitiveType primitive_type, 2656 PrimitiveType primitive_type,
2559 char const* method_name) { 2657 char const* method_name) {
2560 // We might need to loop once due to JSValue unboxing. 2658 // We might need to loop once due to JSValue unboxing.
2561 Variable var_value(this, MachineRepresentation::kTagged); 2659 Variable var_value(this, MachineRepresentation::kTagged);
2562 Label loop(this, &var_value), done_loop(this), 2660 Label loop(this, &var_value), done_loop(this),
2563 done_throw(this, Label::kDeferred); 2661 done_throw(this, Label::kDeferred);
2564 var_value.Bind(value); 2662 var_value.Bind(value);
2565 Goto(&loop); 2663 Goto(&loop);
2566 Bind(&loop); 2664 Bind(&loop);
(...skipping 1392 matching lines...) Expand 10 before | Expand all | Expand 10 after
3959 void CodeStubAssembler::DecrementCounter(StatsCounter* counter, int delta) { 4057 void CodeStubAssembler::DecrementCounter(StatsCounter* counter, int delta) {
3960 DCHECK(delta > 0); 4058 DCHECK(delta > 0);
3961 if (FLAG_native_code_counters && counter->Enabled()) { 4059 if (FLAG_native_code_counters && counter->Enabled()) {
3962 Node* counter_address = ExternalConstant(ExternalReference(counter)); 4060 Node* counter_address = ExternalConstant(ExternalReference(counter));
3963 Node* value = Load(MachineType::Int32(), counter_address); 4061 Node* value = Load(MachineType::Int32(), counter_address);
3964 value = Int32Sub(value, Int32Constant(delta)); 4062 value = Int32Sub(value, Int32Constant(delta));
3965 StoreNoWriteBarrier(MachineRepresentation::kWord32, counter_address, value); 4063 StoreNoWriteBarrier(MachineRepresentation::kWord32, counter_address, value);
3966 } 4064 }
3967 } 4065 }
3968 4066
4067 void CodeStubAssembler::Increment(Variable& variable, int value,
4068 ParameterMode mode) {
4069 DCHECK_IMPLIES(mode == INTPTR_PARAMETERS,
4070 variable.rep() == MachineType::PointerRepresentation());
4071 DCHECK_IMPLIES(mode == SMI_PARAMETERS,
4072 variable.rep() == MachineRepresentation::kTagged ||
4073 variable.rep() == MachineRepresentation::kTaggedSigned);
4074 variable.Bind(IntPtrAdd(variable.value(), IntPtrOrSmiConstant(value, mode)));
4075 }
4076
3969 void CodeStubAssembler::Use(Label* label) { 4077 void CodeStubAssembler::Use(Label* label) {
3970 GotoIf(Word32Equal(Int32Constant(0), Int32Constant(1)), label); 4078 GotoIf(Word32Equal(Int32Constant(0), Int32Constant(1)), label);
3971 } 4079 }
3972 4080
3973 void CodeStubAssembler::TryToName(Node* key, Label* if_keyisindex, 4081 void CodeStubAssembler::TryToName(Node* key, Label* if_keyisindex,
3974 Variable* var_index, Label* if_keyisunique, 4082 Variable* var_index, Label* if_keyisunique,
3975 Label* if_bailout) { 4083 Label* if_bailout) {
3976 DCHECK_EQ(MachineType::PointerRepresentation(), var_index->rep()); 4084 DCHECK_EQ(MachineType::PointerRepresentation(), var_index->rep());
3977 Comment("TryToName"); 4085 Comment("TryToName");
3978 4086
(...skipping 140 matching lines...) Expand 10 before | Expand all | Expand 10 after
4119 4227
4120 Variable var_count(this, MachineType::PointerRepresentation()); 4228 Variable var_count(this, MachineType::PointerRepresentation());
4121 Variable var_entry(this, MachineType::PointerRepresentation()); 4229 Variable var_entry(this, MachineType::PointerRepresentation());
4122 Variable* loop_vars[] = {&var_count, &var_entry, var_name_index}; 4230 Variable* loop_vars[] = {&var_count, &var_entry, var_name_index};
4123 Label loop(this, 3, loop_vars); 4231 Label loop(this, 3, loop_vars);
4124 var_count.Bind(count); 4232 var_count.Bind(count);
4125 var_entry.Bind(entry); 4233 var_entry.Bind(entry);
4126 Goto(&loop); 4234 Goto(&loop);
4127 Bind(&loop); 4235 Bind(&loop);
4128 { 4236 {
4129 Node* count = var_count.value();
4130 Node* entry = var_entry.value(); 4237 Node* entry = var_entry.value();
4131 4238
4132 Node* index = EntryToIndex<Dictionary>(entry); 4239 Node* index = EntryToIndex<Dictionary>(entry);
4133 var_name_index->Bind(index); 4240 var_name_index->Bind(index);
4134 4241
4135 Node* current = 4242 Node* current =
4136 LoadFixedArrayElement(dictionary, index, 0, INTPTR_PARAMETERS); 4243 LoadFixedArrayElement(dictionary, index, 0, INTPTR_PARAMETERS);
4137 GotoIf(WordEqual(current, undefined), if_not_found); 4244 GotoIf(WordEqual(current, undefined), if_not_found);
4138 if (mode == kFindExisting) { 4245 if (mode == kFindExisting) {
4139 GotoIf(WordEqual(current, unique_name), if_found); 4246 GotoIf(WordEqual(current, unique_name), if_found);
4140 } else { 4247 } else {
4141 DCHECK_EQ(kFindInsertionIndex, mode); 4248 DCHECK_EQ(kFindInsertionIndex, mode);
4142 GotoIf(WordEqual(current, the_hole), if_not_found); 4249 GotoIf(WordEqual(current, the_hole), if_not_found);
4143 } 4250 }
4144 4251
4145 // See Dictionary::NextProbe(). 4252 // See Dictionary::NextProbe().
4146 count = IntPtrAdd(count, IntPtrConstant(1)); 4253 Increment(var_count);
4147 entry = WordAnd(IntPtrAdd(entry, count), mask); 4254 entry = WordAnd(IntPtrAdd(entry, var_count.value()), mask);
4148 4255
4149 var_count.Bind(count);
4150 var_entry.Bind(entry); 4256 var_entry.Bind(entry);
4151 Goto(&loop); 4257 Goto(&loop);
4152 } 4258 }
4153 } 4259 }
4154 4260
4155 // Instantiate template methods to workaround GCC compilation issue. 4261 // Instantiate template methods to workaround GCC compilation issue.
4156 template void CodeStubAssembler::NameDictionaryLookup<NameDictionary>( 4262 template void CodeStubAssembler::NameDictionaryLookup<NameDictionary>(
4157 Node*, Node*, Label*, Variable*, Label*, int, LookupMode); 4263 Node*, Node*, Label*, Variable*, Label*, int, LookupMode);
4158 template void CodeStubAssembler::NameDictionaryLookup<GlobalDictionary>( 4264 template void CodeStubAssembler::NameDictionaryLookup<GlobalDictionary>(
4159 Node*, Node*, Label*, Variable*, Label*, int, LookupMode); 4265 Node*, Node*, Label*, Variable*, Label*, int, LookupMode);
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after
4202 Node* the_hole = TheHoleConstant(); 4308 Node* the_hole = TheHoleConstant();
4203 4309
4204 Variable var_count(this, MachineType::PointerRepresentation()); 4310 Variable var_count(this, MachineType::PointerRepresentation());
4205 Variable* loop_vars[] = {&var_count, var_entry}; 4311 Variable* loop_vars[] = {&var_count, var_entry};
4206 Label loop(this, 2, loop_vars); 4312 Label loop(this, 2, loop_vars);
4207 var_count.Bind(count); 4313 var_count.Bind(count);
4208 var_entry->Bind(entry); 4314 var_entry->Bind(entry);
4209 Goto(&loop); 4315 Goto(&loop);
4210 Bind(&loop); 4316 Bind(&loop);
4211 { 4317 {
4212 Node* count = var_count.value();
4213 Node* entry = var_entry->value(); 4318 Node* entry = var_entry->value();
4214 4319
4215 Node* index = EntryToIndex<Dictionary>(entry); 4320 Node* index = EntryToIndex<Dictionary>(entry);
4216 Node* current = 4321 Node* current =
4217 LoadFixedArrayElement(dictionary, index, 0, INTPTR_PARAMETERS); 4322 LoadFixedArrayElement(dictionary, index, 0, INTPTR_PARAMETERS);
4218 GotoIf(WordEqual(current, undefined), if_not_found); 4323 GotoIf(WordEqual(current, undefined), if_not_found);
4219 Label next_probe(this); 4324 Label next_probe(this);
4220 { 4325 {
4221 Label if_currentissmi(this), if_currentisnotsmi(this); 4326 Label if_currentissmi(this), if_currentisnotsmi(this);
4222 Branch(TaggedIsSmi(current), &if_currentissmi, &if_currentisnotsmi); 4327 Branch(TaggedIsSmi(current), &if_currentissmi, &if_currentisnotsmi);
4223 Bind(&if_currentissmi); 4328 Bind(&if_currentissmi);
4224 { 4329 {
4225 Node* current_value = SmiUntag(current); 4330 Node* current_value = SmiUntag(current);
4226 Branch(WordEqual(current_value, intptr_index), if_found, &next_probe); 4331 Branch(WordEqual(current_value, intptr_index), if_found, &next_probe);
4227 } 4332 }
4228 Bind(&if_currentisnotsmi); 4333 Bind(&if_currentisnotsmi);
4229 { 4334 {
4230 GotoIf(WordEqual(current, the_hole), &next_probe); 4335 GotoIf(WordEqual(current, the_hole), &next_probe);
4231 // Current must be the Number. 4336 // Current must be the Number.
4232 Node* current_value = LoadHeapNumberValue(current); 4337 Node* current_value = LoadHeapNumberValue(current);
4233 Branch(Float64Equal(current_value, key_as_float64), if_found, 4338 Branch(Float64Equal(current_value, key_as_float64), if_found,
4234 &next_probe); 4339 &next_probe);
4235 } 4340 }
4236 } 4341 }
4237 4342
4238 Bind(&next_probe); 4343 Bind(&next_probe);
4239 // See Dictionary::NextProbe(). 4344 // See Dictionary::NextProbe().
4240 count = IntPtrAdd(count, IntPtrConstant(1)); 4345 Increment(var_count);
4241 entry = WordAnd(IntPtrAdd(entry, count), mask); 4346 entry = WordAnd(IntPtrAdd(entry, var_count.value()), mask);
4242 4347
4243 var_count.Bind(count);
4244 var_entry->Bind(entry); 4348 var_entry->Bind(entry);
4245 Goto(&loop); 4349 Goto(&loop);
4246 } 4350 }
4247 } 4351 }
4248 4352
4249 template <class Dictionary> 4353 template <class Dictionary>
4250 void CodeStubAssembler::FindInsertionEntry(Node* dictionary, Node* key, 4354 void CodeStubAssembler::FindInsertionEntry(Node* dictionary, Node* key,
4251 Variable* var_key_index) { 4355 Variable* var_key_index) {
4252 UNREACHABLE(); 4356 UNREACHABLE();
4253 } 4357 }
(...skipping 1641 matching lines...) Expand 10 before | Expand all | Expand 10 after
5895 // loop that helps turbofan generate better code. If there's only a single 5999 // loop that helps turbofan generate better code. If there's only a single
5896 // check, then the CodeStubAssembler forces it to be at the beginning of the 6000 // check, then the CodeStubAssembler forces it to be at the beginning of the
5897 // loop requiring a backwards branch at the end of the loop (it's not possible 6001 // loop requiring a backwards branch at the end of the loop (it's not possible
5898 // to force the loop header check at the end of the loop and branch forward to 6002 // to force the loop header check at the end of the loop and branch forward to
5899 // it from the pre-header). The extra branch is slower in the case that the 6003 // it from the pre-header). The extra branch is slower in the case that the
5900 // loop actually iterates. 6004 // loop actually iterates.
5901 Branch(WordEqual(var.value(), end_index), &after_loop, &loop); 6005 Branch(WordEqual(var.value(), end_index), &after_loop, &loop);
5902 Bind(&loop); 6006 Bind(&loop);
5903 { 6007 {
5904 if (mode == IndexAdvanceMode::kPre) { 6008 if (mode == IndexAdvanceMode::kPre) {
5905 var.Bind(IntPtrAdd(var.value(), IntPtrConstant(increment))); 6009 Increment(var, increment);
5906 } 6010 }
5907 body(this, var.value()); 6011 body(this, var.value());
5908 if (mode == IndexAdvanceMode::kPost) { 6012 if (mode == IndexAdvanceMode::kPost) {
5909 var.Bind(IntPtrAdd(var.value(), IntPtrConstant(increment))); 6013 Increment(var, increment);
5910 } 6014 }
5911 Branch(WordNotEqual(var.value(), end_index), &loop, &after_loop); 6015 Branch(WordNotEqual(var.value(), end_index), &loop, &after_loop);
5912 } 6016 }
5913 Bind(&after_loop); 6017 Bind(&after_loop);
5914 } 6018 }
5915 6019
5916 void CodeStubAssembler::BuildFastFixedArrayForEach( 6020 void CodeStubAssembler::BuildFastFixedArrayForEach(
5917 Node* fixed_array, ElementsKind kind, Node* first_element_inclusive, 6021 Node* fixed_array, ElementsKind kind, Node* first_element_inclusive,
5918 Node* last_element_exclusive, 6022 Node* last_element_exclusive,
5919 std::function<void(CodeStubAssembler* assembler, Node* fixed_array, 6023 std::function<void(CodeStubAssembler* assembler, Node* fixed_array,
(...skipping 1618 matching lines...) Expand 10 before | Expand all | Expand 10 after
7538 Node* one = Float64Constant(1.0); 7642 Node* one = Float64Constant(1.0);
7539 Node* finc_result = Float64Add(finc_value, one); 7643 Node* finc_result = Float64Add(finc_value, one);
7540 var_result.Bind(AllocateHeapNumberWithValue(finc_result)); 7644 var_result.Bind(AllocateHeapNumberWithValue(finc_result));
7541 Goto(&end); 7645 Goto(&end);
7542 } 7646 }
7543 7647
7544 Bind(&end); 7648 Bind(&end);
7545 return var_result.value(); 7649 return var_result.value();
7546 } 7650 }
7547 7651
7652 void CodeStubAssembler::GotoIfNotNumber(Node* input, Label* is_not_number) {
7653 Label is_number(this);
7654 GotoIf(TaggedIsSmi(input), &is_number);
7655 Node* input_map = LoadMap(input);
7656 Branch(IsHeapNumberMap(input_map), &is_number, is_not_number);
7657 Bind(&is_number);
7658 }
7659
7660 void CodeStubAssembler::GotoIfNumber(Node* input, Label* is_number) {
7661 GotoIf(TaggedIsSmi(input), is_number);
7662 Node* input_map = LoadMap(input);
7663 GotoIf(IsHeapNumberMap(input_map), is_number);
7664 }
7665
7548 Node* CodeStubAssembler::CreateArrayIterator(Node* array, Node* array_map, 7666 Node* CodeStubAssembler::CreateArrayIterator(Node* array, Node* array_map,
7549 Node* array_type, Node* context, 7667 Node* array_type, Node* context,
7550 IterationKind mode) { 7668 IterationKind mode) {
7551 int kBaseMapIndex = 0; 7669 int kBaseMapIndex = 0;
7552 switch (mode) { 7670 switch (mode) {
7553 case IterationKind::kKeys: 7671 case IterationKind::kKeys:
7554 kBaseMapIndex = Context::TYPED_ARRAY_KEY_ITERATOR_MAP_INDEX; 7672 kBaseMapIndex = Context::TYPED_ARRAY_KEY_ITERATOR_MAP_INDEX;
7555 break; 7673 break;
7556 case IterationKind::kValues: 7674 case IterationKind::kValues:
7557 kBaseMapIndex = Context::UINT8_ARRAY_VALUE_ITERATOR_MAP_INDEX; 7675 kBaseMapIndex = Context::UINT8_ARRAY_VALUE_ITERATOR_MAP_INDEX;
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after
7594 // the receiver is a TypedArray or not. 7712 // the receiver is a TypedArray or not.
7595 7713
7596 Label if_istypedarray(this), if_isgeneric(this); 7714 Label if_istypedarray(this), if_isgeneric(this);
7597 7715
7598 Branch(Word32Equal(array_type, Int32Constant(JS_TYPED_ARRAY_TYPE)), 7716 Branch(Word32Equal(array_type, Int32Constant(JS_TYPED_ARRAY_TYPE)),
7599 &if_istypedarray, &if_isgeneric); 7717 &if_istypedarray, &if_isgeneric);
7600 7718
7601 Bind(&if_isgeneric); 7719 Bind(&if_isgeneric);
7602 { 7720 {
7603 Label if_isfast(this), if_isslow(this); 7721 Label if_isfast(this), if_isslow(this);
7604 BranchIfFastJSArray(array, context, &if_isfast, &if_isslow); 7722 BranchIfFastJSArray(array, context, FastJSArrayAccessMode::INBOUNDS_READ,
7723 &if_isfast, &if_isslow);
7605 7724
7606 Bind(&if_isfast); 7725 Bind(&if_isfast);
7607 { 7726 {
7608 var_map_index.Bind( 7727 var_map_index.Bind(
7609 IntPtrConstant(Context::FAST_ARRAY_KEY_ITERATOR_MAP_INDEX)); 7728 IntPtrConstant(Context::FAST_ARRAY_KEY_ITERATOR_MAP_INDEX));
7610 var_array_map.Bind(array_map); 7729 var_array_map.Bind(array_map);
7611 Goto(&allocate_iterator); 7730 Goto(&allocate_iterator);
7612 } 7731 }
7613 7732
7614 Bind(&if_isslow); 7733 Bind(&if_isslow);
(...skipping 13 matching lines...) Expand all
7628 Goto(&allocate_iterator); 7747 Goto(&allocate_iterator);
7629 } 7748 }
7630 } else { 7749 } else {
7631 Label if_istypedarray(this), if_isgeneric(this); 7750 Label if_istypedarray(this), if_isgeneric(this);
7632 Branch(Word32Equal(array_type, Int32Constant(JS_TYPED_ARRAY_TYPE)), 7751 Branch(Word32Equal(array_type, Int32Constant(JS_TYPED_ARRAY_TYPE)),
7633 &if_istypedarray, &if_isgeneric); 7752 &if_istypedarray, &if_isgeneric);
7634 7753
7635 Bind(&if_isgeneric); 7754 Bind(&if_isgeneric);
7636 { 7755 {
7637 Label if_isfast(this), if_isslow(this); 7756 Label if_isfast(this), if_isslow(this);
7638 BranchIfFastJSArray(array, context, &if_isfast, &if_isslow); 7757 BranchIfFastJSArray(array, context, FastJSArrayAccessMode::INBOUNDS_READ,
7758 &if_isfast, &if_isslow);
7639 7759
7640 Bind(&if_isfast); 7760 Bind(&if_isfast);
7641 { 7761 {
7642 Label if_ispacked(this), if_isholey(this); 7762 Label if_ispacked(this), if_isholey(this);
7643 Node* elements_kind = LoadMapElementsKind(array_map); 7763 Node* elements_kind = LoadMapElementsKind(array_map);
7644 Branch(IsHoleyFastElementsKind(elements_kind), &if_isholey, 7764 Branch(IsHoleyFastElementsKind(elements_kind), &if_isholey,
7645 &if_ispacked); 7765 &if_ispacked);
7646 7766
7647 Bind(&if_isholey); 7767 Bind(&if_isholey);
7648 { 7768 {
(...skipping 122 matching lines...) Expand 10 before | Expand all | Expand 10 after
7771 argc_, FAST_ELEMENTS, mode, 7891 argc_, FAST_ELEMENTS, mode,
7772 (StandardFrameConstants::kFixedSlotCountAboveFp - 1) * kPointerSize); 7892 (StandardFrameConstants::kFixedSlotCountAboveFp - 1) * kPointerSize);
7773 arguments_ = assembler_->IntPtrAddFoldConstants(fp_, offset); 7893 arguments_ = assembler_->IntPtrAddFoldConstants(fp_, offset);
7774 if (mode == CodeStubAssembler::INTEGER_PARAMETERS) { 7894 if (mode == CodeStubAssembler::INTEGER_PARAMETERS) {
7775 argc_ = assembler->ChangeInt32ToIntPtr(argc_); 7895 argc_ = assembler->ChangeInt32ToIntPtr(argc_);
7776 } else if (mode == CodeStubAssembler::SMI_PARAMETERS) { 7896 } else if (mode == CodeStubAssembler::SMI_PARAMETERS) {
7777 argc_ = assembler->SmiUntag(argc_); 7897 argc_ = assembler->SmiUntag(argc_);
7778 } 7898 }
7779 } 7899 }
7780 7900
7781 Node* CodeStubArguments::GetReceiver() { 7901 Node* CodeStubArguments::GetReceiver() const {
7782 return assembler_->Load(MachineType::AnyTagged(), arguments_, 7902 return assembler_->Load(MachineType::AnyTagged(), arguments_,
7783 assembler_->IntPtrConstant(kPointerSize)); 7903 assembler_->IntPtrConstant(kPointerSize));
7784 } 7904 }
7785 7905
7786 Node* CodeStubArguments::AtIndex(Node* index, 7906 Node* CodeStubArguments::AtIndex(Node* index,
7787 CodeStubAssembler::ParameterMode mode) { 7907 CodeStubAssembler::ParameterMode mode) const {
7908 typedef compiler::Node Node;
7788 Node* negated_index = assembler_->IntPtrSubFoldConstants( 7909 Node* negated_index = assembler_->IntPtrSubFoldConstants(
7789 assembler_->IntPtrOrSmiConstant(0, mode), index); 7910 assembler_->IntPtrOrSmiConstant(0, mode), index);
7790 Node* offset = 7911 Node* offset =
7791 assembler_->ElementOffsetFromIndex(negated_index, FAST_ELEMENTS, mode, 0); 7912 assembler_->ElementOffsetFromIndex(negated_index, FAST_ELEMENTS, mode, 0);
7792 return assembler_->Load(MachineType::AnyTagged(), arguments_, offset); 7913 return assembler_->Load(MachineType::AnyTagged(), arguments_, offset);
7793 } 7914 }
7794 7915
7795 Node* CodeStubArguments::AtIndex(int index) { 7916 Node* CodeStubArguments::AtIndex(int index) const {
7796 return AtIndex(assembler_->IntPtrConstant(index)); 7917 return AtIndex(assembler_->IntPtrConstant(index));
7797 } 7918 }
7798 7919
7799 void CodeStubArguments::ForEach(const CodeStubAssembler::VariableList& vars, 7920 void CodeStubArguments::ForEach(const CodeStubAssembler::VariableList& vars,
7800 CodeStubArguments::ForEachBodyFunction body, 7921 CodeStubArguments::ForEachBodyFunction body,
7801 Node* first, Node* last, 7922 Node* first, Node* last,
7802 CodeStubAssembler::ParameterMode mode) { 7923 CodeStubAssembler::ParameterMode mode) {
7803 assembler_->Comment("CodeStubArguments::ForEach"); 7924 assembler_->Comment("CodeStubArguments::ForEach");
7804 DCHECK_IMPLIES(first == nullptr || last == nullptr, 7925 DCHECK_IMPLIES(first == nullptr || last == nullptr,
7805 mode == CodeStubAssembler::INTPTR_PARAMETERS); 7926 mode == CodeStubAssembler::INTPTR_PARAMETERS);
(...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after
7849 7970
7850 Node* CodeStubAssembler::IsDebugActive() { 7971 Node* CodeStubAssembler::IsDebugActive() {
7851 Node* is_debug_active = Load( 7972 Node* is_debug_active = Load(
7852 MachineType::Uint8(), 7973 MachineType::Uint8(),
7853 ExternalConstant(ExternalReference::debug_is_active_address(isolate()))); 7974 ExternalConstant(ExternalReference::debug_is_active_address(isolate())));
7854 return WordNotEqual(is_debug_active, Int32Constant(0)); 7975 return WordNotEqual(is_debug_active, Int32Constant(0));
7855 } 7976 }
7856 7977
7857 } // namespace internal 7978 } // namespace internal
7858 } // namespace v8 7979 } // namespace v8
OLDNEW
« no previous file with comments | « src/code-stub-assembler.h ('k') | src/code-stubs.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698