Commit 20b437f1 authored by Olivier Yiptong's avatar Olivier Yiptong Committed by Commit Bot

Reland "FontAccess: Sort fonts in lexicographical order"

This is a reland of 404b7cc4

The original CL failed some tests because the code assumes that
platform-specific APIs called returned unique data. This was a false
assumption.

This reland follows another CL: https://crrev.com/c/2438875, which
ensures that fonts are not duplicated.

Original change's description:
> FontAccess: Sort fonts in lexicographical order
>
> This change ensures fonts are sorted before being cached. This change is
> due to a concern about fingerprinting:
> https://github.com/w3ctag/design-reviews/issues/399#issuecomment-530679815
>
> This change ensures that fonts are sorted in lexicographical order.
>
> Bug: 1043306
> Change-Id: Ia3acf2a45cb473124df4e489683bdc7bac15dde4
> Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/2427040
> Commit-Queue: Olivier Yiptong <oyiptong@chromium.org>
> Reviewed-by: Joshua Bell <jsbell@chromium.org>
> Cr-Commit-Position: refs/heads/master@{#810519}

Bug: 1043306
Change-Id: Ic3d70744661a838d82349c017a1cb0e8c23a3654
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/2432815
Commit-Queue: Olivier Yiptong <oyiptong@chromium.org>
Reviewed-by: default avatarJoshua Bell <jsbell@chromium.org>
Cr-Commit-Position: refs/heads/master@{#812965}
parent fd364bbd
......@@ -183,11 +183,19 @@ void ValidateFontEnumerationBasic(FontEnumerationStatus status,
base::ReadOnlySharedMemoryMapping mapping = region.Map();
table.ParseFromArray(mapping.memory(), mapping.size());
blink::FontEnumerationTable_FontMetadata previous_font;
for (const auto& font : table.fonts()) {
EXPECT_GT(font.postscript_name().size(), 0ULL)
<< "postscript_name size is not zero.";
EXPECT_GT(font.full_name().size(), 0ULL) << "full_name size is not zero.";
EXPECT_GT(font.family().size(), 0ULL) << "family size is not zero.";
if (previous_font.IsInitialized()) {
EXPECT_LT(previous_font.postscript_name(), font.postscript_name())
<< "font list is sorted";
}
previous_font = font;
}
}
......
......@@ -97,6 +97,16 @@ void FontEnumerationCache::BuildEnumerationCache(
std::unique_ptr<blink::FontEnumerationTable> table) {
DCHECK(!enumeration_cache_built_.IsSet());
// Postscript names, according to spec, are expected to be encoded in a subset
// of ASCII. See:
// https://docs.microsoft.com/en-us/typography/opentype/spec/name This is why
// a "simple" byte-wise comparison is used.
std::sort(table->mutable_fonts()->begin(), table->mutable_fonts()->end(),
[](const blink::FontEnumerationTable_FontMetadata& a,
const blink::FontEnumerationTable_FontMetadata& b) {
return a.postscript_name() < b.postscript_name();
});
enumeration_cache_memory_ =
base::ReadOnlySharedMemoryRegion::Create(table->ByteSizeLong());
......
......@@ -22,3 +22,32 @@ font_access_test(async t => {
assert_fonts_exist(availableFonts, getEnumerationTestSet());
}, 'query(): standard fonts returned');
font_access_test(async t => {
const iterator = navigator.fonts.query();
if (!isPlatformSupported()) {
await promise_rejects_dom(t, 'NotSupportedError', (async () => {
for await (const f of iterator) {
}
})());
return;
}
// The following tests that fonts are sorted. Postscript names are expected to
// be encoded in a subset of the ASCII character set.
// See: https://docs.microsoft.com/en-us/typography/opentype/spec/name
// Should the Postscript name contain characters that are multi-byte, this
// test may erroneously fail.
let previousFont = null;
for await (const font of iterator) {
if (previousFont) {
assert_true(
previousFont.postscriptName < font.postscriptName,
`font is not in expected order. expected: ${
previousFont.postscriptName} < ${font.postscriptName}`);
}
previousFont = font;
}
}, 'query(): fonts are sorted');
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