| Index: third_party/harfbuzz-ng/src/hb-ot-font.cc
|
| diff --git a/third_party/harfbuzz-ng/src/hb-ot-font.cc b/third_party/harfbuzz-ng/src/hb-ot-font.cc
|
| index 69d2503abbf5caf9f62133c68a5421c8a461b79a..8d3330070b18ba8b4fe8b20b75c0562209c99e2a 100644
|
| --- a/third_party/harfbuzz-ng/src/hb-ot-font.cc
|
| +++ b/third_party/harfbuzz-ng/src/hb-ot-font.cc
|
| @@ -46,11 +46,9 @@ struct hb_ot_face_metrics_accelerator_t
|
| hb_blob_t *blob;
|
|
|
| inline void init (hb_face_t *face,
|
| - hb_tag_t _hea_tag, hb_tag_t _mtx_tag,
|
| - unsigned int default_advance_)
|
| + hb_tag_t _hea_tag, hb_tag_t _mtx_tag)
|
| {
|
| - this->default_advance = default_advance_;
|
| - this->num_metrics = face->get_num_glyphs ();
|
| + this->default_advance = face->get_upem ();
|
|
|
| hb_blob_t *_hea_blob = OT::Sanitizer<OT::_hea>::sanitize (face->reference_table (_hea_tag));
|
| const OT::_hea *_hea = OT::Sanitizer<OT::_hea>::lock_instance (_hea_blob);
|
| @@ -58,8 +56,16 @@ struct hb_ot_face_metrics_accelerator_t
|
| hb_blob_destroy (_hea_blob);
|
|
|
| this->blob = OT::Sanitizer<OT::_mtx>::sanitize (face->reference_table (_mtx_tag));
|
| - if (unlikely (!this->num_advances ||
|
| - 2 * (this->num_advances + this->num_metrics) > hb_blob_get_length (this->blob)))
|
| +
|
| + /* Cap num_metrics() and num_advances() based on table length. */
|
| + unsigned int len = hb_blob_get_length (this->blob);
|
| + if (unlikely (this->num_advances * 4 > len))
|
| + this->num_advances = len / 4;
|
| + this->num_metrics = this->num_advances + (len - 4 * this->num_advances) / 2;
|
| +
|
| + /* We MUST set num_metrics to zero if num_advances is zero.
|
| + * Our get_advance() depends on that. */
|
| + if (unlikely (!this->num_advances))
|
| {
|
| this->num_metrics = this->num_advances = 0;
|
| hb_blob_destroy (this->blob);
|
| @@ -245,11 +251,9 @@ _hb_ot_font_create (hb_face_t *face)
|
| if (unlikely (!ot_font))
|
| return NULL;
|
|
|
| - unsigned int upem = face->get_upem ();
|
| -
|
| ot_font->cmap.init (face);
|
| - ot_font->h_metrics.init (face, HB_OT_TAG_hhea, HB_OT_TAG_hmtx, upem>>1);
|
| - ot_font->v_metrics.init (face, HB_OT_TAG_vhea, HB_OT_TAG_vmtx, upem); /* TODO Can we do this lazily? */
|
| + ot_font->h_metrics.init (face, HB_OT_TAG_hhea, HB_OT_TAG_hmtx);
|
| + ot_font->v_metrics.init (face, HB_OT_TAG_vhea, HB_OT_TAG_vmtx); /* TODO Can we do this lazily? */
|
| ot_font->glyf.init (face);
|
|
|
| return ot_font;
|
| @@ -301,52 +305,6 @@ hb_ot_get_glyph_v_advance (hb_font_t *font HB_UNUSED,
|
| }
|
|
|
| static hb_bool_t
|
| -hb_ot_get_glyph_h_origin (hb_font_t *font HB_UNUSED,
|
| - void *font_data HB_UNUSED,
|
| - hb_codepoint_t glyph HB_UNUSED,
|
| - hb_position_t *x HB_UNUSED,
|
| - hb_position_t *y HB_UNUSED,
|
| - void *user_data HB_UNUSED)
|
| -{
|
| - /* We always work in the horizontal coordinates. */
|
| - return true;
|
| -}
|
| -
|
| -static hb_bool_t
|
| -hb_ot_get_glyph_v_origin (hb_font_t *font HB_UNUSED,
|
| - void *font_data,
|
| - hb_codepoint_t glyph,
|
| - hb_position_t *x,
|
| - hb_position_t *y,
|
| - void *user_data HB_UNUSED)
|
| -{
|
| - /* TODO */
|
| - return false;
|
| -}
|
| -
|
| -static hb_position_t
|
| -hb_ot_get_glyph_h_kerning (hb_font_t *font,
|
| - void *font_data,
|
| - hb_codepoint_t left_glyph,
|
| - hb_codepoint_t right_glyph,
|
| - void *user_data HB_UNUSED)
|
| -{
|
| - /* TODO */
|
| - return 0;
|
| -}
|
| -
|
| -static hb_position_t
|
| -hb_ot_get_glyph_v_kerning (hb_font_t *font HB_UNUSED,
|
| - void *font_data HB_UNUSED,
|
| - hb_codepoint_t top_glyph HB_UNUSED,
|
| - hb_codepoint_t bottom_glyph HB_UNUSED,
|
| - void *user_data HB_UNUSED)
|
| -{
|
| - /* OpenType doesn't have vertical-kerning other than GPOS. */
|
| - return 0;
|
| -}
|
| -
|
| -static hb_bool_t
|
| hb_ot_get_glyph_extents (hb_font_t *font HB_UNUSED,
|
| void *font_data,
|
| hb_codepoint_t glyph,
|
| @@ -362,58 +320,52 @@ hb_ot_get_glyph_extents (hb_font_t *font HB_UNUSED,
|
| return ret;
|
| }
|
|
|
| -static hb_bool_t
|
| -hb_ot_get_glyph_contour_point (hb_font_t *font HB_UNUSED,
|
| - void *font_data,
|
| - hb_codepoint_t glyph,
|
| - unsigned int point_index,
|
| - hb_position_t *x,
|
| - hb_position_t *y,
|
| - void *user_data HB_UNUSED)
|
| -{
|
| - /* TODO */
|
| - return false;
|
| -}
|
|
|
| -static hb_bool_t
|
| -hb_ot_get_glyph_name (hb_font_t *font HB_UNUSED,
|
| - void *font_data,
|
| - hb_codepoint_t glyph,
|
| - char *name, unsigned int size,
|
| - void *user_data HB_UNUSED)
|
| -{
|
| - /* TODO */
|
| - return false;
|
| -}
|
| +static hb_font_funcs_t *static_ot_funcs = NULL;
|
|
|
| -static hb_bool_t
|
| -hb_ot_get_glyph_from_name (hb_font_t *font HB_UNUSED,
|
| - void *font_data,
|
| - const char *name, int len, /* -1 means nul-terminated */
|
| - hb_codepoint_t *glyph,
|
| - void *user_data HB_UNUSED)
|
| +#ifdef HB_USE_ATEXIT
|
| +static
|
| +void free_static_ot_funcs (void)
|
| {
|
| - /* TODO */
|
| - return false;
|
| + hb_font_funcs_destroy (static_ot_funcs);
|
| }
|
| -
|
| +#endif
|
|
|
| static hb_font_funcs_t *
|
| _hb_ot_get_font_funcs (void)
|
| {
|
| - static const hb_font_funcs_t ot_ffuncs = {
|
| - HB_OBJECT_HEADER_STATIC,
|
| +retry:
|
| + hb_font_funcs_t *funcs = (hb_font_funcs_t *) hb_atomic_ptr_get (&static_ot_funcs);
|
|
|
| - true, /* immutable */
|
| -
|
| - {
|
| -#define HB_FONT_FUNC_IMPLEMENT(name) hb_ot_get_##name,
|
| - HB_FONT_FUNCS_IMPLEMENT_CALLBACKS
|
| -#undef HB_FONT_FUNC_IMPLEMENT
|
| + if (unlikely (!funcs))
|
| + {
|
| + funcs = hb_font_funcs_create ();
|
| +
|
| + hb_font_funcs_set_glyph_func (funcs, hb_ot_get_glyph, NULL, NULL);
|
| + hb_font_funcs_set_glyph_h_advance_func (funcs, hb_ot_get_glyph_h_advance, NULL, NULL);
|
| + hb_font_funcs_set_glyph_v_advance_func (funcs, hb_ot_get_glyph_v_advance, NULL, NULL);
|
| + //hb_font_funcs_set_glyph_h_origin_func (funcs, hb_ot_get_glyph_h_origin, NULL, NULL);
|
| + //hb_font_funcs_set_glyph_v_origin_func (funcs, hb_ot_get_glyph_v_origin, NULL, NULL);
|
| + //hb_font_funcs_set_glyph_h_kerning_func (funcs, hb_ot_get_glyph_h_kerning, NULL, NULL); TODO
|
| + //hb_font_funcs_set_glyph_v_kerning_func (funcs, hb_ot_get_glyph_v_kerning, NULL, NULL);
|
| + hb_font_funcs_set_glyph_extents_func (funcs, hb_ot_get_glyph_extents, NULL, NULL);
|
| + //hb_font_funcs_set_glyph_contour_point_func (funcs, hb_ot_get_glyph_contour_point, NULL, NULL); TODO
|
| + //hb_font_funcs_set_glyph_name_func (funcs, hb_ot_get_glyph_name, NULL, NULL); TODO
|
| + //hb_font_funcs_set_glyph_from_name_func (funcs, hb_ot_get_glyph_from_name, NULL, NULL); TODO
|
| +
|
| + hb_font_funcs_make_immutable (funcs);
|
| +
|
| + if (!hb_atomic_ptr_cmpexch (&static_ot_funcs, NULL, funcs)) {
|
| + hb_font_funcs_destroy (funcs);
|
| + goto retry;
|
| }
|
| +
|
| +#ifdef HB_USE_ATEXIT
|
| + atexit (free_static_ot_funcs); /* First person registers atexit() callback. */
|
| +#endif
|
| };
|
|
|
| - return const_cast<hb_font_funcs_t *> (&ot_ffuncs);
|
| + return funcs;
|
| }
|
|
|
|
|
|
|