1 /* -*- Mode: C++; tab-width: 20; indent-tabs-mode: nil; c-basic-offset: 2 -*-
2 * This Source Code Form is subject to the terms of the Mozilla Public
3 * License, v. 2.0. If a copy of the MPL was not distributed with this
4 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6 #ifndef GFX_FONTENTRY_H
7 #define GFX_FONTENTRY_H
13 #include "COLRFonts.h"
14 #include "ThebesRLBoxTypes.h"
15 #include "gfxFontUtils.h"
16 #include "gfxFontVariations.h"
19 #include "harfbuzz/hb.h"
20 #include "mozilla/AlreadyAddRefed.h"
21 #include "mozilla/Assertions.h"
22 #include "mozilla/FontPropertyTypes.h"
23 #include "mozilla/MemoryReporting.h"
24 #include "mozilla/Mutex.h"
25 #include "mozilla/RefPtr.h"
26 #include "mozilla/RWLock.h"
27 #include "mozilla/TypedEnumBits.h"
28 #include "mozilla/UniquePtr.h"
29 #include "mozilla/intl/UnicodeScriptCodes.h"
30 #include "nsTHashMap.h"
32 #include "nsHashKeys.h"
33 #include "nsISupports.h"
34 #include "nsStringFwd.h"
42 class gfxPlatformFontList
;
44 class gfxUserFontData
;
47 struct gfxFontFeature
;
49 enum class eFontPresentation
: uint8_t;
57 class SVGContextPaint
;
61 } // namespace fontlist
62 } // namespace mozilla
64 typedef struct gr_face gr_face
;
65 typedef struct FT_MM_Var_ FT_MM_Var
;
67 #define NO_FONT_LANGUAGE_OVERRIDE 0
69 class gfxCharacterMap
: public gfxSparseBitSet
{
71 // gfxCharacterMap instances may be shared across multiple threads via a
72 // global table managed by gfxPlatformFontList. Once a gfxCharacterMap is
73 // inserted in the global table, its mShared flag will be TRUE, and we
74 // cannot safely delete it except from gfxPlatformFontList (which will
75 // use a lock to ensure entries are removed from its table and deleted
78 // AddRef() is pretty much standard. We don't return the refcount as our
79 // users don't care about it.
81 MOZ_ASSERT_TYPE_OK_FOR_REFCOUNTING(gfxCharacterMap
);
82 MOZ_ASSERT(int32_t(mRefCnt
) >= 0, "illegal refcnt");
83 [[maybe_unused
]] nsrefcnt count
= ++mRefCnt
;
84 NS_LOG_ADDREF(this, count
, "gfxCharacterMap", sizeof(*this));
87 // Custom Release(): if the object is referenced from the global shared
88 // table, and we're releasing the last *other* reference to it, then we
89 // notify the global table to consider also releasing its ref. (That may
90 // not actually happen, if another thread is racing with us and takes a
91 // new reference, or completes the release first!)
93 MOZ_ASSERT(int32_t(mRefCnt
) > 0, "dup release");
94 // We can't safely read this after we've decremented mRefCnt, so save it
95 // in a local variable here. Note that the value is never reset to false
96 // once it has been set to true (when recording the cmap in the shared
97 // table), so there's no risk of this resulting in a "false positive" when
98 // tested later. A "false negative" is possible but harmless; it would
99 // just mean we miss an opportunity to release a reference from the shared
101 bool isShared
= mShared
;
103 // Ensure we only access mRefCnt once, for consistency if the object is
104 // being used by multiple threads.
105 nsrefcnt count
= --mRefCnt
;
106 NS_LOG_RELEASE(this, count
, "gfxCharacterMap");
108 // If isShared was true, this object has been shared across threads. In
109 // that case, if the refcount went to 1, we notify the shared table so
110 // it can drop its reference and delete the object.
112 MOZ_ASSERT(count
> 0);
114 NotifyMaybeReleased(this);
119 // Otherwise, this object hasn't been shared and we can safely delete it
120 // as we must have been holding the only reference. (Note that if we were
121 // holding the only reference, there's no other owner who can have set
122 // mShared to true since we read it above.)
128 gfxCharacterMap() = default;
130 explicit gfxCharacterMap(const gfxSparseBitSet
& aOther
)
131 : gfxSparseBitSet(aOther
) {}
133 size_t SizeOfExcludingThis(mozilla::MallocSizeOf aMallocSizeOf
) const {
134 return gfxSparseBitSet::SizeOfExcludingThis(aMallocSizeOf
);
137 // hash of the cmap bitvector
140 // if cmap is built on the fly it's never shared
141 bool mBuildOnTheFly
= false;
143 // Character map is shared globally. This can only be set by the thread that
144 // originally created the map, as no other thread can get a reference until
145 // it has been shared via the global table.
146 bool mShared
= false;
149 friend class gfxPlatformFontList
;
151 // Destructor should not be called except via Release().
152 // (Note that our "friend" gfxPlatformFontList also accesses this from its
153 // MaybeRemoveCmap method.)
154 ~gfxCharacterMap() = default;
156 nsrefcnt
RefCount() const { return mRefCnt
; }
158 void CalcHash() { mHash
= GetChecksum(); }
160 static void NotifyMaybeReleased(gfxCharacterMap
* aCmap
);
162 // Only used when clearing the shared-cmap hashtable during shutdown.
163 void ClearSharedFlag() {
164 MOZ_ASSERT(NS_IsMainThread());
168 mozilla::ThreadSafeAutoRefCnt mRefCnt
;
171 gfxCharacterMap(const gfxCharacterMap
&) = delete;
172 gfxCharacterMap
& operator=(const gfxCharacterMap
&) = delete;
175 // Info on an individual font feature, for reporting available features
176 // to DevTools via the GetFeatureInfo method.
177 struct gfxFontFeatureInfo
{
183 class gfxFontEntryCallbacks
;
187 typedef mozilla::gfx::DrawTarget DrawTarget
;
188 typedef mozilla::intl::Script Script
;
189 typedef mozilla::FontWeight FontWeight
;
190 typedef mozilla::FontSlantStyle FontSlantStyle
;
191 typedef mozilla::FontStretch FontStretch
;
192 typedef mozilla::WeightRange WeightRange
;
193 typedef mozilla::SlantStyleRange SlantStyleRange
;
194 typedef mozilla::StretchRange StretchRange
;
197 NS_INLINE_DECL_THREADSAFE_REFCOUNTING(gfxFontEntry
)
199 explicit gfxFontEntry(const nsACString
& aName
, bool aIsStandardFace
= false);
201 gfxFontEntry() = delete;
202 gfxFontEntry(const gfxFontEntry
&) = delete;
203 gfxFontEntry
& operator=(const gfxFontEntry
&) = delete;
205 // Create a new entry that refers to the same font as this, but without
206 // additional state that may have been set up (such as family name).
207 // (This is only to be used for system fonts in the platform font list,
209 virtual gfxFontEntry
* Clone() const = 0;
211 // unique name for the face, *not* the family; not necessarily the
212 // "real" or user-friendly name, may be an internal identifier
213 const nsCString
& Name() const { return mName
; }
216 const nsCString
& FamilyName() const { return mFamilyName
; }
218 // The following two methods may be relatively expensive, as they
219 // will (usually, except on Linux) load and parse the 'name' table;
220 // they are intended only for the font-inspection API, not for
221 // perf-critical layout/drawing work.
223 // The "real" name of the face, if available from the font resource;
224 // returns Name() if nothing better is available.
225 virtual nsCString
RealFaceName();
227 WeightRange
Weight() const { return mWeightRange
; }
228 StretchRange
Stretch() const { return mStretchRange
; }
229 SlantStyleRange
SlantStyle() const { return mStyleRange
; }
231 bool IsUserFont() const { return mIsDataUserFont
|| mIsLocalUserFont
; }
232 bool IsLocalUserFont() const { return mIsLocalUserFont
; }
233 bool IsFixedPitch() const { return mFixedPitch
; }
234 bool IsItalic() const { return SlantStyle().Min().IsItalic(); }
235 bool IsOblique() const { return SlantStyle().Min().IsOblique(); }
236 bool IsUpright() const { return SlantStyle().Min().IsNormal(); }
237 inline bool SupportsItalic(); // defined below, because of RangeFlags use
238 inline bool SupportsBold();
239 inline bool MayUseSyntheticSlant();
240 bool IgnoreGDEF() const { return mIgnoreGDEF
; }
241 bool IgnoreGSUB() const { return mIgnoreGSUB
; }
243 // Return whether the face corresponds to "normal" CSS style properties:
244 // font-style: normal;
245 // font-weight: normal;
246 // font-stretch: normal;
247 // If this is false, we might want to fall back to a different face and
248 // possibly apply synthetic styling.
249 bool IsNormalStyle() const {
250 return IsUpright() && Weight().Min() <= FontWeight::NORMAL
&&
251 Weight().Max() >= FontWeight::NORMAL
&&
252 Stretch().Min() <= FontStretch::NORMAL
&&
253 Stretch().Max() >= FontStretch::NORMAL
;
256 // whether a feature is supported by the font (limited to a small set
257 // of features for which some form of fallback needs to be implemented)
258 virtual bool SupportsOpenTypeFeature(Script aScript
, uint32_t aFeatureTag
);
259 bool SupportsGraphiteFeature(uint32_t aFeatureTag
);
261 // returns a set containing all input glyph ids for a given feature
262 const hb_set_t
* InputsForOpenTypeFeature(Script aScript
,
263 uint32_t aFeatureTag
);
265 virtual bool HasFontTable(uint32_t aTableTag
);
267 inline bool HasGraphiteTables() {
268 LazyFlag flag
= mHasGraphiteTables
;
269 if (flag
== LazyFlag::Uninitialized
) {
270 flag
= CheckForGraphiteTables() ? LazyFlag::Yes
: LazyFlag::No
;
271 mHasGraphiteTables
= flag
;
273 return flag
== LazyFlag::Yes
;
276 inline bool HasCmapTable() {
277 if (!mCharacterMap
&& !mShmemCharacterMap
) {
279 NS_ASSERTION(mCharacterMap
|| mShmemCharacterMap
,
280 "failed to initialize character map");
282 return mHasCmapTable
;
285 inline bool HasCharacter(uint32_t ch
) {
286 if (mShmemCharacterMap
) {
287 return GetShmemCharacterMap()->test(ch
);
290 if (mShmemFace
&& TrySetShmemCharacterMap()) {
291 // Forget our temporary local copy, now we can use the shared cmap
292 auto* oldCmap
= mCharacterMap
.exchange(nullptr);
293 NS_IF_RELEASE(oldCmap
);
294 return GetShmemCharacterMap()->test(ch
);
296 if (GetCharacterMap()->test(ch
)) {
300 return TestCharacterMap(ch
);
303 virtual bool SkipDuringSystemFallback() { return false; }
304 void EnsureUVSMapInitialized();
305 uint16_t GetUVSGlyph(uint32_t aCh
, uint32_t aVS
);
307 // All concrete gfxFontEntry subclasses (except gfxUserFontEntry) need
308 // to override this, otherwise the font will never be used as it will
309 // be considered to support no characters.
310 // ReadCMAP() must *always* set the mCharacterMap pointer to a valid
311 // gfxCharacterMap, even if empty, as other code assumes this pointer
312 // can be safely dereferenced.
313 virtual nsresult
ReadCMAP(FontInfoData
* aFontInfoData
= nullptr);
315 bool TryGetSVGData(const gfxFont
* aFont
);
316 bool HasSVGGlyph(uint32_t aGlyphId
);
317 bool GetSVGGlyphExtents(DrawTarget
* aDrawTarget
, uint32_t aGlyphId
,
318 gfxFloat aSize
, gfxRect
* aResult
);
319 void RenderSVGGlyph(gfxContext
* aContext
, uint32_t aGlyphId
,
320 mozilla::SVGContextPaint
* aContextPaint
);
321 // Call this when glyph geometry or rendering has changed
322 // (e.g. animated SVG glyphs)
323 void NotifyGlyphsChanged();
325 bool TryGetColorGlyphs();
327 bool HasColorBitmapTable() {
328 LazyFlag flag
= mHasColorBitmapTable
;
329 if (flag
== LazyFlag::Uninitialized
) {
330 flag
= HasFontTable(TRUETYPE_TAG('C', 'B', 'D', 'T')) ||
331 HasFontTable(TRUETYPE_TAG('s', 'b', 'i', 'x'))
334 mHasColorBitmapTable
= flag
;
336 return flag
== LazyFlag::Yes
;
339 // Access to raw font table data (needed for Harfbuzz):
340 // returns a pointer to data owned by the fontEntry or the OS,
341 // which will remain valid until the blob is destroyed.
342 // The data MUST be treated as read-only; we may be getting a
343 // reference to a shared system font cache.
345 // The default implementation uses CopyFontTable to get the data
346 // into a byte array, and maintains a cache of loaded tables.
348 // Subclasses should override this if they can provide more efficient
349 // access than copying table data into our own buffers.
351 // Get blob that encapsulates a specific font table, or nullptr if
352 // the table doesn't exist in the font.
354 // Caller is responsible to call hb_blob_destroy() on the returned blob
355 // (if non-nullptr) when no longer required. For transient access to a
356 // table, use of AutoTable (below) is generally preferred.
357 virtual hb_blob_t
* GetFontTable(uint32_t aTag
);
359 // Stack-based utility to return a specified table, automatically releasing
360 // the blob when the AutoTable goes out of scope.
363 AutoTable(gfxFontEntry
* aFontEntry
, uint32_t aTag
) {
364 mBlob
= aFontEntry
->GetFontTable(aTag
);
366 ~AutoTable() { hb_blob_destroy(mBlob
); }
367 operator hb_blob_t
*() const { return mBlob
; }
372 AutoTable(const AutoTable
&) = delete;
373 AutoTable
& operator=(const AutoTable
&) = delete;
376 // Return a font instance for a particular style. This may be a newly-
377 // created instance, or a font already in the global cache.
378 // We can't return a UniquePtr here, because we may be returning a shared
379 // cached instance; but we also don't return already_AddRefed, because
380 // the caller may only need to use the font temporarily and doesn't need
381 // a strong reference.
382 already_AddRefed
<gfxFont
> FindOrMakeFont(
383 const gfxFontStyle
* aStyle
, gfxCharacterMap
* aUnicodeRangeMap
= nullptr);
385 // Get an existing font table cache entry in aBlob if it has been
386 // registered, or return false if not. Callers must call
387 // hb_blob_destroy on aBlob if true is returned.
389 // Note that some gfxFont implementations may not call this at all,
390 // if it is more efficient to get the table from the OS at that level.
391 bool GetExistingFontTable(uint32_t aTag
, hb_blob_t
** aBlob
);
393 // Elements of aTable are transferred (not copied) to and returned in a
394 // new hb_blob_t which is registered on the gfxFontEntry, but the initial
395 // reference is owned by the caller. Removing the last reference
396 // unregisters the table from the font entry.
398 // Pass nullptr for aBuffer to indicate that the table is not present and
399 // nullptr will be returned. Also returns nullptr on OOM.
400 hb_blob_t
* ShareFontTableAndGetBlob(uint32_t aTag
, nsTArray
<uint8_t>* aTable
);
402 // Get the font's unitsPerEm from the 'head' table, in the case of an
403 // sfnt resource. Will return kInvalidUPEM for non-sfnt fonts,
404 // if present on the platform.
405 uint16_t UnitsPerEm();
407 kMinUPEM
= 16, // Limits on valid unitsPerEm range, from the
408 kMaxUPEM
= 16384, // OpenType spec
409 kInvalidUPEM
= uint16_t(-1)
412 // Shaper face accessors:
413 // NOTE that harfbuzz and graphite handle ownership/lifetime of the face
414 // object in completely different ways.
416 // Create a HarfBuzz face corresponding to this font file.
417 // Our reference to the underlying hb_face_t will be released when the
418 // returned AutoHBFace goes out of scope, but the hb_face_t itself may
419 // be kept alive by other references (e.g. if an hb_font_t has been
420 // instantiated for it).
421 class MOZ_STACK_CLASS AutoHBFace
{
423 explicit AutoHBFace(hb_face_t
* aFace
) : mFace(aFace
) {}
424 ~AutoHBFace() { hb_face_destroy(mFace
); }
426 operator hb_face_t
*() const { return mFace
; }
428 // Not default-constructible, not copyable.
429 AutoHBFace() = delete;
430 AutoHBFace(const AutoHBFace
&) = delete;
431 AutoHBFace
& operator=(const AutoHBFace
&) = delete;
437 AutoHBFace
GetHBFace() {
438 return AutoHBFace(hb_face_create_for_tables(HBGetTable
, this, nullptr));
441 // Get the sandbox instance that graphite is running in.
442 rlbox_sandbox_gr
* GetGrSandbox();
444 // Register and get the callback handle for the glyph advance firefox callback
445 // Since the sandbox instance is shared with multiple test shapers, callback
446 // registration must be handled centrally to ensure multiple instances don't
447 // register the same callback.
448 sandbox_callback_gr
<float (*)(const void*, uint16_t)>*
449 GetGrSandboxAdvanceCallbackHandle();
451 // Get Graphite face corresponding to this font file.
452 // Caller must call gfxFontEntry::ReleaseGrFace when finished with it.
453 // Graphite is run in a sandbox
454 tainted_opaque_gr
<gr_face
*> GetGrFace();
455 void ReleaseGrFace(tainted_opaque_gr
<gr_face
*> aFace
);
457 // Does the font have graphite contextuals that involve the space glyph
458 // (and therefore we should bypass the word cache)?
459 // Since this function inspects data from libGraphite stored in sandbox memory
460 // it can only return a "hint" to the correct return value. This is because
461 // a compromised libGraphite could change the sandbox memory maliciously at
462 // any moment. The caller must ensure the calling code performs safe actions
463 // independent of the value returned, to unwrap this return.
464 tainted_boolean_hint
HasGraphiteSpaceContextuals();
466 // Release any SVG-glyphs document this font may have loaded.
467 void DisconnectSVG();
469 // Called to notify that aFont is being destroyed. Needed when we're tracking
470 // the fonts belonging to this font entry.
471 void NotifyFontDestroyed(gfxFont
* aFont
);
473 // For memory reporting of the platform font list.
474 virtual void AddSizeOfExcludingThis(mozilla::MallocSizeOf aMallocSizeOf
,
475 FontListSizes
* aSizes
) const;
476 virtual void AddSizeOfIncludingThis(mozilla::MallocSizeOf aMallocSizeOf
,
477 FontListSizes
* aSizes
) const;
479 // Used for reporting on individual font entries in the user font cache,
480 // which are not present in the platform font list.
481 size_t ComputedSizeOfExcludingThis(mozilla::MallocSizeOf aMallocSizeOf
) const;
483 // Used when checking for complex script support, to mask off cmap ranges
487 uint32_t numTags
; // number of entries in the tags[] array
488 hb_tag_t tags
[3]; // up to three OpenType script tags to check
491 bool SupportsScriptInGSUB(const hb_tag_t
* aScriptTags
, uint32_t aNumTags
);
494 * Font-variation query methods.
496 * Font backends that don't support variations should provide empty
499 virtual bool HasVariations() = 0;
501 virtual void GetVariationAxes(
502 nsTArray
<gfxFontVariationAxis
>& aVariationAxes
) = 0;
504 virtual void GetVariationInstances(
505 nsTArray
<gfxFontVariationInstance
>& aInstances
) = 0;
507 bool HasBoldVariableWeight();
508 bool HasItalicVariation();
509 bool HasSlantVariation();
510 bool HasOpticalSize();
512 void CheckForVariationAxes();
514 // Set up the entry's weight/stretch/style ranges according to axes found
515 // by GetVariationAxes (for installed fonts; do NOT call this for user
516 // fonts, where the ranges are provided by @font-face descriptors).
517 void SetupVariationRanges();
519 // Get variation axis settings that should be used to implement a particular
520 // font style using this resource.
521 void GetVariationsForStyle(nsTArray
<gfxFontVariation
>& aResult
,
522 const gfxFontStyle
& aStyle
);
524 // Get the font's list of features (if any) for DevTools support.
525 void GetFeatureInfo(nsTArray
<gfxFontFeatureInfo
>& aFeatureInfo
);
527 // This is only called on platforms where we use FreeType.
528 virtual FT_MM_Var
* GetMMVar() { return nullptr; }
530 // Return true if the font has a 'trak' table (and we can successfully
531 // interpret it), otherwise false. This will load and cache the table
532 // the first time it is called.
533 bool HasTrackingTable();
535 // Return the tracking (in font units) to be applied for the given size.
536 // (This is a floating-point number because of possible interpolation.)
537 gfxFloat
TrackingForCSSPx(gfxFloat aSize
) const;
539 mozilla::gfx::Rect
GetFontExtents(float aFUnitScaleFactor
) const {
540 // Flip the y-axis here to match the orientation of Gecko's coordinates.
541 return mozilla::gfx::Rect(float(mXMin
) * aFUnitScaleFactor
,
542 float(-mYMax
) * aFUnitScaleFactor
,
543 float(mXMax
- mXMin
) * aFUnitScaleFactor
,
544 float(mYMax
- mYMin
) * aFUnitScaleFactor
);
548 nsCString mFamilyName
;
550 // These are mutable so that we can take a read lock within a const method.
551 mutable mozilla::RWLock mLock
;
552 mutable mozilla::Mutex mFeatureInfoLock
;
554 mozilla::Atomic
<gfxCharacterMap
*> mCharacterMap
; // strong ref
555 gfxCharacterMap
* GetCharacterMap() const { return mCharacterMap
; }
557 mozilla::fontlist::Face
* mShmemFace
= nullptr;
558 const mozilla::fontlist::Family
* mShmemFamily
= nullptr;
560 mozilla::Atomic
<const SharedBitSet
*> mShmemCharacterMap
;
561 const SharedBitSet
* GetShmemCharacterMap() const {
562 return mShmemCharacterMap
;
565 mozilla::Atomic
<const uint8_t*> mUVSData
;
566 const uint8_t* GetUVSData() const { return mUVSData
; }
568 mozilla::UniquePtr
<gfxUserFontData
> mUserFontData
;
570 mozilla::Atomic
<gfxSVGGlyphs
*> mSVGGlyphs
;
571 gfxSVGGlyphs
* GetSVGGlyphs() const { return mSVGGlyphs
; }
573 // list of gfxFonts that are using SVG glyphs
574 nsTArray
<const gfxFont
*> mFontsUsingSVGGlyphs
MOZ_GUARDED_BY(mLock
);
575 nsTArray
<gfxFontFeature
> mFeatureSettings
;
576 nsTArray
<gfxFontVariation
> mVariationSettings
;
578 mozilla::UniquePtr
<nsTHashMap
<nsUint32HashKey
, bool>> mSupportedFeatures
579 MOZ_GUARDED_BY(mFeatureInfoLock
);
580 mozilla::UniquePtr
<nsTHashMap
<nsUint32HashKey
, hb_set_t
*>> mFeatureInputs
581 MOZ_GUARDED_BY(mFeatureInfoLock
);
583 // Color Layer font support. These tables are inert once loaded, so we don't
584 // need to hold a lock when reading them.
585 mozilla::Atomic
<hb_blob_t
*> mCOLR
;
586 mozilla::Atomic
<hb_blob_t
*> mCPAL
;
587 hb_blob_t
* GetCOLR() const { return mCOLR
; }
588 hb_blob_t
* GetCPAL() const { return mCPAL
; }
590 // bitvector of substitution space features per script, one each
591 // for default and non-default features
592 uint32_t mDefaultSubSpaceFeatures
[(int(Script::NUM_SCRIPT_CODES
) + 31) / 32];
594 mNonDefaultSubSpaceFeatures
[(int(Script::NUM_SCRIPT_CODES
) + 31) / 32];
596 mozilla::Atomic
<uint32_t> mUVSOffset
;
598 uint32_t mLanguageOverride
= NO_FONT_LANGUAGE_OVERRIDE
;
600 WeightRange mWeightRange
= WeightRange(FontWeight::FromInt(500));
601 StretchRange mStretchRange
= StretchRange(FontStretch::NORMAL
);
602 SlantStyleRange mStyleRange
= SlantStyleRange(FontSlantStyle::NORMAL
);
604 // Font metrics overrides (as multiples of used font size); negative values
605 // indicate no override to be applied.
606 float mAscentOverride
= -1.0;
607 float mDescentOverride
= -1.0;
608 float mLineGapOverride
= -1.0;
610 // Scaling factor to be applied to the font size.
611 float mSizeAdjust
= 1.0;
613 // For user fonts (only), we need to record whether or not weight/stretch/
614 // slant variations should be clamped to the range specified in the entry
615 // properties. When the @font-face rule omitted one or more of these
616 // descriptors, it is treated as the initial value for font-matching (and
617 // so that is what we record in the font entry), but when rendering the
618 // range is NOT clamped.
619 enum class RangeFlags
: uint16_t {
621 eAutoWeight
= (1 << 0),
622 eAutoStretch
= (1 << 1),
623 eAutoSlantStyle
= (1 << 2),
625 // Flag to record whether the face has a variable "wght" axis
626 // that supports "bold" values, used to disable the application
627 // of synthetic-bold effects.
628 eBoldVariableWeight
= (1 << 3),
629 // Whether the face has an 'ital' axis.
630 eItalicVariation
= (1 << 4),
631 // Whether the face has a 'slnt' axis.
632 eSlantVariation
= (1 << 5),
634 // Flags to record if the face uses a non-CSS-compatible scale
635 // for weight and/or stretch, in which case we won't map the
636 // properties to the variation axes (though they can still be
637 // explicitly set using font-variation-settings).
638 eNonCSSWeight
= (1 << 6),
639 eNonCSSStretch
= (1 << 7),
641 // Whether the font has an 'opsz' axis.
642 eOpticalSize
= (1 << 8)
644 RangeFlags mRangeFlags
= RangeFlags::eNoFlags
;
646 bool mFixedPitch
: 1;
647 bool mIsBadUnderlineFont
: 1;
648 bool mIsUserFontContainer
: 1; // userfont entry
649 bool mIsDataUserFont
: 1; // platform font entry (data)
650 bool mIsLocalUserFont
: 1; // platform font entry (local)
651 bool mStandardFace
: 1;
652 bool mIgnoreGDEF
: 1;
653 bool mIgnoreGSUB
: 1;
654 bool mSkipDefaultFeatureSpaceCheck
: 1;
656 mozilla::Atomic
<bool> mSVGInitialized
;
657 mozilla::Atomic
<bool> mHasCmapTable
;
658 mozilla::Atomic
<bool> mGrFaceInitialized
;
659 mozilla::Atomic
<bool> mCheckedForColorGlyph
;
660 mozilla::Atomic
<bool> mCheckedForVariationAxes
;
662 // Atomic flags that are lazily evaluated - initially set to UNINITIALIZED,
663 // changed to NO or YES once we determine the actual value.
664 enum class LazyFlag
: uint8_t { Uninitialized
= 0xff, No
= 0, Yes
= 1 };
666 std::atomic
<LazyFlag
> mSpaceGlyphIsInvisible
;
667 std::atomic
<LazyFlag
> mHasGraphiteTables
;
668 std::atomic
<LazyFlag
> mHasGraphiteSpaceContextuals
;
669 std::atomic
<LazyFlag
> mHasColorBitmapTable
;
671 enum class SpaceFeatures
: uint8_t {
672 Uninitialized
= 0xff,
674 HasFeatures
= 1 << 0,
679 std::atomic
<SpaceFeatures
> mHasSpaceFeatures
;
682 friend class gfxPlatformFontList
;
683 friend class gfxFontFamily
;
684 friend class gfxUserFontEntry
;
686 // Protected destructor, to discourage deletion outside of Release():
687 virtual ~gfxFontEntry();
689 virtual gfxFont
* CreateFontInstance(const gfxFontStyle
* aFontStyle
) = 0;
691 inline bool CheckForGraphiteTables() {
692 return HasFontTable(TRUETYPE_TAG('S', 'i', 'l', 'f'));
695 // Copy a font table into aBuffer.
696 // The caller will be responsible for ownership of the data.
697 virtual nsresult
CopyFontTable(uint32_t aTableTag
,
698 nsTArray
<uint8_t>& aBuffer
) {
699 MOZ_ASSERT_UNREACHABLE(
700 "forgot to override either GetFontTable or "
702 return NS_ERROR_FAILURE
;
705 // Helper for HasTrackingTable; check/parse the table and cache pointers
706 // to the subtables we need. Returns false on failure, in which case the
707 // table is unusable.
708 bool ParseTrakTable() MOZ_REQUIRES(mLock
);
710 // lookup the cmap in cached font data
711 virtual already_AddRefed
<gfxCharacterMap
> GetCMAPFromFontInfo(
712 FontInfoData
* aFontInfoData
, uint32_t& aUVSOffset
);
714 // helper for HasCharacter(), which is what client code should call
715 virtual bool TestCharacterMap(uint32_t aCh
);
717 // Try to set mShmemCharacterMap, based on the char map in mShmemFace;
718 // return true if successful, false if it remains null (maybe the parent
719 // hasn't handled our SetCharacterMap message yet).
720 bool TrySetShmemCharacterMap();
722 // Helper for gfxPlatformFontList::CreateFontEntry methods: set properties
723 // of the gfxFontEntry based on shared Face and Family records.
724 void InitializeFrom(mozilla::fontlist::Face
* aFace
,
725 const mozilla::fontlist::Family
* aFamily
);
727 // Shaper-specific face objects, shared by all instantiations of the same
728 // physical font, regardless of size.
729 // Usually, only one of these will actually be created for any given font
730 // entry, depending on the font tables that are present.
732 // hb_face_t is refcounted internally, so each shaper that's using it will
733 // bump the ref count when it acquires the face, and "destroy" (release) it
734 // in its destructor. The font entry has only this non-owning reference to
735 // the face; when the face is deleted, it will tell the font entry to forget
736 // it, so that a new face will be created next time it is needed.
737 mozilla::Atomic
<hb_face_t
*> mHBFace
;
739 static hb_blob_t
* HBGetTable(hb_face_t
* face
, uint32_t aTag
, void* aUserData
);
741 // Callback that the hb_face will use to tell us when it is being deleted.
742 static void HBFaceDeletedCallback(void* aUserData
);
744 // All libGraphite functionality is sandboxed in an rlbox sandbox. This
745 // contains data for the sandbox instance.
746 // Currently graphite shaping is only supported on the main thread.
747 struct GrSandboxData
;
748 GrSandboxData
* mSandboxData
= nullptr;
750 // gr_face is -not- refcounted, so it will be owned directly by the font
751 // entry, and we'll keep a count of how many references we've handed out;
752 // each shaper is responsible to call ReleaseGrFace on its entry when
753 // finished with it, so that we know when it can be deleted.
754 tainted_opaque_gr
<gr_face
*> mGrFace
;
756 // For AAT font, a strong reference to the 'trak' table (if present).
757 hb_blob_t
* const kTrakTableUninitialized
= (hb_blob_t
*)(intptr_t(-1));
758 mozilla::Atomic
<hb_blob_t
*> mTrakTable
;
759 hb_blob_t
* GetTrakTable() const { return mTrakTable
; }
760 bool TrakTableInitialized() const {
761 return mTrakTable
!= kTrakTableUninitialized
;
764 // Cached pointers to tables within 'trak', initialized by ParseTrakTable.
765 // This data is inert once loaded, so locking is not required to read it.
766 const mozilla::AutoSwap_PRInt16
* mTrakValues
= nullptr;
767 const mozilla::AutoSwap_PRInt32
* mTrakSizeTable
= nullptr;
769 // number of current users of this entry's mGrFace
770 nsrefcnt mGrFaceRefCnt
= 0;
772 friend class gfxFontEntryCallbacks
;
774 // For memory reporting: size of user-font data belonging to this entry.
775 // We record this in the font entry because the actual data block may be
776 // handed over to platform APIs, so that it would become difficult (and
777 // platform-specific) to measure it directly at report-gathering time.
778 uint32_t mComputedSizeOfUserFont
= 0;
780 // Font's unitsPerEm from the 'head' table, if available (will be set to
781 // kInvalidUPEM for non-sfnt font formats)
782 uint16_t mUnitsPerEm
= 0;
784 uint16_t mNumTrakSizes
= 0;
786 // Font extents in FUnits. (To be set from the 'head' table; default to
787 // "huge" to avoid any clipping if real extents not available.)
788 int16_t mXMin
= std::numeric_limits
<int16_t>::min();
789 int16_t mYMin
= std::numeric_limits
<int16_t>::min();
790 int16_t mXMax
= std::numeric_limits
<int16_t>::max();
791 int16_t mYMax
= std::numeric_limits
<int16_t>::max();
795 * Font table hashtable, to support GetFontTable for harfbuzz.
797 * The harfbuzz shaper (and potentially other clients) needs access to raw
798 * font table data. This needs to be cached so that it can be used
799 * repeatedly (each time we construct a text run; in some cases, for
800 * each character/glyph within the run) without re-fetching large tables
803 * Because we may instantiate many gfxFonts for the same physical font
804 * file (at different sizes), we should ensure that they can share a
805 * single cached copy of the font tables. To do this, we implement table
806 * access and sharing on the fontEntry rather than the font itself.
808 * The default implementation uses GetFontTable() to read font table
809 * data into byte arrays, and wraps them in blobs which are registered in
810 * a hashtable. The hashtable can then return pre-existing blobs to
813 * Harfbuzz will "destroy" the blobs when it is finished with them. When
814 * the last blob reference is removed, the FontTableBlobData user data
815 * will remove the blob from the hashtable if still registered.
818 class FontTableBlobData
;
821 * FontTableHashEntry manages the entries of hb_blob_t's containing font
824 * This is used to share font tables across fonts with the same
825 * font entry (but different sizes) for use by HarfBuzz. The hashtable
826 * does not own a strong reference to the blob, but keeps a weak pointer,
827 * managed by FontTableBlobData. Similarly FontTableBlobData keeps only a
828 * weak pointer to the hashtable, managed by FontTableHashEntry.
831 class FontTableHashEntry
: public nsUint32HashKey
{
833 // Declarations for nsTHashtable
835 typedef nsUint32HashKey KeyClass
;
836 typedef KeyClass::KeyType KeyType
;
837 typedef KeyClass::KeyTypePointer KeyTypePointer
;
839 explicit FontTableHashEntry(KeyTypePointer aTag
)
840 : KeyClass(aTag
), mSharedBlobData(nullptr), mBlob(nullptr) {}
842 // NOTE: This assumes the new entry belongs to the same hashtable as
843 // the old, because the mHashtable pointer in mSharedBlobData (if
844 // present) will not be updated.
845 FontTableHashEntry(FontTableHashEntry
&& toMove
)
846 : KeyClass(std::move(toMove
)),
847 mSharedBlobData(std::move(toMove
.mSharedBlobData
)),
848 mBlob(std::move(toMove
.mBlob
)) {
849 toMove
.mSharedBlobData
= nullptr;
850 toMove
.mBlob
= nullptr;
853 ~FontTableHashEntry() { Clear(); }
855 // FontTable/Blob API
857 // Transfer (not copy) elements of aTable to a new hb_blob_t and
858 // return ownership to the caller. A weak reference to the blob is
859 // recorded in the hashtable entry so that others may use the same
861 hb_blob_t
* ShareTableAndGetBlob(
862 nsTArray
<uint8_t>&& aTable
,
863 nsTHashtable
<FontTableHashEntry
>* aHashtable
);
865 // Return a strong reference to the blob.
866 // Callers must hb_blob_destroy the returned blob.
867 hb_blob_t
* GetBlob() const;
871 size_t SizeOfExcludingThis(mozilla::MallocSizeOf aMallocSizeOf
) const;
874 static void DeleteFontTableBlobData(void* aBlobData
);
876 FontTableHashEntry
& operator=(FontTableHashEntry
& toCopy
);
878 FontTableBlobData
* mSharedBlobData
;
882 using FontTableCache
= nsTHashtable
<FontTableHashEntry
>;
883 mozilla::Atomic
<FontTableCache
*> mFontTableCache
;
884 FontTableCache
* GetFontTableCache() const { return mFontTableCache
; }
887 MOZ_MAKE_ENUM_CLASS_BITWISE_OPERATORS(gfxFontEntry::RangeFlags
)
888 MOZ_MAKE_ENUM_CLASS_BITWISE_OPERATORS(gfxFontEntry::SpaceFeatures
)
890 inline bool gfxFontEntry::SupportsItalic() {
891 return SlantStyle().Max().IsItalic() ||
892 ((mRangeFlags
& RangeFlags::eAutoSlantStyle
) ==
893 RangeFlags::eAutoSlantStyle
&&
894 HasItalicVariation());
897 inline bool gfxFontEntry::SupportsBold() {
898 // bold == weights 600 and above
899 // We return true if the face has a max weight descriptor >= 600,
900 // OR if it's a user font with auto-weight (no descriptor) and has
901 // a weight axis that supports values >= 600
902 return Weight().Max().IsBold() ||
903 ((mRangeFlags
& RangeFlags::eAutoWeight
) == RangeFlags::eAutoWeight
&&
904 HasBoldVariableWeight());
907 inline bool gfxFontEntry::MayUseSyntheticSlant() {
909 return false; // The resource is already non-upright.
911 if (HasSlantVariation()) {
912 if (mRangeFlags
& RangeFlags::eAutoSlantStyle
) {
915 if (!SlantStyle().IsSingle()) {
916 return false; // The resource has a 'slnt' axis, and has not been
917 // clamped to just its upright setting.
923 // used when iterating over all fonts looking for a match for a given character
924 struct GlobalFontMatch
{
925 GlobalFontMatch(uint32_t aCharacter
, uint32_t aNextCh
,
926 const gfxFontStyle
& aStyle
, eFontPresentation aPresentation
)
930 mPresentation(aPresentation
) {}
932 RefPtr
<gfxFontEntry
> mBestMatch
; // current best match
933 RefPtr
<gfxFontFamily
> mMatchedFamily
; // the family it belongs to
934 mozilla::fontlist::Family
* mMatchedSharedFamily
= nullptr;
935 const gfxFontStyle
& mStyle
; // style to match
936 const uint32_t mCh
; // codepoint to be matched
937 const uint32_t mNextCh
; // following codepoint (or zero)
938 eFontPresentation mPresentation
;
939 uint32_t mCount
= 0; // number of fonts matched
940 uint32_t mCmapsTested
= 0; // number of cmaps tested
941 double mMatchDistance
= INFINITY
; // metric indicating closest match
944 class gfxFontFamily
{
947 NS_INLINE_DECL_THREADSAFE_REFCOUNTING(gfxFontFamily
)
949 gfxFontFamily(const nsACString
& aName
, FontVisibility aVisibility
)
951 mLock("gfxFontFamily lock"),
952 mVisibility(aVisibility
),
953 mIsSimpleFamily(false),
954 mIsBadUnderlineFamily(false),
955 mSkipDefaultFeatureSpaceCheck(false),
956 mCheckForFallbackFaces(false) {}
958 const nsCString
& Name() const { return mName
; }
960 virtual void LocalizedName(nsACString
& aLocalizedName
);
961 virtual bool HasOtherFamilyNames();
963 // See https://bugzilla.mozilla.org/show_bug.cgi?id=835204:
964 // check the font's 'name' table to see if it has a legacy family name
965 // that would have been used by GDI (e.g. to split extra-bold or light
966 // faces in a large family into separate "styled families" because of
967 // GDI's 4-faces-per-family limitation). If found, the styled family
968 // name will be added to the font list's "other family names" table.
969 // Note that the caller must already hold the gfxPlatformFontList lock.
970 bool CheckForLegacyFamilyNames(gfxPlatformFontList
* aFontList
);
972 // Callers must hold a read-lock for as long as they're using the list.
973 const nsTArray
<RefPtr
<gfxFontEntry
>>& GetFontList()
974 MOZ_REQUIRES_SHARED(mLock
) {
975 return mAvailableFonts
;
977 void ReadLock() MOZ_ACQUIRE_SHARED(mLock
) { mLock
.ReadLock(); }
978 void ReadUnlock() MOZ_RELEASE_SHARED(mLock
) { mLock
.ReadUnlock(); }
980 uint32_t FontListLength() const {
981 mozilla::AutoReadLock
lock(mLock
);
982 return mAvailableFonts
.Length();
985 void AddFontEntry(RefPtr
<gfxFontEntry
> aFontEntry
) {
986 mozilla::AutoWriteLock
lock(mLock
);
987 AddFontEntryLocked(aFontEntry
);
990 void AddFontEntryLocked(RefPtr
<gfxFontEntry
> aFontEntry
) MOZ_REQUIRES(mLock
) {
991 // Avoid potentially duplicating entries.
992 if (mAvailableFonts
.Contains(aFontEntry
)) {
995 // bug 589682 - set the IgnoreGDEF flag on entries for Italic faces
996 // of Times New Roman, because of buggy table in those fonts
997 if (aFontEntry
->IsItalic() && !aFontEntry
->IsUserFont() &&
998 Name().EqualsLiteral("Times New Roman")) {
999 aFontEntry
->mIgnoreGDEF
= true;
1001 if (aFontEntry
->mFamilyName
.IsEmpty()) {
1002 aFontEntry
->mFamilyName
= Name();
1004 MOZ_ASSERT(aFontEntry
->mFamilyName
.Equals(Name()));
1006 aFontEntry
->mSkipDefaultFeatureSpaceCheck
= mSkipDefaultFeatureSpaceCheck
;
1007 mAvailableFonts
.AppendElement(aFontEntry
);
1009 // If we're adding a face to a family that has been marked as "simple",
1010 // we need to ensure any null entries are removed, as well as clearing
1011 // the flag (which may be set again later).
1012 if (mIsSimpleFamily
) {
1013 mAvailableFonts
.RemoveElementsBy([](const auto& font
) { return !font
; });
1014 mIsSimpleFamily
= false;
1018 // note that the styles for this family have been added
1019 bool HasStyles() const { return mHasStyles
; }
1020 void SetHasStyles(bool aHasStyles
) { mHasStyles
= aHasStyles
; }
1022 void SetCheckedForLegacyFamilyNames(bool aChecked
) {
1023 mCheckedForLegacyFamilyNames
= aChecked
;
1026 // choose a specific face to match a style using CSS font matching
1027 // rules (weight matching occurs here). may return a face that doesn't
1028 // precisely match (e.g. normal face when no italic face exists).
1029 gfxFontEntry
* FindFontForStyle(const gfxFontStyle
& aFontStyle
,
1030 bool aIgnoreSizeTolerance
= false);
1032 virtual void FindAllFontsForStyle(const gfxFontStyle
& aFontStyle
,
1033 nsTArray
<gfxFontEntry
*>& aFontEntryList
,
1034 bool aIgnoreSizeTolerance
= false);
1036 // Checks for a matching font within the family; used as part of the font
1037 // fallback process.
1038 // Note that when this is called, the caller must already be holding the
1039 // gfxPlatformFontList lock.
1040 void FindFontForChar(GlobalFontMatch
* aMatchData
);
1042 // checks all fonts for a matching font within the family
1043 void SearchAllFontsForChar(GlobalFontMatch
* aMatchData
);
1045 // read in other family names, if any, and use functor to add each into cache
1046 virtual void ReadOtherFamilyNames(gfxPlatformFontList
* aPlatformFontList
);
1048 // set when other family names have been read in
1049 void SetOtherFamilyNamesInitialized() { mOtherFamilyNamesInitialized
= true; }
1051 // Read in other localized family names, fullnames and Postscript names
1052 // for all faces and append to lookup tables.
1053 // Note that when this is called, the caller must already be holding the
1054 // gfxPlatformFontList lock.
1055 virtual void ReadFaceNames(gfxPlatformFontList
* aPlatformFontList
,
1056 bool aNeedFullnamePostscriptNames
,
1057 FontInfoData
* aFontInfoData
= nullptr);
1059 // Find faces belonging to this family (platform implementations override).
1060 // This is a no-op in cases where the family is explicitly populated by other
1061 // means, rather than being asked to find its faces via system API.
1062 virtual void FindStyleVariationsLocked(FontInfoData
* aFontInfoData
= nullptr)
1063 MOZ_REQUIRES(mLock
){};
1064 void FindStyleVariations(FontInfoData
* aFontInfoData
= nullptr) {
1068 mozilla::AutoWriteLock
lock(mLock
);
1069 FindStyleVariationsLocked(aFontInfoData
);
1072 // search for a specific face using the Postscript name
1073 gfxFontEntry
* FindFont(const nsACString
& aFontName
,
1074 const nsCStringComparator
& aCmp
) const;
1076 // Read in cmaps for all the faces.
1077 // Note that when this is called, the caller must already be holding the
1078 // gfxPlatformFontList lock.
1079 void ReadAllCMAPs(FontInfoData
* aFontInfoData
= nullptr);
1081 bool TestCharacterMap(uint32_t aCh
) {
1082 if (!mFamilyCharacterMapInitialized
) {
1085 mozilla::AutoReadLock
lock(mLock
);
1086 return mFamilyCharacterMap
.test(aCh
);
1089 void ResetCharacterMap() MOZ_REQUIRES(mLock
) {
1090 mFamilyCharacterMap
.reset();
1091 mFamilyCharacterMapInitialized
= false;
1094 // mark this family as being in the "bad" underline offset blocklist
1095 void SetBadUnderlineFamily() {
1096 mozilla::AutoWriteLock
lock(mLock
);
1097 mIsBadUnderlineFamily
= true;
1099 SetBadUnderlineFonts();
1103 virtual bool IsSingleFaceFamily() const { return false; }
1105 bool IsBadUnderlineFamily() const { return mIsBadUnderlineFamily
; }
1106 bool CheckForFallbackFaces() const { return mCheckForFallbackFaces
; }
1108 // sort available fonts to put preferred (standard) faces towards the end
1109 void SortAvailableFonts() MOZ_REQUIRES(mLock
);
1111 // check whether the family fits into the simple 4-face model,
1112 // so we can use simplified style-matching;
1113 // if so set the mIsSimpleFamily flag (defaults to False before we've checked)
1114 void CheckForSimpleFamily() MOZ_REQUIRES(mLock
);
1116 // For memory reporter
1117 virtual void AddSizeOfExcludingThis(mozilla::MallocSizeOf aMallocSizeOf
,
1118 FontListSizes
* aSizes
) const;
1119 virtual void AddSizeOfIncludingThis(mozilla::MallocSizeOf aMallocSizeOf
,
1120 FontListSizes
* aSizes
) const;
1123 // Only used for debugging checks - does a linear search
1124 bool ContainsFace(gfxFontEntry
* aFontEntry
);
1127 void SetSkipSpaceFeatureCheck(bool aSkipCheck
) {
1128 mSkipDefaultFeatureSpaceCheck
= aSkipCheck
;
1131 // Check whether this family is appropriate to include in the Preferences
1132 // font list for the given langGroup and CSS generic, if the platform lets
1133 // us determine this.
1134 // Return true if the family should be included in the list, false to omit.
1135 // Default implementation returns true for everything, so no filtering
1136 // will occur; individual platforms may override.
1137 virtual bool FilterForFontList(nsAtom
* aLangGroup
,
1138 const nsACString
& aGeneric
) const {
1142 FontVisibility
Visibility() const { return mVisibility
; }
1143 bool IsHidden() const { return Visibility() == FontVisibility::Hidden
; }
1144 bool IsWebFontFamily() const {
1145 return Visibility() == FontVisibility::Webfont
;
1149 // Protected destructor, to discourage deletion outside of Release():
1150 virtual ~gfxFontFamily();
1152 bool ReadOtherFamilyNamesForFace(gfxPlatformFontList
* aPlatformFontList
,
1153 hb_blob_t
* aNameTable
,
1154 bool useFullName
= false);
1156 // set whether this font family is in "bad" underline offset blocklist.
1157 void SetBadUnderlineFonts() MOZ_REQUIRES(mLock
) {
1158 for (auto& f
: mAvailableFonts
) {
1160 f
->mIsBadUnderlineFont
= true;
1166 nsTArray
<RefPtr
<gfxFontEntry
>> mAvailableFonts
MOZ_GUARDED_BY(mLock
);
1167 gfxSparseBitSet mFamilyCharacterMap
MOZ_GUARDED_BY(mLock
);
1169 mutable mozilla::RWLock mLock
;
1171 FontVisibility mVisibility
;
1173 mozilla::Atomic
<bool> mOtherFamilyNamesInitialized
;
1174 mozilla::Atomic
<bool> mFaceNamesInitialized
;
1175 mozilla::Atomic
<bool> mHasStyles
;
1176 mozilla::Atomic
<bool> mFamilyCharacterMapInitialized
;
1177 mozilla::Atomic
<bool> mCheckedForLegacyFamilyNames
;
1178 mozilla::Atomic
<bool> mHasOtherFamilyNames
;
1180 bool mIsSimpleFamily
: 1 MOZ_GUARDED_BY(mLock
);
1181 bool mIsBadUnderlineFamily
: 1;
1182 bool mSkipDefaultFeatureSpaceCheck
: 1;
1183 bool mCheckForFallbackFaces
: 1; // check other faces for character
1186 // for "simple" families, the faces are stored in mAvailableFonts
1187 // with fixed positions:
1188 kRegularFaceIndex
= 0,
1190 kItalicFaceIndex
= 2,
1191 kBoldItalicFaceIndex
= 3,
1192 // mask values for selecting face with bold and/or italic attributes
1198 // Wrapper for either a raw pointer to a mozilla::fontlist::Family in the shared
1199 // font list or a strong pointer to an unshared gfxFontFamily that belongs just
1200 // to the current process.
1202 FontFamily() = default;
1203 FontFamily(const FontFamily
& aOther
) = default;
1205 explicit FontFamily(RefPtr
<gfxFontFamily
>&& aFamily
)
1206 : mUnshared(std::move(aFamily
)) {}
1208 explicit FontFamily(gfxFontFamily
* aFamily
) : mUnshared(aFamily
) {}
1210 explicit FontFamily(mozilla::fontlist::Family
* aFamily
) : mShared(aFamily
) {}
1212 bool operator==(const FontFamily
& aOther
) const {
1213 return mShared
== aOther
.mShared
&& mUnshared
== aOther
.mUnshared
;
1216 bool IsNull() const { return !mShared
&& !mUnshared
; }
1218 RefPtr
<gfxFontFamily
> mUnshared
;
1219 mozilla::fontlist::Family
* mShared
= nullptr;
1222 // Struct used in the gfxFontGroup font list to keep track of a font family
1223 // together with the CSS generic (if any) that was mapped to it in this
1224 // particular case (so it can be reported to the DevTools font inspector).
1225 struct FamilyAndGeneric final
{
1226 FamilyAndGeneric() : mGeneric(mozilla::StyleGenericFontFamily(0)) {}
1227 FamilyAndGeneric(const FamilyAndGeneric
& aOther
) = default;
1228 explicit FamilyAndGeneric(gfxFontFamily
* aFamily
,
1229 mozilla::StyleGenericFontFamily aGeneric
=
1230 mozilla::StyleGenericFontFamily(0))
1231 : mFamily(aFamily
), mGeneric(aGeneric
) {}
1232 explicit FamilyAndGeneric(RefPtr
<gfxFontFamily
>&& aFamily
,
1233 mozilla::StyleGenericFontFamily aGeneric
=
1234 mozilla::StyleGenericFontFamily(0))
1235 : mFamily(std::move(aFamily
)), mGeneric(aGeneric
) {}
1236 explicit FamilyAndGeneric(mozilla::fontlist::Family
* aFamily
,
1237 mozilla::StyleGenericFontFamily aGeneric
=
1238 mozilla::StyleGenericFontFamily(0))
1239 : mFamily(aFamily
), mGeneric(aGeneric
) {}
1240 explicit FamilyAndGeneric(const FontFamily
& aFamily
,
1241 mozilla::StyleGenericFontFamily aGeneric
=
1242 mozilla::StyleGenericFontFamily(0))
1243 : mFamily(aFamily
), mGeneric(aGeneric
) {}
1245 bool operator==(const FamilyAndGeneric
& aOther
) const {
1246 return mFamily
== aOther
.mFamily
&& mGeneric
== aOther
.mGeneric
;
1250 mozilla::StyleGenericFontFamily mGeneric
;