summaryrefslogtreecommitdiffstats
path: root/src/3rdparty/harfbuzz-ng/src/hb-ot-layout-common-private.hh
diff options
context:
space:
mode:
Diffstat (limited to 'src/3rdparty/harfbuzz-ng/src/hb-ot-layout-common-private.hh')
-rw-r--r--src/3rdparty/harfbuzz-ng/src/hb-ot-layout-common-private.hh1772
1 files changed, 0 insertions, 1772 deletions
diff --git a/src/3rdparty/harfbuzz-ng/src/hb-ot-layout-common-private.hh b/src/3rdparty/harfbuzz-ng/src/hb-ot-layout-common-private.hh
deleted file mode 100644
index 5e699e1967..0000000000
--- a/src/3rdparty/harfbuzz-ng/src/hb-ot-layout-common-private.hh
+++ /dev/null
@@ -1,1772 +0,0 @@
-/*
- * Copyright © 2007,2008,2009 Red Hat, Inc.
- * Copyright © 2010,2012 Google, Inc.
- *
- * This is part of HarfBuzz, a text shaping library.
- *
- * Permission is hereby granted, without written agreement and without
- * license or royalty fees, to use, copy, modify, and distribute this
- * software and its documentation for any purpose, provided that the
- * above copyright notice and the following two paragraphs appear in
- * all copies of this software.
- *
- * IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE TO ANY PARTY FOR
- * DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES
- * ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN
- * IF THE COPYRIGHT HOLDER HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
- * DAMAGE.
- *
- * THE COPYRIGHT HOLDER SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING,
- * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
- * FITNESS FOR A PARTICULAR PURPOSE. THE SOFTWARE PROVIDED HEREUNDER IS
- * ON AN "AS IS" BASIS, AND THE COPYRIGHT HOLDER HAS NO OBLIGATION TO
- * PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
- *
- * Red Hat Author(s): Behdad Esfahbod
- * Google Author(s): Behdad Esfahbod
- */
-
-#ifndef HB_OT_LAYOUT_COMMON_PRIVATE_HH
-#define HB_OT_LAYOUT_COMMON_PRIVATE_HH
-
-#include "hb-private.hh"
-#include "hb-debug.hh"
-#include "hb-ot-layout-private.hh"
-#include "hb-open-type-private.hh"
-#include "hb-set-private.hh"
-
-
-#ifndef HB_MAX_NESTING_LEVEL
-#define HB_MAX_NESTING_LEVEL 6
-#endif
-#ifndef HB_MAX_CONTEXT_LENGTH
-#define HB_MAX_CONTEXT_LENGTH 64
-#endif
-
-
-namespace OT {
-
-
-#define NOT_COVERED ((unsigned int) -1)
-
-
-
-/*
- *
- * OpenType Layout Common Table Formats
- *
- */
-
-
-/*
- * Script, ScriptList, LangSys, Feature, FeatureList, Lookup, LookupList
- */
-
-template <typename Type>
-struct Record
-{
- inline int cmp (hb_tag_t a) const {
- return tag.cmp (a);
- }
-
- struct sanitize_closure_t {
- hb_tag_t tag;
- const void *list_base;
- };
- inline bool sanitize (hb_sanitize_context_t *c, const void *base) const
- {
- TRACE_SANITIZE (this);
- const sanitize_closure_t closure = {tag, base};
- return_trace (c->check_struct (this) && offset.sanitize (c, base, &closure));
- }
-
- Tag tag; /* 4-byte Tag identifier */
- OffsetTo<Type>
- offset; /* Offset from beginning of object holding
- * the Record */
- public:
- DEFINE_SIZE_STATIC (6);
-};
-
-template <typename Type>
-struct RecordArrayOf : SortedArrayOf<Record<Type> > {
- inline const Tag& get_tag (unsigned int i) const
- {
- /* We cheat slightly and don't define separate Null objects
- * for Record types. Instead, we return the correct Null(Tag)
- * here. */
- if (unlikely (i >= this->len)) return Null(Tag);
- return (*this)[i].tag;
- }
- inline unsigned int get_tags (unsigned int start_offset,
- unsigned int *record_count /* IN/OUT */,
- hb_tag_t *record_tags /* OUT */) const
- {
- if (record_count) {
- const Record<Type> *arr = this->sub_array (start_offset, record_count);
- unsigned int count = *record_count;
- for (unsigned int i = 0; i < count; i++)
- record_tags[i] = arr[i].tag;
- }
- return this->len;
- }
- inline bool find_index (hb_tag_t tag, unsigned int *index) const
- {
- /* If we want to allow non-sorted data, we can lsearch(). */
- int i = this->/*lsearch*/bsearch (tag);
- if (i != -1) {
- if (index) *index = i;
- return true;
- } else {
- if (index) *index = Index::NOT_FOUND_INDEX;
- return false;
- }
- }
-};
-
-template <typename Type>
-struct RecordListOf : RecordArrayOf<Type>
-{
- inline const Type& operator [] (unsigned int i) const
- { return this+RecordArrayOf<Type>::operator [](i).offset; }
-
- inline bool sanitize (hb_sanitize_context_t *c) const
- {
- TRACE_SANITIZE (this);
- return_trace (RecordArrayOf<Type>::sanitize (c, this));
- }
-};
-
-
-struct RangeRecord
-{
- inline int cmp (hb_codepoint_t g) const {
- return g < start ? -1 : g <= end ? 0 : +1 ;
- }
-
- inline bool sanitize (hb_sanitize_context_t *c) const
- {
- TRACE_SANITIZE (this);
- return_trace (c->check_struct (this));
- }
-
- inline bool intersects (const hb_set_t *glyphs) const {
- return glyphs->intersects (start, end);
- }
-
- template <typename set_t>
- inline bool add_coverage (set_t *glyphs) const {
- return glyphs->add_range (start, end);
- }
-
- GlyphID start; /* First GlyphID in the range */
- GlyphID end; /* Last GlyphID in the range */
- UINT16 value; /* Value */
- public:
- DEFINE_SIZE_STATIC (6);
-};
-DEFINE_NULL_DATA (RangeRecord, "\000\001");
-
-
-struct IndexArray : ArrayOf<Index>
-{
- inline unsigned int get_indexes (unsigned int start_offset,
- unsigned int *_count /* IN/OUT */,
- unsigned int *_indexes /* OUT */) const
- {
- if (_count) {
- const UINT16 *arr = this->sub_array (start_offset, _count);
- unsigned int count = *_count;
- for (unsigned int i = 0; i < count; i++)
- _indexes[i] = arr[i];
- }
- return this->len;
- }
-};
-
-
-struct Script;
-struct LangSys;
-struct Feature;
-
-
-struct LangSys
-{
- inline unsigned int get_feature_count (void) const
- { return featureIndex.len; }
- inline hb_tag_t get_feature_index (unsigned int i) const
- { return featureIndex[i]; }
- inline unsigned int get_feature_indexes (unsigned int start_offset,
- unsigned int *feature_count /* IN/OUT */,
- unsigned int *feature_indexes /* OUT */) const
- { return featureIndex.get_indexes (start_offset, feature_count, feature_indexes); }
-
- inline bool has_required_feature (void) const { return reqFeatureIndex != 0xFFFFu; }
- inline unsigned int get_required_feature_index (void) const
- {
- if (reqFeatureIndex == 0xFFFFu)
- return Index::NOT_FOUND_INDEX;
- return reqFeatureIndex;;
- }
-
- inline bool sanitize (hb_sanitize_context_t *c,
- const Record<LangSys>::sanitize_closure_t * = nullptr) const
- {
- TRACE_SANITIZE (this);
- return_trace (c->check_struct (this) && featureIndex.sanitize (c));
- }
-
- Offset16 lookupOrderZ; /* = Null (reserved for an offset to a
- * reordering table) */
- UINT16 reqFeatureIndex;/* Index of a feature required for this
- * language system--if no required features
- * = 0xFFFFu */
- IndexArray featureIndex; /* Array of indices into the FeatureList */
- public:
- DEFINE_SIZE_ARRAY (6, featureIndex);
-};
-DEFINE_NULL_DATA (LangSys, "\0\0\xFF\xFF");
-
-
-struct Script
-{
- inline unsigned int get_lang_sys_count (void) const
- { return langSys.len; }
- inline const Tag& get_lang_sys_tag (unsigned int i) const
- { return langSys.get_tag (i); }
- inline unsigned int get_lang_sys_tags (unsigned int start_offset,
- unsigned int *lang_sys_count /* IN/OUT */,
- hb_tag_t *lang_sys_tags /* OUT */) const
- { return langSys.get_tags (start_offset, lang_sys_count, lang_sys_tags); }
- inline const LangSys& get_lang_sys (unsigned int i) const
- {
- if (i == Index::NOT_FOUND_INDEX) return get_default_lang_sys ();
- return this+langSys[i].offset;
- }
- inline bool find_lang_sys_index (hb_tag_t tag, unsigned int *index) const
- { return langSys.find_index (tag, index); }
-
- inline bool has_default_lang_sys (void) const { return defaultLangSys != 0; }
- inline const LangSys& get_default_lang_sys (void) const { return this+defaultLangSys; }
-
- inline bool sanitize (hb_sanitize_context_t *c,
- const Record<Script>::sanitize_closure_t * = nullptr) const
- {
- TRACE_SANITIZE (this);
- return_trace (defaultLangSys.sanitize (c, this) && langSys.sanitize (c, this));
- }
-
- protected:
- OffsetTo<LangSys>
- defaultLangSys; /* Offset to DefaultLangSys table--from
- * beginning of Script table--may be Null */
- RecordArrayOf<LangSys>
- langSys; /* Array of LangSysRecords--listed
- * alphabetically by LangSysTag */
- public:
- DEFINE_SIZE_ARRAY (4, langSys);
-};
-
-typedef RecordListOf<Script> ScriptList;
-
-
-/* http://www.microsoft.com/typography/otspec/features_pt.htm#size */
-struct FeatureParamsSize
-{
- inline bool sanitize (hb_sanitize_context_t *c) const
- {
- TRACE_SANITIZE (this);
- if (unlikely (!c->check_struct (this))) return_trace (false);
-
- /* This subtable has some "history", if you will. Some earlier versions of
- * Adobe tools calculated the offset of the FeatureParams sutable from the
- * beginning of the FeatureList table! Now, that is dealt with in the
- * Feature implementation. But we still need to be able to tell junk from
- * real data. Note: We don't check that the nameID actually exists.
- *
- * Read Roberts wrote on 9/15/06 on opentype-list@indx.co.uk :
- *
- * Yes, it is correct that a new version of the AFDKO (version 2.0) will be
- * coming out soon, and that the makeotf program will build a font with a
- * 'size' feature that is correct by the specification.
- *
- * The specification for this feature tag is in the "OpenType Layout Tag
- * Registry". You can see a copy of this at:
- * http://partners.adobe.com/public/developer/opentype/index_tag8.html#size
- *
- * Here is one set of rules to determine if the 'size' feature is built
- * correctly, or as by the older versions of MakeOTF. You may be able to do
- * better.
- *
- * Assume that the offset to the size feature is according to specification,
- * and make the following value checks. If it fails, assume the the size
- * feature is calculated as versions of MakeOTF before the AFDKO 2.0 built it.
- * If this fails, reject the 'size' feature. The older makeOTF's calculated the
- * offset from the beginning of the FeatureList table, rather than from the
- * beginning of the 'size' Feature table.
- *
- * If "design size" == 0:
- * fails check
- *
- * Else if ("subfamily identifier" == 0 and
- * "range start" == 0 and
- * "range end" == 0 and
- * "range start" == 0 and
- * "menu name ID" == 0)
- * passes check: this is the format used when there is a design size
- * specified, but there is no recommended size range.
- *
- * Else if ("design size" < "range start" or
- * "design size" > "range end" or
- * "range end" <= "range start" or
- * "menu name ID" < 256 or
- * "menu name ID" > 32767 or
- * menu name ID is not a name ID which is actually in the name table)
- * fails test
- * Else
- * passes test.
- */
-
- if (!designSize)
- return_trace (false);
- else if (subfamilyID == 0 &&
- subfamilyNameID == 0 &&
- rangeStart == 0 &&
- rangeEnd == 0)
- return_trace (true);
- else if (designSize < rangeStart ||
- designSize > rangeEnd ||
- subfamilyNameID < 256 ||
- subfamilyNameID > 32767)
- return_trace (false);
- else
- return_trace (true);
- }
-
- UINT16 designSize; /* Represents the design size in 720/inch
- * units (decipoints). The design size entry
- * must be non-zero. When there is a design
- * size but no recommended size range, the
- * rest of the array will consist of zeros. */
- UINT16 subfamilyID; /* Has no independent meaning, but serves
- * as an identifier that associates fonts
- * in a subfamily. All fonts which share a
- * Preferred or Font Family name and which
- * differ only by size range shall have the
- * same subfamily value, and no fonts which
- * differ in weight or style shall have the
- * same subfamily value. If this value is
- * zero, the remaining fields in the array
- * will be ignored. */
- UINT16 subfamilyNameID;/* If the preceding value is non-zero, this
- * value must be set in the range 256 - 32767
- * (inclusive). It records the value of a
- * field in the name table, which must
- * contain English-language strings encoded
- * in Windows Unicode and Macintosh Roman,
- * and may contain additional strings
- * localized to other scripts and languages.
- * Each of these strings is the name an
- * application should use, in combination
- * with the family name, to represent the
- * subfamily in a menu. Applications will
- * choose the appropriate version based on
- * their selection criteria. */
- UINT16 rangeStart; /* Large end of the recommended usage range
- * (inclusive), stored in 720/inch units
- * (decipoints). */
- UINT16 rangeEnd; /* Small end of the recommended usage range
- (exclusive), stored in 720/inch units
- * (decipoints). */
- public:
- DEFINE_SIZE_STATIC (10);
-};
-
-/* http://www.microsoft.com/typography/otspec/features_pt.htm#ssxx */
-struct FeatureParamsStylisticSet
-{
- inline bool sanitize (hb_sanitize_context_t *c) const
- {
- TRACE_SANITIZE (this);
- /* Right now minorVersion is at zero. Which means, any table supports
- * the uiNameID field. */
- return_trace (c->check_struct (this));
- }
-
- UINT16 version; /* (set to 0): This corresponds to a “minor”
- * version number. Additional data may be
- * added to the end of this Feature Parameters
- * table in the future. */
-
- UINT16 uiNameID; /* The 'name' table name ID that specifies a
- * string (or strings, for multiple languages)
- * for a user-interface label for this
- * feature. The values of uiLabelNameId and
- * sampleTextNameId are expected to be in the
- * font-specific name ID range (256-32767),
- * though that is not a requirement in this
- * Feature Parameters specification. The
- * user-interface label for the feature can
- * be provided in multiple languages. An
- * English string should be included as a
- * fallback. The string should be kept to a
- * minimal length to fit comfortably with
- * different application interfaces. */
- public:
- DEFINE_SIZE_STATIC (4);
-};
-
-/* http://www.microsoft.com/typography/otspec/features_ae.htm#cv01-cv99 */
-struct FeatureParamsCharacterVariants
-{
- inline bool sanitize (hb_sanitize_context_t *c) const
- {
- TRACE_SANITIZE (this);
- return_trace (c->check_struct (this) &&
- characters.sanitize (c));
- }
-
- UINT16 format; /* Format number is set to 0. */
- UINT16 featUILableNameID; /* The ‘name’ table name ID that
- * specifies a string (or strings,
- * for multiple languages) for a
- * user-interface label for this
- * feature. (May be nullptr.) */
- UINT16 featUITooltipTextNameID;/* The ‘name’ table name ID that
- * specifies a string (or strings,
- * for multiple languages) that an
- * application can use for tooltip
- * text for this feature. (May be
- * nullptr.) */
- UINT16 sampleTextNameID; /* The ‘name’ table name ID that
- * specifies sample text that
- * illustrates the effect of this
- * feature. (May be nullptr.) */
- UINT16 numNamedParameters; /* Number of named parameters. (May
- * be zero.) */
- UINT16 firstParamUILabelNameID;/* The first ‘name’ table name ID
- * used to specify strings for
- * user-interface labels for the
- * feature parameters. (Must be zero
- * if numParameters is zero.) */
- ArrayOf<UINT24>
- characters; /* Array of the Unicode Scalar Value
- * of the characters for which this
- * feature provides glyph variants.
- * (May be zero.) */
- public:
- DEFINE_SIZE_ARRAY (14, characters);
-};
-
-struct FeatureParams
-{
- inline bool sanitize (hb_sanitize_context_t *c, hb_tag_t tag) const
- {
- TRACE_SANITIZE (this);
- if (tag == HB_TAG ('s','i','z','e'))
- return_trace (u.size.sanitize (c));
- if ((tag & 0xFFFF0000u) == HB_TAG ('s','s','\0','\0')) /* ssXX */
- return_trace (u.stylisticSet.sanitize (c));
- if ((tag & 0xFFFF0000u) == HB_TAG ('c','v','\0','\0')) /* cvXX */
- return_trace (u.characterVariants.sanitize (c));
- return_trace (true);
- }
-
- inline const FeatureParamsSize& get_size_params (hb_tag_t tag) const
- {
- if (tag == HB_TAG ('s','i','z','e'))
- return u.size;
- return Null(FeatureParamsSize);
- }
-
- private:
- union {
- FeatureParamsSize size;
- FeatureParamsStylisticSet stylisticSet;
- FeatureParamsCharacterVariants characterVariants;
- } u;
- DEFINE_SIZE_STATIC (17);
-};
-
-struct Feature
-{
- inline unsigned int get_lookup_count (void) const
- { return lookupIndex.len; }
- inline hb_tag_t get_lookup_index (unsigned int i) const
- { return lookupIndex[i]; }
- inline unsigned int get_lookup_indexes (unsigned int start_index,
- unsigned int *lookup_count /* IN/OUT */,
- unsigned int *lookup_tags /* OUT */) const
- { return lookupIndex.get_indexes (start_index, lookup_count, lookup_tags); }
-
- inline const FeatureParams &get_feature_params (void) const
- { return this+featureParams; }
-
- inline bool sanitize (hb_sanitize_context_t *c,
- const Record<Feature>::sanitize_closure_t *closure = nullptr) const
- {
- TRACE_SANITIZE (this);
- if (unlikely (!(c->check_struct (this) && lookupIndex.sanitize (c))))
- return_trace (false);
-
- /* Some earlier versions of Adobe tools calculated the offset of the
- * FeatureParams subtable from the beginning of the FeatureList table!
- *
- * If sanitizing "failed" for the FeatureParams subtable, try it with the
- * alternative location. We would know sanitize "failed" if old value
- * of the offset was non-zero, but it's zeroed now.
- *
- * Only do this for the 'size' feature, since at the time of the faulty
- * Adobe tools, only the 'size' feature had FeatureParams defined.
- */
-
- OffsetTo<FeatureParams> orig_offset = featureParams;
- if (unlikely (!featureParams.sanitize (c, this, closure ? closure->tag : HB_TAG_NONE)))
- return_trace (false);
-
- if (likely (orig_offset.is_null ()))
- return_trace (true);
-
- if (featureParams == 0 && closure &&
- closure->tag == HB_TAG ('s','i','z','e') &&
- closure->list_base && closure->list_base < this)
- {
- unsigned int new_offset_int = (unsigned int) orig_offset -
- (((char *) this) - ((char *) closure->list_base));
-
- OffsetTo<FeatureParams> new_offset;
- /* Check that it did not overflow. */
- new_offset.set (new_offset_int);
- if (new_offset == new_offset_int &&
- c->try_set (&featureParams, new_offset) &&
- !featureParams.sanitize (c, this, closure ? closure->tag : HB_TAG_NONE))
- return_trace (false);
-
- if (c->edit_count > 1)
- c->edit_count--; /* This was a "legitimate" edit; don't contribute to error count. */
- }
-
- return_trace (true);
- }
-
- OffsetTo<FeatureParams>
- featureParams; /* Offset to Feature Parameters table (if one
- * has been defined for the feature), relative
- * to the beginning of the Feature Table; = Null
- * if not required */
- IndexArray lookupIndex; /* Array of LookupList indices */
- public:
- DEFINE_SIZE_ARRAY (4, lookupIndex);
-};
-
-typedef RecordListOf<Feature> FeatureList;
-
-
-struct LookupFlag : UINT16
-{
- enum Flags {
- RightToLeft = 0x0001u,
- IgnoreBaseGlyphs = 0x0002u,
- IgnoreLigatures = 0x0004u,
- IgnoreMarks = 0x0008u,
- IgnoreFlags = 0x000Eu,
- UseMarkFilteringSet = 0x0010u,
- Reserved = 0x00E0u,
- MarkAttachmentType = 0xFF00u
- };
- public:
- DEFINE_SIZE_STATIC (2);
-};
-
-} /* namespace OT */
-/* This has to be outside the namespace. */
-HB_MARK_AS_FLAG_T (OT::LookupFlag::Flags);
-namespace OT {
-
-struct Lookup
-{
- inline unsigned int get_subtable_count (void) const { return subTable.len; }
-
- template <typename SubTableType>
- inline const SubTableType& get_subtable (unsigned int i) const
- { return this+CastR<OffsetArrayOf<SubTableType> > (subTable)[i]; }
-
- template <typename SubTableType>
- inline const OffsetArrayOf<SubTableType>& get_subtables (void) const
- { return CastR<OffsetArrayOf<SubTableType> > (subTable); }
- template <typename SubTableType>
- inline OffsetArrayOf<SubTableType>& get_subtables (void)
- { return CastR<OffsetArrayOf<SubTableType> > (subTable); }
-
- inline unsigned int get_type (void) const { return lookupType; }
-
- /* lookup_props is a 32-bit integer where the lower 16-bit is LookupFlag and
- * higher 16-bit is mark-filtering-set if the lookup uses one.
- * Not to be confused with glyph_props which is very similar. */
- inline uint32_t get_props (void) const
- {
- unsigned int flag = lookupFlag;
- if (unlikely (flag & LookupFlag::UseMarkFilteringSet))
- {
- const UINT16 &markFilteringSet = StructAfter<UINT16> (subTable);
- flag += (markFilteringSet << 16);
- }
- return flag;
- }
-
- template <typename SubTableType, typename context_t>
- inline typename context_t::return_t dispatch (context_t *c) const
- {
- unsigned int lookup_type = get_type ();
- TRACE_DISPATCH (this, lookup_type);
- unsigned int count = get_subtable_count ();
- for (unsigned int i = 0; i < count; i++) {
- typename context_t::return_t r = get_subtable<SubTableType> (i).dispatch (c, lookup_type);
- if (c->stop_sublookup_iteration (r))
- return_trace (r);
- }
- return_trace (c->default_return_value ());
- }
-
- inline bool serialize (hb_serialize_context_t *c,
- unsigned int lookup_type,
- uint32_t lookup_props,
- unsigned int num_subtables)
- {
- TRACE_SERIALIZE (this);
- if (unlikely (!c->extend_min (*this))) return_trace (false);
- lookupType.set (lookup_type);
- lookupFlag.set (lookup_props & 0xFFFFu);
- if (unlikely (!subTable.serialize (c, num_subtables))) return_trace (false);
- if (lookupFlag & LookupFlag::UseMarkFilteringSet)
- {
- UINT16 &markFilteringSet = StructAfter<UINT16> (subTable);
- markFilteringSet.set (lookup_props >> 16);
- }
- return_trace (true);
- }
-
- inline bool sanitize (hb_sanitize_context_t *c) const
- {
- TRACE_SANITIZE (this);
- /* Real sanitize of the subtables is done by GSUB/GPOS/... */
- if (!(c->check_struct (this) && subTable.sanitize (c))) return_trace (false);
- if (lookupFlag & LookupFlag::UseMarkFilteringSet)
- {
- const UINT16 &markFilteringSet = StructAfter<UINT16> (subTable);
- if (!markFilteringSet.sanitize (c)) return_trace (false);
- }
- return_trace (true);
- }
-
- private:
- UINT16 lookupType; /* Different enumerations for GSUB and GPOS */
- UINT16 lookupFlag; /* Lookup qualifiers */
- ArrayOf<Offset16>
- subTable; /* Array of SubTables */
- UINT16 markFilteringSetX[VAR]; /* Index (base 0) into GDEF mark glyph sets
- * structure. This field is only present if bit
- * UseMarkFilteringSet of lookup flags is set. */
- public:
- DEFINE_SIZE_ARRAY2 (6, subTable, markFilteringSetX);
-};
-
-typedef OffsetListOf<Lookup> LookupList;
-
-
-/*
- * Coverage Table
- */
-
-struct CoverageFormat1
-{
- friend struct Coverage;
-
- private:
- inline unsigned int get_coverage (hb_codepoint_t glyph_id) const
- {
- int i = glyphArray.bsearch (glyph_id);
- static_assert ((((unsigned int) -1) == NOT_COVERED), "");
- return i;
- }
-
- inline bool serialize (hb_serialize_context_t *c,
- Supplier<GlyphID> &glyphs,
- unsigned int num_glyphs)
- {
- TRACE_SERIALIZE (this);
- if (unlikely (!c->extend_min (*this))) return_trace (false);
- glyphArray.len.set (num_glyphs);
- if (unlikely (!c->extend (glyphArray))) return_trace (false);
- for (unsigned int i = 0; i < num_glyphs; i++)
- glyphArray[i] = glyphs[i];
- glyphs.advance (num_glyphs);
- return_trace (true);
- }
-
- inline bool sanitize (hb_sanitize_context_t *c) const
- {
- TRACE_SANITIZE (this);
- return_trace (glyphArray.sanitize (c));
- }
-
- inline bool intersects_coverage (const hb_set_t *glyphs, unsigned int index) const {
- return glyphs->has (glyphArray[index]);
- }
-
- template <typename set_t>
- inline bool add_coverage (set_t *glyphs) const {
- return glyphs->add_sorted_array (glyphArray.array, glyphArray.len);
- }
-
- public:
- /* Older compilers need this to be public. */
- struct Iter {
- inline void init (const struct CoverageFormat1 &c_) { c = &c_; i = 0; };
- inline bool more (void) { return i < c->glyphArray.len; }
- inline void next (void) { i++; }
- inline hb_codepoint_t get_glyph (void) { return c->glyphArray[i]; }
- inline unsigned int get_coverage (void) { return i; }
-
- private:
- const struct CoverageFormat1 *c;
- unsigned int i;
- };
- private:
-
- protected:
- UINT16 coverageFormat; /* Format identifier--format = 1 */
- SortedArrayOf<GlyphID>
- glyphArray; /* Array of GlyphIDs--in numerical order */
- public:
- DEFINE_SIZE_ARRAY (4, glyphArray);
-};
-
-struct CoverageFormat2
-{
- friend struct Coverage;
-
- private:
- inline unsigned int get_coverage (hb_codepoint_t glyph_id) const
- {
- int i = rangeRecord.bsearch (glyph_id);
- if (i != -1) {
- const RangeRecord &range = rangeRecord[i];
- return (unsigned int) range.value + (glyph_id - range.start);
- }
- return NOT_COVERED;
- }
-
- inline bool serialize (hb_serialize_context_t *c,
- Supplier<GlyphID> &glyphs,
- unsigned int num_glyphs)
- {
- TRACE_SERIALIZE (this);
- if (unlikely (!c->extend_min (*this))) return_trace (false);
-
- if (unlikely (!num_glyphs))
- {
- rangeRecord.len.set (0);
- return_trace (true);
- }
-
- unsigned int num_ranges = 1;
- for (unsigned int i = 1; i < num_glyphs; i++)
- if (glyphs[i - 1] + 1 != glyphs[i])
- num_ranges++;
- rangeRecord.len.set (num_ranges);
- if (unlikely (!c->extend (rangeRecord))) return_trace (false);
-
- unsigned int range = 0;
- rangeRecord[range].start = glyphs[0];
- rangeRecord[range].value.set (0);
- for (unsigned int i = 1; i < num_glyphs; i++)
- if (glyphs[i - 1] + 1 != glyphs[i]) {
- range++;
- rangeRecord[range].start = glyphs[i];
- rangeRecord[range].value.set (i);
- rangeRecord[range].end = glyphs[i];
- } else {
- rangeRecord[range].end = glyphs[i];
- }
- glyphs.advance (num_glyphs);
- return_trace (true);
- }
-
- inline bool sanitize (hb_sanitize_context_t *c) const
- {
- TRACE_SANITIZE (this);
- return_trace (rangeRecord.sanitize (c));
- }
-
- inline bool intersects_coverage (const hb_set_t *glyphs, unsigned int index) const {
- unsigned int i;
- unsigned int count = rangeRecord.len;
- for (i = 0; i < count; i++) {
- const RangeRecord &range = rangeRecord[i];
- if (range.value <= index &&
- index < (unsigned int) range.value + (range.end - range.start) &&
- range.intersects (glyphs))
- return true;
- else if (index < range.value)
- return false;
- }
- return false;
- }
-
- template <typename set_t>
- inline bool add_coverage (set_t *glyphs) const {
- unsigned int count = rangeRecord.len;
- for (unsigned int i = 0; i < count; i++)
- if (unlikely (!rangeRecord[i].add_coverage (glyphs)))
- return false;
- return true;
- }
-
- public:
- /* Older compilers need this to be public. */
- struct Iter
- {
- inline void init (const CoverageFormat2 &c_)
- {
- c = &c_;
- coverage = 0;
- i = 0;
- j = c->rangeRecord.len ? c_.rangeRecord[0].start : 0;
- }
- inline bool more (void) { return i < c->rangeRecord.len; }
- inline void next (void)
- {
- if (j >= c->rangeRecord[i].end)
- {
- i++;
- if (more ())
- {
- j = c->rangeRecord[i].start;
- coverage = c->rangeRecord[i].value;
- }
- return;
- }
- coverage++;
- j++;
- }
- inline hb_codepoint_t get_glyph (void) { return j; }
- inline unsigned int get_coverage (void) { return coverage; }
-
- private:
- const struct CoverageFormat2 *c;
- unsigned int i, j, coverage;
- };
- private:
-
- protected:
- UINT16 coverageFormat; /* Format identifier--format = 2 */
- SortedArrayOf<RangeRecord>
- rangeRecord; /* Array of glyph ranges--ordered by
- * Start GlyphID. rangeCount entries
- * long */
- public:
- DEFINE_SIZE_ARRAY (4, rangeRecord);
-};
-
-struct Coverage
-{
- inline unsigned int get_coverage (hb_codepoint_t glyph_id) const
- {
- switch (u.format) {
- case 1: return u.format1.get_coverage(glyph_id);
- case 2: return u.format2.get_coverage(glyph_id);
- default:return NOT_COVERED;
- }
- }
-
- inline bool serialize (hb_serialize_context_t *c,
- Supplier<GlyphID> &glyphs,
- unsigned int num_glyphs)
- {
- TRACE_SERIALIZE (this);
- if (unlikely (!c->extend_min (*this))) return_trace (false);
- unsigned int num_ranges = 1;
- for (unsigned int i = 1; i < num_glyphs; i++)
- if (glyphs[i - 1] + 1 != glyphs[i])
- num_ranges++;
- u.format.set (num_glyphs * 2 < num_ranges * 3 ? 1 : 2);
- switch (u.format) {
- case 1: return_trace (u.format1.serialize (c, glyphs, num_glyphs));
- case 2: return_trace (u.format2.serialize (c, glyphs, num_glyphs));
- default:return_trace (false);
- }
- }
-
- inline bool sanitize (hb_sanitize_context_t *c) const
- {
- TRACE_SANITIZE (this);
- if (!u.format.sanitize (c)) return_trace (false);
- switch (u.format) {
- case 1: return_trace (u.format1.sanitize (c));
- case 2: return_trace (u.format2.sanitize (c));
- default:return_trace (true);
- }
- }
-
- inline bool intersects (const hb_set_t *glyphs) const {
- /* TODO speed this up */
- Coverage::Iter iter;
- for (iter.init (*this); iter.more (); iter.next ()) {
- if (glyphs->has (iter.get_glyph ()))
- return true;
- }
- return false;
- }
-
- inline bool intersects_coverage (const hb_set_t *glyphs, unsigned int index) const {
- switch (u.format) {
- case 1: return u.format1.intersects_coverage (glyphs, index);
- case 2: return u.format2.intersects_coverage (glyphs, index);
- default:return false;
- }
- }
-
- /* Might return false if array looks unsorted.
- * Used for faster rejection of corrupt data. */
- template <typename set_t>
- inline bool add_coverage (set_t *glyphs) const {
- switch (u.format) {
- case 1: return u.format1.add_coverage (glyphs);
- case 2: return u.format2.add_coverage (glyphs);
- default:return false;
- }
- }
-
- struct Iter {
- Iter (void) : format (0), u () {};
- inline void init (const Coverage &c_) {
- format = c_.u.format;
- switch (format) {
- case 1: u.format1.init (c_.u.format1); return;
- case 2: u.format2.init (c_.u.format2); return;
- default: return;
- }
- }
- inline bool more (void) {
- switch (format) {
- case 1: return u.format1.more ();
- case 2: return u.format2.more ();
- default:return false;
- }
- }
- inline void next (void) {
- switch (format) {
- case 1: u.format1.next (); break;
- case 2: u.format2.next (); break;
- default: break;
- }
- }
- inline hb_codepoint_t get_glyph (void) {
- switch (format) {
- case 1: return u.format1.get_glyph ();
- case 2: return u.format2.get_glyph ();
- default:return 0;
- }
- }
- inline unsigned int get_coverage (void) {
- switch (format) {
- case 1: return u.format1.get_coverage ();
- case 2: return u.format2.get_coverage ();
- default:return -1;
- }
- }
-
- private:
- unsigned int format;
- union {
- CoverageFormat2::Iter format2; /* Put this one first since it's larger; helps shut up compiler. */
- CoverageFormat1::Iter format1;
- } u;
- };
-
- protected:
- union {
- UINT16 format; /* Format identifier */
- CoverageFormat1 format1;
- CoverageFormat2 format2;
- } u;
- public:
- DEFINE_SIZE_UNION (2, format);
-};
-
-
-/*
- * Class Definition Table
- */
-
-struct ClassDefFormat1
-{
- friend struct ClassDef;
-
- private:
- inline unsigned int get_class (hb_codepoint_t glyph_id) const
- {
- unsigned int i = (unsigned int) (glyph_id - startGlyph);
- if (unlikely (i < classValue.len))
- return classValue[i];
- return 0;
- }
-
- inline bool sanitize (hb_sanitize_context_t *c) const
- {
- TRACE_SANITIZE (this);
- return_trace (c->check_struct (this) && classValue.sanitize (c));
- }
-
- template <typename set_t>
- inline bool add_coverage (set_t *glyphs) const {
- unsigned int start = 0;
- unsigned int count = classValue.len;
- for (unsigned int i = 0; i < count; i++)
- {
- if (classValue[i])
- continue;
-
- if (start != i)
- if (unlikely (!glyphs->add_range (startGlyph + start, startGlyph + i)))
- return false;
-
- start = i + 1;
- }
- if (start != count)
- if (unlikely (!glyphs->add_range (startGlyph + start, startGlyph + count)))
- return false;
-
- return true;
- }
-
- template <typename set_t>
- inline bool add_class (set_t *glyphs, unsigned int klass) const {
- unsigned int count = classValue.len;
- for (unsigned int i = 0; i < count; i++)
- {
- if (classValue[i] == klass)
- glyphs->add (startGlyph + i);
- }
- return true;
- }
-
- inline bool intersects_class (const hb_set_t *glyphs, unsigned int klass) const {
- unsigned int count = classValue.len;
- if (klass == 0)
- {
- /* Match if there's any glyph that is not listed! */
- hb_codepoint_t g = -1;
- if (!hb_set_next (glyphs, &g))
- return false;
- if (g < startGlyph)
- return true;
- g = startGlyph + count - 1;
- if (hb_set_next (glyphs, &g))
- return true;
- /* Fall through. */
- }
- for (unsigned int i = 0; i < count; i++)
- if (classValue[i] == klass && glyphs->has (startGlyph + i))
- return true;
- return false;
- }
-
- protected:
- UINT16 classFormat; /* Format identifier--format = 1 */
- GlyphID startGlyph; /* First GlyphID of the classValueArray */
- ArrayOf<UINT16>
- classValue; /* Array of Class Values--one per GlyphID */
- public:
- DEFINE_SIZE_ARRAY (6, classValue);
-};
-
-struct ClassDefFormat2
-{
- friend struct ClassDef;
-
- private:
- inline unsigned int get_class (hb_codepoint_t glyph_id) const
- {
- int i = rangeRecord.bsearch (glyph_id);
- if (unlikely (i != -1))
- return rangeRecord[i].value;
- return 0;
- }
-
- inline bool sanitize (hb_sanitize_context_t *c) const
- {
- TRACE_SANITIZE (this);
- return_trace (rangeRecord.sanitize (c));
- }
-
- template <typename set_t>
- inline bool add_coverage (set_t *glyphs) const {
- unsigned int count = rangeRecord.len;
- for (unsigned int i = 0; i < count; i++)
- if (rangeRecord[i].value)
- if (unlikely (!rangeRecord[i].add_coverage (glyphs)))
- return false;
- return true;
- }
-
- template <typename set_t>
- inline bool add_class (set_t *glyphs, unsigned int klass) const {
- unsigned int count = rangeRecord.len;
- for (unsigned int i = 0; i < count; i++)
- {
- if (rangeRecord[i].value == klass)
- if (unlikely (!rangeRecord[i].add_coverage (glyphs)))
- return false;
- }
- return true;
- }
-
- inline bool intersects_class (const hb_set_t *glyphs, unsigned int klass) const {
- unsigned int count = rangeRecord.len;
- if (klass == 0)
- {
- /* Match if there's any glyph that is not listed! */
- hb_codepoint_t g = (hb_codepoint_t) -1;
- for (unsigned int i = 0; i < count; i++)
- {
- if (!hb_set_next (glyphs, &g))
- break;
- if (g < rangeRecord[i].start)
- return true;
- g = rangeRecord[i].end;
- }
- if (g != (hb_codepoint_t) -1 && hb_set_next (glyphs, &g))
- return true;
- /* Fall through. */
- }
- for (unsigned int i = 0; i < count; i++)
- if (rangeRecord[i].value == klass && rangeRecord[i].intersects (glyphs))
- return true;
- return false;
- }
-
- protected:
- UINT16 classFormat; /* Format identifier--format = 2 */
- SortedArrayOf<RangeRecord>
- rangeRecord; /* Array of glyph ranges--ordered by
- * Start GlyphID */
- public:
- DEFINE_SIZE_ARRAY (4, rangeRecord);
-};
-
-struct ClassDef
-{
- inline unsigned int get_class (hb_codepoint_t glyph_id) const
- {
- switch (u.format) {
- case 1: return u.format1.get_class(glyph_id);
- case 2: return u.format2.get_class(glyph_id);
- default:return 0;
- }
- }
-
- inline bool sanitize (hb_sanitize_context_t *c) const
- {
- TRACE_SANITIZE (this);
- if (!u.format.sanitize (c)) return_trace (false);
- switch (u.format) {
- case 1: return_trace (u.format1.sanitize (c));
- case 2: return_trace (u.format2.sanitize (c));
- default:return_trace (true);
- }
- }
-
- /* Might return false if array looks unsorted.
- * Used for faster rejection of corrupt data. */
- template <typename set_t>
- inline bool add_coverage (set_t *glyphs) const {
- switch (u.format) {
- case 1: return u.format1.add_coverage (glyphs);
- case 2: return u.format2.add_coverage (glyphs);
- default:return false;
- }
- }
-
- /* Might return false if array looks unsorted.
- * Used for faster rejection of corrupt data. */
- template <typename set_t>
- inline bool add_class (set_t *glyphs, unsigned int klass) const {
- switch (u.format) {
- case 1: return u.format1.add_class (glyphs, klass);
- case 2: return u.format2.add_class (glyphs, klass);
- default:return false;
- }
- }
-
- inline bool intersects_class (const hb_set_t *glyphs, unsigned int klass) const {
- switch (u.format) {
- case 1: return u.format1.intersects_class (glyphs, klass);
- case 2: return u.format2.intersects_class (glyphs, klass);
- default:return false;
- }
- }
-
- protected:
- union {
- UINT16 format; /* Format identifier */
- ClassDefFormat1 format1;
- ClassDefFormat2 format2;
- } u;
- public:
- DEFINE_SIZE_UNION (2, format);
-};
-
-
-/*
- * Item Variation Store
- */
-
-struct VarRegionAxis
-{
- inline float evaluate (int coord) const
- {
- int start = startCoord, peak = peakCoord, end = endCoord;
-
- /* TODO Move these to sanitize(). */
- if (unlikely (start > peak || peak > end))
- return 1.;
- if (unlikely (start < 0 && end > 0 && peak != 0))
- return 1.;
-
- if (peak == 0 || coord == peak)
- return 1.;
-
- if (coord <= start || end <= coord)
- return 0.;
-
- /* Interpolate */
- if (coord < peak)
- return float (coord - start) / (peak - start);
- else
- return float (end - coord) / (end - peak);
- }
-
- inline bool sanitize (hb_sanitize_context_t *c) const
- {
- TRACE_SANITIZE (this);
- return_trace (c->check_struct (this));
- /* TODO Handle invalid start/peak/end configs, so we don't
- * have to do that at runtime. */
- }
-
- public:
- F2DOT14 startCoord;
- F2DOT14 peakCoord;
- F2DOT14 endCoord;
- public:
- DEFINE_SIZE_STATIC (6);
-};
-
-struct VarRegionList
-{
- inline float evaluate (unsigned int region_index,
- int *coords, unsigned int coord_len) const
- {
- if (unlikely (region_index >= regionCount))
- return 0.;
-
- const VarRegionAxis *axes = axesZ + (region_index * axisCount);
-
- float v = 1.;
- unsigned int count = MIN (coord_len, (unsigned int) axisCount);
- for (unsigned int i = 0; i < count; i++)
- {
- float factor = axes[i].evaluate (coords[i]);
- if (factor == 0.)
- return 0.;
- v *= factor;
- }
- return v;
- }
-
- inline bool sanitize (hb_sanitize_context_t *c) const
- {
- TRACE_SANITIZE (this);
- return_trace (c->check_struct (this) &&
- c->check_array (axesZ, axesZ[0].static_size,
- (unsigned int) axisCount * (unsigned int) regionCount));
- }
-
- protected:
- UINT16 axisCount;
- UINT16 regionCount;
- VarRegionAxis axesZ[VAR];
- public:
- DEFINE_SIZE_ARRAY (4, axesZ);
-};
-
-struct VarData
-{
- inline unsigned int get_row_size (void) const
- { return shortCount + regionIndices.len; }
-
- inline unsigned int get_size (void) const
- { return itemCount * get_row_size (); }
-
- inline float get_delta (unsigned int inner,
- int *coords, unsigned int coord_count,
- const VarRegionList &regions) const
- {
- if (unlikely (inner >= itemCount))
- return 0.;
-
- unsigned int count = regionIndices.len;
- unsigned int scount = shortCount;
-
- const UINT8 *bytes = &StructAfter<UINT8> (regionIndices);
- const UINT8 *row = bytes + inner * (scount + count);
-
- float delta = 0.;
- unsigned int i = 0;
-
- const INT16 *scursor = reinterpret_cast<const INT16 *> (row);
- for (; i < scount; i++)
- {
- float scalar = regions.evaluate (regionIndices.array[i], coords, coord_count);
- delta += scalar * *scursor++;
- }
- const INT8 *bcursor = reinterpret_cast<const INT8 *> (scursor);
- for (; i < count; i++)
- {
- float scalar = regions.evaluate (regionIndices.array[i], coords, coord_count);
- delta += scalar * *bcursor++;
- }
-
- return delta;
- }
-
- inline bool sanitize (hb_sanitize_context_t *c) const
- {
- TRACE_SANITIZE (this);
- return_trace (c->check_struct (this) &&
- regionIndices.sanitize(c) &&
- shortCount <= regionIndices.len &&
- c->check_array (&StructAfter<UINT8> (regionIndices),
- get_row_size (), itemCount));
- }
-
- protected:
- UINT16 itemCount;
- UINT16 shortCount;
- ArrayOf<UINT16> regionIndices;
- UINT8 bytesX[VAR];
- public:
- DEFINE_SIZE_ARRAY2 (6, regionIndices, bytesX);
-};
-
-struct VariationStore
-{
- inline float get_delta (unsigned int outer, unsigned int inner,
- int *coords, unsigned int coord_count) const
- {
- if (unlikely (outer >= dataSets.len))
- return 0.;
-
- return (this+dataSets[outer]).get_delta (inner,
- coords, coord_count,
- this+regions);
- }
-
- inline float get_delta (unsigned int index,
- int *coords, unsigned int coord_count) const
- {
- unsigned int outer = index >> 16;
- unsigned int inner = index & 0xFFFF;
- return get_delta (outer, inner, coords, coord_count);
- }
-
- inline bool sanitize (hb_sanitize_context_t *c) const
- {
- TRACE_SANITIZE (this);
- return_trace (c->check_struct (this) &&
- format == 1 &&
- regions.sanitize (c, this) &&
- dataSets.sanitize (c, this));
- }
-
- protected:
- UINT16 format;
- LOffsetTo<VarRegionList> regions;
- OffsetArrayOf<VarData, UINT32> dataSets;
- public:
- DEFINE_SIZE_ARRAY (8, dataSets);
-};
-
-/*
- * Feature Variations
- */
-
-struct ConditionFormat1
-{
- friend struct Condition;
-
- private:
- inline bool evaluate (const int *coords, unsigned int coord_len) const
- {
- int coord = axisIndex < coord_len ? coords[axisIndex] : 0;
- return filterRangeMinValue <= coord && coord <= filterRangeMaxValue;
- }
-
- inline bool sanitize (hb_sanitize_context_t *c) const
- {
- TRACE_SANITIZE (this);
- return_trace (c->check_struct (this));
- }
-
- protected:
- UINT16 format; /* Format identifier--format = 1 */
- UINT16 axisIndex;
- F2DOT14 filterRangeMinValue;
- F2DOT14 filterRangeMaxValue;
- public:
- DEFINE_SIZE_STATIC (8);
-};
-
-struct Condition
-{
- inline bool evaluate (const int *coords, unsigned int coord_len) const
- {
- switch (u.format) {
- case 1: return u.format1.evaluate (coords, coord_len);
- default:return false;
- }
- }
-
- inline bool sanitize (hb_sanitize_context_t *c) const
- {
- TRACE_SANITIZE (this);
- if (!u.format.sanitize (c)) return_trace (false);
- switch (u.format) {
- case 1: return_trace (u.format1.sanitize (c));
- default:return_trace (true);
- }
- }
-
- protected:
- union {
- UINT16 format; /* Format identifier */
- ConditionFormat1 format1;
- } u;
- public:
- DEFINE_SIZE_UNION (2, format);
-};
-
-struct ConditionSet
-{
- inline bool evaluate (const int *coords, unsigned int coord_len) const
- {
- unsigned int count = conditions.len;
- for (unsigned int i = 0; i < count; i++)
- if (!(this+conditions.array[i]).evaluate (coords, coord_len))
- return false;
- return true;
- }
-
- inline bool sanitize (hb_sanitize_context_t *c) const
- {
- TRACE_SANITIZE (this);
- return_trace (conditions.sanitize (c, this));
- }
-
- protected:
- OffsetArrayOf<Condition, UINT32> conditions;
- public:
- DEFINE_SIZE_ARRAY (2, conditions);
-};
-
-struct FeatureTableSubstitutionRecord
-{
- friend struct FeatureTableSubstitution;
-
- inline bool sanitize (hb_sanitize_context_t *c, const void *base) const
- {
- TRACE_SANITIZE (this);
- return_trace (c->check_struct (this) && feature.sanitize (c, base));
- }
-
- protected:
- UINT16 featureIndex;
- LOffsetTo<Feature> feature;
- public:
- DEFINE_SIZE_STATIC (6);
-};
-
-struct FeatureTableSubstitution
-{
- inline const Feature *find_substitute (unsigned int feature_index) const
- {
- unsigned int count = substitutions.len;
- for (unsigned int i = 0; i < count; i++)
- {
- const FeatureTableSubstitutionRecord &record = substitutions.array[i];
- if (record.featureIndex == feature_index)
- return &(this+record.feature);
- }
- return nullptr;
- }
-
- inline bool sanitize (hb_sanitize_context_t *c) const
- {
- TRACE_SANITIZE (this);
- return_trace (version.sanitize (c) &&
- likely (version.major == 1) &&
- substitutions.sanitize (c, this));
- }
-
- protected:
- FixedVersion<> version; /* Version--0x00010000u */
- ArrayOf<FeatureTableSubstitutionRecord>
- substitutions;
- public:
- DEFINE_SIZE_ARRAY (6, substitutions);
-};
-
-struct FeatureVariationRecord
-{
- friend struct FeatureVariations;
-
- inline bool sanitize (hb_sanitize_context_t *c, const void *base) const
- {
- TRACE_SANITIZE (this);
- return_trace (conditions.sanitize (c, base) &&
- substitutions.sanitize (c, base));
- }
-
- protected:
- LOffsetTo<ConditionSet>
- conditions;
- LOffsetTo<FeatureTableSubstitution>
- substitutions;
- public:
- DEFINE_SIZE_STATIC (8);
-};
-
-struct FeatureVariations
-{
- static const unsigned int NOT_FOUND_INDEX = 0xFFFFFFFFu;
-
- inline bool find_index (const int *coords, unsigned int coord_len,
- unsigned int *index) const
- {
- unsigned int count = varRecords.len;
- for (unsigned int i = 0; i < count; i++)
- {
- const FeatureVariationRecord &record = varRecords.array[i];
- if ((this+record.conditions).evaluate (coords, coord_len))
- {
- *index = i;
- return true;
- }
- }
- *index = NOT_FOUND_INDEX;
- return false;
- }
-
- inline const Feature *find_substitute (unsigned int variations_index,
- unsigned int feature_index) const
- {
- const FeatureVariationRecord &record = varRecords[variations_index];
- return (this+record.substitutions).find_substitute (feature_index);
- }
-
- inline bool sanitize (hb_sanitize_context_t *c) const
- {
- TRACE_SANITIZE (this);
- return_trace (version.sanitize (c) &&
- likely (version.major == 1) &&
- varRecords.sanitize (c, this));
- }
-
- protected:
- FixedVersion<> version; /* Version--0x00010000u */
- LArrayOf<FeatureVariationRecord>
- varRecords;
- public:
- DEFINE_SIZE_ARRAY (8, varRecords);
-};
-
-
-/*
- * Device Tables
- */
-
-struct HintingDevice
-{
- friend struct Device;
-
- private:
-
- inline hb_position_t get_x_delta (hb_font_t *font) const
- { return get_delta (font->x_ppem, font->x_scale); }
-
- inline hb_position_t get_y_delta (hb_font_t *font) const
- { return get_delta (font->y_ppem, font->y_scale); }
-
- inline unsigned int get_size (void) const
- {
- unsigned int f = deltaFormat;
- if (unlikely (f < 1 || f > 3 || startSize > endSize)) return 3 * UINT16::static_size;
- return UINT16::static_size * (4 + ((endSize - startSize) >> (4 - f)));
- }
-
- inline bool sanitize (hb_sanitize_context_t *c) const
- {
- TRACE_SANITIZE (this);
- return_trace (c->check_struct (this) && c->check_range (this, this->get_size ()));
- }
-
- private:
-
- inline int get_delta (unsigned int ppem, int scale) const
- {
- if (!ppem) return 0;
-
- int pixels = get_delta_pixels (ppem);
-
- if (!pixels) return 0;
-
- return (int) (pixels * (int64_t) scale / ppem);
- }
- inline int get_delta_pixels (unsigned int ppem_size) const
- {
- unsigned int f = deltaFormat;
- if (unlikely (f < 1 || f > 3))
- return 0;
-
- if (ppem_size < startSize || ppem_size > endSize)
- return 0;
-
- unsigned int s = ppem_size - startSize;
-
- unsigned int byte = deltaValue[s >> (4 - f)];
- unsigned int bits = (byte >> (16 - (((s & ((1 << (4 - f)) - 1)) + 1) << f)));
- unsigned int mask = (0xFFFFu >> (16 - (1 << f)));
-
- int delta = bits & mask;
-
- if ((unsigned int) delta >= ((mask + 1) >> 1))
- delta -= mask + 1;
-
- return delta;
- }
-
- protected:
- UINT16 startSize; /* Smallest size to correct--in ppem */
- UINT16 endSize; /* Largest size to correct--in ppem */
- UINT16 deltaFormat; /* Format of DeltaValue array data: 1, 2, or 3
- * 1 Signed 2-bit value, 8 values per uint16
- * 2 Signed 4-bit value, 4 values per uint16
- * 3 Signed 8-bit value, 2 values per uint16
- */
- UINT16 deltaValue[VAR]; /* Array of compressed data */
- public:
- DEFINE_SIZE_ARRAY (6, deltaValue);
-};
-
-struct VariationDevice
-{
- friend struct Device;
-
- private:
-
- inline hb_position_t get_x_delta (hb_font_t *font, const VariationStore &store) const
- { return font->em_scalef_x (get_delta (font, store)); }
-
- inline hb_position_t get_y_delta (hb_font_t *font, const VariationStore &store) const
- { return font->em_scalef_y (get_delta (font, store)); }
-
- inline bool sanitize (hb_sanitize_context_t *c) const
- {
- TRACE_SANITIZE (this);
- return_trace (c->check_struct (this));
- }
-
- private:
-
- inline float get_delta (hb_font_t *font, const VariationStore &store) const
- {
- return store.get_delta (outerIndex, innerIndex, font->coords, font->num_coords);
- }
-
- protected:
- UINT16 outerIndex;
- UINT16 innerIndex;
- UINT16 deltaFormat; /* Format identifier for this table: 0x0x8000 */
- public:
- DEFINE_SIZE_STATIC (6);
-};
-
-struct DeviceHeader
-{
- protected:
- UINT16 reserved1;
- UINT16 reserved2;
- public:
- UINT16 format; /* Format identifier */
- public:
- DEFINE_SIZE_STATIC (6);
-};
-
-struct Device
-{
- inline hb_position_t get_x_delta (hb_font_t *font, const VariationStore &store=Null(VariationStore)) const
- {
- switch (u.b.format)
- {
- case 1: case 2: case 3:
- return u.hinting.get_x_delta (font);
- case 0x8000:
- return u.variation.get_x_delta (font, store);
- default:
- return 0;
- }
- }
- inline hb_position_t get_y_delta (hb_font_t *font, const VariationStore &store=Null(VariationStore)) const
- {
- switch (u.b.format)
- {
- case 1: case 2: case 3:
- return u.hinting.get_y_delta (font);
- case 0x8000:
- return u.variation.get_y_delta (font, store);
- default:
- return 0;
- }
- }
-
- inline bool sanitize (hb_sanitize_context_t *c) const
- {
- TRACE_SANITIZE (this);
- if (!u.b.format.sanitize (c)) return_trace (false);
- switch (u.b.format) {
- case 1: case 2: case 3:
- return_trace (u.hinting.sanitize (c));
- case 0x8000:
- return_trace (u.variation.sanitize (c));
- default:
- return_trace (true);
- }
- }
-
- protected:
- union {
- DeviceHeader b;
- HintingDevice hinting;
- VariationDevice variation;
- } u;
- public:
- DEFINE_SIZE_UNION (6, b);
-};
-
-
-} /* namespace OT */
-
-
-#endif /* HB_OT_LAYOUT_COMMON_PRIVATE_HH */