Commit 6f41bff2 authored by Z Nguyen-Huu's avatar Z Nguyen-Huu Committed by Commit Bot

Move RequireObjectCoercible to base.tq, update callsites

Use it in String builtins in CSA and String, Array, Object builtins in Torque

Change-Id: I9c828cb1f5f04622470bb71317654cbe09305049
Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/1680648
Commit-Queue: Z Nguyen-Huu <duongn@microsoft.com>
Reviewed-by: 's avatarJakob Gruber <jgruber@chromium.org>
Cr-Commit-Position: refs/heads/master@{#62473}
parent 569e5d23
...@@ -114,9 +114,7 @@ namespace array { ...@@ -114,9 +114,7 @@ namespace array {
ArrayEvery(js-implicit context: Context, receiver: Object)(...arguments): ArrayEvery(js-implicit context: Context, receiver: Object)(...arguments):
Object { Object {
try { try {
if (IsNullOrUndefined(receiver)) { RequireObjectCoercible(receiver, 'Array.prototype.every');
goto NullOrUndefinedError;
}
// 1. Let O be ? ToObject(this value). // 1. Let O be ? ToObject(this value).
const o: JSReceiver = ToObject_Inline(context, receiver); const o: JSReceiver = ToObject_Inline(context, receiver);
...@@ -146,8 +144,5 @@ namespace array { ...@@ -146,8 +144,5 @@ namespace array {
label TypeError deferred { label TypeError deferred {
ThrowTypeError(kCalledNonCallable, arguments[0]); ThrowTypeError(kCalledNonCallable, arguments[0]);
} }
label NullOrUndefinedError deferred {
ThrowTypeError(kCalledOnNullOrUndefined, 'Array.prototype.every');
}
} }
} }
...@@ -150,9 +150,7 @@ namespace array_filter { ...@@ -150,9 +150,7 @@ namespace array_filter {
ArrayFilter(js-implicit context: Context, receiver: Object)(...arguments): ArrayFilter(js-implicit context: Context, receiver: Object)(...arguments):
Object { Object {
try { try {
if (IsNullOrUndefined(receiver)) { RequireObjectCoercible(receiver, 'Array.prototype.filter');
goto NullOrUndefinedError;
}
// 1. Let O be ? ToObject(this value). // 1. Let O be ? ToObject(this value).
const o: JSReceiver = ToObject_Inline(context, receiver); const o: JSReceiver = ToObject_Inline(context, receiver);
...@@ -201,8 +199,5 @@ namespace array_filter { ...@@ -201,8 +199,5 @@ namespace array_filter {
label TypeError deferred { label TypeError deferred {
ThrowTypeError(kCalledNonCallable, arguments[0]); ThrowTypeError(kCalledNonCallable, arguments[0]);
} }
label NullOrUndefinedError deferred {
ThrowTypeError(kCalledOnNullOrUndefined, 'Array.prototype.filter');
}
} }
} }
...@@ -122,9 +122,7 @@ namespace array_find { ...@@ -122,9 +122,7 @@ namespace array_find {
ArrayPrototypeFind(js-implicit context: Context, receiver: Object)( ArrayPrototypeFind(js-implicit context: Context, receiver: Object)(
...arguments): Object { ...arguments): Object {
try { try {
if (IsNullOrUndefined(receiver)) { RequireObjectCoercible(receiver, 'Array.prototype.find');
goto NullOrUndefinedError;
}
// 1. Let O be ? ToObject(this value). // 1. Let O be ? ToObject(this value).
const o: JSReceiver = ToObject_Inline(context, receiver); const o: JSReceiver = ToObject_Inline(context, receiver);
...@@ -154,8 +152,5 @@ namespace array_find { ...@@ -154,8 +152,5 @@ namespace array_find {
label NotCallableError deferred { label NotCallableError deferred {
ThrowTypeError(kCalledNonCallable, arguments[0]); ThrowTypeError(kCalledNonCallable, arguments[0]);
} }
label NullOrUndefinedError deferred {
ThrowTypeError(kCalledOnNullOrUndefined, 'Array.prototype.find');
}
} }
} }
...@@ -123,9 +123,7 @@ namespace array_findindex { ...@@ -123,9 +123,7 @@ namespace array_findindex {
ArrayPrototypeFindIndex(js-implicit context: Context, receiver: Object)( ArrayPrototypeFindIndex(js-implicit context: Context, receiver: Object)(
...arguments): Object { ...arguments): Object {
try { try {
if (IsNullOrUndefined(receiver)) { RequireObjectCoercible(receiver, 'Array.prototype.findIndex');
goto NullOrUndefinedError;
}
// 1. Let O be ? ToObject(this value). // 1. Let O be ? ToObject(this value).
const o: JSReceiver = ToObject_Inline(context, receiver); const o: JSReceiver = ToObject_Inline(context, receiver);
...@@ -156,8 +154,5 @@ namespace array_findindex { ...@@ -156,8 +154,5 @@ namespace array_findindex {
label NotCallableError deferred { label NotCallableError deferred {
ThrowTypeError(kCalledNonCallable, arguments[0]); ThrowTypeError(kCalledNonCallable, arguments[0]);
} }
label NullOrUndefinedError deferred {
ThrowTypeError(kCalledOnNullOrUndefined, 'Array.prototype.findIndex');
}
} }
} }
...@@ -95,9 +95,7 @@ namespace array_foreach { ...@@ -95,9 +95,7 @@ namespace array_foreach {
ArrayForEach(js-implicit context: Context, receiver: Object)(...arguments): ArrayForEach(js-implicit context: Context, receiver: Object)(...arguments):
Object { Object {
try { try {
if (IsNullOrUndefined(receiver)) { RequireObjectCoercible(receiver, 'Array.prototype.forEach');
goto NullOrUndefinedError;
}
// 1. Let O be ? ToObject(this value). // 1. Let O be ? ToObject(this value).
const o: JSReceiver = ToObject_Inline(context, receiver); const o: JSReceiver = ToObject_Inline(context, receiver);
...@@ -130,8 +128,5 @@ namespace array_foreach { ...@@ -130,8 +128,5 @@ namespace array_foreach {
label TypeError deferred { label TypeError deferred {
ThrowTypeError(kCalledNonCallable, arguments[0]); ThrowTypeError(kCalledNonCallable, arguments[0]);
} }
label NullOrUndefinedError deferred {
ThrowTypeError(kCalledOnNullOrUndefined, 'Array.prototype.forEach');
}
} }
} }
...@@ -227,7 +227,7 @@ namespace array_map { ...@@ -227,7 +227,7 @@ namespace array_map {
ArrayMap(js-implicit context: Context, receiver: Object)(...arguments): ArrayMap(js-implicit context: Context, receiver: Object)(...arguments):
Object { Object {
try { try {
if (IsNullOrUndefined(receiver)) goto NullOrUndefinedError; RequireObjectCoercible(receiver, 'Array.prototype.map');
// 1. Let O be ? ToObject(this value). // 1. Let O be ? ToObject(this value).
const o: JSReceiver = ToObject_Inline(context, receiver); const o: JSReceiver = ToObject_Inline(context, receiver);
...@@ -269,8 +269,5 @@ namespace array_map { ...@@ -269,8 +269,5 @@ namespace array_map {
label TypeError deferred { label TypeError deferred {
ThrowTypeError(kCalledNonCallable, arguments[0]); ThrowTypeError(kCalledNonCallable, arguments[0]);
} }
label NullOrUndefinedError deferred {
ThrowTypeError(kCalledOnNullOrUndefined, 'Array.prototype.map');
}
} }
} }
...@@ -145,9 +145,7 @@ namespace array { ...@@ -145,9 +145,7 @@ namespace array {
ArrayReduceRight(js-implicit context: Context, receiver: Object)( ArrayReduceRight(js-implicit context: Context, receiver: Object)(
...arguments): Object { ...arguments): Object {
try { try {
if (IsNullOrUndefined(receiver)) { RequireObjectCoercible(receiver, 'Array.prototype.reduceRight');
goto NullOrUndefinedError;
}
// 1. Let O be ? ToObject(this value). // 1. Let O be ? ToObject(this value).
const o: JSReceiver = ToObject_Inline(context, receiver); const o: JSReceiver = ToObject_Inline(context, receiver);
...@@ -180,8 +178,5 @@ namespace array { ...@@ -180,8 +178,5 @@ namespace array {
label NoCallableError deferred { label NoCallableError deferred {
ThrowTypeError(kCalledNonCallable, arguments[0]); ThrowTypeError(kCalledNonCallable, arguments[0]);
} }
label NullOrUndefinedError deferred {
ThrowTypeError(kCalledOnNullOrUndefined, 'Array.prototype.reduceRight');
}
} }
} }
...@@ -145,9 +145,7 @@ namespace array { ...@@ -145,9 +145,7 @@ namespace array {
ArrayReduce(js-implicit context: Context, receiver: Object)(...arguments): ArrayReduce(js-implicit context: Context, receiver: Object)(...arguments):
Object { Object {
try { try {
if (IsNullOrUndefined(receiver)) { RequireObjectCoercible(receiver, 'Array.prototype.reduce');
goto NullOrUndefinedError;
}
// 1. Let O be ? ToObject(this value). // 1. Let O be ? ToObject(this value).
const o: JSReceiver = ToObject_Inline(context, receiver); const o: JSReceiver = ToObject_Inline(context, receiver);
...@@ -180,8 +178,5 @@ namespace array { ...@@ -180,8 +178,5 @@ namespace array {
label NoCallableError deferred { label NoCallableError deferred {
ThrowTypeError(kCalledNonCallable, arguments[0]); ThrowTypeError(kCalledNonCallable, arguments[0]);
} }
label NullOrUndefinedError deferred {
ThrowTypeError(kCalledOnNullOrUndefined, 'Array.prototype.reduce');
}
} }
} }
...@@ -114,9 +114,7 @@ namespace array { ...@@ -114,9 +114,7 @@ namespace array {
ArraySome(js-implicit context: Context, receiver: Object)(...arguments): ArraySome(js-implicit context: Context, receiver: Object)(...arguments):
Object { Object {
try { try {
if (IsNullOrUndefined(receiver)) { RequireObjectCoercible(receiver, 'Array.prototype.some');
goto NullOrUndefinedError;
}
// 1. Let O be ? ToObject(this value). // 1. Let O be ? ToObject(this value).
const o: JSReceiver = ToObject_Inline(context, receiver); const o: JSReceiver = ToObject_Inline(context, receiver);
...@@ -146,8 +144,5 @@ namespace array { ...@@ -146,8 +144,5 @@ namespace array {
label TypeError deferred { label TypeError deferred {
ThrowTypeError(kCalledNonCallable, arguments[0]); ThrowTypeError(kCalledNonCallable, arguments[0]);
} }
label NullOrUndefinedError deferred {
ThrowTypeError(kCalledOnNullOrUndefined, 'Array.prototype.some');
}
} }
} }
...@@ -2859,6 +2859,15 @@ macro ToBoolean(obj: Object): bool { ...@@ -2859,6 +2859,15 @@ macro ToBoolean(obj: Object): bool {
} }
} }
@export
macro RequireObjectCoercible(implicit context: Context)(
value: Object, name: constexpr string): Object {
if (IsNullOrUndefined(value)) {
ThrowTypeError(kCalledOnNullOrUndefined, name);
}
return value;
}
extern macro BranchIfSameValue(Object, Object): never labels Taken, NotTaken; extern macro BranchIfSameValue(Object, Object): never labels Taken, NotTaken;
transitioning macro ToIndex(input: Object, context: Context): Number transitioning macro ToIndex(input: Object, context: Context): Number
......
...@@ -952,19 +952,6 @@ void StringIncludesIndexOfAssembler::Generate(SearchVariant variant, ...@@ -952,19 +952,6 @@ void StringIncludesIndexOfAssembler::Generate(SearchVariant variant,
} }
} }
void StringBuiltinsAssembler::RequireObjectCoercible(Node* const context,
Node* const value,
const char* method_name) {
Label out(this), throw_exception(this, Label::kDeferred);
Branch(IsNullOrUndefined(value), &throw_exception, &out);
BIND(&throw_exception);
ThrowTypeError(context, MessageTemplate::kCalledOnNullOrUndefined,
method_name);
BIND(&out);
}
void StringBuiltinsAssembler::MaybeCallFunctionAtSymbol( void StringBuiltinsAssembler::MaybeCallFunctionAtSymbol(
Node* const context, Node* const object, Node* const maybe_string, Node* const context, Node* const object, Node* const maybe_string,
Handle<Symbol> symbol, DescriptorIndexAndName symbol_index, Handle<Symbol> symbol, DescriptorIndexAndName symbol_index,
...@@ -1072,10 +1059,10 @@ compiler::Node* StringBuiltinsAssembler::GetSubstitution( ...@@ -1072,10 +1059,10 @@ compiler::Node* StringBuiltinsAssembler::GetSubstitution(
TF_BUILTIN(StringPrototypeReplace, StringBuiltinsAssembler) { TF_BUILTIN(StringPrototypeReplace, StringBuiltinsAssembler) {
Label out(this); Label out(this);
Node* const receiver = Parameter(Descriptor::kReceiver); TNode<Object> receiver = CAST(Parameter(Descriptor::kReceiver));
Node* const search = Parameter(Descriptor::kSearch); Node* const search = Parameter(Descriptor::kSearch);
Node* const replace = Parameter(Descriptor::kReplace); Node* const replace = Parameter(Descriptor::kReplace);
Node* const context = Parameter(Descriptor::kContext); TNode<Context> context = CAST(Parameter(Descriptor::kContext));
TNode<Smi> const smi_zero = SmiConstant(0); TNode<Smi> const smi_zero = SmiConstant(0);
...@@ -1578,7 +1565,7 @@ TF_BUILTIN(StringPrototypeSplit, StringBuiltinsAssembler) { ...@@ -1578,7 +1565,7 @@ TF_BUILTIN(StringPrototypeSplit, StringBuiltinsAssembler) {
ChangeInt32ToIntPtr(Parameter(Descriptor::kJSActualArgumentsCount)); ChangeInt32ToIntPtr(Parameter(Descriptor::kJSActualArgumentsCount));
CodeStubArguments args(this, argc); CodeStubArguments args(this, argc);
Node* const receiver = args.GetReceiver(); TNode<Object> receiver = args.GetReceiver();
Node* const separator = args.GetOptionalArgumentValue(kSeparatorArg); Node* const separator = args.GetOptionalArgumentValue(kSeparatorArg);
Node* const limit = args.GetOptionalArgumentValue(kLimitArg); Node* const limit = args.GetOptionalArgumentValue(kLimitArg);
TNode<Context> context = CAST(Parameter(Descriptor::kContext)); TNode<Context> context = CAST(Parameter(Descriptor::kContext));
......
...@@ -76,9 +76,6 @@ class StringBuiltinsAssembler : public CodeStubAssembler { ...@@ -76,9 +76,6 @@ class StringBuiltinsAssembler : public CodeStubAssembler {
TNode<Smi> subject_length, TNode<Smi> subject_length,
TNode<Number> limit_number); TNode<Number> limit_number);
void RequireObjectCoercible(Node* const context, Node* const value,
const char* method_name);
TNode<BoolT> SmiIsNegative(TNode<Smi> value) { TNode<BoolT> SmiIsNegative(TNode<Smi> value) {
return SmiLessThan(value, SmiConstant(0)); return SmiLessThan(value, SmiConstant(0));
} }
......
...@@ -122,9 +122,8 @@ namespace object_setprototypeof { ...@@ -122,9 +122,8 @@ namespace object_setprototypeof {
js-implicit context: js-implicit context:
Context)(_receiver: Object, object: Object, proto: Object): Object { Context)(_receiver: Object, object: Object, proto: Object): Object {
// 1. Set O to ? RequireObjectCoercible(O). // 1. Set O to ? RequireObjectCoercible(O).
if (IsNullOrUndefined(object)) { RequireObjectCoercible(object, 'Object.setPrototypeOf');
ThrowTypeError(kCalledOnNullOrUndefined, 'Object.setPrototypeOf');
}
// 2. If Type(proto) is neither Object nor Null, throw a TypeError // 2. If Type(proto) is neither Object nor Null, throw a TypeError
// exception. // exception.
// 3. If Type(O) is not Object, return O. // 3. If Type(O) is not Object, return O.
......
...@@ -31,9 +31,10 @@ namespace string { ...@@ -31,9 +31,10 @@ namespace string {
js-implicit context: Context, receiver: Object)(...arguments): Boolean { js-implicit context: Context, receiver: Object)(...arguments): Boolean {
const searchString: Object = arguments[0]; const searchString: Object = arguments[0];
const endPosition: Object = arguments[1]; const endPosition: Object = arguments[1];
const kBuiltinName: constexpr string = 'String.prototype.endsWith';
// 1. Let O be ? RequireObjectCoercible(this value). // 1. Let O be ? RequireObjectCoercible(this value).
const object: Object = RequireObjectCoercible(receiver); const object: Object = RequireObjectCoercible(receiver, kBuiltinName);
// 2. Let S be ? ToString(O). // 2. Let S be ? ToString(O).
const string: String = ToString_Inline(context, object); const string: String = ToString_Inline(context, object);
...@@ -41,7 +42,7 @@ namespace string { ...@@ -41,7 +42,7 @@ namespace string {
// 3. Let isRegExp be ? IsRegExp(searchString). // 3. Let isRegExp be ? IsRegExp(searchString).
// 4. If isRegExp is true, throw a TypeError exception. // 4. If isRegExp is true, throw a TypeError exception.
if (IsRegExp(searchString)) { if (IsRegExp(searchString)) {
ThrowTypeError(kFirstArgumentNotRegExp, 'String.prototype.endsWith'); ThrowTypeError(kFirstArgumentNotRegExp, kBuiltinName);
} }
// 5. Let searchStr be ? ToString(searchString). // 5. Let searchStr be ? ToString(searchString).
......
...@@ -8,23 +8,15 @@ namespace string { ...@@ -8,23 +8,15 @@ namespace string {
extern macro RegExpBuiltinsAssembler::IsRegExp(implicit context: extern macro RegExpBuiltinsAssembler::IsRegExp(implicit context:
Context)(Object): bool; Context)(Object): bool;
// TODO(ryzokuken): Add RequireObjectCoercible to base.tq and update callsites
macro RequireObjectCoercible(implicit context: Context)(argument: Object):
Object {
if (IsNullOrUndefined(argument)) {
ThrowTypeError(kCalledOnNullOrUndefined, 'String.prototype.startsWith');
}
return argument;
}
// https://tc39.github.io/ecma262/#sec-string.prototype.startswith // https://tc39.github.io/ecma262/#sec-string.prototype.startswith
transitioning javascript builtin StringPrototypeStartsWith( transitioning javascript builtin StringPrototypeStartsWith(
js-implicit context: Context, receiver: Object)(...arguments): Boolean { js-implicit context: Context, receiver: Object)(...arguments): Boolean {
const searchString: Object = arguments[0]; const searchString: Object = arguments[0];
const position: Object = arguments[1]; const position: Object = arguments[1];
const kBuiltinName: constexpr string = 'String.prototype.startsWith';
// 1. Let O be ? RequireObjectCoercible(this value). // 1. Let O be ? RequireObjectCoercible(this value).
const object: Object = RequireObjectCoercible(receiver); const object: Object = RequireObjectCoercible(receiver, kBuiltinName);
// 2. Let S be ? ToString(O). // 2. Let S be ? ToString(O).
const string: String = ToString_Inline(context, object); const string: String = ToString_Inline(context, object);
...@@ -32,7 +24,7 @@ namespace string { ...@@ -32,7 +24,7 @@ namespace string {
// 3. Let isRegExp be ? IsRegExp(searchString). // 3. Let isRegExp be ? IsRegExp(searchString).
// 4. If isRegExp is true, throw a TypeError exception. // 4. If isRegExp is true, throw a TypeError exception.
if (IsRegExp(searchString)) { if (IsRegExp(searchString)) {
ThrowTypeError(kFirstArgumentNotRegExp, 'String.prototype.startsWith'); ThrowTypeError(kFirstArgumentNotRegExp, kBuiltinName);
} }
// 5. Let searchStr be ? ToString(searchString). // 5. Let searchStr be ? ToString(searchString).
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment