[Intl] Fix error message to report the right method.

Bug: v8:9464
Change-Id: I3252de850bbaa5fdb15f5fc2103f1ebb7be3e1ea
Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/1799396
Commit-Queue: Frank Tang <ftang@chromium.org>
Reviewed-by: Jakob Kummerow <jkummerow@chromium.org>
Cr-Commit-Position: refs/heads/master@{#63734}
This commit is contained in:
Frank Tang 2019-09-12 11:24:26 -07:00 committed by Commit Bot
parent ee0581c332
commit 6cf125a90c
17 changed files with 166 additions and 107 deletions

View File

@ -125,26 +125,24 @@ Object BigIntToStringImpl(Handle<Object> receiver, Handle<Object> radix,
BUILTIN(BigIntPrototypeToLocaleString) {
HandleScope scope(isolate);
const char* method = "BigInt.prototype.toLocaleString";
#ifdef V8_INTL_SUPPORT
if (FLAG_harmony_intl_bigint) {
// 1. Let x be ? thisBigIntValue(this value).
Handle<BigInt> x;
ASSIGN_RETURN_FAILURE_ON_EXCEPTION(
isolate, x,
ThisBigIntValue(isolate, args.receiver(),
"BigInt.prototype.toLocaleString"));
isolate, x, ThisBigIntValue(isolate, args.receiver(), method));
RETURN_RESULT_OR_FAILURE(
isolate,
Intl::NumberToLocaleString(isolate, x, args.atOrUndefined(isolate, 1),
args.atOrUndefined(isolate, 2)));
args.atOrUndefined(isolate, 2), method));
}
// Fallbacks to old toString implemention if flag is off or no
// V8_INTL_SUPPORT
#endif // V8_INTL_SUPPORT
Handle<Object> radix = isolate->factory()->undefined_value();
return BigIntToStringImpl(args.receiver(), radix, isolate,
"BigInt.prototype.toLocaleString");
return BigIntToStringImpl(args.receiver(), radix, isolate, method);
}
BUILTIN(BigIntPrototypeToString) {

View File

@ -854,16 +854,18 @@ BUILTIN(DatePrototypeToLocaleDateString) {
isolate->CountUsage(v8::Isolate::UseCounterFeature::kDateToLocaleDateString);
CHECK_RECEIVER(JSDate, date, "Date.prototype.toLocaleDateString");
const char* method = "Date.prototype.toLocaleDateString";
CHECK_RECEIVER(JSDate, date, method);
RETURN_RESULT_OR_FAILURE(
isolate, JSDateTimeFormat::ToLocaleDateTime(
isolate,
date, // date
args.atOrUndefined(isolate, 1), // locales
args.atOrUndefined(isolate, 2), // options
JSDateTimeFormat::RequiredOption::kDate, // required
JSDateTimeFormat::DefaultsOption::kDate)); // defaults
date, // date
args.atOrUndefined(isolate, 1), // locales
args.atOrUndefined(isolate, 2), // options
JSDateTimeFormat::RequiredOption::kDate, // required
JSDateTimeFormat::DefaultsOption::kDate, // defaults
method)); // method
}
// ecma402 #sup-date.prototype.tolocalestring
@ -872,16 +874,18 @@ BUILTIN(DatePrototypeToLocaleString) {
isolate->CountUsage(v8::Isolate::UseCounterFeature::kDateToLocaleString);
CHECK_RECEIVER(JSDate, date, "Date.prototype.toLocaleString");
const char* method = "Date.prototype.toLocaleString";
CHECK_RECEIVER(JSDate, date, method);
RETURN_RESULT_OR_FAILURE(
isolate, JSDateTimeFormat::ToLocaleDateTime(
isolate,
date, // date
args.atOrUndefined(isolate, 1), // locales
args.atOrUndefined(isolate, 2), // options
JSDateTimeFormat::RequiredOption::kAny, // required
JSDateTimeFormat::DefaultsOption::kAll)); // defaults
date, // date
args.atOrUndefined(isolate, 1), // locales
args.atOrUndefined(isolate, 2), // options
JSDateTimeFormat::RequiredOption::kAny, // required
JSDateTimeFormat::DefaultsOption::kAll, // defaults
method)); // method
}
// ecma402 #sup-date.prototype.tolocaletimestring
@ -890,16 +894,18 @@ BUILTIN(DatePrototypeToLocaleTimeString) {
isolate->CountUsage(v8::Isolate::UseCounterFeature::kDateToLocaleTimeString);
CHECK_RECEIVER(JSDate, date, "Date.prototype.toLocaleTimeString");
const char* method = "Date.prototype.toLocaleTimeString";
CHECK_RECEIVER(JSDate, date, method);
RETURN_RESULT_OR_FAILURE(
isolate, JSDateTimeFormat::ToLocaleDateTime(
isolate,
date, // date
args.atOrUndefined(isolate, 1), // locales
args.atOrUndefined(isolate, 2), // options
JSDateTimeFormat::RequiredOption::kTime, // required
JSDateTimeFormat::DefaultsOption::kTime)); // defaults
date, // date
args.atOrUndefined(isolate, 1), // locales
args.atOrUndefined(isolate, 2), // options
JSDateTimeFormat::RequiredOption::kTime, // required
JSDateTimeFormat::DefaultsOption::kTime, // defaults
method)); // method
}
#endif // V8_INTL_SUPPORT

View File

@ -282,8 +282,8 @@ Object LegacyFormatConstructor(BuiltinArguments args, Isolate* isolate,
// 3. Perform ? Initialize<T>(Format, locales, options).
Handle<T> format;
ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, format,
T::New(isolate, map, locales, options));
ASSIGN_RETURN_FAILURE_ON_EXCEPTION(
isolate, format, T::New(isolate, map, locales, options, method));
// 4. Let this be the this value.
Handle<Object> receiver = args.receiver();
@ -367,7 +367,8 @@ Object DisallowCallConstructor(BuiltinArguments args, Isolate* isolate,
* Common code shared by Collator and V8BreakIterator
*/
template <class T>
Object CallOrConstructConstructor(BuiltinArguments args, Isolate* isolate) {
Object CallOrConstructConstructor(BuiltinArguments args, Isolate* isolate,
const char* method) {
Handle<JSReceiver> new_target;
if (args.new_target()->IsUndefined(isolate)) {
@ -386,7 +387,8 @@ Object CallOrConstructConstructor(BuiltinArguments args, Isolate* isolate) {
ASSIGN_RETURN_FAILURE_ON_EXCEPTION(
isolate, map, JSFunction::GetDerivedMap(isolate, target, new_target));
RETURN_RESULT_OR_FAILURE(isolate, T::New(isolate, map, locales, options));
RETURN_RESULT_OR_FAILURE(isolate,
T::New(isolate, map, locales, options, method));
}
} // namespace
@ -884,7 +886,7 @@ BUILTIN(CollatorConstructor) {
isolate->CountUsage(v8::Isolate::UseCounterFeature::kCollator);
return CallOrConstructConstructor<JSCollator>(args, isolate);
return CallOrConstructConstructor<JSCollator>(args, isolate, "Intl.Collator");
}
BUILTIN(CollatorPrototypeResolvedOptions) {
@ -1069,7 +1071,8 @@ BUILTIN(SegmenterPrototypeSegment) {
BUILTIN(V8BreakIteratorConstructor) {
HandleScope scope(isolate);
return CallOrConstructConstructor<JSV8BreakIterator>(args, isolate);
return CallOrConstructConstructor<JSV8BreakIterator>(args, isolate,
"Intl.v8BreakIterator");
}
BUILTIN(V8BreakIteratorPrototypeResolvedOptions) {

View File

@ -111,6 +111,7 @@ BUILTIN(NumberPrototypeToFixed) {
// ES6 section 20.1.3.4 Number.prototype.toLocaleString ( [ r1 [ , r2 ] ] )
BUILTIN(NumberPrototypeToLocaleString) {
HandleScope scope(isolate);
const char* method = "Number.prototype.toLocaleString";
isolate->CountUsage(v8::Isolate::UseCounterFeature::kNumberToLocaleString);
@ -123,17 +124,17 @@ BUILTIN(NumberPrototypeToLocaleString) {
// 1. Let x be ? thisNumberValue(this value)
if (!value->IsNumber()) {
THROW_NEW_ERROR_RETURN_FAILURE(
isolate, NewTypeError(MessageTemplate::kNotGeneric,
isolate->factory()->NewStringFromAsciiChecked(
"Number.prototype.toLocaleString"),
isolate->factory()->Number_string()));
isolate,
NewTypeError(MessageTemplate::kNotGeneric,
isolate->factory()->NewStringFromAsciiChecked(method),
isolate->factory()->Number_string()));
}
#ifdef V8_INTL_SUPPORT
RETURN_RESULT_OR_FAILURE(
isolate,
Intl::NumberToLocaleString(isolate, value, args.atOrUndefined(isolate, 1),
args.atOrUndefined(isolate, 2)));
args.atOrUndefined(isolate, 2), method));
#else
// Turn the {value} into a String.
return *isolate->factory()->NumberToString(value);

View File

@ -136,20 +136,21 @@ BUILTIN(StringPrototypeLocaleCompare) {
HandleScope handle_scope(isolate);
isolate->CountUsage(v8::Isolate::UseCounterFeature::kStringLocaleCompare);
const char* method = "String.prototype.localeCompare";
#ifdef V8_INTL_SUPPORT
TO_THIS_STRING(str1, "String.prototype.localeCompare");
TO_THIS_STRING(str1, method);
Handle<String> str2;
ASSIGN_RETURN_FAILURE_ON_EXCEPTION(
isolate, str2, Object::ToString(isolate, args.atOrUndefined(isolate, 1)));
RETURN_RESULT_OR_FAILURE(
isolate, Intl::StringLocaleCompare(isolate, str1, str2,
args.atOrUndefined(isolate, 2),
args.atOrUndefined(isolate, 3)));
isolate, Intl::StringLocaleCompare(
isolate, str1, str2, args.atOrUndefined(isolate, 2),
args.atOrUndefined(isolate, 3), method));
#else
DCHECK_EQ(2, args.length());
TO_THIS_STRING(str1, "String.prototype.localeCompare");
TO_THIS_STRING(str1, method);
Handle<String> str2;
ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, str2,
Object::ToString(isolate, args.at(1)));

View File

@ -177,12 +177,13 @@ const UChar* GetUCharBufferFromFlat(const String::FlatContent& flat,
template <typename T>
MaybeHandle<T> New(Isolate* isolate, Handle<JSFunction> constructor,
Handle<Object> locales, Handle<Object> options) {
Handle<Object> locales, Handle<Object> options,
const char* method) {
Handle<Map> map;
ASSIGN_RETURN_ON_EXCEPTION(
isolate, map,
JSFunction::GetDerivedMap(isolate, constructor, constructor), T);
return T::New(isolate, map, locales, options);
return T::New(isolate, map, locales, options, method);
}
} // namespace
@ -995,11 +996,9 @@ MaybeHandle<String> Intl::StringLocaleConvertCase(Isolate* isolate,
}
}
MaybeHandle<Object> Intl::StringLocaleCompare(Isolate* isolate,
Handle<String> string1,
Handle<String> string2,
Handle<Object> locales,
Handle<Object> options) {
MaybeHandle<Object> Intl::StringLocaleCompare(
Isolate* isolate, Handle<String> string1, Handle<String> string2,
Handle<Object> locales, Handle<Object> options, const char* method) {
// We only cache the instance when both locales and options are undefined,
// as that is the only case when the specified side-effects of examining
// those arguments are unobservable.
@ -1025,7 +1024,7 @@ MaybeHandle<Object> Intl::StringLocaleCompare(Isolate* isolate,
Handle<JSCollator> collator;
ASSIGN_RETURN_ON_EXCEPTION(
isolate, collator,
New<JSCollator>(isolate, constructor, locales, options), Object);
New<JSCollator>(isolate, constructor, locales, options, method), Object);
if (can_cache) {
isolate->set_icu_object_in_cache(
Isolate::ICUObjectCacheType::kDefaultCollator,
@ -1084,7 +1083,8 @@ Handle<Object> Intl::CompareStrings(Isolate* isolate,
MaybeHandle<String> Intl::NumberToLocaleString(Isolate* isolate,
Handle<Object> num,
Handle<Object> locales,
Handle<Object> options) {
Handle<Object> options,
const char* method) {
Handle<Object> numeric_obj;
if (FLAG_harmony_intl_bigint) {
ASSIGN_RETURN_ON_EXCEPTION(isolate, numeric_obj,
@ -1119,7 +1119,8 @@ MaybeHandle<String> Intl::NumberToLocaleString(Isolate* isolate,
// 2. Let numberFormat be ? Construct(%NumberFormat%, « locales, options »).
ASSIGN_RETURN_ON_EXCEPTION(
isolate, number_format,
New<JSNumberFormat>(isolate, constructor, locales, options), String);
New<JSNumberFormat>(isolate, constructor, locales, options, method),
String);
if (can_cache) {
isolate->set_icu_object_in_cache(

View File

@ -164,7 +164,7 @@ class Intl {
V8_WARN_UNUSED_RESULT static MaybeHandle<Object> StringLocaleCompare(
Isolate* isolate, Handle<String> s1, Handle<String> s2,
Handle<Object> locales, Handle<Object> options);
Handle<Object> locales, Handle<Object> options, const char* method);
V8_WARN_UNUSED_RESULT static Handle<Object> CompareStrings(
Isolate* isolate, const icu::Collator& collator, Handle<String> s1,
@ -173,7 +173,7 @@ class Intl {
// ecma402/#sup-properties-of-the-number-prototype-object
V8_WARN_UNUSED_RESULT static MaybeHandle<String> NumberToLocaleString(
Isolate* isolate, Handle<Object> num, Handle<Object> locales,
Handle<Object> options);
Handle<Object> options, const char* method);
// ecma402/#sec-setnfdigitoptions
struct NumberFormatDigitOptions {

View File

@ -17,7 +17,7 @@ namespace internal {
MaybeHandle<JSV8BreakIterator> JSV8BreakIterator::New(
Isolate* isolate, Handle<Map> map, Handle<Object> locales,
Handle<Object> options_obj) {
Handle<Object> options_obj, const char* service) {
Factory* factory = isolate->factory();
// 1. Let requestedLocales be ? CanonicalizeLocaleList(locales).
@ -31,15 +31,14 @@ MaybeHandle<JSV8BreakIterator> JSV8BreakIterator::New(
if (options_obj->IsUndefined(isolate)) {
options = factory->NewJSObjectWithNullProto();
} else {
ASSIGN_RETURN_ON_EXCEPTION(
isolate, options,
Object::ToObject(isolate, options_obj, "Intl.JSV8BreakIterator"),
JSV8BreakIterator);
ASSIGN_RETURN_ON_EXCEPTION(isolate, options,
Object::ToObject(isolate, options_obj, service),
JSV8BreakIterator);
}
// Extract locale string
Maybe<Intl::MatcherOption> maybe_locale_matcher =
Intl::GetLocaleMatcher(isolate, options, "Intl.JSV8BreakIterator");
Intl::GetLocaleMatcher(isolate, options, service);
MAYBE_RETURN(maybe_locale_matcher, MaybeHandle<JSV8BreakIterator>());
Intl::MatcherOption matcher = maybe_locale_matcher.FromJust();
@ -49,7 +48,7 @@ MaybeHandle<JSV8BreakIterator> JSV8BreakIterator::New(
// Extract type from options
Maybe<Type> maybe_type = Intl::GetStringOption<Type>(
isolate, options, "type", "Intl.v8BreakIterator",
isolate, options, "type", service,
{"word", "character", "sentence", "line"},
{Type::WORD, Type::CHARACTER, Type::SENTENCE, Type::LINE}, Type::WORD);
MAYBE_RETURN(maybe_type, MaybeHandle<JSV8BreakIterator>());

View File

@ -31,7 +31,7 @@ class JSV8BreakIterator : public JSObject {
public:
V8_WARN_UNUSED_RESULT static MaybeHandle<JSV8BreakIterator> New(
Isolate* isolate, Handle<Map> map, Handle<Object> input_locales,
Handle<Object> input_options);
Handle<Object> input_options, const char* service);
static Handle<JSObject> ResolvedOptions(
Isolate* isolate, Handle<JSV8BreakIterator> break_iterator);

View File

@ -243,7 +243,8 @@ void SetCaseFirstOption(icu::Collator* icu_collator,
// static
MaybeHandle<JSCollator> JSCollator::New(Isolate* isolate, Handle<Map> map,
Handle<Object> locales,
Handle<Object> options_obj) {
Handle<Object> options_obj,
const char* service) {
// 1. Let requestedLocales be ? CanonicalizeLocaleList(locales).
Maybe<std::vector<std::string>> maybe_requested_locales =
Intl::CanonicalizeLocaleList(isolate, locales);
@ -258,9 +259,9 @@ MaybeHandle<JSCollator> JSCollator::New(Isolate* isolate, Handle<Map> map,
} else {
// 3. Else
// 3. a. Let options be ? ToObject(options).
ASSIGN_RETURN_ON_EXCEPTION(
isolate, options_obj,
Object::ToObject(isolate, options_obj, "Intl.Collator"), JSCollator);
ASSIGN_RETURN_ON_EXCEPTION(isolate, options_obj,
Object::ToObject(isolate, options_obj, service),
JSCollator);
}
// At this point, options_obj can either be a JSObject or a JSProxy only.
@ -269,7 +270,7 @@ MaybeHandle<JSCollator> JSCollator::New(Isolate* isolate, Handle<Map> map,
// 4. Let usage be ? GetOption(options, "usage", "string", « "sort",
// "search" », "sort").
Maybe<Usage> maybe_usage = Intl::GetStringOption<Usage>(
isolate, options, "usage", "Intl.Collator", {"sort", "search"},
isolate, options, "usage", service, {"sort", "search"},
{Usage::SORT, Usage::SEARCH}, Usage::SORT);
MAYBE_RETURN(maybe_usage, MaybeHandle<JSCollator>());
Usage usage = maybe_usage.FromJust();
@ -278,7 +279,7 @@ MaybeHandle<JSCollator> JSCollator::New(Isolate* isolate, Handle<Map> map,
// « "lookup", "best fit" », "best fit").
// 10. Set opt.[[localeMatcher]] to matcher.
Maybe<Intl::MatcherOption> maybe_locale_matcher =
Intl::GetLocaleMatcher(isolate, options, "Intl.Collator");
Intl::GetLocaleMatcher(isolate, options, service);
MAYBE_RETURN(maybe_locale_matcher, MaybeHandle<JSCollator>());
Intl::MatcherOption matcher = maybe_locale_matcher.FromJust();
@ -293,14 +294,14 @@ MaybeHandle<JSCollator> JSCollator::New(Isolate* isolate, Handle<Map> map,
//
// 13. Set opt.[[kn]] to numeric.
bool numeric;
Maybe<bool> found_numeric = Intl::GetBoolOption(isolate, options, "numeric",
"Intl.Collator", &numeric);
Maybe<bool> found_numeric =
Intl::GetBoolOption(isolate, options, "numeric", service, &numeric);
MAYBE_RETURN(found_numeric, MaybeHandle<JSCollator>());
// 14. Let caseFirst be ? GetOption(options, "caseFirst", "string",
// « "upper", "lower", "false" », undefined).
Maybe<Intl::CaseFirst> maybe_case_first =
Intl::GetCaseFirst(isolate, options, "Intl.Collator");
Intl::GetCaseFirst(isolate, options, service);
MAYBE_RETURN(maybe_case_first, MaybeHandle<JSCollator>());
Intl::CaseFirst case_first = maybe_case_first.FromJust();
@ -411,7 +412,7 @@ MaybeHandle<JSCollator> JSCollator::New(Isolate* isolate, Handle<Map> map,
// 24. Let sensitivity be ? GetOption(options, "sensitivity",
// "string", « "base", "accent", "case", "variant" », undefined).
Maybe<Sensitivity> maybe_sensitivity = Intl::GetStringOption<Sensitivity>(
isolate, options, "sensitivity", "Intl.Collator",
isolate, options, "sensitivity", service,
{"base", "accent", "case", "variant"},
{Sensitivity::kBase, Sensitivity::kAccent, Sensitivity::kCase,
Sensitivity::kVariant},
@ -451,9 +452,8 @@ MaybeHandle<JSCollator> JSCollator::New(Isolate* isolate, Handle<Map> map,
// 27.Let ignorePunctuation be ? GetOption(options,
// "ignorePunctuation", "boolean", undefined, false).
bool ignore_punctuation;
Maybe<bool> found_ignore_punctuation =
Intl::GetBoolOption(isolate, options, "ignorePunctuation",
"Intl.Collator", &ignore_punctuation);
Maybe<bool> found_ignore_punctuation = Intl::GetBoolOption(
isolate, options, "ignorePunctuation", service, &ignore_punctuation);
MAYBE_RETURN(found_ignore_punctuation, MaybeHandle<JSCollator>());
// 28. Set collator.[[IgnorePunctuation]] to ignorePunctuation.

View File

@ -34,7 +34,7 @@ class JSCollator : public JSObject {
// ecma402/#sec-initializecollator
V8_WARN_UNUSED_RESULT static MaybeHandle<JSCollator> New(
Isolate* isolate, Handle<Map> map, Handle<Object> locales,
Handle<Object> options);
Handle<Object> options, const char* service);
// ecma402/#sec-intl.collator.prototype.resolvedoptions
static Handle<JSObject> ResolvedOptions(Isolate* isolate,

View File

@ -641,7 +641,8 @@ Isolate::ICUObjectCacheType ConvertToCacheType(
MaybeHandle<String> JSDateTimeFormat::ToLocaleDateTime(
Isolate* isolate, Handle<Object> date, Handle<Object> locales,
Handle<Object> options, RequiredOption required, DefaultsOption defaults) {
Handle<Object> options, RequiredOption required, DefaultsOption defaults,
const char* method) {
Isolate::ICUObjectCacheType cache_type = ConvertToCacheType(defaults);
Factory* factory = isolate->factory();
@ -691,7 +692,8 @@ MaybeHandle<String> JSDateTimeFormat::ToLocaleDateTime(
Handle<JSDateTimeFormat> date_time_format;
ASSIGN_RETURN_ON_EXCEPTION(
isolate, date_time_format,
JSDateTimeFormat::New(isolate, map, locales, internal_options), String);
JSDateTimeFormat::New(isolate, map, locales, internal_options, method),
String);
if (can_cache) {
isolate->set_icu_object_in_cache(
@ -1215,7 +1217,7 @@ enum FormatMatcherOption { kBestFit, kBasic };
// ecma402/#sec-initializedatetimeformat
MaybeHandle<JSDateTimeFormat> JSDateTimeFormat::New(
Isolate* isolate, Handle<Map> map, Handle<Object> locales,
Handle<Object> input_options) {
Handle<Object> input_options, const char* service) {
Factory* factory = isolate->factory();
// 1. Let requestedLocales be ? CanonicalizeLocaleList(locales).
Maybe<std::vector<std::string>> maybe_requested_locales =
@ -1265,21 +1267,21 @@ MaybeHandle<JSDateTimeFormat> JSDateTimeFormat::New(
}
Maybe<Intl::MatcherOption> maybe_locale_matcher =
Intl::GetLocaleMatcher(isolate, options, "Intl.DateTimeFormat");
Intl::GetLocaleMatcher(isolate, options, service);
MAYBE_RETURN(maybe_locale_matcher, MaybeHandle<JSDateTimeFormat>());
Intl::MatcherOption locale_matcher = maybe_locale_matcher.FromJust();
// 6. Let hour12 be ? GetOption(options, "hour12", "boolean", undefined,
// undefined).
bool hour12;
Maybe<bool> maybe_get_hour12 = Intl::GetBoolOption(
isolate, options, "hour12", "Intl.DateTimeFormat", &hour12);
Maybe<bool> maybe_get_hour12 =
Intl::GetBoolOption(isolate, options, "hour12", service, &hour12);
MAYBE_RETURN(maybe_get_hour12, Handle<JSDateTimeFormat>());
// 7. Let hourCycle be ? GetOption(options, "hourCycle", "string", « "h11",
// "h12", "h23", "h24" », undefined).
Maybe<Intl::HourCycle> maybe_hour_cycle =
Intl::GetHourCycle(isolate, options, "Intl.DateTimeFormat");
Intl::GetHourCycle(isolate, options, service);
MAYBE_RETURN(maybe_hour_cycle, MaybeHandle<JSDateTimeFormat>());
Intl::HourCycle hour_cycle = maybe_hour_cycle.FromJust();
@ -1321,9 +1323,8 @@ MaybeHandle<JSDateTimeFormat> JSDateTimeFormat::New(
// 17. Let timeZone be ? Get(options, "timeZone").
const std::vector<const char*> empty_values;
std::unique_ptr<char[]> timezone = nullptr;
Maybe<bool> maybe_timezone =
Intl::GetStringOption(isolate, options, "timeZone", empty_values,
"Intl.DateTimeFormat", &timezone);
Maybe<bool> maybe_timezone = Intl::GetStringOption(
isolate, options, "timeZone", empty_values, service, &timezone);
MAYBE_RETURN(maybe_timezone, Handle<JSDateTimeFormat>());
std::unique_ptr<icu::TimeZone> tz = CreateTimeZone(isolate, timezone.get());
@ -1413,7 +1414,7 @@ MaybeHandle<JSDateTimeFormat> JSDateTimeFormat::New(
// "full", "long", "medium", "short" », undefined).
Maybe<DateTimeStyle> maybe_date_style =
Intl::GetStringOption<DateTimeStyle>(
isolate, options, "dateStyle", "Intl.DateTimeFormat",
isolate, options, "dateStyle", service,
{"full", "long", "medium", "short"},
{DateTimeStyle::kFull, DateTimeStyle::kLong, DateTimeStyle::kMedium,
DateTimeStyle::kShort},
@ -1427,7 +1428,7 @@ MaybeHandle<JSDateTimeFormat> JSDateTimeFormat::New(
// "full", "long", "medium", "short" »).
Maybe<DateTimeStyle> maybe_time_style =
Intl::GetStringOption<DateTimeStyle>(
isolate, options, "timeStyle", "Intl.DateTimeFormat",
isolate, options, "timeStyle", service,
{"full", "long", "medium", "short"},
{DateTimeStyle::kFull, DateTimeStyle::kLong, DateTimeStyle::kMedium,
DateTimeStyle::kShort},
@ -1455,9 +1456,9 @@ MaybeHandle<JSDateTimeFormat> JSDateTimeFormat::New(
// i. Let prop be the name given in the Property column of the row.
// ii. Let value be ? GetOption(options, prop, "string", « the strings
// given in the Values column of the row », undefined).
Maybe<bool> maybe_get_option = Intl::GetStringOption(
isolate, options, item.property.c_str(), item.allowed_values,
"Intl.DateTimeFormat", &input);
Maybe<bool> maybe_get_option =
Intl::GetStringOption(isolate, options, item.property.c_str(),
item.allowed_values, service, &input);
MAYBE_RETURN(maybe_get_option, Handle<JSDateTimeFormat>());
if (maybe_get_option.FromJust()) {
if (item.property == "hour") {
@ -1486,8 +1487,7 @@ MaybeHandle<JSDateTimeFormat> JSDateTimeFormat::New(
// « "basic", "best fit" », "best fit").
Maybe<FormatMatcherOption> maybe_format_matcher =
Intl::GetStringOption<FormatMatcherOption>(
isolate, options, "formatMatcher", "Intl.DateTimeFormat",
{"best fit", "basic"},
isolate, options, "formatMatcher", service, {"best fit", "basic"},
{FormatMatcherOption::kBestFit, FormatMatcherOption::kBasic},
FormatMatcherOption::kBestFit);
MAYBE_RETURN(maybe_format_matcher, MaybeHandle<JSDateTimeFormat>());

View File

@ -34,7 +34,7 @@ class JSDateTimeFormat : public JSObject {
public:
V8_WARN_UNUSED_RESULT static MaybeHandle<JSDateTimeFormat> New(
Isolate* isolate, Handle<Map> map, Handle<Object> locales,
Handle<Object> options);
Handle<Object> options, const char* service);
V8_WARN_UNUSED_RESULT static MaybeHandle<JSObject> ResolvedOptions(
Isolate* isolate, Handle<JSDateTimeFormat> date_time_format);
@ -82,7 +82,8 @@ class JSDateTimeFormat : public JSObject {
V8_WARN_UNUSED_RESULT static MaybeHandle<String> ToLocaleDateTime(
Isolate* isolate, Handle<Object> date, Handle<Object> locales,
Handle<Object> options, RequiredOption required, DefaultsOption defaults);
Handle<Object> options, RequiredOption required, DefaultsOption defaults,
const char* method);
V8_EXPORT_PRIVATE static const std::set<std::string>& GetAvailableLocales();

View File

@ -837,7 +837,8 @@ MaybeHandle<JSNumberFormat> JSNumberFormat::UnwrapNumberFormat(
MaybeHandle<JSNumberFormat> JSNumberFormat::New(Isolate* isolate,
Handle<Map> map,
Handle<Object> locales,
Handle<Object> options_obj) {
Handle<Object> options_obj,
const char* service) {
Factory* factory = isolate->factory();
// 1. Let requestedLocales be ? CanonicalizeLocaleList(locales).
@ -854,10 +855,9 @@ MaybeHandle<JSNumberFormat> JSNumberFormat::New(Isolate* isolate,
} else {
// 3. Else
// 3. a. Let options be ? ToObject(options).
ASSIGN_RETURN_ON_EXCEPTION(
isolate, options_obj,
Object::ToObject(isolate, options_obj, "Intl.NumberFormat"),
JSNumberFormat);
ASSIGN_RETURN_ON_EXCEPTION(isolate, options_obj,
Object::ToObject(isolate, options_obj, service),
JSNumberFormat);
}
// At this point, options_obj can either be a JSObject or a JSProxy only.
@ -868,7 +868,7 @@ MaybeHandle<JSNumberFormat> JSNumberFormat::New(Isolate* isolate,
// "lookup", "best fit" », "best fit").
// 6. Set opt.[[localeMatcher]] to matcher.
Maybe<Intl::MatcherOption> maybe_locale_matcher =
Intl::GetLocaleMatcher(isolate, options, "Intl.NumberFormat");
Intl::GetLocaleMatcher(isolate, options, service);
MAYBE_RETURN(maybe_locale_matcher, MaybeHandle<JSNumberFormat>());
Intl::MatcherOption matcher = maybe_locale_matcher.FromJust();
@ -914,7 +914,6 @@ MaybeHandle<JSNumberFormat> JSNumberFormat::New(Isolate* isolate,
// 12. Let style be ? GetOption(options, "style", "string", « "decimal",
// "percent", "currency" », "decimal").
const char* service = "Intl.NumberFormat";
std::vector<const char*> style_str_values({"decimal", "percent", "currency"});
std::vector<JSNumberFormat::Style> style_enum_values(
@ -1035,7 +1034,7 @@ MaybeHandle<JSNumberFormat> JSNumberFormat::New(Isolate* isolate,
THROW_NEW_ERROR(
isolate,
NewTypeError(MessageTemplate::kInvalidUnit,
factory->NewStringFromStaticChars("Intl.NumberFormat"),
factory->NewStringFromAsciiChecked(service),
factory->empty_string()),
JSNumberFormat);
}
@ -1047,10 +1046,9 @@ MaybeHandle<JSNumberFormat> JSNumberFormat::New(Isolate* isolate,
if (maybe_wellformed.IsNothing()) {
THROW_NEW_ERROR(
isolate,
NewRangeError(
MessageTemplate::kInvalidUnit,
factory->NewStringFromStaticChars("Intl.NumberFormat"),
factory->NewStringFromAsciiChecked(unit.c_str())),
NewRangeError(MessageTemplate::kInvalidUnit,
factory->NewStringFromAsciiChecked(service),
factory->NewStringFromAsciiChecked(unit.c_str())),
JSNumberFormat);
}
std::pair<icu::MeasureUnit, icu::MeasureUnit> unit_pair =

View File

@ -36,7 +36,7 @@ class JSNumberFormat : public JSObject {
// ecma402/#sec-initializenumberformat
V8_WARN_UNUSED_RESULT static MaybeHandle<JSNumberFormat> New(
Isolate* isolate, Handle<Map> map, Handle<Object> locales,
Handle<Object> options);
Handle<Object> options, const char* service);
// ecma402/#sec-unwrapnumberformat
V8_WARN_UNUSED_RESULT static MaybeHandle<JSNumberFormat> UnwrapNumberFormat(

View File

@ -157,7 +157,7 @@ function assertThrows(code, type_opt, cause_opt) {
assertInstanceof(e, type_opt);
}
if (arguments.length >= 3) {
assertEquals(cause_opt, e.type, 'thrown exception type mismatch');
assertEquals(cause_opt, e.message, 'thrown exception type mismatch');
}
// Success.
return;

View File

@ -0,0 +1,51 @@
// Copyright 2019 the V8 project authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
// Number, BigInt and Intl.NumberFormat
assertThrows(
"new Intl.NumberFormat('en', { style: 'unit', unit: 'son'});",
RangeError,
"Invalid unit argument for Intl.NumberFormat() 'son'");
assertThrows(
"123n.toLocaleString('en', { style: 'unit', unit: 'son'});",
RangeError,
"Invalid unit argument for BigInt.prototype.toLocaleString() 'son'");
assertThrows(
"Math.PI.toLocaleString('en', { style: 'unit', unit: 'son'});",
RangeError,
"Invalid unit argument for Number.prototype.toLocaleString() 'son'");
// String and Intl.Collator
assertThrows(
"new Intl.Collator('en', { usage: 'mom'});",
RangeError,
"Value mom out of range for Intl.Collator options property usage");
assertThrows(
"'abc'.localeCompare('efg', 'en', { usage: 'mom'});",
RangeError,
"Value mom out of range for String.prototype.localeCompare options property usage");
// Date and Intl.DateTimeFormat
assertThrows(
"new Intl.DateTimeFormat('en', { hour: 'dad'});",
RangeError,
"Value dad out of range for Intl.DateTimeFormat options property hour");
assertThrows(
"(new Date).toLocaleDateString('en', { hour: 'dad'});",
RangeError,
"Value dad out of range for Date.prototype.toLocaleDateString options property hour");
assertThrows(
"(new Date).toLocaleString('en', { hour: 'dad'});",
RangeError,
"Value dad out of range for Date.prototype.toLocaleString options property hour");
assertThrows(
"(new Date).toLocaleTimeString('en', { hour: 'dad'});",
RangeError,
"Value dad out of range for Date.prototype.toLocaleTimeString options property hour");