[cherry-pick m140] Fix FontConfig font matching with Fontations generated cache
When Fontations indexes font files and encounters a WOFF or WOFF2 font,
it generates a cache entry that only specifies that the font wrapper is
SFNT, and what the filename is. FreeType indexing generates more
metadata for an SFNT, as it loads the whole font and extracts such
metadata.
We should anyway not instantiate system fonts from WOFF2 files as that
does not work with memory mapping, and we previously haven't done so
as were filtering for typical extensions of only uncompressed files.
As a fix, make sure we are not trying to instantiate such fonts, by
a) Adding a pattern expectation for "fontwrapper" to be "SFNT" (which
will work with FontConfig versions >= 2.15)
b) Checking that we only use fonts as valid candidates that have at
least a font_format object in the pattern.
Bug: 40075390, 438643337
Fixed: 440023833
Change-Id: I958a9ddce3d49f67ce27ed0b0db847233349d576
Reviewed-on: https://skia-review.googlesource.com/c/skia/+/1041496
Auto-Submit: Dominik Röttsches <drott@google.com>
Reviewed-by: Ben Wagner <bungeman@google.com>
Commit-Queue: Dominik Röttsches <drott@google.com>
Reviewed-by: Dominik Röttsches <drott@google.com>
Commit-Queue: Ben Wagner <bungeman@google.com>
(cherry picked from commit c7bf48f472ac510fcfd4cb08a5af08c606e484ef)
Reviewed-on: https://skia-review.googlesource.com/c/skia/+/1043156
diff --git a/src/ports/SkFontConfigInterface_direct.cpp b/src/ports/SkFontConfigInterface_direct.cpp
index 021c58c..652059d 100644
--- a/src/ports/SkFontConfigInterface_direct.cpp
+++ b/src/ports/SkFontConfigInterface_direct.cpp
@@ -393,6 +393,11 @@
#define FC_WEIGHT_DEMILIGHT 65
#endif
+// Available since FontConfig 2.15.
+#ifndef FC_FONT_WRAPPER
+#define FC_FONT_WRAPPER "fontwrapper"
+#endif
+
static SkFontStyle skfontstyle_from_fcpattern(FcPattern* pattern) {
typedef SkFontStyle SkFS;
@@ -514,9 +519,8 @@
bool SkFontConfigInterfaceDirect::isValidPattern(FcPattern* pattern) {
#ifdef SK_FONT_CONFIG_INTERFACE_ONLY_ALLOW_SFNT_FONTS
const char* font_format = get_string(pattern, FC_FONTFORMAT);
- if (font_format
- && 0 != strcmp(font_format, kFontFormatTrueType)
- && 0 != strcmp(font_format, kFontFormatCFF))
+ if (!font_format || (0 != strcmp(font_format, kFontFormatTrueType) &&
+ 0 != strcmp(font_format, kFontFormatCFF)))
{
return false;
}
@@ -612,6 +616,10 @@
FcPatternAddBool(pattern, FC_SCALABLE, FcTrue);
+ // Prefer SFNT fonts in order to reduce the chance of having to reject the font
+ // in isValidPattern().
+ FcPatternAddString(pattern, FC_FONT_WRAPPER, reinterpret_cast<const FcChar8*>("SFNT"));
+
FcConfigSubstitute(fc, pattern, FcMatchPattern);
FcDefaultSubstitute(pattern);