Add hhea-table support
diff --git a/src/Makefile.am b/src/Makefile.am
index 4ce5665..00f0101 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -32,6 +32,7 @@
 	hb-ot-tag.cc \
 	hb-private.hh \
 	hb-shape.cc \
+	hb-tt-font.cc \
 	hb-unicode-private.hh \
 	hb-unicode.cc \
 	$(NULL)
diff --git a/src/hb-open-type-private.hh b/src/hb-open-type-private.hh
index ae44ed7..8143b28 100644
--- a/src/hb-open-type-private.hh
+++ b/src/hb-open-type-private.hh
@@ -392,6 +392,12 @@
 typedef IntType<uint32_t> ULONG;	/* 32-bit unsigned integer. */
 typedef IntType<int32_t>  LONG;		/* 32-bit signed integer. */
 
+/* 16-bit signed integer (SHORT) that describes a quantity in FUnits. */
+typedef SHORT FWORD;
+
+/* 16-bit unsigned integer (USHORT) that describes a quantity in FUnits. */
+typedef USHORT UFWORD;
+
 /* Date represented in number of seconds since 12:00 midnight, January 1,
  * 1904. The value is represented as a signed 64-bit integer. */
 struct LONGDATETIME
diff --git a/src/hb-ot-head-table.hh b/src/hb-ot-head-table.hh
index a0624c1..a4d8d5f 100644
--- a/src/hb-ot-head-table.hh
+++ b/src/hb-ot-head-table.hh
@@ -32,7 +32,7 @@
 
 
 /*
- * head
+ * head -- Font Header
  */
 
 #define HB_OT_TAG_head HB_TAG('h','e','a','d')
diff --git a/src/hb-ot-hhea-table.hh b/src/hb-ot-hhea-table.hh
new file mode 100644
index 0000000..f7d0f86
--- /dev/null
+++ b/src/hb-ot-hhea-table.hh
@@ -0,0 +1,93 @@
+/*
+ * Copyright © 2011  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.
+ *
+ * Google Author(s): Behdad Esfahbod
+ */
+
+#ifndef HB_OT_HHEA_TABLE_HH
+#define HB_OT_HHEA_TABLE_HH
+
+#include "hb-open-type-private.hh"
+
+
+
+/*
+ * hhea -- The Horizontal Header Table
+ */
+
+#define HB_OT_TAG_hhea HB_TAG('h','h','e','a')
+
+
+struct hhea
+{
+  static const hb_tag_t Tag	= HB_OT_TAG_hhea;
+  /* TODO */
+
+  inline bool sanitize (hb_sanitize_context_t *c) {
+    TRACE_SANITIZE ();
+    return c->check_struct (this) && likely (version.major == 1);
+  }
+
+  private:
+  FixedVersion	version;		/* 0x00010000 for version 1.0. */
+  FWORD		ascender;		/* Typographic ascent. <a
+					 * href="http://developer.apple.com/fonts/TTRefMan/RM06/Chap6hhea.html">
+					 * (Distance from baseline of highest
+					 * ascender)</a> */
+  FWORD		descender;		/* Typographic descent. <a
+					 * href="http://developer.apple.com/fonts/TTRefMan/RM06/Chap6hhea.html">
+					 * (Distance from baseline of lowest
+					 * descender)</a> */
+  FWORD		lineGap;		/* Typographic line gap. Negative
+					 * LineGap values are treated as zero
+					 * in Windows 3.1, System 6, and
+					 * System 7. */
+  UFWORD	advanceWidthMax;	/* Maximum advance width value in
+					 * 'hmtx' table. */
+  FWORD		minLeftSideBearing;	/* Minimum left sidebearing value in
+					 * 'hmtx' table. */
+  FWORD		minRightSideBearing;	/* Minimum right sidebearing value;
+					 * calculated as Min(aw - lsb -
+					 * (xMax - xMin)). */
+  FWORD		xMaxExtent;		/* Max(lsb + (xMax - xMin)). */
+  SHORT		caretSlopeRise;		/* Used to calculate the slope of the
+					 * cursor (rise/run); 1 for vertical. */
+  SHORT		caretSlopeRun;		/* 0 for vertical. */
+  SHORT		caretOffset;		/* The amount by which a slanted
+					 * highlight on a glyph needs
+					 * to be shifted to produce the
+					 * best appearance. Set to 0 for
+					 * non--slanted fonts */
+  SHORT		reserved1;		/* set to 0 */
+  SHORT		reserved2;		/* set to 0 */
+  SHORT		reserved3;		/* set to 0 */
+  SHORT		reserved4;		/* set to 0 */
+  SHORT		metricDataFormat;	/* 0 for current format. */
+  USHORT	numberOfHMetrics;	/* Number of hMetric entries in 'hmtx'
+					 * table */
+  public:
+  DEFINE_SIZE_STATIC (36);
+};
+
+
+#endif /* HB_OT_HHEA_TABLE_HH */
diff --git a/src/hb-ot-layout-gdef-table.hh b/src/hb-ot-layout-gdef-table.hh
index a5b1e87..ee9c508 100644
--- a/src/hb-ot-layout-gdef-table.hh
+++ b/src/hb-ot-layout-gdef-table.hh
@@ -320,7 +320,7 @@
 
 
 /*
- * GDEF
+ * GDEF -- The Glyph Definition Table
  */
 
 struct GDEF
diff --git a/src/hb-ot-layout-gpos-table.hh b/src/hb-ot-layout-gpos-table.hh
index 987524c..cff1deb 100644
--- a/src/hb-ot-layout-gpos-table.hh
+++ b/src/hb-ot-layout-gpos-table.hh
@@ -1488,7 +1488,7 @@
 typedef OffsetListOf<PosLookup> PosLookupList;
 
 /*
- * GPOS
+ * GPOS -- The Glyph Positioning Table
  */
 
 struct GPOS : GSUBGPOS
diff --git a/src/hb-ot-layout-gsub-table.hh b/src/hb-ot-layout-gsub-table.hh
index 852f5f4..4f4c171 100644
--- a/src/hb-ot-layout-gsub-table.hh
+++ b/src/hb-ot-layout-gsub-table.hh
@@ -851,7 +851,7 @@
 typedef OffsetListOf<SubstLookup> SubstLookupList;
 
 /*
- * GSUB
+ * GSUB -- The Glyph Substitution Table
  */
 
 struct GSUB : GSUBGPOS
diff --git a/src/hb-ot-maxp-table.hh b/src/hb-ot-maxp-table.hh
index 6a9f8a4..c3ac1c2 100644
--- a/src/hb-ot-maxp-table.hh
+++ b/src/hb-ot-maxp-table.hh
@@ -32,7 +32,7 @@
 
 
 /*
- * maxp
+ * maxp -- The Maximum Profile Table
  */
 
 #define HB_OT_TAG_maxp HB_TAG('m','a','x','p')
diff --git a/src/hb-ot-name-table.hh b/src/hb-ot-name-table.hh
index 3fd2a17..9fad178 100644
--- a/src/hb-ot-name-table.hh
+++ b/src/hb-ot-name-table.hh
@@ -32,11 +32,12 @@
 
 
 /*
- * name
+ * name -- The Naming Table
  */
 
 #define HB_OT_TAG_name HB_TAG('n','a','m','e')
 
+
 struct NameRecord
 {
   static int cmp (const NameRecord *a, const NameRecord *b)
diff --git a/src/hb-tt-font.cc b/src/hb-tt-font.cc
new file mode 100644
index 0000000..4bca983
--- /dev/null
+++ b/src/hb-tt-font.cc
@@ -0,0 +1,207 @@
+/*
+ * Copyright © 2011  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.
+ *
+ * Google Author(s): Behdad Esfahbod
+ */
+
+#include "hb-open-type-private.hh"
+
+#include "hb-ot-hhea-table.hh"
+
+#include "hb-font-private.hh"
+#include "hb-blob.h"
+
+#include <string.h>
+
+
+
+/*
+ * hb_tt_font_funcs_t
+ */
+
+#if 0
+static hb_bool_t
+hb_font_get_glyph_nil (hb_font_t *font HB_UNUSED,
+		       void *font_data HB_UNUSED,
+		       hb_codepoint_t unicode,
+		       hb_codepoint_t variation_selector,
+		       hb_codepoint_t *glyph,
+		       void *user_data HB_UNUSED)
+{
+  if (font->parent)
+    return hb_font_get_glyph (font->parent, unicode, variation_selector, glyph);
+
+  *glyph = 0;
+  return FALSE;
+}
+
+static hb_position_t
+hb_font_get_glyph_h_advance_nil (hb_font_t *font HB_UNUSED,
+				 void *font_data HB_UNUSED,
+				 hb_codepoint_t glyph,
+				 void *user_data HB_UNUSED)
+{
+  if (font->parent)
+    return font->parent_scale_x_distance (hb_font_get_glyph_h_advance (font->parent, glyph));
+
+  return font->x_scale;
+}
+
+static hb_position_t
+hb_font_get_glyph_v_advance_nil (hb_font_t *font HB_UNUSED,
+				 void *font_data HB_UNUSED,
+				 hb_codepoint_t glyph,
+				 void *user_data HB_UNUSED)
+{
+  if (font->parent)
+    return font->parent_scale_y_distance (hb_font_get_glyph_v_advance (font->parent, glyph));
+
+  return font->y_scale;
+}
+
+static hb_bool_t
+hb_font_get_glyph_h_origin_nil (hb_font_t *font HB_UNUSED,
+				void *font_data HB_UNUSED,
+				hb_codepoint_t glyph,
+				hb_position_t *x,
+				hb_position_t *y,
+				void *user_data HB_UNUSED)
+{
+  if (font->parent) {
+    hb_bool_t ret = hb_font_get_glyph_h_origin (font->parent,
+						glyph,
+						x, y);
+    if (ret)
+      font->parent_scale_position (x, y);
+    return ret;
+  }
+
+  *x = *y = 0;
+  return FALSE;
+}
+
+static hb_bool_t
+hb_font_get_glyph_v_origin_nil (hb_font_t *font HB_UNUSED,
+				void *font_data HB_UNUSED,
+				hb_codepoint_t glyph,
+				hb_position_t *x,
+				hb_position_t *y,
+				void *user_data HB_UNUSED)
+{
+  if (font->parent) {
+    hb_bool_t ret = hb_font_get_glyph_v_origin (font->parent,
+						glyph,
+						x, y);
+    if (ret)
+      font->parent_scale_position (x, y);
+    return ret;
+  }
+
+  *x = *y = 0;
+  return FALSE;
+}
+
+static hb_position_t
+hb_font_get_glyph_h_kerning_nil (hb_font_t *font HB_UNUSED,
+				 void *font_data HB_UNUSED,
+				 hb_codepoint_t left_glyph,
+				 hb_codepoint_t right_glyph,
+				 void *user_data HB_UNUSED)
+{
+  if (font->parent)
+    return font->parent_scale_x_distance (hb_font_get_glyph_h_kerning (font->parent, left_glyph, right_glyph));
+
+  return 0;
+}
+
+static hb_position_t
+hb_font_get_glyph_v_kerning_nil (hb_font_t *font HB_UNUSED,
+				 void *font_data HB_UNUSED,
+				 hb_codepoint_t top_glyph,
+				 hb_codepoint_t bottom_glyph,
+				 void *user_data HB_UNUSED)
+{
+  if (font->parent)
+    return font->parent_scale_y_distance (hb_font_get_glyph_v_kerning (font->parent, top_glyph, bottom_glyph));
+
+  return 0;
+}
+
+static hb_bool_t
+hb_font_get_glyph_extents_nil (hb_font_t *font HB_UNUSED,
+			       void *font_data HB_UNUSED,
+			       hb_codepoint_t glyph,
+			       hb_glyph_extents_t *extents,
+			       void *user_data HB_UNUSED)
+{
+  if (font->parent) {
+    hb_bool_t ret = hb_font_get_glyph_extents (font->parent,
+					       glyph,
+					       extents);
+    if (ret) {
+      font->parent_scale_position (&extents->x_bearing, &extents->y_bearing);
+      font->parent_scale_distance (&extents->width, &extents->height);
+    }
+    return ret;
+  }
+
+  memset (extents, 0, sizeof (*extents));
+  return FALSE;
+}
+
+static hb_bool_t
+hb_font_get_glyph_contour_point_nil (hb_font_t *font HB_UNUSED,
+				     void *font_data HB_UNUSED,
+				     hb_codepoint_t glyph,
+				     unsigned int point_index,
+				     hb_position_t *x,
+				     hb_position_t *y,
+				     void *user_data HB_UNUSED)
+{
+  if (font->parent) {
+    hb_bool_t ret = hb_font_get_glyph_contour_point (font->parent,
+						     glyph, point_index,
+						     x, y);
+    if (ret)
+      font->parent_scale_position (x, y);
+    return ret;
+  }
+
+  *x = *y = 0;
+  return FALSE;
+}
+
+
+static hb_font_funcs_t _hb_font_funcs_nil = {
+  HB_OBJECT_HEADER_STATIC,
+
+  TRUE, /* immutable */
+
+  {
+#define HB_FONT_FUNC_IMPLEMENT(name) hb_font_get_##name##_nil,
+    HB_FONT_FUNCS_IMPLEMENT_CALLBACKS
+#undef HB_FONT_FUNC_IMPLEMENT
+  }
+};
+#endif
+