Commit d82b2455 authored by Zhang, Shiyu's avatar Zhang, Shiyu Committed by Commit Bot

[intl] Speed up String.prototype.localCompare via compareUTF8

The localeCompare for ASCII chars needs to expand the string contents
from one-byte representation into two-byte representation, which
requires memory copy. This CL skips the representation conversion by
using compareUTF8. It can improve the JetStream2 cdjs case by 21% on
my machine.

Change-Id: I3841dc700e36744aadd9a1ff9fa7d93c84dc04fd
Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/1624705
Commit-Queue: Jakob Kummerow <jkummerow@chromium.org>
Reviewed-by: 's avatarJakob Kummerow <jkummerow@chromium.org>
Cr-Commit-Position: refs/heads/master@{#62408}
parent e79751b3
......@@ -209,6 +209,24 @@ icu::UnicodeString Intl::ToICUUnicodeString(Isolate* isolate,
return icu::UnicodeString(uchar_buffer, length);
}
icu::StringPiece Intl::ToICUStringPiece(Isolate* isolate,
Handle<String> string) {
DCHECK(string->IsFlat());
DisallowHeapAllocation no_gc;
const String::FlatContent& flat = string->GetFlatContent(no_gc);
if (!flat.IsOneByte()) return icu::StringPiece(nullptr, 0);
int32_t length = string->length();
const char* char_buffer =
reinterpret_cast<const char*>(flat.ToOneByteVector().begin());
if (!String::IsAscii(char_buffer, length)) {
return icu::StringPiece(nullptr, 0);
}
return icu::StringPiece(char_buffer, length);
}
namespace {
MaybeHandle<String> LocaleConvertCase(Isolate* isolate, Handle<String> s,
bool is_to_upper, const char* lang) {
......@@ -1044,6 +1062,16 @@ Handle<Object> Intl::CompareStrings(Isolate* isolate,
UCollationResult result;
UErrorCode status = U_ZERO_ERROR;
icu::StringPiece string_piece1 = Intl::ToICUStringPiece(isolate, string1);
if (!string_piece1.empty()) {
icu::StringPiece string_piece2 = Intl::ToICUStringPiece(isolate, string2);
if (!string_piece2.empty()) {
result = icu_collator.compareUTF8(string_piece1, string_piece2, status);
DCHECK(U_SUCCESS(status));
return factory->NewNumberFromInt(result);
}
}
icu::UnicodeString string_val1 = Intl::ToICUUnicodeString(isolate, string1);
icu::UnicodeString string_val2 = Intl::ToICUUnicodeString(isolate, string2);
result = icu_collator.compare(string_val1, string_val2, status);
......
......@@ -324,6 +324,10 @@ class Intl {
static icu::UnicodeString ToICUUnicodeString(Isolate* isolate,
Handle<String> string);
// Convert a Handle<String> to icu::StringPiece
static icu::StringPiece ToICUStringPiece(Isolate* isolate,
Handle<String> string);
static const uint8_t* ToLatin1LowerTable();
static String ConvertOneByteToLower(String src, String dst);
......
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