Commit a711f281 authored by Adam Klein's avatar Adam Klein Committed by Commit Bot

Make Object::ToObject() output more useful error messages

This allows us to avoid a separate receiver typecheck in a few places
without regressing the error messages generated.

As more Array methods move to C++, this will get more usage.

Bug: v8:3577
Change-Id: Ibdd17c781548520172ce62442bc3a800e5c09e99
Reviewed-on: https://chromium-review.googlesource.com/486103Reviewed-by: 's avatarSathya Gunasekaran <gsathya@chromium.org>
Commit-Queue: Adam Klein <adamk@chromium.org>
Cr-Commit-Position: refs/heads/master@{#44904}
parent 6058b447
......@@ -1206,15 +1206,9 @@ BUILTIN(ArrayConcat) {
HandleScope scope(isolate);
Handle<Object> receiver = args.receiver();
// TODO(bmeurer): Do we really care about the exact exception message here?
if (receiver->IsNullOrUndefined(isolate)) {
THROW_NEW_ERROR_RETURN_FAILURE(
isolate, NewTypeError(MessageTemplate::kCalledOnNullOrUndefined,
isolate->factory()->NewStringFromAsciiChecked(
"Array.prototype.concat")));
}
ASSIGN_RETURN_FAILURE_ON_EXCEPTION(
isolate, receiver, Object::ToObject(isolate, args.receiver()));
isolate, receiver,
Object::ToObject(isolate, args.receiver(), "Array.prototype.concat"));
args[0] = *receiver;
Handle<JSArray> result_array;
......
......@@ -1121,9 +1121,10 @@ bool Object::ToUint32(uint32_t* value) {
// static
MaybeHandle<JSReceiver> Object::ToObject(Isolate* isolate,
Handle<Object> object) {
Handle<Object> object,
const char* method_name) {
if (object->IsJSReceiver()) return Handle<JSReceiver>::cast(object);
return ToObject(isolate, object, isolate->native_context());
return ToObject(isolate, object, isolate->native_context(), method_name);
}
......
......@@ -108,10 +108,10 @@ Handle<FieldType> Object::OptimalType(Isolate* isolate,
return FieldType::Any(isolate);
}
MaybeHandle<JSReceiver> Object::ToObject(Isolate* isolate,
Handle<Object> object,
Handle<Context> native_context) {
Handle<Context> native_context,
const char* method_name) {
if (object->IsJSReceiver()) return Handle<JSReceiver>::cast(object);
Handle<JSFunction> constructor;
if (object->IsSmi()) {
......@@ -120,6 +120,14 @@ MaybeHandle<JSReceiver> Object::ToObject(Isolate* isolate,
int constructor_function_index =
Handle<HeapObject>::cast(object)->map()->GetConstructorFunctionIndex();
if (constructor_function_index == Map::kNoConstructorFunctionIndex) {
if (method_name != nullptr) {
THROW_NEW_ERROR(
isolate,
NewTypeError(
MessageTemplate::kCalledOnNullOrUndefined,
isolate->factory()->NewStringFromAsciiChecked(method_name)),
JSReceiver);
}
THROW_NEW_ERROR(isolate,
NewTypeError(MessageTemplate::kUndefinedOrNullToObject),
JSReceiver);
......
......@@ -1234,12 +1234,19 @@ class Object {
// ES6 section 7.2.13 Strict Equality Comparison
bool StrictEquals(Object* that);
// ES6 section 7.1.13 ToObject
// Convert to a JSObject if needed.
// native_context is used when creating wrapper object.
//
// Passing a non-null method_name allows us to give a more informative
// error message for those cases where ToObject is being called on
// the receiver of a built-in method.
MUST_USE_RESULT static inline MaybeHandle<JSReceiver> ToObject(
Isolate* isolate, Handle<Object> object);
Isolate* isolate, Handle<Object> object,
const char* method_name = nullptr);
MUST_USE_RESULT static MaybeHandle<JSReceiver> ToObject(
Isolate* isolate, Handle<Object> object, Handle<Context> context);
Isolate* isolate, Handle<Object> object, Handle<Context> native_context,
const char* method_name = nullptr);
// ES6 section 9.2.1.2, OrdinaryCallBindThis for sloppy callee.
MUST_USE_RESULT static MaybeHandle<JSReceiver> ConvertReceiver(
......
......@@ -531,16 +531,10 @@ RUNTIME_FUNCTION(Runtime_ArrayIndexOf) {
CONVERT_ARG_HANDLE_CHECKED(Object, from_index, 2);
// Let O be ? ToObject(this value).
Handle<Object> receiver_obj = args.at(0);
if (receiver_obj->IsNullOrUndefined(isolate)) {
THROW_NEW_ERROR_RETURN_FAILURE(
isolate, NewTypeError(MessageTemplate::kCalledOnNullOrUndefined,
isolate->factory()->NewStringFromAsciiChecked(
"Array.prototype.indexOf")));
}
Handle<JSReceiver> object;
ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, object,
Object::ToObject(isolate, args.at(0)));
ASSIGN_RETURN_FAILURE_ON_EXCEPTION(
isolate, object,
Object::ToObject(isolate, args.at(0), "Array.prototype.indexOf"));
// Let len be ? ToLength(? Get(O, "length")).
int64_t len;
......
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