[HarfBuzz] harfbuzz: Branch 'master' - 2 commits
Behdad Esfahbod
behdad at kemper.freedesktop.org
Thu Sep 13 18:32:51 UTC 2018
src/hb-open-file.hh | 30 ++++++++-------------
src/hb-open-type.hh | 58 ++++++++++++++++++++++++++++++++++++-----
src/hb-ot-layout-gsub-table.hh | 10 +++----
src/hb-ot-layout-gsubgpos.hh | 10 +++----
4 files changed, 73 insertions(+), 35 deletions(-)
New commits:
commit 3789c557ca06aef430726f4942cafecac6fe4eef
Author: Behdad Esfahbod <behdad at behdad.org>
Date: Thu Sep 13 20:30:04 2018 +0200
[dfont] Solve the mystery +2 offset thing!
Previously, ResourceForkHeader was defined as 30 bytes, having the typeCountM1 as last member.
There was a mysterious offset-by-2 in the code, derived from FontTools and JDK code this was
ported from.
In testing, I observed that typeListZ offset is actually 28. Suggesting that the typeCountM1
does NOT actually belong to ResourceForkHeader, but belongs to the array itself. Adjusting for
that resolves the mystery +2 offset hack, so everything is clean and good now.
This, concludes my dfont hacking. The code looks great now, and I'm happy to leave it.
Fuzzers might disagree though, we will see!
diff --git a/src/hb-open-file.hh b/src/hb-open-file.hh
index 5c653fed..cd7d78a3 100644
--- a/src/hb-open-file.hh
+++ b/src/hb-open-file.hh
@@ -357,13 +357,6 @@ struct ResourceTypeRecord
struct ResourceMap
{
- inline const ResourceTypeRecord& get_type_record (unsigned int i) const
- {
- // Why offset from the third byte of the object? I'm not sure
- return hb_array_t<ResourceTypeRecord> (((2 + (const char *) this )+typeListZ).arrayZ,
- get_type_count ()) [i];
- }
-
inline unsigned int get_face_count (void) const
{
unsigned int count = get_type_count ();
@@ -386,7 +379,7 @@ struct ResourceMap
/* The check for idx < count is here because ResourceRecord is NOT null-safe.
* Because an offset of 0 there does NOT mean null. */
if (type.is_sfnt () && idx < type.get_resource_count ())
- return type.get_resource_record (idx, &(this+typeListZ)).get_face (data_base);
+ return type.get_resource_record (idx, &(this+typeList)).get_face (data_base);
}
return Null (OpenTypeFontFace);
}
@@ -394,30 +387,31 @@ struct ResourceMap
inline bool sanitize (hb_sanitize_context_t *c, const void *data_base) const
{
TRACE_SANITIZE (this);
- const void *type_base = &(this+typeListZ);
+ const void *type_base = &(this+typeList);
return_trace (c->check_struct (this) &&
- typeListZ.sanitize (c, 2 + (const char *) this,
- get_type_count (),
- type_base,
- data_base));
+ typeList.sanitize (c, this,
+ type_base,
+ data_base));
}
private:
- inline unsigned int get_type_count (void) const { return typeCountM1 + 1; }
+ inline unsigned int get_type_count (void) const { return (this+typeList).lenM1 + 1; }
+
+ inline const ResourceTypeRecord& get_type_record (unsigned int i) const
+ { return (this+typeList)[i]; }
protected:
HBUINT8 reserved0[16]; /* Reserved for copy of resource header */
HBUINT32 reserved1; /* Reserved for handle to next resource map */
HBUINT16 resreved2; /* Reserved for file reference number */
HBUINT16 attrs; /* Resource fork attribute */
- OffsetTo<UnsizedArrayOf<ResourceTypeRecord> >
- typeListZ; /* Offset from beginning of map to
+ OffsetTo<ArrayOfM1<ResourceTypeRecord> >
+ typeList; /* Offset from beginning of map to
* resource type list */
Offset16 nameList; /* Offset from beginning of map to
* resource name list */
- HBUINT16 typeCountM1; /* Number of types in the map minus 1 */
public:
- DEFINE_SIZE_STATIC (30);
+ DEFINE_SIZE_STATIC (28);
};
struct ResourceForkHeader
diff --git a/src/hb-open-type.hh b/src/hb-open-type.hh
index 68079738..4f16c7d3 100644
--- a/src/hb-open-type.hh
+++ b/src/hb-open-type.hh
@@ -628,6 +628,50 @@ struct HeadlessArrayOf
DEFINE_SIZE_ARRAY (sizeof (LenType), arrayZ);
};
+/* An array storing length-1. */
+template <typename Type, typename LenType=HBUINT16>
+struct ArrayOfM1
+{
+ inline const Type& operator [] (unsigned int i) const
+ {
+ if (unlikely (i > lenM1)) return Null(Type);
+ return arrayZ[i];
+ }
+ inline Type& operator [] (unsigned int i)
+ {
+ if (unlikely (i > lenM1)) return Crap(Type);
+ return arrayZ[i];
+ }
+ inline unsigned int get_size (void) const
+ { return lenM1.static_size + (lenM1 + 1) * Type::static_size; }
+
+ template <typename T>
+ inline bool sanitize (hb_sanitize_context_t *c, const void *base, T user_data) const
+ {
+ TRACE_SANITIZE (this);
+ if (unlikely (!sanitize_shallow (c))) return_trace (false);
+ unsigned int count = lenM1 + 1;
+ for (unsigned int i = 0; i < count; i++)
+ if (unlikely (!arrayZ[i].sanitize (c, base, user_data)))
+ return_trace (false);
+ return_trace (true);
+ }
+
+ private:
+ inline bool sanitize_shallow (hb_sanitize_context_t *c) const
+ {
+ TRACE_SANITIZE (this);
+ return_trace (lenM1.sanitize (c) &&
+ (c->check_array (arrayZ, lenM1 + 1)));
+ }
+
+ public:
+ LenType lenM1;
+ Type arrayZ[VAR];
+ public:
+ DEFINE_SIZE_ARRAY (sizeof (LenType), arrayZ);
+};
+
/* An array with sorted elements. Supports binary searching. */
template <typename Type, typename LenType=HBUINT16>
struct SortedArrayOf : ArrayOf<Type, LenType>
commit effc7ced72a6ce0fea328a8b68dc3d55f09774f1
Author: Behdad Esfahbod <behdad at behdad.org>
Date: Thu Sep 13 20:21:54 2018 +0200
Rename HeadlessArrayOf::len to lenP1
So it doesn't accidentally match our templates, etc.
diff --git a/src/hb-open-type.hh b/src/hb-open-type.hh
index b10d33b1..68079738 100644
--- a/src/hb-open-type.hh
+++ b/src/hb-open-type.hh
@@ -570,16 +570,16 @@ struct HeadlessArrayOf
{
inline const Type& operator [] (unsigned int i) const
{
- if (unlikely (i >= len || !i)) return Null(Type);
+ if (unlikely (i >= lenP1 || !i)) return Null(Type);
return arrayZ[i-1];
}
inline Type& operator [] (unsigned int i)
{
- if (unlikely (i >= len || !i)) return Crap(Type);
+ if (unlikely (i >= lenP1 || !i)) return Crap(Type);
return arrayZ[i-1];
}
inline unsigned int get_size (void) const
- { return len.static_size + (len ? len - 1 : 0) * Type::static_size; }
+ { return lenP1.static_size + (lenP1 ? lenP1 - 1 : 0) * Type::static_size; }
inline bool serialize (hb_serialize_context_t *c,
Supplier<Type> &items,
@@ -587,7 +587,7 @@ struct HeadlessArrayOf
{
TRACE_SERIALIZE (this);
if (unlikely (!c->extend_min (*this))) return_trace (false);
- len.set (items_len); /* TODO(serialize) Overflow? */
+ lenP1.set (items_len); /* TODO(serialize) Overflow? */
if (unlikely (!items_len)) return_trace (true);
if (unlikely (!c->extend (*this))) return_trace (false);
for (unsigned int i = 0; i < items_len - 1; i++)
@@ -617,12 +617,12 @@ struct HeadlessArrayOf
inline bool sanitize_shallow (hb_sanitize_context_t *c) const
{
TRACE_SANITIZE (this);
- return_trace (len.sanitize (c) &&
- (!len || c->check_array (arrayZ, len - 1)));
+ return_trace (lenP1.sanitize (c) &&
+ (!lenP1 || c->check_array (arrayZ, lenP1 - 1)));
}
public:
- LenType len;
+ LenType lenP1;
Type arrayZ[VAR];
public:
DEFINE_SIZE_ARRAY (sizeof (LenType), arrayZ);
diff --git a/src/hb-ot-layout-gsub-table.hh b/src/hb-ot-layout-gsub-table.hh
index 4d5db6ae..7e36e063 100644
--- a/src/hb-ot-layout-gsub-table.hh
+++ b/src/hb-ot-layout-gsub-table.hh
@@ -710,7 +710,7 @@ struct Ligature
{
inline bool intersects (const hb_set_t *glyphs) const
{
- unsigned int count = component.len;
+ unsigned int count = component.lenP1;
for (unsigned int i = 1; i < count; i++)
if (!glyphs->has (component[i]))
return false;
@@ -720,7 +720,7 @@ struct Ligature
inline void closure (hb_closure_context_t *c) const
{
TRACE_CLOSURE (this);
- unsigned int count = component.len;
+ unsigned int count = component.lenP1;
for (unsigned int i = 1; i < count; i++)
if (!c->glyphs->has (component[i]))
return;
@@ -730,14 +730,14 @@ struct Ligature
inline void collect_glyphs (hb_collect_glyphs_context_t *c) const
{
TRACE_COLLECT_GLYPHS (this);
- c->input->add_array (component.arrayZ, component.len ? component.len - 1 : 0);
+ c->input->add_array (component.arrayZ, component.lenP1 ? component.lenP1 - 1 : 0);
c->output->add (ligGlyph);
}
inline bool would_apply (hb_would_apply_context_t *c) const
{
TRACE_WOULD_APPLY (this);
- if (c->len != component.len)
+ if (c->len != component.lenP1)
return_trace (false);
for (unsigned int i = 1; i < c->len; i++)
@@ -750,7 +750,7 @@ struct Ligature
inline bool apply (hb_ot_apply_context_t *c) const
{
TRACE_APPLY (this);
- unsigned int count = component.len;
+ unsigned int count = component.lenP1;
if (unlikely (!count)) return_trace (false);
diff --git a/src/hb-ot-layout-gsubgpos.hh b/src/hb-ot-layout-gsubgpos.hh
index eae73ce3..ff9783ed 100644
--- a/src/hb-ot-layout-gsubgpos.hh
+++ b/src/hb-ot-layout-gsubgpos.hh
@@ -1879,7 +1879,7 @@ struct ChainRule
const ArrayOf<HBUINT16> &lookahead = StructAfter<ArrayOf<HBUINT16> > (input);
return chain_context_intersects (glyphs,
backtrack.len, backtrack.arrayZ,
- input.len, input.arrayZ,
+ input.lenP1, input.arrayZ,
lookahead.len, lookahead.arrayZ,
lookup_context);
}
@@ -1892,7 +1892,7 @@ struct ChainRule
const ArrayOf<LookupRecord> &lookup = StructAfter<ArrayOf<LookupRecord> > (lookahead);
chain_context_closure_lookup (c,
backtrack.len, backtrack.arrayZ,
- input.len, input.arrayZ,
+ input.lenP1, input.arrayZ,
lookahead.len, lookahead.arrayZ,
lookup.len, lookup.arrayZ,
lookup_context);
@@ -1906,7 +1906,7 @@ struct ChainRule
const ArrayOf<LookupRecord> &lookup = StructAfter<ArrayOf<LookupRecord> > (lookahead);
chain_context_collect_glyphs_lookup (c,
backtrack.len, backtrack.arrayZ,
- input.len, input.arrayZ,
+ input.lenP1, input.arrayZ,
lookahead.len, lookahead.arrayZ,
lookup.len, lookup.arrayZ,
lookup_context);
@@ -1920,7 +1920,7 @@ struct ChainRule
const ArrayOf<LookupRecord> &lookup = StructAfter<ArrayOf<LookupRecord> > (lookahead);
return_trace (chain_context_would_apply_lookup (c,
backtrack.len, backtrack.arrayZ,
- input.len, input.arrayZ,
+ input.lenP1, input.arrayZ,
lookahead.len, lookahead.arrayZ, lookup.len,
lookup.arrayZ, lookup_context));
}
@@ -1933,7 +1933,7 @@ struct ChainRule
const ArrayOf<LookupRecord> &lookup = StructAfter<ArrayOf<LookupRecord> > (lookahead);
return_trace (chain_context_apply_lookup (c,
backtrack.len, backtrack.arrayZ,
- input.len, input.arrayZ,
+ input.lenP1, input.arrayZ,
lookahead.len, lookahead.arrayZ, lookup.len,
lookup.arrayZ, lookup_context));
}
More information about the HarfBuzz
mailing list