From 3194963657a3049961fb64c9be86c1629afcea4b Mon Sep 17 00:00:00 2001 From: Behdad Esfahbod Date: Thu, 4 May 2023 16:29:48 -0600 Subject: [PATCH] Revert "[layout] Cache subtable coverages in hb_map_t" This reverts commit 7a715d74e06720c17d28ba7b4c3da0b583f8d1d3. --- src/OT/Layout/GPOS/CursivePosFormat1.hh | 4 +- src/OT/Layout/GPOS/MarkBasePosFormat1.hh | 5 +- src/OT/Layout/GPOS/MarkLigPosFormat1.hh | 5 +- src/OT/Layout/GPOS/MarkMarkPosFormat1.hh | 5 +- src/OT/Layout/GPOS/PairPosFormat1.hh | 6 +- src/OT/Layout/GPOS/PairPosFormat2.hh | 4 +- src/OT/Layout/GPOS/PosLookup.hh | 4 +- src/OT/Layout/GPOS/SinglePosFormat1.hh | 4 +- src/OT/Layout/GPOS/SinglePosFormat2.hh | 8 ++- src/OT/Layout/GSUB/AlternateSubstFormat1.hh | 8 ++- src/OT/Layout/GSUB/LigatureSubstFormat1.hh | 8 ++- src/OT/Layout/GSUB/MultipleSubstFormat1.hh | 8 ++- .../GSUB/ReverseChainSingleSubstFormat1.hh | 9 ++- src/OT/Layout/GSUB/SingleSubstFormat1.hh | 4 +- src/OT/Layout/GSUB/SingleSubstFormat2.hh | 8 ++- src/OT/Layout/GSUB/SubstLookup.hh | 4 +- src/hb-ot-layout-gsubgpos.hh | 70 ++++++++++--------- 17 files changed, 99 insertions(+), 65 deletions(-) diff --git a/src/OT/Layout/GPOS/CursivePosFormat1.hh b/src/OT/Layout/GPOS/CursivePosFormat1.hh index 0c97f1dfc..b8773ba0a 100644 --- a/src/OT/Layout/GPOS/CursivePosFormat1.hh +++ b/src/OT/Layout/GPOS/CursivePosFormat1.hh @@ -113,12 +113,12 @@ struct CursivePosFormat1 const Coverage &get_coverage () const { return this+coverage; } - bool apply (hb_ot_apply_context_t *c, unsigned coverage_index) const + bool apply (hb_ot_apply_context_t *c) const { TRACE_APPLY (this); hb_buffer_t *buffer = c->buffer; - const EntryExitRecord &this_record = entryExitRecord[coverage_index]; + const EntryExitRecord &this_record = entryExitRecord[(this+coverage).get_coverage (buffer->cur().codepoint)]; if (!this_record.entryAnchor) return_trace (false); hb_ot_apply_context_t::skipping_iterator_t &skippy_iter = c->iter_input; diff --git a/src/OT/Layout/GPOS/MarkBasePosFormat1.hh b/src/OT/Layout/GPOS/MarkBasePosFormat1.hh index c48875d8a..eb4712049 100644 --- a/src/OT/Layout/GPOS/MarkBasePosFormat1.hh +++ b/src/OT/Layout/GPOS/MarkBasePosFormat1.hh @@ -109,11 +109,12 @@ struct MarkBasePosFormat1_2 ); } - bool apply (hb_ot_apply_context_t *c, unsigned coverage_index) const + bool apply (hb_ot_apply_context_t *c) const { TRACE_APPLY (this); hb_buffer_t *buffer = c->buffer; - unsigned int mark_index = coverage_index; + unsigned int mark_index = (this+markCoverage).get_coverage (buffer->cur().codepoint); + if (likely (mark_index == NOT_COVERED)) return_trace (false); /* Now we search backwards for a non-mark glyph. * We don't use skippy_iter.prev() to avoid O(n^2) behavior. */ diff --git a/src/OT/Layout/GPOS/MarkLigPosFormat1.hh b/src/OT/Layout/GPOS/MarkLigPosFormat1.hh index 899000484..92e83a0e9 100644 --- a/src/OT/Layout/GPOS/MarkLigPosFormat1.hh +++ b/src/OT/Layout/GPOS/MarkLigPosFormat1.hh @@ -92,11 +92,12 @@ struct MarkLigPosFormat1_2 const Coverage &get_coverage () const { return this+markCoverage; } - bool apply (hb_ot_apply_context_t *c, unsigned coverage_index) const + bool apply (hb_ot_apply_context_t *c) const { TRACE_APPLY (this); hb_buffer_t *buffer = c->buffer; - unsigned int mark_index = coverage_index; + unsigned int mark_index = (this+markCoverage).get_coverage (buffer->cur().codepoint); + if (likely (mark_index == NOT_COVERED)) return_trace (false); /* Now we search backwards for a non-mark glyph */ diff --git a/src/OT/Layout/GPOS/MarkMarkPosFormat1.hh b/src/OT/Layout/GPOS/MarkMarkPosFormat1.hh index ecdfb71e4..9dae5ce5d 100644 --- a/src/OT/Layout/GPOS/MarkMarkPosFormat1.hh +++ b/src/OT/Layout/GPOS/MarkMarkPosFormat1.hh @@ -91,11 +91,12 @@ struct MarkMarkPosFormat1_2 const Coverage &get_coverage () const { return this+mark1Coverage; } - bool apply (hb_ot_apply_context_t *c, unsigned coverage_index) const + bool apply (hb_ot_apply_context_t *c) const { TRACE_APPLY (this); hb_buffer_t *buffer = c->buffer; - unsigned int mark1_index = coverage_index; + unsigned int mark1_index = (this+mark1Coverage).get_coverage (buffer->cur().codepoint); + if (likely (mark1_index == NOT_COVERED)) return_trace (false); /* now we search backwards for a suitable mark glyph until a non-mark glyph */ hb_ot_apply_context_t::skipping_iterator_t &skippy_iter = c->iter_input; diff --git a/src/OT/Layout/GPOS/PairPosFormat1.hh b/src/OT/Layout/GPOS/PairPosFormat1.hh index 60d0135ec..714b4bec7 100644 --- a/src/OT/Layout/GPOS/PairPosFormat1.hh +++ b/src/OT/Layout/GPOS/PairPosFormat1.hh @@ -102,10 +102,12 @@ struct PairPosFormat1_3 const Coverage &get_coverage () const { return this+coverage; } - bool apply (hb_ot_apply_context_t *c, unsigned coverage_index) const + bool apply (hb_ot_apply_context_t *c) const { TRACE_APPLY (this); hb_buffer_t *buffer = c->buffer; + unsigned int index = (this+coverage).get_coverage (buffer->cur().codepoint); + if (likely (index == NOT_COVERED)) return_trace (false); hb_ot_apply_context_t::skipping_iterator_t &skippy_iter = c->iter_input; skippy_iter.reset_fast (buffer->idx, 1); @@ -116,7 +118,7 @@ struct PairPosFormat1_3 return_trace (false); } - return_trace ((this+pairSet[coverage_index]).apply (c, valueFormat, skippy_iter.idx)); + return_trace ((this+pairSet[index]).apply (c, valueFormat, skippy_iter.idx)); } bool subset (hb_subset_context_t *c) const diff --git a/src/OT/Layout/GPOS/PairPosFormat2.hh b/src/OT/Layout/GPOS/PairPosFormat2.hh index 76f5309fe..31329dfcb 100644 --- a/src/OT/Layout/GPOS/PairPosFormat2.hh +++ b/src/OT/Layout/GPOS/PairPosFormat2.hh @@ -122,10 +122,12 @@ struct PairPosFormat2_4 const Coverage &get_coverage () const { return this+coverage; } - bool apply (hb_ot_apply_context_t *c, unsigned coverage_index) const + bool apply (hb_ot_apply_context_t *c) const { TRACE_APPLY (this); hb_buffer_t *buffer = c->buffer; + unsigned int index = (this+coverage).get_coverage (buffer->cur().codepoint); + if (likely (index == NOT_COVERED)) return_trace (false); hb_ot_apply_context_t::skipping_iterator_t &skippy_iter = c->iter_input; skippy_iter.reset_fast (buffer->idx, 1); diff --git a/src/OT/Layout/GPOS/PosLookup.hh b/src/OT/Layout/GPOS/PosLookup.hh index 4aef08075..c4e57bb54 100644 --- a/src/OT/Layout/GPOS/PosLookup.hh +++ b/src/OT/Layout/GPOS/PosLookup.hh @@ -20,10 +20,10 @@ struct PosLookup : Lookup return false; } - bool apply (hb_ot_apply_context_t *c, unsigned coverage_index) const + bool apply (hb_ot_apply_context_t *c) const { TRACE_APPLY (this); - return_trace (dispatch (c, coverage_index)); + return_trace (dispatch (c)); } bool intersects (const hb_set_t *glyphs) const diff --git a/src/OT/Layout/GPOS/SinglePosFormat1.hh b/src/OT/Layout/GPOS/SinglePosFormat1.hh index 5c3e105eb..623e4e66b 100644 --- a/src/OT/Layout/GPOS/SinglePosFormat1.hh +++ b/src/OT/Layout/GPOS/SinglePosFormat1.hh @@ -61,10 +61,12 @@ struct SinglePosFormat1 ValueFormat get_value_format () const { return valueFormat; } - bool apply (hb_ot_apply_context_t *c, unsigned coverage_index) const + bool apply (hb_ot_apply_context_t *c) const { TRACE_APPLY (this); hb_buffer_t *buffer = c->buffer; + unsigned int index = (this+coverage).get_coverage (buffer->cur().codepoint); + if (likely (index == NOT_COVERED)) return_trace (false); if (HB_BUFFER_MESSAGE_MORE && c->buffer->messaging ()) { diff --git a/src/OT/Layout/GPOS/SinglePosFormat2.hh b/src/OT/Layout/GPOS/SinglePosFormat2.hh index 3b82b9b05..e8f2d7c2c 100644 --- a/src/OT/Layout/GPOS/SinglePosFormat2.hh +++ b/src/OT/Layout/GPOS/SinglePosFormat2.hh @@ -61,12 +61,14 @@ struct SinglePosFormat2 ValueFormat get_value_format () const { return valueFormat; } - bool apply (hb_ot_apply_context_t *c, unsigned coverage_index) const + bool apply (hb_ot_apply_context_t *c) const { TRACE_APPLY (this); hb_buffer_t *buffer = c->buffer; + unsigned int index = (this+coverage).get_coverage (buffer->cur().codepoint); + if (likely (index == NOT_COVERED)) return_trace (false); - if (unlikely (coverage_index >= valueCount)) return_trace (false); + if (unlikely (index >= valueCount)) return_trace (false); if (HB_BUFFER_MESSAGE_MORE && c->buffer->messaging ()) { @@ -76,7 +78,7 @@ struct SinglePosFormat2 } valueFormat.apply_value (c, this, - &values[coverage_index * valueFormat.get_len ()], + &values[index * valueFormat.get_len ()], buffer->cur_pos()); if (HB_BUFFER_MESSAGE_MORE && c->buffer->messaging ()) diff --git a/src/OT/Layout/GSUB/AlternateSubstFormat1.hh b/src/OT/Layout/GSUB/AlternateSubstFormat1.hh index 94d123244..adec65d58 100644 --- a/src/OT/Layout/GSUB/AlternateSubstFormat1.hh +++ b/src/OT/Layout/GSUB/AlternateSubstFormat1.hh @@ -69,10 +69,14 @@ struct AlternateSubstFormat1_2 { return (this+alternateSet[(this+coverage).get_coverage (gid)]) .get_alternates (start_offset, alternate_count, alternate_glyphs); } - bool apply (hb_ot_apply_context_t *c, unsigned coverage_index) const + bool apply (hb_ot_apply_context_t *c) const { TRACE_APPLY (this); - return_trace ((this+alternateSet[coverage_index]).apply (c)); + + unsigned int index = (this+coverage).get_coverage (c->buffer->cur().codepoint); + if (likely (index == NOT_COVERED)) return_trace (false); + + return_trace ((this+alternateSet[index]).apply (c)); } bool serialize (hb_serialize_context_t *c, diff --git a/src/OT/Layout/GSUB/LigatureSubstFormat1.hh b/src/OT/Layout/GSUB/LigatureSubstFormat1.hh index a36212fe6..5c7df97d1 100644 --- a/src/OT/Layout/GSUB/LigatureSubstFormat1.hh +++ b/src/OT/Layout/GSUB/LigatureSubstFormat1.hh @@ -78,10 +78,14 @@ struct LigatureSubstFormat1_2 return lig_set.would_apply (c); } - bool apply (hb_ot_apply_context_t *c, unsigned coverage_index) const + bool apply (hb_ot_apply_context_t *c) const { TRACE_APPLY (this); - const auto &lig_set = this+ligatureSet[coverage_index]; + + unsigned int index = (this+coverage).get_coverage (c->buffer->cur ().codepoint); + if (likely (index == NOT_COVERED)) return_trace (false); + + const auto &lig_set = this+ligatureSet[index]; return_trace (lig_set.apply (c)); } diff --git a/src/OT/Layout/GSUB/MultipleSubstFormat1.hh b/src/OT/Layout/GSUB/MultipleSubstFormat1.hh index 0c4eff367..3b4bd1169 100644 --- a/src/OT/Layout/GSUB/MultipleSubstFormat1.hh +++ b/src/OT/Layout/GSUB/MultipleSubstFormat1.hh @@ -61,10 +61,14 @@ struct MultipleSubstFormat1_2 bool would_apply (hb_would_apply_context_t *c) const { return c->len == 1 && (this+coverage).get_coverage (c->glyphs[0]) != NOT_COVERED; } - bool apply (hb_ot_apply_context_t *c, unsigned coverage_index) const + bool apply (hb_ot_apply_context_t *c) const { TRACE_APPLY (this); - return_trace ((this+sequence[coverage_index]).apply (c)); + + unsigned int index = (this+coverage).get_coverage (c->buffer->cur().codepoint); + if (likely (index == NOT_COVERED)) return_trace (false); + + return_trace ((this+sequence[index]).apply (c)); } templatelen == 1 && (this+coverage).get_coverage (c->glyphs[0]) != NOT_COVERED; } - bool apply (hb_ot_apply_context_t *c, unsigned coverage_index) const + bool apply (hb_ot_apply_context_t *c) const { TRACE_APPLY (this); if (unlikely (c->nesting_level_left != HB_MAX_NESTING_LEVEL)) return_trace (false); /* No chaining to this type */ + unsigned int index = (this+coverage).get_coverage (c->buffer->cur ().codepoint); + if (likely (index == NOT_COVERED)) return_trace (false); + const auto &lookahead = StructAfter (backtrack); const auto &substitute = StructAfter (lookahead); - if (unlikely (coverage_index >= substitute.len)) return_trace (false); + if (unlikely (index >= substitute.len)) return_trace (false); unsigned int start_index = 0, end_index = 0; if (match_backtrack (c, @@ -136,7 +139,7 @@ struct ReverseChainSingleSubstFormat1 c->buffer->idx); } - c->replace_glyph_inplace (substitute[coverage_index]); + c->replace_glyph_inplace (substitute[index]); if (HB_BUFFER_MESSAGE_MORE && c->buffer->messaging ()) { diff --git a/src/OT/Layout/GSUB/SingleSubstFormat1.hh b/src/OT/Layout/GSUB/SingleSubstFormat1.hh index 622f8dce1..850be86c0 100644 --- a/src/OT/Layout/GSUB/SingleSubstFormat1.hh +++ b/src/OT/Layout/GSUB/SingleSubstFormat1.hh @@ -123,10 +123,12 @@ struct SingleSubstFormat1_3 return 1; } - bool apply (hb_ot_apply_context_t *c, unsigned coverage_index) const + bool apply (hb_ot_apply_context_t *c) const { TRACE_APPLY (this); hb_codepoint_t glyph_id = c->buffer->cur().codepoint; + unsigned int index = (this+coverage).get_coverage (glyph_id); + if (likely (index == NOT_COVERED)) return_trace (false); hb_codepoint_t d = deltaGlyphID; hb_codepoint_t mask = get_mask (); diff --git a/src/OT/Layout/GSUB/SingleSubstFormat2.hh b/src/OT/Layout/GSUB/SingleSubstFormat2.hh index 2429d9d5b..9c651abe7 100644 --- a/src/OT/Layout/GSUB/SingleSubstFormat2.hh +++ b/src/OT/Layout/GSUB/SingleSubstFormat2.hh @@ -100,11 +100,13 @@ struct SingleSubstFormat2_4 return 1; } - bool apply (hb_ot_apply_context_t *c, unsigned coverage_index) const + bool apply (hb_ot_apply_context_t *c) const { TRACE_APPLY (this); + unsigned int index = (this+coverage).get_coverage (c->buffer->cur().codepoint); + if (likely (index == NOT_COVERED)) return_trace (false); - if (unlikely (coverage_index >= substitute.len)) return_trace (false); + if (unlikely (index >= substitute.len)) return_trace (false); if (HB_BUFFER_MESSAGE_MORE && c->buffer->messaging ()) { @@ -114,7 +116,7 @@ struct SingleSubstFormat2_4 c->buffer->idx); } - c->replace_glyph (substitute[coverage_index]); + c->replace_glyph (substitute[index]); if (HB_BUFFER_MESSAGE_MORE && c->buffer->messaging ()) { diff --git a/src/OT/Layout/GSUB/SubstLookup.hh b/src/OT/Layout/GSUB/SubstLookup.hh index 75d969756..d49dcc0e0 100644 --- a/src/OT/Layout/GSUB/SubstLookup.hh +++ b/src/OT/Layout/GSUB/SubstLookup.hh @@ -35,10 +35,10 @@ struct SubstLookup : Lookup return dispatch (&c); } - bool apply (hb_ot_apply_context_t *c, unsigned coverage_index) const + bool apply (hb_ot_apply_context_t *c) const { TRACE_APPLY (this); - return_trace (dispatch (c, coverage_index)); + return_trace (dispatch (c)); } bool intersects (const hb_set_t *glyphs) const diff --git a/src/hb-ot-layout-gsubgpos.hh b/src/hb-ot-layout-gsubgpos.hh index 4ddd802da..8e5be92d1 100644 --- a/src/hb-ot-layout-gsubgpos.hh +++ b/src/hb-ot-layout-gsubgpos.hh @@ -680,7 +680,7 @@ struct hb_ot_apply_context_t : const char *get_name () { return "APPLY"; } typedef return_t (*recurse_func_t) (hb_ot_apply_context_t *c, unsigned int lookup_index); template - return_t dispatch (const T &obj, unsigned coverage_index) { return obj.apply (this, coverage_index); } + return_t dispatch (const T &obj) { return obj.apply (this); } static return_t default_return_value () { return false; } bool stop_sublookup_iteration (return_t r) const { return r; } return_t recurse (unsigned int sub_lookup_index) @@ -893,24 +893,22 @@ struct hb_accelerate_subtables_context_t : hb_dispatch_context_t { template - static inline bool apply_to (const void *obj, hb_ot_apply_context_t *c, unsigned coverage_index) + static inline bool apply_to (const void *obj, hb_ot_apply_context_t *c) { const Type *typed_obj = (const Type *) obj; - return typed_obj->apply (c, coverage_index); + return typed_obj->apply (c); } #ifndef HB_NO_OT_LAYOUT_LOOKUP_CACHE template - static inline auto apply_cached_ (const T *obj, hb_ot_apply_context_t *c, unsigned coverage_index, hb_priority<1>) - HB_RETURN (bool, obj->apply_cached (c, coverage_index) ) + static inline auto apply_cached_ (const T *obj, hb_ot_apply_context_t *c, hb_priority<1>) HB_RETURN (bool, obj->apply_cached (c) ) template - static inline auto apply_cached_ (const T *obj, hb_ot_apply_context_t *c, unsigned coverage_index, hb_priority<0>) - HB_RETURN (bool, obj->apply (c, coverage_index) ) + static inline auto apply_cached_ (const T *obj, hb_ot_apply_context_t *c, hb_priority<0>) HB_RETURN (bool, obj->apply (c) ) template - static inline bool apply_cached_to (const void *obj, hb_ot_apply_context_t *c, unsigned coverage_index) + static inline bool apply_cached_to (const void *obj, hb_ot_apply_context_t *c) { const Type *typed_obj = (const Type *) obj; - return apply_cached_ (typed_obj, c, coverage_index, hb_prioritize); + return apply_cached_ (typed_obj, c, hb_prioritize); } template @@ -925,7 +923,7 @@ struct hb_accelerate_subtables_context_t : } #endif - typedef bool (*hb_apply_func_t) (const void *obj, hb_ot_apply_context_t *c, unsigned coverage_index); + typedef bool (*hb_apply_func_t) (const void *obj, hb_ot_apply_context_t *c); typedef bool (*hb_cache_func_t) (const void *obj, hb_ot_apply_context_t *c, bool enter); struct hb_applicable_t @@ -950,22 +948,16 @@ struct hb_accelerate_subtables_context_t : #endif digest.init (); obj_.get_coverage ().collect_coverage (&digest); - coverage_map.init (); - auto &coverage = obj_.get_coverage (); - for (hb_codepoint_t g : hb_iter (coverage)) - coverage_map.set (g, coverage.get_coverage (g)); } bool apply (hb_ot_apply_context_t *c) const { - unsigned *v; - return coverage_map.has (c->buffer->cur().codepoint, &v) && apply_func (obj, c, *v); + return digest.may_have (c->buffer->cur().codepoint) && apply_func (obj, c); } #ifndef HB_NO_OT_LAYOUT_LOOKUP_CACHE bool apply_cached (hb_ot_apply_context_t *c) const { - unsigned *v; - return coverage_map.has (c->buffer->cur().codepoint, &v) && apply_cached_func (obj, c, *v); + return digest.may_have (c->buffer->cur().codepoint) && apply_cached_func (obj, c); } bool cache_enter (hb_ot_apply_context_t *c) const { @@ -985,7 +977,6 @@ struct hb_accelerate_subtables_context_t : hb_cache_func_t cache_func; #endif hb_set_digest_t digest; - hb_map_t coverage_map; }; #ifndef HB_NO_OT_LAYOUT_LOOKUP_CACHE @@ -2242,11 +2233,14 @@ struct ContextFormat1_4 const Coverage &get_coverage () const { return this+coverage; } - bool apply (hb_ot_apply_context_t *c, unsigned coverage_index) const + bool apply (hb_ot_apply_context_t *c) const { TRACE_APPLY (this); + unsigned int index = (this+coverage).get_coverage (c->buffer->cur().codepoint); + if (likely (index == NOT_COVERED)) + return_trace (false); - const RuleSet &rule_set = this+ruleSet[coverage_index]; + const RuleSet &rule_set = this+ruleSet[index]; struct ContextApplyLookupContext lookup_context = { {match_glyph}, nullptr @@ -2457,11 +2451,13 @@ struct ContextFormat2_5 } } - bool apply_cached (hb_ot_apply_context_t *c, unsigned coverage_index) const { return _apply (c, coverage_index, true); } - bool apply (hb_ot_apply_context_t *c, unsigned coverage_index) const { return _apply (c, coverage_index, false); } - bool _apply (hb_ot_apply_context_t *c, unsigned coverage_index, bool cached) const + bool apply_cached (hb_ot_apply_context_t *c) const { return _apply (c, true); } + bool apply (hb_ot_apply_context_t *c) const { return _apply (c, false); } + bool _apply (hb_ot_apply_context_t *c, bool cached) const { TRACE_APPLY (this); + unsigned int index = (this+coverage).get_coverage (c->buffer->cur().codepoint); + if (likely (index == NOT_COVERED)) return_trace (false); const ClassDef &class_def = this+classDef; @@ -2470,7 +2466,6 @@ struct ContextFormat2_5 &class_def }; - unsigned index; if (cached && c->buffer->cur().syllable() < 255) index = c->buffer->cur().syllable (); else @@ -2648,9 +2643,11 @@ struct ContextFormat3 const Coverage &get_coverage () const { return this+coverageZ[0]; } - bool apply (hb_ot_apply_context_t *c, unsigned coverage_index) const + bool apply (hb_ot_apply_context_t *c) const { TRACE_APPLY (this); + unsigned int index = (this+coverageZ[0]).get_coverage (c->buffer->cur().codepoint); + if (likely (index == NOT_COVERED)) return_trace (false); const LookupRecord *lookupRecord = &StructAfter (coverageZ.as_array (glyphCount)); struct ContextApplyLookupContext lookup_context = { @@ -3320,11 +3317,13 @@ struct ChainContextFormat1_4 const Coverage &get_coverage () const { return this+coverage; } - bool apply (hb_ot_apply_context_t *c, unsigned coverage_index) const + bool apply (hb_ot_apply_context_t *c) const { TRACE_APPLY (this); + unsigned int index = (this+coverage).get_coverage (c->buffer->cur().codepoint); + if (likely (index == NOT_COVERED)) return_trace (false); - const ChainRuleSet &rule_set = this+ruleSet[coverage_index]; + const ChainRuleSet &rule_set = this+ruleSet[index]; struct ChainContextApplyLookupContext lookup_context = { {{match_glyph, match_glyph, match_glyph}}, {nullptr, nullptr, nullptr} @@ -3557,11 +3556,13 @@ struct ChainContextFormat2_5 } } - bool apply_cached (hb_ot_apply_context_t *c, unsigned coverage_index) const { return _apply (c, coverage_index, true); } - bool apply (hb_ot_apply_context_t *c, unsigned coverage_index) const { return _apply (c, coverage_index, false); } - bool _apply (hb_ot_apply_context_t *c, unsigned coverage_index, bool cached) const + bool apply_cached (hb_ot_apply_context_t *c) const { return _apply (c, true); } + bool apply (hb_ot_apply_context_t *c) const { return _apply (c, false); } + bool _apply (hb_ot_apply_context_t *c, bool cached) const { TRACE_APPLY (this); + unsigned int index = (this+coverage).get_coverage (c->buffer->cur().codepoint); + if (likely (index == NOT_COVERED)) return_trace (false); const ClassDef &backtrack_class_def = this+backtrackClassDef; const ClassDef &input_class_def = this+inputClassDef; @@ -3586,7 +3587,7 @@ struct ChainContextFormat2_5 &lookahead_class_def} }; - unsigned index = input_class_def.get_class (c->buffer->cur().codepoint); + index = input_class_def.get_class (c->buffer->cur().codepoint); const ChainRuleSet &rule_set = this+ruleSet[index]; return_trace (rule_set.apply (c, lookup_context)); } @@ -3804,11 +3805,14 @@ struct ChainContextFormat3 return this+input[0]; } - bool apply (hb_ot_apply_context_t *c, unsigned coverage_index) const + bool apply (hb_ot_apply_context_t *c) const { TRACE_APPLY (this); const auto &input = StructAfter (backtrack); + unsigned int index = (this+input[0]).get_coverage (c->buffer->cur().codepoint); + if (likely (index == NOT_COVERED)) return_trace (false); + const auto &lookahead = StructAfter (input); const auto &lookup = StructAfter (lookahead); struct ChainContextApplyLookupContext lookup_context = {