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

Side by Side Diff: src/builtins/builtins-array-gen.cc

Issue 2775203002: [builtins] Implement %TypedArray%.prototype.{some,every} in the CSA (Closed)
Patch Set: fix switching backing store bug Created 3 years, 8 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 unified diff | Download patch
« no previous file with comments | « src/builtins/builtins.h ('k') | src/code-stub-assembler.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 2017 the V8 project authors. All rights reserved. 1 // Copyright 2017 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 4
5 #include "src/builtins/builtins-utils-gen.h" 5 #include "src/builtins/builtins-utils-gen.h"
6 #include "src/builtins/builtins.h" 6 #include "src/builtins/builtins.h"
7 #include "src/code-stub-assembler.h" 7 #include "src/code-stub-assembler.h"
8 8
9 namespace v8 { 9 namespace v8 {
10 namespace internal { 10 namespace internal {
(...skipping 277 matching lines...) Expand 10 before | Expand all | Expand 10 after
288 context_ = context; 288 context_ = context;
289 this_arg_ = this_arg; 289 this_arg_ = this_arg;
290 callbackfn_ = callbackfn; 290 callbackfn_ = callbackfn;
291 a_.Bind(a); 291 a_.Bind(a);
292 k_.Bind(initial_k); 292 k_.Bind(initial_k);
293 o_ = o; 293 o_ = o;
294 len_ = len; 294 len_ = len;
295 to_.Bind(to); 295 to_.Bind(to);
296 } 296 }
297 297
298 void GenerateIteratingTypedArrayBuiltinBody(
299 const char* name, const BuiltinResultGenerator& generator,
300 const CallResultProcessor& processor, const PostLoopAction& action) {
301 Node* name_string =
302 HeapConstant(isolate()->factory()->NewStringFromAsciiChecked(name));
303
304 // ValidateTypedArray: tc39.github.io/ecma262/#sec-validatetypedarray
305
306 Label not_typed_array(this, Label::kDeferred),
petermarshall 2017/03/29 13:21:58 I would rename not_typed_array to say what it does
307 detached(this, Label::kDeferred);
308
309 GotoIf(TaggedIsSmi(receiver_), &not_typed_array);
310 GotoIfNot(HasInstanceType(receiver_, JS_TYPED_ARRAY_TYPE),
311 &not_typed_array);
312
313 o_ = receiver_;
314 Node* array_buffer = LoadObjectField(o_, JSTypedArray::kBufferOffset);
315 GotoIf(IsDetachedBuffer(array_buffer), &detached);
316
317 len_ = LoadObjectField(o_, JSTypedArray::kLengthOffset);
318
319 Label not_callable(this, Label::kDeferred);
petermarshall 2017/03/29 13:21:58 Same here, throw_not_callable
320 Label start(this);
321 GotoIf(TaggedIsSmi(callbackfn_), &not_callable);
322 Branch(IsCallableMap(LoadMap(callbackfn_)), &start, &not_callable);
323
324 Bind(&not_typed_array);
325 {
326 CallRuntime(Runtime::kThrowTypeError, context_,
327 SmiConstant(MessageTemplate::kNotTypedArray));
328 Unreachable();
329 }
330
331 Bind(&detached);
332 {
333 CallRuntime(Runtime::kThrowTypeError, context_,
334 SmiConstant(MessageTemplate::kDetachedOperation),
335 name_string);
336 Unreachable();
337 }
338
339 Bind(&not_callable);
340 {
341 CallRuntime(Runtime::kThrowTypeError, context_,
342 SmiConstant(MessageTemplate::kCalledNonCallable),
343 callbackfn_);
344 Unreachable();
345 }
346
347 Label unexpected_instance_type(this);
348 Bind(&unexpected_instance_type);
349 Unreachable();
350
351 std::vector<int32_t> instance_types = {
352 #define INSTANCE_TYPE(Type, type, TYPE, ctype, size) FIXED_##TYPE##_ARRAY_TYPE,
353 TYPED_ARRAYS(INSTANCE_TYPE)
354 #undef INSTANCE_TYPE
355 };
356 std::vector<Label> labels;
357 for (size_t i = 0; i < instance_types.size(); ++i) {
358 labels.push_back(Label(this));
359 }
360 std::vector<Label*> label_ptrs;
361 for (Label& label : labels) {
362 label_ptrs.push_back(&label);
363 }
364
365 Bind(&start);
366 a_.Bind(generator(this));
367 Node* elements_type = LoadInstanceType(LoadElements(o_));
368 Switch(elements_type, &unexpected_instance_type, instance_types.data(),
369 label_ptrs.data(), labels.size());
370
371 for (size_t i = 0; i < labels.size(); ++i) {
372 Bind(&labels[i]);
373 Label done(this);
374 // TODO(tebbi): Silently cancelling the loop on buffer detachment is a
375 // spec violation. Should go to &detached and throw a TypeError instead.
376 VisitAllTypedArrayElements(
377 ElementsKindForInstanceType(
378 static_cast<InstanceType>(instance_types[i])),
379 array_buffer, processor, &done);
380 Goto(&done);
381 action(this);
382 // No exception, return success
383 Bind(&done);
384 Return(a_.value());
385 }
386 }
387
298 void GenerateIteratingArrayBuiltinLoopContinuation( 388 void GenerateIteratingArrayBuiltinLoopContinuation(
299 const CallResultProcessor& processor, const PostLoopAction& action, 389 const CallResultProcessor& processor, const PostLoopAction& action,
300 ForEachDirection direction = ForEachDirection::kForward) { 390 ForEachDirection direction = ForEachDirection::kForward) {
301 Label loop(this, {&k_, &a_, &to_}); 391 Label loop(this, {&k_, &a_, &to_});
302 Label after_loop(this); 392 Label after_loop(this);
303 Goto(&loop); 393 Goto(&loop);
304 Bind(&loop); 394 Bind(&loop);
305 { 395 {
306 if (direction == ForEachDirection::kForward) { 396 if (direction == ForEachDirection::kForward) {
307 // 8. Repeat, while k < len 397 // 8. Repeat, while k < len
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after
343 } 433 }
344 Goto(&loop); 434 Goto(&loop);
345 } 435 }
346 Bind(&after_loop); 436 Bind(&after_loop);
347 437
348 action(this); 438 action(this);
349 Return(a_.value()); 439 Return(a_.value());
350 } 440 }
351 441
352 private: 442 private:
443 static ElementsKind ElementsKindForInstanceType(InstanceType type) {
444 switch (type) {
445 #define INSTANCE_TYPE_TO_ELEMENTS_KIND(Type, type, TYPE, ctype, size) \
446 case FIXED_##TYPE##_ARRAY_TYPE: \
447 return TYPE##_ELEMENTS;
448
449 TYPED_ARRAYS(INSTANCE_TYPE_TO_ELEMENTS_KIND)
450 #undef INSTANCE_TYPE_TO_ELEMENTS_KIND
451
452 default:
453 UNREACHABLE();
454 return static_cast<ElementsKind>(-1);
455 }
456 }
457
458 void VisitAllTypedArrayElements(ElementsKind kind, Node* array_buffer,
459 const CallResultProcessor& processor,
460 Label* detached) {
461 VariableList list({&a_, &k_, &to_}, zone());
462
463 FastLoopBody body = [&](Node* index) {
464 GotoIf(IsDetachedBuffer(array_buffer), detached);
465 Node* elements = LoadElements(o_);
466 Node* base_ptr =
467 LoadObjectField(elements, FixedTypedArrayBase::kBasePointerOffset);
468 Node* external_ptr =
469 LoadObjectField(elements, FixedTypedArrayBase::kExternalPointerOffset,
470 MachineType::Pointer());
471 Node* data_ptr = IntPtrAdd(BitcastTaggedToWord(base_ptr), external_ptr);
472 Node* value = LoadFixedTypedArrayElementAsTagged(data_ptr, index, kind,
473 SMI_PARAMETERS);
474 k_.Bind(index);
475 a_.Bind(processor(this, value, index));
476 };
477 BuildFastLoop(list, SmiConstant(0), len_, body, 1,
478 ParameterMode::SMI_PARAMETERS, IndexAdvanceMode::kPost);
479 }
480
353 void VisitAllFastElementsOneKind(ElementsKind kind, 481 void VisitAllFastElementsOneKind(ElementsKind kind,
354 const CallResultProcessor& processor, 482 const CallResultProcessor& processor,
355 Label* array_changed, ParameterMode mode, 483 Label* array_changed, ParameterMode mode,
356 ForEachDirection direction) { 484 ForEachDirection direction) {
357 Comment("begin VisitAllFastElementsOneKind"); 485 Comment("begin VisitAllFastElementsOneKind");
358 Variable original_map(this, MachineRepresentation::kTagged); 486 Variable original_map(this, MachineRepresentation::kTagged);
359 original_map.Bind(LoadMap(o())); 487 original_map.Bind(LoadMap(o()));
360 VariableList list({&original_map, &a_, &k_, &to_}, zone()); 488 VariableList list({&original_map, &a_, &k_, &to_}, zone());
361 Node* start = IntPtrOrSmiConstant(0, mode); 489 Node* start = IntPtrOrSmiConstant(0, mode);
362 Node* end = TaggedToParameter(len(), mode); 490 Node* end = TaggedToParameter(len(), mode);
(...skipping 339 matching lines...) Expand 10 before | Expand all | Expand 10 after
702 new_target); 830 new_target);
703 831
704 GenerateIteratingArrayBuiltinBody( 832 GenerateIteratingArrayBuiltinBody(
705 "Array.prototype.some", 833 "Array.prototype.some",
706 &ArrayBuiltinCodeStubAssembler::SomeResultGenerator, 834 &ArrayBuiltinCodeStubAssembler::SomeResultGenerator,
707 &ArrayBuiltinCodeStubAssembler::SomeProcessor, 835 &ArrayBuiltinCodeStubAssembler::SomeProcessor,
708 &ArrayBuiltinCodeStubAssembler::NullPostLoopAction, 836 &ArrayBuiltinCodeStubAssembler::NullPostLoopAction,
709 CodeFactory::ArraySomeLoopContinuation(isolate())); 837 CodeFactory::ArraySomeLoopContinuation(isolate()));
710 } 838 }
711 839
840 TF_BUILTIN(TypedArrayPrototypeSome, ArrayBuiltinCodeStubAssembler) {
841 Node* context = Parameter(Descriptor::kContext);
842 Node* receiver = Parameter(Descriptor::kReceiver);
843 Node* callbackfn = Parameter(Descriptor::kCallbackFn);
844 Node* this_arg = Parameter(Descriptor::kThisArg);
845 Node* new_target = Parameter(Descriptor::kNewTarget);
846
847 InitIteratingArrayBuiltinBody(context, receiver, callbackfn, this_arg,
848 new_target);
849
850 GenerateIteratingTypedArrayBuiltinBody(
851 "%TypedArray%.prototype.some",
852 &ArrayBuiltinCodeStubAssembler::SomeResultGenerator,
853 &ArrayBuiltinCodeStubAssembler::SomeProcessor,
854 &ArrayBuiltinCodeStubAssembler::NullPostLoopAction);
855 }
856
712 TF_BUILTIN(ArrayEveryLoopContinuation, ArrayBuiltinCodeStubAssembler) { 857 TF_BUILTIN(ArrayEveryLoopContinuation, ArrayBuiltinCodeStubAssembler) {
713 Node* context = Parameter(Descriptor::kContext); 858 Node* context = Parameter(Descriptor::kContext);
714 Node* receiver = Parameter(Descriptor::kReceiver); 859 Node* receiver = Parameter(Descriptor::kReceiver);
715 Node* callbackfn = Parameter(Descriptor::kCallbackFn); 860 Node* callbackfn = Parameter(Descriptor::kCallbackFn);
716 Node* this_arg = Parameter(Descriptor::kThisArg); 861 Node* this_arg = Parameter(Descriptor::kThisArg);
717 Node* array = Parameter(Descriptor::kArray); 862 Node* array = Parameter(Descriptor::kArray);
718 Node* object = Parameter(Descriptor::kObject); 863 Node* object = Parameter(Descriptor::kObject);
719 Node* initial_k = Parameter(Descriptor::kInitialK); 864 Node* initial_k = Parameter(Descriptor::kInitialK);
720 Node* len = Parameter(Descriptor::kLength); 865 Node* len = Parameter(Descriptor::kLength);
721 Node* to = Parameter(Descriptor::kTo); 866 Node* to = Parameter(Descriptor::kTo);
(...skipping 18 matching lines...) Expand all
740 new_target); 885 new_target);
741 886
742 GenerateIteratingArrayBuiltinBody( 887 GenerateIteratingArrayBuiltinBody(
743 "Array.prototype.every", 888 "Array.prototype.every",
744 &ArrayBuiltinCodeStubAssembler::EveryResultGenerator, 889 &ArrayBuiltinCodeStubAssembler::EveryResultGenerator,
745 &ArrayBuiltinCodeStubAssembler::EveryProcessor, 890 &ArrayBuiltinCodeStubAssembler::EveryProcessor,
746 &ArrayBuiltinCodeStubAssembler::NullPostLoopAction, 891 &ArrayBuiltinCodeStubAssembler::NullPostLoopAction,
747 CodeFactory::ArrayEveryLoopContinuation(isolate())); 892 CodeFactory::ArrayEveryLoopContinuation(isolate()));
748 } 893 }
749 894
895 TF_BUILTIN(TypedArrayPrototypeEvery, ArrayBuiltinCodeStubAssembler) {
896 Node* context = Parameter(Descriptor::kContext);
897 Node* receiver = Parameter(Descriptor::kReceiver);
898 Node* callbackfn = Parameter(Descriptor::kCallbackFn);
899 Node* this_arg = Parameter(Descriptor::kThisArg);
900 Node* new_target = Parameter(Descriptor::kNewTarget);
901
902 InitIteratingArrayBuiltinBody(context, receiver, callbackfn, this_arg,
903 new_target);
904
905 GenerateIteratingTypedArrayBuiltinBody(
906 "%TypedArray%.prototype.every",
907 &ArrayBuiltinCodeStubAssembler::EveryResultGenerator,
908 &ArrayBuiltinCodeStubAssembler::EveryProcessor,
909 &ArrayBuiltinCodeStubAssembler::NullPostLoopAction);
910 }
911
750 TF_BUILTIN(ArrayReduceLoopContinuation, ArrayBuiltinCodeStubAssembler) { 912 TF_BUILTIN(ArrayReduceLoopContinuation, ArrayBuiltinCodeStubAssembler) {
751 Node* context = Parameter(Descriptor::kContext); 913 Node* context = Parameter(Descriptor::kContext);
752 Node* receiver = Parameter(Descriptor::kReceiver); 914 Node* receiver = Parameter(Descriptor::kReceiver);
753 Node* callbackfn = Parameter(Descriptor::kCallbackFn); 915 Node* callbackfn = Parameter(Descriptor::kCallbackFn);
754 Node* this_arg = Parameter(Descriptor::kThisArg); 916 Node* this_arg = Parameter(Descriptor::kThisArg);
755 Node* accumulator = Parameter(Descriptor::kAccumulator); 917 Node* accumulator = Parameter(Descriptor::kAccumulator);
756 Node* object = Parameter(Descriptor::kObject); 918 Node* object = Parameter(Descriptor::kObject);
757 Node* initial_k = Parameter(Descriptor::kInitialK); 919 Node* initial_k = Parameter(Descriptor::kInitialK);
758 Node* len = Parameter(Descriptor::kLength); 920 Node* len = Parameter(Descriptor::kLength);
759 Node* to = Parameter(Descriptor::kTo); 921 Node* to = Parameter(Descriptor::kTo);
(...skipping 1194 matching lines...) Expand 10 before | Expand all | Expand 10 after
1954 { 2116 {
1955 Node* message = SmiConstant(MessageTemplate::kDetachedOperation); 2117 Node* message = SmiConstant(MessageTemplate::kDetachedOperation);
1956 CallRuntime(Runtime::kThrowTypeError, context, message, 2118 CallRuntime(Runtime::kThrowTypeError, context, message,
1957 HeapConstant(operation)); 2119 HeapConstant(operation));
1958 Unreachable(); 2120 Unreachable();
1959 } 2121 }
1960 } 2122 }
1961 2123
1962 } // namespace internal 2124 } // namespace internal
1963 } // namespace v8 2125 } // namespace v8
OLDNEW
« no previous file with comments | « src/builtins/builtins.h ('k') | src/code-stub-assembler.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698